Monitor是否使用内核维护的布尔变量



我们知道像AutoResetEventManualResetEvent这样的事件只是由内核维护的布尔变量。与Events相比,Monitor具有额外的功能,如线程所有权和递归锁,就像System.Threading.Mutex一样。

Monitor是否使用内核维护的相同布尔变量?如果是,那么Monitoris在透视或操作系统内核方面与Mutex相同吗?

Monitor采用对象引用,对象有一个特殊的头,CLI使用它来存储有关锁的信息,以及在需要时如何将锁提升为内核事件。

对象标头

典型对象标头格式中的最高有效字节如下所示。

|31            0|    
----------------| 
|7|6|5|4|3|2| --|
| | | | | |
| | | | | +- BIT_SBLK_IS_HASHCODE : set if the rest of the word is a hash code (or sync block index)
| | | | +--- BIT_SBLK_IS_HASH_OR_SYNCBLKINDEX : set if hashcode or sync block index is set
| | | +----- BIT_SBLK_SPIN_LOCK : lock the header for exclusive mutation on spin
| | +------- BIT_SBLK_GC_RESERVE : set if the object is pinned
| +--------- BIT_SBLK_FINALIZER_RUN : set if finalized already
+----------- BIT_SBLK_AGILE_IN_PROGRESS : set if locking on AppDomain 

在对象上创建锁/监视器后,CLR将查看标头,并首先确定是否需要在同步块表中查找任何锁定信息,它只需查看设置的位即可完成此操作。如果没有瘦锁,它将创建一个(如果适用(。如果存在瘦锁定,它将尝试旋转并等待它。如果标头已膨胀,它将在同步块表中查找锁定信息。

瘦锁基本上由应用程序域索引、递归级别和托管线程Id组成。线程Id由锁定线程原子设置,如果为零,或者如果为非零,则使用简单的旋转等待来多次重读锁状态以获取锁。如果一段时间后锁定仍然不可用,则需要升级锁定(如果尚未升级(,将瘦锁定扩展到同步块表,并且需要根据内核事件(如自动重置事件(向操作注册true*锁定。

请注意,这是我的一个更大的稍微相关的答案的摘录,如果你非常无聊,可以看看这里

为什么C#中的锁需要实例?

最新更新