System::Threading::Mutex, вызывается из несинхронизированного блока кода. Неожиданный тупик

В попытке избавить мой графический интерфейс от условий гонки и взаимных блокировок у меня есть следующая функция, которую я вызываю из c'tor, и всякий раз, когда мне нужен сервис, который разделяет мои именованные mutex предоставить свой вклад:

void EnvCapt::FireServiceAndOrHold() {
    try {
        mutTimerSyncEx->ReleaseMutex();
        Thread::Sleep(100); //Time enough for the service to complete.
        if (!mutTimerSyncEx->WaitOne(3 * int_ms)) {//int_ms = the polling period
            //Must've been doubly locked or worse.
            mutTimerSyncEx->ReleaseMutex();
            FireServiceAndOrHold();
        }
    } catch (Exception ^ ex) {
        //Released unheld mutex. Retake control.
        mutTimerSyncEx->WaitOne();
        FireServiceAndOrHold();
    }
}

Это работает относительно хорошо, но я звоню по этому поводу, прежде чем позволить службе, теперь я готов принять ввод, поэтому он никогда не пытается ждать, пока я не отпущу мьютекс для него. Прежде чем я попытаюсь изменить порядок вещей, я хотел бы знать, что происходит с вышеуказанной функцией. Я получаю ошибку:

Метод синхронизации объекта был вызван из несинхронизированного блока кода.

Потому что называть релиз на mutex это не было WaitOne Я брослю, я поймаю это, зная, что я свободен, чтобы завладеть этим и продолжить. Но я не прав. Он навсегда висит на WaitOne() заявление. Я знаю, что другой процесс делает все это время, потому что он заперт в моем втором окне отладчика. Это не касается мьютекса.

ОБНОВИТЬ

Я попытался изменить порядок, который я сначала предложил, это казалось хорошим, но теперь я нахожу, что мьютекс является всего лишь видом Global, несмотря на то, что у него есть Global \ name.

  • Это разделяется, потому что, когда мой GUI c'tor это firstInstance ложно, поэтому я пытаюсь взять его под контроль.

  • Это не является общим, потому что, когда вызовы GUI WaitOne() на нем графический интерфейс блокируется на неопределенный срок. В то время как сервис танцует прямо через призыв к WaitOne() без заботы в мире.

1 ответ

Решение

Я просто подумал, что может быть не так для вас там:

Подсказка: вы не можете освободить мьютекс от имени другого процесса! Другой процесс должен освободить мьютекс, если он его держит:

Process 1:                           Process 2:
============                         =============

    WaitOne (locks the mutex)

    // do work                       WaitOne (awaits the mutex)

    // do more work

    // done
    ReleaseMutex         ------>     WaitOne returns from the wait _with 
                                             the mutex locked_
Другие вопросы по тегам