1*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple i686-windows-msvc -emit-llvm -std=c11 -O0 -o - %s | FileCheck --check-prefix=CHECK --check-prefix=MS %s 2*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple x86_64-windows-msvc -emit-llvm -std=c11 -O0 -o - %s | FileCheck --check-prefix=CHECK --check-prefix=MS %s 3*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple i686-windows-gnu -emit-llvm -std=c11 -O0 -o - %s | FileCheck --check-prefix=CHECK --check-prefix=GNU %s 4*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple x86_64-windows-gnu -emit-llvm -std=c11 -O0 -o - %s | FileCheck --check-prefix=CHECK --check-prefix=GNU %s 5*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple i686-windows-msvc -emit-llvm -std=c11 -O1 -o - %s | FileCheck --check-prefix=O1 --check-prefix=MO1 %s 6*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -triple i686-windows-gnu -emit-llvm -std=c11 -O1 -o - %s | FileCheck --check-prefix=O1 --check-prefix=GO1 %s 7*0a6a1f1dSLionel Sambuc 8*0a6a1f1dSLionel Sambuc #define JOIN2(x, y) x##y 9*0a6a1f1dSLionel Sambuc #define JOIN(x, y) JOIN2(x, y) 10*0a6a1f1dSLionel Sambuc #define USEVAR(var) int JOIN(use, __LINE__)() { return var; } 11*0a6a1f1dSLionel Sambuc #define USE(func) void JOIN(use, __LINE__)() { func(); } 12*0a6a1f1dSLionel Sambuc 13*0a6a1f1dSLionel Sambuc 14*0a6a1f1dSLionel Sambuc 15*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===// 16*0a6a1f1dSLionel Sambuc // Globals 17*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===// 18*0a6a1f1dSLionel Sambuc 19*0a6a1f1dSLionel Sambuc // Import declaration. 20*0a6a1f1dSLionel Sambuc // CHECK: @ExternGlobalDecl = external dllimport global i32 21*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int ExternGlobalDecl; 22*0a6a1f1dSLionel Sambuc USEVAR(ExternGlobalDecl) 23*0a6a1f1dSLionel Sambuc 24*0a6a1f1dSLionel Sambuc // dllimport implies a declaration. 25*0a6a1f1dSLionel Sambuc // CHECK: @GlobalDecl = external dllimport global i32 26*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalDecl; 27*0a6a1f1dSLionel Sambuc USEVAR(GlobalDecl) 28*0a6a1f1dSLionel Sambuc 29*0a6a1f1dSLionel Sambuc // Redeclarations 30*0a6a1f1dSLionel Sambuc // CHECK: @GlobalRedecl1 = external dllimport global i32 31*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl1; 32*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl1; 33*0a6a1f1dSLionel Sambuc USEVAR(GlobalRedecl1) 34*0a6a1f1dSLionel Sambuc 35*0a6a1f1dSLionel Sambuc // CHECK: @GlobalRedecl2 = external dllimport global i32 36*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalRedecl2; 37*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalRedecl2; 38*0a6a1f1dSLionel Sambuc USEVAR(GlobalRedecl2) 39*0a6a1f1dSLionel Sambuc 40*0a6a1f1dSLionel Sambuc // NB: MSVC issues a warning and makes GlobalRedecl3 dllexport. We follow GCC 41*0a6a1f1dSLionel Sambuc // and drop the dllimport with a warning. 42*0a6a1f1dSLionel Sambuc // CHECK: @GlobalRedecl3 = external global i32 43*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl3; 44*0a6a1f1dSLionel Sambuc extern int GlobalRedecl3; // dllimport ignored 45*0a6a1f1dSLionel Sambuc USEVAR(GlobalRedecl3) 46*0a6a1f1dSLionel Sambuc 47*0a6a1f1dSLionel Sambuc // Make sure this works even if the decl has been used before it's defined (PR20792). 48*0a6a1f1dSLionel Sambuc // CHECK: @GlobalRedecl4 = common global i32 49*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl4; 50*0a6a1f1dSLionel Sambuc USEVAR(GlobalRedecl4) 51*0a6a1f1dSLionel Sambuc int GlobalRedecl4; // dllimport ignored 52*0a6a1f1dSLionel Sambuc 53*0a6a1f1dSLionel Sambuc // FIXME: dllimport is dropped in the AST; this should be reflected in codegen (PR02803). 54*0a6a1f1dSLionel Sambuc // CHECK: @GlobalRedecl5 = external dllimport global i32 55*0a6a1f1dSLionel Sambuc __declspec(dllimport) extern int GlobalRedecl5; 56*0a6a1f1dSLionel Sambuc USEVAR(GlobalRedecl5) 57*0a6a1f1dSLionel Sambuc extern int GlobalRedecl5; // dllimport ignored 58*0a6a1f1dSLionel Sambuc 59*0a6a1f1dSLionel Sambuc // Redeclaration in local context. 60*0a6a1f1dSLionel Sambuc // CHECK: @GlobalRedecl6 = external dllimport global i32 61*0a6a1f1dSLionel Sambuc __declspec(dllimport) int GlobalRedecl6; functionScope()62*0a6a1f1dSLionel Sambucint functionScope() { 63*0a6a1f1dSLionel Sambuc extern int GlobalRedecl6; // still dllimport 64*0a6a1f1dSLionel Sambuc return GlobalRedecl6; 65*0a6a1f1dSLionel Sambuc } 66*0a6a1f1dSLionel Sambuc 67*0a6a1f1dSLionel Sambuc 68*0a6a1f1dSLionel Sambuc 69*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===// 70*0a6a1f1dSLionel Sambuc // Functions 71*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===// 72*0a6a1f1dSLionel Sambuc 73*0a6a1f1dSLionel Sambuc // Import function declaration. 74*0a6a1f1dSLionel Sambuc // CHECK-DAG: declare dllimport void @decl() 75*0a6a1f1dSLionel Sambuc __declspec(dllimport) void decl(void); 76*0a6a1f1dSLionel Sambuc 77*0a6a1f1dSLionel Sambuc // Initialize use_decl with the address of the thunk. 78*0a6a1f1dSLionel Sambuc // CHECK-DAG: @use_decl = global void ()* @decl 79*0a6a1f1dSLionel Sambuc void (*use_decl)(void) = &decl; 80*0a6a1f1dSLionel Sambuc 81*0a6a1f1dSLionel Sambuc // Import inline function. 82*0a6a1f1dSLionel Sambuc // MS-DAG: declare dllimport void @inlineFunc() 83*0a6a1f1dSLionel Sambuc // MO1-DAG: define available_externally dllimport void @inlineFunc() 84*0a6a1f1dSLionel Sambuc // GNU-DAG: declare void @inlineFunc() 85*0a6a1f1dSLionel Sambuc // GO1-DAG: define available_externally void @inlineFunc() inlineFunc(void)86*0a6a1f1dSLionel Sambuc__declspec(dllimport) inline void inlineFunc(void) {} USE(inlineFunc)87*0a6a1f1dSLionel SambucUSE(inlineFunc) 88*0a6a1f1dSLionel Sambuc 89*0a6a1f1dSLionel Sambuc // inline attributes 90*0a6a1f1dSLionel Sambuc // MS-DAG: declare dllimport void @noinline() 91*0a6a1f1dSLionel Sambuc // MO1-DAG: define available_externally dllimport void @noinline() 92*0a6a1f1dSLionel Sambuc // GNU-DAG: declare void @noinline() 93*0a6a1f1dSLionel Sambuc // GO1-DAG: define available_externally void @noinline() 94*0a6a1f1dSLionel Sambuc // CHECK-NOT: @alwaysInline() 95*0a6a1f1dSLionel Sambuc // O1-NOT: @alwaysInline() 96*0a6a1f1dSLionel Sambuc __declspec(dllimport) __attribute__((noinline)) inline void noinline(void) {} alwaysInline(void)97*0a6a1f1dSLionel Sambuc__declspec(dllimport) __attribute__((always_inline)) inline void alwaysInline(void) {} 98*0a6a1f1dSLionel Sambuc USE(noinline) 99*0a6a1f1dSLionel Sambuc USE(alwaysInline) 100*0a6a1f1dSLionel Sambuc 101*0a6a1f1dSLionel Sambuc // Redeclarations 102*0a6a1f1dSLionel Sambuc // CHECK-DAG: declare dllimport void @redecl1() 103*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl1(void); 104*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl1(void); 105*0a6a1f1dSLionel Sambuc USE(redecl1) 106*0a6a1f1dSLionel Sambuc 107*0a6a1f1dSLionel Sambuc // NB: MSVC issues a warning and makes redecl2/redecl3 dllexport. We follow GCC 108*0a6a1f1dSLionel Sambuc // and drop the dllimport with a warning. 109*0a6a1f1dSLionel Sambuc // CHECK-DAG: declare void @redecl2() 110*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl2(void); 111*0a6a1f1dSLionel Sambuc void redecl2(void); 112*0a6a1f1dSLionel Sambuc USE(redecl2) 113*0a6a1f1dSLionel Sambuc 114*0a6a1f1dSLionel Sambuc // CHECK-DAG: define void @redecl3() 115*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl3(void); redecl3(void)116*0a6a1f1dSLionel Sambuc void redecl3(void) {} // dllimport ignored 117*0a6a1f1dSLionel Sambuc USE(redecl3) 118*0a6a1f1dSLionel Sambuc 119*0a6a1f1dSLionel Sambuc // Make sure this works even if the decl is used before it's defined (PR20792). 120*0a6a1f1dSLionel Sambuc // CHECK-DAG: define void @redecl4() 121*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl4(void); USE(redecl4)122*0a6a1f1dSLionel SambucUSE(redecl4) 123*0a6a1f1dSLionel Sambuc void redecl4(void) {} // dllimport ignored 124*0a6a1f1dSLionel Sambuc 125*0a6a1f1dSLionel Sambuc // FIXME: dllimport is dropped in the AST; this should be reflected in codegen (PR20803). 126*0a6a1f1dSLionel Sambuc // CHECK-DAG: declare dllimport 127*0a6a1f1dSLionel Sambuc __declspec(dllimport) void redecl5(void); 128*0a6a1f1dSLionel Sambuc USE(redecl5) 129*0a6a1f1dSLionel Sambuc void redecl5(void); // dllimport ignored 130