Browse Source

+ support for the ARM hard float EABI on Linux (patch by Peter Green):
o new eabihf (hard float) abi
o vfpv3_d16 variant of VFP (default variant used by EABI assemblers: VFPv3
with only 16 double registers instead of 32) and pass it to GNU as
o make the odd numbered single precision floating point VFP registers
available for explicit allocation for use by the calling convention
* fixed copy/paste error in stdname of S30 register
-> use -dFPC_ARMHF to create an ARM eabi hard float compiler
(mantis #21554)

git-svn-id: trunk@20660 -

Jonas Maebe 13 năm trước cách đây
mục cha
commit
6ba8dc7146

+ 9 - 1
compiler/arm/agarmgas.pas

@@ -80,9 +80,17 @@ unit agarmgas;
         result:=inherited MakeCmdLine;
         result:=inherited MakeCmdLine;
         if (current_settings.fputype = fpu_soft) then
         if (current_settings.fputype = fpu_soft) then
           result:='-mfpu=softvfp '+result;
           result:='-mfpu=softvfp '+result;
-
+        if (current_settings.fputype = fpu_vfpv2) then
+          result:='-mfpu=vfpv2 '+result;
+        if (current_settings.fputype = fpu_vfpv3) then
+          result:='-mfpu=vfpv3 '+result;
+        if (current_settings.fputype = fpu_vfpv3_d16) then
+          result:='-mfpu=vfpv3-d16 '+result;
         if current_settings.cputype = cpu_armv7m then
         if current_settings.cputype = cpu_armv7m then
           result:='-march=armv7m -mthumb -mthumb-interwork '+result;
           result:='-march=armv7m -mthumb -mthumb-interwork '+result;
+        if target_info.abi = abi_eabihf then
+          { options based on what gcc uses on debian armhf }
+          result:='-mfloat-abi=hard -meabi=5 '+result;
       end;
       end;
 
 
     procedure TArmGNUAssembler.WriteExtraHeader;
     procedure TArmGNUAssembler.WriteExtraHeader;

+ 24 - 21
compiler/arm/armreg.dat

@@ -34,57 +34,60 @@ F6,$02,$00,$06,f6,32,22
 F7,$02,$00,$07,f7,32,23
 F7,$02,$00,$07,f7,32,23
 
 
 ; MM registers
 ; MM registers
-; S0/S1/D0 etc have the same register number because the register allocated
-; cannot deal with D0 conflicting with both S0 and S1. This unfortunately
-; means that we can only use 16 single precision registers instead of 32,
-; even if no double precision ones are used...
+; odd numbered single registers must not be made available to the register
+; allocator because it cannot deal with D0 conflicting with both S0 and S1. 
+; This unfortunately means that we can only use 16 single precision registers 
+; instead of 32,  even if no double precision ones are used...
+; Nevertheless the odd numbered single registers must have seperate register 
+; numbers to allow implementation of the "EABI VFP hardfloat" calling convention.
+
 S0,$04,$06,$00,s0,0,0
 S0,$04,$06,$00,s0,0,0
-S1,$04,$06,$00,s1,0,0
+S1,$04,$06,$20,s1,0,0
 D0,$04,$07,$00,d0,0,0
 D0,$04,$07,$00,d0,0,0
 S2,$04,$06,$01,s2,0,0
 S2,$04,$06,$01,s2,0,0
-S3,$04,$06,$01,s3,0,0
+S3,$04,$06,$21,s3,0,0
 D1,$04,$07,$01,d1,0,0
 D1,$04,$07,$01,d1,0,0
 S4,$04,$06,$02,s4,0,0
 S4,$04,$06,$02,s4,0,0
-S5,$04,$06,$02,s5,0,0
+S5,$04,$06,$22,s5,0,0
 D2,$04,$07,$02,d2,0,0
 D2,$04,$07,$02,d2,0,0
 S6,$04,$06,$03,s6,0,0
 S6,$04,$06,$03,s6,0,0
-S7,$04,$06,$03,s7,0,0
+S7,$04,$06,$23,s7,0,0
 D3,$04,$07,$03,d3,0,0
 D3,$04,$07,$03,d3,0,0
 S8,$04,$06,$04,s8,0,0
 S8,$04,$06,$04,s8,0,0
-S9,$04,$06,$04,s9,0,0
+S9,$04,$06,$24,s9,0,0
 D4,$04,$07,$04,d4,0,0
 D4,$04,$07,$04,d4,0,0
 S10,$04,$06,$05,s10,0,0
 S10,$04,$06,$05,s10,0,0
-S11,$04,$06,$05,s11,0,0
+S11,$04,$06,$25,s11,0,0
 D5,$04,$07,$05,d5,0,0
 D5,$04,$07,$05,d5,0,0
 S12,$04,$06,$06,s12,0,0
 S12,$04,$06,$06,s12,0,0
-S13,$04,$06,$06,s13,0,0
+S13,$04,$06,$26,s13,0,0
 D6,$04,$07,$06,d6,0,0
 D6,$04,$07,$06,d6,0,0
 S14,$04,$06,$07,s14,0,0
 S14,$04,$06,$07,s14,0,0
-S15,$04,$06,$07,s15,0,0
+S15,$04,$06,$27,s15,0,0
 D7,$04,$07,$07,d7,0,0
 D7,$04,$07,$07,d7,0,0
 S16,$04,$06,$08,s16,0,0
 S16,$04,$06,$08,s16,0,0
-S17,$04,$06,$08,s17,0,0
+S17,$04,$06,$28,s17,0,0
 D8,$04,$07,$08,d8,0,0
 D8,$04,$07,$08,d8,0,0
 S18,$04,$06,$09,s18,0,0
 S18,$04,$06,$09,s18,0,0
-S19,$04,$06,$09,s19,0,0
+S19,$04,$06,$29,s19,0,0
 D9,$04,$07,$09,d9,0,0
 D9,$04,$07,$09,d9,0,0
 S20,$04,$06,$0A,s20,0,0
 S20,$04,$06,$0A,s20,0,0
-S21,$04,$06,$0A,s21,0,0
+S21,$04,$06,$2A,s21,0,0
 D10,$04,$07,$0A,d10,0,0
 D10,$04,$07,$0A,d10,0,0
 S22,$04,$06,$0B,s22,0,0
 S22,$04,$06,$0B,s22,0,0
-S23,$04,$06,$0B,s23,0,0
+S23,$04,$06,$2B,s23,0,0
 D11,$04,$07,$0B,d11,0,0
 D11,$04,$07,$0B,d11,0,0
 S24,$04,$06,$0C,s24,0,0
 S24,$04,$06,$0C,s24,0,0
-S25,$04,$06,$0C,s25,0,0
+S25,$04,$06,$2C,s25,0,0
 D12,$04,$07,$0C,d12,0,0
 D12,$04,$07,$0C,d12,0,0
 S26,$04,$06,$0D,s26,0,0
 S26,$04,$06,$0D,s26,0,0
-S27,$04,$06,$0D,s27,0,0
+S27,$04,$06,$2D,s27,0,0
 D13,$04,$07,$0D,d13,0,0
 D13,$04,$07,$0D,d13,0,0
 S28,$04,$06,$0E,s28,0,0
 S28,$04,$06,$0E,s28,0,0
-S29,$04,$06,$0E,s29,0,0
+S29,$04,$06,$2E,s29,0,0
 D14,$04,$07,$0E,d14,0,0
 D14,$04,$07,$0E,d14,0,0
-S30,$04,$06,$0F,s20,0,0
-S31,$04,$06,$0F,s21,0,0
+S30,$04,$06,$0F,s30,0,0
+S31,$04,$06,$2F,s21,0,0
 D15,$04,$07,$0F,d15,0,0
 D15,$04,$07,$0F,d15,0,0
 D16,$04,$07,$10,d16,0,0
 D16,$04,$07,$10,d16,0,0
 D17,$04,$07,$11,d17,0,0
 D17,$04,$07,$11,d17,0,0

+ 10 - 6
compiler/arm/cgcpu.pas

@@ -1438,7 +1438,8 @@ unit cgcpu;
                       end;
                       end;
                 end;
                 end;
               fpu_vfpv2,
               fpu_vfpv2,
-              fpu_vfpv3:
+              fpu_vfpv3,
+              fpu_vfpv3_d16:
                 begin;
                 begin;
                   mmregs:=rg[R_MMREGISTER].used_in_proc-paramanager.get_volatile_registers_mm(pocall_stdcall);
                   mmregs:=rg[R_MMREGISTER].used_in_proc-paramanager.get_volatile_registers_mm(pocall_stdcall);
                 end;
                 end;
@@ -1509,7 +1510,7 @@ unit cgcpu;
              begin
              begin
                reference_reset(ref,4);
                reference_reset(ref,4);
                if (tg.direction*tarmprocinfo(current_procinfo).floatregstart>=1023) or
                if (tg.direction*tarmprocinfo(current_procinfo).floatregstart>=1023) or
-                  (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3]) then
+                  (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3,fpu_vfpv3_d16]) then
                  begin
                  begin
                    if not is_shifter_const(tarmprocinfo(current_procinfo).floatregstart,shift) then
                    if not is_shifter_const(tarmprocinfo(current_procinfo).floatregstart,shift) then
                      begin
                      begin
@@ -1537,7 +1538,8 @@ unit cgcpu;
                        lastfloatreg-firstfloatreg+1,ref));
                        lastfloatreg-firstfloatreg+1,ref));
                    end;
                    end;
                  fpu_vfpv2,
                  fpu_vfpv2,
-                 fpu_vfpv3:
+                 fpu_vfpv3,
+                 fpu_vfpv3_d16:
                    begin
                    begin
                      ref.index:=ref.base;
                      ref.index:=ref.base;
                      ref.base:=NR_NO;
                      ref.base:=NR_NO;
@@ -1591,7 +1593,8 @@ unit cgcpu;
                       end;
                       end;
                 end;
                 end;
               fpu_vfpv2,
               fpu_vfpv2,
-              fpu_vfpv3:
+              fpu_vfpv3,
+              fpu_vfpv3_d16:
                 begin;
                 begin;
                   { restore vfp registers? }
                   { restore vfp registers? }
                   mmregs:=rg[R_MMREGISTER].used_in_proc-paramanager.get_volatile_registers_mm(pocall_stdcall);
                   mmregs:=rg[R_MMREGISTER].used_in_proc-paramanager.get_volatile_registers_mm(pocall_stdcall);
@@ -1603,7 +1606,7 @@ unit cgcpu;
               begin
               begin
                 reference_reset(ref,4);
                 reference_reset(ref,4);
                 if (tg.direction*tarmprocinfo(current_procinfo).floatregstart>=1023) or
                 if (tg.direction*tarmprocinfo(current_procinfo).floatregstart>=1023) or
-                   (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3]) then
+                   (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3,fpu_vfpv3_d16]) then
                   begin
                   begin
                     if not is_shifter_const(tarmprocinfo(current_procinfo).floatregstart,shift) then
                     if not is_shifter_const(tarmprocinfo(current_procinfo).floatregstart,shift) then
                       begin
                       begin
@@ -1630,7 +1633,8 @@ unit cgcpu;
                         lastfloatreg-firstfloatreg+1,ref));
                         lastfloatreg-firstfloatreg+1,ref));
                     end;
                     end;
                   fpu_vfpv2,
                   fpu_vfpv2,
-                  fpu_vfpv3:
+                  fpu_vfpv3,
+                  fpu_vfpv3_d16:
                     begin
                     begin
                       ref.index:=ref.base;
                       ref.index:=ref.base;
                       ref.base:=NR_NO;
                       ref.base:=NR_NO;

+ 3 - 3
compiler/arm/cpubase.pas

@@ -87,7 +87,7 @@ unit cpubase;
 
 
       { MM Super register first and last }
       { MM Super register first and last }
       first_mm_supreg    = RS_S0;
       first_mm_supreg    = RS_S0;
-      first_mm_imreg     = $20;
+      first_mm_imreg     = $30;
 
 
 { TODO: Calculate bsstart}
 { TODO: Calculate bsstart}
       regnumber_count_bsstart = 64;
       regnumber_count_bsstart = 64;
@@ -106,7 +106,7 @@ unit cpubase;
       { registers which may be destroyed by calls }
       { registers which may be destroyed by calls }
       VOLATILE_INTREGISTERS = [RS_R0..RS_R3,RS_R12..RS_R14];
       VOLATILE_INTREGISTERS = [RS_R0..RS_R3,RS_R12..RS_R14];
       VOLATILE_FPUREGISTERS = [RS_F0..RS_F3];
       VOLATILE_FPUREGISTERS = [RS_F0..RS_F3];
-      VOLATILE_MMREGISTERS =  [RS_D0..RS_D7,RS_D16..RS_D31];
+      VOLATILE_MMREGISTERS =  [RS_D0..RS_D7,RS_D16..RS_D31,RS_S1..RS_S15];
 
 
       VOLATILE_INTREGISTERS_DARWIN = [RS_R0..RS_R3,RS_R9,RS_R12..RS_R14];
       VOLATILE_INTREGISTERS_DARWIN = [RS_R0..RS_R3,RS_R9,RS_R12..RS_R14];
 
 
@@ -286,7 +286,7 @@ unit cpubase;
 
 
       NR_FPU_RESULT_REG = NR_F0;
       NR_FPU_RESULT_REG = NR_F0;
 
 
-      NR_MM_RESULT_REG  = NR_NO;
+      NR_MM_RESULT_REG  = NR_D0;
 
 
       NR_RETURN_ADDRESS_REG = NR_FUNCTION_RETURN_REG;
       NR_RETURN_ADDRESS_REG = NR_FUNCTION_RETURN_REG;
 
 

+ 6 - 4
compiler/arm/cpuinfo.pas

@@ -56,7 +56,8 @@ Type
       fpu_fpa10,
       fpu_fpa10,
       fpu_fpa11,
       fpu_fpa11,
       fpu_vfpv2,
       fpu_vfpv2,
-      fpu_vfpv3
+      fpu_vfpv3,
+      fpu_vfpv3_d16
      );
      );
 
 
    tcontrollertype =
    tcontrollertype =
@@ -197,14 +198,15 @@ Const
      'ARMV7M'
      'ARMV7M'
    );
    );
 
 
-   fputypestr : array[tfputype] of string[6] = ('',
+   fputypestr : array[tfputype] of string[9] = ('',
      'SOFT',
      'SOFT',
      'LIBGCC',
      'LIBGCC',
      'FPA',
      'FPA',
      'FPA10',
      'FPA10',
      'FPA11',
      'FPA11',
      'VFPV2',
      'VFPV2',
-     'VFPV3'
+     'VFPV3',
+     'VFPV3_D16'
    );
    );
 
 
 
 
@@ -1015,7 +1017,7 @@ Const
         )
         )
     );
     );
 
 
-   vfp_scalar = [fpu_vfpv2,fpu_vfpv3];
+   vfp_scalar = [fpu_vfpv2,fpu_vfpv3,fpu_vfpv3_d16];
 
 
    { Supported optimizations, only used for information }
    { Supported optimizations, only used for information }
    supported_optimizerswitches = genericlevel1optimizerswitches+
    supported_optimizerswitches = genericlevel1optimizerswitches+

