mirror of
https://github.com/reactos/reactos.git
synced 2024-12-26 17:14:41 +00:00
Incorporated changed from Boudewijn
svn path=/trunk/; revision=206
This commit is contained in:
parent
d4195242ff
commit
67c37a748e
8 changed files with 796 additions and 649 deletions
|
@ -22,209 +22,6 @@ LPTOP_LEVEL_EXCEPTION_FILTER GlobalTopLevelExceptionFilter;
|
|||
|
||||
UINT GetErrorMode(void);
|
||||
|
||||
//FIXME Please remove comments in funcs.h
|
||||
LPTOP_LEVEL_EXCEPTION_FILTER
|
||||
STDCALL
|
||||
SetUnhandledExceptionFilter(
|
||||
LPTOP_LEVEL_EXCEPTION_FILTER lpTopLevelExceptionFilter
|
||||
);
|
||||
|
||||
|
||||
// these are in various flavors
|
||||
|
||||
|
||||
typedef enum _EXCEPTION_DISPOSITION
|
||||
{
|
||||
ExceptionContinueExecution,
|
||||
ExceptionContinueSearch,
|
||||
ExceptionNestedException,
|
||||
ExceptionCollidedUnwind
|
||||
} EXCEPTION_DISPOSITION;
|
||||
|
||||
|
||||
#define DISPOSITION_DISMISS 0
|
||||
#define DISPOSITION_CONTINUE_SEARCH 1
|
||||
#define DISPOSITION_NESTED_EXCEPTION 2
|
||||
#define DISPOSITION_COLLIDED_UNWIND 3
|
||||
|
||||
// following values can be returned by exception filters
|
||||
// in a try{} except() block.
|
||||
|
||||
//#define EXCEPTION_EXECUTE_HANDLER 1
|
||||
//#define EXCEPTION_CONTINUE_SEARCH 0
|
||||
//#define EXCEPTION_CONTINUE_EXECUTION -1
|
||||
|
||||
// OS/2 filter return codes
|
||||
#define FILTER_ACCEPT 1
|
||||
#define FILTER_DISMISS -1
|
||||
#define FILTER_CONTINUE_SEARCH 0
|
||||
|
||||
|
||||
#define TRYLEVEL_NONE -1
|
||||
#define TRYLEVEL_INVALID -2
|
||||
|
||||
//callback interface codes (mimimal required set)
|
||||
|
||||
#define CB_GET_MAX_CODE 0
|
||||
#define CB_DO_LOCAL_UNWIND 1
|
||||
#define CB_GET_FRAME_EBP 2
|
||||
#define CB_GET_SCOPE_INDEX 3
|
||||
#define CB_GET_SCOPE_DATA 4
|
||||
#define MAX_CALLBACK_CODE 4
|
||||
|
||||
|
||||
#define EH_NONCONTINUABLE 1
|
||||
#define EH_UNWINDING 2
|
||||
#define EH_EXIT_UNWIND 4
|
||||
#define EH_STACK_INVALID 8
|
||||
#define EH_NESTED_CALL 16
|
||||
|
||||
//#define FACILITY_RPC_RUNTIME 2
|
||||
//#define FACILITY_RPC_STUBS 3
|
||||
//#define FACILITY_IO_ERROR_CODE 4
|
||||
|
||||
//#define SEVERITY_CODE_SUCCESS 0
|
||||
//#define SEVERITY_CODE_INFORMATIONAL 1
|
||||
//#define SEVERITY_CODE_WARNING 2
|
||||
//#define SEVERITY_CODE_ERROR 3
|
||||
|
||||
|
||||
#define XCPT_FATAL_EXCEPTION (0xC0000000)
|
||||
#define XCPT_SEVERITY_CODE (0xC0000000)
|
||||
#define XCPT_CUSTOMER_CODE (0x20000000)
|
||||
#define XCPT_FACILITY_CODE (0x1FFF0000)
|
||||
#define XCPT_EXCEPTION_CODE (0x0000FFFF)
|
||||
|
||||
|
||||
// this is the definition of NTSTATUS
|
||||
|
||||
// definition of NTSTATUS
|
||||
|
||||
typedef struct _NTSTATUSDEF
|
||||
{
|
||||
USHORT Code;
|
||||
USHORT Facility :12;
|
||||
UCHAR Reserved : 1;
|
||||
UCHAR CstCodeFlag : 1;
|
||||
UCHAR Severity : 2;
|
||||
} NTSTATUSDEF;
|
||||
|
||||
// Violation flags in ExceptionInfo
|
||||
|
||||
#define XCPT_UNKNOWN_ACCESS 0x00000000
|
||||
#define XCPT_READ_ACCESS 0x00000001
|
||||
#define XCPT_WRITE_ACCESS 0x00000002
|
||||
#define XCPT_EXECUTE_ACCESS 0x00000004
|
||||
#define XCPT_SPACE_ACCESS 0x00000008 // address space access violation
|
||||
#define XCPT_LIMIT_ACCESS 0x00000010 // out of bounds
|
||||
#define XCPT_DATA_UNKNOWN 0xFFFFFFFF
|
||||
|
||||
|
||||
// some status values with corresponding ExceptionInfo values
|
||||
|
||||
//#define STATUS_GUARD_PAGE_VIOLATION 0x80000001
|
||||
// ExceptionInfo[ 0 ] - Access Code: XCPT_READ_ACCESS | XCPT_WRITE_ACCESS
|
||||
// ExceptionInfo[ 1 ] - FaultAddr
|
||||
|
||||
|
||||
//#define STATUS_DATATYPE_MISALIGNMENT 0x80000002
|
||||
// OS/2 XCPT is at 0xC000009E
|
||||
// ExceptionInfo[ 0 ] - Access Code: XCPT_READ_ACCESS | XCPT_WRITE_ACCESS
|
||||
// ExceptionInfo[ 1 ] - Alignment
|
||||
// ExceptionInfo[ 2 ] - FaultAddr
|
||||
|
||||
|
||||
//#define STATUS_ACCESS_VIOLATION 0xC0000005
|
||||
// ExceptionInfo[ 0 ] - Access Code: XCPT_READ_ACCESS | XCPT_WRITE_ACCESS
|
||||
// ExceptionInfo[ 1 ] - FaultAddr
|
||||
|
||||
|
||||
//#define STATUS_IN_PAGE_ERROR 0xC0000006
|
||||
// ExceptionInfo[ 0 ] - FaultAddr
|
||||
|
||||
//#define STATUS_NONCONTINUABLE_EXCEPTION 0xC0000025
|
||||
//#define STATUS_INVALID_DISPOSITION 0xC0000026
|
||||
|
||||
|
||||
// Exceptions generated by the exception handler
|
||||
|
||||
#define STATUS_UNWIND 0xC0000027
|
||||
#define STATUS_BAD_STACK 0xC0000028
|
||||
#define STATUS_INVALID_UNWIND_TARGET 0xC0000029
|
||||
|
||||
|
||||
typedef struct _EXCEPTION_REGISTRATION;
|
||||
|
||||
typedef EXCEPTION_DISPOSITION
|
||||
(STDCALL *ExceptionHandlerType)(
|
||||
struct _EXCEPTION_RECORD *ExceptionRecord,
|
||||
struct _EXCEPTION_REGISTRATION *EstablisherFrame,
|
||||
struct _CONTEXT *Context,
|
||||
struct _EXCEPTION_RECORD *DispatcherContext
|
||||
);
|
||||
|
||||
|
||||
|
||||
|
||||
typedef struct _SCOPE_TABLE {
|
||||
DWORD prevTryLevel;
|
||||
LPTOP_LEVEL_EXCEPTION_FILTER lpfnFilter;
|
||||
ExceptionHandlerType lpfnHandler;
|
||||
} SCOPE_TABLE , *PSCOPE_TABLE;
|
||||
|
||||
typedef struct _EXCEPTION_REGISTRATION {
|
||||
struct _EXCEPTION_REGISTRATION *Prev;
|
||||
ExceptionHandlerType Handler;
|
||||
PSCOPE_TABLE ScopeTable;
|
||||
unsigned int TryLevel;
|
||||
unsigned int _ebp;
|
||||
PEXCEPTION_POINTERS *Pointers;
|
||||
} EXCEPTION_REGISTRATION, *PEXCEPTION_REGISTRATION;
|
||||
|
||||
#define END_OF_CHAIN ((PEXCEPTION_REGISTRATION) -1)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
EXCEPTION_DISPOSITION
|
||||
CDECL
|
||||
ExceptionHandler(
|
||||
struct _EXCEPTION_RECORD *ExceptionRecord,
|
||||
struct _EXCEPTION_REGISTRATION *RegistrationFrame,
|
||||
CONTEXT *Context,
|
||||
struct _EXCEPTION_RECORD *DispatcherContext
|
||||
);
|
||||
|
||||
void KiUserExceptionDispatcher(
|
||||
struct _EXCEPTION_RECORD *ExceptionRecord,
|
||||
CONTEXT *Context);
|
||||
|
||||
NTSTATUS RtlDispatchException(
|
||||
struct _EXCEPTION_RECORD *ExceptionRecord,
|
||||
CONTEXT *Context);
|
||||
|
||||
struct _EXCEPTION_REGISTRATION *RtlpGetRegistrationHead(VOID);
|
||||
|
||||
void RtlpCaptureContext(CONTEXT *Context);
|
||||
void RtlpGetStackLimits(void *StackBase, void *StackLimit);
|
||||
void RtlpUnlinkHandler(struct _EXCEPTION_REGISTRATION *__head);
|
||||
void RtlpLinkHandler(struct _EXCEPTION_REGISTRATION *__head);
|
||||
void RtlUnwind(struct _EXCEPTION_REGISTRATION *RegistratonFrame,
|
||||
VOID *ReturnAddress, // Unused
|
||||
struct _EXCEPTION_RECORD *ExceptionRecord,
|
||||
DWORD _eax);
|
||||
|
||||
void RtlRaiseException(struct _EXCEPTION_RECORD *ExceptionRecord);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
UINT GetErrorMode(void)
|
||||
|
@ -260,91 +57,6 @@ SetUnhandledExceptionFilter(
|
|||
|
||||
|
||||
|
||||
LONG
|
||||
STDCALL
|
||||
ExceptionFilter (
|
||||
PEXCEPTION_POINTERS ExceptionInfo
|
||||
)
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
EXCEPTION_DISPOSITION
|
||||
CDECL
|
||||
ExceptionHandler(
|
||||
struct _EXCEPTION_RECORD *ExceptionRecord,
|
||||
struct _EXCEPTION_REGISTRATION *RegistrationFrame,
|
||||
CONTEXT *Context,
|
||||
struct _EXCEPTION_RECORD *DispatcherContext
|
||||
)
|
||||
{
|
||||
int FilterRet;
|
||||
unsigned int TryLevel;
|
||||
EXCEPTION_POINTERS ExceptionPointers;
|
||||
SCOPE_TABLE *ScopeTable;
|
||||
unsigned int _ebp;
|
||||
|
||||
|
||||
// __asm { cld };
|
||||
|
||||
if ( ExceptionRecord->ExceptionFlags != EH_UNWINDING &&
|
||||
ExceptionRecord->ExceptionFlags != EH_EXIT_UNWIND )
|
||||
{
|
||||
ExceptionPointers.ExceptionRecord= ExceptionRecord;
|
||||
ExceptionPointers.ContextRecord = Context;
|
||||
|
||||
//
|
||||
|
||||
TryLevel = RegistrationFrame->TryLevel;
|
||||
|
||||
ScopeTable = RegistrationFrame->ScopeTable;
|
||||
|
||||
if ( RegistrationFrame->TryLevel != TRYLEVEL_NONE )
|
||||
{
|
||||
if ( RegistrationFrame->ScopeTable[TryLevel].lpfnFilter != NULL)
|
||||
{
|
||||
_ebp = RegistrationFrame->_ebp;
|
||||
//__asm { push ebp
|
||||
// mov ebp, _ebp
|
||||
//}
|
||||
FilterRet = ScopeTable->lpfnFilter(NULL);
|
||||
//__asm { pop ebp }
|
||||
|
||||
if ( FilterRet < 0 )
|
||||
return ExceptionContinueExecution;
|
||||
|
||||
if ( FilterRet == EXCEPTION_EXECUTE_HANDLER )
|
||||
{
|
||||
ScopeTable = RegistrationFrame->ScopeTable;
|
||||
RtlUnwind(RegistrationFrame,NULL,ExceptionRecord,0);
|
||||
//__asm { mov ebp, _ebp }
|
||||
// local unwind
|
||||
// nlg
|
||||
|
||||
RegistrationFrame->TryLevel = ScopeTable->prevTryLevel;
|
||||
RegistrationFrame->ScopeTable[TryLevel].lpfnHandler(ExceptionRecord,RegistrationFrame,Context, DispatcherContext);
|
||||
NtContinue(Context,PASSIVE_LEVEL);
|
||||
//return;
|
||||
|
||||
}
|
||||
else {
|
||||
ScopeTable = RegistrationFrame->ScopeTable;
|
||||
TryLevel = ScopeTable->prevTryLevel;
|
||||
// search for handler
|
||||
return DISPOSITION_CONTINUE_SEARCH;
|
||||
}
|
||||
|
||||
}
|
||||
} else { // TRYLEVEL_NONE
|
||||
return DISPOSITION_CONTINUE_SEARCH;
|
||||
}
|
||||
} else { // EXCEPTION_UNWINDING or EXCEPTION_EXIT_UNWIND
|
||||
//
|
||||
return DISPOSITION_CONTINUE_SEARCH;
|
||||
}
|
||||
return DISPOSITION_CONTINUE_SEARCH;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
@ -399,226 +111,6 @@ UnhandledExceptionFilter(struct _EXCEPTION_POINTERS *ExceptionInfo)
|
|||
}
|
||||
|
||||
|
||||
void KiUserExceptionDispatcher(PEXCEPTION_RECORD ExceptionRecord, PCONTEXT Context)
|
||||
{
|
||||
NTSTATUS errCode;
|
||||
|
||||
if ( RtlDispatchException(ExceptionRecord,Context) )
|
||||
errCode = NtContinue(Context,PASSIVE_LEVEL);
|
||||
else
|
||||
errCode = NtRaiseException(ExceptionRecord,Context,(BOOLEAN)FALSE);
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
NTSTATUS RtlDispatchException(PEXCEPTION_RECORD ExceptionRecord, PCONTEXT Context)
|
||||
{
|
||||
NTSTATUS errCode;
|
||||
ULONG StackBase, StackLimit;
|
||||
PEXCEPTION_REGISTRATION RegistrationFrame;
|
||||
EXCEPTION_RECORD DispatcherContext;
|
||||
EXCEPTION_RECORD FatalExceptionRecord;
|
||||
|
||||
//RtlpGetStackLimits(&StackBase,&StackTop);
|
||||
RegistrationFrame = RtlpGetRegistrationHead();
|
||||
|
||||
while( RegistrationFrame != END_OF_CHAIN ) {
|
||||
|
||||
//FIXME Check the stack
|
||||
RtlpGetStackLimits(&StackBase, &StackLimit);
|
||||
|
||||
errCode = RegistrationFrame->Handler(
|
||||
ExceptionRecord,
|
||||
RegistrationFrame,
|
||||
Context,
|
||||
&DispatcherContext);
|
||||
|
||||
//errCode = RtlpExecuteHandlerForException(ExceptionRecord, RegistrationFrame,
|
||||
// Context, &DispatcherContext);
|
||||
|
||||
if ( RegistrationFrame == NULL )
|
||||
ExceptionRecord->ExceptionFlags &= ~EH_NESTED_CALL;
|
||||
|
||||
switch( errCode ) {
|
||||
case DISPOSITION_DISMISS:
|
||||
if ( ExceptionRecord->ExceptionFlags & EH_NONCONTINUABLE ) {
|
||||
FatalExceptionRecord.ExceptionRecord = ExceptionRecord;
|
||||
FatalExceptionRecord.ExceptionCode = STATUS_NONCONTINUABLE_EXCEPTION;
|
||||
FatalExceptionRecord.ExceptionFlags = EH_NONCONTINUABLE;
|
||||
FatalExceptionRecord.NumberParameters = 0;
|
||||
RtlRaiseException(&FatalExceptionRecord);
|
||||
}
|
||||
else
|
||||
return DISPOSITION_CONTINUE_SEARCH;
|
||||
break;
|
||||
case DISPOSITION_CONTINUE_SEARCH:
|
||||
break;
|
||||
case DISPOSITION_NESTED_EXCEPTION:
|
||||
ExceptionRecord->ExceptionFlags |= EH_EXIT_UNWIND;
|
||||
break;
|
||||
|
||||
default:
|
||||
FatalExceptionRecord.ExceptionRecord = ExceptionRecord;
|
||||
FatalExceptionRecord.ExceptionCode = STATUS_NONCONTINUABLE_EXCEPTION;
|
||||
FatalExceptionRecord.ExceptionFlags = EH_NONCONTINUABLE;
|
||||
FatalExceptionRecord.NumberParameters = 0;
|
||||
RtlRaiseException(&FatalExceptionRecord);
|
||||
break;
|
||||
}
|
||||
|
||||
RegistrationFrame = RegistrationFrame->Prev;
|
||||
}
|
||||
return DISPOSITION_DISMISS;
|
||||
|
||||
|
||||
}
|
||||
|
||||
PEXCEPTION_REGISTRATION RtlpGetRegistrationHead(VOID)
|
||||
{
|
||||
PEXCEPTION_REGISTRATION __head;
|
||||
/*
|
||||
__asm {
|
||||
mov eax, fs:[0]
|
||||
mov __head,eax
|
||||
}
|
||||
*/
|
||||
return __head;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void RtlUnwind(PEXCEPTION_REGISTRATION RegistrationFrame,
|
||||
PVOID ReturnAddress, // Unused
|
||||
PEXCEPTION_RECORD ExceptionRecord,
|
||||
DWORD _eax)
|
||||
{
|
||||
NTSTATUS errCode, retval;
|
||||
DWORD StackBase;
|
||||
DWORD StackTop;
|
||||
CONTEXT Context;
|
||||
PEXCEPTION_REGISTRATION TraversingFrame;
|
||||
EXCEPTION_RECORD TraversingRecord;
|
||||
EXCEPTION_RECORD DispatcherContext;
|
||||
|
||||
|
||||
/* build an exception record, if we do not have one */
|
||||
if(ExceptionRecord != NULL)
|
||||
{
|
||||
ExceptionRecord->ExceptionCode = (DWORD)STATUS_UNWIND; //STATUS_INVALID_DISPOSITION;
|
||||
ExceptionRecord->ExceptionFlags = 0;
|
||||
ExceptionRecord->ExceptionRecord = NULL;
|
||||
//ExceptionRecord->ExceptionAddress = (LPVOID)pcontext->Eip;
|
||||
ExceptionRecord->NumberParameters = 0;
|
||||
ExceptionRecord->ExceptionInformation[0] =0;
|
||||
|
||||
|
||||
if ( RegistrationFrame != NULL )
|
||||
ExceptionRecord->ExceptionFlags |= EH_UNWINDING;
|
||||
else
|
||||
ExceptionRecord->ExceptionFlags |=
|
||||
(EH_UNWINDING|EH_EXIT_UNWIND);
|
||||
}
|
||||
Context.ContextFlags |=
|
||||
(CONTEXT_i386|CONTEXT_FULL);
|
||||
RtlpCaptureContext(&Context);
|
||||
Context.Esp += 0x10;
|
||||
Context.Eax = _eax;
|
||||
|
||||
TraversingFrame = RtlpGetRegistrationHead();
|
||||
|
||||
while( ( TraversingFrame != NULL ) && ( TraversingFrame != END_OF_CHAIN ) && ( TraversingFrame != RegistrationFrame ) )
|
||||
{
|
||||
|
||||
errCode = TraversingFrame->Handler(
|
||||
ExceptionRecord,
|
||||
TraversingFrame,
|
||||
&Context,
|
||||
&DispatcherContext);
|
||||
if ( (retval == ExceptionCollidedUnwind) && (TraversingFrame != (LPVOID)&DispatcherContext) )
|
||||
TraversingFrame = (LPVOID)&DispatcherContext;
|
||||
else if ((TraversingFrame != RegistrationFrame) && (TraversingFrame != TraversingFrame->Prev) ) {
|
||||
RtlpUnlinkHandler(TraversingFrame);
|
||||
TraversingFrame = TraversingFrame->Prev;
|
||||
}
|
||||
else
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void RtlpUnlinkHandler(PEXCEPTION_REGISTRATION __head)
|
||||
{
|
||||
PEXCEPTION_REGISTRATION theHead;
|
||||
PEXCEPTION_REGISTRATION theLast;
|
||||
theHead = RtlpGetRegistrationHead();
|
||||
|
||||
/*
|
||||
if ( __head == NULL )
|
||||
return;
|
||||
|
||||
if ( theHead == __head ) {
|
||||
theHead = theHead->Prev;
|
||||
__asm {
|
||||
mov eax, theHead
|
||||
mov fs:[0], eax
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
else {
|
||||
do {
|
||||
theLast = theHead;
|
||||
theHead = theHead->Prev;
|
||||
if ( theHead == __head ) {
|
||||
theLast->Prev = theHead->Prev;
|
||||
}
|
||||
} while ( theHead != NULL && theHead != END_OF_CHAIN );
|
||||
}
|
||||
|
||||
*/
|
||||
return;
|
||||
}
|
||||
|
||||
void RtlpLinkHandler(PEXCEPTION_REGISTRATION __head)
|
||||
{
|
||||
PEXCEPTION_REGISTRATION theHead;
|
||||
if (__head == NULL)
|
||||
return;
|
||||
|
||||
theHead = RtlpGetRegistrationHead();
|
||||
__head->Prev = theHead;
|
||||
/*
|
||||
__asm {
|
||||
mov eax, __head
|
||||
mov fs:[0], eax
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
||||
|
||||
void RtlpCaptureContext(PCONTEXT Context)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
void RtlpGetStackLimits(void *StackBase, void *StackLimit)
|
||||
{
|
||||
/*
|
||||
__asm{ mov eax, fs:[4]
|
||||
mov StackBase, eax }
|
||||
__asm{ mov eax, fs:[5]
|
||||
mov StackLimit, eax }
|
||||
*/
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
void RtlRaiseException(struct _EXCEPTION_RECORD *ExceptionRecord)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -3,7 +3,6 @@
|
|||
* PROJECT: ReactOS system libraries
|
||||
* FILE: lib/kernel32/file/curdir.c
|
||||
* PURPOSE: Current directory functions
|
||||
* PROGRAMMER: David Welch (welch@mcmail.com)
|
||||
* UPDATE HISTORY:
|
||||
* Created 30/09/98
|
||||
*/
|
||||
|
@ -12,16 +11,35 @@
|
|||
/* INCLUDES ******************************************************************/
|
||||
|
||||
#include <windows.h>
|
||||
|
||||
#define NDEBUG
|
||||
#include <kernel32/kernel32.h>
|
||||
|
||||
|
||||
/* GLOBALS *******************************************************************/
|
||||
|
||||
#define MAX_DOS_DRIVES 26
|
||||
|
||||
static WCHAR CurrentDirectoryW[MAX_PATH] = {0,};
|
||||
static WCHAR SystemDirectoryW[MAX_PATH];
|
||||
static WCHAR WindowsDirectoryW[MAX_PATH];
|
||||
WCHAR CurrentDirectoryW[MAX_PATH] = {0,};
|
||||
HANDLE hCurrentDirectory = NULL;
|
||||
int drive= 2;
|
||||
|
||||
char DriveDirectoryW[MAX_DOS_DRIVES][MAX_PATH] = { {"A:\\"},{"B:\\"},{"C:\\"},{"D:\\"},
|
||||
{"E:\\"},{"F:\\"},{"G:\\"},{"H:\\"},
|
||||
{"I:\\"},{"J:\\"},{"K:\\"},{"L:\\"},
|
||||
{"M:\\"},{"N:\\"},{"O:\\"},{"P:\\"},
|
||||
{"Q:\\"},{"R:\\"},{"S:\\"},{"T:\\"},
|
||||
{"U:\\"},{"V:\\"},{"W:\\"},{"X:\\"},
|
||||
{"Y:\\"},{"Z:\\"} };
|
||||
|
||||
WCHAR SystemDirectoryW[MAX_PATH];
|
||||
|
||||
WCHAR WindowsDirectoryW[MAX_PATH];
|
||||
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
SetCurrentDirectoryW(
|
||||
LPCWSTR lpPathName
|
||||
);
|
||||
|
||||
/* FUNCTIONS *****************************************************************/
|
||||
|
||||
|
@ -30,6 +48,8 @@ DWORD STDCALL GetCurrentDirectoryA(DWORD nBufferLength, LPSTR lpBuffer)
|
|||
UINT uSize,i;
|
||||
if ( lpBuffer == NULL )
|
||||
return 0;
|
||||
|
||||
|
||||
uSize = lstrlenW(CurrentDirectoryW);
|
||||
if ( nBufferLength > uSize ) {
|
||||
i = 0;
|
||||
|
@ -60,76 +80,115 @@ DWORD STDCALL GetCurrentDirectoryW(DWORD nBufferLength, LPWSTR lpBuffer)
|
|||
return uSize;
|
||||
}
|
||||
|
||||
BOOL STDCALL SetCurrentDirectoryA(LPCSTR lpPathName)
|
||||
WINBOOL STDCALL SetCurrentDirectoryA(LPCSTR lpPathName)
|
||||
{
|
||||
UINT i;
|
||||
WCHAR TempStr[MAX_PATH];
|
||||
|
||||
DPRINT("SetCurrentDirectoryA(lpPathName %s)\n",lpPathName);
|
||||
WCHAR PathNameW[MAX_PATH];
|
||||
|
||||
|
||||
if ( lpPathName == NULL )
|
||||
return FALSE;
|
||||
if ( lstrlenA(lpPathName) > MAX_PATH )
|
||||
return FALSE;
|
||||
return FALSE;
|
||||
if ( strlen(lpPathName) > MAX_PATH )
|
||||
return FALSE;
|
||||
i = 0;
|
||||
while ((lpPathName[i])!=0 && i < MAX_PATH)
|
||||
{
|
||||
TempStr[i] = (unsigned short)lpPathName[i];
|
||||
i++;
|
||||
PathNameW[i] = (WCHAR)lpPathName[i];
|
||||
i++;
|
||||
}
|
||||
TempStr[i] = 0;
|
||||
|
||||
return(SetCurrentDirectoryW(TempStr));
|
||||
PathNameW[i] = 0;
|
||||
|
||||
return SetCurrentDirectoryW(PathNameW);
|
||||
}
|
||||
|
||||
|
||||
WINBOOL STDCALL SetCurrentDirectoryW(LPCWSTR lpPathName)
|
||||
WINBOOL
|
||||
STDCALL
|
||||
SetCurrentDirectoryW(
|
||||
LPCWSTR lpPathName
|
||||
)
|
||||
{
|
||||
WCHAR TempDir[MAX_PATH];
|
||||
HANDLE TempHandle;
|
||||
ULONG Len;
|
||||
|
||||
DPRINT("SetCurrentDirectoryW(lpPathName %w)\n",lpPathName);
|
||||
|
||||
int len;
|
||||
int i,j;
|
||||
HANDLE hDirOld = hCurrentDirectory;
|
||||
WCHAR PathName[MAX_PATH];
|
||||
|
||||
if ( lpPathName == NULL )
|
||||
return FALSE;
|
||||
if ( lstrlenW(lpPathName) > MAX_PATH )
|
||||
return FALSE;
|
||||
return FALSE;
|
||||
len = lstrlenW(lpPathName);
|
||||
if ( len > MAX_PATH )
|
||||
return FALSE;
|
||||
|
||||
if ( len == 2 && isalpha(lpPathName[0]) && lpPathName[1] == ':' ) {
|
||||
len = lstrlenW(CurrentDirectoryW);
|
||||
for(i=0;i<len+1;i++)
|
||||
DriveDirectoryW[drive][i] = CurrentDirectoryW[i];
|
||||
drive = toupper((char)lpPathName[0]) - 'A';
|
||||
len = lstrlenW(DriveDirectoryW[drive]);
|
||||
for(i=0;i<len+1;i++)
|
||||
CurrentDirectoryW[i] = DriveDirectoryW[drive][i];
|
||||
if ( hDirOld != NULL )
|
||||
CloseHandle(hDirOld);
|
||||
return TRUE;
|
||||
}
|
||||
if ( lpPathName[0] == '.' && lpPathName[1] == '\\') {
|
||||
lstrcpyW(PathName,CurrentDirectoryW);
|
||||
lstrcatW(PathName,&lpPathName[2]);
|
||||
}
|
||||
else if ( lpPathName[0] == '.' && lpPathName[1] == '.' ) {
|
||||
lstrcpyW(PathName,CurrentDirectoryW);
|
||||
lstrcatW(PathName,lpPathName);
|
||||
}
|
||||
else if ( lpPathName[0] != '.' && lpPathName[1] != ':' ) {
|
||||
lstrcpyW(PathName,CurrentDirectoryW);
|
||||
lstrcatW(PathName,lpPathName);
|
||||
|
||||
}
|
||||
else
|
||||
lstrcpyW(PathName,CurrentDirectoryW);
|
||||
|
||||
len = lstrlenW(PathName);
|
||||
for(i=0;i<len+1;i++) {
|
||||
if ( PathName[i] == '.' && PathName[i+1] == '.' )
|
||||
if ( i + 2 < len && PathName[i+2] != '\\' && PathName[i+2] != 0 )
|
||||
PathName[i+2] = 0;
|
||||
}
|
||||
|
||||
|
||||
if ( len > 0 && PathName[len-1] == L'\\' ) {
|
||||
PathName[len-1] = 0;
|
||||
}
|
||||
len = lstrlenW(PathName);
|
||||
for(i=3;i<len-2 && PathName[i] != 0;i++) {
|
||||
if ( PathName[i] == L'\\' && PathName[i+1] == L'.' && PathName[i+2] == L'.' ) {
|
||||
for(j = i-1;j>=2 && PathName[j] != '\\';j-- ) {}
|
||||
PathName[j+1] = 0;
|
||||
if ( i+4 < len ) {
|
||||
PathName[i+3] = 0;
|
||||
lstrcatW(PathName,&PathName[i+4]);
|
||||
}
|
||||
len = lstrlenW(PathName);
|
||||
}
|
||||
}
|
||||
|
||||
hCurrentDirectory = CreateFileW(PathName,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,FILE_FLAG_BACKUP_SEMANTICS|FILE_ATTRIBUTE_DIRECTORY,NULL);
|
||||
if ( hCurrentDirectory == - 1 ) {
|
||||
hCurrentDirectory = hDirOld;
|
||||
DPRINT("%d\n",GetLastError());
|
||||
return FALSE;
|
||||
}
|
||||
else
|
||||
CloseHandle(hDirOld);
|
||||
|
||||
|
||||
lstrcpyW(TempDir, CurrentDirectoryW);
|
||||
GetFullPathNameW(lpPathName,
|
||||
MAX_PATH,
|
||||
TempDir,
|
||||
NULL);
|
||||
|
||||
Len = lstrlenW(TempDir);
|
||||
if (TempDir[Len-1] != '\\')
|
||||
{
|
||||
TempDir[Len] = '\\';
|
||||
TempDir[Len+1] = 0;
|
||||
}
|
||||
|
||||
DPRINT("TempDir %w\n",TempDir);
|
||||
|
||||
TempHandle = CreateFileW(TempDir,
|
||||
FILE_TRAVERSE,
|
||||
0,
|
||||
NULL,
|
||||
OPEN_EXISTING,
|
||||
FILE_ATTRIBUTE_DIRECTORY,
|
||||
NULL);
|
||||
if (TempHandle == NULL)
|
||||
{
|
||||
return(FALSE);
|
||||
}
|
||||
CloseHandle(TempHandle);
|
||||
lstrcpyW(CurrentDirectoryW, TempDir);
|
||||
|
||||
DPRINT("CurrentDirectoryW %w\n",CurrentDirectoryW);
|
||||
|
||||
return(TRUE);
|
||||
lstrcpyW(CurrentDirectoryW,PathName);
|
||||
lstrcatW(CurrentDirectoryW,L"\\");
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
|
||||
DWORD STDCALL GetTempPathA(DWORD nBufferLength, LPSTR lpBuffer)
|
||||
{
|
||||
WCHAR BufferW[MAX_PATH];
|
||||
|
@ -199,7 +258,12 @@ UINT STDCALL GetWindowsDirectoryA(LPSTR lpBuffer, UINT uSize)
|
|||
return uPathSize;
|
||||
}
|
||||
|
||||
UINT STDCALL GetSystemDirectoryW(LPWSTR lpBuffer, UINT uSize)
|
||||
UINT
|
||||
STDCALL
|
||||
GetSystemDirectoryW(
|
||||
LPWSTR lpBuffer,
|
||||
UINT uSize
|
||||
)
|
||||
{
|
||||
UINT uPathSize;
|
||||
if ( lpBuffer == NULL )
|
||||
|
@ -212,7 +276,12 @@ UINT STDCALL GetSystemDirectoryW(LPWSTR lpBuffer, UINT uSize)
|
|||
return uPathSize;
|
||||
}
|
||||
|
||||
UINT STDCALL GetWindowsDirectoryW(LPWSTR lpBuffer, UINT uSize)
|
||||
UINT
|
||||
STDCALL
|
||||
GetWindowsDirectoryW(
|
||||
LPWSTR lpBuffer,
|
||||
UINT uSize
|
||||
)
|
||||
{
|
||||
UINT uPathSize;
|
||||
if ( lpBuffer == NULL )
|
||||
|
@ -223,3 +292,5 @@ UINT STDCALL GetWindowsDirectoryW(LPWSTR lpBuffer, UINT uSize)
|
|||
|
||||
return uPathSize;
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -44,8 +44,7 @@ CopyFileExA(
|
|||
DWORD dwCopyFlags
|
||||
);
|
||||
|
||||
DWORD
|
||||
GetCurrentTime(VOID);
|
||||
|
||||
|
||||
BOOLEAN bIsFileApiAnsi; // set the file api to ansi or oem
|
||||
|
||||
|
@ -91,10 +90,10 @@ WINBOOL STDCALL WriteFile(HANDLE hFile,
|
|||
LARGE_INTEGER Offset;
|
||||
HANDLE hEvent = NULL;
|
||||
NTSTATUS errCode;
|
||||
PIO_STATUS_BLOCK IoStatusBlock;
|
||||
IO_STATUS_BLOCK IIosb;
|
||||
|
||||
WCHAR Buffer[1000];
|
||||
|
||||
//printk("%.*s",nNumberOfBytesToWrite,lpBuffer);
|
||||
|
||||
|
||||
if (lpOverLapped != NULL )
|
||||
{
|
||||
|
@ -102,9 +101,15 @@ WINBOOL STDCALL WriteFile(HANDLE hFile,
|
|||
SET_LARGE_INTEGER_HIGH_PART(Offset, lpOverLapped->OffsetHigh);
|
||||
lpOverLapped->Internal = STATUS_PENDING;
|
||||
hEvent= lpOverLapped->hEvent;
|
||||
IoStatusBlock = (PIO_STATUS_BLOCK)lpOverLapped;
|
||||
}
|
||||
else
|
||||
{
|
||||
IoStatusBlock = &IIosb;
|
||||
Offset = NULL;
|
||||
}
|
||||
errCode = NtWriteFile(hFile,hEvent,NULL,NULL,
|
||||
(PIO_STATUS_BLOCK)lpOverLapped,
|
||||
IoStatusBlock,
|
||||
(PVOID)lpBuffer,
|
||||
nNumberOfBytesToWrite,
|
||||
&Offset,
|
||||
|
@ -114,7 +119,8 @@ WINBOOL STDCALL WriteFile(HANDLE hFile,
|
|||
SetLastError(RtlNtStatusToDosError(errCode));
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if ( !lpNumberOfBytesWritten )
|
||||
*lpNumberOfBytesWritten = IoStatusBlock->Information;
|
||||
return(TRUE);
|
||||
}
|
||||
|
||||
|
@ -163,6 +169,8 @@ WINBOOL STDCALL ReadFile(HANDLE hFile,
|
|||
return FALSE;
|
||||
}
|
||||
|
||||
if ( !lpNumberOfBytesRead )
|
||||
*lpNumberOfBytesRead = IoStatusBlock->Information;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
@ -213,6 +221,8 @@ ReadFileEx(
|
|||
SetLastError(RtlNtStatusToDosError(errCode));
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
@ -1265,17 +1275,7 @@ SetFileAttributesW(
|
|||
|
||||
|
||||
|
||||
DWORD
|
||||
GetCurrentTime(VOID)
|
||||
{
|
||||
NTSTATUS errCode;
|
||||
FILETIME CurrentTime;
|
||||
memset(&CurrentTime,sizeof(FILETIME),0);
|
||||
// errCode = NtQuerySystemTime (
|
||||
// (TIME *)&CurrentTime
|
||||
// );
|
||||
return CurrentTime.dwLowDateTime;
|
||||
}
|
||||
|
||||
|
||||
UINT
|
||||
STDCALL
|
||||
|
|
|
@ -4,9 +4,20 @@
|
|||
* FILE: lib/kernel32/file/volume.c
|
||||
* PURPOSE: File volume functions
|
||||
* PROGRAMMER: Ariadne ( ariadne@xs4all.nl)
|
||||
Erik Bos, Alexandre Julliard :
|
||||
DRIVE_IsValid, GetLogicalDriveStringsA,
|
||||
GetLogicalDriveStringsW, GetLogicalDrives
|
||||
* UPDATE HISTORY:
|
||||
* Created 01/11/98
|
||||
*/
|
||||
//WINE copyright notice:
|
||||
/*
|
||||
* DOS drives handling functions
|
||||
*
|
||||
* Copyright 1993 Erik Bos
|
||||
* Copyright 1996 Alexandre Julliard
|
||||
*/
|
||||
|
||||
#undef WIN32_LEAN_AND_MEAN
|
||||
#include <windows.h>
|
||||
#include <ddk/ntddk.h>
|
||||
|
@ -14,13 +25,29 @@
|
|||
#include <string.h>
|
||||
#include <ddk/li.h>
|
||||
|
||||
DWORD
|
||||
STDCALL
|
||||
GetLogicalDrives(VOID)
|
||||
#define MAX_DOS_DRIVES 26
|
||||
|
||||
int DRIVE_IsValid( int drive )
|
||||
{
|
||||
return (DWORD)-1;
|
||||
char Drives[4];
|
||||
Drives[0] = 'A';
|
||||
Drives[1] = ':';
|
||||
Drives[2] = '\\';
|
||||
Drives[3] = 0;
|
||||
|
||||
Drives[0] = 'A' + drive -1;
|
||||
if ((drive < 0) || (drive >= MAX_DOS_DRIVES)) return 0;
|
||||
if ( CreateFileA(Drives,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,FILE_FLAG_BACKUP_SEMANTICS|FILE_ATTRIBUTE_DIRECTORY,NULL) == -1 ) {
|
||||
return 0;
|
||||
}
|
||||
return drive;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
DWORD
|
||||
STDCALL
|
||||
GetLogicalDriveStringsA(
|
||||
|
@ -28,8 +55,27 @@ GetLogicalDriveStringsA(
|
|||
LPSTR lpBuffer
|
||||
)
|
||||
{
|
||||
int drive, count;
|
||||
|
||||
for (drive = count = 0; drive < MAX_DOS_DRIVES; drive++)
|
||||
if (DRIVE_IsValid(drive)) count++;
|
||||
if (count * 4 * sizeof(char) <= nBufferLength)
|
||||
{
|
||||
LPSTR p = lpBuffer;
|
||||
for (drive = 0; drive < MAX_DOS_DRIVES; drive++)
|
||||
if (DRIVE_IsValid(drive))
|
||||
{
|
||||
*p++ = 'A' + drive;
|
||||
*p++ = ':';
|
||||
*p++ = '\\';
|
||||
*p++ = '\0';
|
||||
}
|
||||
*p = '\0';
|
||||
}
|
||||
return count * 4 * sizeof(char);
|
||||
}
|
||||
|
||||
|
||||
DWORD
|
||||
STDCALL
|
||||
GetLogicalDriveStringsW(
|
||||
|
@ -37,8 +83,41 @@ GetLogicalDriveStringsW(
|
|||
LPWSTR lpBuffer
|
||||
)
|
||||
{
|
||||
int drive, count;
|
||||
|
||||
for (drive = count = 0; drive < MAX_DOS_DRIVES; drive++)
|
||||
if (DRIVE_IsValid(drive)) count++;
|
||||
if (count * 4 * sizeof(WCHAR) <= nBufferLength)
|
||||
{
|
||||
LPWSTR p = lpBuffer;
|
||||
for (drive = 0; drive < MAX_DOS_DRIVES; drive++)
|
||||
if (DRIVE_IsValid(drive))
|
||||
{
|
||||
*p++ = (WCHAR)('A' + drive);
|
||||
*p++ = (WCHAR)':';
|
||||
*p++ = (WCHAR)'\\';
|
||||
*p++ = (WCHAR)'\0';
|
||||
}
|
||||
*p = (WCHAR)'\0';
|
||||
}
|
||||
return count * 4 * sizeof(WCHAR);
|
||||
}
|
||||
|
||||
|
||||
DWORD
|
||||
STDCALL
|
||||
GetLogicalDrives(VOID)
|
||||
{
|
||||
DWORD ret = 0;
|
||||
int drive;
|
||||
|
||||
for (drive = 0; drive < MAX_DOS_DRIVES; drive++)
|
||||
if (DRIVE_IsValid(drive)) ret |= (1 << drive);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
GetDiskFreeSpaceA(
|
||||
|
|
|
@ -3,7 +3,7 @@ all: kernel32.a
|
|||
SYNCH_OBJECTS = synch/critical.o synch/event.o synch/wait.o
|
||||
|
||||
MISC_OBJECTS = misc/error.o misc/atom.o misc/handle.o misc/env.o misc/dllmain.o \
|
||||
misc/console.o
|
||||
misc/console.o misc/time.o
|
||||
|
||||
FILE_OBJECTS = file/file.o file/curdir.o file/lfile.o file/dir.o \
|
||||
file/iocompl.o file/volume.o file/deviceio.o file/dosdev.o \
|
||||
|
|
|
@ -57,22 +57,72 @@ ReadConsoleA(
|
|||
LPVOID lpReserved
|
||||
)
|
||||
{
|
||||
return ReadFile(hConsoleInput,lpBuffer,nNumberOfCharsToRead,lpNumberOfCharsRead,lpReserved);
|
||||
KEY_EVENT_RECORD *k;
|
||||
OVERLAPPED Overlapped;
|
||||
OVERLAPPED * lpOverlapped;
|
||||
int kSize;
|
||||
int i,j;
|
||||
|
||||
if ( lpReserved == NULL ) {
|
||||
Overlapped.Internal = 0;
|
||||
Overlapped.InternalHigh = 0;
|
||||
Overlapped.Offset = 0;
|
||||
Overlapped.OffsetHigh = 0;
|
||||
// Overlapped.hEvent = CreateEvent(NULL,FALSE,TRUE,NULL);
|
||||
lpOverlapped = &Overlapped;
|
||||
}
|
||||
else
|
||||
lpOverlapped = lpReserved;
|
||||
|
||||
|
||||
kSize = nNumberOfCharsToRead*sizeof(kSize);
|
||||
k = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,kSize);
|
||||
if ( k == NULL || kSize == 0 )
|
||||
return FALSE;
|
||||
|
||||
k[0].AsciiChar = 0;
|
||||
while(k[0].AsciiChar == 0 )
|
||||
{
|
||||
ReadFile(hConsoleInput,k,kSize,lpNumberOfCharsRead,lpOverlapped);
|
||||
|
||||
}
|
||||
j = 0;
|
||||
i = 0;
|
||||
//if ( k[i].bKeyDown )
|
||||
{
|
||||
((char *)lpBuffer)[j] = k[i].AsciiChar;
|
||||
j++;
|
||||
}
|
||||
i++;
|
||||
while(j < nNumberOfCharsToRead && i < *lpNumberOfCharsRead ) {
|
||||
//if ( k[i].bKeyDown )
|
||||
{
|
||||
((char *)lpBuffer)[j] = k[i].AsciiChar;
|
||||
j++;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
|
||||
HeapFree(GetProcessHeap(),0,k);
|
||||
//if ( lpReserved == NULL ) {
|
||||
// CloseHandle(Overlapped.hEvent);
|
||||
//}
|
||||
|
||||
}
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
AllocConsole( VOID )
|
||||
{
|
||||
StdInput = CreateFile("\\Keyboard",
|
||||
StdInput = CreateFile("\\Device\\Keyboard",
|
||||
FILE_GENERIC_READ,
|
||||
0,
|
||||
NULL,
|
||||
OPEN_EXISTING,
|
||||
0,
|
||||
FILE_FLAG_OVERLAPPED,
|
||||
NULL);
|
||||
|
||||
StdOutput = CreateFile("\\BlueScreen",
|
||||
StdOutput = CreateFile("\\Device\\BlueScreen",
|
||||
FILE_GENERIC_WRITE|FILE_GENERIC_READ,
|
||||
0,
|
||||
NULL,
|
||||
|
@ -90,6 +140,8 @@ WINBOOL
|
|||
STDCALL
|
||||
FreeConsole( VOID )
|
||||
{
|
||||
CloseHandle(StdInput);
|
||||
CloseHandle(StdOutput);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
@ -123,9 +175,9 @@ SetConsoleCursorPosition(
|
|||
|
||||
if( !GetConsoleScreenBufferInfo(hConsoleOutput,&ConsoleScreenBufferInfo) )
|
||||
return FALSE;
|
||||
// ConsoleScreenBufferInfo.dwCursorPosition.X = dwCursorPosition.X;
|
||||
// ConsoleScreenBufferInfo.dwCursorPosition.Y = dwCursorPosition.Y;
|
||||
return TRUE;
|
||||
ConsoleScreenBufferInfo.dwCursorPosition.X = dwCursorPosition.X;
|
||||
ConsoleScreenBufferInfo.dwCursorPosition.Y = dwCursorPosition.Y;
|
||||
|
||||
if( !DeviceIoControl(
|
||||
hConsoleOutput,
|
||||
FSCTL_SET_CONSOLE_SCREEN_BUFFER_INFO,
|
||||
|
@ -164,5 +216,6 @@ FillConsoleOutputCharacterW(
|
|||
LPDWORD lpNumberOfCharsWritten
|
||||
)
|
||||
{
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
|
|
@ -233,59 +233,10 @@ GetVersionExA(
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
VOID GetSystemTime(
|
||||
LPSYSTEMTIME lpSystemTime
|
||||
)
|
||||
{
|
||||
NTSTATUS errCode;
|
||||
memset(lpSystemTime,sizeof(SYSTEMTIME),0);
|
||||
// errCode = NtQuerySystemTime (
|
||||
// (TIME *)lpSystemTime
|
||||
// );
|
||||
return;
|
||||
}
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
SetSystemTime(
|
||||
CONST SYSTEMTIME *lpSystemTime
|
||||
)
|
||||
{
|
||||
NTSTATUS errCode;
|
||||
LARGE_INTEGER NewSystemTime;
|
||||
errCode = NtSetSystemTime (
|
||||
(LARGE_INTEGER *)lpSystemTime,
|
||||
&NewSystemTime
|
||||
);
|
||||
if ( !NT_SUCCESS(errCode) )
|
||||
return FALSE;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
VOID
|
||||
STDCALL
|
||||
GetLocalTime(
|
||||
LPSYSTEMTIME lpSystemTime
|
||||
)
|
||||
{
|
||||
GetSystemTime(lpSystemTime);
|
||||
}
|
||||
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
SetLocalTime(
|
||||
CONST SYSTEMTIME *lpSystemTime
|
||||
)
|
||||
{
|
||||
return SetSystemTime(lpSystemTime);
|
||||
}
|
||||
|
||||
LPSTR
|
||||
STDCALL
|
||||
GetEnvironmentStringsA(
|
||||
|
|
501
reactos/lib/kernel32/misc/time.c
Normal file
501
reactos/lib/kernel32/misc/time.c
Normal file
|
@ -0,0 +1,501 @@
|
|||
/*
|
||||
* COPYRIGHT: See COPYING in the top level directory
|
||||
* PROJECT: ReactOS system libraries
|
||||
* FILE: lib/kernel32/misc/time.c
|
||||
* PURPOSE: Time conversion functions
|
||||
* PROGRAMMER: Boudewijn ( ariadne@xs4all.nl)
|
||||
DOSDATE and DOSTIME structures from Onno Hovers
|
||||
* UPDATE HISTORY:
|
||||
* Created 19/01/99
|
||||
*/
|
||||
#include <windows.h>
|
||||
#include <ddk/ntddk.h>
|
||||
|
||||
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;
|
||||
|
||||
#define NSPERSEC 10000000
|
||||
|
||||
#define SECOND 1
|
||||
#define MINUTE 60*SECOND
|
||||
#define HOUR 60*MINUTE
|
||||
#define DAY 24*HOUR
|
||||
#define YEAR (365*DAY)
|
||||
#define FOURYEAR (4*YEAR+DAY)
|
||||
#define CENTURY (25*FOURYEAR-DAY)
|
||||
#define MILLENIUM (100*CENTURY)
|
||||
|
||||
|
||||
#define LISECOND RtlEnlargedUnsignedMultiply(SECOND,NSPERSEC)
|
||||
#define LIMINUTE RtlEnlargedUnsignedMultiply(MINUTE,NSPERSEC)
|
||||
#define LIHOUR RtlEnlargedUnsignedMultiply(HOUR,NSPERSEC)
|
||||
#define LIDAY RtlEnlargedUnsignedMultiply(DAY,NSPERSEC)
|
||||
#define LIYEAR RtlEnlargedUnsignedMultiply(YEAR,NSPERSEC)
|
||||
#define LIFOURYEAR RtlEnlargedUnsignedMultiply(FOURYEAR,NSPERSEC)
|
||||
#define LICENTURY RtlEnlargedUnsignedMultiply(CENTURY,NSPERSEC)
|
||||
#define LIMILLENIUM RtlEnlargedUnsignedMultiply(CENTURY,10*NSPERSEC)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
FileTimeToDosDateTime(
|
||||
CONST FILETIME *lpFileTime,
|
||||
LPWORD lpFatDate,
|
||||
LPWORD lpFatTime
|
||||
)
|
||||
{
|
||||
|
||||
PDOSTIME pdtime=(PDOSTIME) lpFatTime;
|
||||
PDOSDATE pddate=(PDOSDATE) lpFatDate;
|
||||
SYSTEMTIME SystemTime;
|
||||
|
||||
if ( lpFileTime == NULL )
|
||||
return FALSE;
|
||||
|
||||
if ( lpFatDate == NULL )
|
||||
return FALSE;
|
||||
|
||||
if ( lpFatTime == NULL )
|
||||
return FALSE;
|
||||
|
||||
FileTimeToSystemTime(
|
||||
lpFileTime,
|
||||
&SystemTime
|
||||
);
|
||||
|
||||
pdtime->Second = SystemTime.wSecond;
|
||||
pdtime->Minute = SystemTime.wMinute;
|
||||
pdtime->Hour = SystemTime.wHour;
|
||||
|
||||
|
||||
pddate->Day = SystemTime.wDay;
|
||||
pddate->Month = SystemTime.wMonth;
|
||||
pddate->Year = SystemTime.wYear - 1980;
|
||||
|
||||
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
DosDateTimeToFileTime(
|
||||
WORD wFatDate,
|
||||
WORD wFatTime,
|
||||
LPFILETIME lpFileTime
|
||||
)
|
||||
{
|
||||
|
||||
PDOSTIME pdtime = (PDOSTIME) &wFatTime;
|
||||
PDOSDATE pddate = (PDOSDATE) &wFatDate;
|
||||
SYSTEMTIME SystemTime;
|
||||
|
||||
if ( lpFileTime == NULL )
|
||||
return FALSE;
|
||||
|
||||
|
||||
|
||||
SystemTime.wMilliseconds = 0;
|
||||
SystemTime.wSecond = pdtime->Second;
|
||||
SystemTime.wMinute = pdtime->Minute;
|
||||
SystemTime.wHour = pdtime->Hour;
|
||||
|
||||
|
||||
SystemTime.wDay = pddate->Day;
|
||||
SystemTime.wMonth = pddate->Month;
|
||||
SystemTime.wYear = 1980 + pddate->Year;
|
||||
|
||||
SystemTimeToFileTime(&SystemTime,lpFileTime);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
LONG
|
||||
STDCALL
|
||||
CompareFileTime(
|
||||
CONST FILETIME *lpFileTime1,
|
||||
CONST FILETIME *lpFileTime2
|
||||
)
|
||||
{
|
||||
|
||||
if ( lpFileTime1 == NULL )
|
||||
return 0;
|
||||
if ( lpFileTime2 == NULL )
|
||||
return 0;
|
||||
/*
|
||||
if ((GET_LARGE_INTEGER_HIGH_PART(lpFileTime1)) > (GET_LARGE_INTEGER_HIGH_PART(lpFileTime2)) )
|
||||
return 1;
|
||||
else if ((GET_LARGE_INTEGER_HIGH_PART(lpFileTime1)) < (GET_LARGE_INTEGER_HIGH_PART(lpFileTime2)))
|
||||
return -1;
|
||||
else if ((GET_LARGE_INTEGER_LOW_PART(lpFileTime1)) > (GET_LARGE_INTEGER_LOW_PART(lpFileTime2)))
|
||||
return 1;
|
||||
else if ((GET_LARGE_INTEGER_LOW_PART(lpFileTime1)) < (GET_LARGE_INTEGER_LOW_PART(lpFileTime2)))
|
||||
return -1;
|
||||
else
|
||||
return 0;
|
||||
|
||||
*/
|
||||
}
|
||||
|
||||
VOID
|
||||
STDCALL
|
||||
GetSystemTimeAsFileTime(PFILETIME lpFileTime)
|
||||
{
|
||||
NTSTATUS errCode;
|
||||
|
||||
errCode = NtQuerySystemTime (
|
||||
(TIME *)lpFileTime
|
||||
);
|
||||
return;
|
||||
}
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
SystemTimeToFileTime(
|
||||
CONST SYSTEMTIME * lpSystemTime,
|
||||
LPFILETIME lpFileTime
|
||||
)
|
||||
|
||||
{
|
||||
|
||||
|
||||
LARGE_INTEGER FileTime;
|
||||
LARGE_INTEGER Year;
|
||||
LARGE_INTEGER Month;
|
||||
LARGE_INTEGER Day;
|
||||
LARGE_INTEGER Hour;
|
||||
LARGE_INTEGER Minute;
|
||||
LARGE_INTEGER Second;
|
||||
LARGE_INTEGER Milliseconds;
|
||||
DWORD LeapDay = 0;
|
||||
DWORD dwMonthDays = 0;
|
||||
|
||||
if ( (lpSystemTime->wYear % 4 == 0 && lpSystemTime->wYear % 100 != 0) || lpSystemTime->wYear % 400 == 0)
|
||||
LeapDay = 1;
|
||||
else
|
||||
LeapDay = 0;
|
||||
|
||||
|
||||
Year = RtlEnlargedIntegerMultiply(lpSystemTime->wYear - 1601,YEAR);
|
||||
if ( lpSystemTime->wMonth > 1)
|
||||
dwMonthDays = 31;
|
||||
if ( lpSystemTime->wMonth > 2)
|
||||
dwMonthDays += ( 28 + LeapDay );
|
||||
if ( lpSystemTime->wMonth > 3)
|
||||
dwMonthDays += 31;
|
||||
if ( lpSystemTime->wMonth > 4)
|
||||
dwMonthDays += 30;
|
||||
if ( lpSystemTime->wMonth > 5)
|
||||
dwMonthDays += 31;
|
||||
if ( lpSystemTime->wMonth > 6)
|
||||
dwMonthDays += 30;
|
||||
if ( lpSystemTime->wMonth > 7)
|
||||
dwMonthDays += 31;
|
||||
if ( lpSystemTime->wMonth > 8)
|
||||
dwMonthDays += 31;
|
||||
if ( lpSystemTime->wMonth > 9)
|
||||
dwMonthDays += 30;
|
||||
if ( lpSystemTime->wMonth > 10)
|
||||
dwMonthDays += 31;
|
||||
if ( lpSystemTime->wMonth > 11)
|
||||
dwMonthDays += 30;
|
||||
|
||||
Month = RtlEnlargedIntegerMultiply(dwMonthDays,DAY);
|
||||
|
||||
Day = RtlEnlargedIntegerMultiply(lpSystemTime->wDay,DAY);
|
||||
|
||||
Hour = RtlEnlargedIntegerMultiply(lpSystemTime->wHour,HOUR);
|
||||
Minute = RtlEnlargedIntegerMultiply(lpSystemTime->wMinute,MINUTE);
|
||||
Second = RtlEnlargedIntegerMultiply(lpSystemTime->wSecond,DAY);
|
||||
|
||||
Milliseconds = RtlEnlargedIntegerMultiply(lpSystemTime->wMilliseconds,10000);
|
||||
|
||||
FileTime += RtlLargeIntegerAdd(FileTime,Year);
|
||||
FileTime += RtlLargeIntegerAdd(FileTime,Month);
|
||||
FileTime += RtlLargeIntegerAdd(FileTime,Day);
|
||||
FileTime += RtlLargeIntegerAdd(FileTime,Hour);
|
||||
FileTime += RtlLargeIntegerAdd(FileTime,Minute);
|
||||
FileTime += RtlLargeIntegerAdd(FileTime,Second);
|
||||
|
||||
FileTime = RtlExtendedIntegerMultiply(FileTime,NSPERSEC);
|
||||
|
||||
FileTime = RtlLargeIntegerAdd(FileTime,Milliseconds);
|
||||
|
||||
memcpy(lpFileTime,&FileTime,sizeof(FILETIME));
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
FileTimeToSystemTime(
|
||||
CONST FILETIME *lpFileTime,
|
||||
LPSYSTEMTIME lpSystemTime
|
||||
)
|
||||
{
|
||||
|
||||
|
||||
LARGE_INTEGER FileTime;
|
||||
|
||||
LARGE_INTEGER dwMillenium;
|
||||
LARGE_INTEGER dwRemMillenium;
|
||||
|
||||
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;
|
||||
|
||||
|
||||
DWORD LeapDay = 0;
|
||||
|
||||
|
||||
memcpy(&FileTime,lpFileTime,sizeof(FILETIME));
|
||||
|
||||
|
||||
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) GET_LARGE_INTEGER_LOW_PART(dwHour);
|
||||
lpSystemTime->wMinute= (WORD)GET_LARGE_INTEGER_LOW_PART(dwMinute);
|
||||
lpSystemTime->wSecond= (WORD)GET_LARGE_INTEGER_LOW_PART(dwSecond);
|
||||
lpSystemTime->wMilliseconds = (WORD)(GET_LARGE_INTEGER_LOW_PART(dwRemSecond)/10000);
|
||||
|
||||
|
||||
if ( lpSystemTime->wSecond > 60 ) {
|
||||
lpSystemTime->wSecond -= 60;
|
||||
lpSystemTime->wMinute ++;
|
||||
}
|
||||
|
||||
if ( lpSystemTime->wMinute > 60 ) {
|
||||
lpSystemTime->wMinute -= 60;
|
||||
lpSystemTime->wHour ++;
|
||||
}
|
||||
|
||||
if (lpSystemTime->wHour > 24 ) {
|
||||
lpSystemTime->wHour-= 24;
|
||||
SET_LARGE_INTEGER_LOW_PART(dwDay,GET_LARGE_INTEGER_LOW_PART(dwDay)+1);
|
||||
}
|
||||
|
||||
//FIXME since 1972 some years have a leap second [ aprox 15 out of 20 ]
|
||||
|
||||
// if leap year
|
||||
lpSystemTime->wYear= 1601 + 1000* (LONG)GET_LARGE_INTEGER_LOW_PART(dwMillenium) + 100 * (LONG)GET_LARGE_INTEGER_LOW_PART(dwCentury) + 4*(LONG)GET_LARGE_INTEGER_LOW_PART(dwFourYear) + (LONG)GET_LARGE_INTEGER_LOW_PART(dwYear);
|
||||
|
||||
if ( (lpSystemTime->wYear % 4 == 0 && lpSystemTime->wYear % 100 != 0) || lpSystemTime->wYear % 400 == 0)
|
||||
LeapDay = 1;
|
||||
else
|
||||
LeapDay = 0;
|
||||
|
||||
|
||||
|
||||
if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= 0 && GET_LARGE_INTEGER_LOW_PART(dwDay) < 31 ) {
|
||||
lpSystemTime->wMonth = 1;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1;
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= 31 && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 59 + LeapDay )) {
|
||||
lpSystemTime->wMonth = 2;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - 31;
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= ( 59 + LeapDay ) && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 90 + LeapDay ) ) {
|
||||
lpSystemTime->wMonth = 3;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - ( 59 + LeapDay);
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= 90+ LeapDay && GET_LARGE_INTEGER_LOW_PART(dwDay) < 120 + LeapDay) {
|
||||
lpSystemTime->wMonth = 4;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - (31 + LeapDay );
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= 120 + LeapDay && GET_LARGE_INTEGER_LOW_PART(dwDay) < 151 + LeapDay ) {
|
||||
lpSystemTime->wMonth = 5;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - (120 + LeapDay);
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= ( 151 + LeapDay) && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 181 + LeapDay ) ) {
|
||||
lpSystemTime->wMonth = 6;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - ( 151 + LeapDay );
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= ( 181 + LeapDay ) && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 212 + LeapDay ) ) {
|
||||
lpSystemTime->wMonth = 7;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - ( 181 + LeapDay );
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= ( 212 + LeapDay ) && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 243 + LeapDay ) ) {
|
||||
lpSystemTime->wMonth = 8;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - (212 + LeapDay );
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= ( 243+ LeapDay ) && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 273 + LeapDay ) ) {
|
||||
lpSystemTime->wMonth = 9;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - ( 243 + LeapDay );
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= ( 273 + LeapDay ) && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 304 + LeapDay ) ) {
|
||||
lpSystemTime->wMonth = 10;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - ( 273 + LeapDay);
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= ( 304 + LeapDay ) && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 334 + LeapDay ) ) {
|
||||
lpSystemTime->wMonth = 11;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - ( 304 + LeapDay );
|
||||
}
|
||||
else if ( GET_LARGE_INTEGER_LOW_PART(dwDay) >= ( 334 + LeapDay ) && GET_LARGE_INTEGER_LOW_PART(dwDay) < ( 365 + LeapDay )) {
|
||||
lpSystemTime->wMonth = 12;
|
||||
lpSystemTime->wDay = GET_LARGE_INTEGER_LOW_PART(dwDay) + 1 - ( 334 + LeapDay );
|
||||
}
|
||||
|
||||
|
||||
dwDayOfWeek = RtlLargeIntegerDivide(FileTime,LIDAY,&dwRemDay);
|
||||
lpSystemTime->wDayOfWeek = 1 + GET_LARGE_INTEGER_LOW_PART(dwDayOfWeek) % 7;
|
||||
|
||||
|
||||
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
FileTimeToLocalFileTime(
|
||||
CONST FILETIME *lpFileTime,
|
||||
LPFILETIME lpLocalFileTime
|
||||
)
|
||||
{
|
||||
// memcpy(lpLocalFileTime,lpFileTime,sizeof(FILETIME));
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
LocalFileTimeToFileTime(
|
||||
CONST FILETIME *lpLocalFileTime,
|
||||
LPFILETIME lpFileTime
|
||||
)
|
||||
{
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
VOID
|
||||
STDCALL
|
||||
GetLocalTime(
|
||||
LPSYSTEMTIME lpSystemTime
|
||||
)
|
||||
{
|
||||
GetSystemTime(lpSystemTime);
|
||||
return;
|
||||
}
|
||||
|
||||
VOID
|
||||
STDCALL
|
||||
GetSystemTime(
|
||||
LPSYSTEMTIME lpSystemTime
|
||||
)
|
||||
{
|
||||
FILETIME FileTime;
|
||||
GetSystemTimeAsFileTime(&FileTime);
|
||||
FileTimeToSystemTime(&FileTime,lpSystemTime);
|
||||
return;
|
||||
}
|
||||
|
||||
WINBOOL
|
||||
STDCALL
|
||||
SetLocalTime(
|
||||
CONST SYSTEMTIME *lpSystemTime
|
||||
)
|
||||
{
|
||||
return SetSystemTime(lpSystemTime);
|
||||
}
|
||||
WINBOOL
|
||||
STDCALL
|
||||
SetSystemTime(
|
||||
CONST SYSTEMTIME *lpSystemTime
|
||||
)
|
||||
{
|
||||
NTSTATUS errCode;
|
||||
LARGE_INTEGER NewSystemTime;
|
||||
|
||||
SystemTimeToFileTime(lpSystemTime, (FILETIME *)&NewSystemTime);
|
||||
errCode = NtSetSystemTime (&NewSystemTime,&NewSystemTime);
|
||||
if ( !NT_SUCCESS(errCode) )
|
||||
return FALSE;
|
||||
return TRUE;
|
||||
|
||||
}
|
||||
/*
|
||||
typedef struct _TIME_ZONE_INFORMATION { // tzi
|
||||
LONG Bias;
|
||||
WCHAR StandardName[ 32 ];
|
||||
SYSTEMTIME StandardDate;
|
||||
LONG StandardBias;
|
||||
WCHAR DaylightName[ 32 ];
|
||||
SYSTEMTIME DaylightDate;
|
||||
LONG DaylightBias;
|
||||
} TIME_ZONE_INFORMATION;
|
||||
TIME_ZONE_INFORMATION TimeZoneInformation = {60,"CET",;
|
||||
|
||||
*/
|
||||
DWORD
|
||||
STDCALL
|
||||
GetTimeZoneInformation(
|
||||
LPTIME_ZONE_INFORMATION lpTimeZoneInformation
|
||||
)
|
||||
{
|
||||
// aprintf("GetTimeZoneInformation()\n");
|
||||
|
||||
// memset(lpTimeZoneInformation, 0, sizeof(TIME_ZONE_INFORMATION));
|
||||
|
||||
return TIME_ZONE_ID_UNKNOWN;
|
||||
}
|
||||
|
||||
DWORD
|
||||
STDCALL
|
||||
GetCurrentTime(VOID)
|
||||
{
|
||||
return GetTickCount();
|
||||
}
|
||||
|
||||
DWORD
|
||||
STDCALL
|
||||
GetTickCount(VOID)
|
||||
{
|
||||
ULONG UpTime;
|
||||
NtGetTickCount(&UpTime);
|
||||
return UpTime;
|
||||
}
|
Loading…
Reference in a new issue