Основные данные:«Перехват» Windows завершает работу и выполняет команду
Язык C++ (visual C++ 2013). моя программа - это приложение win32, многопоточное (3 потока), и для его разработки он работает как критический процесс (используя RtlSetProcessIsCritical, он выполняет эту работу). Я могу программно включать и выключать его (две функции, одна устанавливает текущий процесс на критический, второй превращает текущий процесс в некритический).
Если я просто нажимаю start -> выключает окна, система, очевидно, сбой с bsod, тот же bsod, который вы получаете, если вы вручную завершите критический процесс.
Как я могу обнаружить, когда окна закрываются/перезапускаются? поэтому я могу выполнить функцию «превратить в некритичную», что приведет к чистому отключению. :)
Один из потоков состоит из цикла, который запускается каждые 5 или 10 секунд, добавив, что обнаружение выключения Windows здесь является единственным жизнеспособным вариантом.
Я пробовал только одну вещь, WM_ENDSESSION, как показано здесь http://msdn.microsoft.com/en-us/library/aa376889%28v=VS.85%29.aspx. но он «не удается» обнаружить остановку os, и он заканчивается bsod.
Я бы нашел несколько примеров или сведений, которые очень полезны. если дополнительные подробности необходимы, дайте мне знать, у меня будет доступ к компьютеру, где моя программа хранится через пару часов. спасибо.
изменить: почему downvote? я учился и хотел спросить о чем-то, что я не могу исправить.
Редактировать: не могли бы вы привести пример того, где/как добавить фактическую проверку сообщения в моем цикле? я не могу справиться с этим, у меня уже есть случай WM_QUERYENDSESSION в инструкции switch .. спасибо.
--------------- EDIT:
я не могу получить его, чтобы работать, независимо от того, что я стараюсь это не будет работать .. моя программа в псевдокоде:
thread 1
{
functionx();
functiony();
}
thread 2
{
functionz();
functionf();
}
thread 3
{
for (;;)
{
functiong();
functionh();
}
}
int main()
{
thread 1;
thread 2;
thread 3;
}
для части Айв GetMessage использовал код здесь http://www.winprog.org/tutorial/window_click.html и повторно отрегулировать, чтобы соответствовать моим потребностям:
HWND hwnd;
MSG Msg;
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch (msg)
{
case WM_QUERYENDSESSION:
function_to_turn_critical_process_OFF();
return 0;
break;
case WM_ENDSESSION:
function_to_turn_critical_process_OFF();
return 0;
break;
}
return 0;
}
петля сообщение:
ok, если я вставляю контур сообщения в main(), как первое, что выполнено, я запускаю проблему номер 1, GetMessage, похоже, переводит всю вещь в сон, поэтому моя программа даже не начинает делать свои вещи.
Если я вставляю петлю сообщений в main() в качестве последней выполняемой вещи (в потоке 3), я запускаю номер проблемы 2, так как поток 3 никогда не заканчивается (петли навсегда), цикл сообщений, вероятно, никогда не запускается. Кроме того, цикл потока 3 содержит немного спящего режима в течение нескольких секунд, ив попытался поместить туда цикл получения сообщения, но он не смог его поймать, я не могу удалить исходный код, не могу изменить петли или удалить небольшую функцию сна.
Если я вставляю петлю сообщения в цикл потока 3, он просто не обнаруживает WM_QUERYENDSESSION, и я заканчиваю работу BSOD на закрытых окнах, поэтому моя функция «turn critical off» не выполняется.
что я могу сделать?Google не помогает в этой конкретной вещи. Я знаю, что в простой программе, которую я предположил бы поставить цикл сообщений в основном, и он будет работать для последнего, но я собираюсь сделать гайки здесь, пытаясь найти место в моем коде для этого цикла сообщений.
любая помощь приветствуется ..
Получаете ли вы какие-либо сообщения в своей цепочке сообщений? Ответ на сообщение WM_QUERY_ENDSESSION приведен ниже. Ваша основная программа должна создать окно, запустить рабочие потоки и затем выполнить цикл обработки сообщений. Когда вы обрабатываете WM_ENDSESSION, измените приоритет приложения и, возможно, сообщите, что потоки закончатся изящно (SetEvent или что-то подобное). – lordjeb