首页 > 程序开发 > 软件开发 > 其他 >

多线程的那点儿事(之避免死锁)

2011-12-05

【 声明:版权所有,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing @163.com】预防死锁的注意事项:(1)在编写多线程程序之前,首先编写正确的程序,然后再移植到多线程(2)时刻检查自己写的程序有没...

【 声明:版权所有,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing @163.com】

预防死锁的注意事项:

(1)在编写多线程程序之前,首先编写正确的程序,然后再移植到多线程

(2)时刻检查自己写的程序有没有在跳出时忘记释放锁

(3)如果自己的模块可能重复使用一个锁,建议使用嵌套锁

(4)对于某些锁代码,不要临时重新编写,建议使用库里面的锁,或者自己曾经编写的锁

(5)如果某项业务需要获取多个锁,必须保证锁的按某种顺序获取,否则必定死锁

(6)编写简单的测试用例,验证有没有死锁

(7)编写验证死锁的程序,从源头避免死锁

首先,定义基本的数据结构和宏,

typedef struct _LOCK_INFO

{

char lockName[32];

HANDLE hLock;

}LOCK_INFO:

typedef struct _THREAD_LOCK

{

int threadId;

LOCK_INFO* pLockInfo[32];

}THREAD_LOCK;

#define CRITICAL_SECTION_TYPE 1

#define MUTEX_LOCK_TYPE 2

#define SEMAPHORE_LOCK_TYPE 3

#define NORMAL_LOCK_TYPE 4

#define WaitForSingleObject(a, b) \

WaitForSingleObject_stub((void*)a, NORMAL_LOCK_TYPE)

#define EnterCriticalSection(a) \

WaitForSingleObject_stub((void*)a, CRITICAL_SECTION_TYPE)

#define ReleaseMutex(a) \

ReleaseLock_stub((void*)a, MUTEX_LOCK_TYPE))

#define ReleaseSemaphore(a, b, c) \

ReleaseLock_stub((void*)a, SEMAPHORE_LOCK_TYPE))

#define LeaveCriticalSection(a) \

ReleaseLock_stub((void*)a, CRITICAL_SECTION_TYPE))

typedef struct _LOCK_INFO

{

char lockName[32];

HANDLE hLock;

}LOCK_INFO:

typedef struct _THREAD_LOCK

{

int threadId;

LOCK_INFO* pLockInfo[32];

}THREAD_LOCK;

#define CRITICAL_SECTION_TYPE 1

#define MUTEX_LOCK_TYPE 2

#define SEMAPHORE_LOCK_TYPE 3

#define NORMAL_LOCK_TYPE 4

#define WaitForSingleObject(a, b) \

WaitForSingleObject_stub((void*)a, NORMAL_LOCK_TYPE)

#define EnterCriticalSection(a) \

WaitForSingleObject_stub((void*)a, CRITICAL_SECTION_TYPE)

#define ReleaseMutex(a) \

ReleaseLock_stub((void*)a, MUTEX_LOCK_TYPE))

#define ReleaseSemaphore(a, b, c) \

ReleaseLock_stub((void*)a, SEMAPHORE_LOCK_TYPE))

#define LeaveCriticalSection(a) \

ReleaseLock_stub((void*)a, CRITICAL_SECTION_TYPE)) 然后,改写锁的申请函数,

void WaitForSingleObject_stub(void* hLock, int type)

{

/* step 1 */

WaitForSingleObject(hDbgLock);

/* check if lock loops arounds threads */

ReleaseMutex(hDbgLock);

/* step 2 */

if(NORMAL_LOCK_TYPE == type)

WaitForSingleObject((HANDLE)hLock, INFINITE);

else if(CRITICAL_SECTION_TYPE == type)

EnterCriticalSection((LPCRITICAL_SECTION)hLock);

else

assert(0);

/* step 3 */

WaitForSingleObject(DbgLock);

/* add lock to specified threadid list */

ReleaseMutex(hDbgLock);

}

void WaitForSingleObject_stub(void* hLock, int type)

{

/* step 1 */

WaitForSingleObject(hDbgLock);

/* check if lock loops arounds threads */

ReleaseMutex(hDbgLock);

/* step 2 */

if(NORMAL_LOCK_TYPE == type)

WaitForSingleObject((HANDLE)hLock, INFINITE);

else if(CRITICAL_SECTION_TYPE == type)

EnterCriticalSection((LPCRITICAL_SECTION)hLock);

else

assert(0);

/* step 3 */

WaitForSingleObject(DbgLock);

/* add lock to specified threadid list */

ReleaseMutex(hDbgLock);

} 最后,需要改写锁的释放函数。

void ReleaseLock_stub(void* hLock, int type)

{

/* step 1 */

WaitForSingleObject(hDbgLock);

/* remove lock from specified threadid list */

ReleaseMutex(hDbgLock);

/* step 2 */

if(MUTEX_LOCK_TYPE))== type)

ReleaseMutex(HANDLE)hLock);

else if(SEMAPHORE_LOCK_TYPE == type)

ReleaseSemaphore((HANDLE)hLock, 1, NULL);

else if(CRITICAL_SECTION_TYPE == type)

LeaveCriticalSection((LPCRITICAL_SECTION)hLock);

assert(0);

}

void ReleaseLock_stub(void* hLock, int type)

{

/* step 1 */

WaitForSingleObject(hDbgLock);

/* remove lock from specified threadid list */

ReleaseMutex(hDbgLock);

/* step 2 */

if(MUTEX_LOCK_TYPE))== type)

ReleaseMutex(HANDLE)hLock);

else if(SEMAPHORE_LOCK_TYPE == type)

ReleaseSemaphore((HANDLE)hLock, 1, NULL);

else if(CRITICAL_SECTION_TYPE == type)

LeaveCriticalSection((LPCRITICAL_SECTION)hLock);

assert(0);

}

相关文章
最新文章
热点推荐