+ 90 - 18
compiler/arm/cpupara.pas

@@ -44,9 +44,9 @@ unit cpupara;
           function create_varargs_paraloc_info(p : tabstractprocdef; varargspara:tvarargsparalist):longint;override;
           function create_varargs_paraloc_info(p : tabstractprocdef; varargspara:tvarargsparalist):longint;override;
           function get_funcretloc(p : tabstractprocdef; side: tcallercallee; def: tdef): tcgpara;override;
           function get_funcretloc(p : tabstractprocdef; side: tcallercallee; def: tdef): tcgpara;override;
          private
          private
-          procedure init_values(var curintreg, curfloatreg, curmmreg: tsuperregister; var cur_stack_offset: aword);
+          procedure init_values(var curintreg, curfloatreg, curmmreg: tsuperregister; var cur_stack_offset: aword; var sparesinglereg: tregister);
           function create_paraloc_info_intern(p : tabstractprocdef; side: tcallercallee; paras: tparalist;
           function create_paraloc_info_intern(p : tabstractprocdef; side: tcallercallee; paras: tparalist;
-            var curintreg, curfloatreg, curmmreg: tsuperregister; var cur_stack_offset: aword):longint;
+            var curintreg, curfloatreg, curmmreg: tsuperregister; var cur_stack_offset: aword; var sparesinglereg: tregister; isvariadic: boolean):longint;
           procedure create_funcretloc_info(p : tabstractprocdef; side: tcallercallee);
           procedure create_funcretloc_info(p : tabstractprocdef; side: tcallercallee);
        end;
        end;
 
 
@@ -110,7 +110,7 @@ unit cpupara;
       end;
       end;
 
 
 
 
-    function getparaloc(calloption : tproccalloption; p : tdef) : tcgloc;
+    function getparaloc(calloption : tproccalloption; p : tdef; isvariadic: boolean) : tcgloc;
       begin
       begin
          { Later, the LOC_REFERENCE is in most cases changed into LOC_REGISTER
          { Later, the LOC_REFERENCE is in most cases changed into LOC_REGISTER
            if push_addr_param for the def is true
            if push_addr_param for the def is true
@@ -119,11 +119,15 @@ unit cpupara;
             orddef:
             orddef:
               getparaloc:=LOC_REGISTER;
               getparaloc:=LOC_REGISTER;
             floatdef:
             floatdef:
-              if (calloption in [pocall_cdecl,pocall_cppdecl,pocall_softfloat]) or
+              if (target_info.abi = abi_eabihf) and
+                 (not isvariadic) then
+                getparaloc:=LOC_MMREGISTER
+              else if (calloption in [pocall_cdecl,pocall_cppdecl,pocall_softfloat]) or
                  (cs_fp_emulation in current_settings.moduleswitches) or
                  (cs_fp_emulation in current_settings.moduleswitches) or
-                 (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3]) then
+                 (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3,fpu_vfpv3_d16]) then
                 { the ARM eabi also allows passing VFP values via VFP registers,
                 { the ARM eabi also allows passing VFP values via VFP registers,
-                  but at least neither Mac OS X nor Linux seems to do that }
+                  but Mac OS X doesn't seem to do that and linux only does it if
+                  built with the "-mfloat-abi=hard" option }
                 getparaloc:=LOC_REGISTER
                 getparaloc:=LOC_REGISTER
               else
               else
                 getparaloc:=LOC_FPUREGISTER;
                 getparaloc:=LOC_FPUREGISTER;
@@ -213,17 +217,18 @@ unit cpupara;
       end;
       end;
 
 
 
 
-    procedure tarmparamanager.init_values(var curintreg, curfloatreg, curmmreg: tsuperregister; var cur_stack_offset: aword);
+    procedure tarmparamanager.init_values(var curintreg, curfloatreg, curmmreg: tsuperregister; var cur_stack_offset: aword; var sparesinglereg: tregister);
       begin
       begin
         curintreg:=RS_R0;
         curintreg:=RS_R0;
         curfloatreg:=RS_F0;
         curfloatreg:=RS_F0;
         curmmreg:=RS_D0;
         curmmreg:=RS_D0;
         cur_stack_offset:=0;
         cur_stack_offset:=0;
+        sparesinglereg := NR_NO;
       end;
       end;
 
 
 
 
     function tarmparamanager.create_paraloc_info_intern(p : tabstractprocdef; side: tcallercallee; paras: tparalist;
     function tarmparamanager.create_paraloc_info_intern(p : tabstractprocdef; side: tcallercallee; paras: tparalist;
-        var curintreg, curfloatreg, curmmreg: tsuperregister; var cur_stack_offset: aword):longint;
+        var curintreg, curfloatreg, curmmreg: tsuperregister; var cur_stack_offset: aword; var sparesinglereg: tregister; isvariadic: boolean):longint;
 
 
       var
       var
         nextintreg,nextfloatreg,nextmmreg : tsuperregister;
         nextintreg,nextfloatreg,nextmmreg : tsuperregister;
@@ -302,7 +307,7 @@ unit cpupara;
                   paralen := paradef.size
                   paralen := paradef.size
                 else
                 else
                   paralen := tcgsize2size[def_cgsize(paradef)];
                   paralen := tcgsize2size[def_cgsize(paradef)];
-                loc := getparaloc(p.proccalloption,paradef);
+                loc := getparaloc(p.proccalloption,paradef,isvariadic);
                 if (paradef.typ in [objectdef,arraydef,recorddef]) and
                 if (paradef.typ in [objectdef,arraydef,recorddef]) and
                   not is_special_array(paradef) and
                   not is_special_array(paradef) and
                   (hp.varspez in [vs_value,vs_const]) then
                   (hp.varspez in [vs_value,vs_const]) then
@@ -349,7 +354,7 @@ unit cpupara;
                     LOC_REGISTER:
                     LOC_REGISTER:
                       begin
                       begin
                         { align registers for eabi }
                         { align registers for eabi }
-                        if (target_info.abi=abi_eabi) and
+                        if (target_info.abi in [abi_eabi,abi_eabihf]) and
                            firstparaloc and
                            firstparaloc and
                            (paradef.alignment=8) then
                            (paradef.alignment=8) then
                           begin
                           begin
@@ -405,6 +410,52 @@ unit cpupara;
                             end;
                             end;
                           end;
                           end;
                       end;
                       end;
+                    LOC_MMREGISTER:
+                      begin
+                        if (nextmmreg<=RS_D7) or
+                           ((paraloc^.size = OS_F32) and
+                            (sparesinglereg<>NR_NO)) then
+                          begin
+                            paraloc^.loc:=LOC_MMREGISTER;
+                            case paraloc^.size of
+                              OS_F32:
+                                if sparesinglereg = NR_NO then 
+                                  begin     
+                                    paraloc^.register:=newreg(R_MMREGISTER,nextmmreg,R_SUBFS);
+                                    sparesinglereg:=newreg(R_MMREGISTER,nextmmreg-RS_S0+RS_S1,R_SUBFS);
+                                    inc(nextmmreg);
+                                  end
+                                else
+                                  begin
+                                    paraloc^.register:=sparesinglereg;
+                                    sparesinglereg := NR_NO;
+                                  end;
+                              OS_F64:
+                                begin
+                                  paraloc^.register:=newreg(R_MMREGISTER,nextmmreg,R_SUBFD);
+                                  inc(nextmmreg);
+                                end;
+                              else
+                                internalerror(2012031601);
+                            end;
+                          end
+                        else
+                          begin
+                            { once a floating point parameters has been placed
+                            on the stack we must not pass any more in vfp regs
+                            even if there is a single precision register still
+                            free}
+                            sparesinglereg := NR_NO;
+                            { LOC_REFERENCE always contains everything that's left }
+                            paraloc^.loc:=LOC_REFERENCE;
+                            paraloc^.size:=int_cgsize(paralen);
+                            if (side=callerside) then
+                              paraloc^.reference.index:=NR_STACK_POINTER_REG;
+                            paraloc^.reference.offset:=stack_offset;
+                            inc(stack_offset,align(paralen,4));
+                            paralen:=0;
+                         end;
+                      end;
                     LOC_REFERENCE:
                     LOC_REFERENCE:
                       begin
                       begin
                         if push_addr_param(hp.varspez,paradef,p.proccalloption) then
                         if push_addr_param(hp.varspez,paradef,p.proccalloption) then
@@ -415,7 +466,7 @@ unit cpupara;
                         else
                         else
                           begin
                           begin
                             { align stack for eabi }
                             { align stack for eabi }
-                            if (target_info.abi=abi_eabi) and
+                            if (target_info.abi in [abi_eabi,abi_eabihf]) and
                                firstparaloc and
                                firstparaloc and
                                (paradef.alignment=8) then
                                (paradef.alignment=8) then
                               stack_offset:=align(stack_offset,8);
                               stack_offset:=align(stack_offset,8);
@@ -499,9 +550,28 @@ unit cpupara;
         { Return in FPU register? }
         { Return in FPU register? }
         if def.typ=floatdef then
         if def.typ=floatdef then
           begin
           begin
-            if (p.proccalloption in [pocall_softfloat]) or
+            if target_info.abi = abi_eabihf then 
+              begin
+                paraloc^.loc:=LOC_MMREGISTER;
+                case retcgsize of
+                  OS_64,
+                  OS_F64:
+                    begin
+                      paraloc^.register:=NR_MM_RESULT_REG;
+                    end;
+                  OS_32,
+                  OS_F32:
+                    begin
+                      paraloc^.register:=NR_S0;
+                    end;
+                  else
+                    internalerror(2012032501);
+                end;
+                paraloc^.size:=retcgsize;
+              end
+            else if (p.proccalloption in [pocall_softfloat]) or
                (cs_fp_emulation in current_settings.moduleswitches) or
                (cs_fp_emulation in current_settings.moduleswitches) or
-               (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3]) then
+               (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3,fpu_vfpv3_d16]) then
               begin
               begin
                 case retcgsize of
                 case retcgsize of
                   OS_64,
                   OS_64,
@@ -563,10 +633,11 @@ unit cpupara;
       var
       var
         cur_stack_offset: aword;
         cur_stack_offset: aword;
         curintreg, curfloatreg, curmmreg: tsuperregister;
         curintreg, curfloatreg, curmmreg: tsuperregister;
+        sparesinglereg:tregister;
       begin
       begin
-        init_values(curintreg,curfloatreg,curmmreg,cur_stack_offset);
+        init_values(curintreg,curfloatreg,curmmreg,cur_stack_offset,sparesinglereg);
 
 
-        result:=create_paraloc_info_intern(p,side,p.paras,curintreg,curfloatreg,curmmreg,cur_stack_offset);
+        result:=create_paraloc_info_intern(p,side,p.paras,curintreg,curfloatreg,curmmreg,cur_stack_offset,sparesinglereg,false);
 
 
         create_funcretloc_info(p,side);
         create_funcretloc_info(p,side);
      end;
      end;
@@ -576,13 +647,14 @@ unit cpupara;
       var
       var
         cur_stack_offset: aword;
         cur_stack_offset: aword;
         curintreg, curfloatreg, curmmreg: tsuperregister;
         curintreg, curfloatreg, curmmreg: tsuperregister;
+        sparesinglereg:tregister;
       begin
       begin
-        init_values(curintreg,curfloatreg,curmmreg,cur_stack_offset);
+        init_values(curintreg,curfloatreg,curmmreg,cur_stack_offset,sparesinglereg);
 
 
-        result:=create_paraloc_info_intern(p,callerside,p.paras,curintreg,curfloatreg,curmmreg,cur_stack_offset);
+        result:=create_paraloc_info_intern(p,callerside,p.paras,curintreg,curfloatreg,curmmreg,cur_stack_offset,sparesinglereg,true);
         if (p.proccalloption in [pocall_cdecl,pocall_cppdecl]) then
         if (p.proccalloption in [pocall_cdecl,pocall_cppdecl]) then
           { just continue loading the parameters in the registers }
           { just continue loading the parameters in the registers }
-          result:=create_paraloc_info_intern(p,callerside,varargspara,curintreg,curfloatreg,curmmreg,cur_stack_offset)
+          result:=create_paraloc_info_intern(p,callerside,varargspara,curintreg,curfloatreg,curmmreg,cur_stack_offset,sparesinglereg,true)
         else
         else
           internalerror(200410231);
           internalerror(200410231);
       end;
       end;

+ 2 - 1
compiler/arm/cpupi.pas

@@ -106,7 +106,8 @@ unit cpupi;
                 floatsavesize:=(lastfloatreg-firstfloatreg+1)*12;
                 floatsavesize:=(lastfloatreg-firstfloatreg+1)*12;
             end;
             end;
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               floatsavesize:=0;
               floatsavesize:=0;
               regs:=cg.rg[R_MMREGISTER].used_in_proc-paramanager.get_volatile_registers_mm(pocall_stdcall);
               regs:=cg.rg[R_MMREGISTER].used_in_proc-paramanager.get_volatile_registers_mm(pocall_stdcall);

+ 4 - 2
compiler/arm/narmadd.pas

@@ -164,7 +164,8 @@ interface
                  cgsize2fpuoppostfix[def_cgsize(resultdef)]));
                  cgsize2fpuoppostfix[def_cgsize(resultdef)]));
             end;
             end;
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               { force mmreg as location, left right doesn't matter
               { force mmreg as location, left right doesn't matter
                 as both will be in a fpureg }
                 as both will be in a fpureg }
@@ -248,7 +249,8 @@ interface
                    cgsize2fpuoppostfix[def_cgsize(resultdef)]));
                    cgsize2fpuoppostfix[def_cgsize(resultdef)]));
             end;
             end;
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               location_force_mmregscalar(current_asmdata.CurrAsmList,left.location,true);
               location_force_mmregscalar(current_asmdata.CurrAsmList,left.location,true);
               location_force_mmregscalar(current_asmdata.CurrAsmList,right.location,true);
               location_force_mmregscalar(current_asmdata.CurrAsmList,right.location,true);

+ 5 - 3
compiler/arm/narmcal.pas

@@ -41,13 +41,15 @@ implementation
     cgbase,
     cgbase,
     cpubase,cpuinfo,
     cpubase,cpuinfo,
     ncgutil,
     ncgutil,
-    paramgr;
+    paramgr,
+    systems;
 
 
   procedure tarmcallnode.set_result_location(realresdef: tstoreddef);
   procedure tarmcallnode.set_result_location(realresdef: tstoreddef);
     begin
     begin
