Как перехватывать фатальные ошибки
От: MT  
Дата: 18.11.03 11:03
Оценка:
Можно ли перехватить фатальные ошибки вроде "Memory could not be read"?
Пробовал так:

  try {

  } catch (...) { 

  }


Но очевидно что не все ошибки перехватываются...
Быстрее, лучше, дешевле — выбери любые два.
(Старая инженерная поговорка)
Re: Как перехватывать фатальные ошибки
От: Vamp Россия  
Дата: 18.11.03 11:05
Оценка:
MT>Но очевидно что не все ошибки перехватываются...
Далеко не все фатальные ошибки являются С++ исключениями.
Да здравствует мыло душистое и веревка пушистая.
Re: Как перехватывать фатальные ошибки
От: Аноним  
Дата: 18.11.03 11:09
Оценка: 1 (1)
Здравствуйте, MT, Вы писали:


Пробуй так:

MT>
 __try {

} __except (...) { 

}
Re[2]: Как перехватывать фатальные ошибки
От: MT  
Дата: 18.11.03 11:10
Оценка:
Здравствуйте, Vamp, Вы писали:

MT>>Но очевидно что не все ошибки перехватываются...

V>Далеко не все фатальные ошибки являются С++ исключениями.


Т.е. является ошибкой уровня ОС (неперехватываемая)?

Как с ними бороться — писать проги без ошибок, использовать "IF" ?
Быстрее, лучше, дешевле — выбери любые два.
(Старая инженерная поговорка)
Re[2]: Как перехватывать фатальные ошибки
От: MT  
Дата: 18.11.03 11:13
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Здравствуйте, MT, Вы писали:



А>Пробуй так:


MT>>
А> __try {

А>} __except (...) { 

А>}
А>


Какой хедер-фаил надо включить в программу для __try/__except?
Быстрее, лучше, дешевле — выбери любые два.
(Старая инженерная поговорка)
Re[3]: Как перехватывать фатальные ошибки
От: Vamp Россия  
Дата: 18.11.03 11:20
Оценка:
MT>Т.е. является ошибкой уровня ОС (неперехватываемая)?
А что ты вообще понимаешь под фатальной ошибкой уровня ОС?
Да здравствует мыло душистое и веревка пушистая.
Re[3]: Как перехватывать фатальные ошибки
От: Lorenzo_LAMAS  
Дата: 18.11.03 11:23
Оценка:
никакого
Of course, the code must be complete enough to compile and link.
Re[4]: Как перехватывать фатальные ошибки
От: MT  
Дата: 18.11.03 11:23
Оценка:
Здравствуйте, Vamp, Вы писали:

MT>>Т.е. является ошибкой уровня ОС (неперехватываемая)?

V>А что ты вообще понимаешь под фатальной ошибкой уровня ОС?

Ошибки "memory couldn't be read/accessed" — бывают часто, но как перехватить?
try/catch(...) не перехватывает.
Быстрее, лучше, дешевле — выбери любые два.
(Старая инженерная поговорка)
Re: Как перехватывать фатальные ошибки
От: _Obelisk_ Россия http://www.ibm.com
Дата: 18.11.03 11:28
Оценка: 5 (2) +1
Здравствуйте, MT, Вы писали:

MT>Можно ли перехватить фатальные ошибки вроде "Memory could not be read"?



Использовать что-то типа Purify и активней применять smart pointer-ы.

Такие ошибки надо не перехватывать, а фиксить.



Душа обязана трудиться! (с) Н.Заболоцкий.
Re[3]: Как перехватывать фатальные ошибки
От: SergeMukhin Россия  
Дата: 18.11.03 11:30
Оценка: 1 (1)
Здравствуйте, MT, Вы писали:

MT>Здравствуйте, Аноним, Вы писали:


А>>Здравствуйте, MT, Вы писали:



А>>Пробуй так:


MT>>>
А>> __try {

А>>} __except (...) { 

А>>}
А>>


MT>Какой хедер-фаил надо включить в программу для __try/__except?



для MS — никакой, но почитай сначала про SEH и его взаимодействие с CPP исключениями.
... << RSDN@Home 1.1.0 stable >>
---
С уважением,
Сергей Мухин
Re: Как перехватывать фатальные ошибки
От: Аноним  
Дата: 18.11.03 11:36
Оценка:
MT>Можно ли перехватить фатальные ошибки вроде "Memory could not be read"?

