1. 产生死锁的原因主要是:
(1) 因为系统资源不足。
(2) 进程运行推进的顺序不合适。
(3) 资源分配不当等。
2. 线程死锁产生的必要条件:
(1)互斥条件:一个资源每次只能被一个进程使用。 (资源固有属性,无法破坏)
(2)请求与保持条件:一个进程因请求资源而阻塞时,对已获得的资源保持不放。 (一次性将资源全部分配)
(3)不可剥夺条件:进程已获得的资源,在末使用完之前,不能强行剥夺。 资源只能由占有者自愿释放;(使用线程优先级,超时机制)
(4)循环等待条件:若干进程之间形成一种头尾相接的循环等待资源关系。(资源有序分配)
避免死锁,
(1) 等待某个资源时,使用超时机制;
(2) 采用消息通信的通信机制;
产生死锁的情况:
1)忘记释放锁
void data_process()
{
EnterCriticalSection();
if(/* error happens */)
return;
LeaveCriticalSection();
}
2)单线程重复申请锁
void sub_func()
{
EnterCriticalSection();
do_something();
LeaveCriticalSection();
}
void data_process()
{
EnterCriticalSection();
sub_func();
LeaveCriticalSection();
}
3)双线程多锁申请
void data_process1()
{
EnterCriticalSection(&cs1);
EnterCriticalSection(&cs2);
do_something1();
LeaveCriticalSection(&cs2);
LeaveCriticalSection(&cs1);
}
void data_process2()
{
EnterCriticalSection(&cs2);
EnterCriticalSection(&cs1);
do_something2();
LeaveCriticalSection(&cs1);
LeaveCriticalSection(&cs2);
}
4)环形锁申请
假设有A、B、C、D四个人在一起吃饭,每个人左右各有一只筷子。所以,这其中要是有一个人想吃饭,他必须首先拿起左边的筷子,再拿 起右边的筷子。现在,我们让所有的人同时开始吃饭。那么就很有可能出现这种情况。每个人都拿起了左边的筷子,或者每个人都拿起了右边的筷子,为了吃饭,他们现在都在等另外一只筷子。此时每个人都想吃饭,同时每个人都不想放弃自己已经得到的一那只筷子。所以,事实上大家都吃不了饭。