2009-11-19 3 views
18

Я настраиваю восстановление для служб Windows для перезапуска с одноминутной задержкой после сбоев. Но я никогда не получал его, чтобы фактически перезапустить службу (даже с самыми вопиющими ошибками).Восстановление служб Windows, не перезагружающих службы

я получаю сообщение в EventViewer:

описание для события с кодом (1) в источнике (MyApp.exe) не может быть найден. На локальном компьютере могут не отображаться необходимые данные реестра или файлы DLL сообщений, чтобы отображать сообщения с удаленного компьютера. Вы можете использовать флаг/AUXSOURCE = для получения этого описания; см. «Справка и поддержка». Следующая информация является частью события: Нарушение прав доступа по адресу 00429874 в модуле «MyApp.exe». Запись адреса 00456704.

Есть ли что-то еще, что мне нужно сделать? Есть ли что-то в моем коде (я использую Delphi), который должен быть установлен, чтобы включить это?

+0

Этот вопрос может помочь http://stackoverflow.com/questions/220382/how-can-a-windows-service-programmatically-restart-itself?rq=1 –

ответ

19

Service Recovery предназначен для обработки случая, когда служба аварийно завершает работу - поэтому, если вы перейдете к taskmgr и щелкните правой кнопкой мыши «завершение процесса» в вашем процессе обслуживания, логика восстановления должна начать работать. Я не считаю, что сервис логика восстановления срабатывает, если ваш сервис выходит изящно (даже если он выходит с ошибкой).

Также сообщение eventvwr указывает, что ваше приложение называлось API ReportEvent, определяющим идентификатор события 1. Но вы не зарегистрировали свои сообщения о событиях в средстве просмотра событий, чтобы он не смог преобразовать идентификатор события 1 в значимую текстовую строку.

+1

Благодарю. Это пролило некоторый свет на ситуацию. Я обнаружил, что после выполнения «Конечного процесса» из taskmgr он производит это в средстве просмотра событий: В течение 60000 миллисекунд будет выполнено следующее корректирующее действие: Перезапустите службу. Теперь моя проблема (связанная с моим кодированием) заключается в том, что она заканчивается «Un-Gracefully», так что логика восстановления будет нажата. –

+1

Если вы вызовете ExitProcess, что должно быть достаточно. –

8

Служба восстановления работает только для неожиданного выхода (exit (-1)) call. На протяжении всего пути, который мы используем для остановки службы обычным способом, не будет работать для восстановления. Если вы хотите остановить службу и хотите восстановить работоспособность, вызовите exit (-1), и вы увидите сообщение об ошибке как «служба остановлена ​​с неожиданной ошибкой», а затем ваша служба перезапустится по мере восстановления.

+0

+1 Спасибо за ваш ответ. Помогло мне много – Jehof

+2

Для тех, кто ищет точный метод, попробуйте Environment.Exit (-1); –

0

Если вы убиваете службу из диспетчера задач, забыли логику восстановления. В фоновом режиме менеджер задач «убивает» процесс «stop service». и, как можно предположить, это не служебный сбой. Это заставило меня убить его с помощью Visual Studio. В диспетчере задач щелкните правой кнопкой мыши процесс обслуживания. Выберите debug. В Visual studio выберите Debug-> Terminate All. И теперь у вас есть симулированное обслуживание. В этом случае логика восстановления работает нормально.

0

Менеджер управления службами попытается перезапустить службу, если вы настроили ее для перезапуска SCM. Подробно here в документации на структуру SERVICE_FAILURE_ACTIONS.

считается Служба потерпела неудачу, когда она завершается, не сообщая статус SERVICE_STOPPED к контроллеру службы.

Это может быть точно настроен путем установки fFailureActionsOnNonCrashFailures флага SERVICE_FAILURE_ACTIONS_FLAG структуры, см here). Этот параметр можно установить из апплета «Службы», установив флажок «Включить действия для остановок с ошибками» на вкладке восстановления.

Если этот элемент является TRUE, а служба настроила действие отказа, действия отказа в очереди, если процесс обслуживания завершается, не сообщая статус SERVICE_STOPPED или если он входит в состоянии SERVICE_STOPPED но член dwWin32ExitCode структуры SERVICE_STATUS не ERROR_SUCCESS (0). Если этот член FALSE, и служба настроила действия сбоя, действия сбоя ставятся в очередь только в том случае, если служба завершает работу без предоставления статуса SERVICE_STOPPED.

Так, в зависимости от того, как вы структурировали свой сервис, как вы настроили свои действия отказа и что вы делаете, когда у вас есть «неустранимая ошибка» может быть достаточно, чтобы назвать ExitProcess() или exit() и возвращает не ноль стоимость. Тем не менее, вероятно, безопаснее обеспечить, чтобы ваша служба выходила без кода, связанного с SCM, сообщающего SCM, что ваша служба достигла состояния SERVICE_STOPPED. Это гарантирует, что ваши действия по сбою ВСЕГДА произойдут ...

Смежные вопросы