А unexpected() тоже не помогает?
Re[2]: Как перехватывать фатальные ошибки
От: MT  
Дата: 18.11.03 11:45
Оценка:
Здравствуйте, Аноним, Вы писали:

MT>>Можно ли перехватить фатальные ошибки вроде "Memory could not be read"?


А>А unexpected() тоже не помогает?


Нет, не помогает
Быстрее, лучше, дешевле — выбери любые два.
(Старая инженерная поговорка)
Re: Как перехватывать фатальные ошибки
От: Аноним  
Дата: 18.11.03 11:46
Оценка: 2 (1)
Здравствуйте, MT, Вы писали:

MT>Можно ли перехватить фатальные ошибки вроде "Memory could not be read"?

[]
MT>Но очевидно что не все ошибки перехватываются...

У Микрософта есть такая странная функция под названием _set_se_translator (см. в MSDN), которая позволяет преобразовывать структурное исключение Windows (см. SEH) в исключение C++.
Re[2]: Как перехватывать фатальные ошибки
От: Дмитрий Наумов  
Дата: 18.11.03 11:49
Оценка:
Здравствуйте, Аноним, Вы писали:

MT>>Можно ли перехватить фатальные ошибки вроде "Memory could not be read"?


А>А unexpected() тоже не помогает?


Не в тему. SEH, без определенных телодвижений, не отмаплен в C++ исключения.
Re[2]: Как перехватывать фатальные ошибки
От: Lorenzo_LAMAS  
Дата: 18.11.03 11:49
Оценка:
А>А unexpected() тоже не помогает?

А как она тут должна была помочь?
Of course, the code must be complete enough to compile and link.
Re[5]: Как перехватывать фатальные ошибки
От: Vamp Россия  
Дата: 18.11.03 11:53
Оценка: +1
V>>А что ты вообще понимаешь под фатальной ошибкой уровня ОС?

MT>Ошибки "memory couldn't be read/accessed" — бывают часто, но как перехватить?


Их не должно быть вовсе. Это значит, ты не туда обращаешься в памяти. Следи за указателями.
Да здравствует мыло душистое и веревка пушистая.
Re[2]: Как перехватывать фатальные ошибки
От: SergeMukhin Россия  
Дата: 18.11.03 12:00
Оценка:
Здравствуйте, <Аноним>, Вы писали:

А>Здравствуйте, MT, Вы писали:


MT>>Можно ли перехватить фатальные ошибки вроде "Memory could not be read"?

А>[]
MT>>Но очевидно что не все ошибки перехватываются...

А>У Микрософта есть такая странная функция под названием _set_se_translator (см. в MSDN), которая позволяет преобразовывать структурное исключение Windows (см. SEH) в исключение C++.



мы пользуемся SetUnhandledExceptionFilter — он практически все перехватывает, но у нас своя обработка ошибок, а так много статей есть и, в том числе в MSDN, о внутренностях SEH и как его подружить с CPP.
... << RSDN@Home 1.1.0 stable >>
---
С уважением,
Сергей Мухин
Re: Как перехватывать фатальные ошибки
От: Дмитрий Наумов  
Дата: 18.11.03 12:34
Оценка:
Здравствуйте, MT, Вы писали:

Сделай примерно так

#define MapSehToCppExeption  _set_se_translator(SEH::TranslateSehToCExeption);


class ERRSPEC SEH: public EXCEPTION
{
  public:

    //Оператор возврата кода исключения
    operator unsigned long();
  
    //Контекст процессора
    CONTEXT          mContext;
    // hook-функция
    static void _cdecl TranslateSehToCExeption(UINT ,EXCEPTION_POINTERS* pep);

  private:
    //Конструктор для создания объекта SEH при возникновении исключения
    SEH(PEXCEPTION_POINTERS pep);

    static char* GetSehMsg(SEH& e,char* s);
    EXCEPTION_RECORD mEr;    
  
};
Как перехватывать фатальные ошибки
От: Шахтер Интернет  
Дата: 19.11.03 01:49
Оценка: 144 (21) -1
#Имя: FAQ.vc.seh
Здравствуйте, MT, Вы писали:

