2022-05-31 07:20:10 +00:00
|
|
|
unit sys_time;
|
|
|
|
|
|
|
|
{$mode ObjFPC}{$H+}
|
|
|
|
|
|
|
|
interface
|
|
|
|
|
|
|
|
uses
|
|
|
|
windows,
|
|
|
|
ntapi,
|
|
|
|
sys_types,
|
|
|
|
sys_kernel;
|
|
|
|
|
|
|
|
function _usec2msec(usec:QWORD):QWORD; //Microsecond to Milisecond
|
2022-06-04 15:56:00 +00:00
|
|
|
function _msec2usec(msec:QWORD):QWORD; //Milisecond to Microsecond
|
2022-05-31 07:20:10 +00:00
|
|
|
function _usec2nsec(usec:QWORD):QWORD; //Microsecond to Nanosecond
|
2022-06-04 15:56:00 +00:00
|
|
|
function _nsec2usec(nsec:QWORD):QWORD; //Nanosecond to Microsecond
|
|
|
|
function _msec2nsec(msec:QWORD):QWORD; //Milisecond to Nanosecond
|
|
|
|
function _nsec2msec(nsec:QWORD):QWORD; //Nanosecond to Milisecond
|
2022-05-31 07:20:10 +00:00
|
|
|
|
|
|
|
function _time_in_ms_from_timespec(const ts:timespec):QWORD; inline; //Milisecond
|
|
|
|
function _time_in_ns_from_timespec(const ts:timespec):QWORD; inline; //Nanosecond
|
|
|
|
function dwMilliSecs(ms:QWORD):DWORD;
|
|
|
|
|
|
|
|
function filetime_to_hnsec(ft:TFILETIME):QWORD; inline;
|
|
|
|
function filetime_to_timespec(ft:TFILETIME):timespec;
|
|
|
|
|
|
|
|
procedure SwQueryPerformanceCounter(var pc,pf:QWORD);
|
|
|
|
procedure SwSaveTime(var pc:QWORD);
|
|
|
|
function SwTimePassedUnits(ot:QWORD):QWORD;
|
|
|
|
function SwGetTimeUnits:Int64;
|
|
|
|
|
|
|
|
procedure SwGetSystemTimeAsFileTime(var lpSystemTimeAsFileTime:TFILETIME);
|
|
|
|
procedure Swgettimezone(z:Ptimezone);
|
|
|
|
function Swgetntptimeofday(tp:Ptimespec;z:Ptimezone):Integer;
|
|
|
|
|
|
|
|
Const
|
|
|
|
FILETIME_1970 =116444736000000000;
|
|
|
|
HECTONANOSEC_PER_SEC =10000000;
|
|
|
|
DELTA_EPOCH_IN_100NS =116444736000000000;
|
|
|
|
POW10_7 =10000000;
|
|
|
|
POW10_9 =1000000000;
|
|
|
|
//POW10_11 =100000000000;
|
|
|
|
|
|
|
|
implementation
|
|
|
|
|
|
|
|
uses
|
|
|
|
sys_signal;
|
|
|
|
|
|
|
|
function _usec2msec(usec:QWORD):QWORD; //Microsecond to Milisecond
|
|
|
|
begin
|
|
|
|
Result:=(usec+999) div 1000;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function _msec2usec(msec:QWORD):QWORD; //Milisecond to Microsecond
|
|
|
|
begin
|
|
|
|
Result:=msec*1000;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function _usec2nsec(usec:QWORD):QWORD; //Microsecond to Nanosecond
|
|
|
|
begin
|
|
|
|
Result:=usec*1000;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function _nsec2usec(nsec:QWORD):QWORD; //Nanosecond to Microsecond
|
|
|
|
begin
|
|
|
|
Result:=(nsec+999) div 1000;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function _msec2nsec(msec:QWORD):QWORD; //Milisecond to Nanosecond
|
|
|
|
begin
|
|
|
|
Result:=msec*1000000;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function _nsec2msec(nsec:QWORD):QWORD; //Nanosecond to Milisecond
|
|
|
|
begin
|
|
|
|
Result:=(nsec+999999) div 1000000;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function _time_in_ms_from_timespec(const ts:timespec):QWORD; inline; //Milisecond
|
|
|
|
begin
|
|
|
|
Result:=QWORD(ts.tv_sec)*1000+QWORD(ts.tv_nsec+999999) div 1000000;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function _time_in_ns_from_timespec(const ts:timespec):QWORD; inline; //Nanosecond
|
|
|
|
begin
|
|
|
|
Result:=QWORD(ts.tv_sec)*POW10_9+QWORD(ts.tv_nsec);
|
|
|
|
end;
|
|
|
|
|
|
|
|
function dwMilliSecs(ms:QWORD):DWORD;
|
|
|
|
begin
|
|
|
|
if (ms>=$ffffffff) then
|
|
|
|
Result:=$ffffffff
|
|
|
|
else
|
|
|
|
Result:=DWORD(ms);
|
|
|
|
end;
|
|
|
|
|
|
|
|
function filetime_to_hnsec(ft:TFILETIME):QWORD; inline;
|
|
|
|
begin
|
|
|
|
Result:=QWORD(ft)-FILETIME_1970;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function filetime_to_timespec(ft:TFILETIME):timespec;
|
|
|
|
begin
|
|
|
|
QWORD(ft):=filetime_to_hnsec(ft);
|
|
|
|
Result.tv_sec :=QWORD(ft) div HECTONANOSEC_PER_SEC;
|
|
|
|
Result.tv_nsec:=(QWORD(ft) mod HECTONANOSEC_PER_SEC)*100;
|
|
|
|
end;
|
|
|
|
|
|
|
|
procedure SwQueryPerformanceCounter(var pc,pf:QWORD);
|
|
|
|
begin
|
|
|
|
pc:=0;
|
|
|
|
pf:=1;
|
|
|
|
_sig_lock;
|
|
|
|
NtQueryPerformanceCounter(@pc,@pf);
|
|
|
|
_sig_unlock;
|
|
|
|
end;
|
|
|
|
|
|
|
|
procedure SwSaveTime(var pc:QWORD);
|
|
|
|
var
|
|
|
|
pf:QWORD;
|
|
|
|
begin
|
|
|
|
pc:=0;
|
|
|
|
pf:=1;
|
|
|
|
_sig_lock;
|
|
|
|
NtQueryPerformanceCounter(@pc,@pf);
|
|
|
|
_sig_unlock;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function SwTimePassedUnits(ot:QWORD):QWORD;
|
|
|
|
var
|
|
|
|
pc:QWORD;
|
|
|
|
pf:QWORD;
|
|
|
|
sec:QWORD;
|
|
|
|
uec:QWORD;
|
|
|
|
begin
|
|
|
|
pc:=0;
|
|
|
|
pf:=1;
|
|
|
|
_sig_lock;
|
|
|
|
NtQueryPerformanceCounter(@pc,@pf);
|
|
|
|
_sig_unlock;
|
|
|
|
|
|
|
|
if (pc>ot) then
|
|
|
|
pc:=pc-ot
|
|
|
|
else
|
|
|
|
pc:=(ot+High(QWORD))+pc;
|
|
|
|
|
|
|
|
sec:=pc div pf;
|
|
|
|
uec:=((pc mod pf)*POW10_7{POW10_11}+(pf shr 1)) div pf;
|
|
|
|
Result:=sec*POW10_7{POW10_11}+uec;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function SwGetTimeUnits:Int64;
|
|
|
|
var
|
|
|
|
pc:QWORD;
|
|
|
|
pf:QWORD;
|
|
|
|
sec:QWORD;
|
|
|
|
uec:QWORD;
|
|
|
|
begin
|
|
|
|
pc:=0;
|
|
|
|
pf:=1;
|
|
|
|
_sig_lock;
|
|
|
|
NtQueryPerformanceCounter(@pc,@pf);
|
|
|
|
_sig_unlock;
|
|
|
|
sec:=pc div pf;
|
|
|
|
uec:=((pc mod pf)*POW10_7{POW10_11}+(pf shr 1)) div pf;
|
|
|
|
Result:=sec*POW10_7{POW10_11}+uec;
|
|
|
|
end;
|
|
|
|
|
|
|
|
type
|
|
|
|
TGetSystemTimeAsFileTime=procedure(var lpSystemTimeAsFileTime:TFILETIME); stdcall;
|
|
|
|
|
|
|
|
var
|
|
|
|
_GetSystemTimeAsFileTime:TGetSystemTimeAsFileTime;
|
|
|
|
|
|
|
|
procedure SwGetSystemTimeAsFileTime(var lpSystemTimeAsFileTime:TFILETIME);
|
|
|
|
var
|
|
|
|
h:HMODULE;
|
|
|
|
begin
|
|
|
|
if (_GetSystemTimeAsFileTime=nil) then
|
|
|
|
begin
|
|
|
|
h:=GetModuleHandle('kernel32.dll');
|
|
|
|
Pointer(_GetSystemTimeAsFileTime):=GetProcAddress(h,'GetSystemTimePreciseAsFileTime');
|
|
|
|
if (_GetSystemTimeAsFileTime=nil) then
|
|
|
|
begin
|
|
|
|
Pointer(_GetSystemTimeAsFileTime):=GetProcAddress(h,'GetSystemTimeAsFileTime');
|
|
|
|
end;
|
|
|
|
end;
|
|
|
|
_sig_lock;
|
|
|
|
_GetSystemTimeAsFileTime(lpSystemTimeAsFileTime);
|
|
|
|
_sig_unlock;
|
|
|
|
end;
|
|
|
|
|
|
|
|
procedure Swgettimezone(z:Ptimezone);
|
|
|
|
var
|
|
|
|
TZInfo:TTimeZoneInformation;
|
|
|
|
tzi:DWORD;
|
|
|
|
begin
|
|
|
|
if (z<>nil) then
|
|
|
|
begin
|
|
|
|
_sig_lock;
|
|
|
|
tzi:=GetTimeZoneInformation(@TZInfo);
|
|
|
|
_sig_unlock;
|
|
|
|
if (tzi<>TIME_ZONE_ID_INVALID) then
|
|
|
|
begin
|
|
|
|
z^.tz_minuteswest:=TZInfo.Bias;
|
|
|
|
if (tzi=TIME_ZONE_ID_DAYLIGHT) then
|
|
|
|
z^.tz_dsttime:=1
|
|
|
|
else
|
|
|
|
z^.tz_dsttime:=0;
|
|
|
|
end else
|
|
|
|
begin
|
|
|
|
z^.tz_minuteswest:=0;
|
|
|
|
z^.tz_dsttime :=0;
|
|
|
|
end;
|
|
|
|
end;
|
|
|
|
end;
|
|
|
|
|
|
|
|
function Swgetntptimeofday(tp:Ptimespec;z:Ptimezone):Integer;
|
|
|
|
var
|
|
|
|
_now:TFILETIME;
|
|
|
|
begin
|
|
|
|
Swgettimezone(z);
|
|
|
|
if (tp<>nil) then
|
|
|
|
begin
|
|
|
|
GetSystemTimeAsFileTime(_now);
|
|
|
|
QWORD(_now):=filetime_to_hnsec(_now);
|
|
|
|
tp^.tv_sec :=QWORD(_now) div HECTONANOSEC_PER_SEC;
|
|
|
|
tp^.tv_nsec:=(QWORD(_now) mod HECTONANOSEC_PER_SEC)*100;
|
|
|
|
end;
|
|
|
|
Result:=0;
|
|
|
|
end;
|
|
|
|
|
|
|
|
|
|
|
|
end.
|
|
|
|
|