diff --git a/compiler/z80/cgcpu.pas b/compiler/z80/cgcpu.pas
index cab2f7bf87..ed45ba87d7 100644
--- a/compiler/z80/cgcpu.pas
+++ b/compiler/z80/cgcpu.pas
@@ -98,8 +98,7 @@ unit cgcpu;
 
         procedure a_jmp_cond(list : TAsmList;cond : TOpCmp;l: tasmlabel);
         procedure fixref(list : TAsmList;var ref : treference);
-        function normalize_ref(list : TAsmList;ref : treference;
-          tmpreg : tregister) : treference;
+        function normalize_ref(list : TAsmList;ref : treference; const refopertypes:trefoperandtypes) : treference;
 
         procedure emit_mov(list: TAsmList;reg2: tregister; reg1: tregister);
 
@@ -1189,112 +1188,66 @@ unit cgcpu;
       end;
 
 
-    function tcgz80.normalize_ref(list:TAsmList;ref: treference;tmpreg : tregister) : treference;
-
+    function tcgz80.normalize_ref(list: TAsmList; ref: treference; const refopertypes: trefoperandtypes): treference;
       var
         tmpref : treference;
         l : tasmlabel;
       begin
-        Result:=ref;
-//
-//         if ref.addressmode<>AM_UNCHANGED then
-//           internalerror(2011021701);
-//
-//        { Be sure to have a base register }
-//        if (ref.base=NR_NO) then
-//          begin
-//            { only symbol+offset? }
-//            if ref.index=NR_NO then
-//              exit;
-//            ref.base:=ref.index;
-//            ref.index:=NR_NO;
-//          end;
-//
-//        { can we take advantage of adiw/sbiw? }
-//        if (current_settings.cputype>=cpu_avr2) and not(assigned(ref.symbol)) and (ref.offset<>0) and (ref.offset>=-63) and (ref.offset<=63) and
-//          ((tmpreg=NR_R24) or (tmpreg=NR_R26) or (tmpreg=NR_R28) or (tmpreg=NR_R30)) and (ref.base<>NR_NO) then
-//          begin
-//            maybegetcpuregister(list,tmpreg);
-//            emit_mov(list,tmpreg,ref.base);
-//            maybegetcpuregister(list,GetNextReg(tmpreg));
-//            emit_mov(list,GetNextReg(tmpreg),GetNextReg(ref.base));
-//            if ref.index<>NR_NO then
-//              begin
-//                list.concat(taicpu.op_reg_reg(A_ADD,tmpreg,ref.index));
-//                list.concat(taicpu.op_reg_reg(A_ADC,GetNextReg(tmpreg),GetNextReg(ref.index)));
-//              end;
-//            if ref.offset>0 then
-//              list.concat(taicpu.op_reg_const(A_ADIW,tmpreg,ref.offset))
-//            else
-//              list.concat(taicpu.op_reg_const(A_SBIW,tmpreg,-ref.offset));
-//            ref.offset:=0;
-//            ref.base:=tmpreg;
-//            ref.index:=NR_NO;
-//          end
-//        else if assigned(ref.symbol) or (ref.offset<>0) then
-//          begin
-//            reference_reset(tmpref,0,[]);
-//            tmpref.symbol:=ref.symbol;
-//            tmpref.offset:=ref.offset;
-//            if assigned(ref.symbol) and (ref.symbol.typ in [AT_FUNCTION,AT_LABEL]) then
-//              tmpref.refaddr:=addr_lo8_gs
-//            else
-//              tmpref.refaddr:=addr_lo8;
-//            maybegetcpuregister(list,tmpreg);
-//            list.concat(taicpu.op_reg_ref(A_LDI,tmpreg,tmpref));
-//
-//            if assigned(ref.symbol) and (ref.symbol.typ in [AT_FUNCTION,AT_LABEL]) then
-//              tmpref.refaddr:=addr_hi8_gs
-//            else
-//              tmpref.refaddr:=addr_hi8;
-//            maybegetcpuregister(list,GetNextReg(tmpreg));
-//            list.concat(taicpu.op_reg_ref(A_LDI,GetNextReg(tmpreg),tmpref));
-//
-//            if (ref.base<>NR_NO) then
-//              begin
-//                list.concat(taicpu.op_reg_reg(A_ADD,tmpreg,ref.base));
-//                list.concat(taicpu.op_reg_reg(A_ADC,GetNextReg(tmpreg),GetNextReg(ref.base)));
-//              end;
-//            if (ref.index<>NR_NO) then
-//              begin
-//                list.concat(taicpu.op_reg_reg(A_ADD,tmpreg,ref.index));
-//                list.concat(taicpu.op_reg_reg(A_ADC,GetNextReg(tmpreg),GetNextReg(ref.index)));
-//              end;
-//            ref.symbol:=nil;
-//            ref.offset:=0;
-//            ref.base:=tmpreg;
-//            ref.index:=NR_NO;
-//          end
-//        else if (ref.base<>NR_NO) and (ref.index<>NR_NO) then
-//          begin
-//            maybegetcpuregister(list,tmpreg);
-//            emit_mov(list,tmpreg,ref.base);
-//            maybegetcpuregister(list,GetNextReg(tmpreg));
-//            emit_mov(list,GetNextReg(tmpreg),GetNextReg(ref.base));
-//            list.concat(taicpu.op_reg_reg(A_ADD,tmpreg,ref.index));
-//            list.concat(taicpu.op_reg_reg(A_ADC,GetNextReg(tmpreg),GetNextReg(ref.index)));
-//            ref.base:=tmpreg;
-//            ref.index:=NR_NO;
-//          end
-//        else if (ref.base<>NR_NO) then
-//          begin
-//            maybegetcpuregister(list,tmpreg);
-//            emit_mov(list,tmpreg,ref.base);
-//            maybegetcpuregister(list,GetNextReg(tmpreg));
-//            emit_mov(list,GetNextReg(tmpreg),GetNextReg(ref.base));
-//            ref.base:=tmpreg;
-//            ref.index:=NR_NO;
-//          end
-//        else if (ref.index<>NR_NO) then
-//          begin
-//            maybegetcpuregister(list,tmpreg);
-//            emit_mov(list,tmpreg,ref.index);
-//            maybegetcpuregister(list,GetNextReg(tmpreg));
-//            emit_mov(list,GetNextReg(tmpreg),GetNextReg(ref.index));
-//            ref.base:=tmpreg;
-//            ref.index:=NR_NO;
-//          end;
-        Result:=ref;
+        if (ref.base=NR_NO) and (ref.index<>NR_NO) and (ref.scalefactor<=1) then
+          begin
+            ref.base:=ref.index;
+            ref.index:=NR_NO;
+          end;
+
+        if is_ref_in_opertypes(ref,refopertypes) then
+          begin
+            Result:=ref;
+            exit;
+          end;
+
+        { can we use the HL register? }
+        if OT_REF_HL in refopertypes then
+          begin
+            getcpuregister(list,NR_H);
+            getcpuregister(list,NR_L);
+            if assigned(ref.symbol) then
+              begin
+                reference_reset(tmpref,0,[]);
+                tmpref.symbol:=ref.symbol;
+                tmpref.offset:=ref.offset;
+
+                tmpref.refaddr:=addr_full;
+                list.concat(taicpu.op_reg_ref(A_LD,NR_HL,tmpref));
+              end
+            else
+              list.concat(taicpu.op_reg_const(A_LD,NR_HL,ref.offset));
+            if ref.base<>NR_NO then
+              begin
+                getcpuregister(list,NR_A);
+                emit_mov(list,NR_A,NR_L);
+                list.concat(taicpu.op_reg_reg(A_ADD,NR_A,ref.base));
+                emit_mov(list,NR_L,NR_A);
+                emit_mov(list,NR_A,NR_H);
+                list.concat(taicpu.op_reg_reg(A_ADC,NR_A,GetNextReg(ref.base)));
+                emit_mov(list,NR_H,NR_A);
+                ungetcpuregister(list,NR_A);
+              end;
+            if ref.index<>NR_NO then
+              begin
+                if ref.scalefactor>1 then
+                  internalerror(2020042002);
+                getcpuregister(list,NR_A);
+                emit_mov(list,NR_A,NR_L);
+                list.concat(taicpu.op_reg_reg(A_ADD,NR_A,ref.index));
+                emit_mov(list,NR_L,NR_A);
+                emit_mov(list,NR_A,NR_H);
+                list.concat(taicpu.op_reg_reg(A_ADC,NR_A,GetNextReg(ref.index)));
+                emit_mov(list,NR_H,NR_A);
+                ungetcpuregister(list,NR_A);
+              end;
+          end
+        else
+          internalerror(2020042001);
       end;