-      if (realresdef.typ=floatdef) and
+      if (realresdef.typ=floatdef) and 
+         (target_info.abi <> abi_eabihf) and
          ((cs_fp_emulation in current_settings.moduleswitches) or
          ((cs_fp_emulation in current_settings.moduleswitches) or
-          (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3])) then
+          (current_settings.fputype in [fpu_vfpv2,fpu_vfpv3,fpu_vfpv3_d16])) then
         begin
         begin
           { keep the fpu values in integer registers for now, the code
           { keep the fpu values in integer registers for now, the code
             generator will move them to memory or an mmregister when necessary
             generator will move them to memory or an mmregister when necessary

+ 4 - 2
compiler/arm/narmcnv.pas

@@ -116,7 +116,8 @@ implementation
               fpu_fpa11:
               fpu_fpa11:
                 expectloc:=LOC_FPUREGISTER;
                 expectloc:=LOC_FPUREGISTER;
               fpu_vfpv2,
               fpu_vfpv2,
-              fpu_vfpv3:
+              fpu_vfpv3,
+              fpu_vfpv3_d16:
                 expectloc:=LOC_MMREGISTER;
                 expectloc:=LOC_MMREGISTER;
               else
               else
                 internalerror(2009112702);
                 internalerror(2009112702);
@@ -195,7 +196,8 @@ implementation
               end;
               end;
             end;
             end;
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               location_reset(location,LOC_MMREGISTER,def_cgsize(resultdef));
               location_reset(location,LOC_MMREGISTER,def_cgsize(resultdef));
               signed:=left.location.size=OS_S32;
               signed:=left.location.size=OS_S32;

+ 14 - 7
compiler/arm/narminl.pas

@@ -89,7 +89,8 @@ implementation
                end;
                end;
             end;
             end;
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               location_force_mmregscalar(current_asmdata.CurrAsmList,left.location,true);
               location_force_mmregscalar(current_asmdata.CurrAsmList,left.location,true);
               location_copy(location,left.location);
               location_copy(location,left.location);
@@ -118,7 +119,8 @@ implementation
               fpu_fpa11:
               fpu_fpa11:
                 expectloc:=LOC_FPUREGISTER;
                 expectloc:=LOC_FPUREGISTER;
               fpu_vfpv2,
               fpu_vfpv2,
-              fpu_vfpv3:
+              fpu_vfpv3,
+              fpu_vfpv3_d16:
                 expectloc:=LOC_MMREGISTER;
                 expectloc:=LOC_MMREGISTER;
               else
               else
                 internalerror(2009112401);
                 internalerror(2009112401);
@@ -140,7 +142,8 @@ implementation
               fpu_fpa11:
               fpu_fpa11:
                 expectloc:=LOC_FPUREGISTER;
                 expectloc:=LOC_FPUREGISTER;
               fpu_vfpv2,
               fpu_vfpv2,
-              fpu_vfpv3:
+              fpu_vfpv3,
+              fpu_vfpv3_d16:
                 expectloc:=LOC_MMREGISTER;
                 expectloc:=LOC_MMREGISTER;
               else
               else
                 internalerror(2009112402);
                 internalerror(2009112402);
@@ -162,7 +165,8 @@ implementation
               fpu_fpa11:
               fpu_fpa11:
                 expectloc:=LOC_FPUREGISTER;
                 expectloc:=LOC_FPUREGISTER;
               fpu_vfpv2,
               fpu_vfpv2,
-              fpu_vfpv3:
+              fpu_vfpv3,
+              fpu_vfpv3_d16:
                 expectloc:=LOC_MMREGISTER;
                 expectloc:=LOC_MMREGISTER;
               else
               else
                 internalerror(2009112403);
                 internalerror(2009112403);
@@ -213,7 +217,8 @@ implementation
           fpu_fpa11:
           fpu_fpa11:
             current_asmdata.CurrAsmList.concat(setoppostfix(taicpu.op_reg_reg(A_ABS,location.register,left.location.register),get_fpu_postfix(resultdef)));
             current_asmdata.CurrAsmList.concat(setoppostfix(taicpu.op_reg_reg(A_ABS,location.register,left.location.register),get_fpu_postfix(resultdef)));
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               if singleprec then
               if singleprec then
                 op:=A_FABSS
                 op:=A_FABSS
@@ -239,7 +244,8 @@ implementation
           fpu_fpa11:
           fpu_fpa11:
             current_asmdata.CurrAsmList.concat(setoppostfix(taicpu.op_reg_reg_reg(A_MUF,location.register,left.location.register,left.location.register),get_fpu_postfix(resultdef)));
             current_asmdata.CurrAsmList.concat(setoppostfix(taicpu.op_reg_reg_reg(A_MUF,location.register,left.location.register,left.location.register),get_fpu_postfix(resultdef)));
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               if singleprec then
               if singleprec then
                 op:=A_FMULS
                 op:=A_FMULS
@@ -265,7 +271,8 @@ implementation
           fpu_fpa11:
           fpu_fpa11:
             current_asmdata.CurrAsmList.concat(setoppostfix(taicpu.op_reg_reg(A_SQT,location.register,left.location.register),get_fpu_postfix(resultdef)));
             current_asmdata.CurrAsmList.concat(setoppostfix(taicpu.op_reg_reg(A_SQT,location.register,left.location.register),get_fpu_postfix(resultdef)));
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               if singleprec then
               if singleprec then
                 op:=A_FSQRTS
                 op:=A_FSQRTS

+ 2 - 1
compiler/arm/narmmat.pas

@@ -331,7 +331,8 @@ implementation
                 cgsize2fpuoppostfix[def_cgsize(resultdef)]));
                 cgsize2fpuoppostfix[def_cgsize(resultdef)]));
             end;
             end;
           fpu_vfpv2,
           fpu_vfpv2,
-          fpu_vfpv3:
+          fpu_vfpv3,
+          fpu_vfpv3_d16:
             begin
             begin
               location_force_mmregscalar(current_asmdata.CurrAsmList,left.location,true);
               location_force_mmregscalar(current_asmdata.CurrAsmList,left.location,true);
               location:=left.location;
               location:=left.location;

+ 16 - 16
compiler/arm/rarmcon.inc

@@ -25,52 +25,52 @@ NR_F5 = tregister($02000005);
 NR_F6 = tregister($02000006);
 NR_F6 = tregister($02000006);
 NR_F7 = tregister($02000007);
 NR_F7 = tregister($02000007);
 NR_S0 = tregister($04060000);
 NR_S0 = tregister($04060000);
-NR_S1 = tregister($04060000);
+NR_S1 = tregister($04060020);
 NR_D0 = tregister($04070000);
 NR_D0 = tregister($04070000);
 NR_S2 = tregister($04060001);
 NR_S2 = tregister($04060001);
-NR_S3 = tregister($04060001);
+NR_S3 = tregister($04060021);
 NR_D1 = tregister($04070001);
 NR_D1 = tregister($04070001);
 NR_S4 = tregister($04060002);
 NR_S4 = tregister($04060002);
-NR_S5 = tregister($04060002);
+NR_S5 = tregister($04060022);
 NR_D2 = tregister($04070002);
 NR_D2 = tregister($04070002);
 NR_S6 = tregister($04060003);
 NR_S6 = tregister($04060003);
-NR_S7 = tregister($04060003);
+NR_S7 = tregister($04060023);
 NR_D3 = tregister($04070003);
 NR_D3 = tregister($04070003);
 NR_S8 = tregister($04060004);
 NR_S8 = tregister($04060004);
-NR_S9 = tregister($04060004);
+NR_S9 = tregister($04060024);
 NR_D4 = tregister($04070004);
 NR_D4 = tregister($04070004);
 NR_S10 = tregister($04060005);
 NR_S10 = tregister($04060005);
-NR_S11 = tregister($04060005);
+NR_S11 = tregister($04060025);
 NR_D5 = tregister($04070005);
 NR_D5 = tregister($04070005);
 NR_S12 = tregister($04060006);
 NR_S12 = tregister($04060006);
-NR_S13 = tregister($04060006);
+NR_S13 = tregister($04060026);
 NR_D6 = tregister($04070006);
 NR_D6 = tregister($04070006);
 NR_S14 = tregister($04060007);
 NR_S14 = tregister($04060007);
-NR_S15 = tregister($04060007);
+NR_S15 = tregister($04060027);
 NR_D7 = tregister($04070007);
 NR_D7 = tregister($04070007);
 NR_S16 = tregister($04060008);
 NR_S16 = tregister($04060008);
-NR_S17 = tregister($04060008);
+NR_S17 = tregister($04060028);
 NR_D8 = tregister($04070008);
 NR_D8 = tregister($04070008);
 NR_S18 = tregister($04060009);
 NR_S18 = tregister($04060009);
-NR_S19 = tregister($04060009);
+NR_S19 = tregister($04060029);
 NR_D9 = tregister($04070009);
 NR_D9 = tregister($04070009);
 NR_S20 = tregister($0406000A);
 NR_S20 = tregister($0406000A);
-NR_S21 = tregister($0406000A);
+NR_S21 = tregister($0406002A);
 NR_D10 = tregister($0407000A);
 NR_D10 = tregister($0407000A);
 NR_S22 = tregister($0406000B);
 NR_S22 = tregister($0406000B);
-NR_S23 = tregister($0406000B);
+NR_S23 = tregister($0406002B);
 NR_D11 = tregister($0407000B);
 NR_D11 = tregister($0407000B);
 NR_S24 = tregister($0406000C);
 NR_S24 = tregister($0406000C);
-NR_S25 = tregister($0406000C);
+NR_S25 = tregister($0406002C);
 NR_D12 = tregister($0407000C);
 NR_D12 = tregister($0407000C);
 NR_S26 = tregister($0406000D);
 NR_S26 = tregister($0406000D);
-NR_S27 = tregister($0406000D);
+NR_S27 = tregister($0406002D);
 NR_D13 = tregister($0407000D);
 NR_D13 = tregister($0407000D);
 NR_S28 = tregister($0406000E);
 NR_S28 = tregister($0406000E);
-NR_S29 = tregister($0406000E);
+NR_S29 = tregister($0406002E);
 NR_D14 = tregister($0407000E);
 NR_D14 = tregister($0407000E);
 NR_S30 = tregister($0406000F);
 NR_S30 = tregister($0406000F);
-NR_S31 = tregister($0406000F);
+NR_S31 = tregister($0406002F);
 NR_D15 = tregister($0407000F);
 NR_D15 = tregister($0407000F);
 NR_D16 = tregister($04070010);
 NR_D16 = tregister($04070010);
 NR_D17 = tregister($04070011);
 NR_D17 = tregister($04070011);

+ 16 - 16
compiler/arm/rarmnum.inc

@@ -25,52 +25,52 @@ tregister($02000005),
 tregister($02000006),
 tregister($02000006),
 tregister($02000007),
 tregister($02000007),
 tregister($04060000),
 tregister($04060000),
-tregister($04060000),
+tregister($04060020),
 tregister($04070000),
 tregister($04070000),
 tregister($04060001),
 tregister($04060001),
-tregister($04060001),
+tregister($04060021),
 tregister($04070001),
 tregister($04070001),
 tregister($04060002),
 tregister($04060002),
-tregister($04060002),
+tregister($04060022),
 tregister($04070002),
 tregister($04070002),
 tregister($04060003),
 tregister($04060003),
-tregister($04060003),
+tregister($04060023),
 tregister($04070003),
 tregister($04070003),
 tregister($04060004),
 tregister($04060004),
-tregister($04060004),
+tregister($04060024),
 tregister($04070004),
 tregister($04070004),
 tregister($04060005),
 tregister($04060005),
-tregister($04060005),
+tregister($04060025),
 tregister($04070005),
 tregister($04070005),
 tregister($04060006),
 tregister($04060006),
-tregister($04060006),
+tregister($04060026),
 tregister($04070006),
 tregister($04070006),
 tregister($04060007),
 tregister($04060007),
-tregister($04060007),
+tregister($04060027),
 tregister($04070007),
 tregister($04070007),
 tregister($04060008),
 tregister($04060008),
-tregister($04060008),
+tregister($04060028),
 tregister($04070008),
 tregister($04070008),
 tregister($04060009),
 tregister($04060009),
-tregister($04060009),
+tregister($04060029),
 tregister($04070009),
 tregister($04070009),
 tregister($0406000A),
 tregister($0406000A),
-tregister($0406000A),
+tregister($0406002A),
 tregister($0407000A),
 tregister($0407000A),
 tregister($0406000B),
 tregister($0406000B),
-tregister($0406000B),
+tregister($0406002B),
 tregister($0407000B),
 tregister($0407000B),
 tregister($0406000C),
 tregister($0406000C),
-tregister($0406000C),
+tregister($0406002C),
 tregister($0407000C),
 tregister($0407000C),
 tregister($0406000D),
 tregister($0406000D),
-tregister($0406000D),
+tregister($0406002D),
 tregister($0407000D),
 tregister($0407000D),
 tregister($0406000E),
 tregister($0406000E),
-tregister($0406000E),
+tregister($0406002E),
 tregister($0407000E),
 tregister($0407000E),
 tregister($0406000F),
 tregister($0406000F),
-tregister($0406000F),
+tregister($0406002F),
 tregister($0407000F),
 tregister($0407000F),
 tregister($04070010),
 tregister($04070010),
 tregister($04070011),
 tregister($04070011),

+ 15 - 15
compiler/arm/rarmrni.inc

@@ -25,37 +25,37 @@
 23,
 23,
 24,
 24,
 25,
 25,
-26,
-29,
 28,
 28,
 31,
 31,
-32,
-35,
 34,
 34,
 37,
 37,
-38,
-41,
 40,
 40,
 43,
 43,
-44,
-47,
 46,
 46,
 49,
 49,
-50,
-53,
 52,
 52,
 55,
 55,
-56,
-59,
 58,
 58,
 61,
 61,
-62,
-65,
 64,
 64,
 67,
 67,
+70,
+26,
+29,
+32,
+35,
+38,
+41,
+44,
+47,
+50,
+53,
+56,
+59,
+62,
+65,
 68,
 68,
 71,
 71,
-70,
 27,
 27,
 30,
 30,
 33,
 33,

+ 1 - 1
compiler/arm/rarmsri.inc

@@ -72,7 +72,6 @@
 53,
 53,
 28,
 28,
 55,
 55,
-70,
 71,
 71,
 56,
 56,
 58,
 58,
@@ -84,6 +83,7 @@
 67,
 67,
 68,
 68,
 29,
 29,
+70,
 31,
 31,
 32,
 32,
 34,
 34,

+ 1 - 1
compiler/arm/rarmstd.inc

@@ -69,7 +69,7 @@
 's28',
 's28',
 's29',
 's29',
 'd14',
 'd14',
-'s20',
+'s30',
 's21',
 's21',
 'd15',
 'd15',
 'd16',
 'd16',

+ 16 - 16
compiler/arm/rarmsup.inc

@@ -25,52 +25,52 @@ RS_F5 = $05;
 RS_F6 = $06;
 RS_F6 = $06;
 RS_F7 = $07;
 RS_F7 = $07;
 RS_S0 = $00;
 RS_S0 = $00;
-RS_S1 = $00;
+RS_S1 = $20;
 RS_D0 = $00;
 RS_D0 = $00;
 RS_S2 = $01;
 RS_S2 = $01;
-RS_S3 = $01;
+RS_S3 = $21;
 RS_D1 = $01;
 RS_D1 = $01;
 RS_S4 = $02;
 RS_S4 = $02;
-RS_S5 = $02;
+RS_S5 = $22;
 RS_D2 = $02;
 RS_D2 = $02;
 RS_S6 = $03;
 RS_S6 = $03;
