2011-06-23 71 views
1

xsubpp可以爲從.xs文件轉換而來的c/C++文件生成異常處理代碼。它產生了下面的一段代碼,我xsubpp C++異常

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,包羅萬象,ENDHANDLERS沒有在perl的頭文件中的任何地方定義。我修改了我的代碼來定義上述這些令牌。

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

但是我無法給出Xname和Xreason的有意義的定義。上述定義是否正確?我們如何處理上述關鍵字

+0

你檢查,如果這些'#define'令牌可見的實現代碼? – iammilind

回答

2

這屬於「不要那麼做」類別。 (對「醫生」的規範答案,當我做X時會感到痛苦)。看看生成的代碼:

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

這不會傳播異常。它正在打印一條消息,然後完全忽略發生錯誤的事實!

Perl對C++的支持很弱。這應該不會令人驚訝; perl是用C語言編寫的,針對C語言的外部子程序。

我的建議是:處理異常,但不要使用那些爲'免費'提供的klunky異常東西,從xsubpp。請自己編寫try ... catch ...塊。使catch塊將那些捕獲的C++異常轉換爲perl異常。致電Perl_croak致命錯誤,Perl_warn致命錯誤。

祝你好運。將perl連接到C/C++並不容易。

一些潛在的有用的鏈接:

+0

感謝您的建議和鏈接。現在已經過去幾個星期了,我只能寫一個最小類的擴展。 – Surya

0

我一無所知xsubpp(或Perl,對於這個問題),但如果拋出的異常可以假設從std::exception派生,那麼你可以做這樣的事情:

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

然後Xreason可映射到ex.what()Xname比較棘手。你可以使它像typeid(ex).name(),這可能比沒有好。

這是我能想到的最好的解決方案,除非有一些xsubpp特定的技巧。

0

它看起來就像它以與語言無關的方式收集信息,然後將其傳播給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";