Selaa lähdekoodia

Replace forbidden chars in more places in the GAS assembler writer.
Add support for .set and .weak on AVR.
Fix 64 bit negation on AVR.
Add cpu_capabilities to cpuinfo.pas and fixed some peephole optimizations.
Pass >4 byte parameters by reference.

git-svn-id: trunk@26943 -

Jeppe Johansen 11 vuotta sitten
vanhempi
commit
2227045e23

+ 8 - 2
compiler/aggas.pas

@@ -1352,11 +1352,17 @@ implementation
 {$endif arm}
 {$endif arm}
            ait_set:
            ait_set:
              begin
              begin
-               AsmWriteLn(#9'.set '+tai_set(hp).sym^+', '+tai_set(hp).value^);
+               if replaceforbidden then
+                 AsmWriteLn(#9'.set '+ReplaceForbiddenAsmSymbolChars(tai_set(hp).sym^)+', '+ReplaceForbiddenAsmSymbolChars(tai_set(hp).value^))
+               else
+                 AsmWriteLn(#9'.set '+tai_set(hp).sym^+', '+tai_set(hp).value^);
              end;
              end;
            ait_weak:
            ait_weak:
              begin
              begin
-               AsmWriteLn(#9'.weak '+tai_weak(hp).sym^);
+               if replaceforbidden then
+                 AsmWriteLn(#9'.weak '+ReplaceForbiddenAsmSymbolChars(tai_weak(hp).sym^))
+               else
+                 AsmWriteLn(#9'.weak '+tai_weak(hp).sym^);
              end;
              end;
            ait_symbol_end :
            ait_symbol_end :
              begin
              begin

+ 2 - 0
compiler/avr/aasmcpu.pas

@@ -420,6 +420,8 @@ implementation
                       end;
                       end;
                     ait_align:
                     ait_align:
                       inc(CurrOffset,tai_align(curtai).aligntype);
                       inc(CurrOffset,tai_align(curtai).aligntype);
+                    ait_weak,
+                    ait_set,
                     ait_marker:
                     ait_marker:
                       ;
                       ;
                     ait_label:
                     ait_label:

+ 3 - 1
compiler/avr/aoptcpu.pas

@@ -42,6 +42,7 @@ Type
 Implementation
 Implementation
 
 
   uses
   uses
+    cpuinfo,
     aasmbase,aasmcpu,
     aasmbase,aasmcpu,
     globals,globtype;
     globals,globtype;
 
 
@@ -275,7 +276,8 @@ Implementation
                     to
                     to
                     movw reg2,reg0
                     movw reg2,reg0
                   }
                   }
-                  else if (taicpu(p).ops=2) and
+                  else if (CPUAVR_HAS_MOVW in cpu_capabilities[current_settings.cputype]) and
+                     (taicpu(p).ops=2) and
                      (taicpu(p).oper[0]^.typ = top_reg) and
                      (taicpu(p).oper[0]^.typ = top_reg) and
                      (taicpu(p).oper[1]^.typ = top_reg) and
                      (taicpu(p).oper[1]^.typ = top_reg) and
                      getnextinstruction(p,hp1) and
                      getnextinstruction(p,hp1) and

+ 33 - 11
compiler/avr/cgcpu.pas

@@ -226,7 +226,7 @@ unit cgcpu;
         end;
         end;
 
 
       var
       var
-        i : longint;
+        i, i2 : longint;
         hp : PCGParaLocation;
         hp : PCGParaLocation;
 
 
       begin
       begin
@@ -277,15 +277,29 @@ unit cgcpu;
 
 
             hp:=cgpara.location;
             hp:=cgpara.location;
 
 
-            for i:=1 to tcgsize2size[cgpara.Size] do
+            i:=0;
+            while i<tcgsize2size[cgpara.Size] do
               begin
               begin
-                if not(assigned(hp)) or
-                  (tcgsize2size[hp^.size]<>1) or
-                  (hp^.shiftval<>0) then
+                if not(assigned(hp)) then
                   internalerror(2014011102);
                   internalerror(2014011102);
-                load_para_loc(r,hp);
-                hp:=hp^.Next;
-                r:=GetNextReg(r);
+
+                inc(i, tcgsize2size[hp^.Size]);
+
+                if hp^.Loc=LOC_REGISTER then
+                  begin
+                    load_para_loc(r,hp);
+                    hp:=hp^.Next;
+                    r:=GetNextReg(r);
+                  end
+                else
+                  begin
+                    load_para_loc(r,hp);
+
+                    for i2:=1 to tcgsize2size[hp^.Size] do
+                      r:=GetNextReg(r);
+
+                    hp:=hp^.Next;
+                  end;
               end;
               end;
             if assigned(hp) then
             if assigned(hp) then
               internalerror(2014011103);
               internalerror(2014011103);
@@ -485,7 +499,15 @@ unit cgcpu;
            OP_NEG:
            OP_NEG:
              begin
              begin
                if src<>dst then
                if src<>dst then
-                 a_load_reg_reg(list,size,size,src,dst);
+                 begin
+                   if size in [OS_S64,OS_64] then
+                     begin
+                       a_load_reg_reg(list,OS_32,OS_32,src,dst);
+                       a_load_reg_reg(list,OS_32,OS_32,srchi,dsthi);
+                     end
+                   else
+                     a_load_reg_reg(list,size,size,src,dst);
+                 end;
 
 
                if size in [OS_S16,OS_16,OS_S32,OS_32,OS_S64,OS_64] then
                if size in [OS_S16,OS_16,OS_S32,OS_32,OS_S64,OS_64] then
                  begin
                  begin
@@ -499,7 +521,7 @@ unit cgcpu;
                    tmpreg:=GetNextReg(dst);
                    tmpreg:=GetNextReg(dst);
                    for i:=2 to tcgsize2size[size] do
                    for i:=2 to tcgsize2size[size] do
                      begin
                      begin
-                       list.concat(taicpu.op_reg_const(A_SBCI,dst,-1));
+                       list.concat(taicpu.op_reg_const(A_SBCI,tmpreg,-1));
                        NextTmp;
                        NextTmp;
                    end;
                    end;
                  end;
                  end;
@@ -1869,7 +1891,7 @@ unit cgcpu;
 
 
     procedure tcgavr.g_intf_wrapper(list: TAsmList; procdef: tprocdef; const labelname: string; ioffset: longint);
     procedure tcgavr.g_intf_wrapper(list: TAsmList; procdef: tprocdef; const labelname: string; ioffset: longint);
       begin
       begin
-        internalerror(2011021324);
+        //internalerror(2011021324);
       end;
       end;
 
 
 
 

+ 10 - 10
compiler/avr/cpuinfo.pas

@@ -194,16 +194,16 @@ Const
  const
  const
    cpu_capabilities : array[tcputype] of set of tcpuflags =
    cpu_capabilities : array[tcputype] of set of tcpuflags =
      ( { cpu_none } [],
      ( { cpu_none } [],
-       { cpu_avr1 } [],
-       { cpu_avr2 } [],
-       { cpu_avr25 } [],
-       { cpu_avr3 } [],
-       { cpu_avr31 } [],
-       { cpu_avr35 } [],
-       { cpu_avr4 } [],
-       { cpu_avr5 } [],
-       { cpu_avr51 } [],
-       { cpu_avr6 } []
+       { cpu_avr1 } [CPUAVR_2_BYTE_PC],
+       { cpu_avr2 } [CPUAVR_2_BYTE_PC],
+       { cpu_avr25 } [CPUAVR_HAS_MOVW,CPUAVR_HAS_LPMX,CPUAVR_2_BYTE_PC],
+       { cpu_avr3 } [CPUAVR_HAS_JMP_CALL,CPUAVR_2_BYTE_PC],
+       { cpu_avr31 } [CPUAVR_HAS_JMP_CALL,CPUAVR_HAS_RAMPZ,CPUAVR_HAS_ELPM,CPUAVR_2_BYTE_PC],
+       { cpu_avr35 } [CPUAVR_HAS_JMP_CALL,CPUAVR_HAS_MOVW,CPUAVR_HAS_LPMX,CPUAVR_2_BYTE_PC],
+       { cpu_avr4 } [CPUAVR_HAS_MOVW,CPUAVR_HAS_LPMX,CPUAVR_HAS_MUL,CPUAVR_2_BYTE_PC],
+       { cpu_avr5 } [CPUAVR_HAS_JMP_CALL,CPUAVR_HAS_MOVW,CPUAVR_HAS_LPMX,CPUAVR_HAS_MUL,CPUAVR_2_BYTE_PC],
+       { cpu_avr51 } [CPUAVR_HAS_JMP_CALL,CPUAVR_HAS_MOVW,CPUAVR_HAS_LPMX,CPUAVR_HAS_MUL,CPUAVR_HAS_RAMPZ,CPUAVR_HAS_ELPM,CPUAVR_HAS_ELPMX,CPUAVR_2_BYTE_PC],
+       { cpu_avr6 } [CPUAVR_HAS_JMP_CALL,CPUAVR_HAS_MOVW,CPUAVR_HAS_LPMX,CPUAVR_HAS_MUL,CPUAVR_HAS_RAMPZ,CPUAVR_HAS_ELPM,CPUAVR_HAS_ELPMX,CPUAVR_3_BYTE_PC]
      );
      );
 
 
 Implementation
 Implementation

+ 2 - 0
compiler/avr/cpupara.pas

@@ -141,6 +141,8 @@ unit cpupara;
             result:=not is_smallset(def);
             result:=not is_smallset(def);
           stringdef :
           stringdef :
             result:=tstringdef(def).stringtype in [st_shortstring,st_longstring];
             result:=tstringdef(def).stringtype in [st_shortstring,st_longstring];
+        else
+          result:=def.size>4;
         end;
         end;
       end;
       end;
 
 

+ 2 - 2
compiler/ncgutil.pas

@@ -994,7 +994,7 @@ implementation
                     LOC_REGISTER:
                     LOC_REGISTER:
                       begin
                       begin
                         case para.locations_count of
                         case para.locations_count of
-{$ifdef cpu16bitalu}
+{$if defined(cpu16bitalu) or defined(cpu8bitalu)}
                           { 4 paralocs? }
                           { 4 paralocs? }
                           4:
                           4:
                             if (target_info.endian=ENDIAN_BIG) then
                             if (target_info.endian=ENDIAN_BIG) then
@@ -1026,7 +1026,7 @@ implementation
                                 unget_para(paraloc^.next^.next^.next^);
                                 unget_para(paraloc^.next^.next^.next^);
                                 cg.a_load_cgparaloc_anyreg(list,OS_16,paraloc^.next^.next^.next^,GetNextReg(destloc.register64.reghi),2);
                                 cg.a_load_cgparaloc_anyreg(list,OS_16,paraloc^.next^.next^.next^,GetNextReg(destloc.register64.reghi),2);
                               end;
                               end;
-{$endif cpu16bitalu}
+{$endif defined(cpu16bitalu) or defined(cpu8bitalu)}
                           2:
                           2:
                             if (target_info.endian=ENDIAN_BIG) then
                             if (target_info.endian=ENDIAN_BIG) then
                               begin
                               begin