Browse Source

pas2js: search case insensitive by default

git-svn-id: trunk@38046 -
Mattias Gaertner 7 years ago
parent
commit
bd37d43f1c

+ 1 - 0
packages/pastojs/src/pas2jscompiler.pp

@@ -3229,6 +3229,7 @@ begin
   l('   -Ju<x> : Add <x> to foreign unit paths. Foreign units are not compiled.');
   {$IFDEF EnablePas2jsPrecompiled}
   l('   -JU    : Create precompiled units in '+PrecompiledExt+' format.');
+  // ToDo: list all registered formats
   {$ENDIF}
   l('  -l      : Write logo');
   l('  -MDelphi: Delphi 7 compatibility mode');

+ 66 - 18
packages/pastojs/src/pas2jsfilecache.pp

@@ -122,6 +122,7 @@ type
     procedure Clear;
     function DirectoryExists(Filename: string): boolean;
     function FileExists(Filename: string): boolean;
+    function FileExistsI(var Filename: string): boolean;
     function FileAge(Filename: string): TPas2jsFileAgeTime;
     function FileAttr(Filename: string): TPas2jsFileAttr;
     function FileSize(Filename: string): TPas2jsFileSize;
@@ -173,6 +174,7 @@ type
     function FindUnitJSFileName(const aUnitFilename: string): String;
     function FindCustomJSFileName(const aFilename: string): String;
     function FileExistsLogged(const Filename: string): boolean;
+    function FileExistsILogged(var Filename: string): boolean;
     function SearchLowUpCase(var Filename: string): boolean; virtual;
     property Cache: TPas2jsFilesCache read FCache;
   end;
@@ -840,6 +842,24 @@ begin
     Result:=SysUtils.FileExists(Info.Filename);
 end;
 
+function TPas2jsCachedDirectories.FileExistsI(var Filename: string): boolean;
+var
+  Info: TFileInfo;
+  i: Integer;
+begin
+  Info.Filename:=Filename;
+  if not GetFileInfo(Info) then exit(false);
+  if Info.Dir=nil then
+    Result:=SysUtils.FileExists(Info.Filename)
+  else
+  begin
+    i:=Info.Dir.IndexOfFileCaseInsensitive(Info.ShortFilename);
+    Result:=i>=0;
+    if Result then
+      Filename:=ExtractFilePath(Filename)+Info.Dir[i].Name;
+  end;
+end;
+
 function TPas2jsCachedDirectories.FileAge(Filename: string): TPas2jsFileAgeTime;
 var
   Info: TFileInfo;
@@ -1106,7 +1126,7 @@ begin
   Filename:=FindIncludeFileName(aFilename);
   if Filename='' then exit;
   try
-    Result := TFileLineReader.Create(Filename); // ToDo: 1. convert encoding to UTF-8, 2. use cache
+    Result := TFileLineReader.Create(Filename);
   except
     // error is shown in the scanner, which has the context information
   end;
@@ -1168,12 +1188,20 @@ begin
 end;
 
 function TPas2jsFileResolver.FindSourceFile(const aFilename: string): TLineReader;
+var
+  CurFilename: String;
+  Found: Boolean;
 begin
   Result:=nil;
-  if not Cache.DirectoryCache.FileExists(aFilename) then
+  CurFilename:=aFilename;
+  if Cache.SearchLikeFPC then
+    Found:=Cache.DirectoryCache.FileExists(CurFilename)
+  else
+    Found:=Cache.DirectoryCache.FileExistsI(CurFilename);
+  if not Found then
     raise EFileNotFoundError.Create(aFilename)
   else
