There are a number of calling conventions that set the rules on how arguments are passed to a function and how the values are returned from the function.
The following table summarizes the supported calling conventions on Windows* OS:
Calling Convention |
Compiler option |
Description |
---|---|---|
__cdecl |
/Gd |
Default calling convention for C/C++ programs. Can be specified on a function with variable arguments. |
__thiscall |
none |
Default calling convention used by C++ member functions that do not use variable arguments. |
__clrcall |
none |
Calling convention that specifies that a function can only be called from managed code. |
__stdcall |
/Gz |
Standard calling convention used for Win32 API functions. |
__fastcall |
/Gr |
Fast calling convention that specifies that arguments are passed in registers rather than on the stack. |
__regcall |
/Qregcall ,which specifies that __regcall is the default calling convention for functions in the compilation, unless another calling convention is specified on a declaration |
Intel Compiler calling convention that specifies that as many arguments as possible are passed in registers; likewise, __regcall uses registers whenever possible to return values. This calling convention is ignored if specified on a function with variable arguments. |
__thiscall |
none |
Default calling convention used by C++ member functions that do not use variable arguments. |
The following table summarizes the supported calling conventions on Linux* OS and Mac OS* X:
Calling Convention |
Compiler Option |
Description |
---|---|---|
__attribute((cdecl)) |
none |
Default calling convention for C/C++ programs. Can be specified on a function with variable arguments. |
__attribute((stdcall)) |
none |
Calling convention that specifies the arguments are passed on the stack. Cannot be specified on a function with variable arguments. |
__attribute((regparm (number))) |
none |
On systems based on IA-32 architecture, the Intel 386, the regparm attribute causes the compiler to pass up to number arguments in registers EAX, EDX, and ECX instead of on the stack. Functions that take a variable number of arguments will continue to pass all of their arguments on the stack. |
__regcall __attribute__((regcall)) |
-regcall , which specifies that __regcall is the default calling convention for functions in the compilation, unless another calling convention is specified on a declaration |
Intel Compiler calling convention that specifies that as many arguments as possible are passed in registers; likewise, __regcall uses registers whenever possible to return values. This calling convention is ignored if specified on a function with variable arguments. |
The __regcall calling convention is unique to the Intel compiler and requires some additional explanation.
To use __regcall, place the keyword before a function declaration. For example:
__regcall int foo (int i, int j);
__attribute__((regcall)) foo (int I, int j); (Linux OS and Mac OS X only)
The number of registers in a __regcall function that can be used for parameter passing/returning a value is normally all available registers available on the platform, except those reserved by the compiler. The following table lists registers are available in each register class depending on the default ABI for the compilation. The registers are used in the order shown in the table.
Register class/Architecture |
IA-32 |
Intel® 64 |
---|---|---|
GPR (see Note 1) |
EAX, ECX, EDX, EDI, ESI |
RAX, RCX, RDX, RDI, RSI, R8 - R15 |
FP |
ST0 |
ST0 |
MMX |
None |
None |
XMM |
XMM0 - XMM7 |
XMM0 - XMM15 |
YMM |
YMM0 - YMM7 |
YMM0 - YMM15 |
Note 1: On Windows systems based on Intel® 64 architecture, R13 is not used for passing parameters or returning values and should be treated as reserved.
Parameters and return values for __regcall are classified by data type and are passed in the registers of the classes shown in the following table.
Type (for both unsigned and signed types) |
IA-32 |
Intel® 64 |
---|---|---|
bool, char, int, enum, _Decimal32, long, pointer |
GPR |
GPR |
short, __mmask |
GPR |
GPR |
long long, __int64 |
See Note 3; also see Structured Data Type Classification Rules |
GPR |
_Decimal64 |
XMM |
GPR |
long double |
FP |
FP |
float, double, float128, _Decimal128 |
XMM |
XMM |
__m128, __m128i, __m128d |
XMM |
XMM |
__m256, __m256i, __m256d |
YMM |
YMM |
__m512 |
n/a |
n/a |
complex <type>, struct, union |
Note 2: For the purpose of structured types,the classification of GPR class is used.
Note 3: On systems based on IA-32 architecture, these 64-bit integer types (long long, __int64) get classified to the GPR class and are passed in 2 registers, as if they were implemented as a structure of two 32-bit integer fields.
Types that are smaller in size than registers than registers of their associated class are passed in the lower part of those registers; for example, float is passed in the lower 4 bytes of an XMM register.
Structures/unions and complex types are classified similarly to what is described in the x86_64 ABI, with the following exceptions:
There is no limitation on the overall size of a structure.
The register classes for basic types are given in Data Type Classifications.
For systems based on the IA-32 architecture, classification is performed on four-bytes. For systems based on other architectures, classification is performed on eight-bytes.
After the classification described in Data Type Classifications and Structured Data Type Classification Rules, __regcall parameters and return values are either put into registers specified in Available Registers or placed in memory, according to the following:
Each chunk (eight bytes on systems based on Intel® 64 architecture or four-bytes on systems based on IA-32 architecture) of a value of Data Type is assigned a register class. If enough registers from Available Registers are available, the whole value is passed in registers, otherwise the value is passed using the stack.
If the classification were to use one or more register classes, then the registers of these classes from the table in Available Registers are used, in the order given there.
If no more registers are available in one of the required register classes, then the whole value is put on the stack.
The following registers preserve their values across a __regcall call, as long as they were not used for passing a parameter or returning a value:
Register class/ABI |
IA-32 |
Intel® 64 |
---|---|---|
GPR |
ESI, EDI, EBX, EBP, ESP |
R10 - R15, RBX, RBP, RSP |
FP |
None |
None |
MMX |
None |
None |
XMM |
XMM4 - XMM7 |
XMM8 - XMM15 |
YMM |
XMM4 - XMM7 |
XMM8 - XMM15 |
All other registers do not preserve their values across this call.
Function names used with __regcall are decorated. Specifically, they are prepended with __regcall__ before any further traditional mangling occurs. For example, the function foo would be decorated as follows: __regcall__foo. This helps avoid improper linking with a name following a different calling convention, while allowing the full range of manipulations to be done with foo (such as setting a breakpoint in the debugger).
Copyright © 1996-2011, Intel Corporation. All rights reserved.