Win32 multi-threaded program design learning notes (Chapter 4)

zhaozj2021-02-08  191

Win32 multi-threaded program design learning notes (Chapter 4)

So far, I have known how to create threads, destroy the thread and how to determine if a thread is over; how can I use threads, manage threads, how to make threads to operate correctly and difficult to do with multi-threaded program design.

Everyone knows that the thread has concurrency, there is a number of threads in the same time period, and when these threads are available at the same time, there is a problem. Just like in the supermarket reservoir, the item box is empty, when turning and gets the item, it is found to be occupied. At this time, the item box is the same data I said, and the person refers to the thread.

So, how to let threads cooperate with each other, do not interfere with each other? ------ Coordinating threads are completed by synchronization mechanisms. As mentioned in the book: "There are multiple synchronous mechanisms to be used. Which of the issues are used to solve the problem, these synchronization mechanisms can also be used together to generate more sophisticated mechanisms ".

First, let's take a look at a synchronization mechanism that is most likely; it contains design ideas of synchronous mechanisms, and holds it. It can also hold other synchronization mechanisms.

1: Critical Sections (Key Areas, Critical Regions)

Program fragment:

Critical_section gboxkey;

DWORD WINAPI Threadfun (lpvoid n)

{

// Enter key areas (scenario: close the item box, diagram the key)

EntercreiticalSection (& gboxkey); (1)

// Handle some indivisible operations. . . . .

// (Scenario: Turning items, reservoir, go shopping ....)

// Leave the key area (Scenario: Open the item box, take out the stored item, plug in the key)

LeavecreiticalSection (& gboxkey); (2)

}

void main ()

{

// Initialize the global lock (scenario: the key to generate the item box)

InitializeCriticalSection (& gboxkey);

// Generate two threads (Scenario: Prepare two people to grab a piece of item)

Handle Hman1 = CreateThread (Null, 0, Threadfun, ...);

Handle Hman2 = CreateThread (null, 0, threadfun, ...;

CloseHandle (HMAN1);

CloseHandle (HMAN2);

// Delete the global lock (scenario: Delete the key of the item box)

DeletecriticalSection (& gboxkey);

}

According to the above program, I will not happen in the "supermarket reservoir" described in the beginning of the note, and will not have the possibility of being taken away. Due to the concurrency of threads, from I saw a empty box to me in the item in the item in the item, it should be indiscriminately; otherwise, the item box I have seen will be robbed at any time. go. So how do you guarantee that the operation is continuous, can not be divided? Simple: See empty box, close the box, make the key (1), at this time, others can't use this box. When I no longer need the box, open the box, insert the key (2), you can use it. The above is a basic idea for multi-threaded processing shared resources.

2: Mutexes (Mluo)

Program fragment:

Handle HBoxKey; DWORD WINAPI THREADFUN (LPVOID N)

{

// Enter key areas (scenario: close the item box, diagram the key)

WaitForsingleObject (HBoxKey, Infinite); (1)

// Handle some indivisible operations. . . . .

// (Scenario: Turning items, reservoir, go shopping ....)

/ Leave Key Areas (Scenario: Open the item box, take out the stored items, plug in the key)

ReleaseMutex (HBoxKey); (2)

}

void main ()

{

// Initialize the global lock (scenario: the key to generate the item box)

HBoxKey = Createmutex (NULL, FALSE, NULL);

// Generate two threads (Scenario: Prepare two people to grab a piece of item)

Handle Hman1 = CreateThread (Null, 0, Threadfun, ...);

Handle Hman2 = CreateThread (null, 0, threadfun, ...;

CloseHandle (HMAN1);

CloseHandle (HMAN2);

// Delete the global lock (scenario: Delete the key of the item box)

CloseHandle (HBoxKey);

}

did you see? Regardless of the idea of ​​shared resources, or from the program code, it is only a difference between using Mutexes and using critical sections; but as a Mutexes mechanism, it is definitely the reason; we will see such a situation, After I took the key, because some factors couldn't come back, then this box could no longer be used. That is, if the Critical Sections thread is rid of the way, then the thread is no longer caught in Critical Sections (a resource is wasting), and threads that need to enter critical sections will stop in the entry no longer execute, thread Always ending.

How to do? (Solve with WaitforsingleObject)

Remember the WAITFORSINGLEOBJECT learned in the previous chapter? The previous chapter mainly uses it to wait for the end of the thread, but this function's role is not limited to this, here, we will enter a small step before, explore the wonderful use of WaitForsingleObject this function.

prototype:

DWORD WAITFORSINGLEOBJECT (HANDLE HOBJECT, DWORD TIME);

HOBJECT: Handle waiting for the object (represents a core object), in the previous chapter represents threaded handle, not, hobject is a core object, that is, as long as it is a core object, WaitForsingleObject can handle, the principle of processing is "When the core object is excited, the function returns" (how many core objects is there.

Here, I have encountered a Mutex core object, and Mutex's definition is: "When there is no thread owns the MUTEX, and there is a thread is waiting for the Mutex, which is a short-handed excitation. State, so that wait ... () is returned, then in other cases, Mutex is in an unstimed state. "

Ok, we have further understanding the waitforsingleObject function, then how do I solve the difficulties encountered by critical sections? When ReleaseMutex is called before the end of the Mutex thread (whether the thread is when it is, or forgets to call ReleaseMutex), then other threads waiting for this MUTEX to wait for this MUTEX. With this value, I will solve the problem. Program fragment:

DWORD RC = WaitForsingleObject (hmutex);

IF (rc == Wait_Object_0)

{

// Normal processing

}

Else

{

IF (rc == Wait_abandoned_0)

{

// There is no normal release MUTEX (such as a thread with MUTEX death)

}

}

I think, from the perspective of notes, the above to Mutex description can help me get started very quickly, as for Mutex more detailed instructions, or have to take a book .. (Of course, I hope that this paragraph can help you understand MUTEXJ)

in conclusion:

Critical_section Mutex core object

InitializecriticalSECTION () CREATEMUTEX ()

Openmutex ()

EntercriticalSection () WaitforsingleObject ()

LeavecriticalSection () ReleaseMutex ()

DeletecriticalSECTION () CloseHandle ()

Note: The above text is purely to strengthen memory, content or unknown, or even mistakes, please forgive me, hurry !!!

转载请注明原文地址:https://www.9cbs.com/read-3141.html

New Post(0)