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