mingw __dllexport__
librik@panix.com
librik@panix.com
Thu, 14 Nov 2002 15:11:06 -0500 (EST)
> For gcc I'm going to change the windows DLL function declarations in
> gmp.h from "__declspec(dllexport)" to "__declspec(__dllexport__)", in
> order to keep out of what is, strictly speaking, application
> namespace.
>
> Does the same or similar work for Microsoft C? What about Borland C?
No. Microsoft Visual C requires __declspec(dllexport). Unlike
in Borland C, the _export keyword is no longer a legal synonym.
For Microsoft Visual C, the current use of __GMP_DECLSPEC in
gmp-h.in is correct. (Remember that it was wrong in the original
GMP 4.0, and you moved it to the beginning of the declaration to
make it right.) Also, the form that you use is correct for _MSC_VER:
#if defined (__GNUC__) || defined (_MSC_VER) || defined (__BORLANDC__)
#define __GMP_DECLSPEC_EXPORT __declspec(dllexport)
#define __GMP_DECLSPEC_IMPORT __declspec(dllimport)
#endif
The syntax of __declspec(dllexport) requires that it go at the
beginning of the declaration. Here's an extract from the MSDN
documentation:
__declspec ( extended-attribute ) declarator
extended-attribute
allocate(segname)
dllimport
dllexport
naked
noreturn
nothrow
novtable
property({get=get_func_name|, put=put_func_name})
selectany
thread
uuid(ComObjectGUID)
....<snip>....
The __declspec keywords should be placed at the beginning of a
simple declaration. THe compiler ignores, without warning, any
__declspec keywords placed after * or & and in front of the
variable identifier in a declaration.
A __declspec attribute specified in the beginning of a user-defined
type declaration applies to the variable of that type. For example:
__declspec(dllimport) class X {} varX;
In this case, the attribute applies to varX. A __declspec
attribute placed after the class or struct keyword applies to
the user-defined type. For example:
class __declspec(dllimport) X {};
In this case, the attribute applies to X.
The general guideline for using the __declspec attribute for
simple declarations is as follows:
decl-specifier-seq init-declarator-list;
The decl-specifier-seq should contain, among other things,
a base type (e.g. int, float, a typedef, or a class name),
a storage class (e.g. static, extern), or the __declspec
extension. The init-declarator-list should contain, among
other things, the pointer part of declarations. For example:
__declspec(selectany) int * pi1 = 0;
//OK, selectany & int both part of decl-specifier
int __declspec(selectany) * pi2 = 0;
//OK, selectany & int both part of decl-specifier
int * __declspec(selectany) pi3 = 0;
//ERROR, selectany is not part of a declarator
Example
The following code declares an integer thread local variable
and initializes it with a value:
// Example of the __declspec keyword
__declspec( thread ) int tls_i = 1;
In short, for Microsoft Visual C++, don't change __declspec(dllexport).
- David Librik
librik@panix.com