ReactOS  0.4.14-dev-50-g13bb5e2
obwait.c File Reference
#include <ntoskrnl.h>
#include <debug.h>
Include dependency graph for obwait.c:

Go to the source code of this file.

Macros

#define NDEBUG
 

Functions

NTSTATUS NTAPI NtWaitForMultipleObjects (IN ULONG ObjectCount, IN PHANDLE HandleArray, IN WAIT_TYPE WaitType, IN BOOLEAN Alertable, IN PLARGE_INTEGER TimeOut OPTIONAL)
 
NTSTATUS NTAPI NtWaitForMultipleObjects32 (IN ULONG ObjectCount, IN PLONG Handles, IN WAIT_TYPE WaitType, IN BOOLEAN Alertable, IN PLARGE_INTEGER TimeOut OPTIONAL)
 
NTSTATUS NTAPI NtWaitForSingleObject (IN HANDLE ObjectHandle, IN BOOLEAN Alertable, IN PLARGE_INTEGER TimeOut OPTIONAL)
 
NTSTATUS NTAPI NtSignalAndWaitForSingleObject (IN HANDLE ObjectHandleToSignal, IN HANDLE WaitableObjectHandle, IN BOOLEAN Alertable, IN PLARGE_INTEGER TimeOut OPTIONAL)
 

Macro Definition Documentation

◆ NDEBUG

#define NDEBUG

Definition at line 13 of file obwait.c.

Function Documentation

◆ NtSignalAndWaitForSingleObject()

NTSTATUS NTAPI NtSignalAndWaitForSingleObject ( IN HANDLE  ObjectHandleToSignal,
IN HANDLE  WaitableObjectHandle,
IN BOOLEAN  Alertable,
IN PLARGE_INTEGER TimeOut  OPTIONAL 
)

Definition at line 473 of file obwait.c.

