升级锁如何避免读/写锁中的死锁



我理解升级锁试图解决经典死锁的例子,其中两个并发线程持有读锁并试图获取写锁将死锁。

线程A: S锁(已获取)

线程B: S锁(已获取)

线程A: X锁(等待线程B释放S锁)

线程B: X锁(等待A释放S锁)DEADLOCKED

为什么升级锁没有同样的问题?该文档说,只有一个线程可以被授予升级锁,并且允许在其他线程仍然持有S锁的情况下这样做。有人能解释一下为什么运行此模式的两个并发线程不会陷入死锁吗?

  lock.AcquireSharedLock()      // Thread A and B both acquired this S lock
  lock.EnterUpgradeableReadLock();  // Only one (e.g. A) acquired U lock and other (e.g. B) is blocked here.
  if(somecondition)
  {
    lock.AcquireExclusiveLock();   // A tries to acquire X lock. But wouldn't it get blocked since B is already holding onto S lock? B is already blocked, so this has to be a deadlock
  }

有趣的是,我刚刚回答了SQL Server和UPDATE语句的相同问题:UPDATE锁如何防止常见形式的死锁?

答案的关键方面是可升级事务从不使用s锁。他们立即u型锁。因此,s锁和x锁之间永远不会有冲突。

在你的例子中,

lock.AcquireSharedLock()

不应该存在。您可以 S-lock U-lock。

最新更新