死锁防御战

在某些应用场景下,能够做到预防死锁的发生。本文会描述三种情形:

  1. Lock Ordering
  2. Lock Timeout
  3. Deadlock Detection

Lock Ordering

多个线程需要相同的锁来完成代码顺畅运行,但是访问锁的顺序是不同的,那么就可能会发生死锁的情况。

也就是说,如果多个线程需要相同的锁,但是他们对锁的访问顺序是相同的,那么就不可能会出现死锁的情况。

Thread 1:
    lock A
    lock B

Thread 2:
    wait for A
    lock C (when A locked)

Thread 3:
    wait for A
    wait for B
    wait for C

如果现在有一个线程,需要多个锁(和 Thread 3 类似),它必须要找既定的顺序去获取锁,它不能在没获取前面锁的情况下(例如:A)去获取排在后面的锁(例如:B)。

“锁排序”是一种简单而有效的死锁预防机制。但是,只有在获取任何锁之前就知道所需的所有锁才能使用这种方式防御。

Lock Timeout

另一个死锁预防机制是对尝试“获取锁”设置超时时长,这意味着尝试获取锁的线程只会在放弃之前阻塞这么长的时间。

如果一个线程在给定的超时时间内仍没有成功获取所有必要的锁,那么它将阻塞并释放所有已持有的锁,等待一段随机时间,然后重试。

等待的随机时间用于让其他线程尝试获取相同的锁,从而让应用程序继续运行而不阻塞。

下面的例子就是两个线程尝试以不同的顺序获取相同的锁,然后线程阻塞和重试:

Thread 1 locks A
Thread 2 locks B

Thread 1 attempts to lock B but is blocked
Thread 2 attempts to lock A but is blocked

Thread 1's lock attempt on B times out
Thread 1 backs up and releases A as well
Thread 1 waits randomly (e.g. 257 millis) before retrying.

Thread 2's lock attempt on A times out
Thread 2 backs up and releases B as well
Thread 2 waits randomly (e.g. 43 millis) before retrying.

上例中,Thread 2 比 Thread 1 先 200ms 进行重新尝试并且在这种情况下很大可能会成功获取两个必要锁。Thread 1 将继续等待 lock A。当Thread 2运行结束,Thread 1 也能够获取两个锁。(除非Thread 2 或者其他线程在又开始插足锁得获取)

注:锁超时并不意味着线程已经死锁,也可能意味着持有锁的线程(导致另一个线程超时)需要很长的时间来完成它的任务。

另外,如果有很多的线程竞争相同的资源,他们仍然有可能多次的同时重试,即使超时和阻塞。这种情况在两个线程在重试之前等待0到500ms可能不会发生,但是如果是10到20个线程,那么情况就不一样了。它和两个线程等待相用时间或者近乎相同的时间再重试的情况差不多。

但是,锁的超时机制并不能在Java的同步代码块中设置超时,你将不得不创建自定义锁类或使用java.util.concurrency包中的一个Java 5并发结构,编写自定义锁并不困难,但超出本文范围,有兴趣的自行了解。

Deadlock Detection

死锁检测是一种较重的死锁防御机制,针对无法获取锁顺序和锁超时不可行的情况。

每当线程takes锁时,都会在线程和锁的数据结构中注明。另外,线程requests锁也会在数据结构中注明。

当线程请求锁的请求被拒绝时,线程可以遍历锁图来检查死锁。例如,如果线程A请求 lock 7,但是 lock 7被线程B持有,线程A会检测线程B是否请求线程A已经持有的锁(如果有)。如果线程B请求是线程A已经持有的锁,则发生死锁。

当然,大部分情况会更加复杂,往往都是多个线程造成死锁。

那么发现线程死锁该如何做呢?

一种可能的操作时释放所有锁,阻塞等待一段随机时间,然后重试。这和更简单的锁超时机制类似,只是线程仅在确定发生死锁的时候进行阻塞,而不仅根据发生锁超时来判断。但是,如果很多线程正在争夺相同的锁,即使它们阻塞并等待,它们也可能会重复地陷入僵局。

一个更好的选择是确定和分配线程的优先级,以便于阻塞一个(或几个)线程,其余的线程继续获取他们所需的锁,就像没有死锁发生一样。如果分配给线程的优先级是固定的,相同的线程将总是被富裕更高的优先级。为了避免这种情况,可以在检测死锁时随机分配优先级。

原文链接:

http://tutorials.jenkov.com/java-concurrency/deadlock-prevention.html#timeout

我的博客

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,711评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,079评论 3 387
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 159,194评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,089评论 1 286
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,197评论 6 385
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,306评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,338评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,119评论 0 269
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,541评论 1 306
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,846评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,014评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,694评论 4 337
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,322评论 3 318
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,026评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,257评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,863评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,895评论 2 351

推荐阅读更多精彩内容

  • 一、多线程 说明下线程的状态 java中的线程一共有 5 种状态。 NEW:这种情况指的是,通过 New 关键字创...
    Java旅行者阅读 4,673评论 0 44
  • ReentrantLock 介绍 一个可重入的互斥锁,它具有与使用{synchronized}方法和语句访问的隐式...
    tomas家的小拨浪鼓阅读 4,047评论 1 4
  • 接着上上节 thread ,本节主要介绍mutex的内容,练习代码地址。<mutex>:该头文件主要声明了与互斥量...
    jorion阅读 12,480评论 2 4
  • 三分明月诗, 诗美不凭吹。 吹得诗仙闷, 闷愁愚昧追。 附花屋主人萧寒原诗: 涧深水浪急,饮马意迟迟。檀溪一跃过,...
    艾思阅读 542评论 27 36
  • 清晨醒来 房间寂静明朗 阳光倾泻 望见幸福美满 冬日 天气严寒 但人心安暖 十二月的积雪 一月的葡萄架 或许 春天...
    安生_ba14阅读 123评论 0 2