-RS_S7 = $03;
+RS_S7 = $23;
 RS_D3 = $03;
 RS_D3 = $03;
 RS_S8 = $04;
 RS_S8 = $04;
-RS_S9 = $04;
+RS_S9 = $24;
 RS_D4 = $04;
 RS_D4 = $04;
 RS_S10 = $05;
 RS_S10 = $05;
-RS_S11 = $05;
+RS_S11 = $25;
 RS_D5 = $05;
 RS_D5 = $05;
 RS_S12 = $06;
 RS_S12 = $06;
-RS_S13 = $06;
+RS_S13 = $26;
 RS_D6 = $06;
 RS_D6 = $06;
 RS_S14 = $07;
 RS_S14 = $07;
-RS_S15 = $07;
+RS_S15 = $27;
 RS_D7 = $07;
 RS_D7 = $07;
 RS_S16 = $08;
 RS_S16 = $08;
-RS_S17 = $08;
+RS_S17 = $28;
 RS_D8 = $08;
 RS_D8 = $08;
 RS_S18 = $09;
 RS_S18 = $09;
-RS_S19 = $09;
+RS_S19 = $29;
 RS_D9 = $09;
 RS_D9 = $09;
 RS_S20 = $0A;
 RS_S20 = $0A;
-RS_S21 = $0A;
+RS_S21 = $2A;
 RS_D10 = $0A;
 RS_D10 = $0A;
 RS_S22 = $0B;
 RS_S22 = $0B;
-RS_S23 = $0B;
+RS_S23 = $2B;
 RS_D11 = $0B;
 RS_D11 = $0B;
 RS_S24 = $0C;
 RS_S24 = $0C;
-RS_S25 = $0C;
+RS_S25 = $2C;
 RS_D12 = $0C;
 RS_D12 = $0C;
 RS_S26 = $0D;
 RS_S26 = $0D;
-RS_S27 = $0D;
+RS_S27 = $2D;
 RS_D13 = $0D;
 RS_D13 = $0D;
 RS_S28 = $0E;
 RS_S28 = $0E;
-RS_S29 = $0E;
+RS_S29 = $2E;
 RS_D14 = $0E;
 RS_D14 = $0E;
 RS_S30 = $0F;
 RS_S30 = $0F;
-RS_S31 = $0F;
+RS_S31 = $2F;
 RS_D15 = $0F;
 RS_D15 = $0F;
 RS_D16 = $10;
 RS_D16 = $10;
 RS_D17 = $11;
 RS_D17 = $11;

+ 7 - 3
compiler/fpcdefs.inc

@@ -130,17 +130,21 @@
   {$define cputargethasfixedstack}
   {$define cputargethasfixedstack}
   {$define cpurefshaveindexreg}
   {$define cpurefshaveindexreg}
   { default to armel }
   { default to armel }
-  {$if not(defined(CPUARM)) and not(defined(CPUARMEB)) and not(defined(FPC_OARM)) and not(defined(FPC_ARMEB))}
+  {$if not(defined(CPUARM)) and not(defined(CPUARMEB)) and not(defined(FPC_OARM)) and not(defined(FPC_ARMEB)) and not(defined(FPC_ARMHF))}
     {$define FPC_ARMEL}
     {$define FPC_ARMEL}
   {$endif}
   {$endif}
   { inherit FPC_ARMEL? }
   { inherit FPC_ARMEL? }
-  {$if defined(CPUARMEL) and not(defined(FPC_OARM)) and not(defined(FPC_ARMEB))}
+  {$if defined(CPUARMEL) and not(defined(FPC_OARM)) and not(defined(FPC_ARMEB)) and not(defined(FPC_ARMHF))}
     {$define FPC_ARMEL}
     {$define FPC_ARMEL}
   {$endif}
   {$endif}
   { inherit FPC_ARMEB? }
   { inherit FPC_ARMEB? }
-  {$if defined(CPUARMEB) and not(defined(FPC_OARM)) and not(defined(FPC_ARMEL))}
+  {$if defined(CPUARMEB) and not(defined(FPC_OARM)) and not(defined(FPC_ARMEL)) and not(defined(FPC_ARMHF))}
     {$define FPC_ARMEB}
     {$define FPC_ARMEB}
   {$endif}
   {$endif}
+  { inherit FPC_ARMHF? }
+  {$if defined(CPUARMHF) and not(defined(FPC_OARM)) and not(defined(FPC_ARMEL)) and not(defined(FPC_ARMEB))}
+    {$define FPC_ARMHF}
+  {$endif}
 {$endif arm}
 {$endif arm}
 
 
 {$ifdef m68k}
 {$ifdef m68k}

+ 5 - 1
compiler/msg/errore.msg

@@ -2877,7 +2877,7 @@ unit_u_indirect_crc_changed=10062_U_Indirect interface (objects/classes) CRC cha
 #
 #
 #  Options
 #  Options
 #
 #
-# 11051 is the last used one
+# 11052 is the last used one
 #
 #
 option_usage=11000_O_$1 [options] <inputfile> [options]
 option_usage=11000_O_$1 [options] <inputfile> [options]
 # BeginOfTeX
 # BeginOfTeX
@@ -3013,6 +3013,10 @@ option_invalid_iphoneos_deployment_target=11051_E_Invalid value for IPHONEOS_DEP
 % XY.Z or XY.Z.AB with X, Y,Z , A and B all digits from 0-9.
 % XY.Z or XY.Z.AB with X, Y,Z , A and B all digits from 0-9.
 % In case of iOS, it has to be X.Z.A, where X, Z and A can all be either 1 or 2
 % In case of iOS, it has to be X.Z.A, where X, Z and A can all be either 1 or 2
 % digits from 0-9.
 % digits from 0-9.
+option_illegal_fpu_eabihf=11052_E_You must use a FPU type of VFPV2, VFPV3 or VFPV3_D16 when using the EABIHF ABI target
+% The EABIHF (VFP hardfloat) ABI target can only be used with VFP FPUs.
+
+
 %\end{description}
 %\end{description}
 # EndOfTeX
 # EndOfTeX
 
 

+ 3 - 2
compiler/msgidx.inc

@@ -900,6 +900,7 @@ const
   option_dwarf_smartlink_creation=11049;
   option_dwarf_smartlink_creation=11049;
   option_invalid_macosx_deployment_target=11050;
   option_invalid_macosx_deployment_target=11050;
   option_invalid_iphoneos_deployment_target=11051;
   option_invalid_iphoneos_deployment_target=11051;
+  option_illegal_fpu_eabihf=11052;
   wpo_cant_find_file=12000;
   wpo_cant_find_file=12000;
   wpo_begin_processing=12001;
   wpo_begin_processing=12001;
   wpo_end_processing=12002;
   wpo_end_processing=12002;
@@ -924,9 +925,9 @@ const
   option_info=11024;
   option_info=11024;
   option_help_pages=11025;
   option_help_pages=11025;
 
 
-  MsgTxtSize = 63069;
+  MsgTxtSize = 63163;
 
 
   MsgIdxMax : array[1..20] of longint=(
   MsgIdxMax : array[1..20] of longint=(
     26,90,315,112,85,55,116,26,202,63,
     26,90,315,112,85,55,116,26,202,63,
-    52,20,1,1,1,1,1,1,1,1
+    53,20,1,1,1,1,1,1,1,1
   );
   );

+ 164 - 163
compiler/msgtxt.inc

@@ -1,7 +1,7 @@
 {$ifdef Delphi}
 {$ifdef Delphi}
