_set_se_translator преодаление границ модуля
От: eks314  
Дата: 10.06.09 17:46
Оценка:
Обнаружены странные баги. Может быть кто-то их полечил?

Есть 2 модуля: DLL и EXE. DLL скомпилено с /EHa, EXE — с /EHs. DLL ставит свою функцию трансляции каких-то SE исключений в С++ исключение CMyException. EXE отлавливает CMyException.

SE происходит в недрах DLL. Отрабатывает функция трансляции, кидается CMyException. Если теперь CMyException не поймано в DLL, а летит за пределы модуля в вызывающий EXE, то вместо того чтобы быть обработаным в EXE оно валит приложение. Точнее приложение падает с оригинальным SE исключением.

Если откомпилить EXE с /EHa, то все работает. Исключение штатно ловится внутри EXE.

Если в DLL поймать CMyException и сделать "throw;", то все падает.
Если в DLL поймать CMyException и создать новый CMyException и кинуть его взамен, то все работает.

И не ясно почему C++ исключение может валить приложение..
Re: _set_se_translator преодаление границ модуля
От: eks314  
Дата: 10.06.09 17:52
Оценка:
Цель — не требовать вызывающий модуль быть /EHa. Получается что это достигается только перехватом C++ исключения во всех экспортируемых DLL функциях. При этом исключение нужно поймать и пересоздать и кинуть заново.. Бред.

Другой вариант решения __try / __except вместо _set_se_translator. Но этот вариант еще хуже, т.к. самодельные __try блоки запрещают иметь в функции объекты с деструкторами и нужно все передавать через ссылки или указатели.
Re[2]: _set_se_translator преодаление границ модуля
От: K13 http://akvis.com
Дата: 11.06.09 04:28
Оценка:
E>Цель — не требовать вызывающий модуль быть /EHa. Получается что это достигается только перехватом C++ исключения во всех экспортируемых DLL функциях. При этом исключение нужно поймать и пересоздать и кинуть заново.. Бред.

Зачем вообще DLL собирать с /EHa ?
плюсовые исключения кидаются через throw
Если же нарвались на невалидный указатель, то надо писать креш-дамп и завершаться.
Re[2]: _set_se_translator преодаление границ модуля
От: Sergey Chadov Россия  
Дата: 11.06.09 10:04
Оценка: 5 (2) +1
Здравствуйте, eks314, Вы писали:

E>Цель — не требовать вызывающий модуль быть /EHa. Получается что это достигается только перехватом C++ исключения во всех экспортируемых DLL функциях. При этом исключение нужно поймать и пересоздать и кинуть заново.. Бред.


Кидать С++-ные исключения за пределы модуля почти всегда плохая идея. Это иногда может быть нормально, если разделение на модули чисто логическое, то есть приложение остается единым. Но в таком случае непонятно почему бы не привести параметры компиляции к общему знаменателю. Если приложение концептуально не едино, например модули могут поставляться другими разработчиками, то такой подход в корне неверен, потому как привязывает этих других разработчиков к точно той же версии рантайма, что и во всех остальных модулях.
Re[3]: _set_se_translator преодаление границ модуля
От: Аноним  
Дата: 15.06.09 15:36
Оценка:
Здравствуйте, K13, Вы писали:

K13>Зачем вообще DLL собирать с /EHa ?

K13>плюсовые исключения кидаются через throw
K13>Если же нарвались на невалидный указатель, то надо писать креш-дамп и завершаться.

MSDN статья "Reading and Writing From a File View"

...
Reading from or writing to a file view of a file other than the page file can cause an EXCEPTION_IN_PAGE_ERROR exception. For example, accessing a mapped file that resides on a remote server can generate an exception if the connection to the server is lost.
...


Это пример случая, когда нужно обрабатывать SEH.
Re[3]: _set_se_translator преодаление границ модуля
От: Аноним  
Дата: 15.06.09 15:54
Оценка:
Здравствуйте, Sergey Chadov, Вы писали:

SC>Кидать С++-ные исключения за пределы модуля почти всегда плохая идея. Это иногда может быть нормально, если разделение на модули чисто логическое, то есть приложение остается единым. Но в таком случае непонятно почему бы не привести параметры компиляции к общему знаменателю. Если приложение концептуально не едино, например модули могут поставляться другими разработчиками, то такой подход в корне неверен, потому как привязывает этих других разработчиков к точно той же версии рантайма, что и во всех остальных модулях.


Наша DLL используется несколькими нашими приложениями. И runtime будет един. В принципе, конечно, мы можем попросить всех пользователей использовать EHa. Но, во-первых, не понятно почему мы должны так делать, ведь механизм _set_se_translator ничего такого в общем не требует (исходя из описания).

У нас есть оговоренный механзм связи наших DLL (общая библиотека). Наша DLL начинает выбиваться из общих правил и ставит доп. требование на вызывающее приложение. Также существует DLL, которая использует проблемную DLL в своих целях. Получается что и ей нужно требовать EHa от пользователя. Лишние связи, о которых хочется избавиться. + вроде бы есть какая-то потеря производительности при использовании EHa вместо EHs, но здесь не очень разбираюсь, может быть несущественно.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.