завершение процесса C ++ - PullRequest
1 голос
/ 06 января 2010

У меня следующая проблема: у меня есть приложение (сервер, который никогда не заканчивается), написанный на C ++, работающий как служба, содержащая внутри основного потока также 3 потока (в основном, выполняющих ввод-вывод).

В главном цикле я ловлю все возможные исключения.

Процесс завершен, и ничего не было напечатано ни основным циклом, ни самими потоками. В журнале событий я увидел, что процесс остановился с кодом 1000.

  1. Windows создает файлы Core как в unix?
  2. Если из журнала событий я получаю адрес памяти, есть ли способ узнать, в какой части приложения это произошло?
  3. Может быть, это подсказка: одновременно с этим я запустил другое приложение (не того типа).

Ответы [ 5 ]

5 голосов
/ 06 января 2010

попробуйте установить windbg в качестве посмертного отладчика.

  1. установка windbg
  2. из командной строки выполнить "windbg -I"
  3. запустите ваше приложение, затем вы, когда ваше приложение получит необработанное исключение, windbg будет активирован.
  4. из windbg используйте "kb" or "!uniqstack", чтобы увидеть трассировку стека.

    ищите здесь больше команд.
    и посмотрите здесь для анализа.

и попробуйте использовать SEH:

#include "windows.h"
#include "stdio.h"

DWORD FilterFunction() 
{ 
 printf("you will see this message first.\n");
 return EXCEPTION_EXECUTE_HANDLER; 
} 


int main(char** argv, int c)
{
 __try
 {
  int this_will_be_zero = (c == 9999);
  int blowup = 1 / this_will_be_zero;
 }
 __except ( FilterFunction()) 
 {
  printf("you will see this message\n");
 }

 return 0;
}
2 голосов
/ 06 января 2010

Вам нужно использовать ключ компилятора / EHa при сборке приложения, чтобы перехватывать структурированные исключения Windows (например, нарушение прав доступа) с помощью конструкций C ++ try / catch.

В Visual Studio это в свойствах проекта Свойства конфигурации -> C / C ++ -> Генерация кода -> Включить исключения C ++. Вы хотите "Да с исключениями SEH (/ EHa)". Я помню, что настройки чтения имеют некоторые существенные недостатки, хотя я не могу вспомнить, какими они были в точности.

Ссылка: MSDN на C ++, модель обработки исключений

Редактировать: Как предполагает whunmr , прямое использование структурированных исключений, вероятно, лучше, чем / EHa

2 голосов
/ 06 января 2010

Имейте в виду, что catch(...) не перехватывает все, что может пойти не так в вашем коде, если вы не используете структурированную обработку исключений. Например,

#include "stdio.h"
int main(char** argv, int c)
{
  try {
    int this_will_be_zero = (c == 9999);
    int blowup = 1 / this_will_be_zero;
  } catch (...) {
    printf("you won't see this message\n");
  }
}
1 голос
/ 06 января 2010

Windows будет использовать любую программу, которую вы используете в качестве отладчика, в зависимости от настройки:

[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\AeDebug]
"Auto"="0"
"Debugger"="My_Debugger" -p %ld -e %ld"
"UserDebuggerHotKey"=dword:00000000

Вы можете изменить My_Debugger на полный путь к любой программе / IDE, которую вы используете для отладки.

Это часто устанавливается доктору Уотсону, который создает запись в журнале аварии, которая не соответствует вашим ожиданиям.

1 голос
/ 06 января 2010

Windows создает файлы Core как в unix?

это не так, автоматически. Однако вы можете включить такие файлы с помощью либо реализуя его в своем коде, либо с помощью внешнего приложения как windbg, или Dr. Уотсон

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

В общем случае это невозможно, если вы не храните файлы с отладочной информацией (pdb)

Может быть, это подсказка: одновременно с этим я запустил другое приложение (не того типа).

это не полезная информация, если оба приложения не взаимодействуют друг с другом

...