__cdecl
Microsoft 固有の仕様 →
__cdecl は、C および C++ プログラムの既定の呼び出し規約です。 スタックは呼び出し元によってクリーンアップされるため、vararg 関数を実行できます。 __cdecl 呼び出し規約は、各関数呼び出しにスタック クリーンアップ コードを含めるように要求するため、__stdcall よりも大きな実行可能ファイルを作成します。 次の一覧は、この呼び出し規約の実装例を示しています。
要素 |
実装 |
---|---|
引数を渡す順序 |
右から左。 |
スタック メンテナンスの役割 |
呼び出し元の関数によって、スタックから引数がポップされます。 |
名前装飾規約 |
C リンケージを使用する __cdecl 関数をエクスポートする場合を除いて、アンダースコア (_) 文字が名前の前に付けられます。 |
大文字と小文字の変換規約 |
大文字小文字は変換されません。 |
注意
関連情報については、「装飾名」を参照してください。
変数名または関数名の前に __cdecl 修飾子を置きます。 C の名前と呼び出し規約は既定であるため、__cdecl を x86 コードで使用する必要があるのは、/Gv (vectorcall)、/Gz (stdcall)、または /Gr (fastcall) コンパイラ オプションを指定したときだけです。 /Gd コンパイラ オプションは、__cdecl 呼び出し規約を強制的に適用します。
ARM と x64 のプロセッサでは、__cdecl はコンパイラによって受け入れられますが、通常は無視されます。 ARM と x64 の規約に基づいて、引数は可能であればレジスタで渡され、残りの引数はスタックで渡されます。 x64 コードでは、__cdecl を指定することで、/Gv コンパイラ オプションを無効にし、既定の呼び出し規約を使用します。
静的でないクラスの関数が行外で宣言されている場合、行外の宣言で呼び出し規約の修飾子を指定する必要はありません。 つまり、クラスの静的でないメンバー メソッドの場合は、宣言時に指定された呼び出し規約が定義の時点で仮定されます。 次のクラス定義があるとします。
struct CMyClass {
void __cdecl mymethod();
};
ここで、
void CMyClass::mymethod() { return; }
は次の記述と同じです。
void __cdecl CMyClass::mymethod() { return; }
使用例
次の例では、コンパイラは、system 関数に対して C の命名規則と呼び出し規約を使用するように指示されます。
// Example of the __cdecl keyword on function
int __cdecl system(const char *);
// Example of the __cdecl keyword on function pointer
typedef BOOL (__cdecl *funcname_ptr)(void * arg1, const char * arg2, DWORD flags, ...);