wait.c
来自「一个类似windows」· C语言 代码 · 共 310 行
C
310 行
/* $Id: wait.c 21253 2006-03-08 21:33:04Z audit $
*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS system libraries
* FILE: lib/kernel32/synch/wait.c
* PURPOSE: Wait functions
* PROGRAMMER: Ariadne ( ariadne@xs4all.nl)
* UPDATE HISTORY:
* Created 01/11/98
*/
/* INCLUDES *****************************************************************/
#include <k32.h>
#define NDEBUG
#include "../include/debug.h"
/* FUNCTIONS ****************************************************************/
DWORD STDCALL
GetConsoleInputWaitHandle (VOID);
/*
* @implemented
*/
DWORD STDCALL
WaitForSingleObject(HANDLE hHandle,
DWORD dwMilliseconds)
{
return WaitForSingleObjectEx(hHandle,
dwMilliseconds,
FALSE);
}
/*
* @implemented
*/
DWORD STDCALL
WaitForSingleObjectEx(HANDLE hHandle,
DWORD dwMilliseconds,
BOOL bAlertable)
{
PLARGE_INTEGER TimePtr;
LARGE_INTEGER Time;
NTSTATUS Status;
/* Get real handle */
switch ((ULONG)hHandle)
{
case STD_INPUT_HANDLE:
hHandle = NtCurrentPeb()->ProcessParameters->StandardInput;
break;
case STD_OUTPUT_HANDLE:
hHandle = NtCurrentPeb()->ProcessParameters->StandardOutput;
break;
case STD_ERROR_HANDLE:
hHandle = NtCurrentPeb()->ProcessParameters->StandardError;
break;
}
/* Check for console handle */
if (IsConsoleHandle(hHandle))
{
if (!VerifyConsoleIoHandle(hHandle))
{
SetLastError (ERROR_INVALID_HANDLE);
return WAIT_FAILED;
}
hHandle = (HANDLE)GetConsoleInputWaitHandle();
if (hHandle == NULL || hHandle == INVALID_HANDLE_VALUE)
{
SetLastError (ERROR_INVALID_HANDLE);
return WAIT_FAILED;
}
}
if (dwMilliseconds == INFINITE)
{
TimePtr = NULL;
}
else
{
Time.QuadPart = -10000 * (LONGLONG)dwMilliseconds;
TimePtr = &Time;
}
do
{
Status = NtWaitForSingleObject(hHandle,
(BOOLEAN) bAlertable,
TimePtr);
if (HIWORD(Status))
{
SetLastErrorByStatus (Status);
return WAIT_FAILED;
}
} while (Status == STATUS_ALERTED && bAlertable);
return Status;
}
/*
* @implemented
*/
DWORD STDCALL
WaitForMultipleObjects(DWORD nCount,
CONST HANDLE *lpHandles,
BOOL bWaitAll,
DWORD dwMilliseconds)
{
return WaitForMultipleObjectsEx(nCount,
lpHandles,
bWaitAll,
dwMilliseconds,
FALSE);
}
/*
* @implemented
*/
DWORD STDCALL
WaitForMultipleObjectsEx(DWORD nCount,
CONST HANDLE *lpHandles,
BOOL bWaitAll,
DWORD dwMilliseconds,
BOOL bAlertable)
{
PLARGE_INTEGER TimePtr;
LARGE_INTEGER Time;
PHANDLE HandleBuffer;
HANDLE Handle[3];
DWORD i;
NTSTATUS Status;
DPRINT("nCount %lu\n", nCount);
if (nCount > 3)
{
HandleBuffer = RtlAllocateHeap(RtlGetProcessHeap(), 0, nCount * sizeof(HANDLE));
if (HandleBuffer == NULL)
{
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
return WAIT_FAILED;
}
}
else
{
HandleBuffer = Handle;
}
for (i = 0; i < nCount; i++)
{
switch ((DWORD)lpHandles[i])
{
case STD_INPUT_HANDLE:
HandleBuffer[i] = NtCurrentPeb()->ProcessParameters->StandardInput;
break;
case STD_OUTPUT_HANDLE:
HandleBuffer[i] = NtCurrentPeb()->ProcessParameters->StandardOutput;
break;
case STD_ERROR_HANDLE:
HandleBuffer[i] = NtCurrentPeb()->ProcessParameters->StandardError;
break;
default:
HandleBuffer[i] = lpHandles[i];
break;
}
/* Check for console handle */
if (IsConsoleHandle(HandleBuffer[i]))
{
if (!VerifyConsoleIoHandle(HandleBuffer[i]))
{
if (HandleBuffer != Handle)
{
RtlFreeHeap(GetProcessHeap(),0,HandleBuffer);
}
SetLastError (ERROR_INVALID_HANDLE);
return WAIT_FAILED;
}
HandleBuffer[i] = (HANDLE)GetConsoleInputWaitHandle();
if (HandleBuffer[i] == NULL || HandleBuffer[i] == INVALID_HANDLE_VALUE)
{
if (HandleBuffer != Handle)
{
RtlFreeHeap(GetProcessHeap(),0,HandleBuffer);
}
SetLastError (ERROR_INVALID_HANDLE);
return WAIT_FAILED;
}
}
}
if (dwMilliseconds == INFINITE)
{
TimePtr = NULL;
}
else
{
Time.QuadPart = -10000 * (LONGLONG)dwMilliseconds;
TimePtr = &Time;
}
do
{
Status = NtWaitForMultipleObjects (nCount,
HandleBuffer,
bWaitAll ? WaitAll : WaitAny,
(BOOLEAN)bAlertable,
TimePtr);
if (HIWORD(Status))
{
SetLastErrorByStatus (Status);
Status = WAIT_FAILED;
}
} while (Status == STATUS_ALERTED && bAlertable);
if (HandleBuffer != Handle)
{
RtlFreeHeap(RtlGetProcessHeap(), 0, HandleBuffer);
}
return Status;
}
/*
* @implemented
*/
DWORD STDCALL
SignalObjectAndWait(HANDLE hObjectToSignal,
HANDLE hObjectToWaitOn,
DWORD dwMilliseconds,
BOOL bAlertable)
{
PLARGE_INTEGER TimePtr;
LARGE_INTEGER Time;
NTSTATUS Status;
/* Get real handle */
switch ((ULONG)hObjectToWaitOn)
{
case STD_INPUT_HANDLE:
hObjectToWaitOn = NtCurrentPeb()->ProcessParameters->StandardInput;
break;
case STD_OUTPUT_HANDLE:
hObjectToWaitOn = NtCurrentPeb()->ProcessParameters->StandardOutput;
break;
case STD_ERROR_HANDLE:
hObjectToWaitOn = NtCurrentPeb()->ProcessParameters->StandardError;
break;
}
/* Check for console handle */
if (IsConsoleHandle(hObjectToWaitOn))
{
if (VerifyConsoleIoHandle(hObjectToWaitOn))
{
DPRINT1("Console handles are not supported yet!\n");
SetLastError(ERROR_INVALID_HANDLE);
return WAIT_FAILED;
}
}
if (dwMilliseconds == INFINITE)
{
TimePtr = NULL;
}
else
{
Time.QuadPart = -10000 * (LONGLONG)dwMilliseconds;
TimePtr = &Time;
}
do
{
Status = NtSignalAndWaitForSingleObject (hObjectToSignal,
hObjectToWaitOn,
(BOOLEAN)bAlertable,
TimePtr);
if (!NT_SUCCESS(Status))
{
SetLastErrorByStatus (Status);
return WAIT_FAILED;
}
} while (Status == STATUS_ALERTED && bAlertable);
/* STATUS_SUCCESS maps to WAIT_OBJECT_0 */
return Status;
}
/* EOF */
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?