From aac68dba7e7e9eaaa145cc7f1ea3856bc4d99a75 Mon Sep 17 00:00:00 2001 From: Makhaon <35131832+Makhaon@users.noreply.github.com> Date: Tue, 6 Nov 2018 19:35:33 +0300 Subject: [PATCH 01/13] Update superobject.pas FPC compatibility --- superobject.pas | 43 ++++++++++++++++++++++++++++--------------- 1 file changed, 28 insertions(+), 15 deletions(-) diff --git a/superobject.pas b/superobject.pas index 4cd4282..5eb0fa4 100644 --- a/superobject.pas +++ b/superobject.pas @@ -77,7 +77,7 @@ *) {$IFDEF FPC} - {$MODE OBJFPC}{$H+} + {$MODE DELPHI}{$H+} {$ENDIF} {$DEFINE SUPER_METHOD} @@ -94,13 +94,13 @@ {$define VER230ORGREATER} {$ifend} -{$if defined(FPC) or defined(VER170) or defined(VER180) or defined(VER190) +{$if defined(FPC) or defined(VER170) or defined(VER180) or defined(VER190) or defined(VER200) or defined(VER210ORGREATER)} {$DEFINE HAVE_INLINE} {$ifend} {$if defined(VER210ORGREATER)} - {$define HAVE_RTTI} + {$define HAVE_RTTI} {$ifend} {$if defined(VER230ORGREATER)} @@ -118,7 +118,7 @@ interface uses - Classes, supertypes + Classes, supertypes, Types {$IFDEF HAVE_RTTI} ,Generics.Collections, RTTI, TypInfo {$ENDIF} @@ -517,7 +517,7 @@ TSuperEnumerator = class function GetProcessing: boolean; procedure SetProcessing(value: boolean); function ForcePath(const path: SOString; dataType: TSuperType = stObject): ISuperObject; - function Format(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; + function FormatStr(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; function GetO(const path: SOString): ISuperObject; procedure PutO(const path: SOString; const Value: ISuperObject); @@ -636,8 +636,8 @@ TSuperObject = class(TObject, ISuperObject) {$ELSE} function QueryInterface(const IID: TGUID; out Obj): HResult; virtual; stdcall; {$ENDIF} - function _AddRef: Integer; virtual; stdcall; - function _Release: Integer; virtual; stdcall; + function _AddRef: Integer; virtual; {$IFDEF UNIX}cdecl{$ELSE}stdcall{$ENDIF}; + function _Release: Integer; virtual; {$IFDEF UNIX}cdecl{$ELSE}stdcall{$ENDIF}; function GetO(const path: SOString): ISuperObject; procedure PutO(const path: SOString; const Value: ISuperObject); @@ -712,7 +712,7 @@ TSuperObject = class(TObject, ISuperObject) function GetN(const path: SOString): ISuperObject; procedure PutN(const path: SOString; const Value: ISuperObject); function ForcePath(const path: SOString; dataType: TSuperType = stObject): ISuperObject; - function Format(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; + function FormatStr(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; property N[const path: SOString]: ISuperObject read GetN write PutN; property O[const path: SOString]: ISuperObject read GetO write PutO; default; @@ -815,6 +815,7 @@ function SO(const value: Variant): ISuperObject; overload; function SO(const Args: array of const): ISuperObject; overload; function SA(const Args: array of const): ISuperObject; overload; +function SA(const AStrings: TStringDynArray): ISuperObject; overload; function TryObjectToDate(const obj: ISuperObject; var dt: TDateTime): Boolean; function UUIDToString(const g: TGUID): SOString; @@ -837,7 +838,11 @@ function SOInvoke(const obj: TValue; const method: string; const params: string; implementation uses - sysutils, Windows, superdate + sysutils, + {$IFDEF MSWINDOWS} + Windows, + {$ENDIF} + superdate {$IFDEF FPC} ,sockets {$ELSE} @@ -1011,7 +1016,7 @@ function TryObjectToDate(const obj: ISuperObject; var dt: TDateTime): Boolean; end; end; -function SO(const s: SOString): ISuperObject; overload; +function SO(const s: SOString = '{}'): ISuperObject; begin Result := TSuperObject.ParseString(PSOChar(s), False); end; @@ -1043,7 +1048,7 @@ function SA(const Args: array of const): ISuperObject; overload; if TVarRec(Args[j]).VInterface = nil then Add(nil) else if IInterface(TVarRec(Args[j]).VInterface).QueryInterface(ISuperObject, intf) = 0 then - Add(ISuperObject(intf)) else + Add(TSuperObject(intf)) else Add(nil); vtPointer : if TVarRec(Args[j]).VPointer = nil then @@ -1068,6 +1073,15 @@ function SA(const Args: array of const): ISuperObject; overload; end; end; +function SA(const AStrings: TStringDynArray): ISuperObject; overload; +var + i: integer; +begin + Result := TSuperObject.Create(stArray); + for i := 0 to High(AStrings) do + Result.AsArray.Add(TSuperObject.Create(AStrings[i])); +end; + function SO(const Args: array of const): ISuperObject; overload; var j: Integer; @@ -3501,7 +3515,7 @@ function TSuperObject.ForcePath(const path: SOString; dataType: TSuperType = stO Result := ParseString(PSOChar(path), False, True, Self, [foCreatePath], nil, dataType); end; -function TSuperObject.Format(const str: SOString; BeginSep: SOChar; EndSep: SOChar): SOString; +function TSuperObject.FormatStr(const str: SOString; BeginSep: SOChar; EndSep: SOChar): SOString; var p1, p2: PSOChar; begin @@ -4235,12 +4249,12 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje end; end; -function TSuperObject._AddRef: Integer; stdcall; +function TSuperObject._AddRef: Integer; begin Result := InterlockedIncrement(FRefCount); end; -function TSuperObject._Release: Integer; stdcall; +function TSuperObject._Release: Integer; begin Result := InterlockedDecrement(FRefCount); if Result = 0 then @@ -6623,4 +6637,3 @@ finalization Assert(debugcount = 0, 'Memory leak'); {$ENDIF} end. - From 4ce75499259b5ab406460a3f901078c4fe629bc3 Mon Sep 17 00:00:00 2001 From: Makhaon <35131832+Makhaon@users.noreply.github.com> Date: Tue, 6 Nov 2018 19:37:34 +0300 Subject: [PATCH 02/13] Update supertimezone.pas FPC Windows/Linux compatibility --- supertimezone.pas | 60 +++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 53 insertions(+), 7 deletions(-) diff --git a/supertimezone.pas b/supertimezone.pas index 9f68f23..877f7f0 100644 --- a/supertimezone.pas +++ b/supertimezone.pas @@ -3,7 +3,10 @@ interface uses - Windows, Registry, SysUtils, Math, Generics.Collections, + {$IFDEF MSWINDOWS} + Windows, + {$ENDIF} + Registry, SysUtils, Math, Generics.Collections, supertypes; type @@ -17,6 +20,7 @@ TSuperTimeZone = class FName: SOString; function GetName: SOString; + {$IFDEF MSWINDOWS} { Windows Internals } function TzSpecificLocalTimeToSystemTime( const lpTimeZoneInformation: PTimeZoneInformation; @@ -34,6 +38,7 @@ TSuperTimeZone = class function DayLightCompareDate(const date: PSystemTime; const compareDate: PSystemTime): Integer; + {$ENDIF} private class constructor Init; class destructor Finish; @@ -64,7 +69,9 @@ TSuperTimeZone = class { TZ Info } class function GetCurrentTimeZone: SOString; + {$IFDEF MSWINDOWS} function GetTimeZoneInformation(Year: Word; var TZI: TTimeZoneInformation): Boolean; + {$ENDIF} function GetDaylightDisabled: Boolean; property Name: SOString read GetName; @@ -81,27 +88,29 @@ TSuperTimeZone = class { Windows 2000+ } function _SystemTimeToTzSpecificLocalTime( lpTimeZoneInformation: PTimeZoneInformation; - var lpUniversalTime, lpLocalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'SystemTimeToTzSpecificLocalTime' delayed; + var lpUniversalTime, lpLocalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'SystemTimeToTzSpecificLocalTime'{$IFNDEF FPC} delayed{$ENDIF}; { Windows XP+ } function _TzSpecificLocalTimeToSystemTime( lpTimeZoneInformation: PTimeZoneInformation; - var lpLocalTime, lpUniversalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'TzSpecificLocalTimeToSystemTime' delayed; + var lpLocalTime, lpUniversalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'TzSpecificLocalTimeToSystemTime'{$IFNDEF FPC} delayed{$ENDIF}; (* EXtended version - DST Aware *) +{$IFNDEF FPC} { Windows 7+ } function _TzSpecificLocalTimeToSystemTimeEx( const lpTimeZoneInformation: PDynamicTimeZoneInformation; - const lpLocalTime: PSystemTime; var lpUniversalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'TzSpecificLocalTimeToSystemTimeEx' delayed; + const lpLocalTime: PSystemTime; var lpUniversalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'TzSpecificLocalTimeToSystemTimeEx'{$IFNDEF FPC} delayed{$ENDIF}; { Windows 7+ } function _SystemTimeToTzSpecificLocalTimeEx( const lpTimeZoneInformation: PDynamicTimeZoneInformation; - const lpUniversalTime: PSystemTime; var lpLocalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'SystemTimeToTzSpecificLocalTimeEx' delayed; + const lpUniversalTime: PSystemTime; var lpLocalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'SystemTimeToTzSpecificLocalTimeEx'{$IFNDEF FPC} delayed{$ENDIF}; +{$ENDIF} { Convert Local <=> UTC for specific time-zones using the Windows API only. NOT Guaranteed to work } - + function _ConvertLocalDateTimeToUTC(const TimeZoneName: SOString; const Local: TDateTime; var UTC: TDateTime): Boolean; @@ -119,9 +128,11 @@ implementation function _ConvertLocalDateTimeToUTC(const TimeZoneName: SOString; const Local: TDateTime; var UTC: TDateTime): Boolean; +{$IFNDEF FPC} var DTZI: TDynamicTimeZoneInformation; local_st, utc_st: TSystemTime; +{$ENDIF} begin if not CheckWin32Version(6, 1) then begin @@ -129,6 +140,7 @@ function _ConvertLocalDateTimeToUTC(const TimeZoneName: SOString; Exit; end; + {$IFNDEF FPC} { We work with system times } DateTimeToSystemTime(Local, local_st); @@ -148,15 +160,18 @@ function _ConvertLocalDateTimeToUTC(const TimeZoneName: SOString; end else Result := False; + {$ENDIF} end; { Convert UTC -> Local for specific time-zones using the Windows API only. NOT Guaranteed to work } function _ConvertUTCDateTimeToLocal(const TimeZoneName: SOString; const UTC: TDateTime; var Local: TDateTime): Boolean; +{$IFNDEF FPC} var DTZI: TDynamicTimeZoneInformation; utc_st, local_st: TSystemTime; +{$ENDIF} begin if not CheckWin32Version(6, 1) then begin @@ -164,6 +179,7 @@ function _ConvertUTCDateTimeToLocal(const TimeZoneName: SOString; Exit; end; + {$IFNDEF FPC} { We work with system times } DateTimeToSystemTime(UTC, utc_st); @@ -183,6 +199,7 @@ function _ConvertUTCDateTimeToLocal(const TimeZoneName: SOString; end else Result := False; + {$ENDIF} end; {$ENDIF} @@ -190,14 +207,18 @@ function _ConvertUTCDateTimeToLocal(const TimeZoneName: SOString; class constructor TSuperTimeZone.Init; begin + {$IFNDEF FPC} InitializeCriticalSection(FCacheCS); + {$ENDIF} FCache := TObjectDictionary.Create([doOwnsValues]); end; class destructor TSuperTimeZone.Finish; begin FCache.Free; + {$IFNDEF FPC} DeleteCriticalSection(FCacheCS); + {$ENDIF} end; class function TSuperTimeZone.GetSuperTimeZoneInstance( @@ -227,52 +248,68 @@ constructor TSuperTimeZone.Create(const TimeZoneName: SOString); end; function TSuperTimeZone.LocalToUTC(const DelphiDateTime: TDateTime): TDateTime; +{$IFDEF MSWINDOWS} var local, utc: TSystemTime; tzi: TTimeZoneInformation; + {$ENDIF} begin + {$IFDEF MSWINDOWS} DateTimeToSystemTime(DelphiDateTime, local); if GetTimeZoneInformation(local.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, local, utc) then Result := SystemTimeToDateTime(utc) else + {$ENDIF} Result := DelphiDateTime; end; function TSuperTimeZone.UTCToLocal(const DelphiDateTime: TDateTime): TDateTime; +{$IFDEF MSWINDOWS} var utc, local: TSystemTime; tzi: TTimeZoneInformation; + {$ENDIF} begin + {$IFDEF MSWINDOWS} DateTimeToSystemTime(DelphiDateTime, utc); if GetTimeZoneInformation(utc.wYear, tzi) and SystemTimeToTzSpecificLocalTime(@tzi, utc, local) then Result := SystemTimeToDateTime(local) else + {$ENDIF} Result := DelphiDateTime; end; function TSuperTimeZone.DelphiToJava(const DelphiDateTime: TDateTime): Int64; +{$IFDEF MSWINDOWS} var local, utc, st: TSystemTime; tzi: TTimeZoneInformation; + {$ENDIF} begin +{$IFDEF MSWINDOWS} DateTimeToSystemTime(DelphiDateTime, local); if GetTimeZoneInformation(local.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, local, utc) then st := utc else st := local; Result := Round((SystemTimeToDateTime(st) - 25569) * 86400000); + {$ENDIF} end; function TSuperTimeZone.JavaToDelphi(const JavaDateTime: Int64): TDateTime; +{$IFDEF MSWINDOWS} var utc, local: TSystemTime; tzi: TTimeZoneInformation; + {$ENDIF} begin +{$IFDEF MSWINDOWS} DateTimeToSystemTime(25569 + (JavaDateTime / 86400000), utc); if GetTimeZoneInformation(utc.wYear, tzi) and SystemTimeToTzSpecificLocalTime(@tzi, utc, local) then Result := SystemTimeToDateTime(local) else Result := SystemTimeToDateTime(utc); + {$ENDIF} end; function TSuperTimeZone.DelphiToISO8601( @@ -282,11 +319,14 @@ function TSuperTimeZone.DelphiToISO8601( TZ_Fmt = '%s%.2d:%.2d'; var local, utc: TSystemTime; + {$IFDEF MSWINDOWS} tzi: TTimeZoneInformation; + {$ENDIF} bias: TDateTime; h, m, d: Word; iso: SOString; begin +{$IFDEF MSWINDOWS} DateTimeToSystemTime(DelphiDateTime, local); iso := Format(ISO_Fmt, [ local.wYear, local.wMonth, local.wDay, @@ -302,6 +342,7 @@ function TSuperTimeZone.DelphiToISO8601( end; end else + {$ENDIF} Result := iso; end; @@ -322,18 +363,20 @@ function TSuperTimeZone.ISO8601ToDelphi(const ISO8601Date: SOString; function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: SOString; var JavaDateTime: Int64): Boolean; +{$IFDEF MSWINDOWS} var st: TSystemTime; dayofyear: Integer; week: Word; bias: Integer; havetz, havedate: Boolean; - tzi: TTimeZoneInformation; utc: TSystemTime; m: Word; DayTable: PDayTable; + {$ENDIF} begin +{$IFDEF MSWINDOWS} if ParseISO8601Date(ISO8601Date, st, dayofyear, week, bias, havetz, havedate) then begin if (not havetz) and GetTimeZoneInformation(st.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, st, utc) then @@ -360,6 +403,7 @@ function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: SOString; Result := True; end else + {$ENDIF} Result := False; end; @@ -422,6 +466,7 @@ function TSuperTimeZone.GetDaylightDisabled: Boolean; end; end; +{$IFDEF MSWINDOWS} function TSuperTimeZone.GetTimeZoneInformation(Year: Word; var TZI: TTimeZoneInformation): Boolean; type @@ -705,6 +750,7 @@ function TSuperTimeZone.SystemTimeToTzSpecificLocalTime( PInt64(@ft)^ := llTime; Result := FileTimeToSystemTime(ft, lpLocalTime); end; +{$ENDIF} class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; var st: TSystemTime; var dayofyear: Integer; var week: Word; From 57e7fef39b3f0a60aebcb0f9e90c59bf4f064a5c Mon Sep 17 00:00:00 2001 From: Makhaon <35131832+Makhaon@users.noreply.github.com> Date: Tue, 6 Nov 2018 19:42:35 +0300 Subject: [PATCH 03/13] Update README.md --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index bf582c6..9c42c4c 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,7 @@ # SuperObject +What is new in this repository? New is FPC Windows/Linux compatibility. FPC Version 3.1.1 is used. + ## What is JSON ? - JSON (JavaScript Object Notation) is a lightweight data-interchange format. From 2da5c0136b42243a9111aafbe97c22bb7c97d6fb Mon Sep 17 00:00:00 2001 From: Makhaon <35131832+Makhaon@users.noreply.github.com> Date: Tue, 6 Nov 2018 19:42:59 +0300 Subject: [PATCH 04/13] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 9c42c4c..ebd8ec1 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # SuperObject -What is new in this repository? New is FPC Windows/Linux compatibility. FPC Version 3.1.1 is used. +What is new in this repository? New is the FPC Windows/Linux compatibility. FPC Version 3.1.1 is used. ## What is JSON ? From a6d9e8dfe1e221f09d6bb5b46e7268c215c7cdbd Mon Sep 17 00:00:00 2001 From: Makhaon <35131832+Makhaon@users.noreply.github.com> Date: Thu, 13 Dec 2018 16:41:59 +0300 Subject: [PATCH 05/13] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index ebd8ec1..ccf9e92 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # SuperObject -What is new in this repository? New is the FPC Windows/Linux compatibility. FPC Version 3.1.1 is used. +This version is compitible with Delphi and FPC complilers. Also it has Windows/Linux compatibility. Tested with FPC Version 3.0.4, 3.1.1 and last 3.3.1. ## What is JSON ? From 510872497a209fc3caca6c86ac15ee105227f8fa Mon Sep 17 00:00:00 2001 From: Makhaon <35131832+Makhaon@users.noreply.github.com> Date: Tue, 18 Dec 2018 11:09:56 +0300 Subject: [PATCH 06/13] Update README.md --- README.md | 65 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 65 insertions(+) diff --git a/README.md b/README.md index ccf9e92..94c58b6 100644 --- a/README.md +++ b/README.md @@ -216,3 +216,68 @@ SO('{собственность: bla bla bla}'); // excadecimal SO('{foo: \xFF}'); ``` +## Additional examples + +Get a Json string: + + function TDataModule3.GetSearchLostStatus: string; + var + X: ISuperObject; + begin + X := SO; + with FServiceThread do + begin + X.B['NowSearchForFile'] := NowSearchForFile; + X.S['LastLostFile'] := LastLostFile; + X.B['NowSearchForRec'] := NowSearchForRec; + X.S['LostRecProgress'] := LostRecProgress; + end; + Result := X.AsJSON; + end; + +Get data back from the Json string: + + procedure TForm2.SetSearchLostStatus(const Params: string); + var + s: string; + X: ISuperObject; + begin + X := TSuperObject.ParseString(PChar(Params), True); + FNowSearchForFile := not X.B['NowSearchForFile']; + FLastLostFile := X.S['LastLostFile']; + FNowSearchForRec := X.B['NowSearchForRec']; + FLostRecProgress := X.I['LostRecProgress']; + end; + +An array usage: + + procedure TForm4.SetQueueStatus(const Params: string); + var + j: integer; + X: ISuperObject; + X1: TSuperArray; + s: string; + begin + X := TSuperObject.ParseString(PChar(s), True); + X1 := X.A['Queues']; + StringGrid1.RowCount := X1.Length + 1; + for j := 0 to X1.Length - 1 do + with StringGrid1, X1[j] do + begin + Cells[0, j + 1] := S['NAME']; + if j = 0 then + Cells[1, j + 1] := S['FILES_QUEUED1'] + ' + ' + S['FILES_QUEUED2'] + else + Cells[1, j + 1] := S['FILES_QUEUED']; + Cells[2, j + 1] := S['STATUS']; + Cells[3, j + 1] := S['FILES_DONE']; + Cells[4, j + 1] := S['FILES_SKIPPED']; + end; + end; + +Path usage: + + var s: string; json, field: iSuperObject; + .... + field := json.O['Document.CurrentItems.DocumentItem.Fields.FieldValue[1].Value']; + s := json.O['Value'].AsString; From cb5d0dc6c8daaca3ff68ae0371075745b88a7643 Mon Sep 17 00:00:00 2001 From: Dm Bel Date: Wed, 12 Jun 2019 00:38:41 +0300 Subject: [PATCH 07/13] compatibility fixes --- superobject.pas | 8 ++--- supertimezone.pas | 80 +++++++++++++++++++++++++++++------------------ 2 files changed, 54 insertions(+), 34 deletions(-) diff --git a/superobject.pas b/superobject.pas index 5eb0fa4..894c04f 100644 --- a/superobject.pas +++ b/superobject.pas @@ -517,7 +517,7 @@ TSuperEnumerator = class function GetProcessing: boolean; procedure SetProcessing(value: boolean); function ForcePath(const path: SOString; dataType: TSuperType = stObject): ISuperObject; - function FormatStr(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; + function Format(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; function GetO(const path: SOString): ISuperObject; procedure PutO(const path: SOString; const Value: ISuperObject); @@ -712,7 +712,7 @@ TSuperObject = class(TObject, ISuperObject) function GetN(const path: SOString): ISuperObject; procedure PutN(const path: SOString; const Value: ISuperObject); function ForcePath(const path: SOString; dataType: TSuperType = stObject): ISuperObject; - function FormatStr(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; + function Format(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; property N[const path: SOString]: ISuperObject read GetN write PutN; property O[const path: SOString]: ISuperObject read GetO write PutO; default; @@ -1048,7 +1048,7 @@ function SA(const Args: array of const): ISuperObject; overload; if TVarRec(Args[j]).VInterface = nil then Add(nil) else if IInterface(TVarRec(Args[j]).VInterface).QueryInterface(ISuperObject, intf) = 0 then - Add(TSuperObject(intf)) else + Add(ISuperObject(intf)) else Add(nil); vtPointer : if TVarRec(Args[j]).VPointer = nil then @@ -3515,7 +3515,7 @@ function TSuperObject.ForcePath(const path: SOString; dataType: TSuperType = stO Result := ParseString(PSOChar(path), False, True, Self, [foCreatePath], nil, dataType); end; -function TSuperObject.FormatStr(const str: SOString; BeginSep: SOChar; EndSep: SOChar): SOString; +function TSuperObject.Format(const str: SOString; BeginSep: SOChar; EndSep: SOChar): SOString; var p1, p2: PSOChar; begin diff --git a/supertimezone.pas b/supertimezone.pas index 877f7f0..db4adaf 100644 --- a/supertimezone.pas +++ b/supertimezone.pas @@ -1,5 +1,9 @@ unit supertimezone; +{$IFDEF FPC} + {$mode Delphi} +{$ENDIF} + interface uses @@ -771,12 +775,28 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; TState = (stStart, stYear, stMonth, stWeek, stWeekDay, stDay, stDayOfYear, stHour, stMin, stSec, stMs, stUTC, stGMTH, stGMTM, stGMTend, stEnd); TPerhaps = (yes, no, perhaps); +type + TSystemTimeInt = record + Year: Word; + Month: Word; + DayOfWeek: Word; + Day: Word; + Hour: Word; + Minute: Word; + Second: Word; + Millisecond: Word; + end; var p: PSOChar; sep: TPerhaps; state: TState; pos, v: Word; inctz: Boolean; + {$IFDEF MSWINDOWS} + st1: TSystemTimeInt absolute st; + {$ELSE MSWINDOWS} + st1: TSystemTime absolute st; + {$ENDIF MSWINDOWS} label error; begin @@ -812,7 +832,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; stYear: case pos of 0 .. 1, 3: - if get(st.wYear, p^) then + if get(st1.Year, p^) then begin Inc(pos); Inc(p); @@ -823,15 +843,15 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; case p^ of '0' .. '9': begin - st.wYear := st.wYear * 10 + Ord(p^) - Ord('0'); + st1.Year := st1.Year * 10 + Ord(p^) - Ord('0'); Inc(pos); Inc(p); end; ':': begin havedate := False; - st.wHour := st.wYear; - st.wYear := 0; + st1.Hour := st1.Year; + st1.Year := 0; Inc(p); pos := 0; state := stMin; @@ -866,13 +886,13 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; state := stHour; pos := 0; Inc(p); - st.wMonth := 1; - st.wDay := 1; + st1.Month := 1; + st1.Day := 1; end; #0: begin - st.wMonth := 1; - st.wDay := 1; + st1.Month := 1; + st1.Day := 1; state := stEnd; end; else @@ -885,7 +905,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; case p^ of '0' .. '9': begin - st.wMonth := Ord(p^) - Ord('0'); + st1.Month := Ord(p^) - Ord('0'); Inc(pos); Inc(p); end; @@ -899,7 +919,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; goto error; end; 1: - if get(st.wMonth, p^) then + if get(st1.Month, p^) then begin Inc(pos); Inc(p); @@ -927,8 +947,8 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; end else begin - dayofyear := st.wMonth * 10 + Ord(p^) - Ord('0'); - st.wMonth := 0; + dayofyear := st1.Month * 10 + Ord(p^) - Ord('0'); + st1.Month := 0; Inc(p); pos := 3; state := stDayOfYear; @@ -938,11 +958,11 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; state := stHour; pos := 0; Inc(p); - st.wDay := 1; + st1.Day := 1; end; #0: begin - st.wDay := 1; + st1.Day := 1; state := stEnd; end; else @@ -952,7 +972,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; stDay: case pos of 0: - if get(st.wDay, p^) then + if get(st1.Day, p^) then begin Inc(pos); Inc(p); @@ -960,16 +980,16 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; else goto error; 1: - if get(st.wDay, p^) then + if get(st1.Day, p^) then begin Inc(pos); Inc(p); end else if sep in [no, perhaps] then begin - dayofyear := st.wMonth * 10 + st.wDay; - st.wDay := 0; - st.wMonth := 0; + dayofyear := st1.Month * 10 + st1.Day; + st1.Day := 0; + st1.Month := 0; state := stDayOfYear; end else @@ -1042,12 +1062,12 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; end; stWeekDay: begin - if (week > 0) and get(st.wDayOfWeek, p^) then + if (week > 0) and get(st1.DayOfWeek, p^) then begin Inc(p); - v := st.wYear - 1; + v := st1.Year - 1; v := ((v * 365) + (v div 4) - (v div 100) + (v div 400)) mod 7 + 1; - dayofyear := (st.wDayOfWeek - v) + ((week) * 7) + 1; + dayofyear := (st1.DayOfWeek - v) + ((week) * 7) + 1; if v <= 4 then Dec(dayofyear, 7); case p^ of @@ -1071,7 +1091,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; 0: case p^ of '0' .. '9': - if get(st.wHour, p^) then + if get(st1.Hour, p^) then begin Inc(pos); Inc(p); @@ -1087,7 +1107,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; goto error; end; 1: - if get(st.wHour, p^) then + if get(st1.Hour, p^) then begin Inc(pos); Inc(p); @@ -1157,7 +1177,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; 0: case p^ of '0' .. '9': - if get(st.wMinute, p^) then + if get(st1.Minute, p^) then begin Inc(pos); Inc(p); @@ -1173,7 +1193,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; goto error; end; 1: - if get(st.wMinute, p^) then + if get(st1.Minute, p^) then begin Inc(pos); Inc(p); @@ -1240,7 +1260,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; stSec: case pos of 0 .. 1: - if get(st.wSecond, p^) then + if get(st1.Second, p^) then begin Inc(pos); Inc(p); @@ -1290,7 +1310,7 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; case p^ of '0' .. '9': begin - st.wMilliseconds := st.wMilliseconds * 10 + Ord(p^) - Ord('0'); + st1.MilliSecond := st1.MilliSecond * 10 + Ord(p^) - Ord('0'); Inc(p); end; '+': @@ -1409,8 +1429,8 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; end; end; - if (st.wHour >= 24) or (st.wMinute >= 60) or (st.wSecond >= 60) or - (st.wMilliseconds >= 1000) or (week > 53) then + if (st1.Hour >= 24) or (st1.Minute >= 60) or (st1.Second >= 60) or + (st1.MilliSecond >= 1000) or (week > 53) then goto error; Result := True; From 11baa801e975ba4ca59c9ec4dab962f856344ba7 Mon Sep 17 00:00:00 2001 From: Makhaon <35131832+Makhaon@users.noreply.github.com> Date: Wed, 12 Jun 2019 10:16:48 +0300 Subject: [PATCH 08/13] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 94c58b6..0f486bb 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # SuperObject -This version is compitible with Delphi and FPC complilers. Also it has Windows/Linux compatibility. Tested with FPC Version 3.0.4, 3.1.1 and last 3.3.1. +This version is compatible with Delphi and FPC complilers. Also it has Windows/Linux compatibility. Tested with FPC Version 3.0.4, 3.1.1 and last 3.3.1. ## What is JSON ? From 93ad1621abc762ae6b3ca54a80050fa6cdb0c199 Mon Sep 17 00:00:00 2001 From: Dmitry Date: Fri, 29 May 2020 08:32:53 +0300 Subject: [PATCH 09/13] Add new SA function --- superobject.pas | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/superobject.pas b/superobject.pas index 894c04f..a8890bc 100644 --- a/superobject.pas +++ b/superobject.pas @@ -816,6 +816,7 @@ function SO(const Args: array of const): ISuperObject; overload; function SA(const Args: array of const): ISuperObject; overload; function SA(const AStrings: TStringDynArray): ISuperObject; overload; +function SA(const AStrings: TArray): ISuperObject; overload; function TryObjectToDate(const obj: ISuperObject; var dt: TDateTime): Boolean; function UUIDToString(const g: TGUID): SOString; @@ -1082,6 +1083,15 @@ function SA(const AStrings: TStringDynArray): ISuperObject; overload; Result.AsArray.Add(TSuperObject.Create(AStrings[i])); end; +function SA(const AStrings: TArray): ISuperObject; overload; +var + i: integer; +begin + Result := TSuperObject.Create(stArray); + for i := 0 to High(AStrings) do + Result.AsArray.Add(TSuperObject.Create(AStrings[i])); +end; + function SO(const Args: array of const): ISuperObject; overload; var j: Integer; @@ -1687,6 +1697,7 @@ destructor TSuperEnumerator.Destroy; begin if FObjEnum <> nil then FObjEnum.Free; + inherited; end; function TSuperEnumerator.MoveNext: Boolean; @@ -5899,6 +5910,7 @@ destructor TSuperRttiContext.Destroy; SerialFromJson.Free; SerialToJson.Free; Context.Free; + inherited; end; class function TSuperRttiContext.GetFieldName(r: TRttiField): string; From ed893f2efbc370c81e2a8f54c2e16f862645fd5b Mon Sep 17 00:00:00 2001 From: Dmitry Date: Thu, 7 Jan 2021 00:11:50 +0300 Subject: [PATCH 10/13] fix different fpc warnings --- superdate.pas | 26 +- superobject.pas | 875 ++++++++++++++++++++++++++++++---------------- supertimezone.pas | 129 +++++-- 3 files changed, 681 insertions(+), 349 deletions(-) diff --git a/superdate.pas b/superdate.pas index efef963..f7999a3 100644 --- a/superdate.pas +++ b/superdate.pas @@ -3,43 +3,43 @@ interface uses - supertypes, supertimezone; + supertimezone; -function JavaToDelphiDateTime(const dt: Int64; const TimeZone: SOString = ''): TDateTime; -function DelphiToJavaDateTime(const dt: TDateTime; const TimeZone: SOString = ''): Int64; -function JavaDateTimeToISO8601Date(const dt: Int64; const TimeZone: SOString = ''): SOString; -function DelphiDateTimeToISO8601Date(const dt: TDateTime; const TimeZone: SOString = ''): SOString; -function ISO8601DateToJavaDateTime(const str: SOString; var ms: Int64; const TimeZone: SOString = ''): Boolean; -function ISO8601DateToDelphiDateTime(const str: SOString; var dt: TDateTime; const TimeZone: SOString = ''): Boolean; +function JavaToDelphiDateTime(const dt: Int64; const TimeZone: string = ''): TDateTime; +function DelphiToJavaDateTime(const dt: TDateTime; const TimeZone: string = ''): Int64; +function JavaDateTimeToISO8601Date(const dt: Int64; const TimeZone: string = ''): string; +function DelphiDateTimeToISO8601Date(const dt: TDateTime; const TimeZone: string = ''): string; +function ISO8601DateToJavaDateTime(const str: string; out ms: Int64; const TimeZone: string = ''): Boolean; +function ISO8601DateToDelphiDateTime(const str: string; out dt: TDateTime; const TimeZone: string = ''): Boolean; implementation -function JavaToDelphiDateTime(const dt: Int64; const TimeZone: SOString = ''): TDateTime; +function JavaToDelphiDateTime(const dt: Int64; const TimeZone: string = ''): TDateTime; begin Result := TSuperTimeZone.Zone[TimeZone].JavaToDelphi(dt); end; -function DelphiToJavaDateTime(const dt: TDateTime; const TimeZone: SOString = ''): Int64; +function DelphiToJavaDateTime(const dt: TDateTime; const TimeZone: string = ''): Int64; begin Result := TSuperTimeZone.Zone[TimeZone].DelphiToJava(dt); end; -function JavaDateTimeToISO8601Date(const dt: Int64; const TimeZone: SOString = ''): SOString; +function JavaDateTimeToISO8601Date(const dt: Int64; const TimeZone: string = ''): string; begin Result := TSuperTimeZone.Zone[TimeZone].JavaToISO8601(dt); end; -function DelphiDateTimeToISO8601Date(const dt: TDateTime; const TimeZone: SOString = ''): SOString; +function DelphiDateTimeToISO8601Date(const dt: TDateTime; const TimeZone: string = ''): string; begin Result := TSuperTimeZone.Zone[TimeZone].DelphiToISO8601(dt); end; -function ISO8601DateToJavaDateTime(const str: SOString; var ms: Int64; const TimeZone: SOString = ''): Boolean; +function ISO8601DateToJavaDateTime(const str: string; out ms: Int64; const TimeZone: string = ''): Boolean; begin Result := TSuperTimeZone.Zone[TimeZone].ISO8601ToJava(str, ms); end; -function ISO8601DateToDelphiDateTime(const str: SOString; var dt: TDateTime; const TimeZone: SOString = ''): Boolean; +function ISO8601DateToDelphiDateTime(const str: string; out dt: TDateTime; const TimeZone: string): Boolean; begin Result := TSuperTimeZone.Zone[TimeZone].ISO8601ToDelphi(str, dt); end; diff --git a/superobject.pas b/superobject.pas index a8890bc..82700b2 100644 --- a/superobject.pas +++ b/superobject.pas @@ -83,33 +83,34 @@ {$DEFINE SUPER_METHOD} {.$DEFINE DEBUG} // track memory leack +{$IFDEF FPC} + {$DEFINE HAVE_INLINE} -{$if defined(VER210) or defined(VER220)} - {$define VER210ORGREATER} -{$ifend} - -{$if defined(VER230) or defined(VER240) or defined(VER250) or - defined(VER260) or defined(VER270) or defined(VER280)} - {$define VER210ORGREATER} - {$define VER230ORGREATER} -{$ifend} - -{$if defined(FPC) or defined(VER170) or defined(VER180) or defined(VER190) - or defined(VER200) or defined(VER210ORGREATER)} - {$DEFINE HAVE_INLINE} -{$ifend} - -{$if defined(VER210ORGREATER)} - {$define HAVE_RTTI} -{$ifend} - -{$if defined(VER230ORGREATER)} - {$define NEED_FORMATSETTINGS} -{$ifend} - -{$if defined(FPC) and defined(VER2_6)} - {$define NEED_FORMATSETTINGS} -{$ifend} + {$IF Defined (FPC_FULLVERSION) and (FPC_FULLVERSION >= 20600)} + {$define NEED_FORMATSETTINGS} + {$ENDIF} +{$ELSE} + {$IF CompilerVersion >= 21.0} + {$define VER210ORGREATER} + {$ENDIF} + + {$IF CompilerVersion >= 23.0} + {$define VER230ORGREATER} + {$ENDIF} + + {$if defined(VER170) or defined(VER180) or defined(VER190) + or defined(VER200) or defined(VER210ORGREATER)} + {$DEFINE HAVE_INLINE} + {$ENDIF} + + {$if defined(VER210ORGREATER)} + {$define HAVE_RTTI} + {$ENDIF} + + {$if defined(VER230ORGREATER)} + {$define NEED_FORMATSETTINGS} + {$ENDIF} +{$ENDIF} {$OVERFLOWCHECKS OFF} {$RANGECHECKS OFF} @@ -118,7 +119,7 @@ interface uses - Classes, supertypes, Types + Classes, supertypes, Variants {$IFDEF HAVE_RTTI} ,Generics.Collections, RTTI, TypInfo {$ENDIF} @@ -170,6 +171,8 @@ TSuperAvlEntry = class property Value: ISuperObject read GetValue write SetValue; end; + { TSuperAvlTree } + TSuperAvlTree = class private FRoot: TSuperAvlEntry; @@ -270,8 +273,8 @@ TSuperArray = class procedure PutD(const index: integer; Value: Double); function GetC(const index: integer): Currency; procedure PutC(const index: integer; Value: Currency); - function GetS(const index: integer): SOString; - procedure PutS(const index: integer; const Value: SOString); + function GetS(const index: integer): string; + procedure PutS(const index: integer; const Value: string); {$IFDEF SUPER_METHOD} function GetM(const index: integer): TSuperMethod; procedure PutM(const index: integer; Value: TSuperMethod); @@ -283,7 +286,7 @@ TSuperArray = class destructor Destroy; override; function Add(const Data: ISuperObject): Integer; overload; function Add(Data: SuperInt): Integer; overload; - function Add(const Data: SOString): Integer; overload; + function Add(const Data: string): Integer; overload; function Add(Data: Boolean): Integer; overload; function Add(Data: Double): Integer; overload; function AddC(const Data: Currency): Integer; @@ -299,7 +302,7 @@ TSuperArray = class property I[const index: integer]: SuperInt read GetI write PutI; property D[const index: integer]: Double read GetD write PutD; property C[const index: integer]: Currency read GetC write PutC; - property S[const index: integer]: SOString read GetS write PutS; + property S[const index: integer]: string read GetS write PutS; {$IFDEF SUPER_METHOD} property M[const index: integer]: TSuperMethod read GetM write PutM; {$ENDIF} @@ -325,7 +328,7 @@ TSuperWriterString = class(TSuperWriter) procedure TrimRight; constructor Create; virtual; destructor Destroy; override; - function GetString: SOString; + function GetString: string; property Data: PSOChar read FBuf; property Size: Integer read FSize; property Position: integer read FBPos; @@ -516,30 +519,30 @@ TSuperEnumerator = class function GetDataType: TSuperType; function GetProcessing: boolean; procedure SetProcessing(value: boolean); - function ForcePath(const path: SOString; dataType: TSuperType = stObject): ISuperObject; - function Format(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; - - function GetO(const path: SOString): ISuperObject; - procedure PutO(const path: SOString; const Value: ISuperObject); - function GetB(const path: SOString): Boolean; - procedure PutB(const path: SOString; Value: Boolean); - function GetI(const path: SOString): SuperInt; - procedure PutI(const path: SOString; Value: SuperInt); - function GetD(const path: SOString): Double; - procedure PutC(const path: SOString; Value: Currency); - function GetC(const path: SOString): Currency; - procedure PutD(const path: SOString; Value: Double); - function GetS(const path: SOString): SOString; - procedure PutS(const path: SOString; const Value: SOString); + function ForcePath(const path: string; dataType: TSuperType = stObject): ISuperObject; + function Format(const str: string; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): string; + + function GetO(const path: string): ISuperObject; + procedure PutO(const path: string; const Value: ISuperObject); + function GetB(const path: string): Boolean; + procedure PutB(const path: string; Value: Boolean); + function GetI(const path: string): SuperInt; + procedure PutI(const path: string; Value: SuperInt); + function GetD(const path: string): Double; + procedure PutC(const path: string; Value: Currency); + function GetC(const path: string): Currency; + procedure PutD(const path: string; Value: Double); + function GetS(const path: string): string; + procedure PutS(const path: string; const Value: string); {$IFDEF SUPER_METHOD} - function GetM(const path: SOString): TSuperMethod; - procedure PutM(const path: SOString; Value: TSuperMethod); + function GetM(const path: string): TSuperMethod; + procedure PutM(const path: string; Value: TSuperMethod); {$ENDIF} - function GetA(const path: SOString): TSuperArray; + function GetA(const path: string): TSuperArray; // Null Object Design patern - function GetN(const path: SOString): ISuperObject; - procedure PutN(const path: SOString; const Value: ISuperObject); + function GetN(const path: string): ISuperObject; + procedure PutN(const path: string; const Value: ISuperObject); // Writers function Write(writer: TSuperWriter; indent: boolean; escape: boolean; level: integer): Integer; @@ -553,48 +556,48 @@ TSuperEnumerator = class function AsInteger: SuperInt; function AsDouble: Double; function AsCurrency: Currency; - function AsString: SOString; + function AsString: string; function AsArray: TSuperArray; function AsObject: TSuperTableString; {$IFDEF SUPER_METHOD} function AsMethod: TSuperMethod; {$ENDIF} - function AsJSon(indent: boolean = false; escape: boolean = true): SOString; + function AsJson(indent: boolean = false; escape: boolean = true): string; procedure Clear(all: boolean = false); procedure Pack(all: boolean = false); - property N[const path: SOString]: ISuperObject read GetN write PutN; - property O[const path: SOString]: ISuperObject read GetO write PutO; default; - property B[const path: SOString]: boolean read GetB write PutB; - property I[const path: SOString]: SuperInt read GetI write PutI; - property D[const path: SOString]: Double read GetD write PutD; - property C[const path: SOString]: Currency read GetC write PutC; - property S[const path: SOString]: SOString read GetS write PutS; + property N[const path: string]: ISuperObject read GetN write PutN; + property O[const path: string]: ISuperObject read GetO write PutO; default; + property B[const path: string]: boolean read GetB write PutB; + property I[const path: string]: SuperInt read GetI write PutI; + property D[const path: string]: Double read GetD write PutD; + property C[const path: string]: Currency read GetC write PutC; + property S[const path: string]: string read GetS write PutS; {$IFDEF SUPER_METHOD} - property M[const path: SOString]: TSuperMethod read GetM write PutM; + property M[const path: string]: TSuperMethod read GetM write PutM; {$ENDIF} - property A[const path: SOString]: TSuperArray read GetA; + property A[const path: string]: TSuperArray read GetA; {$IFDEF SUPER_METHOD} - function call(const path: SOString; const param: ISuperObject = nil): ISuperObject; overload; - function call(const path, param: SOString): ISuperObject; overload; + function call(const path: string; const param: ISuperObject = nil): ISuperObject; overload; + function call(const path, param: string): ISuperObject; overload; {$ENDIF} // clone a node function Clone: ISuperObject; - function Delete(const path: SOString): ISuperObject; + function Delete(const path: string): ISuperObject; // merges tow objects of same type, if reference is true then nodes are not cloned procedure Merge(const obj: ISuperObject; reference: boolean = false); overload; - procedure Merge(const str: SOString); overload; + procedure Merge(const str: string); overload; // validate methods - function Validate(const rules: SOString; const defs: SOString = ''; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; overload; + function Validate(const rules: string; const defs: string = ''; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; overload; function Validate(const rules: ISuperObject; const defs: ISuperObject = nil; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; overload; // compare function Compare(const obj: ISuperObject): TSuperCompareResult; overload; - function Compare(const str: SOString): TSuperCompareResult; overload; + function Compare(const str: string): TSuperCompareResult; overload; // the data type function IsType(AType: TSuperType): boolean; @@ -625,7 +628,7 @@ TSuperObject = class(TObject, ISuperObject) stMethod: (c_method: TSuperMethod); {$ENDIF} end; -{.$ifend} +{.endif} FOString: SOString; function GetDataType: TSuperType; function GetDataPtr: Pointer; @@ -639,30 +642,30 @@ TSuperObject = class(TObject, ISuperObject) function _AddRef: Integer; virtual; {$IFDEF UNIX}cdecl{$ELSE}stdcall{$ENDIF}; function _Release: Integer; virtual; {$IFDEF UNIX}cdecl{$ELSE}stdcall{$ENDIF}; - function GetO(const path: SOString): ISuperObject; - procedure PutO(const path: SOString; const Value: ISuperObject); - function GetB(const path: SOString): Boolean; - procedure PutB(const path: SOString; Value: Boolean); - function GetI(const path: SOString): SuperInt; - procedure PutI(const path: SOString; Value: SuperInt); - function GetD(const path: SOString): Double; - procedure PutD(const path: SOString; Value: Double); - procedure PutC(const path: SOString; Value: Currency); - function GetC(const path: SOString): Currency; - function GetS(const path: SOString): SOString; - procedure PutS(const path: SOString; const Value: SOString); + function GetO(const path: string): ISuperObject; + procedure PutO(const path: string; const Value: ISuperObject); + function GetB(const path: string): Boolean; + procedure PutB(const path: string; Value: Boolean); + function GetI(const path: string): SuperInt; + procedure PutI(const path: string; Value: SuperInt); + function GetD(const path: string): Double; + procedure PutD(const path: string; Value: Double); + procedure PutC(const path: string; Value: Currency); + function GetC(const path: string): Currency; + function GetS(const path: string): string; + procedure PutS(const path: string; const Value: string); {$IFDEF SUPER_METHOD} - function GetM(const path: SOString): TSuperMethod; - procedure PutM(const path: SOString; Value: TSuperMethod); + function GetM(const path: string): TSuperMethod; + procedure PutM(const path: string; Value: TSuperMethod); {$ENDIF} - function GetA(const path: SOString): TSuperArray; + function GetA(const path: string): TSuperArray; function Write(writer: TSuperWriter; indent: boolean; escape: boolean; level: integer): Integer; virtual; public function GetEnumerator: TSuperEnumerator; procedure AfterConstruction; override; procedure BeforeDestruction; override; class function NewInstance: TObject; override; - property RefCount: Integer read FRefCount; + property RefCount: Integer read FRefCount write FRefCount; function GetProcessing: boolean; procedure SetProcessing(value: boolean); @@ -672,7 +675,7 @@ TSuperObject = class(TObject, ISuperObject) function SaveTo(const FileName: string; indent: boolean = false; escape: boolean = true): integer; overload; function SaveTo(socket: longint; indent: boolean = false; escape: boolean = true): integer; overload; function CalcSize(indent: boolean = false; escape: boolean = true): integer; - function AsJSon(indent: boolean = false; escape: boolean = true): SOString; + function AsJSon(indent: boolean = false; escape: boolean = true): string; // parser ... owned! class function ParseString(s: PSOChar; strict: Boolean; partial: boolean = true; const this: ISuperObject = nil; options: TSuperFindOptions = []; @@ -690,7 +693,7 @@ TSuperObject = class(TObject, ISuperObject) constructor Create(i: SuperInt); overload; virtual; constructor Create(d: double); overload; virtual; constructor CreateCurrency(c: Currency); overload; virtual; - constructor Create(const s: SOString); overload; virtual; + constructor Create(const s: string); overload; virtual; {$IFDEF SUPER_METHOD} constructor Create(m: TSuperMethod); overload; virtual; {$ENDIF} @@ -701,7 +704,7 @@ TSuperObject = class(TObject, ISuperObject) function AsInteger: SuperInt; virtual; function AsDouble: Double; virtual; function AsCurrency: Currency; virtual; - function AsString: SOString; virtual; + function AsString: string; virtual; function AsArray: TSuperArray; virtual; function AsObject: TSuperTableString; virtual; {$IFDEF SUPER_METHOD} @@ -709,41 +712,41 @@ TSuperObject = class(TObject, ISuperObject) {$ENDIF} procedure Clear(all: boolean = false); virtual; procedure Pack(all: boolean = false); virtual; - function GetN(const path: SOString): ISuperObject; - procedure PutN(const path: SOString; const Value: ISuperObject); - function ForcePath(const path: SOString; dataType: TSuperType = stObject): ISuperObject; - function Format(const str: SOString; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): SOString; - - property N[const path: SOString]: ISuperObject read GetN write PutN; - property O[const path: SOString]: ISuperObject read GetO write PutO; default; - property B[const path: SOString]: boolean read GetB write PutB; - property I[const path: SOString]: SuperInt read GetI write PutI; - property D[const path: SOString]: Double read GetD write PutD; - property C[const path: SOString]: Currency read GetC write PutC; - property S[const path: SOString]: SOString read GetS write PutS; + function GetN(const path: string): ISuperObject; + procedure PutN(const path: string; const Value: ISuperObject); + function ForcePath(const path: string; dataType: TSuperType = stObject): ISuperObject; + function Format(const str: string; BeginSep: SOChar = '%'; EndSep: SOChar = '%'): string; + + property N[const path: string]: ISuperObject read GetN write PutN; + property O[const path: string]: ISuperObject read GetO write PutO; default; + property B[const path: string]: boolean read GetB write PutB; + property I[const path: string]: SuperInt read GetI write PutI; + property D[const path: string]: Double read GetD write PutD; + property C[const path: string]: Currency read GetC write PutC; + property S[const path: string]: string read GetS write PutS; {$IFDEF SUPER_METHOD} - property M[const path: SOString]: TSuperMethod read GetM write PutM; + property M[const path: string]: TSuperMethod read GetM write PutM; {$ENDIF} - property A[const path: SOString]: TSuperArray read GetA; + property A[const path: string]: TSuperArray read GetA; {$IFDEF SUPER_METHOD} - function call(const path: SOString; const param: ISuperObject = nil): ISuperObject; overload; virtual; - function call(const path, param: SOString): ISuperObject; overload; virtual; + function call(const path: string; const param: ISuperObject = nil): ISuperObject; overload; virtual; + function call(const path, param: string): ISuperObject; overload; virtual; {$ENDIF} // clone a node function Clone: ISuperObject; virtual; - function Delete(const path: SOString): ISuperObject; + function Delete(const path: string): ISuperObject; // merges tow objects of same type, if reference is true then nodes are not cloned procedure Merge(const obj: ISuperObject; reference: boolean = false); overload; - procedure Merge(const str: SOString); overload; + procedure Merge(const str: string); overload; // validate methods - function Validate(const rules: SOString; const defs: SOString = ''; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; overload; + function Validate(const rules: string; const defs: string = ''; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; overload; function Validate(const rules: ISuperObject; const defs: ISuperObject = nil; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; overload; // compare function Compare(const obj: ISuperObject): TSuperCompareResult; overload; - function Compare(const str: SOString): TSuperCompareResult; overload; + function Compare(const str: string): TSuperCompareResult; overload; // the data type function IsType(AType: TSuperType): boolean; @@ -759,6 +762,9 @@ TSuperRttiContext = class; TSerialFromJson = function(ctx: TSuperRttiContext; const obj: ISuperObject; var Value: TValue): Boolean; TSerialToJson = function(ctx: TSuperRttiContext; var value: TValue; const index: ISuperObject): ISuperObject; + TSuperIgnoreAttribute = class(TCustomAttribute) + end; + TSuperAttribute = class(TCustomAttribute) private FName: string; @@ -767,14 +773,45 @@ TSuperAttribute = class(TCustomAttribute) property Name: string read FName; end; + TClassElement = (ceField, ceProperty); + TClassElements = set of TClassElement; + + TClassAttribute = class(TCustomAttribute) + strict private + FElements: TClassElements; + FIgnoredName: string; + + public + constructor Create(const Value: cardinal); overload; + constructor Create(const Value: cardinal; const ignoredName: string); overload; + constructor Create(const Elements: TClassElements; const ignoredName: string = ''); overload; + + function isIgnoredName(const aName: string): boolean; + + property Elements: TClassElements read FElements; + end; + + TArrayAttribute = class(TCustomAttribute) + end; + + SOElements = class(TClassAttribute); + SOIgnore = class(TSuperIgnoreAttribute); SOName = class(TSuperAttribute); SODefault = class(TSuperAttribute); - + SOArray = class(TArrayAttribute); + SOType = class(TSuperAttribute); TSuperRttiContext = class private - class function GetFieldName(r: TRttiField): string; - class function GetFieldDefault(r: TRttiField; const obj: ISuperObject): ISuperObject; + class function isArrayExportable(const aMember: TRttiMember): boolean; + class function isExportable(const aType: TRttiType; const Element: TClassElement): boolean; + class function isIgnoredName(const aType: TRttiType; const rttiMember: TRttiMember): boolean; + class function isIgnoredObject(r: TRttiObject): boolean; + class function GetObjectName(r: TRttiNamedObject): string; + class function GetObjectDefault(r: TRttiObject; const obj: ISuperObject): ISuperObject; + + function Array2Class(const Value: TValue; const index: ISuperObject): TSuperObject; + public Context: TRttiContext; SerialFromJson: TDictionary; @@ -801,35 +838,39 @@ TSuperObjectIter = record Ite: TSuperAvlIterator; end; + const cst_ce_field = 1; + const cst_ce_property = 2; + + function ObjectIsError(obj: TSuperObject): boolean; function ObjectIsType(const obj: ISuperObject; typ: TSuperType): boolean; function ObjectGetType(const obj: ISuperObject): TSuperType; function ObjectIsNull(const obj: ISuperObject): Boolean; -function ObjectFindFirst(const obj: ISuperObject; var F: TSuperObjectIter): boolean; +function ObjectFindFirst(const obj: ISuperObject; out F: TSuperObjectIter): boolean; function ObjectFindNext(var F: TSuperObjectIter): boolean; procedure ObjectFindClose(var F: TSuperObjectIter); -function SO(const s: SOString = '{}'): ISuperObject; overload; +function SO(const s: string = '{}'): ISuperObject; overload; function SO(const value: Variant): ISuperObject; overload; function SO(const Args: array of const): ISuperObject; overload; function SA(const Args: array of const): ISuperObject; overload; -function SA(const AStrings: TStringDynArray): ISuperObject; overload; -function SA(const AStrings: TArray): ISuperObject; overload; +//function SA(const AStrings: TStringDynArray): ISuperObject; overload; +function SAS(const AStrings: TArray): ISuperObject; overload; function TryObjectToDate(const obj: ISuperObject; var dt: TDateTime): Boolean; -function UUIDToString(const g: TGUID): SOString; -function StringToUUID(const str: SOString; var g: TGUID): Boolean; +function UUIDToString(const g: TGUID): string; +function StringToUUID(const str: string; var g: TGUID): Boolean; {$IFDEF HAVE_RTTI} type TSuperInvokeResult = ( irSuccess, - irMethothodError, // method don't exist - irParamError, // invalid parametters - irError // other error + irMethodError, // method don't exist + irParamError, // invalid parametters + irError // other error ); function TrySOInvoke(var ctx: TSuperRttiContext; const obj: TValue; const method: string; const params: ISuperObject; var Return: ISuperObject): TSuperInvokeResult; overload; @@ -851,6 +892,8 @@ implementation {$ENDIF} ; +{$UNDEF DEBUG} + {$IFDEF DEBUG} var debugcount: integer = 0; @@ -871,7 +914,9 @@ implementation ESC_SR: PSOChar = '\/'; ESC_ZERO: PSOChar = '\u0000'; + {$IFDEF MSWINDOWS} TOK_CRLF: PSOChar = #13#10; + {$ENDIF} TOK_SP: PSOChar = #32; TOK_BS: PSOChar = #8; TOK_TAB: PSOChar = #9; @@ -955,18 +1000,18 @@ function StrLen(const Str: PSOChar): Cardinal; Result := (p - Str); end; end; -{$ifend} +{$endif} function FloatToJson(const value: Double): SOString; var p: PSOChar; begin - Result := FloatToStr(value); - if {$if defined(NEED_FORMATSETTINGS)}FormatSettings.{$ifend}DecimalSeparator <> '.' then + Result := SOString(FloatToStr(value)); + if {$if defined(NEED_FORMATSETTINGS)}FormatSettings.{$endif}DecimalSeparator <> '.' then begin p := PSOChar(Result); while p^ <> #0 do - if p^ <> SOChar({$if defined(NEED_FORMATSETTINGS)}FormatSettings.{$ifend}DecimalSeparator) then + if p^ <> SOChar({$if defined(NEED_FORMATSETTINGS)}FormatSettings.{$endif}DecimalSeparator) then inc(p) else begin p^ := '.'; @@ -979,12 +1024,12 @@ function CurrToJson(const value: Currency): SOString; var p: PSOChar; begin - Result := CurrToStr(value); - if {$if defined(NEED_FORMATSETTINGS)}FormatSettings.{$ifend}DecimalSeparator <> '.' then + Result := SOString(CurrToStr(value)); + if {$if defined(NEED_FORMATSETTINGS)}FormatSettings.{$endif}DecimalSeparator <> '.' then begin p := PSOChar(Result); while p^ <> #0 do - if p^ <> SOChar({$if defined(NEED_FORMATSETTINGS)}FormatSettings.{$ifend}DecimalSeparator) then + if p^ <> SOChar({$if defined(NEED_FORMATSETTINGS)}FormatSettings.{$endif}DecimalSeparator) then inc(p) else begin p^ := '.'; @@ -1017,15 +1062,15 @@ function TryObjectToDate(const obj: ISuperObject; var dt: TDateTime): Boolean; end; end; -function SO(const s: SOString = '{}'): ISuperObject; +function SO(const s: string = '{}'): ISuperObject; begin - Result := TSuperObject.ParseString(PSOChar(s), False); + Result := TSuperObject.ParseString(PSOChar(SOString(s)), False); end; function SA(const Args: array of const): ISuperObject; overload; -type +{type TByteArray = array[0..sizeof(integer) - 1] of byte; - PByteArray = ^TByteArray; + PByteArray = ^TByteArray;} var j: Integer; intf: IInterface; @@ -1037,14 +1082,14 @@ function SA(const Args: array of const): ISuperObject; overload; vtInteger : Add(TSuperObject.Create(TVarRec(Args[j]).VInteger)); vtInt64 : Add(TSuperObject.Create(TVarRec(Args[j]).VInt64^)); vtBoolean : Add(TSuperObject.Create(TVarRec(Args[j]).VBoolean)); - vtChar : Add(TSuperObject.Create(SOString(TVarRec(Args[j]).VChar))); - vtWideChar: Add(TSuperObject.Create(SOChar(TVarRec(Args[j]).VWideChar))); + vtChar : Add(TSuperObject.Create(string(TVarRec(Args[j]).VChar))); + vtWideChar: Add(TSuperObject.Create(string(TVarRec(Args[j]).VWideChar))); vtExtended: Add(TSuperObject.Create(TVarRec(Args[j]).VExtended^)); vtCurrency: Add(TSuperObject.CreateCurrency(TVarRec(Args[j]).VCurrency^)); - vtString : Add(TSuperObject.Create(SOString(TVarRec(Args[j]).VString^))); - vtPChar : Add(TSuperObject.Create(SOString(TVarRec(Args[j]).VPChar^))); - vtAnsiString: Add(TSuperObject.Create(SOString(AnsiString(TVarRec(Args[j]).VAnsiString)))); - vtWideString: Add(TSuperObject.Create(SOString(PWideChar(TVarRec(Args[j]).VWideString)))); + vtString : Add(TSuperObject.Create(string(TVarRec(Args[j]).VString^))); + vtPChar : Add(TSuperObject.Create(string(TVarRec(Args[j]).VPChar^))); + vtAnsiString: Add(TSuperObject.Create(string(AnsiString(TVarRec(Args[j]).VAnsiString)))); + vtWideString: Add(TSuperObject.Create(string(PWideChar(TVarRec(Args[j]).VWideString)))); vtInterface: if TVarRec(Args[j]).VInterface = nil then Add(nil) else @@ -1067,23 +1112,23 @@ function SA(const Args: array of const): ISuperObject; overload; Add(TSuperObject.Create(PtrInt(TVarRec(Args[j]).VPointer))); {$if declared(vtUnicodeString)} vtUnicodeString: - Add(TSuperObject.Create(SOString(string(TVarRec(Args[j]).VUnicodeString)))); -{$ifend} + Add(TSuperObject.Create(string(TVarRec(Args[j]).VUnicodeString))); +{$endif} else assert(false); end; end; -function SA(const AStrings: TStringDynArray): ISuperObject; overload; -var - i: integer; -begin - Result := TSuperObject.Create(stArray); - for i := 0 to High(AStrings) do - Result.AsArray.Add(TSuperObject.Create(AStrings[i])); -end; +//function SA(const AStrings: TStringDynArray): ISuperObject; overload; +//var +// i: integer; +//begin +// Result := TSuperObject.Create(stArray); +// for i := 0 to High(AStrings) do +// Result.AsArray.Add(TSuperObject.Create(AStrings[i])); +//end; -function SA(const AStrings: TArray): ISuperObject; overload; +function SAS(const AStrings: TArray): ISuperObject; overload; var i: integer; begin @@ -1101,7 +1146,7 @@ function SO(const Args: array of const): ISuperObject; overload; arr := SA(Args); with arr.AsArray do for j := 0 to (Length div 2) - 1 do - Result.AsObject.PutO(O[j*2].AsString, O[(j*2) + 1]); + Result.AsObject.PutO(SOString(O[j*2].AsString), O[(j*2) + 1]); end; function SO(const value: Variant): ISuperObject; overload; @@ -1116,21 +1161,21 @@ function SO(const value: Variant): ISuperObject; overload; varDouble: Result := TSuperObject.Create(VDouble); varCurrency: Result := TSuperObject.CreateCurrency(VCurrency); varDate: Result := TSuperObject.Create(DelphiToJavaDateTime(vDate)); - varOleStr: Result := TSuperObject.Create(SOString(VOleStr)); + varOleStr: Result := TSuperObject.Create(string(VOleStr)); varBoolean: Result := TSuperObject.Create(VBoolean); varShortInt: Result := TSuperObject.Create(VShortInt); varByte: Result := TSuperObject.Create(VByte); varWord: Result := TSuperObject.Create(VWord); varLongWord: Result := TSuperObject.Create(VLongWord); varInt64: Result := TSuperObject.Create(VInt64); - varString: Result := TSuperObject.Create(SOString(AnsiString(VString))); + varString: Result := TSuperObject.Create(string(AnsiString(VString))); {$if declared(varUString)} {$IFDEF FPC} - varUString: Result := TSuperObject.Create(SOString(UnicodeString(VString))); + varUString: Result := TSuperObject.Create(string(UnicodeString(VString))); {$ELSE} - varUString: Result := TSuperObject.Create(SOString(string(VUString))); + varUString: Result := TSuperObject.Create(string(VUString)); {$ENDIF} -{$ifend} +{$endif} else raise Exception.CreateFmt('Unsuported variant data type: %d', [VType]); end; @@ -1160,7 +1205,7 @@ function ObjectIsNull(const obj: ISuperObject): Boolean; Result := ObjectIsType(obj, stNull); end; -function ObjectFindFirst(const obj: ISuperObject; var F: TSuperObjectIter): boolean; +function ObjectFindFirst(const obj: ISuperObject; out F: TSuperObjectIter): boolean; var i: TSuperAvlEntry; begin @@ -1448,7 +1493,7 @@ TUUID = record Result := True; end; -function UUIDToString(const g: TGUID): SOString; +function UUIDToString(const g: TGUID): string; begin Result := format('%.8x%.4x%.4x%.2x%.2x%.2x%.2x%.2x%.2x%.2x%.2x', [g.D1, g.D2, g.D3, @@ -1457,9 +1502,9 @@ function UUIDToString(const g: TGUID): SOString; g.D4[6], g.D4[7]]); end; -function StringToUUID(const str: SOString; var g: TGUID): Boolean; +function StringToUUID(const str: string; var g: TGUID): Boolean; begin - Result := UuidFromString(PSOChar(str), @g); + Result := UuidFromString(PSOChar(SOString(str)), @g); end; {$IFDEF HAVE_RTTI} @@ -1507,7 +1552,8 @@ function serialfromboolean(ctx: TSuperRttiContext; const obj: ISuperObject; var begin o := SO(obj.AsString); if not ObjectIsType(o, stString) then - Result := serialfromboolean(ctx, SO(obj.AsString), Value) else + Result := serialfromboolean(ctx, SO(obj.AsString), Value) + else Result := False; end; else @@ -1532,12 +1578,13 @@ function serialfromdatetime(ctx: TSuperRttiContext; const obj: ISuperObject; var begin TValueData(Value).FAsDouble := JavaToDelphiDateTime(i); Result := True; - end else - if TryStrToDateTime(obj.AsString, dt) then + end + else if TryStrToDateTime(obj.AsString, dt) then begin TValueData(Value).FAsDouble := dt; Result := True; - end else + end + else Result := False; end; else @@ -1553,7 +1600,8 @@ function serialfromguid(ctx: TSuperRttiContext; const obj: ISuperObject; var Val FillChar(Value.GetReferenceToRawData^, SizeOf(TGUID), 0); Result := True; end; - stString: Result := UuidFromString(PSOChar(obj.AsString), Value.GetReferenceToRawData); + stString: + Result := UuidFromString(PSOChar(obj.AsString), Value.GetReferenceToRawData); else Result := False; end; @@ -1642,7 +1690,7 @@ function TrySOInvoke(var ctx: TSuperRttiContext; const obj: TValue; begin t := TRttiInstanceType(ctx.Context.GetType(obj.AsObject.ClassType)); m := t.GetMethod(method); - if m = nil then Exit(irMethothodError); + if m = nil then Exit(irMethodError); ps := m.GetParameters; SetLength(a, Length(ps)); if not GetParams then Exit(irParamError); @@ -1662,7 +1710,7 @@ function TrySOInvoke(var ctx: TSuperRttiContext; const obj: TValue; begin t := TRttiInstanceType(ctx.Context.GetType(obj.AsClass)); m := t.GetMethod(method); - if m = nil then Exit(irMethothodError); + if m = nil then Exit(irMethodError); ps := m.GetParameters; SetLength(a, Length(ps)); @@ -1864,12 +1912,12 @@ function DoMinimalEscape(str: PSOChar; len: Integer): Integer; var pos, start_offset: Integer; c: SOChar; -type +{type TByteChar = record case integer of 0: (a, b: Byte); 1: (c: WideChar); - end; + end;} begin if str = nil then begin @@ -2143,10 +2191,10 @@ function TSuperObject.AsCurrency: Currency; end; end; -function TSuperObject.AsString: SOString; +function TSuperObject.AsString: string; begin case FDataType of - stString: Result := FOString; + stString: Result := string(FOString); stNull: Result := ''; else Result := AsJSon(false, false); @@ -2183,19 +2231,19 @@ function TSuperObject.AsObject: TSuperTableString; Result := nil; end; -function TSuperObject.AsJSon(indent, escape: boolean): SOString; +function TSuperObject.AsJson(indent, escape: boolean): string; var pb: TSuperWriterString; begin pb := TSuperWriterString.Create; try - if(Write(pb, indent, escape, 0) < 0) then + if Write(pb, indent, escape, 0) < 0 then begin Result := ''; Exit; end; if pb.FBPos > 0 then - Result := pb.FBuf else + Result := string(pb.FBuf) else Result := ''; finally pb.Free; @@ -2271,7 +2319,7 @@ class function TSuperObject.ParseFile(const FileName: string; strict: Boolean; var stream: TFileStream; begin - stream := TFileStream.Create(FileName, fmOpenRead, fmShareDenyWrite); + stream := TFileStream.Create(FileName, fmOpenRead or fmShareDenyWrite); try Result := ParseStream(stream, strict, partial, this, options, put, dt); finally @@ -2529,7 +2577,7 @@ class function TSuperObject.ParseEx(tok: TSuperTokenizer; str: PSOChar; len: int begin if (v = tok.quote_char) then begin - TokRec^.current := TSuperObject.Create(SOString(tok.pb.GetString)); + TokRec^.current := TSuperObject.Create(string(tok.pb.GetString)); TokRec^.saved_state := tsFinish; TokRec^.state := tsEatws; end else @@ -3263,34 +3311,34 @@ class function TSuperObject.ParseEx(tok: TSuperTokenizer; str: PSOChar; len: int Result := nil; end; -procedure TSuperObject.PutO(const path: SOString; const Value: ISuperObject); +procedure TSuperObject.PutO(const path: string; const Value: ISuperObject); begin - ParseString(PSOChar(path), true, False, self, [foCreatePath, foPutValue], Value); + ParseString(PSOChar(SOString(path)), true, False, self, [foCreatePath, foPutValue], Value); end; -procedure TSuperObject.PutB(const path: SOString; Value: Boolean); +procedure TSuperObject.PutB(const path: string; Value: Boolean); begin - ParseString(PSOChar(path), true, False, self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); + ParseString(PSOChar(SOString(path)), true, False, self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); end; -procedure TSuperObject.PutD(const path: SOString; Value: Double); +procedure TSuperObject.PutD(const path: string; Value: Double); begin - ParseString(PSOChar(path), true, False, self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); + ParseString(PSOChar(SOString(path)), true, False, self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); end; -procedure TSuperObject.PutC(const path: SOString; Value: Currency); +procedure TSuperObject.PutC(const path: string; Value: Currency); begin - ParseString(PSOChar(path), true, False, self, [foCreatePath, foPutValue], TSuperObject.CreateCurrency(Value)); + ParseString(PSOChar(SOString(path)), true, False, self, [foCreatePath, foPutValue], TSuperObject.CreateCurrency(Value)); end; -procedure TSuperObject.PutI(const path: SOString; Value: SuperInt); +procedure TSuperObject.PutI(const path: string; Value: SuperInt); begin - ParseString(PSOChar(path), true, False, self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); + ParseString(PSOChar(SOString(path)), true, False, self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); end; -procedure TSuperObject.PutS(const path: SOString; const Value: SOString); +procedure TSuperObject.PutS(const path: string; const Value: string); begin - ParseString(PSOChar(path), true, False, self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); + ParseString(PSOChar(SOString(path)), true, False, self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); end; @@ -3355,10 +3403,10 @@ function TSuperObject.SaveTo(socket: Integer; indent, escape: boolean): integer; pb.Free; end; -constructor TSuperObject.Create(const s: SOString); +constructor TSuperObject.Create(const s: string); begin Create(stString); - FOString := s; + FOString := SOString(s); end; procedure TSuperObject.Clear(all: boolean); @@ -3397,23 +3445,23 @@ procedure TSuperObject.Pack(all: boolean = false); end; end; -function TSuperObject.GetN(const path: SOString): ISuperObject; +function TSuperObject.GetN(const path: string): ISuperObject; begin - Result := ParseString(PSOChar(path), False, true, self); + Result := ParseString(PSOChar(SOString(path)), False, true, self); if Result = nil then Result := TSuperObject.Create(stNull); end; -procedure TSuperObject.PutN(const path: SOString; const Value: ISuperObject); +procedure TSuperObject.PutN(const path: string; const Value: ISuperObject); begin if Value = nil then - ParseString(PSOChar(path), False, True, self, [foCreatePath, foPutValue], TSuperObject.Create(stNull)) else - ParseString(PSOChar(path), False, True, self, [foCreatePath, foPutValue], Value); + ParseString(PSOChar(SOString(path)), False, True, self, [foCreatePath, foPutValue], TSuperObject.Create(stNull)) else + ParseString(PSOChar(SOString(path)), False, True, self, [foCreatePath, foPutValue], Value); end; -function TSuperObject.Delete(const path: SOString): ISuperObject; +function TSuperObject.Delete(const path: string): ISuperObject; begin - Result := ParseString(PSOChar(path), False, true, self, [foDelete]); + Result := ParseString(PSOChar(SOString(path)), False, true, self, [foDelete]); end; function TSuperObject.Clone: ISuperObject; @@ -3427,7 +3475,7 @@ function TSuperObject.Clone: ISuperObject; stDouble: Result := TSuperObject.Create(FO.c_double); stCurrency: Result := TSuperObject.CreateCurrency(FO.c_currency); stInt: Result := TSuperObject.Create(FO.c_int); - stString: Result := TSuperObject.Create(FOString); + stString: Result := TSuperObject.Create(string(FOString)); {$IFDEF SUPER_METHOD} stMethod: Result := TSuperObject.Create(FO.c_method); {$ENDIF} @@ -3435,10 +3483,13 @@ function TSuperObject.Clone: ISuperObject; begin Result := TSuperObject.Create(stObject); if ObjectFindFirst(self, ite) then - with Result.AsObject do - repeat - PutO(ite.key, ite.val.Clone); - until not ObjectFindNext(ite); + with Result.AsObject do + repeat + if ite.val = nil then + PutO(ite.key, nil) + else + PutO(ite.key, ite.val.Clone); + until not ObjectFindNext(ite); ObjectFindClose(ite); end; stArray: @@ -3446,8 +3497,8 @@ function TSuperObject.Clone: ISuperObject; Result := TSuperObject.Create(stArray); arr := AsArray; with Result.AsArray do - for j := 0 to arr.Length - 1 do - Add(arr.GetO(j).Clone); + for j := 0 to arr.Length - 1 do + Add(arr.GetO(j).Clone); end; stNull: Result := TSuperObject.Create(stNull); @@ -3469,7 +3520,7 @@ procedure TSuperObject.Merge(const obj: ISuperObject; reference: boolean); stDouble: FO.c_double := obj.AsDouble; stCurrency: FO.c_currency := obj.AsCurrency; stInt: FO.c_int := obj.AsInteger; - stString: FOString := obj.AsString; + stString: FOString := SOString(obj.AsString); {$IFDEF SUPER_METHOD} stMethod: FO.c_method := obj.AsMethod; {$ENDIF} @@ -3510,9 +3561,9 @@ procedure TSuperObject.Merge(const obj: ISuperObject; reference: boolean); end; end; -procedure TSuperObject.Merge(const str: SOString); +procedure TSuperObject.Merge(const str: string); begin - Merge(TSuperObject.ParseString(PSOChar(str), False), true); + Merge(TSuperObject.ParseString(PSOChar(SOString(str)), False), true); end; class function TSuperObject.NewInstance: TObject; @@ -3521,58 +3572,60 @@ class function TSuperObject.NewInstance: TObject; TSuperObject(Result).FRefCount := 1; end; -function TSuperObject.ForcePath(const path: SOString; dataType: TSuperType = stObject): ISuperObject; +function TSuperObject.ForcePath(const path: string; dataType: TSuperType = stObject): ISuperObject; begin - Result := ParseString(PSOChar(path), False, True, Self, [foCreatePath], nil, dataType); + Result := ParseString(PSOChar(SOString(path)), False, True, Self, [foCreatePath], nil, dataType); end; -function TSuperObject.Format(const str: SOString; BeginSep: SOChar; EndSep: SOChar): SOString; +function TSuperObject.Format(const str: string; BeginSep: SOChar; EndSep: SOChar): string; var p1, p2: PSOChar; + Res: SOString; begin - Result := ''; - p2 := PSOChar(str); + Res := ''; + p2 := PSOChar(SOString(str)); p1 := p2; while true do if p2^ = BeginSep then begin if p2 > p1 then - Result := Result + Copy(p1, 0, p2-p1); + Res := Res + Copy(p1, 0, p2-p1); inc(p2); p1 := p2; while true do if p2^ = EndSep then Break else if p2^ = #0 then Exit else inc(p2); - Result := Result + GetS(copy(p1, 0, p2-p1)); + Res := Res + SOString(GetS(copy(string(p1), 0, p2-p1))); inc(p2); p1 := p2; end else if p2^ = #0 then begin if p2 > p1 then - Result := Result + Copy(p1, 0, p2-p1); + Res := Res + Copy(p1, 0, p2-p1); Break; end else inc(p2); + Result := string(Res); end; -function TSuperObject.GetO(const path: SOString): ISuperObject; +function TSuperObject.GetO(const path: string): ISuperObject; begin - Result := ParseString(PSOChar(path), False, True, Self); + Result := ParseString(PSOChar(SOString(path)), False, True, Self); end; -function TSuperObject.GetA(const path: SOString): TSuperArray; +function TSuperObject.GetA(const path: string): TSuperArray; var obj: ISuperObject; begin - obj := ParseString(PSOChar(path), False, True, Self); + obj := ParseString(PSOChar(SOString(path)), False, True, Self); if obj <> nil then Result := obj.AsArray else Result := nil; end; -function TSuperObject.GetB(const path: SOString): Boolean; +function TSuperObject.GetB(const path: string): Boolean; var obj: ISuperObject; begin @@ -3582,7 +3635,7 @@ function TSuperObject.GetB(const path: SOString): Boolean; Result := false; end; -function TSuperObject.GetD(const path: SOString): Double; +function TSuperObject.GetD(const path: string): Double; var obj: ISuperObject; begin @@ -3592,7 +3645,7 @@ function TSuperObject.GetD(const path: SOString): Double; Result := 0.0; end; -function TSuperObject.GetC(const path: SOString): Currency; +function TSuperObject.GetC(const path: string): Currency; var obj: ISuperObject; begin @@ -3602,7 +3655,7 @@ function TSuperObject.GetC(const path: SOString): Currency; Result := 0.0; end; -function TSuperObject.GetI(const path: SOString): SuperInt; +function TSuperObject.GetI(const path: string): SuperInt; var obj: ISuperObject; begin @@ -3622,7 +3675,7 @@ function TSuperObject.GetDataType: TSuperType; Result := FDataType end; -function TSuperObject.GetS(const path: SOString): SOString; +function TSuperObject.GetS(const path: string): string; var obj: ISuperObject; begin @@ -3644,9 +3697,9 @@ function TSuperObject.SaveTo(const FileName: string; indent, escape: boolean): i end; end; -function TSuperObject.Validate(const rules: SOString; const defs: SOString = ''; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; +function TSuperObject.Validate(const rules: string; const defs: string = ''; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; begin - Result := Validate(TSuperObject.ParseString(PSOChar(rules), False), TSuperObject.ParseString(PSOChar(defs), False), callback, sender); + Result := Validate(TSuperObject.ParseString(PSOChar(SOString(rules)), False), TSuperObject.ParseString(PSOChar(SOString(defs)), False), callback, sender); end; function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObject = nil; callback: TSuperOnValidateError = nil; sender: Pointer = nil): boolean; @@ -3669,7 +3722,7 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje o := p['inherit']; if (o <> nil) and ObjectIsType(o, stString) then begin - e := names.AsObject.Search(o.AsString); + e := names.AsObject.Search(SOString(o.AsString)); if (e <> nil) then Result := FindInheritedProperty(prop, e.Value) else Result := nil; @@ -3686,7 +3739,7 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje obj := FindInheritedProperty('type', o); if obj <> nil then begin - e := datatypes.AsObject.Search(obj.AsString); + e := datatypes.AsObject.Search(SOString(obj.AsString)); if e <> nil then Result := TDataType(e.Value.AsInteger) else Result := dtUnknown; @@ -3745,7 +3798,7 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje o := p['inherit']; if ObjectIsType(o, stString) then begin - e := names.AsObject.Search(o.AsString); + e := names.AsObject.Search(SOString(o.AsString)); if (e <> nil) then Result := FindInheritedField(prop, e.Value) else Result := nil; @@ -3787,7 +3840,7 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje o := p['inherit']; if ObjectIsType(o, stString) then begin - e := names.AsObject.Search(o.AsString); + e := names.AsObject.Search(SOString(o.AsString)); if (e <> nil) then Result := InheritedFieldExist(obj, e.Value, name) and Result; end; @@ -3825,7 +3878,7 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje while e <> nil do begin if list.AsObject.Search(e.Name) = nil then - list[e.Name] := e.Value; + list[string(e.Name)] := e.Value; i.Next; e := i.GetIter; end; @@ -3838,7 +3891,7 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje o := p['inherit']; if ObjectIsType(o, stString) then begin - e := names.AsObject.Search(o.AsString); + e := names.AsObject.Search(SOString(o.AsString)); if (e <> nil) then GetInheritedFieldList(list, e.Value); end; @@ -4074,7 +4127,7 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje stObject: begin for i := 0 to o.AsArray.Length - 1 do - result := process(o.AsArray.GetO(i), sequence, objpath + '[' + IntToStr(i) + ']') and result; + result := process(o.AsArray.GetO(i), sequence, objpath + '[' + SOString(IntToStr(i)) + ']') and result; if getInheritedBool('unique', sequence) then begin // type is unique ? @@ -4082,15 +4135,15 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje try for i := 0 to o.AsArray.Length - 1 do begin - s := o.AsArray.GetO(i).AsString; + s := SOString(o.AsArray.GetO(i).AsString); if (s <> '') then begin if uniquelist.AsObject.Search(s) = nil then - uniquelist[s] := nil else + uniquelist[string(s)] := nil else begin Result := False; if Assigned(callback) then - callback(sender, veDuplicateEntry, objpath + '[' + IntToStr(i) + ']'); + callback(sender, veDuplicateEntry, objpath + '[' + SOString(IntToStr(i)) + ']'); end; end; end; @@ -4120,14 +4173,14 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje o2 := o.AsArray.GetO(i); if o2 <> nil then begin - s := o2.AsObject.GetO(ent.Name).AsString; + s := SOString(o2.AsObject.GetO(ent.Name).AsString); if (s <> '') then if uniquelist.AsObject.Search(s) = nil then - uniquelist[s] := nil else + uniquelist[string(s)] := nil else begin Result := False; if Assigned(callback) then - callback(sender, veDuplicateEntry, objpath + '[' + IntToStr(i) + '].' + ent.name); + callback(sender, veDuplicateEntry, objpath + '[' + SOString(IntToStr(i)) + '].' + ent.name); end; end; end; @@ -4145,8 +4198,6 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje fieldlist := nil; end; end; - - end; stNull: {nop}; else @@ -4155,7 +4206,6 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje callback(sender, veRuleMalformated, objpath); end; Result := Result and CheckLength(o.AsArray.Length, p, objpath); - end; else result := false; @@ -4212,7 +4262,6 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje result := false; end; Result := Result and CheckEnum(o, p, objpath) - end; var j: integer; @@ -4272,9 +4321,9 @@ function TSuperObject._Release: Integer; Destroy; end; -function TSuperObject.Compare(const str: SOString): TSuperCompareResult; +function TSuperObject.Compare(const str: string): TSuperCompareResult; begin - Result := Compare(TSuperObject.ParseString(PSOChar(str), False)); + Result := Compare(TSuperObject.ParseString(PSOChar(SOString(str)), False)); end; function TSuperObject.Compare(const obj: ISuperObject): TSuperCompareResult; @@ -4300,7 +4349,7 @@ function TSuperObject.Compare(const obj: ISuperObject): TSuperCompareResult; stDouble: Result := GetDblCompResult(ord(FO.c_boolean) - obj.AsDouble); stCurrency:Result := GetDblCompResult(ord(FO.c_boolean) - obj.AsCurrency); stInt: Result := GetIntCompResult(ord(FO.c_boolean) - obj.AsInteger); - stString: Result := GetIntCompResult(StrComp(PSOChar(AsString), PSOChar(obj.AsString))); + stString: Result := GetIntCompResult(StrComp(PSOChar(SOString(AsString)), PSOChar(SOString(obj.AsString)))); else Result := cpError; end; @@ -4310,7 +4359,7 @@ function TSuperObject.Compare(const obj: ISuperObject): TSuperCompareResult; stDouble: Result := GetDblCompResult(FO.c_double - obj.AsDouble); stCurrency:Result := GetDblCompResult(FO.c_double - obj.AsCurrency); stInt: Result := GetDblCompResult(FO.c_double - obj.AsInteger); - stString: Result := GetIntCompResult(StrComp(PSOChar(AsString), PSOChar(obj.AsString))); + stString: Result := GetIntCompResult(StrComp(PSOChar(SOString(AsString)), PSOChar(SOString(obj.AsString)))); else Result := cpError; end; @@ -4320,7 +4369,7 @@ function TSuperObject.Compare(const obj: ISuperObject): TSuperCompareResult; stDouble: Result := GetDblCompResult(FO.c_currency - obj.AsDouble); stCurrency:Result := GetDblCompResult(FO.c_currency - obj.AsCurrency); stInt: Result := GetDblCompResult(FO.c_currency - obj.AsInteger); - stString: Result := GetIntCompResult(StrComp(PSOChar(AsString), PSOChar(obj.AsString))); + stString: Result := GetIntCompResult(StrComp(PSOChar(SOString(AsString)), PSOChar(SOString(obj.AsString)))); else Result := cpError; end; @@ -4330,7 +4379,7 @@ function TSuperObject.Compare(const obj: ISuperObject): TSuperCompareResult; stDouble: Result := GetDblCompResult(FO.c_int - obj.AsDouble); stCurrency:Result := GetDblCompResult(FO.c_int - obj.AsCurrency); stInt: Result := GetIntCompResult(FO.c_int - obj.AsInteger); - stString: Result := GetIntCompResult(StrComp(PSOChar(AsString), PSOChar(obj.AsString))); + stString: Result := GetIntCompResult(StrComp(PSOChar(SOString(AsString)), PSOChar(SOString(obj.AsString)))); else Result := cpError; end; @@ -4340,7 +4389,7 @@ function TSuperObject.Compare(const obj: ISuperObject): TSuperCompareResult; stDouble, stCurrency, stInt, - stString: Result := GetIntCompResult(StrComp(PSOChar(AsString), PSOChar(obj.AsString))); + stString: Result := GetIntCompResult(StrComp(PSOChar(SOString(AsString)), PSOChar(SOString(obj.AsString)))); else Result := cpError; end; @@ -4367,11 +4416,11 @@ constructor TSuperObject.Create(m: TSuperMethod); {$ENDIF} {$IFDEF SUPER_METHOD} -function TSuperObject.GetM(const path: SOString): TSuperMethod; +function TSuperObject.GetM(const path: string): TSuperMethod; var v: ISuperObject; begin - v := ParseString(PSOChar(path), False, True, Self); + v := ParseString(PSOChar(SOString(path)), False, True, Self); if (v <> nil) and (ObjectGetType(v) = stMethod) then Result := v.AsMethod else Result := nil; @@ -4379,23 +4428,23 @@ function TSuperObject.GetM(const path: SOString): TSuperMethod; {$ENDIF} {$IFDEF SUPER_METHOD} -procedure TSuperObject.PutM(const path: SOString; Value: TSuperMethod); +procedure TSuperObject.PutM(const path: string; Value: TSuperMethod); begin - ParseString(PSOChar(path), False, True, Self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); + ParseString(PSOChar(SOString(path)), False, True, Self, [foCreatePath, foPutValue], TSuperObject.Create(Value)); end; {$ENDIF} {$IFDEF SUPER_METHOD} -function TSuperObject.call(const path: SOString; const param: ISuperObject): ISuperObject; +function TSuperObject.call(const path: string; const param: ISuperObject): ISuperObject; begin - Result := ParseString(PSOChar(path), False, True, Self, [foCallMethod], param); + Result := ParseString(PSOChar(SOString(path)), False, True, Self, [foCallMethod], param); end; {$ENDIF} {$IFDEF SUPER_METHOD} -function TSuperObject.call(const path, param: SOString): ISuperObject; +function TSuperObject.call(const path, param: string): ISuperObject; begin - Result := ParseString(PSOChar(path), False, True, Self, [foCallMethod], TSuperObject.ParseString(PSOChar(param), False)); + Result := ParseString(PSOChar(SOString(path)), False, True, Self, [foCallMethod], TSuperObject.ParseString(PSOChar(SOString(param)), False)); end; {$ENDIF} @@ -4427,7 +4476,7 @@ function TSuperArray.Add(Data: SuperInt): Integer; Result := Add(TSuperObject.Create(Data)); end; -function TSuperArray.Add(const Data: SOString): Integer; +function TSuperArray.Add(const Data: string): Integer; begin Result := Add(TSuperObject.Create(Data)); end; @@ -4469,7 +4518,7 @@ procedure TSuperArray.Insert(index: Integer; const value: ISuperObject); if (index < FLength) then begin if FLength = FSize then - Expand(FLength); + Expand(index); if Index < FLength then Move(FArray^[index], FArray^[index + 1], (FLength - index) * SizeOf(Pointer)); @@ -4595,7 +4644,7 @@ function TSuperArray.GetI(const index: integer): SuperInt; Result := 0; end; -function TSuperArray.GetS(const index: integer): SOString; +function TSuperArray.GetS(const index: integer): string; var obj: ISuperObject; begin @@ -4656,9 +4705,9 @@ procedure TSuperArray.PutI(const index: integer; Value: SuperInt); PutO(index, TSuperObject.Create(Value)); end; -procedure TSuperArray.PutS(const index: integer; const Value: SOString); +procedure TSuperArray.PutS(const index: integer; const Value: string); begin - PutO(index, TSuperObject.Create(Value)); + PutO(index, TSuperObject.Create(string(Value))); end; {$IFDEF SUPER_METHOD} @@ -4726,9 +4775,12 @@ destructor TSuperWriterString.Destroy; FreeMem(FBuf) end; -function TSuperWriterString.GetString: SOString; +function TSuperWriterString.GetString: string; +var + Res: SOString; begin - SetString(Result, FBuf, FBPos); + SetString(Res, FBuf, FBPos); + Result := string(Res); end; procedure TSuperWriterString.Reset; @@ -5712,7 +5764,7 @@ function TSuperTableString.GetNames: ISuperObject; obj := ite.GetIter; while obj <> nil do begin - Result.AsArray.Add(TSuperObject.Create(obj.FName)); + Result.AsArray.Add(TSuperObject.Create(string(obj.FName))); ite.Next; obj := ite.GetIter; end; @@ -5770,7 +5822,7 @@ procedure TSuperTableString.PutO(const k: SOString; const value: ISuperObject); procedure TSuperTableString.PutS(const k: SOString; const value: SOString); begin - PutO(k, TSuperObject.Create(Value)); + PutO(k, TSuperObject.Create(string(Value))); end; function TSuperTableString.GetS(const k: SOString): SOString; @@ -5779,7 +5831,7 @@ function TSuperTableString.GetS(const k: SOString): SOString; begin obj := GetO(k); if obj <> nil then - Result := obj.AsString else + Result := SOString(obj.AsString) else Result := ''; end; @@ -5913,7 +5965,92 @@ destructor TSuperRttiContext.Destroy; inherited; end; -class function TSuperRttiContext.GetFieldName(r: TRttiField): string; +constructor TClassAttribute.Create(const Value: Cardinal); +begin + if(value and cst_ce_property=cst_ce_property) then + Create([ceProperty], '') + else + begin + Create([], ''); + end; +end; + +constructor TClassAttribute.Create(const Value: Cardinal; const ignoredName: string); +begin + if(value and cst_ce_property=cst_ce_property) then + Create([ceProperty], ignoredName) + else + begin + Create([], ignoredName); + end; +end; + +constructor TClassAttribute.Create(const Elements: TClassElements; const ignoredName: string); +begin + inherited Create; + self.FIgnoredName:=ignoredName; + FElements:=Elements; +end; + +function TClassAttribute.isIgnoredName(const aName: string): boolean; +begin + result:=uppercase(FIgnoredName)=uppercase(aName); +end; + + + +class function TSuperRttiContext.isArrayExportable(const aMember: TRttiMember): boolean; +var + o: TCustomAttribute; +begin + result:=false; + for o in aMember.GetAttributes do + begin + if o is SOArray then + begin + result:=true; + break; + end; + end; +end; + +class function TSuperRttiContext.isExportable(const aType: TRttiType; const Element: TClassElement): boolean; +var + o: TCustomAttribute; +begin + for o in aType.GetAttributes do + begin + if o is TClassAttribute then + Exit(element in SOElements(o).Elements); + end; + + Result := element=ceField; +end; + +class function TSuperRttiContext.isIgnoredName(const aType: TRttiType; const rttiMember: TRttiMember): boolean; +var + o: TCustomAttribute; +begin + for o in aType.GetAttributes do + begin + if o is TClassAttribute then + Exit(TClassAttribute(o).isIgnoredName(rttiMember.Name)); + end; + + Result := false; +end; + +class function TSuperRttiContext.isIgnoredObject(r: TRttiObject): boolean; +var + o: TCustomAttribute; +begin + for o in r.GetAttributes do + if o is SOIgnore then + Exit(true); + Result := false; +end; + +class function TSuperRttiContext.getObjectName(r: TRttiNamedObject): string; var o: TCustomAttribute; begin @@ -5923,7 +6060,7 @@ class function TSuperRttiContext.GetFieldName(r: TRttiField): string; Result := r.Name; end; -class function TSuperRttiContext.GetFieldDefault(r: TRttiField; const obj: ISuperObject): ISuperObject; +class function TSuperRttiContext.GetObjectDefault(r: TRttiObject; const obj: ISuperObject): ISuperObject; var o: TCustomAttribute; begin @@ -5953,6 +6090,39 @@ function TSuperRttiContext.AsJson(const obj: T; const index: ISuperObject = n Result := ToJson(v, so); end; +function TSuperRttiContext.Array2Class(const Value: TValue; const index: ISuperObject): TSuperObject; +var + enumObject, + obj: TObject; + getEnumerator, + moveNext: TRttiMethod; + current: TRttiProperty; + currentValue, + enumeratorValue: TValue; +begin + result:=nil; + obj:=TValueData(Value).FAsObject; + + getEnumerator:=context.GetType(obj.ClassType).GetMethod('GetEnumerator'); + if(getEnumerator<>nil) then + begin + Result := TSuperObject.Create(stArray); + + enumeratorValue:=getEnumerator.Invoke(obj, []); + enumObject:=TValueData(enumeratorValue).FAsObject; + + moveNext:=context.GetType(enumObject.ClassType).GetMethod('MoveNext'); + current:=context.GetType(enumObject.ClassType).GetProperty('Current'); + + while moveNext.Invoke(enumObject, []).AsBoolean do + begin + currentValue:=current.GetValue(enumObject); + result.AsArray.Add(toJSon(currentValue, index)); + end; + end; +end; + + function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject; var Value: TValue): Boolean; @@ -6014,7 +6184,8 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject i := obj.AsInteger; TypeData := GetTypeData(TypeInfo); if TypeData.MaxValue > TypeData.MinValue then - Result := (i >= TypeData.MinValue) and (i <= TypeData.MaxValue) else + Result := (i >= TypeData.MinValue) and (i <= TypeData.MaxValue) + else Result := (i >= TypeData.MinValue) and (i <= Int64(PCardinal(@TypeData.MaxValue)^)); if Result then TValue.Make(@i, TypeInfo, Value); @@ -6031,7 +6202,7 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject end; end; - procedure fromSet; + procedure FromSet; var i: Integer; begin @@ -6105,7 +6276,13 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject procedure FromClass; var f: TRttiField; + p: TRttiProperty; + addMethod,firstmethod: TRttiMethod; + elementType: TRttiType; + arrayValue, v: TValue; + oName: string; + count, i: integer; begin case ObjectGetType(obj) of stObject: @@ -6113,21 +6290,65 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject Result := True; if Value.Kind <> tkClass then Value := GetTypeData(TypeInfo).ClassType.Create; + for f in Context.GetType(Value.AsObject.ClassType).GetFields do if f.FieldType <> nil then begin v := TValue.Empty; - Result := FromJson(f.FieldType.Handle, GetFieldDefault(f, obj.AsObject[GetFieldName(f)]), v); - if Result then - f.SetValue(Value.AsObject, v) else - Exit; + if f.FieldType.ClassType<>TRttiMethodType then + if FromJson(f.FieldType.Handle, getObjectDefault(f, obj.AsObject[GetObjectName(f)]), v) then + f.SetValue(Value.AsObject, v); + end; + + for p in Context.GetType(Value.AsObject.ClassType).GetProperties do + if p.PropertyType <> nil then + begin + v := TValue.Empty; + if p.PropertyType.ClassType<>TRttiMethodType then + if FromJson(p.PropertyType.Handle, getObjectDefault(p, obj.AsObject[GetObjectName(p)]), v) then + if p.IsWritable then + p.SetValue(Value.AsObject, v); end; end; stNull: begin Value := nil; Result := True; - end + end; + stArray: + begin + result:=true; + if Value.Kind <> tkClass then + Value := GetTypeData(TypeInfo).ClassType.Create; + + count := obj.AsArray.Length; + oName:=value.AsObject.ClassName; + delete(oName, 1, pos('<', oName)); + delete(oName, length(oName), 1); + + elementType := nil; + if count>0 then + begin + firstmethod:=Context.GetType(TypeInfo).GetMethod('First'); + if firstmethod<>nil then + begin + elementType := firstmethod.ReturnType; + end + else + elementType:=self.Context.FindType(oName); + end; + if Assigned(elementType) then + for i := 0 to count - 1 do + begin + arrayValue:=TValue.Empty; + if not FromJson(elementType.Handle, obj.AsArray[i], arrayValue) then + Break; + + AddMethod:=Context.GetType(TypeInfo).GetMethod('Add'); + if(addMethod<>nil) then + addMethod.Invoke(value.AsObject, [arrayValue]); + end; + end; else // error Value := nil; @@ -6152,7 +6373,7 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject {$ELSE} p := TValueData(Value).FValueData.GetReferenceToRawData; {$ENDIF} - Result := FromJson(f.FieldType.Handle, GetFieldDefault(f, obj.AsObject[GetFieldName(f)]), v); + Result := FromJson(f.FieldType.Handle, GetObjectDefault(f, obj.AsObject[GetObjectName(f)]), v); if Result then f.SetValue(p, v) else begin @@ -6185,7 +6406,8 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject pb := p; typ := GetTypeData(TypeInfo); if typ.elType <> nil then - el := typ.elType^ else + el := typ.elType^ + else el := typ.elType2^; Result := True; @@ -6199,7 +6421,8 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject Inc(pb, typ.elSize); end; if Result then - TValue.MakeWithoutCopy(@p, TypeInfo, Value) else + TValue.MakeWithoutCopy(@p, TypeInfo, Value) + else DynArrayClear(p, TypeInfo); end; stNull: @@ -6214,7 +6437,8 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject pb := p; typ := GetTypeData(TypeInfo); if typ.elType <> nil then - el := typ.elType^ else + el := typ.elType^ + else el := typ.elType2^; Result := FromJson(el, obj, val); @@ -6336,7 +6560,12 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject begin Value := obj.AsString; Result := True; - end + end; + stNull: + begin + Value := TValue.From(Null); + Result := true; + end; else Value := nil; Result := False; @@ -6344,18 +6573,22 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject end; procedure FromInterface; - const soguid: TGuid = '{4B86A9E3-E094-4E5A-954A-69048B7B6327}'; + const + SOGUID: TGUID = '{4B86A9E3-E094-4E5A-954A-69048B7B6327}'; var o: ISuperObject; + GUID: TGUID; begin - if CompareMem(@GetTypeData(TypeInfo).Guid, @soguid, SizeOf(TGUID)) then + GUID := GetTypeData(TypeInfo).Guid; + if CompareMem(@GUID, @SOGUID, SizeOf(TGUID)) then begin if obj <> nil then - TValue.Make(@obj, TypeInfo, Value) else - begin - o := TSuperObject.Create(stNull); - TValue.Make(@o, TypeInfo, Value); - end; + TValue.Make(@obj, TypeInfo, Value) + else + begin + o := TSuperObject.Create(stNull); + TValue.Make(@o, TypeInfo, Value); + end; Result := True; end else Result := False; @@ -6368,27 +6601,34 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject begin if not SerialFromJson.TryGetValue(TypeInfo, Serial) then case TypeInfo.Kind of - tkChar: FromChar; - tkInt64: FromInt64; - tkEnumeration, tkInteger: FromInt(obj); - tkSet: fromSet; - tkFloat: FromFloat(obj); - tkString, tkLString, tkUString, tkWString: FromString; - tkClass: FromClass; + tkChar: FromChar; + tkInt64: FromInt64; + tkEnumeration, + tkInteger: FromInt(obj); + tkSet: FromSet; + tkFloat: FromFloat(obj); + tkString, + tkLString, + tkUString, + tkWString: FromString; + tkClass: FromClass; tkMethod: ; - tkWChar: FromWideChar; - tkRecord: FromRecord; + tkWChar: FromWideChar; + tkRecord: FromRecord; tkPointer: ; tkInterface: FromInterface; - tkArray: FromArray; - tkDynArray: FromDynArray; - tkClassRef: FromClassRef; + tkArray: FromArray; + tkDynArray: FromDynArray; + tkClassRef: FromClassRef; else FromUnknown end else begin TValue.Make(nil, TypeInfo, Value); Result := Serial(Self, obj, Value); + + if(value.IsObject) then + FromClass; end; end else Result := False; @@ -6429,6 +6669,7 @@ function TSuperRttiContext.ToJson(var value: TValue; const index: ISuperObject): procedure ToClass; var o: ISuperObject; + p: TRttiProperty; f: TRttiField; v: TValue; begin @@ -6439,12 +6680,29 @@ function TSuperRttiContext.ToJson(var value: TValue; const index: ISuperObject): begin Result := TSuperObject.Create(stObject); index[IntToStr(NativeInt(Value.AsObject))] := Result; - for f in Context.GetType(Value.AsObject.ClassType).GetFields do - if f.FieldType <> nil then - begin - v := f.GetValue(Value.AsObject); - Result.AsObject[GetFieldName(f)] := ToJson(v, index); - end + + if isExportable(Context.GetType(Value.AsObject.ClassType), ceField) then + for f in Context.GetType(Value.AsObject.ClassType).GetFields do + if (not isIgnoredObject(f)) and (f.FieldType <> nil) and (not isIgnoredName(Context.GetType(Value.AsObject.ClassType), f)) then + begin + v := f.GetValue(Value.AsObject); + if isArrayExportable(f) then + Result.AsObject[getObjectName(f)] := Array2Class(v, index) + else + Result.AsObject[getObjectName(f)] := ToJson(v, index); + end; + + if isExportable(Context.GetType(Value.AsObject.ClassType), ceProperty) then + for p in Context.GetType(Value.AsObject.ClassType).GetProperties do + if (not isIgnoredObject(p)) and (p.PropertyType <> nil) and (not isIgnoredName(Context.GetType(Value.AsObject.ClassType), p)) then + begin + v := p.GetValue(Value.AsObject); + + if isArrayExportable(p) then + Result.AsObject[getObjectName(p)] := Array2Class(v, index) + else + Result.AsObject[getObjectName(p)] := ToJson(v, index); + end end else Result := o; end else @@ -6468,13 +6726,14 @@ function TSuperRttiContext.ToJson(var value: TValue; const index: ISuperObject): begin Result := TSuperObject.Create(stObject); for f in Context.GetType(Value.TypeInfo).GetFields do + if (not isIgnoredObject(f)) then begin {$IFDEF VER210} v := f.GetValue(IValueData(TValueData(Value).FHeapData).GetReferenceToRawData); {$ELSE} v := f.GetValue(TValueData(Value).FValueData.GetReferenceToRawData); {$ENDIF} - Result.AsObject[GetFieldName(f)] := ToJson(v, index); + Result.AsObject[getObjectName(f)] := ToJson(v, index); end; end; @@ -6643,8 +6902,6 @@ function TSuperObjectHelper.ToJson(ctx: TSuperRttiContext = nil): ISuperObject; {$ENDIF} {$IFDEF DEBUG} -initialization - finalization Assert(debugcount = 0, 'Memory leak'); {$ENDIF} diff --git a/supertimezone.pas b/supertimezone.pas index db4adaf..088870d 100644 --- a/supertimezone.pas +++ b/supertimezone.pas @@ -14,14 +14,31 @@ interface supertypes; type + + { TSuperTimeZone } + TSuperTimeZone = class private const TZ_TZI_KEY = '\SYSTEM\CurrentControlSet\Control\TimeZoneInformation'; { Vista and + } TZ_KEY = '\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Time Zones\'; TZ_KEYNAME = 'TimeZoneKeyName'; + private type + {$IFDEF MSWINDOWS} + TExpirable = record + Timestamp: TDateTime; + Data: T; + function IsValid: Boolean; + class function Box(Data: T): TExpirable; static; + end; + {$ENDIF} private FName: SOString; + {$IFDEF MSWINDOWS} + FDaylightDisabled: TExpirable; + FCacheTZI: TDictionary>; + {$ENDIF} + function GetName: SOString; {$IFDEF MSWINDOWS} @@ -52,6 +69,7 @@ TSuperTimeZone = class class function GetLocalSuperTimeZoneInstance: TSuperTimeZone; static; public constructor Create(const TimeZoneName: SOString = ''); + destructor Destroy; override; { ISO8601 formatted date Parser } class function ParseISO8601Date(const ISO8601Date: SOString; @@ -65,11 +83,11 @@ TSuperTimeZone = class function JavaToDelphi(const JavaDateTime: Int64): TDateTime; function DelphiToJava(const DelphiDateTime: TDateTime): Int64; - function JavaToISO8601(JavaDateTime: Int64): SOString; - function DelphiToISO8601(DelphiDateTime: TDateTime): SOString; + function JavaToISO8601(JavaDateTime: Int64): string; + function DelphiToISO8601(DelphiDateTime: TDateTime): string; - function ISO8601ToJava(const ISO8601Date: SOString; var JavaDateTime: Int64): Boolean; - function ISO8601ToDelphi(const ISO8601Date: SOString; var DelphiDateTime: TDateTime): Boolean; + function ISO8601ToJava(const ISO8601Date: string; out JavaDateTime: Int64): Boolean; + function ISO8601ToDelphi(const ISO8601Date: string; out DelphiDateTime: TDateTime): Boolean; { TZ Info } class function GetCurrentTimeZone: SOString; @@ -249,6 +267,17 @@ constructor TSuperTimeZone.Create(const TimeZoneName: SOString); begin inherited Create; FName := TimeZoneName; + {$IFDEF MSWINDOWS} + FDaylightDisabled := TExpirable.Box(GetDaylightDisabled); + FCacheTZI := TDictionary>.Create; + {$ENDIF} +end; + +destructor TSuperTimeZone.Destroy; +begin + {$IFDEF MSWINDOWS} + FCacheTZI.Free; + {$ENDIF} end; function TSuperTimeZone.LocalToUTC(const DelphiDateTime: TDateTime): TDateTime; @@ -317,7 +346,7 @@ function TSuperTimeZone.JavaToDelphi(const JavaDateTime: Int64): TDateTime; end; function TSuperTimeZone.DelphiToISO8601( - DelphiDateTime: TDateTime): SOString; + DelphiDateTime: TDateTime): string; const ISO_Fmt = '%.4d-%.2d-%.2dT%.2d:%.2d:%.2d.%d'; TZ_Fmt = '%s%.2d:%.2d'; @@ -350,13 +379,12 @@ function TSuperTimeZone.DelphiToISO8601( Result := iso; end; -function TSuperTimeZone.JavaToISO8601(JavaDateTime: Int64): SOString; +function TSuperTimeZone.JavaToISO8601(JavaDateTime: Int64): string; begin Result := DelphiToISO8601(JavaToDelphi(JavaDateTime)); end; -function TSuperTimeZone.ISO8601ToDelphi(const ISO8601Date: SOString; - var DelphiDateTime: TDateTime): Boolean; +function TSuperTimeZone.ISO8601ToDelphi(const ISO8601Date: string; out DelphiDateTime: TDateTime): Boolean; var JavaDateTime: Int64; begin @@ -365,8 +393,8 @@ function TSuperTimeZone.ISO8601ToDelphi(const ISO8601Date: SOString; DelphiDateTime := JavaToDelphi(JavaDateTime); end; -function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: SOString; - var JavaDateTime: Int64): Boolean; +function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: string; + out JavaDateTime: Int64): Boolean; {$IFDEF MSWINDOWS} var st: TSystemTime; @@ -384,7 +412,7 @@ function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: SOString; if ParseISO8601Date(ISO8601Date, st, dayofyear, week, bias, havetz, havedate) then begin if (not havetz) and GetTimeZoneInformation(st.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, st, utc) then - bias := Trunc((SystemTimeToDateTime(st) - SystemTimeToDateTime(utc)) * MinsPerDay); + bias := Round((SystemTimeToDateTime(utc) - SystemTimeToDateTime(st)) * MinsPerDay); JavaDateTime := st.wMilliseconds + st.wSecond * 1000 + (st.wMinute + bias) * 60000 + st.wHour * 3600000; if havedate then begin @@ -454,6 +482,11 @@ function TSuperTimeZone.GetDaylightDisabled: Boolean; var KeyName: SOString; begin + {$IFDEF MSWINDOWS} + if FDaylightDisabled.IsValid then + Exit(FDaylightDisabled.Data); + {$ENDIF} + Result := False; KeyName := TZ_KEY + Name; with TRegistry.Create do @@ -465,6 +498,9 @@ function TSuperTimeZone.GetDaylightDisabled: Boolean; Result := ReadBool('IsObsolete'); CloseKey; end; + {$IFDEF MSWINDOWS} + FDaylightDisabled := TExpirable.Box(Result); + {$ENDIF} finally Free; end; @@ -486,7 +522,14 @@ function TSuperTimeZone.GetTimeZoneInformation(Year: Word; KeyName: SOString; FirstYear, LastYear, ChangeYear: Word; Retry: Boolean; + CachedData: TExpirable; begin + if FCacheTZI.TryGetValue(Year, CachedData) and CachedData.IsValid then + begin + TZI := CachedData.Data; + Exit(True); + end; + FillChar(TZI, SizeOf(TZI), 0); KeyName := TZ_KEY + Name; with TRegistry.Create do @@ -546,6 +589,8 @@ function TSuperTimeZone.GetTimeZoneInformation(Year: Word; TZI.DaylightBias := RegTZI.DaylightBias; Result := True; + + FCacheTZI.AddOrSetValue(Year, TExpirable.Box(TZI)); finally Free; end; @@ -607,6 +652,7 @@ function TSuperTimeZone.CompTimeZoneID(const pTZinfo: PTimeZoneInformation; llTime: Int64; SysTime: TSystemTime; ftTemp: TFileTime; + year: Word; begin llTime := 0; if (not GetDaylightDisabled) and (pTZinfo^.DaylightDate.wMonth <> 0) then @@ -629,38 +675,52 @@ function TSuperTimeZone.CompTimeZoneID(const pTZinfo: PTimeZoneInformation; if (not IsLocal) then begin llTime := PInt64(lpFileTime)^; - Dec(llTime, Int64(pTZinfo^.Bias + pTZinfo^.DaylightBias) * 600000000); + Dec(llTime, Int64(pTZinfo^.Bias) * 600000000); PInt64(@ftTemp)^ := llTime; lpFileTime := @ftTemp; end; FileTimeToSystemTime(lpFileTime^, SysTime); + year := SysTime.wYear; - (* check for daylight savings *) - Ret := DayLightCompareDate(@SysTime, @pTZinfo^.StandardDate); - if (Ret = -2) then + if (not IsLocal) then begin - Result := TIME_ZONE_ID_INVALID; - Exit; + Dec(llTime, Int64(pTZinfo^.DaylightBias) * 600000000); + PInt64(@ftTemp)^ := llTime; + FileTimeToSystemTime(lpFileTime^, SysTime); end; - BeforeStandardDate := Ret < 0; + (* check for daylight savings *) + if (year = SysTime.wYear) then + begin + ret := DayLightCompareDate(@SysTime, @pTZinfo.StandardDate); + if (ret = -2) then + begin + Result := TIME_ZONE_ID_INVALID; + Exit; + end; + beforeStandardDate := ret < 0; + end else + beforeStandardDate := SysTime.wYear < year; - if (not IsLocal) then + if (not islocal) then begin - Dec(llTime, Int64(pTZinfo^.StandardBias - pTZinfo^.DaylightBias) * 600000000); + Dec(llTime, (pTZinfo.StandardBias - pTZinfo.DaylightBias) * 600000000); PInt64(@ftTemp)^ := llTime; FileTimeToSystemTime(lpFileTime^, SysTime); end; - Ret := DayLightCompareDate(@SysTime, @pTZinfo^.DaylightDate); - if (Ret = -2) then + if (year = SysTime.wYear) then begin - Result := TIME_ZONE_ID_INVALID; - Exit; - end; - - AfterDaylightDate := Ret >= 0; + ret := DayLightCompareDate(@SysTime, @pTZinfo.DaylightDate); + if (ret = -2) then + begin + Result := TIME_ZONE_ID_INVALID; + Exit; + end; + afterDaylightDate := ret >= 0; + end else + afterDaylightDate := SysTime.wYear > year; Result := TIME_ZONE_ID_STANDARD; if pTZinfo^.DaylightDate.wMonth < pTZinfo^.StandardDate.wMonth then @@ -1439,4 +1499,19 @@ TSystemTimeInt = record Result := False; end; +{$IFDEF MSWINDOWS} +{ TSuperTimeZone.TExpirable } + +class function TSuperTimeZone.TExpirable.Box(Data: T): TExpirable; +begin + Result.Data := Data; + Result.Timestamp := Now; +end; + +function TSuperTimeZone.TExpirable.IsValid: Boolean; +begin + Result := Trunc(Self.Timestamp) = Trunc(Now); +end; +{$ENDIF} + end. From 104f89ac305ee0db7336ee6ab49fc4c66b9765f4 Mon Sep 17 00:00:00 2001 From: DmBel Date: Mon, 1 Mar 2021 18:02:35 +0300 Subject: [PATCH 11/13] =?UTF-8?q?=D1=82=D0=B5=D0=BA=D1=83=D1=87=D0=BA?= =?UTF-8?q?=D0=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 1 + supertimezone.pas | 58 +++++++++++++++++++++++------------------------ 2 files changed, 29 insertions(+), 30 deletions(-) diff --git a/.gitignore b/.gitignore index 9b20757..4a8e9ef 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,3 @@ *.dcu +*.bak __history \ No newline at end of file diff --git a/supertimezone.pas b/supertimezone.pas index 088870d..db3e542 100644 --- a/supertimezone.pas +++ b/supertimezone.pas @@ -7,7 +7,7 @@ interface uses - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} Windows, {$ENDIF} Registry, SysUtils, Math, Generics.Collections, @@ -24,7 +24,7 @@ TSuperTimeZone = class TZ_KEY = '\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Time Zones\'; TZ_KEYNAME = 'TimeZoneKeyName'; private type - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} TExpirable = record Timestamp: TDateTime; Data: T; @@ -34,14 +34,14 @@ TExpirable = record {$ENDIF} private FName: SOString; - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} FDaylightDisabled: TExpirable; FCacheTZI: TDictionary>; {$ENDIF} function GetName: SOString; - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} { Windows Internals } function TzSpecificLocalTimeToSystemTime( const lpTimeZoneInformation: PTimeZoneInformation; @@ -91,7 +91,7 @@ TExpirable = record { TZ Info } class function GetCurrentTimeZone: SOString; - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} function GetTimeZoneInformation(Year: Word; var TZI: TTimeZoneInformation): Boolean; {$ENDIF} function GetDaylightDisabled: Boolean; @@ -102,7 +102,7 @@ TExpirable = record class property Zone[const TimeZoneName: string]: TSuperTimeZone read GetSuperTimeZoneInstance; end; -{$IFDEF MSWINDOWS} +{$IFNDEF FPC} {$WARN SYMBOL_PLATFORM OFF} (* NOT DST Aware *) @@ -119,7 +119,6 @@ function _TzSpecificLocalTimeToSystemTime( (* EXtended version - DST Aware *) -{$IFNDEF FPC} { Windows 7+ } function _TzSpecificLocalTimeToSystemTimeEx( const lpTimeZoneInformation: PDynamicTimeZoneInformation; @@ -129,7 +128,6 @@ function _TzSpecificLocalTimeToSystemTimeEx( function _SystemTimeToTzSpecificLocalTimeEx( const lpTimeZoneInformation: PDynamicTimeZoneInformation; const lpUniversalTime: PSystemTime; var lpLocalTime: TSystemTime): BOOL; stdcall; external kernel32 name 'SystemTimeToTzSpecificLocalTimeEx'{$IFNDEF FPC} delayed{$ENDIF}; -{$ENDIF} { Convert Local <=> UTC for specific time-zones using the Windows API only. NOT Guaranteed to work } @@ -267,7 +265,7 @@ constructor TSuperTimeZone.Create(const TimeZoneName: SOString); begin inherited Create; FName := TimeZoneName; - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} FDaylightDisabled := TExpirable.Box(GetDaylightDisabled); FCacheTZI := TDictionary>.Create; {$ENDIF} @@ -275,19 +273,19 @@ constructor TSuperTimeZone.Create(const TimeZoneName: SOString); destructor TSuperTimeZone.Destroy; begin - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} FCacheTZI.Free; {$ENDIF} end; function TSuperTimeZone.LocalToUTC(const DelphiDateTime: TDateTime): TDateTime; -{$IFDEF MSWINDOWS} +{$IFNDEF FPC} var local, utc: TSystemTime; tzi: TTimeZoneInformation; - {$ENDIF} +{$ENDIF} begin - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} DateTimeToSystemTime(DelphiDateTime, local); if GetTimeZoneInformation(local.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, local, utc) then Result := SystemTimeToDateTime(utc) @@ -297,13 +295,13 @@ function TSuperTimeZone.LocalToUTC(const DelphiDateTime: TDateTime): TDateTime; end; function TSuperTimeZone.UTCToLocal(const DelphiDateTime: TDateTime): TDateTime; -{$IFDEF MSWINDOWS} +{$IFNDEF FPC} var utc, local: TSystemTime; tzi: TTimeZoneInformation; - {$ENDIF} +{$ENDIF} begin - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} DateTimeToSystemTime(DelphiDateTime, utc); if GetTimeZoneInformation(utc.wYear, tzi) and SystemTimeToTzSpecificLocalTime(@tzi, utc, local) then Result := SystemTimeToDateTime(local) @@ -313,13 +311,13 @@ function TSuperTimeZone.UTCToLocal(const DelphiDateTime: TDateTime): TDateTime; end; function TSuperTimeZone.DelphiToJava(const DelphiDateTime: TDateTime): Int64; -{$IFDEF MSWINDOWS} +{$IFNDEF FPC} var local, utc, st: TSystemTime; tzi: TTimeZoneInformation; - {$ENDIF} +{$ENDIF} begin -{$IFDEF MSWINDOWS} + {$IFNDEF FPC} DateTimeToSystemTime(DelphiDateTime, local); if GetTimeZoneInformation(local.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, local, utc) then st := utc @@ -330,13 +328,13 @@ function TSuperTimeZone.DelphiToJava(const DelphiDateTime: TDateTime): Int64; end; function TSuperTimeZone.JavaToDelphi(const JavaDateTime: Int64): TDateTime; -{$IFDEF MSWINDOWS} +{$IFNDEF FPC} var utc, local: TSystemTime; tzi: TTimeZoneInformation; - {$ENDIF} +{$ENDIF} begin -{$IFDEF MSWINDOWS} + {$IFNDEF FPC} DateTimeToSystemTime(25569 + (JavaDateTime / 86400000), utc); if GetTimeZoneInformation(utc.wYear, tzi) and SystemTimeToTzSpecificLocalTime(@tzi, utc, local) then Result := SystemTimeToDateTime(local) @@ -352,14 +350,14 @@ function TSuperTimeZone.DelphiToISO8601( TZ_Fmt = '%s%.2d:%.2d'; var local, utc: TSystemTime; - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} tzi: TTimeZoneInformation; {$ENDIF} bias: TDateTime; h, m, d: Word; iso: SOString; begin -{$IFDEF MSWINDOWS} + {$IFNDEF FPC} DateTimeToSystemTime(DelphiDateTime, local); iso := Format(ISO_Fmt, [ local.wYear, local.wMonth, local.wDay, @@ -395,7 +393,7 @@ function TSuperTimeZone.ISO8601ToDelphi(const ISO8601Date: string; out DelphiDat function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: string; out JavaDateTime: Int64): Boolean; -{$IFDEF MSWINDOWS} +{$IFNDEF FPC} var st: TSystemTime; dayofyear: Integer; @@ -408,7 +406,7 @@ function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: string; DayTable: PDayTable; {$ENDIF} begin -{$IFDEF MSWINDOWS} + {$IFNDEF FPC} if ParseISO8601Date(ISO8601Date, st, dayofyear, week, bias, havetz, havedate) then begin if (not havetz) and GetTimeZoneInformation(st.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, st, utc) then @@ -482,7 +480,7 @@ function TSuperTimeZone.GetDaylightDisabled: Boolean; var KeyName: SOString; begin - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} if FDaylightDisabled.IsValid then Exit(FDaylightDisabled.Data); {$ENDIF} @@ -498,7 +496,7 @@ function TSuperTimeZone.GetDaylightDisabled: Boolean; Result := ReadBool('IsObsolete'); CloseKey; end; - {$IFDEF MSWINDOWS} + {$IFNDEF FPC} FDaylightDisabled := TExpirable.Box(Result); {$ENDIF} finally @@ -506,7 +504,7 @@ function TSuperTimeZone.GetDaylightDisabled: Boolean; end; end; -{$IFDEF MSWINDOWS} +{$IFNDEF FPC} function TSuperTimeZone.GetTimeZoneInformation(Year: Word; var TZI: TTimeZoneInformation): Boolean; type @@ -1499,7 +1497,7 @@ TSystemTimeInt = record Result := False; end; -{$IFDEF MSWINDOWS} +{$IFNDEF FPC} { TSuperTimeZone.TExpirable } class function TSuperTimeZone.TExpirable.Box(Data: T): TExpirable; From be7911a17f0a5f65da2c02014ac6d8a32f8bcc8b Mon Sep 17 00:00:00 2001 From: DmBel Date: Fri, 14 May 2021 14:43:33 +0300 Subject: [PATCH 12/13] Fix 64bit --- superobject.pas | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/superobject.pas b/superobject.pas index 82700b2..27b0768 100644 --- a/superobject.pas +++ b/superobject.pas @@ -6390,7 +6390,7 @@ function TSuperRttiContext.FromJson(TypeInfo: PTypeInfo; const obj: ISuperObject procedure FromDynArray; var - i: Integer; + i: NativeInt; p: Pointer; pb: PByte; val: TValue; From 5c4adec715a3c5b129555b30bb0a4ada6002b2bf Mon Sep 17 00:00:00 2001 From: DmBel Date: Sat, 9 Oct 2021 12:12:44 +0300 Subject: [PATCH 13/13] added Linux Delphi 10.4.1 compatibility. the FPC compatibility partially removed --- superobject.pas | 41 +++++++++-------- supertimezone.pas | 115 +++++++++++++++++++++++----------------------- supertypes.pas | 2 +- 3 files changed, 79 insertions(+), 79 deletions(-) diff --git a/superobject.pas b/superobject.pas index 27b0768..3ef2f9f 100644 --- a/superobject.pas +++ b/superobject.pas @@ -119,7 +119,8 @@ interface uses - Classes, supertypes, Variants + Classes, supertypes, Variants, + System.SyncObjs {$IFDEF HAVE_RTTI} ,Generics.Collections, RTTI, TypInfo {$ENDIF} @@ -130,7 +131,7 @@ interface SUPER_TOKENER_MAX_DEPTH = 32; SUPER_AVL_MAX_DEPTH = sizeof(longint) * 8; - SUPER_AVL_MASK_HIGH_BIT = not ((not longword(0)) shr 1); + SUPER_AVL_MASK_HIGH_BIT = not ((not FixedUInt(0)) shr 1); type // forward declarations @@ -364,16 +365,17 @@ TSuperWriterFake = class(TSuperWriter) property size: integer read FSize; end; + TSocket = longint; TSuperWriterSock = class(TSuperWriter) private - FSocket: longint; + FSocket: TSocket; FSize: Integer; public function Append(buf: PSOChar; Size: Integer): Integer; override; function Append(buf: PSOChar): Integer; override; procedure Reset; override; - constructor Create(ASocket: longint); reintroduce; virtual; - property Socket: longint read FSocket; + constructor Create(ASocket: TSocket); reintroduce; virtual; + property Socket: TSocket read FSocket; property Size: Integer read FSize; end; @@ -548,7 +550,7 @@ TSuperEnumerator = class function Write(writer: TSuperWriter; indent: boolean; escape: boolean; level: integer): Integer; function SaveTo(stream: TStream; indent: boolean = false; escape: boolean = true): integer; overload; function SaveTo(const FileName: string; indent: boolean = false; escape: boolean = true): integer; overload; - function SaveTo(socket: longint; indent: boolean = false; escape: boolean = true): integer; overload; + function SaveTo(socket: TSocket; indent: boolean = false; escape: boolean = true): integer; overload; function CalcSize(indent: boolean = false; escape: boolean = true): integer; // convert @@ -639,8 +641,8 @@ TSuperObject = class(TObject, ISuperObject) {$ELSE} function QueryInterface(const IID: TGUID; out Obj): HResult; virtual; stdcall; {$ENDIF} - function _AddRef: Integer; virtual; {$IFDEF UNIX}cdecl{$ELSE}stdcall{$ENDIF}; - function _Release: Integer; virtual; {$IFDEF UNIX}cdecl{$ELSE}stdcall{$ENDIF}; + function _AddRef: Integer; virtual; stdcall; + function _Release: Integer; virtual; stdcall; function GetO(const path: string): ISuperObject; procedure PutO(const path: string; const Value: ISuperObject); @@ -673,7 +675,7 @@ TSuperObject = class(TObject, ISuperObject) // Writers function SaveTo(stream: TStream; indent: boolean = false; escape: boolean = true): integer; overload; function SaveTo(const FileName: string; indent: boolean = false; escape: boolean = true): integer; overload; - function SaveTo(socket: longint; indent: boolean = false; escape: boolean = true): integer; overload; + function SaveTo(socket: TSocket; indent, escape: boolean): integer; overload; function CalcSize(indent: boolean = false; escape: boolean = true): integer; function AsJSon(indent: boolean = false; escape: boolean = true): string; @@ -885,8 +887,7 @@ implementation Windows, {$ENDIF} superdate -{$IFDEF FPC} - ,sockets +{$IFDEF LINUX} {$ELSE} ,WinSock {$ENDIF} @@ -2208,7 +2209,7 @@ function TSuperObject.GetEnumerator: TSuperEnumerator; procedure TSuperObject.AfterConstruction; begin - InterlockedDecrement(FRefCount); + TInterlocked.Decrement(FRefCount); end; procedure TSuperObject.BeforeDestruction; @@ -3388,7 +3389,7 @@ function TSuperObject.CalcSize(indent, escape: boolean): integer; pb.Free; end; -function TSuperObject.SaveTo(socket: Integer; indent, escape: boolean): integer; +function TSuperObject.SaveTo(socket: TSocket; indent, escape: boolean): integer; var pb: TSuperWriterSock; begin @@ -4311,12 +4312,12 @@ function TSuperObject.Validate(const rules: ISuperObject; const defs: ISuperObje function TSuperObject._AddRef: Integer; begin - Result := InterlockedIncrement(FRefCount); + Result := TInterlocked.Increment(FRefCount); end; function TSuperObject._Release: Integer; begin - Result := InterlockedDecrement(FRefCount); + Result := TInterlocked.Decrement(FRefCount); if Result = 0 then Destroy; end; @@ -4882,8 +4883,8 @@ function TSuperWriterSock.Append(buf: PSOChar; Size: Integer): Integer; i: Integer; begin if Size = 1 then -{$IFDEF FPC} - Result := fpsend(FSocket, buf, size, 0) else +{$IFDEF LINUX} +// Result := fpsend(FSocket, buf, size, 0) else {$ELSE} Result := send(FSocket, buf^, size, 0) else {$ENDIF} @@ -4894,8 +4895,8 @@ function TSuperWriterSock.Append(buf: PSOChar; Size: Integer): Integer; try for i := 0 to Size - 1 do pBuffer[i] := AnsiChar(buf[i]); -{$IFDEF FPC} - Result := fpsend(FSocket, pBuffer, size, 0); +{$IFDEF LINUX} +// Result := fpsend(FSocket, pBuffer, size, 0); {$ELSE} Result := send(FSocket, pBuffer^, size, 0); {$ENDIF} @@ -4912,7 +4913,7 @@ function TSuperWriterSock.Append(buf: PSOChar): Integer; Result := Append(buf, StrLen(buf)); end; -constructor TSuperWriterSock.Create(ASocket: Integer); +constructor TSuperWriterSock.Create(ASocket: TSocket); begin inherited Create; FSocket := ASocket; diff --git a/supertimezone.pas b/supertimezone.pas index db3e542..62962fb 100644 --- a/supertimezone.pas +++ b/supertimezone.pas @@ -7,16 +7,35 @@ interface uses - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} Windows, + Registry, + {$ELSE} + System.Classes, {$ENDIF} - Registry, SysUtils, Math, Generics.Collections, + System.SyncObjs, + SysUtils, Math, Generics.Collections, supertypes; type { TSuperTimeZone } + TSuperSystemTime = record + Year: Word; + Month: Word; + DayOfWeek: Word; + Day: Word; + Hour: Word; + Minute: Word; + Second: Word; + Millisecond: Word; + end; + + {$IFDEF LINUX} + TSystemTime = TSuperSystemTime; + {$ENDIF} + TSuperTimeZone = class private const @@ -24,25 +43,23 @@ TSuperTimeZone = class TZ_KEY = '\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Time Zones\'; TZ_KEYNAME = 'TimeZoneKeyName'; private type - {$IFNDEF FPC} TExpirable = record Timestamp: TDateTime; Data: T; function IsValid: Boolean; class function Box(Data: T): TExpirable; static; end; - {$ENDIF} private FName: SOString; - {$IFNDEF FPC} FDaylightDisabled: TExpirable; + {$IFDEF MSWINDOWS} FCacheTZI: TDictionary>; {$ENDIF} function GetName: SOString; - {$IFNDEF FPC} { Windows Internals } + {$IFDEF MSWINDOWS} function TzSpecificLocalTimeToSystemTime( const lpTimeZoneInformation: PTimeZoneInformation; var lpLocalTime, lpUniversalTime: TSystemTime): BOOL; @@ -55,7 +72,7 @@ TExpirable = record lpFileTime: PFileTime; islocal: Boolean; pBias: PLongint): Boolean; function CompTimeZoneID(const pTZinfo: PTimeZoneInformation; - lpFileTime: PFileTime; IsLocal: Boolean): LongWord; + lpFileTime: PFileTime; IsLocal: Boolean): FixedUInt; function DayLightCompareDate(const date: PSystemTime; const compareDate: PSystemTime): Integer; @@ -63,7 +80,7 @@ TExpirable = record private class constructor Init; class destructor Finish; - class var FCacheCS: TRTLCriticalSection; + class var FCacheCS: TCriticalSection; class var FCache: TObjectDictionary; class function GetSuperTimeZoneInstance(const Name: string): TSuperTimeZone; static; class function GetLocalSuperTimeZoneInstance: TSuperTimeZone; static; @@ -91,7 +108,7 @@ TExpirable = record { TZ Info } class function GetCurrentTimeZone: SOString; - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} function GetTimeZoneInformation(Year: Word; var TZI: TTimeZoneInformation): Boolean; {$ENDIF} function GetDaylightDisabled: Boolean; @@ -102,7 +119,7 @@ TExpirable = record class property Zone[const TimeZoneName: string]: TSuperTimeZone read GetSuperTimeZoneInstance; end; -{$IFNDEF FPC} +{$IFDEF MSWINDOWS} {$WARN SYMBOL_PLATFORM OFF} (* NOT DST Aware *) @@ -227,24 +244,20 @@ function _ConvertUTCDateTimeToLocal(const TimeZoneName: SOString; class constructor TSuperTimeZone.Init; begin - {$IFNDEF FPC} - InitializeCriticalSection(FCacheCS); - {$ENDIF} + FCacheCS := TCriticalSection.Create; FCache := TObjectDictionary.Create([doOwnsValues]); end; class destructor TSuperTimeZone.Finish; begin FCache.Free; - {$IFNDEF FPC} - DeleteCriticalSection(FCacheCS); - {$ENDIF} + FCacheCS.Free; end; class function TSuperTimeZone.GetSuperTimeZoneInstance( const Name: string): TSuperTimeZone; begin - EnterCriticalSection(FCacheCS); + FCacheCS.Enter; try if not FCache.TryGetValue(Name, Result) then begin @@ -252,7 +265,7 @@ class function TSuperTimeZone.GetSuperTimeZoneInstance( FCache.Add(Name, Result); end; finally - LeaveCriticalSection(FCacheCS); + FCacheCS.Leave; end; end; @@ -265,27 +278,27 @@ constructor TSuperTimeZone.Create(const TimeZoneName: SOString); begin inherited Create; FName := TimeZoneName; - {$IFNDEF FPC} FDaylightDisabled := TExpirable.Box(GetDaylightDisabled); + {$IFDEF MSWINDOWS} FCacheTZI := TDictionary>.Create; {$ENDIF} end; destructor TSuperTimeZone.Destroy; begin - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} FCacheTZI.Free; {$ENDIF} end; function TSuperTimeZone.LocalToUTC(const DelphiDateTime: TDateTime): TDateTime; -{$IFNDEF FPC} +{$IFDEF MSWINDOWS} var local, utc: TSystemTime; tzi: TTimeZoneInformation; {$ENDIF} begin - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} DateTimeToSystemTime(DelphiDateTime, local); if GetTimeZoneInformation(local.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, local, utc) then Result := SystemTimeToDateTime(utc) @@ -295,13 +308,13 @@ function TSuperTimeZone.LocalToUTC(const DelphiDateTime: TDateTime): TDateTime; end; function TSuperTimeZone.UTCToLocal(const DelphiDateTime: TDateTime): TDateTime; -{$IFNDEF FPC} +{$IFDEF MSWINDOWS} var utc, local: TSystemTime; tzi: TTimeZoneInformation; {$ENDIF} begin - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} DateTimeToSystemTime(DelphiDateTime, utc); if GetTimeZoneInformation(utc.wYear, tzi) and SystemTimeToTzSpecificLocalTime(@tzi, utc, local) then Result := SystemTimeToDateTime(local) @@ -311,13 +324,13 @@ function TSuperTimeZone.UTCToLocal(const DelphiDateTime: TDateTime): TDateTime; end; function TSuperTimeZone.DelphiToJava(const DelphiDateTime: TDateTime): Int64; -{$IFNDEF FPC} +{$IFDEF MSWINDOWS} var local, utc, st: TSystemTime; tzi: TTimeZoneInformation; {$ENDIF} begin - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} DateTimeToSystemTime(DelphiDateTime, local); if GetTimeZoneInformation(local.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, local, utc) then st := utc @@ -328,13 +341,13 @@ function TSuperTimeZone.DelphiToJava(const DelphiDateTime: TDateTime): Int64; end; function TSuperTimeZone.JavaToDelphi(const JavaDateTime: Int64): TDateTime; -{$IFNDEF FPC} +{$IFDEF MSWINDOWS} var utc, local: TSystemTime; tzi: TTimeZoneInformation; {$ENDIF} begin - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} DateTimeToSystemTime(25569 + (JavaDateTime / 86400000), utc); if GetTimeZoneInformation(utc.wYear, tzi) and SystemTimeToTzSpecificLocalTime(@tzi, utc, local) then Result := SystemTimeToDateTime(local) @@ -349,15 +362,15 @@ function TSuperTimeZone.DelphiToISO8601( ISO_Fmt = '%.4d-%.2d-%.2dT%.2d:%.2d:%.2d.%d'; TZ_Fmt = '%s%.2d:%.2d'; var + {$IFDEF MSWINDOWS} local, utc: TSystemTime; - {$IFNDEF FPC} tzi: TTimeZoneInformation; - {$ENDIF} bias: TDateTime; h, m, d: Word; + {$ENDIF} iso: SOString; begin - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} DateTimeToSystemTime(DelphiDateTime, local); iso := Format(ISO_Fmt, [ local.wYear, local.wMonth, local.wDay, @@ -393,7 +406,7 @@ function TSuperTimeZone.ISO8601ToDelphi(const ISO8601Date: string; out DelphiDat function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: string; out JavaDateTime: Int64): Boolean; -{$IFNDEF FPC} +{$IFDEF MSWINDOWS} var st: TSystemTime; dayofyear: Integer; @@ -404,9 +417,9 @@ function TSuperTimeZone.ISO8601ToJava(const ISO8601Date: string; utc: TSystemTime; m: Word; DayTable: PDayTable; - {$ENDIF} +{$ENDIF} begin - {$IFNDEF FPC} + {$IFDEF MSWINDOWS} if ParseISO8601Date(ISO8601Date, st, dayofyear, week, bias, havetz, havedate) then begin if (not havetz) and GetTimeZoneInformation(st.wYear, tzi) and TzSpecificLocalTimeToSystemTime(@tzi, st, utc) then @@ -447,6 +460,7 @@ function TSuperTimeZone.GetName: SOString; class function TSuperTimeZone.GetCurrentTimeZone: SOString; begin + {$IFDEF MSWINDOWS} with TRegistry.Create do try RootKey := HKEY_LOCAL_MACHINE; @@ -474,19 +488,20 @@ class function TSuperTimeZone.GetCurrentTimeZone: SOString; CloseKey; Free; end; + {$ELSE} + Result := ''; + {$ENDIF} end; function TSuperTimeZone.GetDaylightDisabled: Boolean; var KeyName: SOString; begin - {$IFNDEF FPC} if FDaylightDisabled.IsValid then Exit(FDaylightDisabled.Data); - {$ENDIF} - Result := False; KeyName := TZ_KEY + Name; + {$IFDEF MSWINDOWS} with TRegistry.Create do try RootKey := HKEY_LOCAL_MACHINE; @@ -496,15 +511,14 @@ function TSuperTimeZone.GetDaylightDisabled: Boolean; Result := ReadBool('IsObsolete'); CloseKey; end; - {$IFNDEF FPC} FDaylightDisabled := TExpirable.Box(Result); - {$ENDIF} finally Free; end; + {$ENDIF} end; -{$IFNDEF FPC} +{$IFDEF MSWINDOWS} function TSuperTimeZone.GetTimeZoneInformation(Year: Word; var TZI: TTimeZoneInformation): Boolean; type @@ -624,7 +638,7 @@ function TSuperTimeZone.GetTimezoneBias(const pTZinfo: PTimeZoneInformation; lpFileTime: PFileTime; islocal: Boolean; pBias: PLongint): Boolean; var bias: LongInt; - tzid: LongWord; + tzid: FixedUInt; begin bias := pTZinfo^.Bias; tzid := CompTimeZoneID(pTZinfo, lpFileTime, islocal); @@ -643,7 +657,7 @@ function TSuperTimeZone.GetTimezoneBias(const pTZinfo: PTimeZoneInformation; end; function TSuperTimeZone.CompTimeZoneID(const pTZinfo: PTimeZoneInformation; - lpFileTime: PFileTime; IsLocal: Boolean): LongWord; + lpFileTime: PFileTime; IsLocal: Boolean): FixedUInt; var Ret: Integer; BeforeStandardDate, AfterDaylightDate: Boolean; @@ -833,28 +847,13 @@ class function TSuperTimeZone.ParseISO8601Date(const ISO8601Date: SOString; TState = (stStart, stYear, stMonth, stWeek, stWeekDay, stDay, stDayOfYear, stHour, stMin, stSec, stMs, stUTC, stGMTH, stGMTM, stGMTend, stEnd); TPerhaps = (yes, no, perhaps); -type - TSystemTimeInt = record - Year: Word; - Month: Word; - DayOfWeek: Word; - Day: Word; - Hour: Word; - Minute: Word; - Second: Word; - Millisecond: Word; - end; var p: PSOChar; sep: TPerhaps; state: TState; pos, v: Word; inctz: Boolean; - {$IFDEF MSWINDOWS} - st1: TSystemTimeInt absolute st; - {$ELSE MSWINDOWS} - st1: TSystemTime absolute st; - {$ENDIF MSWINDOWS} + st1: TSuperSystemTime absolute st; label error; begin diff --git a/supertypes.pas b/supertypes.pas index dbb9a03..9c54282 100644 --- a/supertypes.pas +++ b/supertypes.pas @@ -13,7 +13,7 @@ interface PtrUInt = UInt64; {$ELSE} PtrInt = longint; - PtrUInt = Longword; + PtrUInt = FixedUInt; {$ENDIF} {$ENDIF} SuperInt = Int64;