-const msgtxt : array[0..000262] of string[240]=(
+const msgtxt : array[0..000263] of string[240]=(
 {$else Delphi}
 {$else Delphi}
-const msgtxt : array[0..000262,1..240] of char=(
+const msgtxt : array[0..000263,1..240] of char=(
 {$endif Delphi}
 {$endif Delphi}
   '01000_T_Compiler: $1'#000+
   '01000_T_Compiler: $1'#000+
   '01001_D_Compiler OS: $1'#000+
   '01001_D_Compiler OS: $1'#000+
@@ -1061,60 +1061,62 @@ const msgtxt : array[0..000262,1..240] of char=(
   'e: $1'#000+
   'e: $1'#000+
   '11051_E_Invalid value for IPHONEOS_DEPLOYMENT_TARGET environment varia'+
   '11051_E_Invalid value for IPHONEOS_DEPLOYMENT_TARGET environment varia'+
   'ble: $1'#000+
   'ble: $1'#000+
+  '11052_E_You must use a FPU type of VFPV2, VFPV3 or VFPV3_D16 when usin'+
+  'g the EABIHF AB','I target'#000+
   '12000_F_Cannot open whole program optimization feedback file "$1"'#000+
   '12000_F_Cannot open whole program optimization feedback file "$1"'#000+
-  '12001_D_Processing ','whole program optimization information in wpo fee'+
-  'dback file "$1"'#000+
+  '12001_D_Processing whole program optimization information in wpo feedb'+
+  'ack file "$1"'#000+
   '12002_D_Finished processing the whole program optimization information'+
   '12002_D_Finished processing the whole program optimization information'+
-  ' in wpo feedback file "$1"'#000+
+  ' in wpo fee','dback file "$1"'#000+
   '12003_E_Expected section header, but got "$2" at line $1 of wpo feedba'+
   '12003_E_Expected section header, but got "$2" at line $1 of wpo feedba'+
-  'ck file'#000,
+  'ck file'#000+
   '12004_W_No handler registered for whole program optimization section "'+
   '12004_W_No handler registered for whole program optimization section "'+
   '$2" at line $1 of wpo feedback file, ignoring'#000+
   '$2" at line $1 of wpo feedback file, ignoring'#000+
-  '12005_D_Found whole program optimization section "$1" with information'+
-  ' about "$2"'#000+
-  '12006_F_The selected whole program optimiz','ations require a previousl'+
-  'y generated feedback file (use -Fw to specify)'#000+
+  '12005_D_Found whole program op','timization section "$1" with informati'+
+  'on about "$2"'#000+
+  '12006_F_The selected whole program optimizations require a previously '+
+  'generated feedback file (use -Fw to specify)'#000+
   '12007_E_No collected information necessary to perform "$1" whole progr'+
   '12007_E_No collected information necessary to perform "$1" whole progr'+
-  'am optimization found'#000+
+  'am ','optimization found'#000+
   '12008_F_Specify a whole program optimization feedback file to store th'+
   '12008_F_Specify a whole program optimization feedback file to store th'+
-  'e gen','erated info in (using -FW)'#000+
+  'e generated info in (using -FW)'#000+
   '12009_E_Not generating any whole program optimization information, yet'+
   '12009_E_Not generating any whole program optimization information, yet'+
   ' a feedback file was specified (using -FW)'#000+
   ' a feedback file was specified (using -FW)'#000+
-  '12010_E_Not performing any whole program optimizations, yet an input f'+
-  'eedback file was specified (us','ing -Fw)'#000+
+  '12010_','E_Not performing any whole program optimizations, yet an input'+
+  ' feedback file was specified (using -Fw)'#000+
   '12011_D_Skipping whole program optimization section "$1", because not '+
   '12011_D_Skipping whole program optimization section "$1", because not '+
   'needed by the requested optimizations'#000+
   'needed by the requested optimizations'#000+
-  '12012_W_Overriding previously read information for "$1" from feedback '+
-  'input file using information in section "$2"'#000+
-  '12013_E_','Cannot extract symbol liveness information from program when'+
-  ' stripping symbols, use -Xs-'#000+
-  '12014_E_Cannot extract symbol liveness information from program when w'+
-  'hen not linking'#000+
-  '12015_F_Cannot find "$1" or "$2" to extract symbol liveness infor','mat'+
-  'ion from linked program'#000+
+  '12012_W_Overriding previously',' read information for "$1" from feedbac'+
+  'k input file using information in section "$2"'#000+
+  '12013_E_Cannot extract symbol liveness information from program when s'+
+  'tripping symbols, use -Xs-'#000+
+  '12014_E_Cannot extract symbol liveness information from p','rogram when'+
+  ' when not linking'#000+
+  '12015_F_Cannot find "$1" or "$2" to extract symbol liveness informatio'+
+  'n from linked program'#000+
   '12016_E_Error during reading symbol liveness information produced by "'+
   '12016_E_Error during reading symbol liveness information produced by "'+
   '$1"'#000+
   '$1"'#000+
-  '12017_F_Error executing "$1" (exitcode: $2) to extract symbol informat'+
-  'ion from linked program'#000+
-  '12018_E_Collection of symbol liveness informa','tion can only help when'+
-  ' using smart linking, use -CX -XX'#000+
+  '12017_F_Error executing "$1" (exitcode: $2) t','o extract symbol inform'+
+  'ation from linked program'#000+
+  '12018_E_Collection of symbol liveness information can only help when u'+
+  'sing smart linking, use -CX -XX'#000+
   '12019_E_Cannot create specified whole program optimisation feedback fi'+
   '12019_E_Cannot create specified whole program optimisation feedback fi'+
   'le "$1"'#000+
   'le "$1"'#000+
-  '11023_Free Pascal Compiler version $FPCFULLVERSION [$FPCDATE] for $FPC'+
-  'CPU'#010+
-  'Copyright (c) 1993-2012 by Flor','ian Klaempfl and others'#000+
+  '11023_Free ','Pascal Compiler version $FPCFULLVERSION [$FPCDATE] for $F'+
+  'PCCPU'#010+
+  'Copyright (c) 1993-2012 by Florian Klaempfl and others'#000+
   '11024_Free Pascal Compiler version $FPCVERSION'#010+
   '11024_Free Pascal Compiler version $FPCVERSION'#010+
   #010+
   #010+
   'Compiler Date      : $FPCDATE'#010+
   'Compiler Date      : $FPCDATE'#010+
   'Compiler CPU Target: $FPCCPU'#010+
   'Compiler CPU Target: $FPCCPU'#010+
   #010+
   #010+
-  'Supported targets:'#010+
+  'Supported targ','ets:'#010+
   '  $OSTARGETS'#010+
   '  $OSTARGETS'#010+
   #010+
   #010+
   'Supported CPU instruction sets:'#010+
   'Supported CPU instruction sets:'#010+
   '  $INSTRUCTIONSETS'#010+
   '  $INSTRUCTIONSETS'#010+
   #010+
   #010+
-  'Supported FPU instructi','on sets:'#010+
+  'Supported FPU instruction sets:'#010+
   '  $FPUINSTRUCTIONSETS'#010+
   '  $FPUINSTRUCTIONSETS'#010+
   #010+
   #010+
   'Supported ABI targets:'#010+
   'Supported ABI targets:'#010+
@@ -1123,344 +1125,343 @@ const msgtxt : array[0..000262,1..240] of char=(
   'Supported Optimizations:'#010+
   'Supported Optimizations:'#010+
   '  $OPTIMIZATIONS'#010+
   '  $OPTIMIZATIONS'#010+
   #010+
   #010+
-  'Supported Whole Program Optimizations:'#010+
+  'Supported Whole Program Optimizat','ions:'#010+
   '  All'#010+
   '  All'#010+
   '  $WPOPTIMIZATIONS'#010+
   '  $WPOPTIMIZATIONS'#010+
   #010+
   #010+
   'Supported Microcontroller types:'#010+
   'Supported Microcontroller types:'#010+
   '  $CONTROLLERTYPES'#010+
   '  $CONTROLLERTYPES'#010+
   #010+
   #010+
-  'This prog','ram comes under the GNU General Public Licence'#010+
+  'This program comes under the GNU General Public Licence'#010+
   'For more information read COPYING.FPC'#010+
   'For more information read COPYING.FPC'#010+
   #010+
   #010+
   'Report bugs, suggestions, etc. to:'#010+
   'Report bugs, suggestions, etc. to:'#010+
-  '                 http://bugs.freepascal.org'#010+
+  '                 http://b','ugs.freepascal.org'#010+
   'or'#010+
   'or'#010+
   '                 [email protected]'#000+
   '                 [email protected]'#000+
-  '11025_**0*_Put + after a boolean sw','itch option to enable it, - to di'+
-  'sable it'#010+
+  '11025_**0*_Put + after a boolean switch option to enable it, - to disa'+
+  'ble it'#010+
   '**1a_The compiler doesn'#039't delete the generated assembler file'#010+
   '**1a_The compiler doesn'#039't delete the generated assembler file'#010+
-  '**2al_List sourcecode lines in assembler file'#010+
+  '**2al_List sourcecode lines in assembler f','ile'#010+
   '**2an_List node info in assembler file (-dEXTDEBUG compiler)'#010+
   '**2an_List node info in assembler file (-dEXTDEBUG compiler)'#010+
-  '*L2ap_Use pipes instead of cr','eating temporary assembler files'#010+
+  '*L2ap_Use pipes instead of creating temporary assembler files'#010+
   '**2ar_List register allocation/release info in assembler file'#010+
   '**2ar_List register allocation/release info in assembler file'#010+
-  '**2at_List temp allocation/release info in assembler file'#010+
+  '**2at_List temp allocation/release info in assemble','r file'#010+
   '**1A<x>_Output format:'#010+
   '**1A<x>_Output format:'#010+
   '**2Adefault_Use default assembler'#010+
   '**2Adefault_Use default assembler'#010+
   '3*2Aas_Assemble using GNU AS'#010+
   '3*2Aas_Assemble using GNU AS'#010+
-  '3','*2Amacho_Mach-O (Darwin, Intel 32 bit) using internal writer'#010+
+  '3*2Amacho_Mach-O (Darwin, Intel 32 bit) using internal writer'#010+
   '3*2Anasmcoff_COFF (Go32v2) file using Nasm'#010+
   '3*2Anasmcoff_COFF (Go32v2) file using Nasm'#010+
-  '3*2Anasmelf_ELF32 (Linux) file using Nasm'#010+
+  '3*2Anasmelf_ELF32 (Linux) file using Nasm'#010,
   '3*2Anasmwin32_Win32 object file using Nasm'#010+
   '3*2Anasmwin32_Win32 object file using Nasm'#010+
   '3*2Anasmwdosx_Win32/WDOSX object file using Nasm'#010+
   '3*2Anasmwdosx_Win32/WDOSX object file using Nasm'#010+
-  '3*','2Awasm_Obj file using Wasm (Watcom)'#010+
+  '3*2Awasm_Obj file using Wasm (Watcom)'#010+
   '3*2Anasmobj_Obj file using Nasm'#010+
   '3*2Anasmobj_Obj file using Nasm'#010+
   '3*2Amasm_Obj file using Masm (Microsoft)'#010+
   '3*2Amasm_Obj file using Masm (Microsoft)'#010+
-  '3*2Atasm_Obj file using Tasm (Borland)'#010+
+  '3*2Atasm_Obj file using Tasm (Borland',')'#010+
   '3*2Aelf_ELF (Linux) using internal writer'#010+
   '3*2Aelf_ELF (Linux) using internal writer'#010+
   '3*2Acoff_COFF (Go32v2) using internal writer'#010+
   '3*2Acoff_COFF (Go32v2) using internal writer'#010+
-  '3*2Ap','ecoff_PE-COFF (Win32) using internal writer'#010+
+  '3*2Apecoff_PE-COFF (Win32) using internal writer'#010+
   '4*2Aas_Assemble using GNU AS'#010+
   '4*2Aas_Assemble using GNU AS'#010+
   '4*2Agas_Assemble using GNU GAS'#010+
   '4*2Agas_Assemble using GNU GAS'#010+
-  '4*2Agas-darwin_Assemble darwin Mach-O64 using GNU GAS'#010+
+  '4*2Agas-darwin_Assemble darwin Mach-O64 us','ing GNU GAS'#010+
   '4*2Amasm_Win64 object file using ml64 (Microsoft)'#010+
   '4*2Amasm_Win64 object file using ml64 (Microsoft)'#010+
-  '4*2Apecoff_PE-COFF (Win64) using',' internal writer'#010+
+  '4*2Apecoff_PE-COFF (Win64) using internal writer'#010+
   '4*2Aelf_ELF (Linux-64bit) using internal writer'#010+
   '4*2Aelf_ELF (Linux-64bit) using internal writer'#010+
   '6*2Aas_Unix o-file using GNU AS'#010+
   '6*2Aas_Unix o-file using GNU AS'#010+
   '6*2Agas_GNU Motorola assembler'#010+
   '6*2Agas_GNU Motorola assembler'#010+
-  '6*2Amit_MIT Syntax (old GAS)'#010+
+  '6*2Amit_MIT Syntax',' (old GAS)'#010+
   '6*2Amot_Standard Motorola assembler'#010+
   '6*2Amot_Standard Motorola assembler'#010+
   'A*2Aas_Assemble using GNU AS'#010+
   'A*2Aas_Assemble using GNU AS'#010+
-  'P*2Aas_Assemble us','ing GNU AS'#010+
+  'P*2Aas_Assemble using GNU AS'#010+
   'S*2Aas_Assemble using GNU AS'#010+
   'S*2Aas_Assemble using GNU AS'#010+
   '**1b_Generate browser info'#010+
   '**1b_Generate browser info'#010+
   '**2bl_Generate local symbol info'#010+
   '**2bl_Generate local symbol info'#010+
   '**1B_Build all modules'#010+
   '**1B_Build all modules'#010+
-  '**1C<x>_Code generation options:'#010+
+  '**1C<x>_Code generation',' options:'#010+
   '**2C3<x>_Turn on ieee error checking for constants'#010+
   '**2C3<x>_Turn on ieee error checking for constants'#010+
-  '**2Ca<x>_Select ABI, see fpc -i f','or possible values'#010+
+  '**2Ca<x>_Select ABI, see fpc -i for possible values'#010+
   '**2Cb_Generate big-endian code'#010+
   '**2Cb_Generate big-endian code'#010+
   '**2Cc<x>_Set default calling convention to <x>'#010+
   '**2Cc<x>_Set default calling convention to <x>'#010+
-  '**2CD_Create also dynamic library (not supported)'#010+
+  '**2CD_Create also dynamic library (not supported)',#010+
   '**2Ce_Compilation with emulated floating point opcodes'#010+
   '**2Ce_Compilation with emulated floating point opcodes'#010+
-  '**2Cf<x>_Select fpu instruction set to',' use, see fpc -i for possible '+
-  'values'#010+
+  '**2Cf<x>_Select fpu instruction set to use, see fpc -i for possible va'+
+  'lues'#010+
   '**2CF<x>_Minimal floating point constant precision (default, 32, 64)'#010+
   '**2CF<x>_Minimal floating point constant precision (default, 32, 64)'#010+
   '**2Cg_Generate PIC code'#010+
   '**2Cg_Generate PIC code'#010+
-  '**2Ch<n>_<n> bytes heap (between 1023 and 67107840)'#010+
+  '**2Ch<n>_<n> byt','es heap (between 1023 and 67107840)'#010+
   '**2Ci_IO-checking'#010+
   '**2Ci_IO-checking'#010+
   '**2Cn_Omit linking stage'#010+
   '**2Cn_Omit linking stage'#010+
-  '**2Co_Check ove','rflow of integer operations'#010+
+  '**2Co_Check overflow of integer operations'#010+
   '**2CO_Check for possible overflow of integer operations'#010+
   '**2CO_Check for possible overflow of integer operations'#010+
-  '**2Cp<x>_Select instruction set, see fpc -i for possible values'#010+
+  '**2Cp<x>_Select instruction set, see fpc -i for possible value','s'#010+
   '**2CP<x>=<y>_ packing settings'#010+
   '**2CP<x>=<y>_ packing settings'#010+
-  '**3CPPACKSET=<y>_ <y> set allocation: 0, 1 or DEFAULT or NORM','AL, 2, '+
-  '4 and 8'#010+
+  '**3CPPACKSET=<y>_ <y> set allocation: 0, 1 or DEFAULT or NORMAL, 2, 4 '+
+  'and 8'#010+
   '**2Cr_Range checking'#010+
   '**2Cr_Range checking'#010+
   '**2CR_Verify object method call validity'#010+
   '**2CR_Verify object method call validity'#010+
   '**2Cs<n>_Set stack checking size to <n>'#010+
   '**2Cs<n>_Set stack checking size to <n>'#010+
-  '**2Ct_Stack checking (for testing only, see manual)'#010+
+  '**2Ct_Stack checking (for tes','ting only, see manual)'#010+
   '**2CX_Create also smartlinked library'#010+
   '**2CX_Create also smartlinked library'#010+
   '**1d<x>_Defines the symbol <x>'#010+
   '**1d<x>_Defines the symbol <x>'#010+
-  '**','1D_Generate a DEF file'#010+
+  '**1D_Generate a DEF file'#010+
   '**2Dd<x>_Set description to <x>'#010+
   '**2Dd<x>_Set description to <x>'#010+
   '**2Dv<x>_Set DLL version to <x>'#010+
   '**2Dv<x>_Set DLL version to <x>'#010+
   '*O2Dw_PM application'#010+
   '*O2Dw_PM application'#010+
   '**1e<x>_Set path to executable'#010+
   '**1e<x>_Set path to executable'#010+
-  '**1E_Same as -Cn'#010+
+  '**1E_Sa','me as -Cn'#010+
   '**1fPIC_Same as -Cg'#010+
   '**1fPIC_Same as -Cg'#010+
   '**1F<x>_Set file names and paths:'#010+
   '**1F<x>_Set file names and paths:'#010+
-  '**2Fa<x>[,y]_(for a program) l','oad units <x> and [y] before uses is p'+
-  'arsed'#010+
+  '**2Fa<x>[,y]_(for a program) load units <x> and [y] before uses is par'+
+  'sed'#010+
   '**2Fc<x>_Set input codepage to <x>'#010+
   '**2Fc<x>_Set input codepage to <x>'#010+
   '**2FC<x>_Set RC compiler binary name to <x>'#010+
   '**2FC<x>_Set RC compiler binary name to <x>'#010+
-  '**2Fd_Disable the compiler'#039's internal directory cache'#010+
-  '**2FD<x>_Set the directory where to search for compiler utiliti','es'#010+
+  '**2Fd_Disable the compi','ler'#039's internal directory cache'#010+
+  '**2FD<x>_Set the directory where to search for compiler utilities'#010+
   '**2Fe<x>_Redirect error output to <x>'#010+
   '**2Fe<x>_Redirect error output to <x>'#010+
   '**2Ff<x>_Add <x> to framework path (Darwin only)'#010+
   '**2Ff<x>_Add <x> to framework path (Darwin only)'#010+
   '**2FE<x>_Set exe/unit output path to <x>'#010+
   '**2FE<x>_Set exe/unit output path to <x>'#010+
-  '**2Fi<x>_Add <x> to include path'#010+
+  '**2Fi<x>_Add <x','> to include path'#010+
   '**2Fl<x>_Add <x> to library path'#010+
   '**2Fl<x>_Add <x> to library path'#010+
   '**2FL<x>_Use <x> as dynamic linker'#010+
   '**2FL<x>_Use <x> as dynamic linker'#010+
-  '**2Fm<x>','_Load unicode conversion table from <x>.txt in the compiler '+
-  'dir'#010+
+  '**2Fm<x>_Load unicode conversion table from <x>.txt in the compiler di'+
+  'r'#010+
   '**2Fo<x>_Add <x> to object path'#010+
   '**2Fo<x>_Add <x> to object path'#010+
   '**2Fr<x>_Load error message file <x>'#010+
   '**2Fr<x>_Load error message file <x>'#010+
-  '**2FR<x>_Set resource (.res) linker to <x>'#010+
+  '**2FR<x>_Set ','resource (.res) linker to <x>'#010+
   '**2Fu<x>_Add <x> to unit path'#010+
   '**2Fu<x>_Add <x> to unit path'#010+
-  '**2FU<x>_Set unit output path to <','x>, overrides -FE'#010+
+  '**2FU<x>_Set unit output path to <x>, overrides -FE'#010+
   '**2FW<x>_Store generated whole-program optimization feedback in <x>'#010+
   '**2FW<x>_Store generated whole-program optimization feedback in <x>'#010+
-  '**2Fw<x>_Load previously stored whole-program optimization feedback fr'+
-  'om <x>'#010+
+  '**2Fw<x>_Load previously stored whole-program optimization f','eedback '+
+  'from <x>'#010+
   '*g1g_Generate debug information (default format for target)'#010+
   '*g1g_Generate debug information (default format for target)'#010+
-  '*g2gc_Generate ch','ecks for pointers'#010+
+  '*g2gc_Generate checks for pointers'#010+
   '*g2gh_Use heaptrace unit (for memory leak/corruption debugging)'#010+
   '*g2gh_Use heaptrace unit (for memory leak/corruption debugging)'#010+
   '*g2gl_Use line info unit (show more info with backtraces)'#010+
   '*g2gl_Use line info unit (show more info with backtraces)'#010+
-  '*g2go<x>_Set debug information options'#010+
-  '*g3godwarfsets_ Enable DWARF '#039'set'#039' type debug information (br',
-  'eaks gdb < 6.5)'#010+
+  '*g2go<','x>_Set debug information options'#010+
+  '*g3godwarfsets_ Enable DWARF '#039'set'#039' type debug information (bre'+
+  'aks gdb < 6.5)'#010+
   '*g3gostabsabsincludes_ Store absolute/full include file paths in Stabs'+
   '*g3gostabsabsincludes_ Store absolute/full include file paths in Stabs'+
   #010+
   #010+
-  '*g3godwarfmethodclassprefix_ Prefix method names in DWARF with class n'+
-  'ame'#010+
+  '*g3godwarfmethodclassprefix_ Prefix method names in DWARF w','ith class'+
+  ' name'#010+
   '*g2gp_Preserve case in stabs symbol names'#010+
   '*g2gp_Preserve case in stabs symbol names'#010+
-  '*g2gs_Generate Stabs debug informatio','n'#010+
+  '*g2gs_Generate Stabs debug information'#010+
   '*g2gt_Trash local variables (to detect uninitialized uses)'#010+
   '*g2gt_Trash local variables (to detect uninitialized uses)'#010+
   '*g2gv_Generates programs traceable with Valgrind'#010+
   '*g2gv_Generates programs traceable with Valgrind'#010+
-  '*g2gw_Generate DWARFv2 debug information (same as -gw2)'#010+
+  '*g2gw_Generate DWARFv2 debug informa','tion (same as -gw2)'#010+
   '*g2gw2_Generate DWARFv2 debug information'#010+
   '*g2gw2_Generate DWARFv2 debug information'#010+
-  '*g2gw3_Generate DWARFv3 debug in','formation'#010+
+  '*g2gw3_Generate DWARFv3 debug information'#010+
   '*g2gw4_Generate DWARFv4 debug information (experimental)'#010+
   '*g2gw4_Generate DWARFv4 debug information (experimental)'#010+
   '**1i_Information'#010+
   '**1i_Information'#010+
   '**2iD_Return compiler date'#010+
   '**2iD_Return compiler date'#010+
-  '**2iV_Return short compiler version'#010+
+  '**2iV_Return short compiler version',#010+
   '**2iW_Return full compiler version'#010+
   '**2iW_Return full compiler version'#010+
   '**2iSO_Return compiler OS'#010+
   '**2iSO_Return compiler OS'#010+
-  '**2iSP_Return compiler host proc','essor'#010+
+  '**2iSP_Return compiler host processor'#010+
   '**2iTO_Return target OS'#010+
   '**2iTO_Return target OS'#010+
   '**2iTP_Return target processor'#010+
   '**2iTP_Return target processor'#010+
   '**1I<x>_Add <x> to include path'#010+
   '**1I<x>_Add <x> to include path'#010+
   '**1k<x>_Pass <x> to the linker'#010+
   '**1k<x>_Pass <x> to the linker'#010+
   '**1l_Write logo'#010+
   '**1l_Write logo'#010+
-  '**1M<x>_Set language mode to <x>'#010+
+  '**1M<x','>_Set language mode to <x>'#010+
   '**2Mfpc_Free Pascal dialect (default)'#010+
   '**2Mfpc_Free Pascal dialect (default)'#010+
-  '**2Mobjfpc_FPC mode with Obje','ct Pascal support'#010+
+  '**2Mobjfpc_FPC mode with Object Pascal support'#010+
   '**2Mdelphi_Delphi 7 compatibility mode'#010+
   '**2Mdelphi_Delphi 7 compatibility mode'#010+
   '**2Mtp_TP/BP 7.0 compatibility mode'#010+
   '**2Mtp_TP/BP 7.0 compatibility mode'#010+
-  '**2Mmacpas_Macintosh Pascal dialects compatibility mode'#010+
+  '**2Mmacpas_Macintosh Pascal dialects compatibility mo','de'#010+
   '**1n_Do not read the default config files'#010+
   '**1n_Do not read the default config files'#010+
   '**1N<x>_Node tree optimizations'#010+
   '**1N<x>_Node tree optimizations'#010+
-  '**2Nu_Unroll loop','s'#010+
+  '**2Nu_Unroll loops'#010+
   '**1o<x>_Change the name of the executable produced to <x>'#010+
   '**1o<x>_Change the name of the executable produced to <x>'#010+
   '**1O<x>_Optimizations:'#010+
   '**1O<x>_Optimizations:'#010+
   '**2O-_Disable optimizations'#010+
   '**2O-_Disable optimizations'#010+
-  '**2O1_Level 1 optimizations (quick and debugger friendly)'#010+
+  '**2O1_Level 1 optimizations (quick ','and debugger friendly)'#010+
   '**2O2_Level 2 optimizations (-O1 + quick optimizations)'#010+
   '**2O2_Level 2 optimizations (-O1 + quick optimizations)'#010+
-  '**2O3_Level 3 o','ptimizations (-O2 + slow optimizations)'#010+
+  '**2O3_Level 3 optimizations (-O2 + slow optimizations)'#010+
   '**2Oa<x>=<y>_Set alignment'#010+
   '**2Oa<x>=<y>_Set alignment'#010+
   '**2Oo[NO]<x>_Enable or disable optimizations, see fpc -i for possible '+
   '**2Oo[NO]<x>_Enable or disable optimizations, see fpc -i for possible '+
   'values'#010+
   'values'#010+
-  '**2Op<x>_Set target cpu for optimizing, see fpc -i for possible values'+
-  #010+
-  '**2OW<x>_Generate whole-p','rogram optimization feedback for optimizati'+
-  'on <x>, see fpc -i for possible values'#010+
-  '**2Ow<x>_Perform whole-program optimization <x>, see fpc -i for possib'+
-  'le values'#010+
+  '**','2Op<x>_Set target cpu for optimizing, see fpc -i for possible valu'+
+  'es'#010+
+  '**2OW<x>_Generate whole-program optimization feedback for optimization'+
+  ' <x>, see fpc -i for possible values'#010+
+  '**2Ow<x>_Perform whole-program optimization <x>, see fpc -i for ','poss'+
+  'ible values'#010+
   '**2Os_Optimize for size rather than speed'#010+
   '**2Os_Optimize for size rather than speed'#010+
-  '**1pg_Generate profile code for gpro','f (defines FPC_PROFILE)'#010+
+  '**1pg_Generate profile code for gprof (defines FPC_PROFILE)'#010+
   '**1R<x>_Assembler reading style:'#010+
   '**1R<x>_Assembler reading style:'#010+
   '**2Rdefault_Use default assembler for target'#010+
   '**2Rdefault_Use default assembler for target'#010+
   '3*2Ratt_Read AT&T style assembler'#010+
   '3*2Ratt_Read AT&T style assembler'#010+
-  '3*2Rintel_Read Intel style assembler'#010+
+  '3*2Rintel_','Read Intel style assembler'#010+
   '6*2RMOT_Read motorola style assembler'#010+
   '6*2RMOT_Read motorola style assembler'#010+
   '**1S<x>_Syntax options:'#010+
   '**1S<x>_Syntax options:'#010+
-  '**2S2','_Same as -Mobjfpc'#010+
+  '**2S2_Same as -Mobjfpc'#010+
   '**2Sc_Support operators like C (*=,+=,/= and -=)'#010+
   '**2Sc_Support operators like C (*=,+=,/= and -=)'#010+
   '**2Sa_Turn on assertions'#010+
   '**2Sa_Turn on assertions'#010+
   '**2Sd_Same as -Mdelphi'#010+
   '**2Sd_Same as -Mdelphi'#010+
-  '**2Se<x>_Error options. <x> is a combination of the following:'#010+
-  '**3*_<n> : Compiler halts after the <n> errors (default is 1)'#010,
+  '**2Se<x>_Error options. <x> is ','a combination of the following:'#010+
+  '**3*_<n> : Compiler halts after the <n> errors (default is 1)'#010+
   '**3*_w : Compiler also halts after warnings'#010+
   '**3*_w : Compiler also halts after warnings'#010+
   '**3*_n : Compiler also halts after notes'#010+
   '**3*_n : Compiler also halts after notes'#010+
   '**3*_h : Compiler also halts after hints'#010+
   '**3*_h : Compiler also halts after hints'#010+
-  '**2Sg_Enable LABEL and GOTO (default in -Mtp and -Mdelphi)'#010+
-  '**2Sh_Use ansistrings by default instead of shortstring','s'#010+
+  '**2Sg_Enable LABEL a','nd GOTO (default in -Mtp and -Mdelphi)'#010+
+  '**2Sh_Use ansistrings by default instead of shortstrings'#010+
   '**2Si_Turn on inlining of procedures/functions declared as "inline"'#010+
   '**2Si_Turn on inlining of procedures/functions declared as "inline"'#010+
   '**2Sk_Load fpcylix unit'#010+
   '**2Sk_Load fpcylix unit'#010+
   '**2SI<x>_Set interface style to <x>'#010+
   '**2SI<x>_Set interface style to <x>'#010+
-  '**3SIcom_COM compatible interface (default)'#010+
+  '**3SIcom_COM com','patible interface (default)'#010+
   '**3SIcorba_CORBA compatible interface'#010+
   '**3SIcorba_CORBA compatible interface'#010+
-  '**2Sm_Support macros like C ','(global)'#010+
+  '**2Sm_Support macros like C (global)'#010+
   '**2So_Same as -Mtp'#010+
   '**2So_Same as -Mtp'#010+
   '**2Ss_Constructor name must be init (destructor must be done)'#010+
   '**2Ss_Constructor name must be init (destructor must be done)'#010+
-  '**2Sx_Enable exception keywords (default in Delphi/ObjFPC modes)'#010+
+  '**2Sx_Enable exception keywords (default in Delphi/ObjFP','C modes)'#010+
   '**2Sy_@<pointer> returns a typed pointer, same as $T+'#010+
   '**2Sy_@<pointer> returns a typed pointer, same as $T+'#010+
-  '**1s_Do not call assembler and ','linker'#010+
+  '**1s_Do not call assembler and linker'#010+
   '**2sh_Generate script to link on host'#010+
   '**2sh_Generate script to link on host'#010+
   '**2st_Generate script to link on target'#010+
   '**2st_Generate script to link on target'#010+
   '**2sr_Skip register allocation phase (use with -alr)'#010+
   '**2sr_Skip register allocation phase (use with -alr)'#010+
-  '**1T<x>_Target operating system:'#010+
+  '**1T<x>_','Target operating system:'#010+
   '3*2Tdarwin_Darwin/Mac OS X'#010+
   '3*2Tdarwin_Darwin/Mac OS X'#010+
-  '3*2Temx_OS/2 via EMX (including EMX/RSX ex','tender)'#010+
+  '3*2Temx_OS/2 via EMX (including EMX/RSX extender)'#010+
   '3*2Tfreebsd_FreeBSD'#010+
   '3*2Tfreebsd_FreeBSD'#010+
   '3*2Tgo32v2_Version 2 of DJ Delorie DOS extender'#010+
   '3*2Tgo32v2_Version 2 of DJ Delorie DOS extender'#010+
-  '3*2Tiphonesim_ iPhoneSimulator from iOS SDK 3.2+ (older versions: -Tda'+
+  '3*2Tiphonesim_ iPhoneSimulator from iOS SDK 3.2+ (older versions: -Tda',
   'rwin)'#010+
   'rwin)'#010+
   '3*2Tlinux_Linux'#010+
   '3*2Tlinux_Linux'#010+
   '3*2Tnetbsd_NetBSD'#010+
   '3*2Tnetbsd_NetBSD'#010+
   '3*2Tnetware_Novell Netware Module (clib)'#010+
   '3*2Tnetware_Novell Netware Module (clib)'#010+
-  '3*2Tnetwlibc_','Novell Netware Module (libc)'#010+
+  '3*2Tnetwlibc_Novell Netware Module (libc)'#010+
   '3*2Topenbsd_OpenBSD'#010+
   '3*2Topenbsd_OpenBSD'#010+
   '3*2Tos2_OS/2 / eComStation'#010+
   '3*2Tos2_OS/2 / eComStation'#010+
   '3*2Tsunos_SunOS/Solaris'#010+
   '3*2Tsunos_SunOS/Solaris'#010+
   '3*2Tsymbian_Symbian OS'#010+
   '3*2Tsymbian_Symbian OS'#010+
   '3*2Tsolaris_Solaris'#010+
   '3*2Tsolaris_Solaris'#010+
-  '3*2Twatcom_Watcom compatible DOS extender'#010+
+  '3*2','Twatcom_Watcom compatible DOS extender'#010+
   '3*2Twdosx_WDOSX DOS extender'#010+
   '3*2Twdosx_WDOSX DOS extender'#010+
   '3*2Twin32_Windows 32 Bit'#010+
   '3*2Twin32_Windows 32 Bit'#010+
-  '3','*2Twince_Windows CE'#010+
+  '3*2Twince_Windows CE'#010+
   '4*2Tdarwin_Darwin/Mac OS X'#010+
   '4*2Tdarwin_Darwin/Mac OS X'#010+
   '4*2Tlinux_Linux'#010+
   '4*2Tlinux_Linux'#010+
   '4*2Twin64_Win64 (64 bit Windows systems)'#010+
   '4*2Twin64_Win64 (64 bit Windows systems)'#010+
   '6*2Tamiga_Commodore Amiga'#010+
   '6*2Tamiga_Commodore Amiga'#010+
-  '6*2Tatari_Atari ST/STe/TT'#010+
+  '6*2Tatari_Atari ','ST/STe/TT'#010+
   '6*2Tlinux_Linux'#010+
   '6*2Tlinux_Linux'#010+
   '6*2Tpalmos_PalmOS'#010+
   '6*2Tpalmos_PalmOS'#010+
   'A*2Tdarwin_Darwin/iPhoneOS/iOS'#010+
   'A*2Tdarwin_Darwin/iPhoneOS/iOS'#010+
   'A*2Tlinux_Linux'#010+
   'A*2Tlinux_Linux'#010+
-  'A*2','Twince_Windows CE'#010+
+  'A*2Twince_Windows CE'#010+
   'P*2Tamiga_AmigaOS'#010+
   'P*2Tamiga_AmigaOS'#010+
   'P*2Tdarwin_Darwin/Mac OS X'#010+
   'P*2Tdarwin_Darwin/Mac OS X'#010+
   'P*2Tlinux_Linux'#010+
   'P*2Tlinux_Linux'#010+
   'P*2Tmacos_Mac OS (classic)'#010+
   'P*2Tmacos_Mac OS (classic)'#010+
   'P*2Tmorphos_MorphOS'#010+
   'P*2Tmorphos_MorphOS'#010+
-  'S*2Tsolaris_Solaris'#010+
+  'S*2Tsolaris_Solaris'#010,
   'S*2Tlinux_Linux'#010+
   'S*2Tlinux_Linux'#010+
   '**1u<x>_Undefines the symbol <x>'#010+
   '**1u<x>_Undefines the symbol <x>'#010+
   '**1U_Unit options:'#010+
   '**1U_Unit options:'#010+
-  '**2Un_Do not check where t','he unit name matches the file name'#010+
+  '**2Un_Do not check where the unit name matches the file name'#010+
   '**2Ur_Generate release unit files (never automatically recompiled)'#010+
   '**2Ur_Generate release unit files (never automatically recompiled)'#010+
   '**2Us_Compile a system unit'#010+
   '**2Us_Compile a system unit'#010+
-  '**1v<x>_Be verbose. <x> is a combination of the following letters:'#010+
-  '**2*_e : Show errors (default)       0 : Sh','ow nothing (except errors'+
-  ')'#010+
+  '**1v<x>_Be verbo','se. <x> is a combination of the following letters:'#010+
+  '**2*_e : Show errors (default)       0 : Show nothing (except errors)'#010+
   '**2*_w : Show warnings               u : Show unit info'#010+
   '**2*_w : Show warnings               u : Show unit info'#010+
-  '**2*_n : Show notes                  t : Show tried/used files'#010+
+  '**2*_n : Show notes                  t : Show tried/used files'#010,
   '**2*_h : Show hints                  c : Show conditionals'#010+
   '**2*_h : Show hints                  c : Show conditionals'#010+
-  '**2*_i : Show general info         ','  d : Show debug info'#010+
+  '**2*_i : Show general info           d : Show debug info'#010+
   '**2*_l : Show linenumbers            r : Rhide/GCC compatibility mode'#010+
   '**2*_l : Show linenumbers            r : Rhide/GCC compatibility mode'#010+
-  '**2*_s : Show time stamps            q : Show message numbers'#010+
+  '**2*_s : Show time stamps            q : Show message ','numbers'#010+
   '**2*_a : Show everything             x : Executable info (Win32 only)'#010+
   '**2*_a : Show everything             x : Executable info (Win32 only)'#010+
-  '**2*_b : Write f','ile names messages   p : Write tree.log with parse t'+
-  'ree'#010+
+  '**2*_b : Write file names messages   p : Write tree.log with parse tre'+
+  'e'#010+
   '**2*_    with full path              v : Write fpcdebug.txt with'#010+
   '**2*_    with full path              v : Write fpcdebug.txt with'#010+
-  '**2*_                                    lots of debugging info'#010+
-  '**2*_m<x>,<y> : Don'#039't show messages numbered <x> and <y','>'#010+
+  '**2*_                    ','                lots of debugging info'#010+
+  '**2*_m<x>,<y> : Don'#039't show messages numbered <x> and <y>'#010+
   '**1W<x>_Target-specific options (targets)'#010+
   '**1W<x>_Target-specific options (targets)'#010+
   '3*2WA_Specify native type application (Windows)'#010+
   '3*2WA_Specify native type application (Windows)'#010+
   '4*2WA_Specify native type application (Windows)'#010+
   '4*2WA_Specify native type application (Windows)'#010+
-  'A*2WA_Specify native type application (Windows)'#010+
-  '3*2Wb_Create a bundle instead of a library (Darwin)'#010,
+  'A*2WA_','Specify native type application (Windows)'#010+
+  '3*2Wb_Create a bundle instead of a library (Darwin)'#010+
   'P*2Wb_Create a bundle instead of a library (Darwin)'#010+
   'P*2Wb_Create a bundle instead of a library (Darwin)'#010+
   'p*2Wb_Create a bundle instead of a library (Darwin)'#010+
   'p*2Wb_Create a bundle instead of a library (Darwin)'#010+
-  'A*2Wb_Create a bundle instead of a library (Darwin)'#010+
+  'A*2Wb_Create a bundle instead of a library',' (Darwin)'#010+
   '4*2Wb_Create a bundle instead of a library (Darwin)'#010+
   '4*2Wb_Create a bundle instead of a library (Darwin)'#010+
-  '3*2WB_Create a relocatable image',' (Windows, Symbian)'#010+
+  '3*2WB_Create a relocatable image (Windows, Symbian)'#010+
   '3*2WBxxxx_Set image base to xxxx (Windows, Symbian)'#010+
   '3*2WBxxxx_Set image base to xxxx (Windows, Symbian)'#010+
   '4*2WB_Create a relocatable image (Windows)'#010+
   '4*2WB_Create a relocatable image (Windows)'#010+
-  '4*2WBxxxx_Set image base to xxxx (Windows)'#010+
+  '4*2WBxxxx_Set image base to xxx','x (Windows)'#010+
   'A*2WB_Create a relocatable image (Windows, Symbian)'#010+
   'A*2WB_Create a relocatable image (Windows, Symbian)'#010+
-  'A*2WBxxxx_Set image base to xx','xx (Windows, Symbian)'#010+
+  'A*2WBxxxx_Set image base to xxxx (Windows, Symbian)'#010+
   '3*2WC_Specify console type application (EMX, OS/2, Windows)'#010+
   '3*2WC_Specify console type application (EMX, OS/2, Windows)'#010+
   '4*2WC_Specify console type application (EMX, OS/2, Windows)'#010+
   '4*2WC_Specify console type application (EMX, OS/2, Windows)'#010+
-  'A*2WC_Specify console type application (Windows)'#010+
-  'P*2WC_Specify console type application (Classic M','ac OS)'#010+
+  'A*2W','C_Specify console type application (Windows)'#010+
+  'P*2WC_Specify console type application (Classic Mac OS)'#010+
   '3*2WD_Use DEFFILE to export functions of DLL or EXE (Windows)'#010+
   '3*2WD_Use DEFFILE to export functions of DLL or EXE (Windows)'#010+
   '4*2WD_Use DEFFILE to export functions of DLL or EXE (Windows)'#010+
   '4*2WD_Use DEFFILE to export functions of DLL or EXE (Windows)'#010+
-  'A*2WD_Use DEFFILE to export functions of DLL or EXE (Windows)'#010+
+  'A*2WD_Use DEFFI','LE to export functions of DLL or EXE (Windows)'#010+
   '3*2We_Use external resources (Darwin)'#010+
   '3*2We_Use external resources (Darwin)'#010+
-  '4*2We_Use',' external resources (Darwin)'#010+
+  '4*2We_Use external resources (Darwin)'#010+
   'A*2We_Use external resources (Darwin)'#010+
   'A*2We_Use external resources (Darwin)'#010+
   'P*2We_Use external resources (Darwin)'#010+
   'P*2We_Use external resources (Darwin)'#010+
   'p*2We_Use external resources (Darwin)'#010+
   'p*2We_Use external resources (Darwin)'#010+
-  '3*2WF_Specify full-screen type application (EMX, OS/2)'#010+
-  '3*2WG_Specify graphic type application (EM','X, OS/2, Windows)'#010+
+  '3*2','WF_Specify full-screen type application (EMX, OS/2)'#010+
+  '3*2WG_Specify graphic type application (EMX, OS/2, Windows)'#010+
   '4*2WG_Specify graphic type application (EMX, OS/2, Windows)'#010+
   '4*2WG_Specify graphic type application (EMX, OS/2, Windows)'#010+
   'A*2WG_Specify graphic type application (Windows)'#010+
   'A*2WG_Specify graphic type application (Windows)'#010+
-  'P*2WG_Specify graphic type application (Classic Mac OS)'#010+
+  'P*2WG_Specify graph','ic type application (Classic Mac OS)'#010+
   '3*2Wi_Use internal resources (Darwin)'#010+
   '3*2Wi_Use internal resources (Darwin)'#010+
-  '4*2Wi_Use internal ','resources (Darwin)'#010+
+  '4*2Wi_Use internal resources (Darwin)'#010+
   'A*2Wi_Use internal resources (Darwin)'#010+
   'A*2Wi_Use internal resources (Darwin)'#010+
   'P*2Wi_Use internal resources (Darwin)'#010+
   'P*2Wi_Use internal resources (Darwin)'#010+
   'p*2Wi_Use internal resources (Darwin)'#010+
   'p*2Wi_Use internal resources (Darwin)'#010+
-  '3*2WI_Turn on/off the usage of import sections (Windows)'#010+
-  '4*2WI_Turn on/off the usage of import sections (Wi','ndows)'#010+
+  '3*2WI_Turn on','/off the usage of import sections (Windows)'#010+
+  '4*2WI_Turn on/off the usage of import sections (Windows)'#010+
   'A*2WI_Turn on/off the usage of import sections (Windows)'#010+
   'A*2WI_Turn on/off the usage of import sections (Windows)'#010+
   '3*2WM<x>_Minimum Mac OS X deployment version: 10.4, 10.5.1, ... (Darwi'+
   '3*2WM<x>_Minimum Mac OS X deployment version: 10.4, 10.5.1, ... (Darwi'+
   'n)'#010+
   'n)'#010+
-  '4*2WM<x>_Minimum Mac OS X deployment version: 10.4, 10.5.1, ... (Darwi'+
-  'n)'#010+
-  'p*2WM<x>_Minimum Mac OS X depl','oyment version: 10.4, 10.5.1, ... (Dar'+
+  '4*2WM<x>_','Minimum Mac OS X deployment version: 10.4, 10.5.1, ... (Dar'+
   'win)'#010+
   'win)'#010+
+  'p*2WM<x>_Minimum Mac OS X deployment version: 10.4, 10.5.1, ... (Darwi'+
+  'n)'#010+
   'P*2WM<x>_Minimum Mac OS X deployment version: 10.4, 10.5.1, ... (Darwi'+
   'P*2WM<x>_Minimum Mac OS X deployment version: 10.4, 10.5.1, ... (Darwi'+
   'n)'#010+
   'n)'#010+
-  '3*2WN_Do not generate relocation code, needed for debugging (Windows)'#010+
-  '4*2WN_Do not generate relocation code, needed for debu','gging (Windows'+
+  '3*2WN_Do not generate relocati','on code, needed for debugging (Windows'+
   ')'#010+
   ')'#010+
+  '4*2WN_Do not generate relocation code, needed for debugging (Windows)'#010+
   'A*2WN_Do not generate relocation code, needed for debugging (Windows)'#010+
   'A*2WN_Do not generate relocation code, needed for debugging (Windows)'#010+
-  'A*2Wpxxxx_Specify the controller type, see fpc -i for possible values'#010+
+  'A*2Wpxxxx_Specify the controller type, see fpc -i for possib','le value'+
+  's'#010+
   'V*2Wpxxxx_Specify the controller type, see fpc -i for possible values'#010+
   'V*2Wpxxxx_Specify the controller type, see fpc -i for possible values'#010+
-  '3*2WP<x>_Minim','um iOS deployment version: 3.0, 5.0.1, ... (iphonesim)'+
-  #010+
+  '3*2WP<x>_Minimum iOS deployment version: 3.0, 5.0.1, ... (iphonesim)'#010+
   'A*2WP<x>_Minimum iOS deployment version: 3.0, 5.0.1, ... (Darwin)'#010+
   'A*2WP<x>_Minimum iOS deployment version: 3.0, 5.0.1, ... (Darwin)'#010+
-  '3*2WR_Generate relocation code (Windows)'#010+
+  '3*2WR_Generate relocation',' code (Windows)'#010+
   '4*2WR_Generate relocation code (Windows)'#010+
   '4*2WR_Generate relocation code (Windows)'#010+
-  'A*2WR_Generate relocation code (Windo','ws)'#010+
+  'A*2WR_Generate relocation code (Windows)'#010+
   'P*2WT_Specify MPW tool type application (Classic Mac OS)'#010+
   'P*2WT_Specify MPW tool type application (Classic Mac OS)'#010+
   '**2WX_Enable executable stack (Linux)'#010+
   '**2WX_Enable executable stack (Linux)'#010+
   '**1X_Executable options:'#010+
   '**1X_Executable options:'#010+
-  '**2Xc_Pass --shared/-dynamic to the linker (BeOS, Darwin, FreeBSD, Lin'+
-  'ux)'#010+
-  '**2Xd_Do not use standard library search p','ath (needed for cross comp'+
-  'ile)'#010+
+  '**2Xc_Pass --shared/-d','ynamic to the linker (BeOS, Darwin, FreeBSD, L'+
+  'inux)'#010+
+  '**2Xd_Do not use standard library search path (needed for cross compil'+
+  'e)'#010+
   '**2Xe_Use external linker'#010+
   '**2Xe_Use external linker'#010+
   '**2Xg_Create debuginfo in a separate file and add a debuglink section '+
   '**2Xg_Create debuginfo in a separate file and add a debuglink section '+
   'to executable'#010+
   'to executable'#010+
-  '**2XD_Try to link units dynamically      (defines FPC_LINK_DYNAMIC)'#010+
+  '**2XD','_Try to link units dynamically      (defines FPC_LINK_DYNAMIC)'#010+
   '**2Xi_Use internal linker'#010+
   '**2Xi_Use internal linker'#010+
-  '**2Xm','_Generate link map'#010+
+  '**2Xm_Generate link map'#010+
   '**2XM<x>_Set the name of the '#039'main'#039' program routine (default i'+
   '**2XM<x>_Set the name of the '#039'main'#039' program routine (default i'+
   's '#039'main'#039')'#010+
   's '#039'main'#039')'#010+
-  '**2XP<x>_Prepend the binutils names with the prefix <x>'#010+
+  '**2XP<x>_Prepend the binutils names with the prefix <x>',#010+
   '**2Xr<x>_Set the linker'#039's rlink-path to <x> (needed for cross comp'+
   '**2Xr<x>_Set the linker'#039's rlink-path to <x> (needed for cross comp'+
-  'ile, see the ld manual for ','more information) (BeOS, Linux)'#010+
+  'ile, see the ld manual for more information) (BeOS, Linux)'#010+
   '**2XR<x>_Prepend <x> to all linker search paths (BeOS, Darwin, FreeBSD'+
   '**2XR<x>_Prepend <x> to all linker search paths (BeOS, Darwin, FreeBSD'+
   ', Linux, Mac OS, Solaris)'#010+
   ', Linux, Mac OS, Solaris)'#010+
-  '**2Xs_Strip all symbols from executable'#010+
+  '**2Xs_Strip all sy','mbols from executable'#010+
   '**2XS_Try to link units statically (default, defines FPC_LINK_STATIC)'#010+
   '**2XS_Try to link units statically (default, defines FPC_LINK_STATIC)'#010+
-  '**','2Xt_Link with static libraries (-static is passed to linker)'#010+
+  '**2Xt_Link with static libraries (-static is passed to linker)'#010+
   '**2XX_Try to smartlink units             (defines FPC_LINK_SMART)'#010+
   '**2XX_Try to smartlink units             (defines FPC_LINK_SMART)'#010+
   '**1*_'#010+
   '**1*_'#010+
-  '**1?_Show this help'#010+
+  '**1?_Show thi','s help'#010+
   '**1h_Shows this help without waiting'
   '**1h_Shows this help without waiting'
 );
 );

+ 18 - 15
compiler/ncgutil.pas

@@ -1997,22 +1997,25 @@ implementation
           LOC_CFPUREGISTER :
           LOC_CFPUREGISTER :
             begin
             begin
 {$if defined(sparc) or defined(arm)}
 {$if defined(sparc) or defined(arm)}
-              { Arm and Sparc passes floats in int registers, when loading to fpu register
-                we need a temp }
-              sizeleft := TCGSize2Size[destloc.size];
-              tg.GetTemp(list,sizeleft,sizeleft,tt_normal,tempref);
-              href:=tempref;
-              while assigned(paraloc) do
+              { Arm (with softfloat ABI) and Sparc passes floats in int registers, 
+                when loading to fpu register we need a temp }
+              if (paraloc^.loc = LOC_REGISTER) then 
                 begin
                 begin
-                  unget_para(paraloc^);
-                  cg.a_load_cgparaloc_ref(list,paraloc^,href,sizeleft,destloc.reference.alignment);
-                  inc(href.offset,TCGSize2Size[paraloc^.size]);
-                  dec(sizeleft,TCGSize2Size[paraloc^.size]);
-                  paraloc:=paraloc^.next;
-                end;
-              gen_alloc_regloc(list,destloc);
-              cg.a_loadfpu_ref_reg(list,destloc.size,destloc.size,tempref,destloc.register);
-              tg.UnGetTemp(list,tempref);
+                  sizeleft := TCGSize2Size[destloc.size];
+                  tg.GetTemp(list,sizeleft,sizeleft,tt_normal,tempref);
+                  href:=tempref;
+                  while assigned(paraloc) do
+                    begin
+                      unget_para(paraloc^);
+                      cg.a_load_cgparaloc_ref(list,paraloc^,href,sizeleft,destloc.reference.alignment);
+                      inc(href.offset,TCGSize2Size[paraloc^.size]);
+                      dec(sizeleft,TCGSize2Size[paraloc^.size]);
+                      paraloc:=paraloc^.next;
+                    end;
+                  gen_alloc_regloc(list,destloc);
+                  cg.a_loadfpu_ref_reg(list,destloc.size,destloc.size,tempref,destloc.register);
+                  tg.UnGetTemp(list,tempref);
+               end;
 {$else sparc}
 {$else sparc}
               unget_para(paraloc^);
               unget_para(paraloc^);
               gen_alloc_regloc(list,destloc);
               gen_alloc_regloc(list,destloc);

+ 33 - 0
compiler/options.pas

@@ -2883,6 +2883,11 @@ begin
     undef_system_macro('FPC_ABI_'+abi2str[abi]);
     undef_system_macro('FPC_ABI_'+abi2str[abi]);
   def_system_macro('FPC_ABI_'+abi2str[target_info.abi]);
   def_system_macro('FPC_ABI_'+abi2str[target_info.abi]);
 
 
+  { Define FPC_ABI_EABI in addition to FPC_ABI_EABIHF on EABI VFP hardfloat
+    systems since most code needs to behave the same on both}
+  if target_info.abi = abi_eabihf then 
+    def_system_macro('FPC_ABI_EABI');
+
   { Write logo }
   { Write logo }
   if option.ParaLogo then
   if option.ParaLogo then
     option.writelogo;
     option.writelogo;
@@ -3050,6 +3055,24 @@ begin
 {$endif cpufpemu}
 {$endif cpufpemu}
     end;
     end;
 
 
+{$ifdef arm}
+  if target_info.abi = abi_eabihf then 
+    begin
+      if not(option.FPUSetExplicitly) then 
+        begin
+          init_settings.fputype:=fpu_vfpv3_d16
+        end
+      else
+        begin
+          if not (init_settings.fputype in [fpu_vfpv2,fpu_vfpv3,fpu_vfpv3_d16]) then 
+            begin
+              Message(option_illegal_fpu_eabihf);
+              StopOptions(1);
+            end;
+        end;
+    end;
+{$endif arm}
+
 {$ifdef arm}
 {$ifdef arm}
 { set default cpu type to ARMv6 for Darwin unless specified otherwise }
 { set default cpu type to ARMv6 for Darwin unless specified otherwise }
 if (target_info.system=system_arm_darwin) then
 if (target_info.system=system_arm_darwin) then
@@ -3059,6 +3082,16 @@ if (target_info.system=system_arm_darwin) then
     if not option.OptCPUSetExplicitly then
     if not option.OptCPUSetExplicitly then
       init_settings.optimizecputype:=cpu_armv6;
       init_settings.optimizecputype:=cpu_armv6;
   end;
   end;
+
+{ set default cpu type to ARMv7 for ARMHF unless specified otherwise }
+if (target_info.abi = abi_eabihf) then 
+  begin
+    if not option.CPUSetExplicitly then
+      init_settings.cputype:=cpu_armv7;
+    if not option.OptCPUSetExplicitly then
+      init_settings.optimizecputype:=cpu_armv7;
+  end;
+
 {$endif arm}
 {$endif arm}
 
 
   { now we can define cpu and fpu type }
   { now we can define cpu and fpu type }

+ 1 - 0
compiler/pp.pas

@@ -43,6 +43,7 @@ program pp;
   FPC_ARMEB           create an arm big endian compiler
   FPC_ARMEB           create an arm big endian compiler
   FPC_OARM            create an arm oabi compiler, only needed when the host
   FPC_OARM            create an arm oabi compiler, only needed when the host
                       compiler is ARMEL or ARMEB
                       compiler is ARMEL or ARMEB
+  FPC_ARMHF           create an armhf (eabi vfp variant) compiler
   -----------------------------------------------------------------
   -----------------------------------------------------------------
   cpuflags            The target processor has status flags (on by default)
   cpuflags            The target processor has status flags (on by default)
   cpufpemu            The target compiler will also support emitting software
   cpufpemu            The target compiler will also support emitting software

+ 1 - 1
compiler/systems.inc

@@ -210,7 +210,7 @@
 
 
        tabi = (abi_default
        tabi = (abi_default
             ,abi_powerpc_sysv,abi_powerpc_aix
             ,abi_powerpc_sysv,abi_powerpc_aix
-            ,abi_eabi,abi_armeb
+            ,abi_eabi,abi_armeb,abi_eabihf
        );
        );
 
 
 
 

+ 1 - 1
compiler/systems.pas

@@ -314,7 +314,7 @@ interface
              'mips','arm', 'powerpc64', 'avr', 'mipsel');
              'mips','arm', 'powerpc64', 'avr', 'mipsel');
 
 
        abi2str : array[tabi] of string[10] =
        abi2str : array[tabi] of string[10] =
-         ('DEFAULT','SYSV','AIX','EABI','ARMEB');
+         ('DEFAULT','SYSV','AIX','EABI','ARMEB','EABIHF');
 
 
     var
     var
        targetinfos   : array[tsystem] of psysteminfo;
        targetinfos   : array[tsystem] of psysteminfo;

+ 65 - 0
compiler/systems/i_linux.pas

@@ -534,6 +534,70 @@ unit i_linux;
             abi : abi_default
             abi : abi_default
           );
           );
 
 
