Windows Thread Management. – 2 – Objectives and Benefits Describe Windows thread management Use...

Preview:

Citation preview

Windows Thread Management

Windows Thread Management

– 2 –

Objectives and BenefitsObjectives and Benefits

Describe Windows thread management Use threads in Windows applications Use threads with C library functions Build and execute threaded applications Describe the various Windows synchronization

mechanisms Differentiate synchronization object features and

how to select between them Use synchronization in Windows applications

– 3 –

Threads: Benefits and RisksThreads: Benefits and Risks

BenefitsBenefits Simpler program models Faster code – in many cases

Exploit multiple processorsExploit inherent application parallelism

Reliable, understandable, maintainable code

RisksRisks Slower performance – in some cases Potential defects

– 4 –

ContentsContents

Process and Thread OverviewProcess and Thread Overview

Thread ManagementThread Management

Waiting for Thread TerminationWaiting for Thread Termination

The C Library and ThreadsThe C Library and Threads

Demonstration: Building a Threaded ApplicationDemonstration: Building a Threaded Application

Need for SynchronizationNeed for Synchronization

Thread Synchronization ObjectsThread Synchronization Objects CRITICAL_SECTIONs (Deadlock Example) Mutexes for Mutual Exclusion Events Semaphores

– 5 –

1. Process and Thread Overview1. Process and Thread Overview

Threads Threads inin a process share data and code a process share data and code Each thread has its own stack for function calls Calling thread can pass an argument to a thread at creation

timeThis argument is on the stack

Each thread can allocate its own Thread Local Storage (TLS) indices and set TLS values

Threads are scheduled and run independentlyThreads are scheduled and run independently The executive schedules threads Threads run asynchronously Threads can be preempted

Or restarted at any time

– 6 –

Processes and ThreadsProcesses and ThreadsProcess

Code

Global Variables

Process Heap

Process ResourcesOpen Files

Heaps…

Environment Block

...

Thread 1

Thread Local Storage

Stack

Thread N

Thread Local Storage

Stack

– 7 –

Read File B

Single-Threaded Program Multithreaded Program

Read File A

Read File B

Reading File B before

File A would give the same results

Read File A

Wait forThread 1 and

Thread 2 to finish

Merge datafrom both files

Thread 1

Thread 3

Thread 2

Thread 3

Merge datafrom both files

Threads Performing Parallel TasksThreads Performing Parallel Tasks

– 8 –

2. Thread Management2. Thread Management

Creating a ThreadCreating a Thread

The Thread FunctionThe Thread Function

Thread TerminationThread Termination

Thread Exit CodesThread Exit Codes

Thread IdentitiesThread Identities

Suspending and Resuming Suspending and Resuming ThreadsThreads

– 9 –

Creating a Thread (1/4)Creating a Thread (1/4)

Specify the thread’s start address within the process’ Specify the thread’s start address within the process’ codecode

Specify the stack size, and the stack consumes space Specify the stack size, and the stack consumes space within the process’ address spacewithin the process’ address space The stack cannot be expanded

Specify a pointer to an argument for the threadSpecify a pointer to an argument for the thread Can be nearly anything Interpreted by the thread itself

CreateThreadCreateThread returns a thread’s ID value and its handle returns a thread’s ID value and its handle A NULL handle value indicates failure

– 10 –

Creating a Thread (2/4)Creating a Thread (2/4)

HANDLE CreateThread (

LPSECURITY_ATTRIBUTES lpsa,

DWORD cbStack,

LPTHREAD_START_ROUTINE lpStartAddr,

LPVOID lpvThreadParm,

DWORD dwCreate,

LPDWORD lpIDThread )

– 11 –

Creating a Thread (3/4)Creating a Thread (3/4)

ParametersParameters

lpsalpsa Security attributes structure (use NULL)

cbStackcbStack Byte size for the new thread’s stack Use 0 to default to the primary thread’s stack size (1 MB)

lpStartAddrlpStartAddr Points to the function (within the calling process) to be executed Accepts a single pointer argument and returns a 32-bit DWORD exit

code The thread can interpret the argument as a DWORD or a pointer

lpThreadParmlpThreadParm The pointer passed as the thread argument

– 12 –

Creating a Thread (4/4)Creating a Thread (4/4)

dwCreatedwCreate If zero, the thread is immediately ready to run If CREATE_SUSPENDED, the new thread will be in the

suspended state, requiring a ResumeThread function call to move the thread to the ready state

