1*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -verify -std=c99 -DMS %s 2*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -verify -std=c11 -DMS %s 3*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple i686-mingw32 -fsyntax-only -verify -std=c11 -DGNU %s 4*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -verify -std=c99 -DGNU %s 5*0a6a1f1dSLionel Sambuc 6*0a6a1f1dSLionel Sambuc // Invalid usage. 7*0a6a1f1dSLionel Sambuc __declspec(dllimport) typedef int typedef1; // expected-warning{{'dllimport' attribute only applies to variables and functions}} 8*0a6a1f1dSLionel Sambuc typedef __declspec(dllimport) int typedef2; // expected-warning{{'dllimport' attribute only applies to variables and functions}} 9*0a6a1f1dSLionel Sambuc typedef int __declspec(dllimport) typedef3; // expected-warning{{'dllimport' attribute only applies to variables and functions}} 10*0a6a1f1dSLionel Sambuc typedef __declspec(dllimport) void (*FunTy)(); // expected-warning{{'dllimport' attribute only applies to variables and functions}} 11*0a6a1f1dSLionel Sambuc enum __declspec(dllimport) Enum { EnumVal }; // expected-warning{{'dllimport' attribute only applies to variables and functions}} 12*0a6a1f1dSLionel Sambuc struct __declspec(dllimport) Record {}; // expected-warning{{'dllimport' attribute only applies to variables and functions}} 13*0a6a1f1dSLionel Sambuc 14*0a6a1f1dSLionel Sambuc 15*0a6a1f1dSLionel Sambuc 16*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===// 17*0a6a1f1dSLionel Sambuc // Globals 18*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===// 19*0a6a1f1dSLionel Sambuc 20*0a6a1f1dSLionel Sambuc // Import declaration. 21*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int ExternGlobalDecl; 22*0a6a1f1dSLionel Sambuc 23*0a6a1f1dSLionel Sambuc // dllimport implies a declaration. 24*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalDecl; 25*0a6a1f1dSLionel Sambuc int **__attribute__((dllimport))* GlobalDeclChunkAttr; 26*0a6a1f1dSLionel Sambuc int GlobalDeclAttr __attribute__((dllimport)); 27*0a6a1f1dSLionel Sambuc 28*0a6a1f1dSLionel Sambuc // Address of variables can't be used for initialization in C language modes. 29*0a6a1f1dSLionel Sambuc int *VarForInit = &GlobalDecl; // expected-error{{initializer element is not a compile-time constant}} 30*0a6a1f1dSLionel Sambuc 31*0a6a1f1dSLionel Sambuc // Not allowed on definitions. 32*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int ExternGlobalInit = 1; // expected-error{{definition of dllimport data}} 33*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalInit1 = 1; // expected-error{{definition of dllimport data}} 34*0a6a1f1dSLionel Sambuc int __declspec(dllimport) GlobalInit2 = 1; // expected-error{{definition of dllimport data}} 35*0a6a1f1dSLionel Sambuc 36*0a6a1f1dSLionel Sambuc // Declare, then reject definition. 37*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int ExternGlobalDeclInit; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}} 38*0a6a1f1dSLionel Sambuc int ExternGlobalDeclInit = 1; // expected-warning{{'ExternGlobalDeclInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}} 39*0a6a1f1dSLionel Sambuc 40*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalDeclInit; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}} 41*0a6a1f1dSLionel Sambuc int GlobalDeclInit = 1; // expected-warning{{'GlobalDeclInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}} 42*0a6a1f1dSLionel Sambuc 43*0a6a1f1dSLionel Sambuc int *__attribute__((dllimport)) GlobalDeclChunkAttrInit; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}} 44*0a6a1f1dSLionel Sambuc int *GlobalDeclChunkAttrInit = 0; // expected-warning{{'GlobalDeclChunkAttrInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}} 45*0a6a1f1dSLionel Sambuc 46*0a6a1f1dSLionel Sambuc int GlobalDeclAttrInit __attribute__((dllimport)); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}} 47*0a6a1f1dSLionel Sambuc int GlobalDeclAttrInit = 1; // expected-warning{{'GlobalDeclAttrInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}} 48*0a6a1f1dSLionel Sambuc 49*0a6a1f1dSLionel Sambuc // Redeclarations 50*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl1; 51*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl1; 52*0a6a1f1dSLionel Sambuc 53*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalRedecl2a; 54*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalRedecl2a; 55*0a6a1f1dSLionel Sambuc 56*0a6a1f1dSLionel Sambuc int *__attribute__((dllimport)) GlobalRedecl2b; 57*0a6a1f1dSLionel Sambuc int *__attribute__((dllimport)) GlobalRedecl2b; 58*0a6a1f1dSLionel Sambuc 59*0a6a1f1dSLionel Sambuc int GlobalRedecl2c __attribute__((dllimport)); 60*0a6a1f1dSLionel Sambuc int GlobalRedecl2c __attribute__((dllimport)); 61*0a6a1f1dSLionel Sambuc 62*0a6a1f1dSLionel Sambuc // NB: MSVC issues a warning and makes GlobalRedecl3 dllexport. We follow GCC 63*0a6a1f1dSLionel Sambuc // and drop the dllimport with a warning. 64*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl3; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}} 65*0a6a1f1dSLionel Sambuc extern int GlobalRedecl3; // expected-warning{{'GlobalRedecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}} 66*0a6a1f1dSLionel Sambuc 67*0a6a1f1dSLionel Sambuc // Adding an attribute on redeclaration. 68*0a6a1f1dSLionel Sambuc extern int GlobalRedecl4; // expected-note{{previous declaration is here}} useGlobalRedecl4()69*0a6a1f1dSLionel Sambucint useGlobalRedecl4() { return GlobalRedecl4; } 70*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl4; // expected-error{{redeclaration of 'GlobalRedecl4' cannot add 'dllimport' attribute}} 71*0a6a1f1dSLionel Sambuc 72*0a6a1f1dSLionel Sambuc // Allow with a warning if the decl hasn't been used yet. 73*0a6a1f1dSLionel Sambuc extern int GlobalRedecl5; // expected-note{{previous declaration is here}} 74*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl5; // expected-warning{{redeclaration of 'GlobalRedecl5' should not add 'dllimport' attribute}} 75*0a6a1f1dSLionel Sambuc 76*0a6a1f1dSLionel Sambuc 77*0a6a1f1dSLionel Sambuc // External linkage is required. 78*0a6a1f1dSLionel Sambuc __declspec(dllimport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllimport'}} 79*0a6a1f1dSLionel Sambuc 80*0a6a1f1dSLionel Sambuc // Thread local variables are invalid. 81*0a6a1f1dSLionel Sambuc __declspec(dllimport) __thread int ThreadLocalGlobal; // expected-error{{'ThreadLocalGlobal' cannot be thread local when declared 'dllimport'}} 82*0a6a1f1dSLionel Sambuc 83*0a6a1f1dSLionel Sambuc // Import in local scope. 84*0a6a1f1dSLionel Sambuc __declspec(dllimport) float LocalRedecl1; // expected-note{{previous definition is here}} 85*0a6a1f1dSLionel Sambuc __declspec(dllimport) float LocalRedecl2; // expected-note{{previous definition is here}} 86*0a6a1f1dSLionel Sambuc __declspec(dllimport) float LocalRedecl3; // expected-note{{previous definition is here}} 87*0a6a1f1dSLionel Sambuc __declspec(dllimport) float LocalRedecl4; functionScope()88*0a6a1f1dSLionel Sambucvoid functionScope() { 89*0a6a1f1dSLionel Sambuc __declspec(dllimport) int LocalRedecl1; // expected-error{{redefinition of 'LocalRedecl1' with a different type: 'int' vs 'float'}} 90*0a6a1f1dSLionel Sambuc int *__attribute__((dllimport)) LocalRedecl2; // expected-error{{redefinition of 'LocalRedecl2' with a different type: 'int *' vs 'float'}} 91*0a6a1f1dSLionel Sambuc int LocalRedecl3 __attribute__((dllimport)); // expected-error{{redefinition of 'LocalRedecl3' with a different type: 'int' vs 'float'}} 92*0a6a1f1dSLionel Sambuc 93*0a6a1f1dSLionel Sambuc __declspec(dllimport) int LocalVarDecl; 94*0a6a1f1dSLionel Sambuc __declspec(dllimport) int LocalVarDef = 1; // expected-error{{definition of dllimport data}} 95*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int ExternLocalVarDecl; 96*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int ExternLocalVarDef = 1; // expected-error{{definition of dllimport data}} 97*0a6a1f1dSLionel Sambuc __declspec(dllimport) static int StaticLocalVar; // expected-error{{'StaticLocalVar' must have external linkage when declared 'dllimport'}} 98*0a6a1f1dSLionel Sambuc 99*0a6a1f1dSLionel Sambuc // Local extern redeclaration does not drop the attribute. 100*0a6a1f1dSLionel Sambuc extern float LocalRedecl4; 101*0a6a1f1dSLionel Sambuc } 102*0a6a1f1dSLionel Sambuc 103*0a6a1f1dSLionel Sambuc 104*0a6a1f1dSLionel Sambuc 105*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===// 106*0a6a1f1dSLionel Sambuc // Functions 107*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===// 108*0a6a1f1dSLionel Sambuc 109*0a6a1f1dSLionel Sambuc // Import function declaration. Check different placements. 110*0a6a1f1dSLionel Sambuc __attribute__((dllimport)) void decl1A(); // Sanity check with __attribute__ 111*0a6a1f1dSLionel Sambuc __declspec(dllimport) void decl1B(); 112*0a6a1f1dSLionel Sambuc 113*0a6a1f1dSLionel Sambuc void __attribute__((dllimport)) decl2A(); 114*0a6a1f1dSLionel Sambuc void __declspec(dllimport) decl2B(); 115*0a6a1f1dSLionel Sambuc 116*0a6a1f1dSLionel Sambuc // Address of functions can be used for initialization in C language modes. 117*0a6a1f1dSLionel Sambuc // However, the address of the thunk wrapping the function is used instead of 118*0a6a1f1dSLionel Sambuc // the address in the import address table. 119*0a6a1f1dSLionel Sambuc void (*FunForInit)() = &decl2A; 120*0a6a1f1dSLionel Sambuc 121*0a6a1f1dSLionel Sambuc // Not allowed on function definitions. def()122*0a6a1f1dSLionel Sambuc__declspec(dllimport) void def() {} // expected-error{{dllimport cannot be applied to non-inline function definition}} 123*0a6a1f1dSLionel Sambuc 124*0a6a1f1dSLionel Sambuc // Import inline function. 125*0a6a1f1dSLionel Sambuc #ifdef GNU 126*0a6a1f1dSLionel Sambuc // expected-warning@+3{{'dllimport' attribute ignored on inline function}} 127*0a6a1f1dSLionel Sambuc // expected-warning@+3{{'dllimport' attribute ignored on inline function}} 128*0a6a1f1dSLionel Sambuc #endif inlineFunc1()129*0a6a1f1dSLionel Sambuc__declspec(dllimport) inline void inlineFunc1() {} inlineFunc2()130*0a6a1f1dSLionel Sambucinline void __attribute__((dllimport)) inlineFunc2() {} 131*0a6a1f1dSLionel Sambuc 132*0a6a1f1dSLionel Sambuc // Redeclarations 133*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl1(); 134*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl1(); 135*0a6a1f1dSLionel Sambuc 136*0a6a1f1dSLionel Sambuc // NB: MSVC issues a warning and makes redecl2/redecl3 dllexport. We follow GCC 137*0a6a1f1dSLionel Sambuc // and drop the dllimport with a warning. 138*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl2(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}} 139*0a6a1f1dSLionel Sambuc void redecl2(); // expected-warning{{'redecl2' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}} 140*0a6a1f1dSLionel Sambuc 141*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl3(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}} redecl3()142*0a6a1f1dSLionel Sambuc void redecl3() {} // expected-warning{{'redecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}} 143*0a6a1f1dSLionel Sambuc 144*0a6a1f1dSLionel Sambuc void redecl4(); // expected-note{{previous declaration is here}} useRedecl4()145*0a6a1f1dSLionel Sambucvoid useRedecl4() { redecl4(); } 146*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl4(); // expected-error{{redeclaration of 'redecl4' cannot add 'dllimport' attribute}} 147*0a6a1f1dSLionel Sambuc 148*0a6a1f1dSLionel Sambuc // Allow with a warning if the decl hasn't been used yet. 149*0a6a1f1dSLionel Sambuc void redecl5(); // expected-note{{previous declaration is here}} 150*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl5(); // expected-warning{{redeclaration of 'redecl5' should not add 'dllimport' attribute}} 151*0a6a1f1dSLionel Sambuc 152*0a6a1f1dSLionel Sambuc 153*0a6a1f1dSLionel Sambuc // Inline redeclarations. 154*0a6a1f1dSLionel Sambuc #ifdef GNU 155*0a6a1f1dSLionel Sambuc // expected-warning@+3{{'redecl6' redeclared inline; 'dllimport' attribute ignored}} 156*0a6a1f1dSLionel Sambuc #endif 157*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl6(); redecl6()158*0a6a1f1dSLionel Sambuc inline void redecl6() {} 159*0a6a1f1dSLionel Sambuc 160*0a6a1f1dSLionel Sambuc #ifdef MS 161*0a6a1f1dSLionel Sambuc // expected-note@+5{{previous declaration is here}} 162*0a6a1f1dSLionel Sambuc // expected-warning@+5{{redeclaration of 'redecl7' should not add 'dllimport' attribute}} 163*0a6a1f1dSLionel Sambuc #else 164*0a6a1f1dSLionel Sambuc // expected-warning@+3{{'dllimport' attribute ignored on inline function}} 165*0a6a1f1dSLionel Sambuc #endif 166*0a6a1f1dSLionel Sambuc void redecl7(); redecl7()167*0a6a1f1dSLionel Sambuc__declspec(dllimport) inline void redecl7() {} 168*0a6a1f1dSLionel Sambuc 169*0a6a1f1dSLionel Sambuc // External linkage is required. 170*0a6a1f1dSLionel Sambuc __declspec(dllimport) static int staticFunc(); // expected-error{{'staticFunc' must have external linkage when declared 'dllimport'}} 171