+{$ifdef FPC_ARMHF}
+       system_arm_linux_info : tsysteminfo =
+          (
+            system       : system_arm_Linux;
+            name         : 'Linux for ARMHF';
+            shortname    : 'Linux';
+            flags        : [tf_needs_symbol_size,tf_needs_symbol_type,tf_files_case_sensitive,
+                            tf_requires_proper_alignment,
+                            tf_smartlink_sections,tf_smartlink_library,tf_has_winlike_resources];
+            cpu          : cpu_arm;
+            unit_env     : 'LINUXUNITS';
+            extradefines : 'UNIX;HASUNIX;CPUARMHF';
+            exeext       : '';
+            defext       : '.def';
+            scriptext    : '.sh';
+            smartext     : '.sl';
+            unitext      : '.ppu';
+            unitlibext   : '.ppl';
+            asmext       : '.s';
+            objext       : '.o';
+            resext       : '.res';
+            resobjext    : '.or';
+            sharedlibext : '.so';
+            staticlibext : '.a';
+            staticlibprefix : 'libp';
+            sharedlibprefix : 'lib';
+            sharedClibext : '.so';
+            staticClibext : '.a';
+            staticClibprefix : 'lib';
+            sharedClibprefix : 'lib';
+            importlibprefix : 'libimp';
+            importlibext : '.a';
+            Cprefix      : '';
+            newline      : #10;
+            dirsep       : '/';
+            assem        : as_gas;
+            assemextern  : as_gas;
+            link         : nil;
+            linkextern   : nil;
+            ar           : ar_gnu_ar;
+            res          : res_elf;
+            dbg          : dbg_stabs;
+            script       : script_unix;
+            endian       : endian_little;
+            alignment    :
+              (
+                procalign       : 4;
+                loopalign       : 4;
+                jumpalign       : 0;
+                constalignmin   : 0;
+                constalignmax   : 8;
+                varalignmin     : 0;
+                varalignmax     : 8;
+                localalignmin   : 4;
+                localalignmax   : 8;
+                recordalignmin  : 0;
+                recordalignmax  : 8;
+                maxCrecordalign : 8
+              );
+            first_parm_offset : 8;
+            stacksize    : 8*1024*1024;
+            abi : abi_eabihf
+          );
+{$else FPC_ARMHF}
 {$ifdef FPC_ARMEL}
 {$ifdef FPC_ARMEL}
        system_arm_linux_info : tsysteminfo =
        system_arm_linux_info : tsysteminfo =
           (
           (
@@ -726,6 +790,7 @@ unit i_linux;
           );
           );
 {$endif FPC_ARMEB}
 {$endif FPC_ARMEB}
 {$endif FPC_ARMEL}
 {$endif FPC_ARMEL}