lpIDThreadlpIDThread Points to a DWORD that receives the new thread’s identifier; NULL OK on W2000/NT

– 13 –

The Thread FunctionThe Thread Function

DWORD WINAPI MyThreadFunc (

PVOID pThParam )

{ . . .

ExitThread (ExitCode); /* OR */

return ExitCode;

}

– 14 –

Thread Termination (1/2)Thread Termination (1/2)

Threads Threads areare terminated by terminated by ExitProcessExitProcess The process and all its threads terminate The exit code returned by the thread start function same as the

process exit code Or a thread can simply return with its exit code

ExitThreadExitThread is the preferred technique is the preferred technique The thread’s stack is deallocated on termination

VOID ExitThread (DWORD (dwExitCode)VOID ExitThread (DWORD (dwExitCode)

When the last thread in a process terminates, so does the process When the last thread in a process terminates, so does the process itselfitself

– 15 –

Thread Termination (2/2)Thread Termination (2/2)

You can terminate a different thread with You can terminate a different thread with TerminateThreadTerminateThread Dangerous: The thread’s stack and other resources will not be

deallocated Better to let the thread terminate itself

A thread will remain in the system until the last handle to A thread will remain in the system until the last handle to it is closed (using it is closed (using CloseHandleCloseHandle)) Then the thread will be deleted

Any other thread can retrieve the exit codeAny other thread can retrieve the exit code

– 16 –

Thread Exit CodesThread Exit Codes

BOOL GetExitCodeThread (BOOL GetExitCodeThread (

HANDLE hThread,HANDLE hThread,

LPDWORD lpdwExitCode )LPDWORD lpdwExitCode )

lpdwExitCodelpdwExitCode Contains the thread’s exit code It could be STILL_ACTIVE

– 17 –

Thread IdentitiesThread Identities

A thread has a permanent “A thread has a permanent “ThreadIdThreadId””

A thread is usually accessed by A thread is usually accessed by HANDLEHANDLE

An ID can be converted to a An ID can be converted to a HANDLEHANDLE

HANDLE GetCurrentThread (VOID);HANDLE GetCurrentThread (VOID);

DWORD GetCurrentThreadId (VOID);DWORD GetCurrentThreadId (VOID);

HANDLE OpenThread (HANDLE OpenThread (

DWORD dwDesiredAccess,DWORD dwDesiredAccess,

BOOL InheritableHandle,BOOL InheritableHandle,

DWORD ThreadId );DWORD ThreadId );

/* >= Windows 2000 only *//* >= Windows 2000 only */

– 18 –

Suspend & Resume Threads (1/2)Suspend & Resume Threads (1/2)

Every thread has a suspend countEvery thread has a suspend count A thread can execute only if this count is zero

A thread can be created in the suspended stateA thread can be created in the suspended state

One thread can increment or decrement the suspend One thread can increment or decrement the suspend count of another:count of another:

DWORD ResumeThread (HANDLE hThread)DWORD ResumeThread (HANDLE hThread)

– 19 –

Suspend & Resume Threads (2/2)Suspend & Resume Threads (2/2)

DWORD SuspendThread (HANDLE hThread)DWORD SuspendThread (HANDLE hThread)

Both functions return previous suspend countBoth functions return previous suspend count

0xFFFFFFFF0xFFFFFFFF indicates failure indicates failure

Useful in preventing “race conditions”Useful in preventing “race conditions” Do not allow threads to start until initialization is complete

Unsafe for general synchronizationUnsafe for general synchronization

– 20 –

Waiting for Thread TerminationWaiting for Thread Termination

Wait for a thread to terminate Wait for a thread to terminate using general purpose wait using general purpose wait functionsfunctions

WaitForSingleObjectWaitForSingleObject or or WaitForMultipleObjectsWaitForMultipleObjects Using thread handles

The wait functionThe wait functionss wait for the wait for the threadthread handle to become handle to become signaledsignaled Thread handle is signaled when thread terminates

ExitThreadExitThread and and TerminateThreadTerminateThread set the object to the set the object to the signaled statesignaled state Releasing all other threads waiting on the object

ExitExitProcessProcess sets the process’ state and all its threads’ sets the process’ state and all its threads’ states to signaledstates to signaled

– 21 –

The Wait Functions (1/2)The Wait Functions (1/2)

DWORD WaitForSingleObject (DWORD WaitForSingleObject (

HANDLE hObject,HANDLE hObject,

DWORD dwTimeOut )DWORD dwTimeOut )

– 22 –

The Wait Functions (2/2)The Wait Functions (2/2)

DWORD WaitForMultipleObjects (DWORD WaitForMultipleObjects (

DWORD cObjects,DWORD cObjects,

LPHANDLE lphObjects,LPHANDLE lphObjects,

BOOL fWaitAll,BOOL fWaitAll,

DWORD dwTimeOut )DWORD dwTimeOut )

Return: The cause of the wait completionReturn: The cause of the wait completion

– 23 –

Wait Options (1/2)Wait Options (1/2)

Specify either a single handle Specify either a single handle hObjecthObject

Or an array of Or an array of cObjectscObjects referenced by referenced by lphObjectslphObjects

cObjectscObjects should not exceed should not exceed MAXIMUM_WAIT_OBJECTSMAXIMUM_WAIT_OBJECTS - - 6464

– 24 –

Wait Options (2/2)Wait Options (2/2)

dwTimeOutdwTimeOut is in milliseconds is in milliseconds 0 means the function returns immediately after testing the

state of the specified objects Use INFINITE for no timeout

Wait forever for a thread to terminate

GetExitCodeThreadGetExitCodeThread Returns the thread exit code

– 25 –

Wait Function Return Values (1/2)Wait Function Return Values (1/2)

fWaitAllfWaitAll If TRUE, wait for all threads to terminate

Possible return values are: WAIT_OBJECT_0

The thread terminated (if calling WaitForMultipleObjects; fWaitAll set)

– 26 –

Wait Function Return Values (2/2)Wait Function Return Values (2/2) WAIT_OBJECT_0 + n

where 0 <= n < cObjects Subtract WAIT_OBJECT_0 from the return value to determine

which thread terminated when calling WaitForMultipleObjects with fWaitAll set

WAIT_TIMEOUTTimeout period elapsed

WAIT_ABANDONEDNot possible with thread handles

WAIT_FAILEDCall GetLastError for thread-specific error code

– 27 –

The C Library and ThreadsThe C Library and Threads

Nearly all programsNearly all programs (and thread functions) (and thread functions) use the C use the C librarylibrary

But the normal C library is not “thread safe”But the normal C library is not “thread safe”

The C function The C function _beginthreadex_beginthreadex has exactly the same has exactly the same parameters as parameters as CreateThreadCreateThread

– 28 –

Using _beginthreadexUsing _beginthreadex

Cast the Cast the _beginthreadex_beginthreadex return value to return value to (HANDLE)(HANDLE)

Use Use _endthreadex_endthreadex in place of in place of ExitThreadExitThread

#include <process.h>#include <process.h>

Set the multithreaded environment as follows:Set the multithreaded environment as follows: #define _MT in every source file before <windows.h> Link with LIBCMT.LIB

Override the default library

Preferred Preferred methodmethod using Visual C++ using Visual C++

From the menu barFrom the menu bar:: Build Settings — C/C++ Tab Code Generation category Select a multithreaded run-time library

– 29 –

Ex: A Simple Boss ThreadEx: A Simple Boss Thread

HANDLE hWork[K];volatile LONGLONG WorkDone[K], iTh; /* !! */

. . .for (iTh = 0; iTh < K; iTh++) {

WorkDone[ith] = 0;hWork[iTh] = _beginthreadex (NULL, 0,WorkTh, (PVOID)&iTh, 0, NULL); /* BUG! */

}WaitForMultipleObjects (K, hWork, TRUE,

INFINITE);for (iTh = 0; iTh < K; iTh++)

printf (“Thread %d did %d workunits\n”,iTh, WorkDone[iTh]);

– 30 –

Ex: A Simple Worker ThreadEx: A Simple Worker Thread

DWORD WINAPI WorkTh (PVOID pThNum){

DWORD ThNum = (DWORD)(*pThNum);while (. . .) {

/* Perform work */WorkDone[ThNum]++;

}_endthreadex (0);

}

– 31 –

A SYNCHRONIZATION PROBLEMA SYNCHRONIZATION PROBLEM

M

45

45

M = N;M = M + 1;

Running

N = M;

Running

· · ·

Ready

N

4

5

5

Ready

M = N;M = M + 1;N = M;

Running

Ready

· · ·

Thread 1 Thread 2

– 32 –

2. Thread Synchronization Objects2. Thread Synchronization Objects

Known Windows mechanismKnown Windows mechanism to synchronize to synchronize threadsthreads:: A thread can wait for another to terminate (using ExitThread)

by waiting on the thread handle using WaitForSingleObject or WaitForMultipleObjects

A process can wait for another process to terminate (ExitProcess) in the same way

Other common methods (not covered here):Other common methods (not covered here): Reading from a pipe or socket that allows one process or

thread to wait for another to write to the pipe (socket) File locks are specifically for synchronizing file access

– 33 –

Synchronization ObjectsSynchronization Objects

Windows provides four other objects specifically Windows provides four other objects specifically designed for thread and process synchronizationdesigned for thread and process synchronization

Three are kernel objects (they have Three are kernel objects (they have HANDLEHANDLEs)s) Events Semaphores Mutexes

Many inherently complex problems – beware:Many inherently complex problems – beware: Deadlocks Race conditions Missed signals Many more

– 34 –

Critical Section ObjectsCritical Section Objects

Critical sectionsCritical sections Fourth object type can only synchronize threads within a

process Often the most efficient choice

Apply to many application scenarios“Fast mutexes”Not kernel objects

Critical section objects are initialized, not createdDeleted, not closed

Threads enter and leave critical sections Only 1 thread at a time can be in a specific critical section There is no handle — there is a CRITICAL_SECTION type

– 35 –

3. CRITICAL_SECTIONs3. CRITICAL_SECTIONs

VOID InitializeCriticalSection (VOID InitializeCriticalSection (LPCRITICAL_SECTION lpcsCriticalSection)LPCRITICAL_SECTION lpcsCriticalSection)

VOID DeleteCriticalSection (VOID DeleteCriticalSection (LPCRITICAL_SECTION lpcsCriticalSection)LPCRITICAL_SECTION lpcsCriticalSection)

VOID EnterCriticalSection (VOID EnterCriticalSection (LPCRITICAL_SECTION lpcsCriticalSection)LPCRITICAL_SECTION lpcsCriticalSection)

– 36 –

CRITICAL_SECTION ManagementCRITICAL_SECTION Management

VOID LeaveCriticalSection (VOID LeaveCriticalSection (LPCRITICAL_SECTION lpcsCriticalSection)LPCRITICAL_SECTION lpcsCriticalSection)

BOOL TryCriticalSection (BOOL TryCriticalSection ( LPCRITICAL_SECTION lpcsCriticalSection)LPCRITICAL_SECTION lpcsCriticalSection)

– 37 –

CRITICAL_SECTIONS UsageCRITICAL_SECTIONS Usage

EnterCriticalSection blocks a thread if another thread is in (“owns”) the section

Use TryCriticalSection to avoid blockingA thread can enter a CS more than once (“recursive”)

The waiting thread unblocks when the “owning” thread executes LeaveCriticalSection

A thread must leave a CS once for every time it entered

Common usage: allow threads to access global variablesDon’t forget to declare these variables volatile!

– 38 –

SYNCHRONIZATION CSsSYNCHRONIZATION CSs

M

45

N4

M = N;M = M + 1;

Running

Idle

Thread 1

Idle

Running

· · ·

Thread 2

Blocked

M = N;M = M + 1;N = M;

Running

ECS(&CS);

ECS(&CS);

5

56

6

N = M;

Running

· · ·

LCS (&CS);

LCS(&CS);

– 39 –

CRITICAL_SECTION CommentsCRITICAL_SECTION Comments

CRITICAL_SECTIONS test in user-spaceCRITICAL_SECTIONS test in user-space Fast – no kernel call But wait in kernel space

Usually faster than Mutexes – See Session 3Usually faster than Mutexes – See Session 3 But, not always Factors include number of threads, number of processors, and

amount of thread contention

Performance can sometimes be “tuned”Performance can sometimes be “tuned” Adjust the “spin count” – more later CSs operate using polling and the equivalent of interlocked

functions

– 40 –

4. Deadlock Example4. Deadlock Example

Here is a program defect that could cause a deadlockHere is a program defect that could cause a deadlock Some function calls are abbreviated for brevity Aways enter CSs in the same order; leave in reverse order Deadlocks are specific kind of race condition To avoid deadlocks, create a lock hierarchy

– 41 –

Deadlock ExampleDeadlock Example

CRITICAL_SECTION csM, csN;volatile DWORD M = 0, N = 0;

...InitializeCriticalSection (&csM); ICS (&csN);

...DWORD ThreadFunc (...){

ECS (&csM); ECS (&csN);M = ++N; N = M - 2;LCS (&csN); LCS (&csM);...ECS (&csM); ECS (&csN);M = N--; N = M + 2;LCS (&csN); LCS (&csM);

}

– 42 –

6. Mutexes for Mutual Exclusion6. Mutexes for Mutual Exclusion

Mutexes can be named and have HANDLEsThey are kernel objects

They can be used for interprocess synchronization They are owned by a thread rather than a process Threads gain mutex ownership by waiting on mutex handle

With WaitForSingleObject or WaitForMultipleObjects Threads release ownership with ReleaseMutex

– 43 –

Mutexes (cont’d)Mutexes (cont’d)

Recursive: A thread can acquire a specific mutex several times but must release the mutex the same number of times

Can be convenient, for example, with nested transactions

You can poll a mutex to avoid blocking A mutex becomes “abandoned” if its owning thread terminates Events and semaphores are the other kernel objects

Very similar life cycle and usage

– 44 –

Mutexes (cont’d)Mutexes (cont’d)

HANDLE CreateMutex (LPSECURITY_ATTRIBUTES lpsa,HANDLE CreateMutex (LPSECURITY_ATTRIBUTES lpsa,BOOL fInitialOwner,BOOL fInitialOwner,LPCTSTR lpszMutexName)LPCTSTR lpszMutexName)

The fInitialOwner flag, if TRUE, gives the calling thread immediate ownership of the new mutex

It is overridden if the named mutex already exists

lpszMutexName points to a null-terminated pathnamePathnames are case sensitiveMutexes are unnamed if the parameter is NULL

– 45 –

Mutexes (cont’d)Mutexes (cont’d)

BOOL ReleaseMutex (HANDLE hMutex)BOOL ReleaseMutex (HANDLE hMutex)

ReleaseMutex frees a mutex that the calling thread ownsFails if the thread does not own it

If a mutex is abandoned, a wait will return WAIT_ABANDONED_0This is the base value on a wait multiple

OpenMutex opens an existing named mutexAllows threads in different processes to synchronize

– 46 –

Mutexes (cont’d)Mutexes (cont’d)

Mutex naming:Mutex naming: Name a mutex that is to be used by more than one process

Mutexes, semaphores, & events share the same name spaceMemory mapping objects also use this name spaceSo do waitable timers

Not necessary to name a mutex used in a single process

– 47 –

Mutexes (cont’d)Mutexes (cont’d)

Process interaction with a named mutexProcess interaction with a named mutex

Process 1

Process 2h = CreateMutex ("MName");

h = OpenMutex ("MName");

– 48 –

7. EVENTS (1 of 6)7. EVENTS (1 of 6)

Events can release multiple threads from a wait simultaneously when a single event is signaled

A manual-reset event can signal several threads simultaneously and must be reset by the thread

An auto-reset event signals a single thread, and the event is reset automatically

Signal an event with either PulseEvent or SetEvent Four combinations with very different behavior

Be careful! There are numerous subtle problems

Recommendation: Only use with SignalObjectAndWait(0) (Much) more on this later – Chapter 9

– 49 –

EVENTS (2 of 6)EVENTS (2 of 6)

HANDLE CreateEvent (HANDLE CreateEvent (LPSECURITY_ATTRIBUTES lpsa,LPSECURITY_ATTRIBUTES lpsa,BOOL fManualReset, BOOL fInitialState,BOOL fManualReset, BOOL fInitialState,LPTCSTR lpszEventName)LPTCSTR lpszEventName)

Manual-reset event: set fManualReset to TRUE Event is initially set to signaled if fInitialState is TRUE Open a named event with OpenEvent

Possibly from another process

– 50 –

EVENTS (3 of 6)EVENTS (3 of 6)

The three functions for controlling events are:The three functions for controlling events are:

BOOL SetEvent (HANDLE hEvent)

BOOL ResetEvent (HANDLE hEvent)

BOOL PulseEvent (HANDLE hEvent)

– 51 –

EVENTS (4 of 6)EVENTS (4 of 6)

A thread signals an event with SetEvent If the event is auto-reset, a single waiting thread (possibly one

of many) will be releasedThe event automatically returns to the non-signaled state

If no threads are waiting on the event, it remains in the signaled state until some thread waits on it and is immediately released

– 52 –

EVENTS (5 of 6)EVENTS (5 of 6)

If the event is manual-reset, the event remains signaled until some thread calls ResetEvent for that event

During this time, all waiting threads are released It is possible that other threads will wait, and be released, before

the reset

PulseEvent allows you to release all threads currently waiting on a manual-reset event

The event is then automatically reset

– 53 –

EVENTS (6 of 6)EVENTS (6 of 6)

When using WaitForMultipleEvents, wait for all events to become signaled

A waiting thread will be released only when all events are simultaneously in the signaled state

Some signaled events might be released before the thread is released

– 54 –

Event Notes

Behavior depends on manual or auto reset, Pulse or Behavior depends on manual or auto reset, Pulse or Set EventSet Event All 4 forms are useful

AutoReset ManualReset

SetEvent Exactly one thread is released. All currently waiting threadsIf none are currently waiting released. The event remainson the event, the next thread to signaled until reset by some wait will be released. thread.

PulseEvent Exactly one thread is released, All currently waiting threadsbut only if a thread is currently released, and the event iswaiting on the event. then reset.

– 55 –

8. SEMAPHORES (1 of 4)8. SEMAPHORES (1 of 4)

A semaphore combines event and mutex behaviorCan be emulated with one of each and a counter

Semaphores maintain a countNo ownership concept

The semaphore object is signaled when the count is greater than zero, and the object is not signaled when the count is zero

With care, you can achieve mutual exclusion with a semaphore

– 56 –

SEMAPHORES (2 of 4)SEMAPHORES (2 of 4)

Threads or processes wait in the normal way, using one of the wait functions

When a waiting thread is released, the semaphore’s count is incremented by one

Any thread can releaseNot restricted to the thread that “acquired” the semaphore Consider a producer/consumer model to see why

– 57 –

SEMAPHORES (3 of 4)SEMAPHORES (3 of 4)

HANDLE CreateSemaphore (HANDLE CreateSemaphore (LPSECURITY_ATTRIBUTES lpsa,LPSECURITY_ATTRIBUTES lpsa,LONG cSemInitial, LONG cSemMax,LONG cSemInitial, LONG cSemMax,LPCTSTR lpszSemName)LPCTSTR lpszSemName)

cSemMax is the maximum value for the semaphore Must be one or greater 0 <= cSemInitial <= cSemMax is the initial value You can only decrement the count by one with any given wait

operation, but you can release a semaphore and increment its count by any value up to the maximum value

– 58 –

SEMAPHORES (4 of 4)SEMAPHORES (4 of 4)

BOOL ReleaseSemaphore (BOOL ReleaseSemaphore (HANDLE hSemaphore,HANDLE hSemaphore,LONG cReleaseCount,LONG cReleaseCount,LPLONG lpPreviousCount)LPLONG lpPreviousCount)

You can find the count preceding the release, but the pointer can be NULL if you do not need this value

The release count must be greater than zero, but if it would cause the semaphore count to exceed the maximum, the call will return FALSE and the count will remain unchanged

There is also an OpenSemaphore function

– 59 –

A SEMAPHORE DEADLOCK DEFECTA SEMAPHORE DEADLOCK DEFECT

There is noThere is no “atomic” wait for multiple semaphore units “atomic” wait for multiple semaphore units But you can release multiple units atomically! Here is a potential deadlock in a thread function

for (i = 0; i < NumUnits; i++)

WaitForSingleObject (hSem, INFINITE);

The solution is to treat the loop as a critical section, guarded by a CRITICAL_SECTION or mutex

Or, a multiple wait semaphore can be created with an event, mutex, and counter

9. Windows SYNCHRONIZATION

OBJECTS

9. Windows SYNCHRONIZATION

OBJECTS

SummarySummary

– 61 –

CRITICAL SECTIONCRITICAL SECTION

Named, Securable Synchronization Object

Accessible from MultipleProcesses

Synchronization

Release

Ownership

Effect of Release

No

No

Enter

Leave

One thread at a time. Recursive

One waiting thread can enter

– 62 –

MUTEXMUTEX

Named, Securable Synchronization Object

Accessible from MultipleProcesses

Synchronization

Release

Ownership

Effect of Release

Yes

Yes

Wait

Release or owner terminates

One thread at a time. Recursive

One waiting thread can gain ownership after last release

– 63 –

SEMAPHORESEMAPHORE

Named, Securable Synchronization Object

Accessible from MultipleProcesses

Synchronization

Release

Ownership

Effect of Release

Yes

Yes

Wait

Any thread can release

N/A – Many threads at a time, up to the maximum count

Multiple threads can proceed, depending on release count

– 64 –

EVENTEVENT

Named, Securable Synchronization Object

Accessible from MultipleProcesses

Synchronization

Release

Ownership

Effect of Release

Yes

Yes

Wait

Set, Pulse

N/A – Any thread can Set or Pulse an event

One or several waiting threads will proceed after a Set or Pulse - Caution

Recommended