ioftpd read/write 锁实现
//z ioftpd read/write 锁实现 //z 2014-05-09 18:05:41 L.236'21259 BG57IV3@XCL T3344801563.K.F1390913624[T5,L93,R3,V252] #define LOCK_MAX_COUNT 10000 typedef struct _LOCKOBJECT { HANDLE hEvent[2]; LONG volatile lExclusive; } LOCKOBJECT, *LPLOCKOBJECT; VOID ReleaseExclusiveLock(LPLOCKOBJECT lpLockObject); VOID AcquireExclusiveLock(LPLOCKOBJECT lpLockObject); VOID ReleaseSharedLock(LPLOCKOBJECT lpLockObject); VOID AcquireSharedLock(LPLOCKOBJECT lpLockObject); VOID DeleteLockObject(LPLOCKOBJECT lpLockObject); BOOL InitializeLockObject(LPLOCKOBJECT lpLockObject); //z 2014-05-09 16:53:25 L.236'25595 T1731279863.K[T3,L97,R3,V51] //z 初始化。 BOOL InitializeLockObject(LPLOCKOBJECT lpLockObject) { //z 默认不是排他的 lpLockObject->lExclusive = FALSE; //z Event,人工重置事件,初始化状态为已通知。 lpLockObject->hEvent[0] = CreateEvent(NULL, TRUE, TRUE, NULL); if (lpLockObject->hEvent[0] == INVALID_HANDLE_VALUE) return FALSE; //z 用于 share 锁,控制reader数量 lpLockObject->hEvent[1] = CreateSemaphore(NULL, LOCK_MAX_COUNT, LOCK_MAX_COUNT, 0); if (!lpLockObject->hEvent[1]) { CloseHandle(lpLockObject->hEvent[0]); lpLockObject->hEvent[0] = INVALID_HANDLE_VALUE; return FALSE; } return TRUE; } //dtor VOID DeleteLockObject(LPLOCKOBJECT lpLockObject) { HANDLE hEvent; hEvent = lpLockObject->hEvent[0]; //z 关闭 event;做一些必要的检测 if (hEvent && (hEvent != INVALID_HANDLE_VALUE)) { CloseHandle(hEvent); } //z 关闭后,将其设置为 INVALID_HANDLE_VALUE lpLockObject->hEvent[0] = INVALID_HANDLE_VALUE; hEvent = lpLockObject->hEvent[1]; if (hEvent && (hEvent != INVALID_HANDLE_VALUE)) { CloseHandle(hEvent); } lpLockObject->hEvent[1] = INVALID_HANDLE_VALUE; } //z 获取共享锁。 VOID AcquireSharedLock(LPLOCKOBJECT lpLockObject) { //z 得同时在这两个 event 上等待 //z 在人工重置事件上等待成功后,没有变更其状态,等待成功之后,还是已通知状态。 //z 由semaphore来控制read的数量。 WaitForMultipleObjects(2, lpLockObject->hEvent, TRUE, INFINITE); } //z 释放shared lock VOID ReleaseSharedLock(LPLOCKOBJECT lpLockObject) { ReleaseSemaphore(lpLockObject->hEvent[1], 1, NULL); } //z 获取排它锁 VOID AcquireExclusiveLock(LPLOCKOBJECT lpLockObject) { LONG lCount, lLeft; //z 获取排他性,如果此时 lExclusive 为true,那么其已经被其他排它锁持有,那么就在其上等待 while (InterlockedExchange(&lpLockObject->lExclusive, TRUE)) WaitForSingleObject(lpLockObject->hEvent[0], INFINITE); //z 当前 lExclusive 为 false 或者其他排它锁释放了该锁(重置为已通知状态)。 //z 获取排它锁成功;将event置为未通知状态。这样其他排它锁无法获取。 ResetEvent(lpLockObject->hEvent[0]); //z 然后在读取锁上等待;既然是排他的,那么read锁也得排除,可能更改内容 for (;;) { //z 这个等待主要是为了获取下一句 lCount //z 在count大于0时,为已通知状态。等待成功,则count减少1。 WaitForSingleObject(lpLockObject->hEvent[1], INFINITE); //z count 增加1,lCount获取之前的 count 数目。加上这个释放的,现在一共有 (lCount+1)个 ReleaseSemaphore(lpLockObject->hEvent[1], 1, &lCount); //z 还剩下多少需要等待 lLeft = (LOCK_MAX_COUNT - 1) - lCount; //z 没有需要等待的,获取排它锁成功 if (! lLeft) break; //z 放弃时间片 if (lLeft < 10) { //z SwitchToThread():只要有可调度线程,即便优先级较低,也会让其调度。 SwitchToThread(); } //z sleep ,放弃线程拥有的剩余时间片;与上述区别是 Sleep(0):时间片只能让给优先级相同或更高的线程; else Sleep(10); } } VOID ReleaseExclusiveLock(LPLOCKOBJECT lpLockObject) { //z 注意与上述获取排它锁的过程的顺序对比下。 //z 先重置事件为通知状态 SetEvent(lpLockObject->hEvent[0]); //z 设置 lExclusive 为 FALSE,以供其他等待的排它锁可用。 InterlockedExchange(&lpLockObject->lExclusive, FALSE); }
@IS2120#CNBLOGS.T2169364049[T1,L65,R1,V259]:备忘
$ € ₤ ₭ ₪ ₩ ₮ ₦ ₱ ฿ ₡ ₫ ﷼ ¥ ﷼ ₫ ₡ ฿ ₱ ₦ ₮ ₩ ₪ ₭ ₤ € $