【问题标题】:Wanted: Cross-process synch that doesn't suffer from AbandonedMutexException通缉:不受 AbandonedMutexException 影响的跨进程同步
【发布时间】:2009-03-17 13:08:12
【问题描述】:

我有几个线程获取互斥体然后终止。

互斥体存储在主存储库中,并在程序存在时正确释放。但是,当分配了 Mutex 的线程存在时,mutex 会自动释放,并随后获取 AbandonedMutexException(同样根据the documentation)。

如何避免此异常,并在分配线程完成后继续使用互斥锁? .Net 中是否还有另一个更合适的同步结构没有此限制。

注意 - 我正在寻找一种与 Mutex 语义相似的跨进程同步机制。

【问题讨论】:

    标签: .net windows multithreading synchronization mutex


    【解决方案1】:

    回答问题

    AFAIK 不存在这样的 Mutex 类。 AbandonedMutexException 非常烦人,但它代表了一种可能发生的真实情况,没有自动解决方案。

    当你有跨进程,甚至是跨线程通信时,你必须处理这样一个事实,即任何一个参与实体都可能因各种原因意外并突然终止。互斥锁的存在是为了保护资源,如果线程在持有互斥锁时被放弃,操作系统就无法保证它以任何一致的方式留下数据。这非常重要,因为这意味着放弃线程可能会使其他线程依赖的某些不变量无效。

    AbandonedMutexException 是一种主动表示“坏事发生了,您现在处于不确定状态”的方式。这里的操作系统真的没有其他办法了。

    回复您的回答

    EventWaitHandle 与 Mutex 不同,用途不同。

    Mutex 用于保护特定资源,就像锁定语句一样。当一个特定的线程获得一个互斥锁时,就说它拥有这个互斥锁。一次只能有一个所有者。因此,如果所有涉及的线程都同意仅在拥有 Mutex 所有权时才接触资源,则您可以安全地跨线程访问资源。s

    EventWaitHandle 在一定程度上可以可视化为线程安全事件。它具有信号和非信号的概念,任何数量的线程都可以等待它达到信号状态。当它收到信号时,其中一个等待线程将被唤醒并开始处理。

    您可以使用 EventWaitHandle 来实现一种线程安全形式。不是锁定所有权是访问资源的关键,而是从事件发出信号是访问资源的关键。然而,魔鬼再次出现在细节中。

    1. 谁负责发出事件信号?使用互斥体,每个线程基本上都在尖叫“我我我”,操作系统选择一个线程来获胜。使用 EventWaitHandle,您将负责决定下一个线程何时开始。
    2. 当有人通过 taskmgr 杀死进程时会发生什么?如果被杀死的进程有一个线程当前正在响应 EventWaitHandle 上的事件怎么办?
    3. 2 但是当下一个发出等待句柄信号的项目被删除时会发生什么?您必须考虑到这一点以避免死锁。

    【讨论】:

    • 事实证明,就我的目的而言,一个简单的事件同样好(更好,因为它没有被遗弃)。感谢您的详细回答。我不必决定“谁赢”——操作系统仍然决定两个线程中的哪一个赢得 AutoResetEvent.Wait()。
    • @ripper234 但你这样做了。您是调用 Set 方法的响应,从而决定操作系统何时决定谁获胜。
    • 就像我负责释放互斥锁一样。出于我的目的,我特别不希望操作系统为我决定应该释放互斥锁。
    【解决方案2】:

    看起来 EventWaitHandle 做了我想要的。它有一个带名字的构造函数,因此非常适合跨进程同步,而且没有这个问题。

    【讨论】:

      【解决方案3】:

      在收到AbandonedMutexException 后,没有什么可以阻止您使用 Mutex。来自doc:

      下一个请求互斥锁所有权的线程可以处理这个问题 例外并继续,前提是数据的完整性 结构可以验证。

      当然,这假设您知道您(和您的线程)在崩溃时正在做什么,这基本上意味着获取线程也可以在退出之前释放互斥锁。

      所以最终你自己使用EvenWaitHandle 的解决方案比互斥锁更好。

      【讨论】:

        猜你喜欢
        • 2018-05-05
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-07-01
        • 2017-09-22
        • 2012-07-17
        • 2015-12-31
        • 2016-07-06
        相关资源
        最近更新 更多