嵌套临界区是否有效?

发布于 12-02 11:13 字数 481 浏览 7 评论 0原文

例如,这有效吗?

CRITICAL_SECTION cs;

::InitializeCriticalSection( &cs );

::EnterCriticalSection( &cs );      // First level
::EnterCriticalSection( &cs );        // Second level

/* do some stuff */

::LeaveCriticalSection( &cs );        // Second level
::LeaveCriticalSection( &cs );      // First level

::DeleteCriticalSection( &cs );

显然,我永远不会故意这样做,但是如果这是由于函数调用而发生的,例如调用“第一级”来锁定复杂(例如搜索)算法的对象和“第二级”,该怎么办?在该对象的访问器函数中被调用?

For example, would this be valid?

CRITICAL_SECTION cs;

::InitializeCriticalSection( &cs );

::EnterCriticalSection( &cs );      // First level
::EnterCriticalSection( &cs );        // Second level

/* do some stuff */

::LeaveCriticalSection( &cs );        // Second level
::LeaveCriticalSection( &cs );      // First level

::DeleteCriticalSection( &cs );

Obviously, I would never intentionally do this, but what if this were to come about as a result of function calls such that the "first level" gets called to lock an object for a complex (e.g. search) algorithm and the "second level" gets called in that object's accessor functions?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

贪了杯2024-12-09 11:13:41

是的,在已经位于同一临界区内部时进入该临界区是有效的。来自文档

线程拥有临界区的所有权后,它可以使
对 EnterCriticalSection 或 TryEnterCriticalSection 的其他调用
而不阻止其执行。这可以防止线程
在等待关键部分时陷入死锁
已经拥有了。线程每次进入临界区
EnterCriticalSection 和 TryEnterCriticalSection 成功。一个线程
每次进入时都必须调用一次 LeaveCriticalSection
关键部分。

Yes it is valid to enter the same critical section while already inside it. From the docs:

After a thread has ownership of a critical section, it can make
additional calls to EnterCriticalSection or TryEnterCriticalSection
without blocking its execution. This prevents a thread from
deadlocking itself while waiting for a critical section that it
already owns. The thread enters the critical section each time
EnterCriticalSection and TryEnterCriticalSection succeed. A thread
must call LeaveCriticalSection once for each time that it entered the
critical section.

尾戒2024-12-09 11:13:41

来自文档

线程拥有临界区的所有权后,它可以对 EnterCriticalSection 或 TryEnterCriticalSection 进行其他调用,而不会阻止其执行。这可以防止线程在等待它已经拥有的临界区时发生死锁。每次 EnterCriticalSection 和 TryEnterCriticalSection 成功时,线程都会进入临界区。线程每次进入临界区都必须调用一次 LeaveCriticalSection。

From the documentation:

After a thread has ownership of a critical section, it can make additional calls to EnterCriticalSection or TryEnterCriticalSection without blocking its execution. This prevents a thread from deadlocking itself while waiting for a critical section that it already owns. The thread enters the critical section each time EnterCriticalSection and TryEnterCriticalSection succeed. A thread must call LeaveCriticalSection once for each time that it entered the critical section.

夏有森光若流苏2024-12-09 11:13:41

验证其他两个帖子。快速查看 WinDbg 中的 Critical 部分会发现,cricital 部分维护一个整数变量来保存递归计数。

0:001> dt RTL_CRITICAL_SECTION
+0x000 DebugInfo : Ptr32 _RTL_CRITICAL_SECTION_DEBUG
+0x004 LockCount : Int4B
+0x008 RecursionCount : Int4B
+0x00c OwningThread : Ptr32 Void
+0x010 LockSemaphore : Ptr32 Void
+0x014 SpinCount : Uint4B 

递归计数 -
一个线程可以多次获取临界区。这个领域
指示同一线程获取临界区的次数。经过
默认情况下,该字段的值为0,表示没有线程拥有该
关键部分。

To validate the other two posts. Quick look at Critical section in WinDbg shows that cricital section maintains an integer variable to hold Recursion counts.

0:001> dt RTL_CRITICAL_SECTION
+0x000 DebugInfo : Ptr32 _RTL_CRITICAL_SECTION_DEBUG
+0x004 LockCount : Int4B
+0x008 RecursionCount : Int4B
+0x00c OwningThread : Ptr32 Void
+0x010 LockSemaphore : Ptr32 Void
+0x014 SpinCount : Uint4B 

RecursionCount -
It is possible for a thread to acquire a critical section more than once. This field
indicates how many times the same thread has acquired the critical section. By
default, the value of this field is 0, indicating that there is no thread owning the
critical section.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文