Improved time functions.

svn path=/trunk/; revision=471
This commit is contained in:
Eric Kohl 1999-05-15 17:25:02 +00:00
parent b2274fda0d
commit 0a70b0080a
7 changed files with 291 additions and 257 deletions

View file

@ -13,55 +13,37 @@
#include <ddk/ntddk.h> #include <ddk/ntddk.h>
#include <ddk/cctypes.h> #include <ddk/cctypes.h>
#include <ddk/zwtypes.h> #include <ddk/zwtypes.h>
//#include <ddk/rtl.h>
#define NDEBUG #define NDEBUG
#include <internal/debug.h> #include <internal/debug.h>
#include "vfat.h" #include "vfat.h"
//days from 1st January
static const int MonthsDF1[2][12] =
{
{ 0,31, 59, 90,120,151,181,212,243,273,304,334 },
{ 0,31, 60, 91,121,152,182,213,244,274,305,335 }
};
static __inline int IsLeapYear(int Year)
{
return Year % 4 == 0 && (Year % 100 != 0 || Year % 400 == 0) ? 1 : 0;
}
// function like DosDateTimeToFileTime // function like DosDateTimeToFileTime
BOOL fsdDosDateTimeToFileTime(WORD wDosDate,WORD wDosTime, TIME *FileTime) BOOL FsdDosDateTimeToFileTime(WORD wDosDate,WORD wDosTime, TIME *FileTime)
{ {
WORD Day,Month,Year,Second,Minute,Hour; PDOSTIME pdtime = (PDOSTIME)&wDosTime;
long long int *pTime=(long long int *)FileTime; PDOSDATE pddate = (PDOSDATE)&wDosDate;
long long int mult; TIME_FIELDS TimeFields;
Day=wDosDate&0x001f;
Month= (wDosDate&0x00e0)>>5;//1=January if (FileTime == NULL)
Year= ((wDosDate&0xff00)>>8)+1980; return FALSE;
Second=(wDosTime&0x001f)<<1;
Minute=(wDosTime&0x07e0)>>5; TimeFields.Milliseconds = 0;
Hour= (wDosTime&0xf100)>>11; TimeFields.Second = pdtime->Second;
mult=10000000; TimeFields.Minute = pdtime->Minute;
*pTime=Second*mult; TimeFields.Hour = pdtime->Hour;
mult *=60;
*pTime +=Minute*mult; TimeFields.Day = pddate->Day;
mult *=60; TimeFields.Month = pddate->Month;
*pTime +=Hour*mult; TimeFields.Year = 1980 + pddate->Year;
mult *=24;
*pTime +=(Day-1)*mult; RtlTimeFieldsToTime(&TimeFields, (PLARGE_INTEGER)FileTime);
if((Year % 4 == 0 && (Year % 100 != 0 || Year % 400 == 0) ? 1 : 0))
*pTime += MonthsDF1[1][Month-1];
else
*pTime += MonthsDF1[0][Month-1];
*pTime +=(Year-1601)*mult*365
+(Year-1601)/4
-(Year-1601)/100
+(Year-1601)/400;
return TRUE; return TRUE;
} }
#define DosDateTimeToFileTime fsdDosDateTimeToFileTime
unsigned long vfat_wstrlen(PWSTR s) unsigned long vfat_wstrlen(PWSTR s)
@ -108,13 +90,13 @@ NTSTATUS FsdGetFileDirectoryInformation(PVfatFCB pFcb,
memcpy(pInfo->FileName,pFcb->ObjectName memcpy(pInfo->FileName,pFcb->ObjectName
,sizeof(WCHAR)*(pInfo->FileNameLength)); ,sizeof(WCHAR)*(pInfo->FileNameLength));
// pInfo->FileIndex=; // pInfo->FileIndex=;
DosDateTimeToFileTime(pFcb->entry.CreationDate,pFcb->entry.CreationTime FsdDosDateTimeToFileTime(pFcb->entry.CreationDate,pFcb->entry.CreationTime
,&pInfo->CreationTime); ,&pInfo->CreationTime);
DosDateTimeToFileTime(pFcb->entry.AccessDate,0 FsdDosDateTimeToFileTime(pFcb->entry.AccessDate,0
,&pInfo->LastAccessTime); ,&pInfo->LastAccessTime);
DosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime FsdDosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime
,&pInfo->LastWriteTime); ,&pInfo->LastWriteTime);
DosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime FsdDosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime
,&pInfo->ChangeTime); ,&pInfo->ChangeTime);
pInfo->EndOfFile=RtlConvertUlongToLargeInteger(pFcb->entry.FileSize); pInfo->EndOfFile=RtlConvertUlongToLargeInteger(pFcb->entry.FileSize);
/* Make allocsize a rounded up multiple of BytesPerCluster */ /* Make allocsize a rounded up multiple of BytesPerCluster */
@ -141,13 +123,13 @@ NTSTATUS FsdGetFileFullDirectoryInformation(PVfatFCB pFcb,
memcpy(pInfo->FileName,pFcb->ObjectName memcpy(pInfo->FileName,pFcb->ObjectName
,sizeof(WCHAR)*(pInfo->FileNameLength)); ,sizeof(WCHAR)*(pInfo->FileNameLength));
// pInfo->FileIndex=; // pInfo->FileIndex=;
DosDateTimeToFileTime(pFcb->entry.CreationDate,pFcb->entry.CreationTime FsdDosDateTimeToFileTime(pFcb->entry.CreationDate,pFcb->entry.CreationTime
,&pInfo->CreationTime); ,&pInfo->CreationTime);
DosDateTimeToFileTime(pFcb->entry.AccessDate,0 FsdDosDateTimeToFileTime(pFcb->entry.AccessDate,0
,&pInfo->LastAccessTime); ,&pInfo->LastAccessTime);
DosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime FsdDosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime
,&pInfo->LastWriteTime); ,&pInfo->LastWriteTime);
DosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime FsdDosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime
,&pInfo->ChangeTime); ,&pInfo->ChangeTime);
pInfo->EndOfFile=RtlConvertUlongToLargeInteger(pFcb->entry.FileSize); pInfo->EndOfFile=RtlConvertUlongToLargeInteger(pFcb->entry.FileSize);
/* Make allocsize a rounded up multiple of BytesPerCluster */ /* Make allocsize a rounded up multiple of BytesPerCluster */
@ -175,13 +157,13 @@ NTSTATUS FsdGetFileBothInformation(PVfatFCB pFcb,
memcpy(pInfo->FileName,pFcb->ObjectName memcpy(pInfo->FileName,pFcb->ObjectName
,sizeof(WCHAR)*(pInfo->FileNameLength)); ,sizeof(WCHAR)*(pInfo->FileNameLength));
// pInfo->FileIndex=; // pInfo->FileIndex=;
DosDateTimeToFileTime(pFcb->entry.CreationDate,pFcb->entry.CreationTime FsdDosDateTimeToFileTime(pFcb->entry.CreationDate,pFcb->entry.CreationTime
,&pInfo->CreationTime); ,&pInfo->CreationTime);
DosDateTimeToFileTime(pFcb->entry.AccessDate,0 FsdDosDateTimeToFileTime(pFcb->entry.AccessDate,0
,&pInfo->LastAccessTime); ,&pInfo->LastAccessTime);
DosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime FsdDosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime
,&pInfo->LastWriteTime); ,&pInfo->LastWriteTime);
DosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime FsdDosDateTimeToFileTime(pFcb->entry.UpdateDate,pFcb->entry.UpdateTime
,&pInfo->ChangeTime); ,&pInfo->ChangeTime);
pInfo->EndOfFile=RtlConvertUlongToLargeInteger(pFcb->entry.FileSize); pInfo->EndOfFile=RtlConvertUlongToLargeInteger(pFcb->entry.FileSize);
/* Make allocsize a rounded up multiple of BytesPerCluster */ /* Make allocsize a rounded up multiple of BytesPerCluster */