MT>Можно ли перехватить фатальные ошибки вроде "Memory could not be read"?

MT>Пробовал так:

MT>
MT>  try {

MT>  } catch (...) { 

MT>  }
MT>


MT>Но очевидно что не все ошибки перехватываются...


Рассказываю (и показываю). То что вы называете фатальными ошибками на самом деле являются SEH-исключениями операционной системы (внимательно читаем Рихтера). Они возбуждаются в различных ситуациях, как то: доступ по неправильному адресу, переполнение стека, деление на нуль, ошибка сопроцессора и.т.д. Будучи неперехваченным, SEH-исключение вызывает появление хорошо известного окна с предложением впаять разработчику и принудительной остановки процесса. Как перехватывать такие исключения в C++. Метод __try __except обсуждать не буду, поскольку его использование в C++ программах -- это дурной тон и возможный конфликт с родными C++ исключениями. Наиболее простой подход -- использовать catch(...). Для того, чтобы это работало, необходимо правильно настоить компилятор. Насчет VC++ 6.0 не помню, а вот в 7.0/7.1 придётся повыделываться. Заходим на вкладочку свойств проекта C/C++ Code Generation. Там есть строчка Enable C++ exception. Смело ставим в этой строчке No. Дальше двигаемся в конец к секции Command Line. На соотвествующей вкладочке есть окошко, Additional Options. Вот здесь надо прописать /EHac. Почему так, спросите у Билла Гейтса. Чтобы жизнь была интересней и разнообразней, наверное. Не всё ж галочки в property tab мышкой переключать. В чем недостаток этого подхода -- невозможно определить тип исключения, и ,что более серьёзно, возникают проблемы с плавающей арифметикой. Имеется более усовершенствованный метод. Заключается он в использовании так называемого se транслятора. Вот примерный код.


#include <eh.h>

static void se_translator(unsigned int code,_EXCEPTION_POINTERS *)
 {
  if( code==EXCEPTION_FLT_DENORMAL_OPERAND   ||
      code==EXCEPTION_FLT_DIVIDE_BY_ZERO     ||
      code==EXCEPTION_FLT_INEXACT_RESULT     ||
      code==EXCEPTION_FLT_INVALID_OPERATION  ||
      code==EXCEPTION_FLT_OVERFLOW           ||
      code==EXCEPTION_FLT_STACK_CHECK        ||
      code==EXCEPTION_FLT_UNDERFLOW
    )
    {
     short cw=???;        
        
     __asm { 
              fninit 
              fldcw  cw
           }
    }

  throw Exception(CPUError(code));
 }
 
void Setup_SE_translator()
 {
  _set_se_translator(se_translator);
 }


Смысл в следующем. Вызовом функции _set_se_translator можно инсталировать функцию, которая будет получать управление в случае возникновения в текущем потоке SEH-исключения. Главное назначение этой функции -- получить код SEH-исключения, завернуть в подходящую обёртку и выбросить нормальное C++ исключение. Которое в дальнейшем можно поймать обычным catch. Коды этих исключений можно получить из windows.h, а описание -- в MSDN в статье про EXCEPTION_RECORD. Среди этих кодов есть семейство особо важных, связанных с плавающей точкой. При получении одного из этих кодов, надо делать маленькую дополнительную обработку. А именно, нужно командой fninit сбросить сопроцессор в нормальное состояние. Ну и загрузить подходящее слово управление. Иначе флаги исключений по-прежнему будут висеть в сопроцессоре, что вызовет возбуждение нового исключения при попытке его снова заюзать. Вообще, использование исключений сопроцессора -- это отдельный нетривиальный вопрос. Поскольку с ним связан целый рад фокусов, на которые можно напороться.
... << RSDN@Home 1.1 beta 2 >>
В XXI век с CCore.
Копай Нео, копай -- летать научишься. © Matrix. Парадоксы
Re[2]: Как перехватывать фатальные ошибки
От: Sergey_BG Россия  
Дата: 08.02.05 12:47
Оценка:
Здравствуйте, Шахтер, Вы писали:

Ш>Вообще, использование исключений сопроцессора -- это отдельный нетривиальный вопрос. Поскольку с ним связан целый рад фокусов, на которые можно напороться.


А интересно где нибудь можно по подробней про это почитать?
Сергей
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.