Переменные условия не похожи на мьютексы. Я имею в виду, что они могут использоваться не только одним потоком, управляющим ими. Мьютекс, который защищает условную переменную, обрабатывается таким образом, но он блокируется только на короткие периоды времени, разблокируется вручную потоком после нажатия (сигнализации) условной переменной и автоматически потоком, ожидающим такой удар.
Вы можете иметь полностью отдельный поток (например, ваш детектор взаимоблокировок, назовем его потоком 3), просто нажмите одну из условных переменных, и она разбудит ожидающий ее поток.
Обычный вариант использования переменных условия - потоки ожидают пинка, а затем проверяют, чтобы убедиться, что вы все равно работаете (не думайте, что работа есть, просто потому, что переменная была отброшена). Это чтобы позаботиться о ложных пробуждениях.
Одна возможность состоит в том, чтобы иметь «глобальный» флаг deadlock_occurred, который поток 3 устанавливает при обнаружении взаимоблокировки, а затем иметь поток 3, запускающий все переменные условия.
Первое, что должны сделать потоки 1 и 2 после пробуждения, это проверить этот флаг и предпринять соответствующие действия (вероятно, выйти из потока).
Вы обнаружите, что у вас гораздо меньше проблем типа тупиковой ситуации, если вы будете разрабатывать свои приложения так, чтобы потоки отвечали за их собственный срок службы. Слишком легко внешне уничтожить потоки, когда они не находятся в состоянии, которое может быть прервано. Не поймите меня неправильно, есть и другие способы справиться с этим (например, с помощью точек отмены), но мое испытанное и проверенное решение на сегодняшний день является самым простым, которое я когда-либо нашел.