C# 为什么调用Semaphore.WaitOne时会出现死锁?

C# 为什么调用Semaphore.WaitOne时会出现死锁?,c#,deadlock,semaphore,C#,Deadlock,Semaphore,以下代码中的run()函数是从其他线程同时调用的。根据应用程序的一般设计,在任何时候、任何一行上都可能发生ThreadAbortException,我无法更改 调用pool.Release()时,我有时会收到信号量lexception。我认为如果在调用“pool.WaitOne()”时发生线程中止异常,就会发生这种情况。在调试尝试期间,在发生信号量lexception之后,运行代码没有问题。在该异常之后,pool.WaitOne()调用和其他事情的工作与预期的一样 在本地调试会话期间,我无法获得

以下代码中的
run()
函数是从其他线程同时调用的。根据应用程序的一般设计,在任何时候、任何一行上都可能发生ThreadAbortException,我无法更改

调用
pool.Release()
时,我有时会收到
信号量lexception
。我认为如果在调用“pool.WaitOne()”时发生线程中止异常,就会发生这种情况。在调试尝试期间,在发生信号量lexception之后,运行代码没有问题。在该异常之后,
pool.WaitOne()
调用和其他事情的工作与预期的一样

在本地调试会话期间,我无法获得死锁情况。但是,在远程计算机中,我的代码出现死锁。我使用远程调试器附加该进程,并在
pool.WaitOne()行上看到执行被锁定

我不知道这是怎么发生的,我做错了什么。非常感谢您的帮助

private static object poolLocker = new object();
private static Semaphore _pool;
private static Semaphore pool
{
    get
    {
       if (_pool == null)
           lock (poolLocker)
       if (_pool == null)
       {
           int count = myMaximumThreadCount;
           _pool = new Semaphore(count, count);
       }
       return _pool;
    }
}

private void run()
{
    try
    {
        pool.WaitOne();

        do_something_that_may_throw_exception();
    }
    finally
    {
        try
        {
            pool.Release();
        }
        catch (SemaphoreFullException) { }
    }
}

尝试将
属性中信号量对象的初始化更改为:

private static Semaphore pool
{
    get
    {
       if (_pool == null)
           lock (poolLocker)
       if (_pool == null)
       {
           int count = myMaximumThreadCount;
           _pool = new Semaphore(0, count);
       }
       return _pool;
    }
}

此信号量的初始计数应设置为零。

我已找到死锁的原因;这和我问的问题无关,所以这是一个糟糕的问题,对此表示抱歉。问题中的代码似乎没有问题

原因:在doiSothTyth.TyMayPaulSub异常()函数中,调用C++库的一个外部函数。当C++函数中出现错误时,抛出SEHExtExchange。但是,在我的尝试中,只能在具有HandleProcessCorruptedStateExceptions和SecurityCritical属性的函数中捕获此异常。这个函数恰好调用了问题的run()函数。但是,run()函数的最后一部分将被执行另外,如果您有一个正在使用的(IDisposable对象){…},并且SEHException发生在其中;不会调用对象的Dispose()函数

我使用了以下函数来调用C++函数;一切都很顺利:

SafeCall(()=> call_external_cpp_function());

[HandleProcessCorruptedStateExceptions]
[SecurityCritical]
internal static void SafeCall(Action action)
{
    try
    {
        action();
    }
    catch (System.Threading.ThreadAbortException) { throw; }
    catch (System.Threading.ThreadInterruptedException) { throw; }
    catch (Exception ex)
    {
        throw new Exception(ex.Message);
    }
}

隐藏异常的代码(空的
catch
块)对您的调查没有帮助@Damien\u不信者感谢您的建议。我只是为了捕捉信号量lexception而更改了该部分,而远程计算机上也发生了相同的死锁。报告所有未处理的异常;没有报告任何例外情况。