mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-04-22 00:59:30 +02:00
lazutils: UTF8CompareStr: made 64bit safe, added fast PChar versions
git-svn-id: trunk@38103 -
This commit is contained in:
parent
ecfb0f4478
commit
b240df36a1
@ -271,9 +271,9 @@ type
|
||||
function CompareCTDirectoryCaches(Data1, Data2: Pointer): integer;
|
||||
function CompareAnsiStringAndDirectoryCache(Dir, Cache: Pointer): integer;
|
||||
|
||||
function ComparePCharFirstCaseInsAThenCase(Data1, Data2: Pointer): integer;
|
||||
function ComparePCharCaseInsensitiveA(Data1, Data2: Pointer): integer;
|
||||
function ComparePCharCaseSensitive(Data1, Data2: Pointer): integer;
|
||||
function ComparePCharFirstCaseInsAThenCase(Data1, Data2: Pointer): integer; // insensitive ASCII then byte wise
|
||||
function ComparePCharCaseInsensitiveA(Data1, Data2: Pointer): integer; // insensitive ASCII
|
||||
function ComparePCharCaseSensitive(Data1, Data2: Pointer): integer; // byte wise
|
||||
|
||||
// unit links
|
||||
function SearchUnitInUnitLinks(const UnitLinks, TheUnitName: string;
|
||||
|
@ -25,6 +25,10 @@ function CompareFileExt(const Filename, Ext: string;
|
||||
function CompareFilenameStarts(const Filename1, Filename2: string): integer;
|
||||
function CompareFilenames(Filename1: PChar; Len1: integer;
|
||||
Filename2: PChar; Len2: integer): integer;
|
||||
function CompareFilenamesP(Filename1, Filename2: PChar;
|
||||
IgnoreCase: boolean = false // false = use default
|
||||
): integer;
|
||||
|
||||
function DirPathExists(DirectoryName: string): boolean;
|
||||
function DirectoryIsWritable(const DirectoryName: string): boolean;
|
||||
function ExtractFileNameOnly(const AFilename: string): string;
|
||||
@ -362,6 +366,65 @@ begin
|
||||
{$ENDIF}
|
||||
end;
|
||||
|
||||
function CompareFilenamesP(Filename1, Filename2: PChar;
|
||||
IgnoreCase: boolean = false): integer;
|
||||
var
|
||||
{$IFDEF darwin}
|
||||
F1: CFStringRef;
|
||||
F2: CFStringRef;
|
||||
Flags: CFStringCompareFlags;
|
||||
{$ELSE}
|
||||
File1, File2: string;
|
||||
Len1: SizeInt;
|
||||
Len2: SizeInt;
|
||||
{$ENDIF}
|
||||
begin
|
||||
if (Filename1=nil) or (Filename1^=#0) then begin
|
||||
if (Filename2=nil) or (Filename2^=#0) then begin
|
||||
// both empty
|
||||
exit(0);
|
||||
end else begin
|
||||
// filename1 empty, filename2 not empty
|
||||
exit(-1);
|
||||
end;
|
||||
end else if (Filename2=nil) or (Filename2^=#0) then begin
|
||||
// filename1 not empty, filename2 empty
|
||||
exit(1);
|
||||
end;
|
||||
|
||||
{$IFDEF CaseInsensitiveFilenames}
|
||||
// this platform is by default case insensitive
|
||||
IgnoreCase:=true;
|
||||
{$ENDIF}
|
||||
{$IFDEF darwin}
|
||||
F1:=CFStringCreateWithCString(nil,Pointer(Filename1),kCFStringEncodingUTF8);
|
||||
F2:=CFStringCreateWithCString(nil,Pointer(Filename2),kCFStringEncodingUTF8);
|
||||
Flags:=kCFCompareNonliteral;
|
||||
if IgnoreCase then Flags+=kCFCompareCaseInsensitive;
|
||||
Result:=CFStringCompare(F1,F2,Flags);
|
||||
CFRelease(F1);
|
||||
CFRelease(F2);
|
||||
{$ELSE}
|
||||
if IgnoreCase then begin
|
||||
// compare case insensitive
|
||||
Len1:=StrLen(Filename1);
|
||||
SetLength(File1,Len1);
|
||||
System.Move(Filename1^,File1[1],Len1);
|
||||
Len2:=StrLen(Filename2);
|
||||
SetLength(File2,Len2);
|
||||
System.Move(Filename2^,File2[1],Len2);
|
||||
Result:=UTF8CompareText(File1,File2);
|
||||
end else begin
|
||||
// compare literally
|
||||
while (Filename1^=Filename2^) and (Filename1^<>#0) do begin
|
||||
inc(Filename1);
|
||||
Inc(Filename2);
|
||||
end;
|
||||
Result:=ord(Filename1^)-ord(Filename2^);
|
||||
end;
|
||||
{$ENDIF}
|
||||
end;
|
||||
|
||||
function DirPathExists(DirectoryName: string): boolean;
|
||||
begin
|
||||
Result:=DirectoryExistsUTF8(ChompPathDelim(DirectoryName));
|
||||
|
@ -88,6 +88,8 @@ procedure AssignUTF8ListToAnsi(UTF8List, AnsiList: TStrings);
|
||||
//compare functions
|
||||
|
||||
function UTF8CompareStr(const S1, S2: string): Integer; inline;
|
||||
function UTF8CompareStrP(S1, S2: PChar): Integer;
|
||||
function UTF8CompareStr(S1: PChar; Count1: SizeInt; S2: PChar; Count2: SizeInt): Integer;
|
||||
function UTF8CompareText(const S1, S2: string): Integer;
|
||||
function CompareStrListUTF8LowerCase(List: TStringList; Index1, Index2: Integer): Integer;
|
||||
|
||||
@ -2500,12 +2502,36 @@ end;
|
||||
Params: S1, S2 - UTF8 encoded strings
|
||||
Returns: < 0 if S1 < S2, 0 if S1 = S2, > 0 if S2 > S1.
|
||||
Compare 2 UTF8 encoded strings, case sensitive.
|
||||
Note: Use this function instead of AnsiCompareStr.
|
||||
This function guarantees proper collation on all supported platforms.
|
||||
------------------------------------------------------------------------------}
|
||||
function UTF8CompareStr(const S1, S2: string): Integer;
|
||||
begin
|
||||
Result := SysUtils.CompareStr(S1, S2);
|
||||
Result := UTF8CompareStr(PChar(Pointer(S1)),length(S1),
|
||||
PChar(Pointer(S2)),length(S2));
|
||||
end;
|
||||
|
||||
function UTF8CompareStrP(S1, S2: PChar): Integer;
|
||||
begin
|
||||
Result:=UTF8CompareStr(S1,StrLen(S1),S2,StrLen(S2));
|
||||
end;
|
||||
|
||||
function UTF8CompareStr(S1: PChar; Count1: SizeInt; S2: PChar; Count2: SizeInt
|
||||
): Integer;
|
||||
var
|
||||
Count: SizeInt;
|
||||
begin
|
||||
Result := 0;
|
||||
if Count1>Count2 then
|
||||
Count:=Count2
|
||||
else
|
||||
Count:=Count1;
|
||||
Result := CompareMemRange(Pointer(S1),Pointer(S2), Count); // Note: CompareMemRange can handle nil if Count=0
|
||||
if Result<>0 then exit;
|
||||
if Count1>Count2 then
|
||||
Result:=1
|
||||
else if Count1<Count2 then
|
||||
Result:=-1
|
||||
else
|
||||
Result:=0;
|
||||
end;
|
||||
|
||||
{------------------------------------------------------------------------------
|
||||
|
Loading…
Reference in New Issue
Block a user