477 {
480  PVOID SignalObj, WaitObj, WaitableObject;
481  LARGE_INTEGER SafeTimeOut;
482  OBJECT_HANDLE_INFORMATION HandleInfo;
484 
485  /* Check if we came with a timeout from user mode */
487  if ((TimeOut) && (PreviousMode != KernelMode))
488  {
489  /* Enter SEH for probing */
490  _SEH2_TRY
491  {
492  /* Make a copy on the stack */
493  SafeTimeOut = ProbeForReadLargeInteger(TimeOut);
494  TimeOut = &SafeTimeOut;
495  }
497  {
498  /* Return the exception code */
500  }
501  _SEH2_END;
502  }
503 
504  /* Start by getting the signal object*/
505  Status = ObReferenceObjectByHandle(ObjectHandleToSignal,
506  0,
507  NULL,
508  PreviousMode,
509  &SignalObj,
510  &HandleInfo);
511  if (!NT_SUCCESS(Status)) return Status;
512 
513  /* Now get the wait object */
514  Status = ObReferenceObjectByHandle(WaitableObjectHandle,
515  SYNCHRONIZE,
516  NULL,
517  PreviousMode,
518  &WaitObj,
519  NULL);
520  if (!NT_SUCCESS(Status))
521  {
522  /* Failed to reference the wait object */
523  ObDereferenceObject(SignalObj);
524  return Status;
525  }
526 
527  /* Get the real waitable object */
528  WaitableObject = OBJECT_TO_OBJECT_HEADER(WaitObj)->Type->DefaultObject;
529 
530  /* Handle internal offset */
531  if (IsPointerOffset(WaitableObject))
532  {
533  /* Get real pointer */
534  WaitableObject = (PVOID)((ULONG_PTR)WaitObj +
535  (ULONG_PTR)WaitableObject);
536  }
537 
538  /* Check Signal Object Type */
539  Type = OBJECT_TO_OBJECT_HEADER(SignalObj)->Type;
540  if (Type == ExEventObjectType)
541  {
542  /* Check if we came from user-mode without the right access */
543  if ((PreviousMode != KernelMode) &&
544  !(HandleInfo.GrantedAccess & EVENT_MODIFY_STATE))
545  {
546  /* Fail: lack of rights */
548  goto Quickie;
549  }
550 
551  /* Set the Event */
552  KeSetEvent(SignalObj, EVENT_INCREMENT, TRUE);
553  }
554  else if (Type == ExMutantObjectType)
555  {
556  /* This can raise an exception */
557  _SEH2_TRY
558  {
559  /* Release the mutant */
561  }
566  {
567  /* Get the exception code */
569  }
570  _SEH2_END;
571  }
572  else if (Type == ExSemaphoreObjectType)
573  {
574  /* Check if we came from user-mode without the right access */
575  if ((PreviousMode != KernelMode) &&
576  !(HandleInfo.GrantedAccess & SEMAPHORE_MODIFY_STATE))
577  {
578  /* Fail: lack of rights */
580  goto Quickie;
581  }
582 
583  /* This can raise an exception*/
584  _SEH2_TRY
585  {
586  /* Release the semaphore */
588  }
592  {
593  /* Get the exception code */
595  }
596  _SEH2_END;
597  }
598  else
599  {
600  /* This isn't a valid object to be waiting on */
602  }
603 
604  /* Make sure we didn't fail */
605  if (NT_SUCCESS(Status))
606  {
607  /* SEH this since it can also raise an exception */
608  _SEH2_TRY
609  {
610  /* Perform the wait now */
611  Status = KeWaitForSingleObject(WaitableObject,
612  UserRequest,
613  PreviousMode,
614  Alertable,
615  TimeOut);
616  }
620  {
621  /* Get the exception code */
623  }
624  _SEH2_END;
625  }
626 
627  /* We're done here, dereference both objects */
628 Quickie:
629  ObDereferenceObject(SignalObj);
630  ObDereferenceObject(WaitObj);
631  return Status;
632 }
_In_ PVOID _In_ BOOLEAN Alertable
Definition: exfuncs.h:452
#define TRUE
Definition: types.h:120
Type
Definition: Type.h:6
#define STATUS_SEMAPHORE_LIMIT_EXCEEDED
Definition: ntstatus.h:293
LONG NTSTATUS
Definition: precomp.h:26
#define SEMAPHORE_MODIFY_STATE
Definition: winbase.h:161
KPROCESSOR_MODE NTAPI ExGetPreviousMode(VOID)
Definition: sysinfo.c:3066
VOID NTAPI ObDereferenceObject(IN PVOID Object)
Definition: obref.c:375
LONG NTAPI KeSetEvent(IN PKEVENT Event, IN KPRIORITY Increment, IN BOOLEAN Wait)
Definition: eventobj.c:159
NTSTATUS NTAPI KeWaitForSingleObject(IN PVOID Object, IN KWAIT_REASON WaitReason, IN KPROCESSOR_MODE WaitMode, IN BOOLEAN Alertable, IN PLARGE_INTEGER Timeout OPTIONAL)
Definition: wait.c:416
#define STATUS_MUTANT_NOT_OWNED
Definition: ntstatus.h:292
POBJECT_TYPE ExEventObjectType
Definition: event.c:22
_SEH2_TRY
Definition: create.c:4250
uint32_t ULONG_PTR
Definition: typedefs.h:63
#define OBJECT_TO_OBJECT_HEADER(o)
Definition: obtypes.h:111
#define ExMutantObjectType
Definition: ObTypes.c:127
#define EXCEPTION_CONTINUE_SEARCH
Definition: excpt.h:86
NTSTATUS NTAPI ObReferenceObjectByHandle(IN HANDLE Handle, IN ACCESS_MASK DesiredAccess, IN POBJECT_TYPE ObjectType, IN KPROCESSOR_MODE AccessMode, OUT PVOID *Object, OUT POBJECT_HANDLE_INFORMATION HandleInformation OPTIONAL)
Definition: obref.c:496
ACCESS_MASK GrantedAccess
Definition: iotypes.h:158
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
smooth NULL
Definition: ftsmooth.c:416
void * PVOID
Definition: retypes.h:9
_In_ KPROCESSOR_MODE PreviousMode
Definition: sefuncs.h:103
#define STATUS_OBJECT_TYPE_MISMATCH
Definition: ntstatus.h:259
#define _SEH2_YIELD(STMT_)
Definition: pseh2_64.h:8
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define STATUS_ACCESS_DENIED
Definition: udferr_usr.h:145
#define ProbeForReadLargeInteger(Ptr)
Definition: probe.h:75
CCHAR KPROCESSOR_MODE
Definition: ketypes.h:7
#define MUTANT_INCREMENT
Definition: extypes.h:84
LONG NTAPI KeReleaseMutant(IN PKMUTANT Mutant, IN KPRIORITY Increment, IN BOOLEAN Abandon, IN BOOLEAN Wait)
Definition: mutex.c:98
#define SYNCHRONIZE
Definition: nt_native.h:61
Status
Definition: gdiplustypes.h:24
_SEH2_END
Definition: create.c:4424
#define EVENT_INCREMENT
Definition: iotypes.h:565
LONG NTAPI KeReleaseSemaphore(IN PKSEMAPHORE Semaphore, IN KPRIORITY Increment, IN LONG Adjustment, IN BOOLEAN Wait)
Definition: semphobj.c:54
#define SEMAPHORE_INCREMENT
Definition: iotypes.h:578
#define EVENT_MODIFY_STATE
Definition: winbase.h:163
#define ULONG_PTR
Definition: config.h:101
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:6
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:12
#define STATUS_ABANDONED
Definition: ntstatus.h:75
#define STATUS_MUTANT_LIMIT_EXCEEDED
Definition: ntstatus.h:620
POBJECT_TYPE ExSemaphoreObjectType
Definition: sem.c:22

