Подтвердить что ты не робот

Есть ли опция gcc, чтобы все внешние функции "C" не могли распространять исключения?

Есть ли какой-либо способ, не доставляющий атрибут для каждого прототипа функции, чтобы gcc знал, что C-функции никогда не могут распространять исключения, т.е. что все функции, объявленные внутри extern "C", должны быть __attribute__((nothrow))? Идеал был бы в командной строке -f.

4b9b3361

Ответ 1

Вы всегда можете использовать -fno-exceptions, который гарантирует, что компилятор С++ не генерирует код распространения исключений.

Ответ 2

Боковое примечание:
Вы уверены, что компилятор "все эти функции никогда не бросать" - это именно то, что вы хотите?

Это не обязательно, так что функции extern "C" ... не могут распространять/запускать исключения. Возьмите пример:

class Foo {
public:
    class Away {};
    static void throwaway(void) { throw Away(); }
}

extern "C" {
    void wrap_a_call(void (*wrapped)(void)) { wrapped(); }
}

int main(int argc, char **argv)
{
    wrap_a_call(Foo::throwaway);
    return 0;
}

При компиляции и запуске создается функция C-linkage wrap_a_call(), которая при вызове, как указано выше, с радостью вызовет исключение:

$ ./test
terminate called after throwing an instance of 'Foo::Away'
Abort(coredump)

т.е. может быть "утечка исключений" с помощью extern "C" (путем вызова указателей на функции), и только потому, что вы используете/вызываете extern "C" функции в определенном месте на С++, не гарантирует, что при вызове этих исключений не могут быть исключены.

Ответ 3

Когда возникает исключение, создается прерывание, которое разворачивает стек и переопределяет существующий стек. Он поднимается до точки, где используется try/except синтаксис. Это означает, что у вас нет накладных расходов, если вы не используете исключения. Только накладные расходы в памяти/времени находятся в блоках try/catch и разворачивании стека в throw().

Если ваши c-функции не генерируют исключения, ваши служебные данные будут находиться только в космосе, когда вы вызываете try/catch на вашем С++, но одинаковы для любого количества исключений. (и небольшой промежуток времени при инициализации этого небольшого пробела).

Ответ 4

GCC 4.5, похоже, автоматически оптимизирует их для меня. Действительно, эта строка появляется в списке изменений на http://gcc.gnu.org/gcc-4.5/changes.html:

  • Теперь GCC оптимизирует код обработки исключений. В частности, оптимизированы области очистки, которые оказались неэффективными.