+{$endif FPC_ARMHF}
 
 
        system_mips_linux_info : tsysteminfo =
        system_mips_linux_info : tsysteminfo =
           (
           (

+ 4 - 0
compiler/systems/t_linux.pas

@@ -185,11 +185,15 @@ begin
 {$endif powerpc64}
 {$endif powerpc64}
 
 
 {$ifdef arm}
 {$ifdef arm}
+{$ifdef FPC_ARMHF}
+     defdynlinker:='/lib/arm-linux-gnueabihf/ld-linux.so.3';
+{$else FPC_ARMHF}
 {$ifdef FPC_ARMEL}
 {$ifdef FPC_ARMEL}
      defdynlinker:='/lib/ld-linux.so.3';
      defdynlinker:='/lib/ld-linux.so.3';
 {$else FPC_ARMEL}
 {$else FPC_ARMEL}
      defdynlinker:='/lib/ld-linux.so.2';
      defdynlinker:='/lib/ld-linux.so.2';
 {$endif FPC_ARMEL}
 {$endif FPC_ARMEL}
+{$endif FPC_ARMHF}
 {$endif arm}
 {$endif arm}
 
 
 {$ifdef mips}
 {$ifdef mips}

+ 1 - 1
rtl/arm/arm.inc

@@ -30,7 +30,7 @@ const
 {$if not(defined(wince)) and not(defined(gba)) and not(defined(nds)) and not(defined(FPUSOFT)) and not(defined(FPULIBGCC))}
 {$if not(defined(wince)) and not(defined(gba)) and not(defined(nds)) and not(defined(FPUSOFT)) and not(defined(FPULIBGCC))}
 
 
 {$define FPC_SYSTEM_HAS_SYSINITFPU}
 {$define FPC_SYSTEM_HAS_SYSINITFPU}
-{$if not defined(darwin) and not defined(FPUVFPV2) and not defined(FPUVFPV3)}
+{$if not defined(darwin) and not defined(FPUVFPV2) and not defined(FPUVFPV3) and not defined(FPUVFPV3_D16)}
 Procedure SysInitFPU;{$ifdef SYSTEMINLINE}inline;{$endif}
 Procedure SysInitFPU;{$ifdef SYSTEMINLINE}inline;{$endif}
 begin
 begin
   { Enable FPU exceptions, but disable INEXACT, UNDERFLOW, DENORMAL }
   { Enable FPU exceptions, but disable INEXACT, UNDERFLOW, DENORMAL }

+ 1 - 1
rtl/arm/math.inc

@@ -14,7 +14,7 @@
 
 
  **********************************************************************}
  **********************************************************************}
 
 