Referenced by SignalObjectAndWait().

◆ NtWaitForMultipleObjects()

NTSTATUS NTAPI NtWaitForMultipleObjects ( IN ULONG  ObjectCount,
IN PHANDLE  HandleArray,
IN WAIT_TYPE  WaitType,
IN BOOLEAN  Alertable,
IN PLARGE_INTEGER TimeOut  OPTIONAL 
)

Definition at line 46 of file obwait.c.

51 {
54  PVOID Objects[MAXIMUM_WAIT_OBJECTS];
55  PVOID WaitObjects[MAXIMUM_WAIT_OBJECTS];
56  ULONG i, ReferencedObjects, j;
58  LARGE_INTEGER SafeTimeOut;
59  BOOLEAN LockInUse;
60  PHANDLE_TABLE_ENTRY HandleEntry;
61  POBJECT_HEADER ObjectHeader;
64  PVOID DefaultObject;
66  PAGED_CODE();
67 
68  /* Check for valid Object Count */
70  {
71  /* Fail */
73  }
74 
75  /* Check for valid Wait Type */
76  if ((WaitType != WaitAll) && (WaitType != WaitAny))
77  {
78  /* Fail */
80  }
81 
82  /* Enter SEH */
84  _SEH2_TRY
85  {
86  /* Probe for user mode */
87  if (PreviousMode != KernelMode)
88  {
89  /* Check if we have a timeout */
90  if (TimeOut)
91  {
92  /* Make a local copy of the timeout on the stack */
93  SafeTimeOut = ProbeForReadLargeInteger(TimeOut);
94  TimeOut = &SafeTimeOut;
95  }
96 
97  /* Probe all the handles */
98  ProbeForRead(HandleArray,
99  ObjectCount * sizeof(HANDLE),
100  sizeof(HANDLE));
101  }
102 
103  /*
104  * Make a copy so we don't have to guard with SEH later and keep
105  * track of what objects we referenced if dereferencing pointers
106  * suddenly fails
107  */
108  RtlCopyMemory(Handles,
109  HandleArray,
110  ObjectCount * sizeof(HANDLE));
111  }
112  _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) //ExSystemExceptionFilter()
113  {
114  /* Cover up for kernel mode */
115  if (PreviousMode == KernelMode)
116  {
117  /* But don't fail silently */
118  DbgPrint("Mon dieu! Covering up for BAD driver passing invalid pointer (0x%p)! Hon hon hon!\n", HandleArray);
119  }
120 
121  /* Return the exception code */
123  }
124  _SEH2_END;
125 
126  /* Check if we can use the internal Wait Array */
128  {
129  /* Allocate from Pool */
131  ObjectCount *
132  sizeof(KWAIT_BLOCK),
133  TAG_WAIT);
134  if (!WaitBlockArray)
135  {
136  /* Fail */
138  }
139  }
140  else
141  {
142  /* No need for the array */
143  WaitBlockArray = NULL;
144  }
145 
146  /* Enter a critical region since we'll play with handles */
147  LockInUse = TRUE;
149 
150  /* Start the loop */
151  i = 0;
152  ReferencedObjects = 0;
153  do
154  {
155  /* Use the right Executive Handle */
156  if (ObpIsKernelHandle(Handles[i], PreviousMode))
157  {
158  /* Use the System Handle Table and decode */
161 
162  /* Get a pointer to it */
164  }
165  else
166  {
167  /* Use the Process' Handle table and get the Ex Handle */
168  HandleTable = PsGetCurrentProcess()->ObjectTable;
169 
170  /* Get a pointer to it */
171  HandleEntry = ExMapHandleToPointer(HandleTable, Handles[i]);
172  }
173 
174  /* Check if we have an entry */
175  if (!HandleEntry)
176  {
177  /* Fail, handle is invalid */
179  DPRINT1("Invalid handle %p passed to NtWaitForMultipleObjects\n", Handles[i]);
180  goto Quickie;
181  }
182 
183  /* Check for synchronize access */
184  GrantedAccess = HandleEntry->GrantedAccess;
186  {
187  /* Unlock the entry and fail */
189  DPRINT1("Handle does not have SYNCHRONIZE access\n");
191  goto Quickie;
192  }
193 
194  /* Get the Object Header */
195  ObjectHeader = ObpGetHandleObject(HandleEntry);
196 
197  /* Get default Object */
198  DefaultObject = ObjectHeader->Type->DefaultObject;
199 
200  /* Check if it's the internal offset */
201  if (IsPointerOffset(DefaultObject))
202  {
203  /* Increase reference count */
204  InterlockedIncrementSizeT(&ObjectHeader->PointerCount);
205  ReferencedObjects++;
206 
207  /* Save the Object and Wait Object, this is a relative offset */
208  Objects[i] = &ObjectHeader->Body;
209  WaitObjects[i] = (PVOID)((ULONG_PTR)&ObjectHeader->Body +
210  (ULONG_PTR)DefaultObject);
211  }
212  else
213  {
214  /* This is our internal Object */
215  ReferencedObjects++;
216  Objects[i] = NULL;
217  WaitObjects[i] = DefaultObject;
218  }
219 
220  /* Unlock the Handle Table Entry */
222 
223  /* Keep looping */
224  i++;
225  } while (i < ObjectCount);
226 
227  /* For a Waitall, we can't have the same object more then once */
228  if (WaitType == WaitAll)
229  {
230  /* Clear the main loop variable */
231  i = 0;
232 
233  /* Start the loop */
234  do
235  {
236  /* Check the current and forward object */
237  for (j = i + 1; j < ObjectCount; j++)
238  {
239  /* Make sure they don't match */
240  if (WaitObjects[i] == WaitObjects[j])
241  {
242  /* Fail */
244  DPRINT1("Passed a duplicate object to NtWaitForMultipleObjects\n");
245  goto Quickie;
246  }
247  }
248 
249  /* Keep looping */
250  i++;
251  } while (i < ObjectCount);
252  }
253 
254  /* Now we can finally wait. Always use SEH since it can raise an exception */
255  _SEH2_TRY
256  {
257  /* We're done playing with handles */
258  LockInUse = FALSE;
260 
261  /* Do the kernel wait */
263  WaitObjects,
264  WaitType,
265  UserRequest,
266  PreviousMode,
267  Alertable,
268  TimeOut,
270  }
274  {
275  /* Get the exception code */
277  }
278  _SEH2_END;
279 
280 Quickie:
281  /* First derefence */
282  while (ReferencedObjects)
283  {
284  /* Decrease the number of objects */
285  ReferencedObjects--;
286 
287  /* Check if we had a valid object in this position */
288  if (Objects[ReferencedObjects])
289  {
290  /* Dereference it */
291  ObDereferenceObject(Objects[ReferencedObjects]);
292  }
293  }
294 
295  /* Free wait block array */
297 
298  /* Re-enable APCs if needed */
299  if (LockInUse) KeLeaveCriticalRegion();
300 
301  /* Return status */
302  return Status;
303 }
_In_ PVOID _In_ BOOLEAN Alertable
Definition: exfuncs.h:452
#define TRUE
Definition: types.h:120
NTSYSAPI VOID NTAPI RtlCopyMemory(VOID UNALIGNED *Destination, CONST VOID UNALIGNED *Source, ULONG Length)
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
#define DbgPrint
Definition: loader.c:25
HANDLE KernelHandle
Definition: legacy.c:24
PHANDLE_TABLE_ENTRY NTAPI ExMapHandleToPointer(IN PHANDLE_TABLE HandleTable, IN HANDLE Handle)
Definition: handle.c:1010
#define MAXIMUM_WAIT_OBJECTS
Definition: winbase.h:385
LONG NTSTATUS
Definition: precomp.h:26
PVOID DefaultObject
Definition: obtypes.h:384
#define ObpIsKernelHandle(Handle, ProcessorMode)
Definition: ob.h:64
static XMS_HANDLE HandleTable[XMS_MAX_HANDLES]
Definition: himem.c:83
KPROCESSOR_MODE NTAPI ExGetPreviousMode(VOID)
Definition: sysinfo.c:3066
VOID NTAPI ObDereferenceObject(IN PVOID Object)
Definition: obref.c:375
#define STATUS_INVALID_PARAMETER_MIX
Definition: ntstatus.h:271
VOID NTAPI ExUnlockHandleTableEntry(IN PHANDLE_TABLE HandleTable, IN PHANDLE_TABLE_ENTRY HandleTableEntry)
Definition: handle.c:887
#define STATUS_INVALID_HANDLE
Definition: ntstatus.h:231
#define PAGED_CODE()
Definition: video.h:57
_SEH2_TRY
Definition: create.c:4250
uint32_t ULONG_PTR
Definition: typedefs.h:63
#define EXCEPTION_CONTINUE_SEARCH
Definition: excpt.h:86
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define STATUS_INVALID_PARAMETER_3
Definition: ntstatus.h:463
#define InterlockedIncrementSizeT(a)
Definition: interlocked.h:220
LONG ObjectCount
Definition: comsup.c:7
#define PsGetCurrentProcess
Definition: psfuncs.h:17
Definition: extypes.h:595
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
unsigned char BOOLEAN
smooth NULL
Definition: ftsmooth.c:416
#define ObpGetHandleObject(x)
Definition: ob.h:81
PHANDLE_TABLE ObpKernelHandleTable
Definition: obhandle.c:20
void * PVOID
Definition: retypes.h:9
WaitType
Definition: shlextdbg.cpp:17
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint GLint GLint j
Definition: glfuncs.h:250
_In_ KPROCESSOR_MODE PreviousMode
Definition: sefuncs.h:103
#define _SEH2_YIELD(STMT_)
Definition: pseh2_64.h:8
ULONG GrantedAccess
Definition: extypes.h:606
#define STATUS_ACCESS_DENIED
Definition: udferr_usr.h:145
#define ProbeForReadLargeInteger(Ptr)
Definition: probe.h:75
CCHAR KPROCESSOR_MODE
Definition: ketypes.h:7
NTSTATUS NTAPI KeWaitForMultipleObjects(IN ULONG Count, IN PVOID Object[], IN WAIT_TYPE WaitType, IN KWAIT_REASON WaitReason, IN KPROCESSOR_MODE WaitMode, IN BOOLEAN Alertable, IN PLARGE_INTEGER Timeout OPTIONAL, OUT PKWAIT_BLOCK WaitBlockArray OPTIONAL)
Definition: wait.c:586
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
VOID NTAPI ProbeForRead(IN CONST VOID *Address, IN SIZE_T Length, IN ULONG Alignment)
Definition: exintrin.c:102
#define STATUS_INVALID_PARAMETER_1
Definition: ntstatus.h:461
#define KeEnterCriticalRegion()
Definition: ke_x.h:83
#define SYNCHRONIZE
Definition: nt_native.h:61
Status
Definition: gdiplustypes.h:24
_SEH2_END
Definition: create.c:4424
#define KeLeaveCriticalRegion()
Definition: ke_x.h:114
LONG_PTR PointerCount
Definition: obtypes.h:487
#define DPRINT1
Definition: precomp.h:8
#define TAG_WAIT
Definition: tag.h:191
unsigned int ULONG
Definition: retypes.h:1
#define ULONG_PTR
Definition: config.h:101
_Must_inspect_result_ _In_ WAIT_TYPE _In_opt_ PLARGE_INTEGER _In_opt_ PKWAIT_BLOCK WaitBlockArray
Definition: fsrtlfuncs.h:1151
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:6
#define ExFreePoolWithTag(_P, _T)
Definition: module.h:1099
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:12
#define ObKernelHandleToHandle(Handle)
Definition: ob.h:73
POBJECT_TYPE Type
Definition: obtypes.h:493
_In_ PSECURITY_SUBJECT_CONTEXT _In_ BOOLEAN _In_ ACCESS_MASK _In_ ACCESS_MASK _Outptr_opt_ PPRIVILEGE_SET _In_ PGENERIC_MAPPING _In_ KPROCESSOR_MODE _Out_ PACCESS_MASK GrantedAccess
Definition: sefuncs.h:13
ULONG ACCESS_MASK
Definition: nt_native.h:40
#define STATUS_MUTANT_LIMIT_EXCEEDED
Definition: ntstatus.h:620
#define THREAD_WAIT_OBJECTS
Definition: ketypes.h:480

