我一直在研究一个小沙盒示例,以帮助我弄清楚如何使用rwlocks。一切看起来都相当简单,但是我每隔一段时间就会在我的例子中遇到僵局,并且不明白为什么会发生这种情况。
我已将代码示例放在pastebin上,因为它不仅仅是几行代码:http://pastebin.org/359203
如果您运行该示例。当它最终死锁时,最后三个打印语句将是两种情况之一:
之一:
th4: request lock
th3: request lock
th4: locked
2:
th3: request lock
th4: request lock
th3: locked
基于输出。对我来说,似乎第二次调用锁定函数时会出现最终的死锁,无论是读取锁定还是写入锁定。但由于其中一个线程具有锁定,并且同一个线程调用第二个锁定函数,为什么它会死锁?更有趣的是,在这个小案例中导致僵局的是什么?
请注意,我使用的是Mac OS X,这是一个非常人为的例子。它是我正在努力的其他东西的沙盒子,并且想确保我把这部分做好。
答案 0 :(得分:3)
pthread_rwlock支持递归读锁定,但不递归写锁定。如果您在锁定时锁定锁定,则表明您已进入未定义行为领域。这是thfn3()
。
如果你将线程称为“读者”(thfn4)和“作者”(thfn3),那就更清楚了。案例一是:
在这种情况下,读者可能无法再次锁定,因为有一个作者在等待锁定,而潜在的作者会阻止潜在的读者。
案例二是:
这种情况很可能只能通过诉诸rwlock实现的细节来解释。
答案 1 :(得分:1)
您的问题是pthread_rwlock_wrlock(3)
不可重入。文档清楚地指出,当线程已经持有锁时调用此方法的结果是未定义的。您的代码专门调用该方法两次而不释放它们之间的锁定。
答案 2 :(得分:0)
查看我使用apple报告的错误。这就是问题所在。
https://bugreport.apple.com/cgi-bin/WebObjects/RadarWeb.woa/7/wo/0blX77DJS8lBTTxVnTsNDM/5.83.28.0.13
答案 3 :(得分:0)
这是开放的雷达错误。
答案 4 :(得分:0)
我在这个问题上发布了一个解决方法 Pthread RWLock on MAC Deadlocking but not on Linux?
它是独立于平台的,一般方法应该允许其他技巧,如从读写升级等等。