-{$if defined(FPUFPA) or defined(FPUFPA10) or defined(FPUFPA11) or defined(FPUVFPV2) or defined(FPUVFPV3)}
+{$if defined(FPUFPA) or defined(FPUFPA10) or defined(FPUFPA11) or defined(FPUVFPV2) or defined(FPUVFPV3) or defined(FPUVFPV3_D16)}
     {$define FPC_SYSTEM_HAS_ABS}
     {$define FPC_SYSTEM_HAS_ABS}
     function fpc_abs_real(d : ValReal) : ValReal;compilerproc;
     function fpc_abs_real(d : ValReal) : ValReal;compilerproc;
     begin
     begin

+ 1 - 1
rtl/arm/mathu.inc

@@ -177,7 +177,7 @@ procedure ClearExceptions(RaisePending: Boolean =true);
 begin
 begin
 end;
 end;
 
 
-{$elseif defined(darwin) or defined(FPUVFPV2) or defined(FPUVFPV3)}
+{$elseif defined(darwin) or defined(FPUVFPV2) or defined(FPUVFPV3) or defined(FPUVFPV3_d16)}
 
 
 const
 const
   _VFP_ENABLE_IM  =  1 shl 8;         { invalid operation      }
   _VFP_ENABLE_IM  =  1 shl 8;         { invalid operation      }

+ 3 - 3
rtl/arm/setjump.inc

@@ -16,7 +16,7 @@
 
 
 function fpc_setjmp(var S : jmp_buf) : longint;assembler;[Public, alias : 'FPC_SETJMP'];nostackframe; compilerproc;
 function fpc_setjmp(var S : jmp_buf) : longint;assembler;[Public, alias : 'FPC_SETJMP'];nostackframe; compilerproc;
   asm
   asm
-    {$if defined(FPUVFPV2) or defined(FPUVFPV3)}
+    {$if defined(FPUVFPV2) or defined(FPUVFPV3) or defined(FPUVFPV3_D16)}
     {$if defined(CPUARMV3) or defined(CPUARMV4) or defined(CPUARMV5)}
     {$if defined(CPUARMV3) or defined(CPUARMV4) or defined(CPUARMV5)}
     fstmiax r0!, {d8-d15}
     fstmiax r0!, {d8-d15}
     {$else}
     {$else}
@@ -46,7 +46,7 @@ procedure fpc_longjmp(var S : jmp_buf;value : longint);assembler;[Public, alias
     movs    r0, r1
     movs    r0, r1
     it eq
     it eq
     moveq   r0, #1
     moveq   r0, #1
-    {$if defined(FPUVFPV2) or defined(FPUVFPV3)}
+    {$if defined(FPUVFPV2) or defined(FPUVFPV3) or defined(FPUVFPV3_D16)}
     fldmiad ip!, {d8-d15}
     fldmiad ip!, {d8-d15}
     {$endif}
     {$endif}
     ldmia   ip,{v1-v6, sl, fp}
     ldmia   ip,{v1-v6, sl, fp}
@@ -57,7 +57,7 @@ procedure fpc_longjmp(var S : jmp_buf;value : longint);assembler;[Public, alias
     mov     ip, r0
     mov     ip, r0
     movs    r0, r1
     movs    r0, r1
     moveq   r0, #1
     moveq   r0, #1
-    {$if defined(FPUVFPV2) or defined(FPUVFPV3)}
+    {$if defined(FPUVFPV2) or defined(FPUVFPV3) or defined(FPUVFPV3_D16)}
     {$if defined(CPUARMV3) or defined(CPUARMV4) or defined(CPUARMV5)}
     {$if defined(CPUARMV3) or defined(CPUARMV4) or defined(CPUARMV5)}
     fldmiax ip!, {d8-d15}
     fldmiax ip!, {d8-d15}
     {$else}
     {$else}

+ 1 - 1
rtl/arm/setjumph.inc

@@ -16,7 +16,7 @@
 
 
 type
 type
    jmp_buf = packed record
    jmp_buf = packed record
-{$if defined(FPUVFPV2) or defined(FPUVFPV3)}
+{$if defined(FPUVFPV2) or defined(FPUVFPV3) or defined(FPUVFPV3_D16)}
       d8,d9,d10,d11,d12,d13,d14,d15: double;
       d8,d9,d10,d11,d12,d13,d14,d15: double;
 {$endif}
 {$endif}
       v1,v2,v3,v4,v5,v6,sl,fp,sp,pc : dword;
       v1,v2,v3,v4,v5,v6,sl,fp,sp,pc : dword;