исключения xsubpp c ++ - PullRequest
       1

исключения xsubpp c ++

1 голос
/ 23 июня 2011

xsubpp может генерировать код обработки исключений для файлов c / c ++, преобразованных из файлов .xs. Он генерирует следующий фрагмент кода для меня

TRY {
    char *  CLASS = (char *)SvPV_nolen(ST(0));
    Example *   RETVAL;

    RETVAL = new Example();
    ST(0) = sv_newmortal();
    sv_setref_pv( ST(0), CLASS, (void*)RETVAL );

}
BEGHANDLERS
CATCHALL
    sprintf(errbuf, "%s: %s\tpropagated", Xname, Xreason);
ENDHANDLERS

Но при компиляции сгенерированного кода я получаю ошибки компиляции, поскольку TRY, BEGHANDLERS, CATCHALL, ENDHANDLERS не были определены нигде в заголовочных файлах perl. Я изменил свой код, чтобы определить вышеупомянутые токены следующим образом.

#define TRY try
#define BEGHANDLERS
#define CATCHALL catch (...) {
#define ENDHANDLERS }

Но я не могу дать значимые определения Xname и Xreason. Верны ли приведенные выше определения? Как мы справляемся с вышеупомянутыми ключевыми словами

Ответы [ 3 ]

2 голосов
/ 23 июня 2011

Это относится к категории "ну, не делай этого".(Канонический ответ «Доктор, мне больно, когда я делаю X»).Посмотрите на сгенерированный код:

CATCHALL
    sprintf(errbuf, "%s: %s\tpropagated", Xname, Xreason);
ENDHANDLERS

Это не распространение исключения.Он печатает сообщение, а затем полностью игнорирует тот факт, что произошла ошибка!

Поддержка Perl для C ++ довольно слабая.Это не должно быть таким удивительным;Perl был написан на C и нацелен на C для своих внешних подпрограмм.

Мое предложение: обрабатывать исключения, но не использовать этот довольно клункий материал исключений, предоставляемый для 'free' из xsubpp.Вместо этого напишите блок try ... catch ... самостоятельно.Заставьте блок catch преобразовать перехваченные исключения C ++ в исключения perl.Позвоните Perl_croak для фатальных ошибок, Perl_warn для нефатальных ошибок.

И удачи.Взаимодействие Perl с C / C ++ не так просто.

Некоторые потенциально полезные ссылки:

0 голосов
/ 21 мая 2013

Похоже, что он собирает информацию не зависящим от языка образом, а затем распространяет ее в perl. Код, который вы показываете, генерирует сообщение, а затем должен был сгенерировать код для его распространения:

ENDHANDLERS
if (errbuf[0])
Perl_croak(aTHX_ errbuf);

Так что вам просто нужно выбрать то, что, по вашему мнению, будет полезно кому-то, пытающемуся его отладить. Я думаю, что включение в сообщение того, что исключение пришло из C ++, было бы полезно; и, как сказал предыдущий ответ, включите детали из e.what (). Так что включение чего-то подобного должно работать:

#include <stdexcept>

#define TRY try
#define BEGHANDLERS catch(std::exception const &e){
#define CATCHALL const char * Xreason = e.what();
#define ENDHANDLERS }

const char * Xname = "C++ exception";
0 голосов
/ 23 июня 2011

Я ничего не знаю о xsubpp (или Perl, если на то пошло), но если можно предположить, что выброшенное исключение происходит от std::exception, то вы можете сделать что-то вроде этого:

#define CATCHALL catch(const std::exception& ex) {

ТогдаXreason может быть сопоставлено с ex.what().Xname хитрее.Вы можете сделать что-то вроде typeid(ex).name(), что может быть лучше, чем ничего.

Это лучшее решение, которое я могу придумать, если только не существует какой-то специфический трюк для xsubpp.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...