《Win32多线程程序设计》学习笔记 第4章 同步控制之 信号量(Semaphores)
win32中的一个semaphore可以被锁住最多n次,其中n是semaphore被产生时指定的。n常常被设计成用来代表“可以锁住一份资源”的线程资源,不过并非单独一个线程就不能拥有所有的锁定。理论上,mutex是semaphore的一种退化,如果你产生一个semaphore并令最大值为1,那就是一个mutex。
产生信号量(semaphore)
代码
Creates or opens a named or unnamed semaphore object.To specify an access mask for the object, use the CreateSemaphoreEx function.
HANDLE WINAPI CreateSemaphore(
LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, //安全属性
LONG lInitialCount, //The initial count for the semaphore object. This value must be greater than or equal to zero and less than or equal to lMaximumCount.
LONG lMaximumCount, //The maximum count for the semaphore object. must be greater than zero.
LPCTSTR lpName //semaphore的名称,任何线程或进程都可以用这个名称应用到这个semaphore,可以为NUll。
);
返回值:如果成功传回一个handle,否则为NULL,如果指定的semaphore名称已经存在,该函数还是会成功的,GetLastError会传回ERROR_ALREADY_EXIST.
HANDLE WINAPI CreateSemaphore(
LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, //安全属性
LONG lInitialCount, //The initial count for the semaphore object. This value must be greater than or equal to zero and less than or equal to lMaximumCount.
LONG lMaximumCount, //The maximum count for the semaphore object. must be greater than zero.
LPCTSTR lpName //semaphore的名称,任何线程或进程都可以用这个名称应用到这个semaphore,可以为NUll。
);
返回值:如果成功传回一个handle,否则为NULL,如果指定的semaphore名称已经存在,该函数还是会成功的,GetLastError会传回ERROR_ALREADY_EXIST.
获得锁定
可以使用任何一种wait...函数要求锁定一个semaphore。如果semaphore的限值不为0,wait()...函数会立刻返回。一旦semaphore的现值降为0,就表示资源已经耗尽,此时,任何线程如果调用wait...()函数,就必然要等待,知道某个锁定被解除为止。
解除锁定
调用ReleaseSemaphore解除锁定。
Increases the count of the specified semaphore object by a specified amount.
BOOL WINAPI ReleaseSemaphore(
HANDLE hSemaphore, //A handle to the semaphore object.
LONG lReleaseCount, //Semaphore现值的增额,该值不可以为负值或0
LPLONG lpPreviousCount //传回semaphore的原来的值
);
返回值:如果成功,传回TRUE
BOOL WINAPI ReleaseSemaphore(
HANDLE hSemaphore, //A handle to the semaphore object.
LONG lReleaseCount, //Semaphore现值的增额,该值不可以为负值或0
LPLONG lpPreviousCount //传回semaphore的原来的值
);
返回值:如果成功,传回TRUE
lpPreviousCount 所传的值是一个瞬间值。不可以把lReleaseCount加上*lpPreviousCount 当做是semaphore的现值,因为其他线程可能已经改变了semaphore的值。
与mutex不同,调用ReleaseSemaphore的那个线程,并不一定就是得调用Wait...()的那个线程。任何线程都可以在任何时间调用ReleaseSemaphore(),解除被任何线程锁定的semaphore。
MSDN中有个使用semaphore的例子,可以看一下