Referenced by _main(), ConnectConsole(), IntAllocConsole(), IntAttachConsole(), NtWaitForMultipleObjects32(), START_TEST(), UnhandledExceptionFilter(), Wait_thread_proc(), and WaitForMultipleObjectsEx().

◆ NtWaitForMultipleObjects32()

NTSTATUS NTAPI NtWaitForMultipleObjects32 ( IN ULONG  ObjectCount,
IN PLONG  Handles,
IN WAIT_TYPE  WaitType,
IN BOOLEAN  Alertable,
IN PLARGE_INTEGER TimeOut  OPTIONAL 
)

Definition at line 333 of file obwait.c.

338 {
339  /* FIXME WOW64 */
341  (PHANDLE)Handles,
342  WaitType,
343  Alertable,
344  TimeOut);
345 }
_In_ PVOID _In_ BOOLEAN Alertable
Definition: exfuncs.h:452
NTSTATUS NTAPI NtWaitForMultipleObjects(IN ULONG ObjectCount, IN PHANDLE HandleArray, IN WAIT_TYPE WaitType, IN BOOLEAN Alertable, IN PLARGE_INTEGER TimeOut OPTIONAL)
Definition: obwait.c:46
LONG ObjectCount
Definition: comsup.c:7
WaitType
Definition: shlextdbg.cpp:17
PVOID *typedef PHANDLE
Definition: ntsecpkg.h:414

