欢迎来到天天文库
浏览记录
ID:37893574
大小:37.50 KB
页数:4页
时间:2019-06-02
《pthread_mutex_lock的双重加锁后死锁特性》由会员上传分享,免费在线阅读,更多相关内容在教育资源-天天文库。
1、pthread_mutex_lock的双重加锁后死锁特性一段示例代码,想说明一下可重入函数。所以我在一个函数中使用了pthread_mutex_lock,来说明一旦函数使用了锁,就变成了不可重入的函数。#include#include#include#include#include#includestaticpthread_mutex_tmutex=PTHREAD_MUTEX_INITIALIZER;staticconstchar*constcaller[2]={"m
2、ain","signalhandler"};staticvolatileintsignal_handler_exit=0;staticvoidhold_mutex(intc){printf("enterhold_mutex[caller%s]",caller[c]);pthread_mutex_lock(&mutex);/*保证信号函数退出前,main线程始终拥有锁*/while(!signal_handler_exit&&c!=1){sleep(5);}pthread_mutex_unlock(&mutex);printf("leavehold_mutex[caller%s]",c
3、aller[c]);}staticvoidsignal_handler(intsignum){hold_mutex(1);signal_handler_exit=1;}intmain(){signal(SIGALRM,signal_handler);alarm(3);hold_mutex(0);return0;}上面代码很简单,main函数调用hold_mutex来持有锁。hold_mutex直到SIGALRM信号处理函数返回后,才会释放锁和退出。同时,main利用alarm,在3秒后可以收到信号SIGALRM,而SIGALRM的信号处理函数也会调用hold_mutex。这就保证了,在mai
4、n线程持有锁的过程中,通过信号处理机制,再次进入hold_mutex,来造成“死锁”的场景。用以说明hold_mutex是不可重入的。可是运行结果让我很意外。。。[fgao@fgaotest]#./a.outenterhold_mutex[callermain]enterhold_mutex[callersignalhandler]leavehold_mutex[callersignalhandler]leavehold_mutex[callermain][fgao@fgaotest]#这是怎么回事呢?为什么在main拿到锁以后,信号处理函数还是可以拿到锁呢?我决定在这样试一下,直接在hol
5、d_mutex中再次拿锁。代码变成了下面这样:#include#include#include#include#include#includestaticpthread_mutex_tmutex=PTHREAD_MUTEX_INITIALIZER;staticvoidhold_mutex(intc){if(c==0){return;}printf("enterhold_mutex[caller%d]",c);pthread_mutex_lock(&mutex);h
6、old_mutex(c-1);pthread_mutex_unlock(&mutex);printf("leavehold_mutex[caller%d]",c);}intmain(){hold_mutex(3);return0;}执行结果如下:[fgao@fgaotest]#./a.outenterhold_mutex[caller3]enterhold_mutex[caller2]enterhold_mutex[caller1]leavehold_mutex[caller1]leavehold_mutex[caller2]leavehold_mutex[caller3][fgao@f
7、gaotest]#看到这样的结果,我首先想到难道pthread_mutex_lock是递归锁?但仔细想了想,又推翻了这个想法。递归锁是一种特殊的锁,不大可能会作为默认行为。当我盯着pthread_mutex_lock这个名字,pthread这个关键字给我带来了提示。这个锁是否是跟线程相关呢?当该线程拥有了该锁后,可以继续上锁呢?重读了一遍manual手册,证实了自己的想法。Themutexobjectrefe
此文档下载收益归作者所有