ReactOS 0.4.16-dev-979-g79f281e
critical.c
Go to the documentation of this file.
1/*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS system libraries
4 * FILE: lib/rtl/critical.c
5 * PURPOSE: Critical sections
6 * PROGRAMMERS: Alex Ionescu (alex@relsoft.net)
7 * Gunnar Dalsnes
8 */
9
10/* INCLUDES *****************************************************************/
11
12#include <rtl.h>
13
14#define NDEBUG
15#include <debug.h>
16
17#define MAX_STATIC_CS_DEBUG_OBJECTS 64
18
24
27
30
31/* FUNCTIONS *****************************************************************/
32
33#define CRITSECT_HAS_DEBUG_INFO(CriticalSection) \
34 (((CriticalSection)->DebugInfo != NULL) && \
35 ((CriticalSection)->DebugInfo != LongToPtr(-1)))
36
37/*++
38 * RtlpCreateCriticalSectionSem
39 *
40 * Checks if an Event has been created for the critical section.
41 *
42 * Params:
43 * None
44 *
45 * Returns:
46 * None. Raises an exception if the system call failed.
47 *
48 * Remarks:
49 * None
50 *
51 *--*/
53VOID
55RtlpCreateCriticalSectionSem(PRTL_CRITICAL_SECTION CriticalSection)
56{
58 HANDLE hNewEvent;
60
61 /* Check if we have an event */
62 if (!hEvent)
63 {
64 /* No, so create it */
65 Status = NtCreateEvent(&hNewEvent,
67 NULL,
69 FALSE);
70 if (!NT_SUCCESS(Status))
71 {
72 DPRINT1("Failed to Create Event!\n");
73
74 /*
75 * Use INVALID_HANDLE_VALUE (-1) to signal that
76 * the global keyed event must be used.
77 */
78 hNewEvent = INVALID_HANDLE_VALUE;
79 }
80
81 DPRINT("Created Event: %p\n", hNewEvent);
82
83 /* Exchange the LockSemaphore field with the new handle, if it is still 0 */
85 (PVOID)hNewEvent,
86 NULL) != NULL)
87 {
88 /* Someone else just created an event */
89 if (hNewEvent != INVALID_HANDLE_VALUE)
90 {
91 DPRINT("Closing already created event: %p\n", hNewEvent);
92 NtClose(hNewEvent);
93 }
94 }
95 }
96
97 return;
98}
99
100/*++
101 * RtlpWaitForCriticalSection
102 *
103 * Slow path of RtlEnterCriticalSection. Waits on an Event Object.
104 *
105 * Params:
106 * CriticalSection - Critical section to acquire.
107 *
108 * Returns:
109 * STATUS_SUCCESS, or raises an exception if a deadlock is occuring.
110 *
111 * Remarks:
112 * None
113 *
114 *--*/
116NTAPI
118{
120 EXCEPTION_RECORD ExceptionRecord;
121 BOOLEAN LastChance = FALSE;
122
123 /* Increase the Debug Entry count */
124 DPRINT("Waiting on Critical Section Event: %p %p\n",
127
130
131 /*
132 * If we're shutting down the process, we're allowed to acquire any
133 * critical sections by force (the loader lock in particular)
134 */
136 LdrpShutdownThreadId == NtCurrentTeb()->RealClientId.UniqueThread)
137 {
138 DPRINT("Forcing ownership of critical section %p\n", CriticalSection);
139 return STATUS_SUCCESS;
140 }
141
142 /* Do we have an Event yet? */
144 {
145 RtlpCreateCriticalSectionSem(CriticalSection);
146 }
147
148 for (;;)
149 {
150 /* Increase the number of times we've had contention */
153
154 /* Check if allocating the event failed */
156 {
157 /* Use the global keyed event (NULL as keyed event handle) */
160 FALSE,
162 }
163 else
164 {
165 /* Wait on the Event */
167 FALSE,
169 }
170
171 /* We have Timed out */
172 if (Status == STATUS_TIMEOUT)
173 {
174 /* Is this the 2nd time we've timed out? */
175 if (LastChance)
176 {
177 ERROR_DBGBREAK("Deadlock: 0x%p\n", CriticalSection);
178
179 /* Yes it is, we are raising an exception */
180 ExceptionRecord.ExceptionCode = STATUS_POSSIBLE_DEADLOCK;
181 ExceptionRecord.ExceptionFlags = 0;
182 ExceptionRecord.ExceptionRecord = NULL;
183 ExceptionRecord.ExceptionAddress = RtlRaiseException;
184 ExceptionRecord.NumberParameters = 1;
185 ExceptionRecord.ExceptionInformation[0] = (ULONG_PTR)CriticalSection;
186 RtlRaiseException(&ExceptionRecord);
187 }
188
189 /* One more try */
190 LastChance = TRUE;
191 }
192 else
193 {
194 /* If we are here, everything went fine */
195 return STATUS_SUCCESS;
196 }
197 }
198}
199
200/*++
201 * RtlpUnWaitCriticalSection
202 *
203 * Slow path of RtlLeaveCriticalSection. Fires an Event Object.
204 *
205 * Params:
206 * CriticalSection - Critical section to release.
207 *
208 * Returns:
209 * None. Raises an exception if the system call failed.
210 *
211 * Remarks:
212 * None
213 *
214 *--*/
215VOID
216NTAPI
218{
220
221 /* Do we have an Event yet? */
223 {
224 RtlpCreateCriticalSectionSem(CriticalSection);
225 }
226
227 /* Signal the Event */
228 DPRINT("Signaling Critical Section Event: %p, %p\n",
231
232 /* Check if this critical section needs to use the keyed event */
234 {
235 /* Release keyed event */
237 }
238 else
239 {
240 /* Set the event */
242 }
243
244 if (!NT_SUCCESS(Status))
245 {
246 /* We've failed */
247 DPRINT1("Signaling Failed for: %p, %p, 0x%08lx\n",
250 Status);
252 }
253}
254
255/*++
256 * RtlpInitDeferredCriticalSection
257 *
258 * Initializes the Critical Section implementation.
259 *
260 * Params:
261 * None
262 *
263 * Returns:
264 * None.
265 *
266 * Remarks:
267 * After this call, the Process Critical Section list is protected.
268 *
269 *--*/
270VOID
271NTAPI
273{
274 /* Initialize the CS Protecting the List */
276
277 /* It's now safe to enter it */
279}
280
281/*++
282 * RtlpAllocateDebugInfo
283 *
284 * Finds or allocates memory for a Critical Section Debug Object
285 *
286 * Params:
287 * None
288 *
289 * Returns:
290 * A pointer to an empty Critical Section Debug Object.
291 *
292 * Remarks:
293 * For optimization purposes, the first 64 entries can be cached. From
294 * then on, future Critical Sections will allocate memory from the heap.
295 *
296 *--*/
298NTAPI
300{
301 ULONG i;
302
303 /* Try to allocate from our buffer first */
304 for (i = 0; i < MAX_STATIC_CS_DEBUG_OBJECTS; i++)
305 {
306 /* Check if Entry is free */
308 {
309 /* Mark entry in use */
310 DPRINT("Using entry: %lu. Buffer: %p\n", i, &RtlpStaticDebugInfo[i]);
312
313 /* Use free entry found */
314 return &RtlpStaticDebugInfo[i];
315 }
316 }
317
318 /* We are out of static buffer, allocate dynamic */
319 return RtlAllocateHeap(RtlGetProcessHeap(),
320 0,
322}
323
324/*++
325 * RtlpFreeDebugInfo
326 *
327 * Frees the memory for a Critical Section Debug Object
328 *
329 * Params:
330 * DebugInfo - Pointer to Critical Section Debug Object to free.
331 *
332 * Returns:
333 * None.
334 *
335 * Remarks:
336 * If the pointer is part of the static buffer, then the entry is made
337 * free again. If not, the object is de-allocated from the heap.
338 *
339 *--*/
340VOID
341NTAPI
343{
344 SIZE_T EntryId;
345
346 /* Is it part of our cached entries? */
347 if ((DebugInfo >= RtlpStaticDebugInfo) &&
349 {
350 /* Yes. zero it out */
351 RtlZeroMemory(DebugInfo, sizeof(RTL_CRITICAL_SECTION_DEBUG));
352
353 /* Mark as free */
354 EntryId = (DebugInfo - RtlpStaticDebugInfo);
355 DPRINT("Freeing from Buffer: %p. Entry: %Iu inside Process: %p\n",
356 DebugInfo,
357 EntryId,
359 RtlpDebugInfoFreeList[EntryId] = FALSE;
360
361 }
362 else if (!DebugInfo->Flags)
363 {
364 /* It's a dynamic one, so free from the heap */
365 DPRINT("Freeing from Heap: %p inside Process: %p\n",
366 DebugInfo,
368 RtlFreeHeap(NtCurrentPeb()->ProcessHeap, 0, DebugInfo);
369 }
370 else
371 {
372 /* HACK for Wine: stores a section name pointer in the Flags member */
373 DPRINT("Assuming static: %p inside Process: %p\n",
374 DebugInfo,
376 }
377}
378
379/*++
380 * RtlDeleteCriticalSection
381 * @implemented NT4
382 *
383 * Deletes a Critical Section
384 *
385 * Params:
386 * CriticalSection - Critical section to delete.
387 *
388 * Returns:
389 * STATUS_SUCCESS, or error value returned by NtClose.
390 *
391 * Remarks:
392 * The critical section members should not be read after this call.
393 *
394 *--*/
396NTAPI
398{
400
401 DPRINT("Deleting Critical Section: %p\n", CriticalSection);
402
403 /* Close the Event Object Handle if it exists */
405 {
406 /* In case NtClose fails, return the status */
408 }
409
410 /* Protect List */
412
414 {
415 /* Remove it from the list */
417#if 0
418 /* HACK for Wine: We need to preserve Flags for RtlpFreeDebugInfo */
420#endif
421 }
422
423 /* Unprotect */
425
427 {
428 /* Free it */
430 }
431
432 /* Wipe it out */
434
435 /* Return */
436 return Status;
437}
438
439/*++
440 * RtlSetCriticalSectionSpinCount
441 * @implemented NT4
442 *
443 * Sets the spin count for a critical section.
444 *
445 * Params:
446 * CriticalSection - Critical section to set the spin count for.
447 *
448 * SpinCount - Spin count for the critical section.
449 *
450 * Returns:
451 * STATUS_SUCCESS.
452 *
453 * Remarks:
454 * SpinCount is ignored on single-processor systems.
455 *
456 *--*/
457ULONG
458NTAPI
460 ULONG SpinCount)
461{
463
464 /* Set to parameter if MP, or to 0 if this is Uniprocessor */
465 CriticalSection->SpinCount = (NtCurrentPeb()->NumberOfProcessors > 1) ? SpinCount : 0;
466 return OldCount;
467}
468
469/*++
470 * RtlEnterCriticalSection
471 * @implemented NT4
472 *
473 * Waits to gain ownership of the critical section.
474 *
475 * Params:
476 * CriticalSection - Critical section to wait for.
477 *
478 * Returns:
479 * STATUS_SUCCESS.
480 *
481 * Remarks:
482 * Uses a fast-path unless contention happens.
483 *
484 *--*/
486NTAPI
488{
489 HANDLE Thread = (HANDLE)NtCurrentTeb()->ClientId.UniqueThread;
490
491 /* Try to lock it */
493 {
494 /* We've failed to lock it! Does this thread actually own it? */
496 {
497 /*
498 * You own it, so you'll get it when you're done with it! No need to
499 * use the interlocked functions as only the thread who already owns
500 * the lock can modify this data.
501 */
503 return STATUS_SUCCESS;
504 }
505
506 /* NOTE - CriticalSection->OwningThread can be NULL here because changing
507 this information is not serialized. This happens when thread a
508 acquires the lock (LockCount == 0) and thread b tries to
509 acquire it as well (LockCount == 1) but thread a hasn't had a
510 chance to set the OwningThread! So it's not an error when
511 OwningThread is NULL here! */
512
513 /* We don't own it, so we must wait for it */
515 }
516
517 /*
518 * Lock successful. Changing this information has not to be serialized
519 * because only one thread at a time can actually change it (the one who
520 * acquired the lock)!
521 */
524 NtCurrentTeb()->CountOfOwnedCriticalSections++;
525 return STATUS_SUCCESS;
526}
527
528/*++
529 * RtlInitializeCriticalSection
530 * @implemented NT4
531 *
532 * Initialises a new critical section.
533 *
534 * Params:
535 * CriticalSection - Critical section to initialise
536 *
537 * Returns:
538 * STATUS_SUCCESS.
539 *
540 * Remarks:
541 * Simply calls RtlInitializeCriticalSectionAndSpinCount
542 *
543 *--*/
545NTAPI
547{
548 /* Call the Main Function */
550}
551
552/*++
553 * RtlInitializeCriticalSectionEx
554 * @implemented NT6.0
555 *
556 * Initialises a new critical section.
557 *
558 * Params:
559 * CriticalSection - Critical section to initialise
560 *
561 * SpinCount - Spin count for the critical section.
562 *
563 * Flags - Flags for initialization.
564 *
565 * Returns:
566 * STATUS_SUCCESS.
567 *
568 * Remarks:
569 * SpinCount is ignored on single-processor systems.
570 *
571 *--*/
573NTAPI
576 _In_ ULONG SpinCount,
578{
579 PRTL_CRITICAL_SECTION_DEBUG CritcalSectionDebugData;
580 ULONG AllowedFlags;
582
583 /* Remove lower bits from flags */
585
586 /* These flags generally allowed */
590
591 /* Flags for Windows 7+ (CHECKME) */
592 OsVersion = NtCurrentPeb()->OSMajorVersion << 8 |
593 NtCurrentPeb()->OSMinorVersion;
595 {
598 }
599
600 if (Flags & ~AllowedFlags)
601 {
603 }
604
606 {
608 }
609
610 /* First things first, set up the Object */
611 DPRINT("Initializing Critical Section: %p\n", CriticalSection);
615 CriticalSection->SpinCount = (NtCurrentPeb()->NumberOfProcessors > 1) ? SpinCount : 0;
617
619 {
621 }
622 else
623 {
624 /* Allocate the Debug Data */
625 CritcalSectionDebugData = RtlpAllocateDebugInfo();
626 DPRINT("Allocated Debug Data: %p inside Process: %p\n",
627 CritcalSectionDebugData,
629
630 if (!CritcalSectionDebugData)
631 {
632 /* This is bad! */
633 DPRINT1("Couldn't allocate Debug Data for: %p\n", CriticalSection);
634 return STATUS_NO_MEMORY;
635 }
636
637 /* Set it up */
638 CritcalSectionDebugData->Type = RTL_CRITSECT_TYPE;
639 CritcalSectionDebugData->ContentionCount = 0;
640 CritcalSectionDebugData->EntryCount = 0;
641 CritcalSectionDebugData->CriticalSection = CriticalSection;
642 CritcalSectionDebugData->Flags = 0;
643 CriticalSection->DebugInfo = CritcalSectionDebugData;
644
645 /*
646 * Add it to the List of Critical Sections owned by the process.
647 * If we've initialized the Lock, then use it. If not, then probably
648 * this is the lock initialization itself, so insert it directly.
649 */
651 {
652 DPRINT("Securely Inserting into ProcessLocks: %p, %p, %p\n",
653 &CritcalSectionDebugData->ProcessLocksList,
656
657 /* Protect List */
659
660 /* Add this one */
661 InsertTailList(&RtlCriticalSectionList, &CritcalSectionDebugData->ProcessLocksList);
662
663 /* Unprotect */
665 }
666 else
667 {
668 DPRINT("Inserting into ProcessLocks: %p, %p, %p\n",
669 &CritcalSectionDebugData->ProcessLocksList,
672
673 /* Add it directly */
674 InsertTailList(&RtlCriticalSectionList, &CritcalSectionDebugData->ProcessLocksList);
675 }
676 }
677
678 return STATUS_SUCCESS;
679}
680
681/*++
682 * RtlInitializeCriticalSectionAndSpinCount
683 * @implemented NT4
684 *
685 * Initialises a new critical section.
686 *
687 * Params:
688 * CriticalSection - Critical section to initialise
689 *
690 * SpinCount - Spin count for the critical section.
691 *
692 * Returns:
693 * STATUS_SUCCESS.
694 *
695 * Remarks:
696 * SpinCount is ignored on single-processor systems.
697 *
698 *--*/
700NTAPI
703 _In_ ULONG SpinCount)
704{
705 SpinCount &= ~RTL_CRITICAL_SECTION_ALL_FLAG_BITS;
707}
708
709/*++
710 * RtlGetCriticalSectionRecursionCount
711 * @implemented NT5.2 SP1
712 *
713 * Retrieves the recursion count of a given critical section.
714 *
715 * Params:
716 * CriticalSection - Critical section to retrieve its recursion count.
717 *
718 * Returns:
719 * The recursion count.
720 *
721 * Remarks:
722 * We return the recursion count of the critical section if it is owned
723 * by the current thread, and otherwise we return zero.
724 *
725 *--*/
726LONG
727NTAPI
729{
731 {
732 /*
733 * The critical section is owned by the current thread,
734 * therefore retrieve its actual recursion count.
735 */
737 }
738 else
739 {
740 /*
741 * It is not owned by the current thread, so
742 * for this thread there is no recursion.
743 */
744 return 0;
745 }
746}
747
748/*++
749 * RtlLeaveCriticalSection
750 * @implemented NT4
751 *
752 * Releases a critical section and makes if available for new owners.
753 *
754 * Params:
755 * CriticalSection - Critical section to release.
756 *
757 * Returns:
758 * STATUS_SUCCESS.
759 *
760 * Remarks:
761 * If another thread was waiting, the slow path is entered.
762 *
763 *--*/
765NTAPI
767{
768#if DBG
769 HANDLE Thread = (HANDLE)NtCurrentTeb()->ClientId.UniqueThread;
770
771 /*
772 * In win this case isn't checked. However it's a valid check so it should
773 * only be performed in debug builds!
774 */
776 {
777 DPRINT1("Releasing critical section not owned!\n");
779 }
780#endif
781
782 /*
783 * Decrease the Recursion Count. No need to do this atomically because only
784 * the thread who holds the lock can call this function (unless the program
785 * is totally screwed...
786 */
788 {
790 {
791 DPRINT1("CRITICAL SECTION MESS: Section %p is not acquired!\n", CriticalSection);
792 return STATUS_UNSUCCESSFUL;
793 }
794 /* Someone still owns us, but we are free. This needs to be done atomically. */
796 }
797 else
798 {
799 /*
800 * Nobody owns us anymore. No need to do this atomically.
801 * See comment above.
802 */
804 NtCurrentTeb()->CountOfOwnedCriticalSections--;
805
806 /* Was someone wanting us? This needs to be done atomically. */
808 {
809 /* Let him have us */
811 }
812 }
813
814 /* Sucessful! */
815 return STATUS_SUCCESS;
816}
817
818/*++
819 * RtlTryEnterCriticalSection
820 * @implemented NT4
821 *
822 * Attemps to gain ownership of the critical section without waiting.
823 *
824 * Params:
825 * CriticalSection - Critical section to attempt acquiring.
826 *
827 * Returns:
828 * TRUE if the critical section has been acquired, FALSE otherwise.
829 *
830 * Remarks:
831 * None
832 *
833 *--*/
835NTAPI
837{
838 /* Try to take control */
840 {
841 /* It's ours */
842 CriticalSection->OwningThread = NtCurrentTeb()->ClientId.UniqueThread;
844 NtCurrentTeb()->CountOfOwnedCriticalSections++;
845 return TRUE;
846 }
848 {
849 /* It's already ours */
852 return TRUE;
853 }
854
855 /* It's not ours */
856 return FALSE;
857}
858
859VOID
860NTAPI
862{
864}
865
866ULONG
867NTAPI
869{
870 return CriticalSection->RecursionCount != 0;
871}
872
873ULONG
874NTAPI
876{
877 return CriticalSection->OwningThread == NtCurrentTeb()->ClientId.UniqueThread &&
879}
880
881VOID
882NTAPI
884{
886}
887
888/* EOF */
#define NtCurrentPeb()
Definition: FLS.c:22
unsigned char BOOLEAN
#define InterlockedIncrement
Definition: armddk.h:53
#define InterlockedDecrement
Definition: armddk.h:52
LONG NTSTATUS
Definition: precomp.h:26
HANDLE ProcessHeap
Definition: servman.c:15
#define DPRINT1
Definition: precomp.h:8
#define LongToPtr(l)
Definition: basetsd.h:91
#define UNIMPLEMENTED
Definition: ntoskrnl.c:15
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:616
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:634
BOOLEAN LdrpShutdownInProgress
Definition: ldrinit.c:34
NTSTATUS NTAPI RtlLeaveCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:766
static BOOLEAN RtlpDebugInfoFreeList[MAX_STATIC_CS_DEBUG_OBJECTS]
Definition: critical.c:23
NTSTATUS NTAPI RtlpWaitForCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:117
VOID NTAPI RtlpInitDeferredCriticalSection(VOID)
Definition: critical.c:272
HANDLE LdrpShutdownThreadId
Definition: ldrinit.c:35
VOID NTAPI RtlpUnWaitCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:217
#define CRITSECT_HAS_DEBUG_INFO(CriticalSection)
Definition: critical.c:33
NTSTATUS NTAPI RtlDeleteCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:397
ULONG NTAPI RtlIsCriticalSectionLockedByThread(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:875
LONG NTAPI RtlGetCriticalSectionRecursionCount(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:728
LARGE_INTEGER RtlpTimeout
Definition: critical.c:25
VOID NTAPI RtlCheckForOrphanedCriticalSections(HANDLE ThreadHandle)
Definition: critical.c:861
NTSTATUS NTAPI RtlInitializeCriticalSectionAndSpinCount(_Out_ PRTL_CRITICAL_SECTION CriticalSection, _In_ ULONG SpinCount)
Definition: critical.c:701
#define MAX_STATIC_CS_DEBUG_OBJECTS
Definition: critical.c:17
NTSTATUS NTAPI RtlInitializeCriticalSectionEx(_Out_ PRTL_CRITICAL_SECTION CriticalSection, _In_ ULONG SpinCount, _In_ ULONG Flags)
Definition: critical.c:574
VOID NTAPI RtlpNotOwnerCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:883
ULONG NTAPI RtlIsCriticalSectionLocked(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:868
NTSTATUS NTAPI RtlInitializeCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:546
static BOOLEAN RtlpCritSectInitialized
Definition: critical.c:21
BOOLEAN NTAPI RtlTryEnterCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:836
static RTL_CRITICAL_SECTION RtlCriticalSectionLock
Definition: critical.c:19
static RTL_CRITICAL_SECTION_DEBUG RtlpStaticDebugInfo[MAX_STATIC_CS_DEBUG_OBJECTS]
Definition: critical.c:22
ULONG NTAPI RtlSetCriticalSectionSpinCount(PRTL_CRITICAL_SECTION CriticalSection, ULONG SpinCount)
Definition: critical.c:459
PRTL_CRITICAL_SECTION_DEBUG NTAPI RtlpAllocateDebugInfo(VOID)
Definition: critical.c:299
VOID NTAPI RtlpFreeDebugInfo(PRTL_CRITICAL_SECTION_DEBUG DebugInfo)
Definition: critical.c:342
BOOLEAN RtlpTimeoutDisable
Definition: critical.c:26
static LIST_ENTRY RtlCriticalSectionList
Definition: critical.c:20
NTSTATUS NTAPI RtlEnterCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:487
#define STATUS_TIMEOUT
Definition: d3dkmdt.h:49
#define STATUS_NO_MEMORY
Definition: d3dkmdt.h:51
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:33
#define INVALID_HANDLE_VALUE
Definition: compat.h:731
#define ULONG_PTR
Definition: config.h:101
#define RemoveEntryList(Entry)
Definition: env_spec_w32.h:986
#define InsertTailList(ListHead, Entry)
_In_opt_ PFILE_OBJECT _In_opt_ PETHREAD Thread
Definition: fltkernel.h:2653
Status
Definition: gdiplustypes.h:25
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
NTSYSAPI NTSTATUS WINAPI NtWaitForKeyedEvent(HANDLE, const void *, BOOLEAN, const LARGE_INTEGER *)
NTSYSAPI NTSTATUS WINAPI NtReleaseKeyedEvent(HANDLE, const void *, BOOLEAN, const LARGE_INTEGER *)
#define InterlockedCompareExchangePointer
Definition: interlocked.h:129
#define InterlockedCompareExchange
Definition: interlocked.h:104
#define NtCurrentTeb
CRITICAL_SECTION CriticalSection
Definition: iprtprio.c:40
#define EVENT_ALL_ACCESS
Definition: isotest.c:82
static ULONG OsVersion
static HANDLE hEvent
Definition: comm.c:54
#define _Post_notnull_
Definition: ms_sal.h:701
DECLSPEC_NORETURN NTSYSAPI VOID NTAPI RtlRaiseStatus(_In_ NTSTATUS Status)
NTSYSAPI VOID NTAPI RtlRaiseException(_In_ PEXCEPTION_RECORD ExceptionRecord)
#define RTL_CRITSECT_TYPE
Definition: rtltypes.h:264
#define _At_(t, a)
Definition: no_sal2.h:40
#define _Out_
Definition: no_sal2.h:160
#define _In_
Definition: no_sal2.h:158
NTSTATUS NTAPI NtClose(IN HANDLE Handle)
Definition: obhandle.c:3402
NTSYSAPI NTSTATUS NTAPI NtWaitForSingleObject(IN HANDLE hObject, IN BOOLEAN bAlertable, IN PLARGE_INTEGER Timeout)
@ SynchronizationEvent
NTSTATUS NTAPI NtSetEvent(IN HANDLE EventHandle, OUT PLONG PreviousState OPTIONAL)
Definition: event.c:455
NTSTATUS NTAPI NtCreateEvent(OUT PHANDLE EventHandle, IN ACCESS_MASK DesiredAccess, IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, IN EVENT_TYPE EventType, IN BOOLEAN InitialState)
Definition: event.c:96
#define STATUS_POSSIBLE_DEADLOCK
Definition: ntstatus.h:637
#define STATUS_INVALID_PARAMETER_2
Definition: ntstatus.h:476
#define STATUS_RESOURCE_NOT_OWNED
Definition: ntstatus.h:737
#define STATUS_INVALID_PARAMETER_3
Definition: ntstatus.h:477
long LONG
Definition: pedump.c:60
#define ERROR_DBGBREAK(...)
Definition: debug.h:221
#define _WIN32_WINNT_WIN7
Definition: sdkddkver.h:28
#define STATUS_SUCCESS
Definition: shellext.h:65
#define DPRINT
Definition: sndvol32.h:73
HANDLE UniqueThread
Definition: compat.h:826
HANDLE UniqueProcess
Definition: compat.h:825
LIST_ENTRY ProcessLocksList
Definition: winbase.h:908
ULONG_PTR SpinCount
Definition: winbase.h:930
LONG RecursionCount
Definition: winbase.h:927
PCRITICAL_SECTION_DEBUG DebugInfo
Definition: winbase.h:925
HANDLE LockSemaphore
Definition: winbase.h:929
HANDLE OwningThread
Definition: winbase.h:928
struct _EXCEPTION_RECORD * ExceptionRecord
Definition: compat.h:210
DWORD ExceptionCode
Definition: compat.h:208
DWORD NumberParameters
Definition: compat.h:212
DWORD ExceptionFlags
Definition: compat.h:209
ULONG_PTR ExceptionInformation[EXCEPTION_MAXIMUM_PARAMETERS]
Definition: compat.h:213
PVOID ExceptionAddress
Definition: compat.h:211
Definition: typedefs.h:120
struct _RTL_CRITICAL_SECTION * CriticalSection
Definition: rtltypes.h:1416
#define NTAPI
Definition: typedefs.h:36
PVOID HANDLE
Definition: typedefs.h:73
ULONG_PTR SIZE_T
Definition: typedefs.h:80
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
uint32_t ULONG
Definition: typedefs.h:59
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
#define RTL_CRITICAL_SECTION_FLAG_DYNAMIC_SPIN
Definition: winnt_old.h:1113
#define RTL_CRITICAL_SECTION_FLAG_FORCE_DEBUG_INFO
Definition: winnt_old.h:1116
#define RTL_CRITICAL_SECTION_FLAG_STATIC_INIT
Definition: winnt_old.h:1114
#define RTL_CRITICAL_SECTION_FLAG_NO_DEBUG_INFO
Definition: winnt_old.h:1112
#define RTL_CRITICAL_SECTION_FLAG_RESOURCE_TYPE
Definition: winnt_old.h:1115
#define RTL_CRITICAL_SECTION_ALL_FLAG_BITS
Definition: winnt_old.h:1117
_Must_inspect_result_ _In_ ULONG Flags
Definition: wsk.h:170
_Out_ PCLIENT_ID ClientId
Definition: kefuncs.h:1151