PThread RWLock死锁与递归锁

时间:2010-10-21 04:27:21

标签: locking pthreads deadlock

我一直在研究一个小沙盒示例,以帮助我弄清楚如何使用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,这是一个非常人为的例子。它是我正在努力的其他东西的沙盒子,并且想确保我把这部分做好。

5 个答案:

答案 0 :(得分:3)

pthread_rwlock支持递归读锁定,但递归写锁定。如果您在锁定时锁定锁定,则表明您已进入未定义行为领域。这是thfn3()

的情况

如果你将线程称为“读者”(thfn4)和“作者”(thfn3),那就更清楚了。案例一是:

  • 读者试图锁定
  • writer试图锁定并阻止等待读者释放锁定
  • 读者获取锁定
  • 读者尝试再次锁定并阻止等待编写者获取锁定并释放锁定

在这种情况下,读者可能无法再次锁定,因为有一个作者在等待锁定,而潜在的作者会阻止潜在的读者。

案例二是:

  • 作家试图锁定
  • 读者试图锁定并阻止等待作者完成
  • 作家获得锁定
  • writer尝试再次锁定并阻止

这种情况很可能只能通过诉诸rwlock实现的细节来解释。

答案 1 :(得分:1)

您的问题是pthread_rwlock_wrlock(3)不可重入。文档清楚地指出,当线程已经持有锁时调用此方法的结果是未定义的。您的代码专门调用该方法两次而不释放它们之间的锁定。

答案 2 :(得分:0)

答案 3 :(得分:0)

这是开放的雷达错误。

http://openradar.appspot.com/8588290

答案 4 :(得分:0)

我在这个问题上发布了一个解决方法 Pthread RWLock on MAC Deadlocking but not on Linux?

它是独立于平台的,一般方法应该允许其他技巧,如从读写升级等等。