When multiple threads have shared access to the same data, the threads can interfere with one another. A critical section object protects a section of code from being accessed by more than one thread. A critical section is limited, however, to only one process or DLL and cannot be shared with other processes.
Critical sections work by having a thread call the EnterCriticalSection function to indicate that it has entered a critical section of code. If another thread calls EnterCriticalSection and references the same critical section object, it is blocked until the first thread calls the LeaveCriticalSection function. A critical section can protect more than one section of code as long as each section of code is protected by the same critical section object.
To use a critical section, you must first declare a CRITICAL_SECTION structure. Because other critical section functions require a pointer to this structure, be sure to allocate it within the scope of all functions that are using the critical section. Then, create a handle to the critical section object by calling the InitializeCriticalSection function.
To request ownership of a critical section, call EnterCriticalSection; to release ownership, call LeaveCriticalSection. When you are finished with a critical section, call the DeleteCriticalSection function to release the system resources that were allocated when you initialized the critical section.
The following code example shows the prototype for the critical section functions. Notice that they all require a pointer to the CRITICAL_SECTION structure.
void InitializeCriticalSection (LPCRITICAL_SECTION lpCriticalSection);
void EnterCriticalSection (LPCRITICAL_SECTION lpCriticalSection);
void LeaveCriticalSection (LPCRITICAL_SECTION lpCriticalSection);
void DeleteCriticalSection (LPCRITICAL_SECTION lpCriticalSection);
The following code example shows how a thread initializes, enters, and leaves a critical section. This example uses the try-finally structured exception-handling syntax to ensure that the thread calls LeaveCriticalSection to release the critical section object.
void CriticalSectionExample (void)
{
CRITICAL_SECTION csMyCriticalSection;
InitializeCriticalSection (&csMyCriticalSection);
__try
{
EnterCriticalSection (&csMyCriticalSection);
// Your code to access the shared resource goes here.
}
__finally
{
// Release ownership of the critical section
LeaveCriticalSection (&csMyCriticalSection);
}
} // End of CriticalSectionExample code