◆ NtWaitForSingleObject()

NTSTATUS NTAPI NtWaitForSingleObject ( IN HANDLE  ObjectHandle,
IN BOOLEAN  Alertable,
IN PLARGE_INTEGER TimeOut  OPTIONAL 
)

Definition at line 369 of file obwait.c.

372 {
373  PVOID Object, WaitableObject;
375  LARGE_INTEGER SafeTimeOut;
377 
378  /* Check if we came with a timeout from user mode */
380  if ((TimeOut) && (PreviousMode != KernelMode))
381  {
382  /* Enter SEH for proving */
383  _SEH2_TRY
384  {
385  /* Make a copy on the stack */
386  SafeTimeOut = ProbeForReadLargeInteger(TimeOut);
387  TimeOut = &SafeTimeOut;
388  }
390  {
391  /* Return the exception code */
393  }
394  _SEH2_END;
395  }
396 
397  /* Get the Object */
398  Status = ObReferenceObjectByHandle(ObjectHandle,
399  SYNCHRONIZE,
400  NULL,
401  PreviousMode,
402  &Object,
403  NULL);
404  if (NT_SUCCESS(Status))
405  {
406  /* Get the Waitable Object */
407  WaitableObject = OBJECT_TO_OBJECT_HEADER(Object)->Type->DefaultObject;
408 
409  /* Is it an offset for internal objects? */
410  if (IsPointerOffset(WaitableObject))
411  {
412  /* Turn it into a pointer */
413  WaitableObject = (PVOID)((ULONG_PTR)Object +
414  (ULONG_PTR)WaitableObject);
415  }
416 
417  /* SEH this since it can also raise an exception */
418  _SEH2_TRY
419  {
420  /* Ask the kernel to do the wait */
421  Status = KeWaitForSingleObject(WaitableObject,
422  UserRequest,
423  PreviousMode,
424  Alertable,
425  TimeOut);
426  }
430  {
431  /* Get the exception code */
433  }
434  _SEH2_END;
435 
436  /* Dereference the Object */
438  }
439  else
440  {
441  DPRINT1("Failed to reference the handle with status 0x%x\n", Status);
442  }
443 
444  /* Return the status */
445  return Status;
446 }
_In_ PVOID _In_ BOOLEAN Alertable
Definition: exfuncs.h:452
LONG NTSTATUS
Definition: precomp.h:26
KPROCESSOR_MODE NTAPI ExGetPreviousMode(VOID)
Definition: sysinfo.c:3066
VOID NTAPI ObDereferenceObject(IN PVOID Object)
Definition: obref.c:375
NTSTATUS NTAPI KeWaitForSingleObject(IN PVOID Object, IN KWAIT_REASON WaitReason, IN KPROCESSOR_MODE WaitMode, IN BOOLEAN Alertable, IN PLARGE_INTEGER Timeout OPTIONAL)
Definition: wait.c:416
_SEH2_TRY
Definition: create.c:4250
uint32_t ULONG_PTR
Definition: typedefs.h:63
#define OBJECT_TO_OBJECT_HEADER(o)
Definition: obtypes.h:111
#define EXCEPTION_CONTINUE_SEARCH
Definition: excpt.h:86
NTSTATUS NTAPI ObReferenceObjectByHandle(IN HANDLE Handle, IN ACCESS_MASK DesiredAccess, IN POBJECT_TYPE ObjectType, IN KPROCESSOR_MODE AccessMode, OUT PVOID *Object, OUT POBJECT_HANDLE_INFORMATION HandleInformation OPTIONAL)
Definition: obref.c:496
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
smooth NULL
Definition: ftsmooth.c:416
void * PVOID
Definition: retypes.h:9
_In_ KPROCESSOR_MODE PreviousMode
Definition: sefuncs.h:103
#define _SEH2_YIELD(STMT_)
Definition: pseh2_64.h:8
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define ProbeForReadLargeInteger(Ptr)
Definition: probe.h:75
CCHAR KPROCESSOR_MODE
Definition: ketypes.h:7
static IUnknown Object
Definition: main.c:512
#define SYNCHRONIZE
Definition: nt_native.h:61
Status
Definition: gdiplustypes.h:24
_SEH2_END
Definition: create.c:4424
#define DPRINT1
Definition: precomp.h:8
#define ULONG_PTR
Definition: config.h:101
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:6
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:12
#define STATUS_MUTANT_LIMIT_EXCEEDED
Definition: ntstatus.h:620