我有两个进程,一个写入内存映射文件 - producer
- 而另一个从内存文件中读取 - consumer
。
第一个进程使用 CreateMutex()
函数创建互斥锁,并将initialOwner
参数设置为 TRUE
代码如下:
制作人:
mutexHandle = CreateMutex(NULL, TRUE, TEXT("producerMutex"));
while (condition)
{
WaitForSingleObject(mutexHandle, INFINITE);
// write a random number in the memory mapped file;
// pause the program and prompt the user to open consumer process; do this only one time
ReleaseMutex(mutexHandle);
}
消费者:
mutexHandle = OpenMutex(SYNCRONIZE , FALSE, TEXT("producerMutex"));
while (condition)
{
WaitForSingleObject(mutexHandle, INFINITE);
// read from the file, print it in terminal
ReleaseMutex(mutexHandle);
}
问题是,如果initialOwner
设置为TRUE
则在producer
完成之前,使用者将无法访问互斥锁。为什么?如果initialOwner
设置为 FALSE
,则应用程序可以工作,但它不应该也与TRUE
上设置的它一起使用吗?
来自ReleaseMutex
文档:
要释放其所有权,线程必须调用 ReleaseMutex 一次 每次获得所有权时(通过CreateMutex 或等待功能)。
在此代码中:
mutexHandle = CreateMutex(NULL, TRUE, TEXT("producerMutex"));
while (condition)
{
WaitForSingleObject(mutexHandle, INFINITE);
// write a random number in the memory mapped file;
// pause the program and prompt the user to open consumer process; do this only one time
ReleaseMutex(mutexHandle);
}
您获得互斥锁 N+1
次 - 1 次通过 CreateMutex()
与 bInitialOwner=TRUE
,N
次通过 WaitForSingleObject()
在循环中。但是你在循环中只释放了N
次。 因此,在循环之后仍保持互斥锁,直到线程退出。
要解决此问题,您需要跳过循环中WaitForSingleObject
的第一个调用 - 实际上,您已经是互斥锁的所有者,不需要此调用。 你可以像这样编写代码:
if (mutexHandle = CreateMutex(0, TRUE, L"producerMutex"))
{
goto __firstTime;
do
{
WaitForSingleObject(mutexHandle, INFINITE);
__firstTime:
// write a random number in the memory mapped file;
ReleaseMutex(mutexHandle);
// pause the program and prompt the user to open consumer process; do this only one time
} while (condition);
CloseHandle(mutexHandle);
}
您需要在访问完共享资源后立即调用ReleaseMutex()
。切勿在按住互斥锁时"暂停"程序。 首先释放它,然后暂停。
查看initialOwner
参数的说明:
创建互斥功能:
如果此值为 TRUE 并且调用方创建了互斥锁,则调用线程将获得互斥锁对象的初始所有权。否则,调用线程不会获得互斥锁的所有权。若要确定调用方是否创建了互斥锁,请参阅返回值部分。
您需要在准备好使用信息后调用互斥锁上的ReleaseMutex()
。