Ver código fonte

Darwin version comparisons: factored out into object

Use numeric instead of string comparisons
Jonas Maebe 2 anos atrás
pai
commit
b26703feaa

+ 0 - 67
compiler/cutils.pas

@@ -133,7 +133,6 @@ interface
     function DePascalQuote(var s: ansistring): Boolean;
     function CompareStr(const S1, S2: string): Integer;
     function CompareText(S1, S2: string): integer;
-    function CompareVersionStrings(s1,s2: string): longint;
 
     { releases the string p and assignes nil to p }
     { if p=nil then freemem isn't called          }
@@ -1275,72 +1274,6 @@ implementation
       end;
 
 
-    function CompareVersionStrings(s1,s2: string): longint;
-      var
-        start1, start2,
-        i1, i2,
-        num1,num2,
-        res,
-        err        : longint;
-      begin
-        i1:=1;
-        i2:=1;
-        repeat
-          start1:=i1;
-          start2:=i2;
-          while (i1<=length(s1)) and
-                (s1[i1] in ['0'..'9']) do
-             inc(i1);
-          while (i2<=length(s2)) and
-                (s2[i2] in ['0'..'9']) do
-             inc(i2);
-          { one of the strings misses digits -> other is the largest version }
-          if i1=start1 then
-            if i2=start2 then
-              exit(0)
-            else
-              exit(-1)
-          else if i2=start2 then
-            exit(1);
-          { get version number part }
-          val(copy(s1,start1,i1-start1),num1,err);
-          val(copy(s2,start2,i2-start2),num2,err);
-          { different -> done }
-          res:=num1-num2;
-          if res<>0 then
-            exit(res);
-          { if one of the two is at the end while the other isn't, add a '.0' }
-          if (i1>length(s1)) and
-             (i2<=length(s2)) then
-            s1:=s1+'.0';
-          if (i2>length(s2)) and
-             (i1<=length(s1)) then
-             s2:=s2+'.0';
-          { compare non-numerical characters normally }
-          while (i1<=length(s1)) and
-                not(s1[i1] in ['0'..'9']) and
-                (i2<=length(s2)) and
-                not(s2[i2] in ['0'..'9']) do
-            begin
-              res:=ord(s1[i1])-ord(s2[i2]);
-              if res<>0 then
-                exit(res);
-              inc(i1);
-              inc(i2);
-            end;
-          { both should be digits again now, otherwise pick the one with the
-            digits as the largest (it more likely means that the input was
-            ill-formatted though) }
-          if (i1<=length(s1)) and
-             not(s1[i1] in ['0'..'9']) then
-            exit(-1);
-          if (i2<=length(s2)) and
-             not(s2[i2] in ['0'..'9']) then
-            exit(1);
-        until false;
-      end;
-
-
 {*****************************************************************************
                                Ansistring (PChar+Length)
 *****************************************************************************}

+ 5 - 4
compiler/globals.pas

@@ -47,7 +47,7 @@ interface
 {$if defined(LLVM) or defined(GENERIC_CPU)}
       llvminfo,
 {$endif LLVM or GENERIC_CPU}
-      globtype,version,systems;
+      globtype,version,versioncmp,systems;
 
     const
        delphimodeswitches =
@@ -352,8 +352,9 @@ interface
        GenerateImportSection,
        GenerateImportSectionSetExplicitly,
        RelocSection : boolean;
+
        MacOSXVersionMin,
-       iPhoneOSVersionMin: string[15];
+       iPhoneOSVersionMin: tversion;
        RelocSectionSetExplicitly : boolean;
 
        current_tokenpos,                  { position of the last token }
@@ -1706,8 +1707,8 @@ implementation
         GenerateImportSection:=false;
         RelocSection:=false;
         RelocSectionSetExplicitly:=false;
-        MacOSXVersionMin:='';
-        iPhoneOSVersionMin:='';
+        MacOSXVersionMin.invalidate;
+        iPhoneOSVersionMin.invalidate;
         { memory sizes, will be overridden by parameter or default for target
           in options or init_parser }
         stacksize:=0;

+ 2 - 2
compiler/llvm/nllvmutil.pas

@@ -49,7 +49,7 @@ interface
 implementation
 
     uses
-      verbose,cutils,globals,fmodule,systems,finput,
+      verbose,cutils,globals,fmodule,systems,finput,versioncmp,
       aasmtai,cpubase,llvmbase,aasmllvm,
       aasmcnst,nllvmtcon,
       symbase,symtable,defutil,
@@ -295,7 +295,7 @@ implementation
         begin
           { Objective-C ABI version }
           if not(target_info.system in [system_powerpc_darwin,system_powerpc64_darwin,system_i386_darwin,system_x86_64_darwin]) or
-             (CompareVersionStrings(MacOSXVersionMin,'10.5')>=0) then
+             (MacOSXVersionMin.relationto(10,5,0)>=0) then
             objcabiversion:=2
           else
             objcabiversion:=1;

+ 35 - 22
compiler/options.pas

@@ -26,7 +26,7 @@ unit options;
 interface
 
 uses
-  cfileutl,cclasses,
+  cfileutl,cclasses,versioncmp,
   globtype,globals,verbose,systems,cpuinfo,comprsrc;
 
 Type
@@ -80,7 +80,7 @@ Type
     MacVersionSet: boolean;
     IdfVersionSet: boolean;
     processorstr: TCmdStr;
-    function ParseMacVersionMin(out minstr, emptystr: string; const compvarname, value: string; ios: boolean): boolean;
+    function ParseMacVersionMin(out minversion, invalidateversion: tversion; const compvarname, value: string; ios: boolean): boolean;
     procedure MaybeSetDefaultMacVersionMacro;
 {$ifdef XTENSA}
     function ParseVersionStr(out ver: longint; const compvarname, value: string): boolean;
@@ -1095,7 +1095,7 @@ begin
 end;
 
 
-function toption.ParseMacVersionMin(out minstr, emptystr: string; const compvarname, value: string; ios: boolean): boolean;
+function toption.ParseMacVersionMin(out minversion, invalidateversion: tversion; const compvarname, value: string; ios: boolean): boolean;
 
   function subval(start,maxlen: longint; out stop: longint): string;
     var
@@ -1116,12 +1116,14 @@ function toption.ParseMacVersionMin(out minstr, emptystr: string; const compvarn
 
   var
     temp,
-    compvarvalue: string[15];
-    i: longint;
+    compvarvalue,
+    versionstr: string[15];
+    major, minor, patch: cardinal;
+    i, err: longint;
     osx_minor_two_digits: boolean;
   begin
-    minstr:=value;
-    emptystr:='';
+    invalidateversion.invalidate;
+    versionstr:=value;
     MacVersionSet:=false;
     { check whether the value is a valid version number }
     if value='' then
@@ -1138,10 +1140,16 @@ function toption.ParseMacVersionMin(out minstr, emptystr: string; const compvarn
     if (i>=length(value)) or
        (value[i]<>'.') then
       exit(false);
+    val(compvarvalue,major,err);
+    if err<>0 then
+      exit(false);
     { minor version number }
     temp:=subval(i+1,2,i);
     if temp='' then
       exit(false);
+    val(temp,minor,err);
+    if err<>0 then
+      exit(false);
     { on Mac OS X, the minor version number was originally limited to 1 digit;
       with 10.10 the format changed and two digits were also supported; on iOS,
       the minor version number always takes up two digits }
@@ -1158,6 +1166,7 @@ function toption.ParseMacVersionMin(out minstr, emptystr: string; const compvarn
       temp:='0'+temp;
     compvarvalue:=compvarvalue+temp;
     { optional patch level }
+    patch:=0;
     if i<=length(value) then
       begin
         if value[i]<>'.' then
@@ -1188,19 +1197,23 @@ function toption.ParseMacVersionMin(out minstr, emptystr: string; const compvarn
         { must be the end }
         if i<=length(value) then
           exit(false);
+        val(temp,patch,err);
+        if err<>0 then
+          exit(false);
       end
     else if not ios and
        not osx_minor_two_digits then
       begin
         compvarvalue:=compvarvalue+'0';
-        minstr:=minstr+'.0'
+        versionstr:=versionstr+'.0'
       end
     else
       begin
         compvarvalue:=compvarvalue+'00';
         { command line versions still only use one 0 though }
-        minstr:=minstr+'.0'
+        versionstr:=versionstr+'.0'
       end;
+    minversion.init(versionstr,major,minor,patch);
     set_system_compvar(compvarname,compvarvalue);
     MacVersionSet:=true;
     result:=true;
@@ -1306,7 +1319,7 @@ begin
           begin
 {$ifdef llvm}
              { We only support libunwind as part of libsystem, which happened in Mac OS X 10.6 }
-            if CompareVersionStrings(MacOSXVersionMin,'10.6')<=0 then
+            if MacOSXVersionMin.relationto(10,6,0)<0 then
               Message1(option_invalid_macosx_deployment_target,envstr);
 {$endif}
             exit;
@@ -1325,36 +1338,36 @@ begin
   case target_info.system of
     system_powerpc_darwin:
       begin
-        set_system_compvar('MAC_OS_X_VERSION_MIN_REQUIRED','1030');
-        MacOSXVersionMin:='10.3.0';
+        if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED','10.3.0',false) then
+          internalerror(2022090910);
       end;
     system_powerpc64_darwin:
       begin
-        set_system_compvar('MAC_OS_X_VERSION_MIN_REQUIRED','1040');
-        MacOSXVersionMin:='10.4.0';
+        if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED','10.4.0',false) then
+          internalerror(2022090911);
       end;
     system_i386_darwin,
     system_x86_64_darwin:
       begin
-        set_system_compvar('MAC_OS_X_VERSION_MIN_REQUIRED','1080');
-        MacOSXVersionMin:='10.8.0';
+        if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED','10.8.0',false) then
+          internalerror(2022090912);
       end;
     system_arm_ios,
     system_i386_iphonesim:
       begin
-        set_system_compvar('IPHONE_OS_VERSION_MIN_REQUIRED','90000');
-        iPhoneOSVersionMin:='9.0.0';
+        if not ParseMacVersionMin(iPhoneOSVersionMin,MacOSXVersionMin,'IPHONE_OS_VERSION_MIN_REQUIRED','9.0.0',false) then
+          internalerror(2022090913);
       end;
     system_aarch64_ios,
     system_x86_64_iphonesim:
       begin
-        set_system_compvar('IPHONE_OS_VERSION_MIN_REQUIRED','90000');
-        iPhoneOSVersionMin:='9.0.0';
+        if not ParseMacVersionMin(iPhoneOSVersionMin,MacOSXVersionMin,'IPHONE_OS_VERSION_MIN_REQUIRED','9.0.0',false) then
+          internalerror(2022090914);
       end;
     system_aarch64_darwin:
       begin
-        set_system_compvar('MAC_OS_X_VERSION_MIN_REQUIRED','110000');
-        MacOSXVersionMin:='11.0.0';
+        if not ParseMacVersionMin(MacOSXVersionMin,iPhoneOSVersionMin,'MAC_OS_X_VERSION_MIN_REQUIRED','11.00.0',false) then
+          internalerror(2022090915);
       end
     else
       internalerror(2012031001);

+ 20 - 20
compiler/systems/t_darwin.pas

@@ -173,14 +173,14 @@ implementation
                   system_x86_64_darwin:
                     begin
                       { 10.8 and later: no crt1.* }
-                      if CompareVersionStrings(MacOSXVersionMin,'10.8')>=0 then
+                      if MacOSXVersionMin.relationto(10,8,0)>=0 then
                         exit('');
                       { x86: crt1.10.6.o -> crt1.10.5.o -> crt1.o }
                       { others: crt1.10.5 -> crt1.o }
                       if (target_info.system in [system_i386_darwin,system_x86_64_darwin]) and
-                         (CompareVersionStrings(MacOSXVersionMin,'10.6')>=0) then
+                         (MacOSXVersionMin.relationto(10,6,0)>=0) then
                         exit('crt1.10.6.o');
-                      if CompareVersionStrings(MacOSXVersionMin,'10.5')>=0 then
+                      if MacOSXVersionMin.relationto(10,5,0)>=0 then
                         exit('crt1.10.5.o');
                     end;
                   system_arm_ios:
@@ -190,9 +190,9 @@ implementation
                           iOS 3.1 - 5.x: crt1.3.1.o
                           pre-iOS 3.1: crt1.o
                       }
-                      if (CompareVersionStrings(iPhoneOSVersionMin,'6.0')>=0) then
+                      if iPhoneOSVersionMin.relationto(6,0,0)>=0 then
                         exit('');
-                      if (CompareVersionStrings(iPhoneOSVersionMin,'3.1')>=0) then
+                      if iPhoneOSVersionMin.relationto(3,1,0)>=0 then
                         exit('crt1.3.1.o');
                     end;
                   system_i386_iphonesim,
@@ -202,7 +202,7 @@ implementation
                         What those recent versions could be, is anyone's guess. It
                         still seems to work with 8.1 and no longer with 8.3, so use
                         8.1 as a cut-off point }
-                      if (CompareVersionStrings(iPhoneOSVersionMin,'8.1')>0) then
+                      if iPhoneOSVersionMin.relationto(8,1,0)>0 then
                         exit('');
                     end;
                   system_aarch64_ios,
@@ -220,7 +220,7 @@ implementation
                 result:='gcrt1.o';
                 { 10.8 and later: tell the linker to use 'start' instead of "_main"
                   as entry point }
-                if CompareVersionStrings(MacOSXVersionMin,'10.8')>=0 then
+                if MacOSXVersionMin.relationto(10,8,0)>=0 then
                   Info.ExeCmd[1]:=Info.ExeCmd[1]+' -no_new_main';
               end;
           end
@@ -236,7 +236,7 @@ implementation
                     begin
                       { < 10.6: bundle1.o
                         >= 10.6: nothing }
-                      if CompareVersionStrings(MacOSXVersionMin,'10.6')>=0 then
+                      if MacOSXVersionMin.relationto(10,6,0)>=0 then
                         exit('');
                     end;
                   system_arm_ios,
@@ -244,14 +244,14 @@ implementation
                     begin
                       { iOS: < 3.1: bundle1.o
                              >= 3.1: nothing }
-                      if (CompareVersionStrings(iPhoneOSVersionMin,'3.1')>=0) then
+                      if iPhoneOSVersionMin.relationto(3,1,0)>=0 then
                         exit('');
                     end;
                   system_i386_iphonesim,
                   system_x86_64_iphonesim:
                     begin
                       { see rule for crt1.o }
-                      if (CompareVersionStrings(iPhoneOSVersionMin,'8.1')>0) then
+                      if iPhoneOSVersionMin.relationto(8,1,0)>0 then
                         exit('');
                     end;
                   system_aarch64_darwin:
@@ -273,9 +273,9 @@ implementation
                         = 10.5: dylib1.10.5.o
                         < 10.5: dylib1.o
                       }
-                      if CompareVersionStrings(MacOSXVersionMin,'10.6')>=0 then
+                      if MacOSXVersionMin.relationto(10,6,0)>=0 then
                         exit('');
-                      if CompareVersionStrings(MacOSXVersionMin,'10.5')>=0 then
+                      if MacOSXVersionMin.relationto(10,5,0)>=0 then
                         exit('dylib1.10.5.o');
                     end;
                   system_arm_ios,
@@ -283,14 +283,14 @@ implementation
                     begin
                       { iOS: < 3.1: dylib1.o
                              >= 3.1: nothing }
-                      if (CompareVersionStrings(iPhoneOSVersionMin,'3.1')>=0) then
+                      if iPhoneOSVersionMin.relationto(3,1,0)>=0 then
                         exit('');
                     end;
                   system_i386_iphonesim,
                   system_x86_64_iphonesim:
                     begin
                       { see rule for crt1.o }
-                      if (CompareVersionStrings(iPhoneOSVersionMin,'8.1')>0) then
+                      if iPhoneOSVersionMin.relationto(8,1,0)>0 then
                         exit('');
                     end;
                   system_aarch64_darwin:
@@ -348,20 +348,20 @@ implementation
 
     function tlinkerdarwin.GetLinkVersion: TCmdStr;
       begin
-        if MacOSXVersionMin<>'' then
+        if MacOSXVersionMin.isvalid then
           begin
-            result:='-macosx_version_min '+MacOSXVersionMin;
+            result:='-macosx_version_min '+MacOSXVersionMin.str;
           end
-        else if iPhoneOSVersionMin<>'' then
+        else if iPhoneOSVersionMin.isvalid then
           begin
             if target_info.system in [system_i386_iphonesim,system_x86_64_iphonesim] then
-              result:='-ios_simulator_version_min '+iPhoneOSVersionMin
+              result:='-ios_simulator_version_min '+iPhoneOSVersionMin.str
             else
-              result:='-iphoneos_version_min '+iPhoneOSVersionMin;
+              result:='-iphoneos_version_min '+iPhoneOSVersionMin.str;
           end
         else
           begin
-            result:='';
+            internalerror(2022090920)
           end;
       end;
 

+ 2 - 2
compiler/triplet.pas

@@ -45,9 +45,9 @@ uses
         begin
           result:=result+'-apple';
           if target_info.system in systems_macosx then
-            result:=result+'-macosx'+MacOSXVersionMin
+            result:=result+'-macosx'+MacOSXVersionMin.str
           else
-            result:=result+'-ios'+iPhoneOSVersionMin;
+            result:=result+'-ios'+iPhoneOSVersionMin.str;
         end
       else if target_info.system in (systems_linux+systems_android) then
         result:=result+'-unknown-linux'