The ATTRIBUTES properties (or options) C, STDCALL, REFERENCE, VALUE, and VARYING all affect the calling convention of routines. You can specify:
By default, Fortran passes all data by reference (except the hidden length argument of strings, which is passed by value). If the C or STDCALL option is used, the default changes to passing almost all data except arrays by value. However, in addition to the calling-convention options C and STDCALL, you can specify argument options, VALUE and REFERENCE, to pass arguments by value or by reference, regardless of the calling convention option. Arrays can only be passed by reference.
Different Fortran calling conventions can be specified by declaring the Fortran procedure to have certain attributes. For example, on ia32 systems:
INTERFACE
SUBROUTINE MY_SUB (I)
!DEC$ ATTRIBUTES C, ALIAS:'_My_Sub' :: MY_SUB ! ia32 systems
INTEGER I
END SUBROUTINE MY_SUB
END INTERFACE
This code (on ia32 systems) declares a subroutine named MY_SUB
with the C property and the external name _My_Sub
set with the ALIAS property.
On ia64 systems, there is no leading underscore for external names like
MY_SUB
, so the correct !DEC$ ATTRIBUTES line is:
!DEC$ ATTRIBUTES C, ALIAS:'My_Sub' :: MY_SUB ! ia64 systems
To write code for both ia32 and ia64 platforms, use the conditional compilation features of the IF Directive Construct, perhaps using the predefined preprocessor macros listed under the /define option (such as _M_IX86 and _M_IA64).
The following table summarizes the effect of the most common Fortran calling-convention directives.
Calling Conventions for ATTRIBUTES Options
|
Default | C | STDCALL | C, REFERENCE | STDCALL, REFERENCE |
---|---|---|---|---|---|
Argument | |||||
Scalar | Reference | Value | Value | Reference | Reference |
Scalar [value] | Value | Value | Value | Value | Value |
Scalar [reference] | Reference | Reference | Reference | Reference | Reference |
String | Reference, either Len:Mixed or Len:End | String(1:1) | String(1:1) | Reference, either Len:Mixed or Len:End | Reference, either Len:Mixed or Len:End |
String [value] | Error | String(1:1) | String(1:1) | String(1:1) | String(1:1) |
String [reference] | Reference, either Len:Mixed or No Len | Reference, No Len | Reference, No Len | Reference, No Len | Reference, No Len |
Array | Reference | Reference | Reference | Reference | Reference |
Array [value] | Error | Error | Error | Error | Error |
Array [reference] | Reference | Reference | Reference | Reference | Reference |
Derived Type | Reference | Value, size dependent | Value, size dependent | Reference | Reference |
Derived Type [value] | Value, size dependent | Value, size dependent | Value, size dependent | Value, size dependent | Value, size dependent |
Derived Type [reference] | Reference | Reference | Reference | Reference | Reference |
F90 Pointer | Descriptor | Descriptor | Descriptor | Descriptor | Descriptor |
F90 Pointer [value] | Error | Error | Error | Error | Error |
F90 Pointer [reference] | Descriptor | Descriptor | Descriptor | Descriptor | Descriptor |
Procedure Name | |||||
Suffix | @n (ia32 systems) | none | @n (ia32 systems) | none | @n (ia32 systems) |
Case | Upper Case | Lower Case | Lower Case | Lower Case | Lower Case |
Stack Cleanup | Callee | Caller | Callee | Caller | Callee |
The terms in the above table mean the following:
[value] | Argument assigned the VALUE attribute. |
[reference] | Argument assigned the REFERENCE attribute. |
Value | The argument value is pushed on the stack. All values are padded to the next 4-byte boundary. |
Reference | On ia32 systems, the 4-byte argument address is pushed on the stack. On ia64 systems, the 8-byte argument address is pushed on the stack. |
Len:Mixed or Len:End | For certain string arguments:
|
Len:Mixed or No Len | For certain string arguments:
|
No Len | For string arguments, the length of the string is not available to the called procedure. |
String(1:1) | For string arguments, the first character is converted to INTEGER(4) as in ICHAR(string(1:1)) and pushed on the stack by value. |
Error | Produces a compiler error. |
Descriptor | On ia32 systems, the 4-byte address of the array descriptor. On ia64 systems, the 8-byte address of the array descriptor. |
@n | On ia32 systems, the at sign (@) followed by the number of bytes (in decimal) required for the argument list. |
Size dependent | On ia32 systems, derived-type arguments specified by value are passed as follows:
|
Upper Case | Procedure name in all uppercase. |
Lower Case | Procedure name in all lowercase. |
Callee | The procedure being called is responsible for removing arguments from the stack before returning to the caller. |
Caller | The procedure doing the call is responsible for removing arguments from the stack after the call is over. |
The following table shows which Fortran ATTRIBUTES options match other language calling conventions.
Matching Calling Conventions
Other Language Calling Convention | Matching ATTRIBUTES Option |
---|---|
Visual C/C++ cdecl (default) | C |
Visual C/C++ __stdcall | STDCALL |
Visual Basic | none |
Visual Basic CDECL keyword | C |
MASM C (in PROTO and PROC declarations) | C |
MASM STDCALL (in PROTO and PROC declarations) | STDCALL |
The ALIAS option can be used with any other Fortran calling-convention option to preserve mixed-case names. You can also use the DECORATE option with ALIAS option so the external name specified in ALIAS has prefix and postfix decorations performed on it that are associated with the calling mechanism that is in effect.