_set_se_translator
C++ の Win32 ハンドルとして例外 (C の構造化例外は例外) を入力します。
_se_translator_function _set_se_translator(
_se_translator_function seTransFunction
);
パラメーター
- seTransFunction
作成する C. の構造化例外の変換関数へのポインター。
戻り値
前の関数が後で復元できるように _set_se_translator に登録する前の変換関数へのポインターを返します。前の関数が設定されていない場合の既定の動作を復元するには戻り値を使用できます ; この値は null になることがあります。
解説
_set_se_translator の関数が C++ によって入力された例外として Win32 例外 (C) の構造化例外を処理する方法を提供します。それぞれに C.C++ の例外が C++ catch ハンドラーによりまず C. の例外にクラス型を属性として使用したりすることができる C++. の例外のラッパー クラスを定義します。このクラスを使用するには内部例外処理機構を C. の例外によって発生するというカスタム C の例外の変換関数をインストールします。変換関数では C++ catch ハンドラーでキャッチできる入力された例外をスローできます。
_set_se_translator を使用する場合 /EHa を使用する必要があります。
カスタム変換関数を指定するには引数として移動の関数の名前で _set_se_translator を呼び出します。作成した変換関数は try ブロックはスタックの関数の呼び出しに一度だけ呼び出されます。既定の変換関数はありません。
変換関数はスローC++ の . で入力される例外はにする必要があります。これをスローすることに加えて任意の場合 (ログ ファイルへの書き込みなどのプログラムなど) は変換関数が呼び出された回数がプラットフォーム依存するため正常に動作しないことがあります。
マルチスレッド環境では変換関数はスレッドごとに別々に保持されます。それぞれの変換関数を新しいスレッドが増します。したがって各スレッドは独自の移動を処理する必要があります。_set_se_translator は1 種類のスレッドに固有です。; 別の DLL は別の移動の関数をインストールできます。
作成する seTransFunction の関数はネイティブ コンパイルされた関数である必要があります (/clr でコンパイルされます)。これは引数として _EXCEPTION_POINTERS の Win32 構造に符号なし整数ポインターにするためです。引数はWin32 API GetExceptionCode と GetExceptionInformation の関数呼び出しの戻り値はです。
typedef void (*_se_translator_function)(unsigned int, struct _EXCEPTION_POINTERS* );
_set_se_translator ではCRT に動的にリンクするときに影響を及ぼします ; プロセス内の別の DLL は _set_se_translator を呼び出しそれ自体とそのハンドラーを置き換えることがあります。
マネージ コード (/clr でコンパイルしたコード) の _set_se_translator はネイティブ コードとマネージ コードの混合使用する場合変換がネイティブ コードの生成された例外に影響を与えることに注意してください。System::Exception が発生したときにマネージ コードで生成されたマネージ例外は変換関数で (など) ルーティングされません。マネージ コードで Win32 関数を使用する RaiseException 発生する例外またはがゼロによる除算などのシステム例外による例外は変換を通じてルーティングされます。
必要条件
ルーチン |
必須ヘッダー |
---|---|
_set_se_translator |
<eh.h> |
_set_se_translator で提供される機能は /clr: 純粋 のコンパイラ オプションでコンパイルされたコードでは使用できません。
互換性の詳細については、「C ランタイム ライブラリ」の「互換性」を参照してください。
使用例
// crt_settrans.cpp
// compile with: /EHa
#include <stdio.h>
#include <windows.h>
#include <eh.h>
void SEFunc();
void trans_func( unsigned int, EXCEPTION_POINTERS* );
class SE_Exception
{
private:
unsigned int nSE;
public:
SE_Exception() {}
SE_Exception( unsigned int n ) : nSE( n ) {}
~SE_Exception() {}
unsigned int getSeNumber() { return nSE; }
};
int main( void )
{
try
{
_set_se_translator( trans_func );
SEFunc();
}
catch( SE_Exception e )
{
printf( "Caught a __try exception with SE_Exception.\n" );
}
}
void SEFunc()
{
__try
{
int x, y=0;
x = 5 / y;
}
__finally
{
printf( "In finally\n" );
}
}
void trans_func( unsigned int u, EXCEPTION_POINTERS* pExp )
{
printf( "In trans_func.\n" );
throw SE_Exception();
}
_set_se_translator で提供される機能はマネージ コードで使用できないがネイティブ コードが #pragma unmanaged を使用して表される限りネイティブ コードが /clr スイッチの下にコンパイルにはネイティブ コードでこのマッピングを使用する可能性があります。構造化例外が割り当てられているマネージ コードで未処理 pragma 生成されると例外コードとマークする必要があります。次のコードはの使用方法を示します。詳細については、「プラグマのディレクティブと __Pragma のキーワード」を参照してください。
// crt_set_se_translator_clr.cpp
// compile with: /clr
#include <windows.h>
#include <eh.h>
#include <assert.h>
#include <stdio.h>
int thrower_func(int i) {
int j = i/0;
return 0;
}
class CMyException{
};
#pragma unmanaged
void my_trans_func(unsigned int u, PEXCEPTION_POINTERS pExp )
{
printf("Translating the structured exception to a C++"
" exception.\n");
throw CMyException();
}
void DoTest()
{
try
{
thrower_func(10);
}
catch(CMyException e)
{
printf("Caught CMyException.\n");
}
catch(...)
{
printf("Caught unexpected SEH exception.\n");
}
}
#pragma managed
int main(int argc, char** argv) {
_set_se_translator(my_trans_func);
DoTest();
return 0;
}
同等の .NET Framework 関数
該当なし標準 C 関数を呼び出すには、PInvoke を使用します。詳細については、「プラットフォーム呼び出しの例」を参照してください。