View file

@ -1771,11 +1771,15 @@ NTSTATUS FsdGetBasicInformation(PFILE_OBJECT FileObject,
PFILE_BASIC_INFORMATION BasicInfo) PFILE_BASIC_INFORMATION BasicInfo)
{ {
DPRINT("FsdGetBasicInformation()\n"); DPRINT("FsdGetBasicInformation()\n");
// BasicInfo->CreationTime = FsdDosDateTimeToFileTime(FCB->entry.CreationDate,FCB->entry.CreationTime,
// BasicInfo->LastAccessTime = &BasicInfo->CreationTime);
// BasicInfo->LastWriteTime = FsdDosDateTimeToFileTime(FCB->entry.AccessDate,0,
// BasicInfo->ChangeTime = &BasicInfo->LastAccessTime);
FsdDosDateTimeToFileTime(FCB->entry.UpdateDate,FCB->entry.UpdateTime,
&BasicInfo->LastWriteTime);
FsdDosDateTimeToFileTime(FCB->entry.UpdateDate,FCB->entry.UpdateTime,
&BasicInfo->ChangeTime);
BasicInfo->FileAttributes = FCB->entry.Attrib; BasicInfo->FileAttributes = FCB->entry.Attrib;

View file

@ -131,6 +131,21 @@ typedef struct
#define ENTRIES_PER_SECTOR (BLOCKSIZE / sizeof(FATDirEntry)) #define ENTRIES_PER_SECTOR (BLOCKSIZE / sizeof(FATDirEntry))
typedef struct __DOSTIME
{
WORD Second:5;
WORD Minute:6;
WORD Hour:5;
} DOSTIME, *PDOSTIME;
typedef struct __DOSDATE
{
WORD Day:5;
WORD Month:4;
WORD Year:5;
} DOSDATE, *PDOSDATE;
extern PVfatFCB pFirstFcb; extern PVfatFCB pFirstFcb;
// functions called by i/o manager : // functions called by i/o manager :
@ -155,6 +170,9 @@ BOOLEAN VFATWriteSectors(IN PDEVICE_OBJECT pDeviceObject,
IN ULONG SectorCount, IN ULONG SectorCount,
IN UCHAR* Buffer); IN UCHAR* Buffer);
//internal functions in dir.c :
BOOL FsdDosDateTimeToFileTime(WORD wDosDate,WORD wDosTime, TIME *FileTime);
//internal functions in iface.c : //internal functions in iface.c :
NTSTATUS FindFile(PDEVICE_EXTENSION DeviceExt, PVfatFCB Fcb, NTSTATUS FindFile(PDEVICE_EXTENSION DeviceExt, PVfatFCB Fcb,
PVfatFCB Parent, PWSTR FileToFind,ULONG *StartSector,ULONG *Entry); PVfatFCB Parent, PWSTR FileToFind,ULONG *StartSector,ULONG *Entry);

View file

@ -58,9 +58,9 @@ typedef struct _WIN32_FIND_DATA_ASCII {
static void FileDataToWin32Data(LPWIN32_FIND_DATA lpFindFileData, PKERNEL32_FIND_FILE_DATA IData) static void FileDataToWin32Data(LPWIN32_FIND_DATA lpFindFileData, PKERNEL32_FIND_FILE_DATA IData)
{ {
lpFindFileData->dwFileAttributes = IData->FileInfo.FileAttributes; lpFindFileData->dwFileAttributes = IData->FileInfo.FileAttributes;
// memcpy(&lpFindFileData->ftCreationTime,&IData->FileInfo.CreationTime,sizeof(FILETIME)); memcpy(&lpFindFileData->ftCreationTime,&IData->FileInfo.CreationTime,sizeof(FILETIME));
// memcpy(&lpFindFileData->ftLastAccessTime,&IData->FileInfo.LastAccessTime,sizeof(FILETIME)); memcpy(&lpFindFileData->ftLastAccessTime,&IData->FileInfo.LastAccessTime,sizeof(FILETIME));
// memcpy(&lpFindFileData->ftLastWriteTime,&IData->FileInfo.LastWriteTime,sizeof(FILETIME)); memcpy(&lpFindFileData->ftLastWriteTime,&IData->FileInfo.LastWriteTime,sizeof(FILETIME));
lpFindFileData->nFileSizeHigh = IData->FileInfo.EndOfFile.u.HighPart; lpFindFileData->nFileSizeHigh = IData->FileInfo.EndOfFile.u.HighPart;
lpFindFileData->nFileSizeLow = IData->FileInfo.EndOfFile.u.LowPart; lpFindFileData->nFileSizeLow = IData->FileInfo.EndOfFile.u.LowPart;
} }

View file

@ -60,7 +60,8 @@ CloseHandle = CloseHandle@4
;CmdBatNotification@4 ;CmdBatNotification@4
;CommConfigDialogA@12 ;CommConfigDialogA@12
;CommConfigDialogW@12 ;CommConfigDialogW@12
;CompareFileTime@8 CompareFileTime@8
CompareFileTime = CompareFileTime@8
;CompareStringA@24 ;CompareStringA@24
;CompareStringA = CompareStringA@24 ;CompareStringA = CompareStringA@24
;CompareStringW@24 ;CompareStringW@24
@ -131,7 +132,8 @@ DeleteFileW = DeleteFileW@4
;DeviceIoControl@32 ;DeviceIoControl@32
;DisableThreadLibraryCalls@4 ;DisableThreadLibraryCalls@4
;DisconnectNamedPipe@4 ;DisconnectNamedPipe@4
;DosDateTimeToFileTime@12 DosDateTimeToFileTime@12
DosDateTimeToFileTime = DosDateTimeToFileTime@12
;DuplicateConsoleHandle@16 ;DuplicateConsoleHandle@16
DuplicateHandle@28 DuplicateHandle@28
DuplicateHandle = DuplicateHandle@28 DuplicateHandle = DuplicateHandle@28
@ -168,7 +170,8 @@ ExitProcess = ExitProcess@4
;FatalAppExitA@8 ;FatalAppExitA@8
;FatalAppExitW@8 ;FatalAppExitW@8
;FatalExit@4 ;FatalExit@4
;FileTimeToDosDateTime@12 FileTimeToDosDateTime@12
FileTimeToDosDateTime = FileTimeToDosDateTime@12
FileTimeToLocalFileTime@8 FileTimeToLocalFileTime@8
FileTimeToLocalFileTime = FileTimeToLocalFileTime@8 FileTimeToLocalFileTime = FileTimeToLocalFileTime@8
FileTimeToSystemTime@8 FileTimeToSystemTime@8
@ -403,7 +406,8 @@ GetStdHandle = GetStdHandle@4
;GetSystemDirectoryW@8 ;GetSystemDirectoryW@8
;GetSystemInfo@4 ;GetSystemInfo@4
;GetSystemPowerStatus@4 ;GetSystemPowerStatus@4
;GetSystemTime@4 GetSystemTime@4
GetSystemTime = GetSystemTime@4
;GetSystemTimeAdjustment@12 ;GetSystemTimeAdjustment@12
GetSystemTimeAsFileTime@4 GetSystemTimeAsFileTime@4
GetSystemTimeAsFileTime = GetSystemTimeAsFileTime@4 GetSystemTimeAsFileTime = GetSystemTimeAsFileTime@4
@ -695,7 +699,8 @@ SetLocalTime = SetLocalTime@4
SetStdHandle@8 SetStdHandle@8
SetStdHandle = SetStdHandle@8 SetStdHandle = SetStdHandle@8
;SetSystemPowerState@8 ;SetSystemPowerState@8
;SetSystemTime@4 SetSystemTime@4
SetSystemTime = SetSystemTime@4
;SetSystemTimeAdjustment@8 ;SetSystemTimeAdjustment@8
;SetTapeParameters@12 ;SetTapeParameters@12
;SetTapePosition@24 ;SetTapePosition@24
@ -718,8 +723,10 @@ Sleep@4
Sleep = Sleep@4 Sleep = Sleep@4
;SleepEx@8 ;SleepEx@8
;SuspendThread@4 ;SuspendThread@4
;SystemTimeToFileTime@8 SystemTimeToFileTime@8
;SystemTimeToTzSpecificLocalTime@12 SystemTimeToFileTime = SystemTimeToFileTime@8
SystemTimeToTzSpecificLocalTime@12
SystemTimeToTzSpecificLocalTime = SystemTimeToTzSpecificLocalTime@12
TerminateProcess@8 TerminateProcess@8
TerminateProcess = TerminateProcess@8 TerminateProcess = TerminateProcess@8
;TerminateThread@8 ;TerminateThread@8

View file

@ -4,7 +4,7 @@
* FILE: lib/kernel32/misc/time.c * FILE: lib/kernel32/misc/time.c
* PURPOSE: Time conversion functions * PURPOSE: Time conversion functions
* PROGRAMMER: Boudewijn ( ariadne@xs4all.nl) * PROGRAMMER: Boudewijn ( ariadne@xs4all.nl)
DOSDATE and DOSTIME structures from Onno Hovers * DOSDATE and DOSTIME structures from Onno Hovers
* UPDATE HISTORY: * UPDATE HISTORY:
* Created 19/01/99 * Created 19/01/99
*/ */
@ -12,20 +12,25 @@
#include <ddk/ntddk.h> #include <ddk/ntddk.h>
#include <string.h> #include <string.h>
#define NDEBUG
#include <kernel32/kernel32.h>
typedef struct __DOSTIME typedef struct __DOSTIME
{ {
WORD Second:5; WORD Second:5;
WORD Minute:6; WORD Minute:6;
WORD Hour:5; WORD Hour:5;
} DOSTIME, *PDOSTIME; } DOSTIME, *PDOSTIME;
typedef struct __DOSDATE typedef struct __DOSDATE
{ {
WORD Day:5; WORD Day:5;
WORD Month:4; WORD Month:4;
WORD Year:5; WORD Year:5;
} DOSDATE, *PDOSDATE; } DOSDATE, *PDOSDATE;
#define NSPERSEC 10000000 #define NSPERSEC 10000000
#define SECOND 1 #define SECOND 1
@ -38,18 +43,40 @@ typedef struct __DOSDATE
#define MILLENIUM (100*CENTURY) #define MILLENIUM (100*CENTURY)
#define LISECOND RtlEnlargedUnsignedMultiply(SECOND,NSPERSEC) #define TICKSPERMIN 600000000
#define LIMINUTE RtlEnlargedUnsignedMultiply(MINUTE,NSPERSEC) #define TICKSPERSEC 10000000
#define LIHOUR RtlEnlargedUnsignedMultiply(HOUR,NSPERSEC) #define TICKSPERMSEC 10000
#define LIDAY RtlEnlargedUnsignedMultiply(DAY,NSPERSEC) #define SECSPERDAY 86400
#define LIYEAR RtlEnlargedUnsignedMultiply(YEAR,NSPERSEC) #define SECSPERHOUR 3600
#define LIFOURYEAR RtlEnlargedUnsignedMultiply(FOURYEAR,NSPERSEC) #define SECSPERMIN 60
#define LICENTURY RtlEnlargedUnsignedMultiply(CENTURY,NSPERSEC) #define MINSPERHOUR 60
#define LIMILLENIUM RtlEnlargedUnsignedMultiply(CENTURY,10*NSPERSEC) #define HOURSPERDAY 24
#define EPOCHWEEKDAY 0
#define DAYSPERWEEK 7
#define EPOCHYEAR 1601
#define DAYSPERNORMALYEAR 365
#define DAYSPERLEAPYEAR 366
#define MONSPERYEAR 12
static const int YearLengths[2] = {DAYSPERNORMALYEAR, DAYSPERLEAPYEAR};
static const int MonthLengths[2][MONSPERYEAR] =
{
{ 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 },
{ 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }
};
static __inline int IsLeapYear(int Year)
{
return Year % 4 == 0 && (Year % 100 != 0 || Year % 400 == 0) ? 1 : 0;
}
static __inline void NormalizeTimeFields(CSHORT *FieldToNormalize,
CSHORT *CarryField,
int Modulus)
{
*FieldToNormalize = (CSHORT) (*FieldToNormalize - Modulus);
*CarryField = (CSHORT) (*CarryField + 1);
}
WINBOOL WINBOOL
@ -60,7 +87,6 @@ FileTimeToDosDateTime(
LPWORD lpFatTime LPWORD lpFatTime
) )
{ {
PDOSTIME pdtime=(PDOSTIME) lpFatTime; PDOSTIME pdtime=(PDOSTIME) lpFatTime;
PDOSDATE pddate=(PDOSDATE) lpFatDate; PDOSDATE pddate=(PDOSDATE) lpFatDate;
SYSTEMTIME SystemTime; SYSTEMTIME SystemTime;
@ -83,13 +109,10 @@ FileTimeToDosDateTime(
pdtime->Minute = SystemTime.wMinute; pdtime->Minute = SystemTime.wMinute;
pdtime->Hour = SystemTime.wHour; pdtime->Hour = SystemTime.wHour;
pddate->Day = SystemTime.wDay; pddate->Day = SystemTime.wDay;
pddate->Month = SystemTime.wMonth; pddate->Month = SystemTime.wMonth;
pddate->Year = SystemTime.wYear - 1980; pddate->Year = SystemTime.wYear - 1980;
return TRUE; return TRUE;
} }
@ -101,7 +124,6 @@ DosDateTimeToFileTime(
LPFILETIME lpFileTime LPFILETIME lpFileTime
) )
{ {
PDOSTIME pdtime = (PDOSTIME) &wFatTime; PDOSTIME pdtime = (PDOSTIME) &wFatTime;
PDOSDATE pddate = (PDOSDATE) &wFatDate; PDOSDATE pddate = (PDOSDATE) &wFatDate;
SYSTEMTIME SystemTime; SYSTEMTIME SystemTime;
@ -109,14 +131,11 @@ DosDateTimeToFileTime(
if ( lpFileTime == NULL ) if ( lpFileTime == NULL )
return FALSE; return FALSE;
SystemTime.wMilliseconds = 0; SystemTime.wMilliseconds = 0;
SystemTime.wSecond = pdtime->Second; SystemTime.wSecond = pdtime->Second;
SystemTime.wMinute = pdtime->Minute; SystemTime.wMinute = pdtime->Minute;
SystemTime.wHour = pdtime->Hour; SystemTime.wHour = pdtime->Hour;
SystemTime.wDay = pddate->Day; SystemTime.wDay = pddate->Day;
SystemTime.wMonth = pddate->Month; SystemTime.wMonth = pddate->Month;
SystemTime.wYear = 1980 + pddate->Year; SystemTime.wYear = 1980 + pddate->Year;
@ -133,36 +152,24 @@ CompareFileTime(
CONST FILETIME *lpFileTime2 CONST FILETIME *lpFileTime2
) )
{ {
if ( lpFileTime1 == NULL ) if ( lpFileTime1 == NULL )
return 0; return 0;
if ( lpFileTime2 == NULL ) if ( lpFileTime2 == NULL )
return 0; return 0;
/*
if (lpFileTime1.HighPart > lpFileTime2.HighPart) if (*((PLONGLONG)lpFileTime1) > *((PLONGLONG)lpFileTime2))
return 1; return 1;
else if (lpFileTime1.HighPart < lpFileTime2.HighPart) else if (*((PLONGLONG)lpFileTime1) < *((PLONGLONG)lpFileTime2))
return -1; return -1;
else if (lpFileTime1.LowPart > lpFileTime2.LowPart)
return 1; return 0;
else if (lpFileTime1.LowPart < lpFileTime2.LowPart)
return -1;
else
return 0;
*/
} }
VOID VOID
STDCALL STDCALL
GetSystemTimeAsFileTime(PFILETIME lpFileTime) GetSystemTimeAsFileTime(PFILETIME lpFileTime)
{ {
NTSTATUS errCode; NtQuerySystemTime ((TIME *)lpFileTime);
errCode = NtQuerySystemTime (
(TIME *)lpFileTime
);
return;
} }
WINBOOL WINBOOL
@ -173,7 +180,7 @@ SystemTimeToFileTime(
) )
{ {
LARGE_INTEGER FileTime; LARGE_INTEGER FileTime;
LARGE_INTEGER Year; LARGE_INTEGER Year;
LARGE_INTEGER Month; LARGE_INTEGER Month;
LARGE_INTEGER Day; LARGE_INTEGER Day;
@ -186,7 +193,7 @@ SystemTimeToFileTime(
if ( (lpSystemTime->wYear % 4 == 0 && lpSystemTime->wYear % 100 != 0) || lpSystemTime->wYear % 400 == 0) if ( (lpSystemTime->wYear % 4 == 0 && lpSystemTime->wYear % 100 != 0) || lpSystemTime->wYear % 400 == 0)
LeapDay = 1; LeapDay = 1;
else else
LeapDay = 0; LeapDay = 0;
@ -249,142 +256,70 @@ FileTimeToSystemTime(
LPSYSTEMTIME lpSystemTime LPSYSTEMTIME lpSystemTime
) )
{ {
const int *Months;
int LeapSecondCorrections, SecondsInDay, CurYear;
int LeapYear, CurMonth;
long int Days;
long long int Time = *((long long int*)lpFileTime);
/* Extract millisecond from time and convert time into seconds */
lpSystemTime->wMilliseconds = (WORD)((Time % TICKSPERSEC) / TICKSPERMSEC);
Time = Time / TICKSPERSEC;
LARGE_INTEGER FileTime; /* FIXME: Compute the number of leap second corrections here */
LeapSecondCorrections = 0;
LARGE_INTEGER dwMillenium; /* Split the time into days and seconds within the day */
LARGE_INTEGER dwRemMillenium; Days = Time / SECSPERDAY;
SecondsInDay = Time % SECSPERDAY;
LARGE_INTEGER dwCentury;
LARGE_INTEGER dwRemCentury;
LARGE_INTEGER dwFourYear;
LARGE_INTEGER dwRemFourYear;
LARGE_INTEGER dwYear;
LARGE_INTEGER dwRemYear;
LARGE_INTEGER dwDay;
LARGE_INTEGER dwRemDay;
LARGE_INTEGER dwHour;
LARGE_INTEGER dwRemHour;
LARGE_INTEGER dwMinute;
LARGE_INTEGER dwRemMinute;
LARGE_INTEGER dwSecond;
LARGE_INTEGER dwRemSecond;
LARGE_INTEGER dwDayOfWeek; /* Adjust the values for GMT and leap seconds */
SecondsInDay += LeapSecondCorrections;
while (SecondsInDay < 0)
{
SecondsInDay += SECSPERDAY;
Days--;
}
while (SecondsInDay >= SECSPERDAY)
{
SecondsInDay -= SECSPERDAY;
Days++;
}
/* compute time of day */
lpSystemTime->wHour = (WORD) (SecondsInDay / SECSPERHOUR);
SecondsInDay = SecondsInDay % SECSPERHOUR;
lpSystemTime->wMinute = (WORD) (SecondsInDay / SECSPERMIN);
lpSystemTime->wSecond = (WORD) (SecondsInDay % SECSPERMIN);
DWORD LeapDay = 0; /* FIXME: handle the possibility that we are on a leap second (i.e. Second = 60) */
/* compute day of week */
memcpy(&FileTime,lpFileTime,sizeof(FILETIME)); lpSystemTime->wDayOfWeek = (WORD) ((EPOCHWEEKDAY + Days) % DAYSPERWEEK);
dwMillenium = RtlLargeIntegerDivide(FileTime,LIMILLENIUM,&dwRemMillenium);
dwCentury = RtlLargeIntegerDivide(dwRemMillenium,LICENTURY,&dwRemCentury);
dwFourYear = RtlLargeIntegerDivide(dwRemCentury,LIFOURYEAR,&dwRemFourYear);
dwYear = RtlLargeIntegerDivide(dwRemFourYear,LIYEAR,&dwRemYear);
dwDay = RtlLargeIntegerDivide(dwRemYear,LIDAY,&dwRemDay);
dwHour = RtlLargeIntegerDivide(dwRemDay,LIHOUR,&dwRemHour);
dwMinute = RtlLargeIntegerDivide(dwRemHour,LIMINUTE,&dwRemMinute);
dwSecond = RtlLargeIntegerDivide(dwRemMinute,LISECOND,&dwRemSecond);
lpSystemTime->wHour= (WORD)(dwHour.u.LowPart);
lpSystemTime->wMinute= (WORD)(dwMinute.u.LowPart);
lpSystemTime->wSecond= (WORD)(dwSecond.u.LowPart);
lpSystemTime->wMilliseconds = (WORD)(dwRemSecond.u.LowPart/10000);
if ( lpSystemTime->wSecond > 60 ) { /* compute year */
lpSystemTime->wSecond -= 60; CurYear = EPOCHYEAR;
lpSystemTime->wMinute ++; /* FIXME: handle calendar modifications */
} while (1)
{
LeapYear = IsLeapYear(CurYear);
if (Days < (long) YearLengths[LeapYear])
{
break;
}
CurYear++;
Days = Days - (long) YearLengths[LeapYear];
}
lpSystemTime->wYear = (WORD) CurYear;
if ( lpSystemTime->wMinute > 60 ) { /* Compute month of year */
lpSystemTime->wMinute -= 60; Months = MonthLengths[LeapYear];
lpSystemTime->wHour ++; for (CurMonth = 0; Days >= (long) Months[CurMonth]; CurMonth++)
} Days = Days - (long) Months[CurMonth];
lpSystemTime->wMonth = (WORD) (CurMonth + 1);
lpSystemTime->wDay = (WORD) (Days + 1);
if (lpSystemTime->wHour > 24 ) { return TRUE;
lpSystemTime->wHour-= 24;
dwDay.u.LowPart = dwDay.u.LowPart + 1;
}
//FIXME since 1972 some years have a leap second [ aprox 15 out of 20 ]
// if leap year
lpSystemTime->wYear = 1601 + 1000* (LONG)dwMillenium.u.LowPart + 100 * (LONG)dwCentury.u.LowPart + 4 * (LONG)dwFourYear.u.LowPart + (LONG)dwYear.u.LowPart;
if ( (lpSystemTime->wYear % 4 == 0 && lpSystemTime->wYear % 100 != 0) || lpSystemTime->wYear % 400 == 0)
LeapDay = 1;
else
LeapDay = 0;
if ( dwDay.u.LowPart >= 0 && dwDay.u.LowPart < 31 ) {
lpSystemTime->wMonth = 1;
lpSystemTime->wDay = dwDay.u.LowPart + 1;
}
else if ( dwDay.u.LowPart >= 31 && dwDay.u.LowPart < ( 59 + LeapDay )) {
lpSystemTime->wMonth = 2;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - 31;
}
else if ( dwDay.u.LowPart >= ( 59 + LeapDay ) && dwDay.u.LowPart < ( 90 + LeapDay ) ) {
lpSystemTime->wMonth = 3;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - ( 59 + LeapDay);
}
else if ( dwDay.u.LowPart >= 90+ LeapDay && dwDay.u.LowPart < 120 + LeapDay) {
lpSystemTime->wMonth = 4;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - (31 + LeapDay );
}
else if ( dwDay.u.LowPart >= 120 + LeapDay && dwDay.u.LowPart < 151 + LeapDay ) {
lpSystemTime->wMonth = 5;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - (120 + LeapDay);
}
else if ( dwDay.u.LowPart >= ( 151 + LeapDay) && dwDay.u.LowPart < ( 181 + LeapDay ) ) {
lpSystemTime->wMonth = 6;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - ( 151 + LeapDay );
}
else if ( dwDay.u.LowPart >= ( 181 + LeapDay ) && dwDay.u.LowPart < ( 212 + LeapDay ) ) {
lpSystemTime->wMonth = 7;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - ( 181 + LeapDay );
}
else if ( dwDay.u.LowPart >= ( 212 + LeapDay ) && dwDay.u.LowPart < ( 243 + LeapDay ) ) {
lpSystemTime->wMonth = 8;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - (212 + LeapDay );
}
else if ( dwDay.u.LowPart >= ( 243+ LeapDay ) && dwDay.u.LowPart < ( 273 + LeapDay ) ) {
lpSystemTime->wMonth = 9;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - ( 243 + LeapDay );
}
else if ( dwDay.u.LowPart >= ( 273 + LeapDay ) && dwDay.u.LowPart < ( 304 + LeapDay ) ) {
lpSystemTime->wMonth = 10;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - ( 273 + LeapDay);
}
else if ( dwDay.u.LowPart >= ( 304 + LeapDay ) && dwDay.u.LowPart < ( 334 + LeapDay ) ) {
lpSystemTime->wMonth = 11;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - ( 304 + LeapDay );
}
else if ( dwDay.u.LowPart >= ( 334 + LeapDay ) && dwDay.u.LowPart < ( 365 + LeapDay )) {
lpSystemTime->wMonth = 12;
lpSystemTime->wDay = dwDay.u.LowPart + 1 - ( 334 + LeapDay );
}
dwDayOfWeek = RtlLargeIntegerDivide(FileTime,LIDAY,&dwRemDay);
lpSystemTime->wDayOfWeek = 1 + dwDayOfWeek.u.LowPart % 7;
return TRUE;
} }
@ -395,9 +330,10 @@ FileTimeToLocalFileTime(
LPFILETIME lpLocalFileTime LPFILETIME lpLocalFileTime
) )
{ {
// memcpy(lpLocalFileTime,lpFileTime,sizeof(FILETIME)); // FIXME: include time bias
*((PLONGLONG)lpLocalFileTime) = *((PLONGLONG)lpFileTime);
return TRUE;
return TRUE;
} }
WINBOOL WINBOOL
@ -407,8 +343,10 @@ LocalFileTimeToFileTime(
LPFILETIME lpFileTime LPFILETIME lpFileTime
) )
{ {
// FIXME: include time bias
return TRUE; *((PLONGLONG)lpFileTime) = *((PLONGLONG)lpLocalFileTime);
return TRUE;
} }
VOID VOID
@ -417,8 +355,12 @@ GetLocalTime(
LPSYSTEMTIME lpSystemTime LPSYSTEMTIME lpSystemTime
) )
{ {
GetSystemTime(lpSystemTime); FILETIME FileTime;
return; FILETIME LocalFileTime;
NtQuerySystemTime ((TIME*)&FileTime);
FileTimeToLocalFileTime (&FileTime, &LocalFileTime);
FileTimeToSystemTime (&LocalFileTime, lpSystemTime);
} }
VOID VOID
@ -428,9 +370,9 @@ GetSystemTime(
) )
{ {
FILETIME FileTime; FILETIME FileTime;
GetSystemTimeAsFileTime(&FileTime);
FileTimeToSystemTime(&FileTime,lpSystemTime); NtQuerySystemTime ((TIME*)&FileTime);
return; FileTimeToSystemTime (&FileTime, lpSystemTime);
} }
WINBOOL WINBOOL
@ -439,24 +381,34 @@ SetLocalTime(
CONST SYSTEMTIME *lpSystemTime CONST SYSTEMTIME *lpSystemTime
) )
{ {
return SetSystemTime(lpSystemTime); FILETIME LocalFileTime;
LARGE_INTEGER FileTime;
NTSTATUS errCode;
SystemTimeToFileTime (lpSystemTime, &LocalFileTime);
LocalFileTimeToFileTime (&LocalFileTime, (FILETIME *)&FileTime);
errCode = NtSetSystemTime (&FileTime, &FileTime);
if (!NT_SUCCESS(errCode))
return FALSE;
return TRUE;
} }
WINBOOL WINBOOL
STDCALL STDCALL
SetSystemTime( SetSystemTime(
CONST SYSTEMTIME *lpSystemTime CONST SYSTEMTIME *lpSystemTime
) )
{ {
NTSTATUS errCode; LARGE_INTEGER NewSystemTime;
LARGE_INTEGER NewSystemTime; NTSTATUS errCode;
SystemTimeToFileTime(lpSystemTime, (FILETIME *)&NewSystemTime); SystemTimeToFileTime (lpSystemTime, (PFILETIME)&NewSystemTime);
errCode = NtSetSystemTime (&NewSystemTime,&NewSystemTime); errCode = NtSetSystemTime (&NewSystemTime, &NewSystemTime);
if ( !NT_SUCCESS(errCode) ) if (!NT_SUCCESS(errCode))
return FALSE; return FALSE;
return TRUE; return TRUE;
}
}
/* /*
typedef struct _TIME_ZONE_INFORMATION { // tzi typedef struct _TIME_ZONE_INFORMATION { // tzi
LONG Bias; LONG Bias;
@ -483,16 +435,85 @@ GetTimeZoneInformation(
return TIME_ZONE_ID_UNKNOWN; return TIME_ZONE_ID_UNKNOWN;
} }
BOOL
STDCALL
SetTimeZoneInformation(
CONST TIME_ZONE_INFORMATION *lpTimeZoneInformation
)
{
return FALSE;
}
DWORD STDCALL GetCurrentTime(VOID) DWORD STDCALL GetCurrentTime(VOID)
{ {
return GetTickCount(); return GetTickCount ();
} }
DWORD DWORD
STDCALL STDCALL
GetTickCount(VOID) GetTickCount(VOID)
{ {
ULONG UpTime; ULONG UpTime;
NtGetTickCount(&UpTime); NtGetTickCount (&UpTime);
return UpTime; return UpTime;
}
WINBOOL STDCALL
SystemTimeToTzSpecificLocalTime(
LPTIME_ZONE_INFORMATION lpTimeZoneInformation,
LPSYSTEMTIME lpUniversalTime,
LPSYSTEMTIME lpLocalTime
)
{
TIME_ZONE_INFORMATION TimeZoneInformation;
LPTIME_ZONE_INFORMATION lpTzInfo;
LARGE_INTEGER FileTime;
if (!lpTimeZoneInformation)
{
GetTimeZoneInformation (&TimeZoneInformation);
lpTzInfo = &TimeZoneInformation;
}
else
lpTzInfo = lpTimeZoneInformation;
if (!lpUniversalTime)
return FALSE;
if (!lpLocalTime)
return FALSE;
SystemTimeToFileTime (lpUniversalTime, (PFILETIME)&FileTime);
FileTime.QuadPart -= (lpTzInfo->Bias * TICKSPERMIN);
FileTimeToSystemTime ((PFILETIME)&FileTime, lpLocalTime);
return TRUE;
}
WINBOOL
STDCALL
GetSystemTimeAdjustment(
PDWORD lpTimeAdjustment,
PDWORD lpTimeIncrement,
PBOOL lpTimeAdjustmentDisabled
)
{
// FIXME: Preliminary default settings.
*lpTimeAdjustment = 0;
*lpTimeIncrement = 0;
*lpTimeAdjustmentDisabled = TRUE;
return TRUE;
}
WINBOOL
STDCALL
SetSystemTimeAdjustment(
DWORD dwTimeAdjustment,
BOOL bTimeAdjustmentDisabled
)
{
return TRUE;
} }

View file

@ -54,6 +54,8 @@ RtlInitUnicodeString
RtlLargeIntegerAdd RtlLargeIntegerAdd
RtlLargeIntegerGreaterThan RtlLargeIntegerGreaterThan
RtlLargeIntegerShiftRight RtlLargeIntegerShiftRight
RtlTimeFieldsToTime
RtlTimeToTimeFields
RtlZeroMemory RtlZeroMemory
ZwCreateDirectoryObject@12 ZwCreateDirectoryObject@12
isdigit isdigit