-    Result:=Cache.LoadTextFile(aFilename).CreateLineReader(false);
+    Result:=Cache.LoadTextFile(CurFilename).CreateLineReader(false);
 end;
 
 function TPas2jsFileResolver.FindUnitFileName(const aUnitname,
@@ -1297,30 +1325,50 @@ begin
       Cache.Log.LogMsgIgnoreFilter(nSearchingFileNotFound,[Cache.FormatPath(Filename)]);
 end;
 
+function TPas2jsFileResolver.FileExistsILogged(var Filename: string): boolean;
+begin
+  Result:=Cache.DirectoryCache.FileExistsI(Filename);
+  if Cache.ShowTriedUsedFiles then
+    if Result then
+      Cache.Log.LogMsgIgnoreFilter(nSearchingFileFound,[Cache.FormatPath(Filename)])
+    else
+      Cache.Log.LogMsgIgnoreFilter(nSearchingFileNotFound,[Cache.FormatPath(Filename)]);
+end;
+
 function TPas2jsFileResolver.SearchLowUpCase(var Filename: string): boolean;
 {$IFNDEF CaseInsensitiveFilenames}
 var
   CasedFilename: String;
 {$ENDIF}
 begin
-  if FileExistsLogged(Filename) then
-    exit(true);
-  if StrictFileCase then
-    exit(false);
-  {$IFNDEF CaseInsensitiveFilenames}
-  CasedFilename:=ExtractFilePath(Filename)+LowerCase(ExtractFileName(Filename));
-  if (Filename<>CasedFilename) and FileExistsLogged(CasedFilename) then
+  if StrictFileCase or Cache.SearchLikeFPC then
   begin
-    Filename:=CasedFilename;
-    exit(true);
-  end;
-  CasedFilename:=ExtractFilePath(Filename)+UpperCase(ExtractFileName(Filename));
-  if (Filename<>CasedFilename) and FileExistsLogged(CasedFilename) then
+    if FileExistsLogged(Filename) then
+      exit(true);
+    if StrictFileCase then
+      exit(false);
+    {$IFNDEF CaseInsensitiveFilenames}
+    // FPC like search:
+    // first as written, then lowercase, then uppercase
+    CasedFilename:=ExtractFilePath(Filename)+LowerCase(ExtractFileName(Filename));
+    if (Filename<>CasedFilename) and FileExistsLogged(CasedFilename) then
+    begin
+      Filename:=CasedFilename;
+      exit(true);
+    end;
+    CasedFilename:=ExtractFilePath(Filename)+UpperCase(ExtractFileName(Filename));
+    if (Filename<>CasedFilename) and FileExistsLogged(CasedFilename) then
+    begin
+      Filename:=CasedFilename;
+      exit(true);
+    end;
+    {$ENDIF}
+  end else
   begin
-    Filename:=CasedFilename;
-    exit(true);
+    // search case insensitive
+    if FileExistsILogged(Filename) then
+      exit(true);
   end;
-  {$ENDIF}
   Result:=false;
 end;
 

+ 6 - 4
utils/pas2js/docs/translation.html

@@ -140,6 +140,10 @@ Put + after a boolean switch option to enable it, - to disable it
   -I&lt;x&gt;   : Add &lt;x&gt; to include paths, same as -Fi
   -J...  Extra options of pas2js
    -Jc    : Write all JavaScript concatenated into the output file
+   -Je&lt;x&gt; : Encode messages as &lt;x&gt;.
+     -Jeconsole : Console codepage. Default.
+     -Jesystem  : System codepage. On non Windows console and system are the same.
+     -Jeutf-8   : Unicode UTF-8. Default when using -Fe.
    -Ji&lt;x&gt; : Insert JS file &lt;x&gt; into main JS file. E.g. -Jirtl.js. Can be given multiple times.
    -Jl    : lower case identifiers
    -Jm    : generate source maps
@@ -148,11 +152,9 @@ Put + after a boolean switch option to enable it, - to disable it
      -Jminclude : include Pascal sources in source map.
      -Jmxssiheader : start source map with XSSI protection )]}.
      -Jm- : disable generating source maps
+   -Jo&lt;x&gt; : Enable or disable extra option. The x is case insensitive:
+     -JoSearchLikeFPC : search source files like FPC, default: search case insensitive.
    -Ju&lt;x&gt; : Add &lt;x&gt; to foreign unit paths. Foreign units are not compiled.
-   -Je&lt;x&gt; : Encode messages as &lt;x&gt;.
-     -Jeconsole : Console codepage. Default.
-     -Jesystem  : System codepage. On non Windows console and system are the same.
-     -Jeutf-8   : Unicode UTF-8. Default when using -Fe.
   -l      : Write logo
   -MDelphi: Delphi 7 compatibility mode
   -MObjFPC: FPC's Object Pascal compatibility mode (default)