Home | History | Annotate | Download | only in SemaCXX
      1 // RUN: %clang_cc1 -triple i686-win32     -fsyntax-only -fms-extensions -verify -std=c++11 -Wunsupported-dll-base-class-template -DMS %s
      2 // RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions -verify -std=c++1y -Wunsupported-dll-base-class-template -DMS %s
      3 // RUN: %clang_cc1 -triple i686-mingw32   -fsyntax-only -fms-extensions -verify -std=c++1y -Wunsupported-dll-base-class-template -DGNU %s
      4 // RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -fms-extensions -verify -std=c++11 -Wunsupported-dll-base-class-template -DGNU %s
      5 
      6 // Helper structs to make templates more expressive.
      7 struct ImplicitInst_Imported {};
      8 struct ExplicitDecl_Imported {};
      9 struct ExplicitInst_Imported {};
     10 struct ExplicitSpec_Imported {};
     11 struct ExplicitSpec_Def_Imported {};
     12 struct ExplicitSpec_InlineDef_Imported {};
     13 struct ExplicitSpec_NotImported {};
     14 namespace { struct Internal {}; }
     15 
     16 
     17 // Invalid usage.
     18 __declspec(dllimport) typedef int typedef1; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
     19 typedef __declspec(dllimport) int typedef2; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
     20 typedef int __declspec(dllimport) typedef3; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
     21 typedef __declspec(dllimport) void (*FunTy)(); // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
     22 enum __declspec(dllimport) Enum {}; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
     23 #if __has_feature(cxx_strong_enums)
     24   enum class __declspec(dllimport) EnumClass {}; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
     25 #endif
     26 
     27 
     28 
     29 //===----------------------------------------------------------------------===//
     30 // Globals
     31 //===----------------------------------------------------------------------===//
     32 
     33 // Import declaration.
     34 __declspec(dllimport) extern int ExternGlobalDecl;
     35 
     36 // dllimport implies a declaration.
     37 __declspec(dllimport) int GlobalDecl;
     38 int **__attribute__((dllimport))* GlobalDeclChunkAttr;
     39 int GlobalDeclAttr __attribute__((dllimport));
     40 
     41 // Not allowed on definitions.
     42 __declspec(dllimport) extern int ExternGlobalInit = 1; // expected-error{{definition of dllimport data}}
     43 __declspec(dllimport) int GlobalInit1 = 1; // expected-error{{definition of dllimport data}}
     44 int __declspec(dllimport) GlobalInit2 = 1; // expected-error{{definition of dllimport data}}
     45 
     46 // Declare, then reject definition.
     47 __declspec(dllimport) extern int ExternGlobalDeclInit; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
     48 int ExternGlobalDeclInit = 1; // expected-warning{{'ExternGlobalDeclInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
     49 
     50 __declspec(dllimport) int GlobalDeclInit; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
     51 int GlobalDeclInit = 1; // expected-warning{{'GlobalDeclInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
     52 
     53 int *__attribute__((dllimport)) GlobalDeclChunkAttrInit; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
     54 int *GlobalDeclChunkAttrInit = 0; // expected-warning{{'GlobalDeclChunkAttrInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
     55 
     56 int GlobalDeclAttrInit __attribute__((dllimport)); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
     57 int GlobalDeclAttrInit = 1; // expected-warning{{'GlobalDeclAttrInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
     58 
     59 // Redeclarations
     60 __declspec(dllimport) extern int GlobalRedecl1;
     61 __declspec(dllimport) extern int GlobalRedecl1;
     62 
     63 __declspec(dllimport) int GlobalRedecl2a;
     64 __declspec(dllimport) int GlobalRedecl2a;
     65 
     66 int *__attribute__((dllimport)) GlobalRedecl2b;
     67 int *__attribute__((dllimport)) GlobalRedecl2b;
     68 
     69 int GlobalRedecl2c __attribute__((dllimport));
     70 int GlobalRedecl2c __attribute__((dllimport));
     71 
     72 // NB: MSVC issues a warning and makes GlobalRedecl3 dllexport. We follow GCC
     73 // and drop the dllimport with a warning.
     74 __declspec(dllimport) extern int GlobalRedecl3; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
     75                       extern int GlobalRedecl3; // expected-warning{{'GlobalRedecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
     76 
     77                       extern int GlobalRedecl4; // expected-note{{previous declaration is here}}
     78 __declspec(dllimport) extern int GlobalRedecl4; // expected-warning{{redeclaration of 'GlobalRedecl4' should not add 'dllimport' attribute}}
     79 
     80 extern "C" {
     81                       extern int GlobalRedecl5; // expected-note{{previous declaration is here}}
     82 __declspec(dllimport) extern int GlobalRedecl5; // expected-warning{{redeclaration of 'GlobalRedecl5' should not add 'dllimport' attribute}}
     83 }
     84 
     85 // External linkage is required.
     86 __declspec(dllimport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllimport'}}
     87 __declspec(dllimport) Internal InternalTypeGlobal; // expected-error{{'InternalTypeGlobal' must have external linkage when declared 'dllimport'}}
     88 namespace    { __declspec(dllimport) int InternalGlobal; } // expected-error{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllimport'}}
     89 namespace ns { __declspec(dllimport) int ExternalGlobal; }
     90 
     91 __declspec(dllimport) auto InternalAutoTypeGlobal = Internal(); // expected-error{{'InternalAutoTypeGlobal' must have external linkage when declared 'dllimport'}}
     92                                                                 // expected-error@-1{{definition of dllimport data}}
     93 
     94 // Thread local variables are invalid.
     95 __declspec(dllimport) __thread int ThreadLocalGlobal; // expected-error{{'ThreadLocalGlobal' cannot be thread local when declared 'dllimport'}}
     96 // This doesn't work on MinGW, because there, dllimport on the inline function is ignored.
     97 #ifndef GNU
     98 inline void __declspec(dllimport) ImportedInlineWithThreadLocal() {
     99   static __thread int OK; // no-error
    100 }
    101 #endif
    102 
    103 // Import in local scope.
    104 __declspec(dllimport) float LocalRedecl1; // expected-note{{previous declaration is here}}
    105 __declspec(dllimport) float LocalRedecl2; // expected-note{{previous declaration is here}}
    106 __declspec(dllimport) float LocalRedecl3; // expected-note{{previous declaration is here}}
    107 void functionScope() {
    108   __declspec(dllimport) int LocalRedecl1; // expected-error{{redeclaration of 'LocalRedecl1' with a different type: 'int' vs 'float'}}
    109   int *__attribute__((dllimport)) LocalRedecl2; // expected-error{{redeclaration of 'LocalRedecl2' with a different type: 'int *' vs 'float'}}
    110   int LocalRedecl3 __attribute__((dllimport)); // expected-error{{redeclaration of 'LocalRedecl3' with a different type: 'int' vs 'float'}}
    111 
    112   __declspec(dllimport)        int LocalVarDecl;
    113   __declspec(dllimport)        int LocalVarDef = 1; // expected-error{{definition of dllimport data}}
    114   __declspec(dllimport) extern int ExternLocalVarDecl;
    115   __declspec(dllimport) extern int ExternLocalVarDef = 1; // expected-error{{definition of dllimport data}}
    116   __declspec(dllimport) static int StaticLocalVar; // expected-error{{'StaticLocalVar' must have external linkage when declared 'dllimport'}}
    117 }
    118 
    119 
    120 
    121 //===----------------------------------------------------------------------===//
    122 // Variable templates
    123 //===----------------------------------------------------------------------===//
    124 #if __has_feature(cxx_variable_templates)
    125 
    126 // Import declaration.
    127 template<typename T> __declspec(dllimport) extern int ExternVarTmplDecl;
    128 
    129 // dllimport implies a declaration.
    130 template<typename T> __declspec(dllimport) int VarTmplDecl;
    131 
    132 // Not allowed on definitions.
    133 template<typename T> __declspec(dllimport) extern int ExternVarTmplInit = 1; // expected-error{{definition of dllimport data}}
    134 template<typename T> __declspec(dllimport) int VarTmplInit1 = 1; // expected-error{{definition of dllimport data}}
    135 template<typename T> int __declspec(dllimport) VarTmplInit2 = 1; // expected-error{{definition of dllimport data}}
    136 
    137 // Declare, then reject definition.
    138 template<typename T> __declspec(dllimport) extern int ExternVarTmplDeclInit; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    139 template<typename T>                              int ExternVarTmplDeclInit = 1; // expected-warning{{'ExternVarTmplDeclInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    140 
    141 template<typename T> __declspec(dllimport) int VarTmplDeclInit; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    142 template<typename T>                       int VarTmplDeclInit = 1; // expected-warning{{'VarTmplDeclInit' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    143 
    144 // Redeclarations
    145 template<typename T> __declspec(dllimport) extern int VarTmplRedecl1;
    146 template<typename T> __declspec(dllimport) extern int VarTmplRedecl1;
    147 
    148 template<typename T> __declspec(dllimport) int VarTmplRedecl2;
    149 template<typename T> __declspec(dllimport) int VarTmplRedecl2;
    150 
    151 template<typename T> __declspec(dllimport) extern int VarTmplRedecl3; // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    152 template<typename T>                       extern int VarTmplRedecl3; // expected-warning{{'VarTmplRedecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    153 
    154 template<typename T>                       extern int VarTmplRedecl4; // expected-note{{previous declaration is here}}
    155 template<typename T> __declspec(dllimport) extern int VarTmplRedecl4; // expected-error{{redeclaration of 'VarTmplRedecl4' cannot add 'dllimport' attribute}}
    156 
    157 // External linkage is required.
    158 template<typename T> __declspec(dllimport) static int StaticVarTmpl; // expected-error{{'StaticVarTmpl' must have external linkage when declared 'dllimport'}}
    159 template<typename T> __declspec(dllimport) Internal InternalTypeVarTmpl; // expected-error{{'InternalTypeVarTmpl' must have external linkage when declared 'dllimport'}}
    160 namespace    { template<typename T> __declspec(dllimport) int InternalVarTmpl; } // expected-error{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllimport'}}
    161 namespace ns { template<typename T> __declspec(dllimport) int ExternalVarTmpl; }
    162 
    163 template<typename T> __declspec(dllimport) auto InternalAutoTypeVarTmpl = Internal(); // expected-error{{definition of dllimport data}} // expected-error{{'InternalAutoTypeVarTmpl' must have external linkage when declared 'dllimport'}}
    164 
    165 
    166 template<typename T> int VarTmpl;
    167 template<typename T> __declspec(dllimport) int ImportedVarTmpl;
    168 
    169 // Import implicit instantiation of an imported variable template.
    170 int useVarTmpl() { return ImportedVarTmpl<ImplicitInst_Imported>; }
    171 
    172 // Import explicit instantiation declaration of an imported variable template.
    173 extern template int ImportedVarTmpl<ExplicitDecl_Imported>;
    174 
    175 // An explicit instantiation definition of an imported variable template cannot
    176 // be imported because the template must be defined which is illegal.
    177 
    178 // Import specialization of an imported variable template.
    179 template<> __declspec(dllimport) int ImportedVarTmpl<ExplicitSpec_Imported>;
    180 template<> __declspec(dllimport) int ImportedVarTmpl<ExplicitSpec_Def_Imported> = 1; // expected-error{{definition of dllimport data}}
    181 
    182 // Not importing specialization of an imported variable template without
    183 // explicit dllimport.
    184 template<> int ImportedVarTmpl<ExplicitSpec_NotImported>;
    185 
    186 
    187 // Import explicit instantiation declaration of a non-imported variable template.
    188 extern template __declspec(dllimport) int VarTmpl<ExplicitDecl_Imported>;
    189 
    190 // Import explicit instantiation definition of a non-imported variable template.
    191 template __declspec(dllimport) int VarTmpl<ExplicitInst_Imported>;
    192 
    193 // Import specialization of a non-imported variable template.
    194 template<> __declspec(dllimport) int VarTmpl<ExplicitSpec_Imported>;
    195 template<> __declspec(dllimport) int VarTmpl<ExplicitSpec_Def_Imported> = 1; // expected-error{{definition of dllimport data}}
    196 
    197 #endif // __has_feature(cxx_variable_templates)
    198 
    199 
    200 //===----------------------------------------------------------------------===//
    201 // Functions
    202 //===----------------------------------------------------------------------===//
    203 
    204 // Import function declaration. Check different placements.
    205 __attribute__((dllimport)) void decl1A(); // Sanity check with __attribute__
    206 __declspec(dllimport)      void decl1B();
    207 
    208 void __attribute__((dllimport)) decl2A();
    209 void __declspec(dllimport)      decl2B();
    210 
    211 // Not allowed on function definitions.
    212 __declspec(dllimport) void def() {} // expected-error{{dllimport cannot be applied to non-inline function definition}}
    213 
    214 // extern  "C"
    215 extern "C" __declspec(dllimport) void externC();
    216 
    217 // Import inline function.
    218 #ifdef GNU
    219 // expected-warning@+3{{'dllimport' attribute ignored on inline function}}
    220 // expected-warning@+3{{'dllimport' attribute ignored on inline function}}
    221 #endif
    222 __declspec(dllimport) inline void inlineFunc1() {}
    223 inline void __attribute__((dllimport)) inlineFunc2() {}
    224 
    225 #ifdef GNU
    226 // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    227 #endif
    228 __declspec(dllimport) inline void inlineDecl();
    229                              void inlineDecl() {}
    230 
    231 __declspec(dllimport) void inlineDef();
    232 #ifdef GNU
    233 // expected-warning@+2{{'inlineDef' redeclared inline; 'dllimport' attribute ignored}}
    234 #endif
    235                inline void inlineDef() {}
    236 
    237 // Redeclarations
    238 __declspec(dllimport) void redecl1();
    239 __declspec(dllimport) void redecl1();
    240 
    241 // NB: MSVC issues a warning and makes redecl2/redecl3 dllexport. We follow GCC
    242 // and drop the dllimport with a warning.
    243 __declspec(dllimport) void redecl2(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    244                       void redecl2(); // expected-warning{{'redecl2' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    245 
    246 __declspec(dllimport) void redecl3(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    247                       void redecl3() {} // expected-warning{{'redecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    248 
    249                       void redecl4(); // expected-note{{previous declaration is here}}
    250 __declspec(dllimport) void redecl4(); // expected-warning{{redeclaration of 'redecl4' should not add 'dllimport' attribute}}
    251 
    252 extern "C" {
    253                       void redecl5(); // expected-note{{previous declaration is here}}
    254 __declspec(dllimport) void redecl5(); // expected-warning{{redeclaration of 'redecl5' should not add 'dllimport' attribute}}
    255 }
    256 
    257 #ifdef MS
    258                       void redecl6(); // expected-note{{previous declaration is here}}
    259 __declspec(dllimport) inline void redecl6() {} // expected-warning{{redeclaration of 'redecl6' should not add 'dllimport' attribute}}
    260 #else
    261                       void redecl6();
    262 __declspec(dllimport) inline void redecl6() {} // expected-warning{{'dllimport' attribute ignored on inline function}}
    263 #endif
    264 
    265 // Friend functions
    266 struct FuncFriend {
    267   friend __declspec(dllimport) void friend1();
    268   friend __declspec(dllimport) void friend2(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    269   friend __declspec(dllimport) void friend3(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    270   friend                       void friend4(); // expected-note{{previous declaration is here}}
    271 #ifdef MS
    272 // expected-note@+2{{previous declaration is here}}
    273 #endif
    274   friend                       void friend5();
    275 };
    276 __declspec(dllimport) void friend1();
    277                       void friend2(); // expected-warning{{'friend2' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    278                       void friend3() {} // expected-warning{{'friend3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    279 __declspec(dllimport) void friend4(); // expected-warning{{redeclaration of 'friend4' should not add 'dllimport' attribute}}
    280 #ifdef MS
    281 __declspec(dllimport) inline void friend5() {} // expected-warning{{redeclaration of 'friend5' should not add 'dllimport' attribute}}
    282 #else
    283 __declspec(dllimport) inline void friend5() {} // expected-warning{{'dllimport' attribute ignored on inline function}}
    284 #endif
    285 
    286 
    287 void __declspec(dllimport) friend6(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    288 void __declspec(dllimport) friend7();
    289 struct FuncFriend2 {
    290   friend void friend6(); // expected-warning{{'friend6' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    291   friend void ::friend7();
    292 };
    293 
    294 // Implicit declarations can be redeclared with dllimport.
    295 __declspec(dllimport) void* operator new(__SIZE_TYPE__ n);
    296 
    297 // External linkage is required.
    298 __declspec(dllimport) static int staticFunc(); // expected-error{{'staticFunc' must have external linkage when declared 'dllimport'}}
    299 __declspec(dllimport) Internal internalRetFunc(); // expected-error{{'internalRetFunc' must have external linkage when declared 'dllimport'}}
    300 namespace    { __declspec(dllimport) void internalFunc(); } // expected-error{{'(anonymous namespace)::internalFunc' must have external linkage when declared 'dllimport'}}
    301 namespace ns { __declspec(dllimport) void externalFunc(); }
    302 
    303 // Import deleted functions.
    304 // FIXME: Deleted functions are definitions so a missing inline is diagnosed
    305 // here which is irrelevant. But because the delete keyword is parsed later
    306 // there is currently no straight-forward way to avoid this diagnostic.
    307 __declspec(dllimport) void deletedFunc() = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}} expected-error{{dllimport cannot be applied to non-inline function definition}}
    308 #ifdef MS
    309 __declspec(dllimport) inline void deletedInlineFunc() = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}}
    310 #else
    311 __declspec(dllimport) inline void deletedInlineFunc() = delete; // expected-warning{{'dllimport' attribute ignored on inline function}}
    312 #endif
    313 
    314 
    315 
    316 //===----------------------------------------------------------------------===//
    317 // Function templates
    318 //===----------------------------------------------------------------------===//
    319 
    320 // Import function template declaration. Check different placements.
    321 template<typename T> __declspec(dllimport) void funcTmplDecl1();
    322 template<typename T> void __declspec(dllimport) funcTmplDecl2();
    323 
    324 // Import function template definition.
    325 template<typename T> __declspec(dllimport) void funcTmplDef() {} // expected-error{{dllimport cannot be applied to non-inline function definition}}
    326 
    327 // Import inline function template.
    328 #ifdef GNU
    329 // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    330 // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    331 // expected-warning@+6{{'dllimport' attribute ignored on inline function}}
    332 // expected-warning@+9{{'inlineFuncTmplDef' redeclared inline; 'dllimport' attribute ignored}}
    333 #endif
    334 template<typename T> __declspec(dllimport) inline void inlineFuncTmpl1() {}
    335 template<typename T> inline void __attribute__((dllimport)) inlineFuncTmpl2() {}
    336 
    337 template<typename T> __declspec(dllimport) inline void inlineFuncTmplDecl();
    338 template<typename T>                              void inlineFuncTmplDecl() {}
    339 
    340 template<typename T> __declspec(dllimport) void inlineFuncTmplDef();
    341 template<typename T>                inline void inlineFuncTmplDef() {}
    342 
    343 // Redeclarations
    344 template<typename T> __declspec(dllimport) void funcTmplRedecl1();
    345 template<typename T> __declspec(dllimport) void funcTmplRedecl1();
    346 
    347 template<typename T> __declspec(dllimport) void funcTmplRedecl2(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    348 template<typename T>                       void funcTmplRedecl2(); // expected-warning{{'funcTmplRedecl2' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    349 
    350 template<typename T> __declspec(dllimport) void funcTmplRedecl3(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    351 template<typename T>                       void funcTmplRedecl3() {} // expected-warning{{'funcTmplRedecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    352 
    353 template<typename T>                       void funcTmplRedecl4(); // expected-note{{previous declaration is here}}
    354 template<typename T> __declspec(dllimport) void funcTmplRedecl4(); // expected-error{{redeclaration of 'funcTmplRedecl4' cannot add 'dllimport' attribute}}
    355 
    356 #ifdef MS
    357 template<typename T>                       void funcTmplRedecl5(); // expected-note{{previous declaration is here}}
    358 template<typename T> __declspec(dllimport) inline void funcTmplRedecl5() {} // expected-error{{redeclaration of 'funcTmplRedecl5' cannot add 'dllimport' attribute}}
    359 #endif
    360 
    361 // Function template friends
    362 struct FuncTmplFriend {
    363   template<typename T> friend __declspec(dllimport) void funcTmplFriend1();
    364   template<typename T> friend __declspec(dllimport) void funcTmplFriend2(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    365   template<typename T> friend __declspec(dllimport) void funcTmplFriend3(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    366   template<typename T> friend                       void funcTmplFriend4(); // expected-note{{previous declaration is here}}
    367 #ifdef GNU
    368 // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    369 #endif
    370   template<typename T> friend __declspec(dllimport) inline void funcTmplFriend5();
    371 };
    372 template<typename T> __declspec(dllimport) void funcTmplFriend1();
    373 template<typename T>                       void funcTmplFriend2(); // expected-warning{{'funcTmplFriend2' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    374 template<typename T>                       void funcTmplFriend3() {} // expected-warning{{'funcTmplFriend3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    375 template<typename T> __declspec(dllimport) void funcTmplFriend4(); // expected-error{{redeclaration of 'funcTmplFriend4' cannot add 'dllimport' attribute}}
    376 template<typename T>                       inline void funcTmplFriend5() {}
    377 
    378 // External linkage is required.
    379 template<typename T> __declspec(dllimport) static int staticFuncTmpl(); // expected-error{{'staticFuncTmpl' must have external linkage when declared 'dllimport'}}
    380 template<typename T> __declspec(dllimport) Internal internalRetFuncTmpl(); // expected-error{{'internalRetFuncTmpl' must have external linkage when declared 'dllimport'}}
    381 namespace    { template<typename T> __declspec(dllimport) void internalFuncTmpl(); } // expected-error{{'(anonymous namespace)::internalFuncTmpl' must have external linkage when declared 'dllimport'}}
    382 namespace ns { template<typename T> __declspec(dllimport) void externalFuncTmpl(); }
    383 
    384 
    385 template<typename T> void funcTmpl() {}
    386 template<typename T> inline void inlineFuncTmpl() {}
    387 template<typename T> __declspec(dllimport) void importedFuncTmplDecl();
    388 #ifdef GNU
    389 // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    390 #endif
    391 template<typename T> __declspec(dllimport) inline void importedFuncTmpl() {}
    392 
    393 // Import implicit instantiation of an imported function template.
    394 void useFunTmplDecl() { importedFuncTmplDecl<ImplicitInst_Imported>(); }
    395 void useFunTmplDef() { importedFuncTmpl<ImplicitInst_Imported>(); }
    396 
    397 // Import explicit instantiation declaration of an imported function template.
    398 extern template void importedFuncTmpl<ExplicitDecl_Imported>();
    399 
    400 // Import explicit instantiation definition of an imported function template.
    401 // NB: MSVC fails this instantiation without explicit dllimport which is most
    402 // likely a bug because an implicit instantiation is accepted.
    403 template void importedFuncTmpl<ExplicitInst_Imported>();
    404 
    405 // Import specialization of an imported function template. A definition must be
    406 // declared inline.
    407 template<> __declspec(dllimport) void importedFuncTmpl<ExplicitSpec_Imported>();
    408 template<> __declspec(dllimport) void importedFuncTmpl<ExplicitSpec_Def_Imported>() {} // expected-error{{dllimport cannot be applied to non-inline function definition}}
    409 #ifdef MS
    410 template<> __declspec(dllimport) inline void importedFuncTmpl<ExplicitSpec_InlineDef_Imported>() {}
    411 #endif
    412 
    413 // Not importing specialization of an imported function template without
    414 // explicit dllimport.
    415 template<> void importedFuncTmpl<ExplicitSpec_NotImported>() {}
    416 
    417 
    418 // Import explicit instantiation declaration of a non-imported function template.
    419 extern template __declspec(dllimport) void funcTmpl<ExplicitDecl_Imported>();
    420 #ifdef GNU
    421 // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    422 #endif
    423 extern template __declspec(dllimport) void inlineFuncTmpl<ExplicitDecl_Imported>();
    424 
    425 // Import explicit instantiation definition of a non-imported function template.
    426 template __declspec(dllimport) void funcTmpl<ExplicitInst_Imported>();
    427 #ifdef GNU
    428 // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    429 #endif
    430 template __declspec(dllimport) void inlineFuncTmpl<ExplicitInst_Imported>();
    431 
    432 // Import specialization of a non-imported function template. A definition must
    433 // be declared inline.
    434 template<> __declspec(dllimport) void funcTmpl<ExplicitSpec_Imported>();
    435 template<> __declspec(dllimport) void funcTmpl<ExplicitSpec_Def_Imported>() {} // expected-error{{dllimport cannot be applied to non-inline function definition}}
    436 #ifdef GNU
    437 // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    438 #endif
    439 template<> __declspec(dllimport) inline void funcTmpl<ExplicitSpec_InlineDef_Imported>() {}
    440 
    441 
    442 //===----------------------------------------------------------------------===//
    443 // Class members
    444 //===----------------------------------------------------------------------===//
    445 
    446 // Import individual members of a class.
    447 struct ImportMembers {
    448   struct Nested {
    449     __declspec(dllimport) void normalDecl();
    450     __declspec(dllimport) void normalDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    451   };
    452 
    453 #ifdef GNU
    454 // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    455 // expected-warning@+6{{'dllimport' attribute ignored on inline function}}
    456 #endif
    457   __declspec(dllimport)                void normalDecl();
    458   __declspec(dllimport)                void normalDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    459   __declspec(dllimport)                void normalInclass() {}
    460   __declspec(dllimport)                void normalInlineDef();
    461   __declspec(dllimport)         inline void normalInlineDecl();
    462 #ifdef GNU
    463 // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    464 // expected-warning@+6{{'dllimport' attribute ignored on inline function}}
    465 #endif
    466   __declspec(dllimport) virtual        void virtualDecl();
    467   __declspec(dllimport) virtual        void virtualDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    468   __declspec(dllimport) virtual        void virtualInclass() {}
    469   __declspec(dllimport) virtual        void virtualInlineDef();
    470   __declspec(dllimport) virtual inline void virtualInlineDecl();
    471 #ifdef GNU
    472 // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    473 // expected-warning@+6{{'dllimport' attribute ignored on inline function}}
    474 #endif
    475   __declspec(dllimport) static         void staticDecl();
    476   __declspec(dllimport) static         void staticDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    477   __declspec(dllimport) static         void staticInclass() {}
    478   __declspec(dllimport) static         void staticInlineDef();
    479   __declspec(dllimport) static  inline void staticInlineDecl();
    480 
    481 protected:
    482   __declspec(dllimport)                void protectedDecl();
    483 private:
    484   __declspec(dllimport)                void privateDecl();
    485 public:
    486 
    487   __declspec(dllimport)                int  Field; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
    488   __declspec(dllimport) static         int  StaticField;
    489   __declspec(dllimport) static         int  StaticFieldDef; // expected-note{{attribute is here}}
    490   __declspec(dllimport) static  const  int  StaticConstField;
    491   __declspec(dllimport) static  const  int  StaticConstFieldDef; // expected-note{{attribute is here}}
    492   __declspec(dllimport) static  const  int  StaticConstFieldEqualInit = 1;
    493   __declspec(dllimport) static  const  int  StaticConstFieldBraceInit{1};
    494   __declspec(dllimport) constexpr static int ConstexprField = 1;
    495   __declspec(dllimport) constexpr static int ConstexprFieldDef = 1; // expected-note{{attribute is here}}
    496 };
    497 
    498        void ImportMembers::Nested::normalDef() {} // expected-warning{{'ImportMembers::Nested::normalDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    499        void ImportMembers::normalDef() {} // expected-warning{{'ImportMembers::normalDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    500 #ifdef GNU
    501 // expected-warning@+2{{'ImportMembers::normalInlineDef' redeclared inline; 'dllimport' attribute ignored}}
    502 #endif
    503 inline void ImportMembers::normalInlineDef() {}
    504        void ImportMembers::normalInlineDecl() {}
    505        void ImportMembers::virtualDef() {} // expected-warning{{'ImportMembers::virtualDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    506 #ifdef GNU
    507 // expected-warning@+2{{'ImportMembers::virtualInlineDef' redeclared inline; 'dllimport' attribute ignored}}
    508 #endif
    509 inline void ImportMembers::virtualInlineDef() {}
    510        void ImportMembers::virtualInlineDecl() {}
    511        void ImportMembers::staticDef() {} // expected-warning{{'ImportMembers::staticDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    512 #ifdef GNU
    513 // expected-warning@+2{{'ImportMembers::staticInlineDef' redeclared inline; 'dllimport' attribute ignored}}
    514 #endif
    515 inline void ImportMembers::staticInlineDef() {}
    516        void ImportMembers::staticInlineDecl() {}
    517 
    518        int  ImportMembers::StaticFieldDef; // expected-error{{definition of dllimport static field not allowed}}
    519 const  int  ImportMembers::StaticConstFieldDef = 1; // expected-error{{definition of dllimport static field not allowed}}
    520 constexpr int ImportMembers::ConstexprFieldDef; // expected-error{{definition of dllimport static field not allowed}}
    521 
    522 
    523 // Import on member definitions.
    524 struct ImportMemberDefs {
    525   __declspec(dllimport)                void normalDef();
    526   __declspec(dllimport)                void normalInlineDef();
    527   __declspec(dllimport) virtual        void virtualDef();
    528   __declspec(dllimport) virtual        void virtualInlineDef();
    529   __declspec(dllimport) static         void staticDef();
    530   __declspec(dllimport) static         void staticInlineDef();
    531 #ifdef MS
    532   __declspec(dllimport)         inline void normalInlineDecl();
    533   __declspec(dllimport) virtual inline void virtualInlineDecl();
    534   __declspec(dllimport) static  inline void staticInlineDecl();
    535 #endif
    536 
    537   __declspec(dllimport) static         int  StaticField;
    538   __declspec(dllimport) static  const  int  StaticConstField;
    539   __declspec(dllimport) constexpr static int ConstexprField = 1;
    540 };
    541 
    542 __declspec(dllimport)        void ImportMemberDefs::normalDef() {} // expected-error{{dllimport cannot be applied to non-inline function definition}}
    543 __declspec(dllimport)        void ImportMemberDefs::virtualDef() {} // expected-error{{dllimport cannot be applied to non-inline function definition}}
    544 __declspec(dllimport)        void ImportMemberDefs::staticDef() {} // expected-error{{dllimport cannot be applied to non-inline function definition}}
    545 #ifdef MS
    546 __declspec(dllimport) inline void ImportMemberDefs::normalInlineDef() {}
    547 __declspec(dllimport)        void ImportMemberDefs::normalInlineDecl() {}
    548 __declspec(dllimport) inline void ImportMemberDefs::virtualInlineDef() {}
    549 __declspec(dllimport)        void ImportMemberDefs::virtualInlineDecl() {}
    550 __declspec(dllimport) inline void ImportMemberDefs::staticInlineDef() {}
    551 __declspec(dllimport)        void ImportMemberDefs::staticInlineDecl() {}
    552 #endif
    553 
    554 __declspec(dllimport)        int  ImportMemberDefs::StaticField; // expected-error{{definition of dllimport static field not allowed}} expected-note{{attribute is here}}
    555 __declspec(dllimport) const  int  ImportMemberDefs::StaticConstField = 1; // expected-error{{definition of dllimport static field not allowed}} expected-note{{attribute is here}}
    556 __declspec(dllimport) constexpr int ImportMemberDefs::ConstexprField; // expected-error{{definition of dllimport static field not allowed}} expected-note{{attribute is here}}
    557 
    558 
    559 // Import special member functions.
    560 struct ImportSpecials {
    561   __declspec(dllimport) ImportSpecials();
    562   __declspec(dllimport) ~ImportSpecials();
    563   __declspec(dllimport) ImportSpecials(const ImportSpecials&);
    564   __declspec(dllimport) ImportSpecials& operator=(const ImportSpecials&);
    565   __declspec(dllimport) ImportSpecials(ImportSpecials&&);
    566   __declspec(dllimport) ImportSpecials& operator=(ImportSpecials&&);
    567 };
    568 
    569 
    570 // Import deleted member functions.
    571 struct ImportDeleted {
    572 #ifdef MS
    573   __declspec(dllimport) ImportDeleted() = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}}
    574   __declspec(dllimport) ~ImportDeleted() = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}}
    575   __declspec(dllimport) ImportDeleted(const ImportDeleted&) = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}}
    576   __declspec(dllimport) ImportDeleted& operator=(const ImportDeleted&) = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}}
    577   __declspec(dllimport) ImportDeleted(ImportDeleted&&) = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}}
    578   __declspec(dllimport) ImportDeleted& operator=(ImportDeleted&&) = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}}
    579   __declspec(dllimport) void deleted() = delete; // expected-error{{attribute 'dllimport' cannot be applied to a deleted function}}
    580 #else
    581   __declspec(dllimport) ImportDeleted() = delete; // expected-warning{{'dllimport' attribute ignored on inline function}}
    582   __declspec(dllimport) ~ImportDeleted() = delete; // expected-warning{{'dllimport' attribute ignored on inline function}}
    583   __declspec(dllimport) ImportDeleted(const ImportDeleted&) = delete; // expected-warning{{'dllimport' attribute ignored on inline function}}
    584   __declspec(dllimport) ImportDeleted& operator=(const ImportDeleted&) = delete; // expected-warning{{'dllimport' attribute ignored on inline function}}
    585   __declspec(dllimport) ImportDeleted(ImportDeleted&&) = delete; // expected-warning{{'dllimport' attribute ignored on inline function}}
    586   __declspec(dllimport) ImportDeleted& operator=(ImportDeleted&&) = delete; // expected-warning{{'dllimport' attribute ignored on inline function}}
    587   __declspec(dllimport) void deleted() = delete; // expected-warning{{'dllimport' attribute ignored on inline function}}
    588 #endif
    589 };
    590 
    591 
    592 // Import allocation functions.
    593 struct ImportAlloc {
    594   __declspec(dllimport) void* operator new(__SIZE_TYPE__);
    595   __declspec(dllimport) void* operator new[](__SIZE_TYPE__);
    596   __declspec(dllimport) void operator delete(void*);
    597   __declspec(dllimport) void operator delete[](void*);
    598 };
    599 
    600 
    601 // Import defaulted member functions.
    602 struct ImportDefaulted {
    603 #ifdef GNU
    604   // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    605   // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    606   // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    607   // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    608   // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    609   // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    610 #endif
    611   __declspec(dllimport) ImportDefaulted() = default;
    612   __declspec(dllimport) ~ImportDefaulted() = default;
    613   __declspec(dllimport) ImportDefaulted(const ImportDefaulted&) = default;
    614   __declspec(dllimport) ImportDefaulted& operator=(const ImportDefaulted&) = default;
    615   __declspec(dllimport) ImportDefaulted(ImportDefaulted&&) = default;
    616   __declspec(dllimport) ImportDefaulted& operator=(ImportDefaulted&&) = default;
    617 };
    618 
    619 
    620 // Import defaulted member function definitions.
    621 struct ImportDefaultedDefs {
    622   __declspec(dllimport) ImportDefaultedDefs();
    623   __declspec(dllimport) ~ImportDefaultedDefs(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    624 
    625 #ifdef GNU
    626 // expected-warning@+3{{'dllimport' attribute ignored on inline function}}
    627 // expected-note@+2{{previous declaration is here}}
    628 #endif
    629   __declspec(dllimport) inline ImportDefaultedDefs(const ImportDefaultedDefs&);
    630   __declspec(dllimport) ImportDefaultedDefs& operator=(const ImportDefaultedDefs&);
    631 
    632   __declspec(dllimport) ImportDefaultedDefs(ImportDefaultedDefs&&);
    633   __declspec(dllimport) ImportDefaultedDefs& operator=(ImportDefaultedDefs&&); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    634 };
    635 
    636 // Not allowed on definitions.
    637 __declspec(dllimport) ImportDefaultedDefs::ImportDefaultedDefs() = default; // expected-error{{dllimport cannot be applied to non-inline function definition}}
    638 
    639 // dllimport cannot be dropped.
    640 ImportDefaultedDefs::~ImportDefaultedDefs() = default; // expected-warning{{'ImportDefaultedDefs::~ImportDefaultedDefs' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    641 
    642 // Import inline declaration and definition.
    643 #ifdef GNU
    644 // expected-error@+3{{redeclaration of 'ImportDefaultedDefs::ImportDefaultedDefs' cannot add 'dllimport' attribute}}
    645 // expected-warning@+3{{'ImportDefaultedDefs::operator=' redeclared inline; 'dllimport' attribute ignored}}
    646 #endif
    647 __declspec(dllimport) ImportDefaultedDefs::ImportDefaultedDefs(const ImportDefaultedDefs&) = default;
    648 inline ImportDefaultedDefs& ImportDefaultedDefs::operator=(const ImportDefaultedDefs&) = default;
    649 
    650 __declspec(dllimport) ImportDefaultedDefs::ImportDefaultedDefs(ImportDefaultedDefs&&) = default; // expected-error{{dllimport cannot be applied to non-inline function definition}}
    651 ImportDefaultedDefs& ImportDefaultedDefs::operator=(ImportDefaultedDefs&&) = default; // expected-warning{{'ImportDefaultedDefs::operator=' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    652 
    653 
    654 // Redeclarations cannot add dllimport.
    655 struct MemberRedecl {
    656                  void normalDef();         // expected-note{{previous declaration is here}}
    657           inline void normalInlineDecl();  // expected-note{{previous declaration is here}}
    658   virtual        void virtualDef();        // expected-note{{previous declaration is here}}
    659   virtual inline void virtualInlineDecl(); // expected-note{{previous declaration is here}}
    660   static         void staticDef();         // expected-note{{previous declaration is here}}
    661   static  inline void staticInlineDecl();  // expected-note{{previous declaration is here}}
    662 
    663 #ifdef MS
    664   // expected-note@+4{{previous declaration is here}}
    665   // expected-note@+4{{previous declaration is here}}
    666   // expected-note@+4{{previous declaration is here}}
    667 #endif
    668                  void normalInlineDef();
    669   virtual        void virtualInlineDef();
    670   static         void staticInlineDef();
    671 
    672   static         int  StaticField;         // expected-note{{previous declaration is here}}
    673   static  const  int  StaticConstField;    // expected-note{{previous declaration is here}}
    674   constexpr static int ConstexprField = 1; // expected-note{{previous declaration is here}}
    675 };
    676 
    677 __declspec(dllimport)        void MemberRedecl::normalDef() {}         // expected-error{{redeclaration of 'MemberRedecl::normalDef' cannot add 'dllimport' attribute}}
    678                                                                        // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
    679 __declspec(dllimport)        void MemberRedecl::normalInlineDecl() {}  // expected-error{{redeclaration of 'MemberRedecl::normalInlineDecl' cannot add 'dllimport' attribute}}
    680 __declspec(dllimport)        void MemberRedecl::virtualDef() {}        // expected-error{{redeclaration of 'MemberRedecl::virtualDef' cannot add 'dllimport' attribute}}
    681                                                                        // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
    682 __declspec(dllimport)        void MemberRedecl::virtualInlineDecl() {} // expected-error{{redeclaration of 'MemberRedecl::virtualInlineDecl' cannot add 'dllimport' attribute}}
    683 __declspec(dllimport)        void MemberRedecl::staticDef() {}         // expected-error{{redeclaration of 'MemberRedecl::staticDef' cannot add 'dllimport' attribute}}
    684                                                                        // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
    685 __declspec(dllimport)        void MemberRedecl::staticInlineDecl() {}  // expected-error{{redeclaration of 'MemberRedecl::staticInlineDecl' cannot add 'dllimport' attribute}}
    686 
    687 #ifdef MS
    688 __declspec(dllimport) inline void MemberRedecl::normalInlineDef() {}   // expected-error{{redeclaration of 'MemberRedecl::normalInlineDef' cannot add 'dllimport' attribute}}
    689 __declspec(dllimport) inline void MemberRedecl::virtualInlineDef() {}  // expected-error{{redeclaration of 'MemberRedecl::virtualInlineDef' cannot add 'dllimport' attribute}}
    690 __declspec(dllimport) inline void MemberRedecl::staticInlineDef() {}   // expected-error{{redeclaration of 'MemberRedecl::staticInlineDef' cannot add 'dllimport' attribute}}
    691 #else
    692 __declspec(dllimport) inline void MemberRedecl::normalInlineDef() {}   // expected-warning{{'dllimport' attribute ignored on inline function}}
    693 __declspec(dllimport) inline void MemberRedecl::virtualInlineDef() {}  // expected-warning{{'dllimport' attribute ignored on inline function}}
    694 __declspec(dllimport) inline void MemberRedecl::staticInlineDef() {}   // expected-warning{{'dllimport' attribute ignored on inline function}}
    695 #endif
    696 
    697 
    698 
    699 __declspec(dllimport)        int  MemberRedecl::StaticField = 1;       // expected-error{{redeclaration of 'MemberRedecl::StaticField' cannot add 'dllimport' attribute}}
    700                                                                        // expected-error@-1{{definition of dllimport static field not allowed}}
    701                                                                        // expected-note@-2{{attribute is here}}
    702 __declspec(dllimport) const  int  MemberRedecl::StaticConstField = 1;  // expected-error{{redeclaration of 'MemberRedecl::StaticConstField' cannot add 'dllimport' attribute}}
    703                                                                        // expected-error@-1{{definition of dllimport static field not allowed}}
    704                                                                        // expected-note@-2{{attribute is here}}
    705 __declspec(dllimport) constexpr int MemberRedecl::ConstexprField;      // expected-error{{redeclaration of 'MemberRedecl::ConstexprField' cannot add 'dllimport' attribute}}
    706                                                                        // expected-error@-1{{definition of dllimport static field not allowed}}
    707                                                                        // expected-note@-2{{attribute is here}}
    708 
    709 
    710 
    711 //===----------------------------------------------------------------------===//
    712 // Class member templates
    713 //===----------------------------------------------------------------------===//
    714 
    715 struct ImportMemberTmpl {
    716   template<typename T> __declspec(dllimport)               void normalDecl();
    717   template<typename T> __declspec(dllimport)               void normalDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    718   template<typename T> __declspec(dllimport)               void normalInlineDef();
    719   template<typename T> __declspec(dllimport) static        void staticDecl();
    720   template<typename T> __declspec(dllimport) static        void staticDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    721   template<typename T> __declspec(dllimport) static        void staticInlineDef();
    722 
    723 #ifdef GNU
    724   // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    725   // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    726   // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    727   // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
    728 #endif
    729   template<typename T> __declspec(dllimport)               void normalInclass() {}
    730   template<typename T> __declspec(dllimport)        inline void normalInlineDecl();
    731   template<typename T> __declspec(dllimport) static        void staticInclass() {}
    732   template<typename T> __declspec(dllimport) static inline void staticInlineDecl();
    733 
    734 #if __has_feature(cxx_variable_templates)
    735   template<typename T> __declspec(dllimport) static        int  StaticField;
    736   template<typename T> __declspec(dllimport) static        int  StaticFieldDef; // expected-note{{attribute is here}}
    737   template<typename T> __declspec(dllimport) static const  int  StaticConstField;
    738   template<typename T> __declspec(dllimport) static const  int  StaticConstFieldDef; // expected-note{{attribute is here}}
    739   template<typename T> __declspec(dllimport) static const  int  StaticConstFieldEqualInit = 1;
    740   template<typename T> __declspec(dllimport) static const  int  StaticConstFieldBraceInit{1};
    741   template<typename T> __declspec(dllimport) constexpr static int ConstexprField = 1;
    742   template<typename T> __declspec(dllimport) constexpr static int ConstexprFieldDef = 1; // expected-note{{attribute is here}}
    743 #endif // __has_feature(cxx_variable_templates)
    744 };
    745 
    746 template<typename T>        void ImportMemberTmpl::normalDef() {} // expected-warning{{'ImportMemberTmpl::normalDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    747 template<typename T>        void ImportMemberTmpl::normalInlineDecl() {}
    748 template<typename T>        void ImportMemberTmpl::staticDef() {} // expected-warning{{'ImportMemberTmpl::staticDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
    749 template<typename T>        void ImportMemberTmpl::staticInlineDecl() {}
    750 
    751 #ifdef GNU
    752 // expected-warning@+3{{ImportMemberTmpl::normalInlineDef' redeclared inline; 'dllimport' attribute ignored}}
    753 // expected-warning@+3{{ImportMemberTmpl::staticInlineDef' redeclared inline; 'dllimport' attribute ignored}}
    754 #endif
    755 template<typename T> inline void ImportMemberTmpl::normalInlineDef() {}
    756 template<typename T> inline void ImportMemberTmpl::staticInlineDef() {}
    757 
    758 #if __has_feature(cxx_variable_templates)
    759 template<typename T>        int  ImportMemberTmpl::StaticFieldDef; // expected-error{{definition of dllimport static field not allowed}}
    760 template<typename T> const  int  ImportMemberTmpl::StaticConstFieldDef = 1; // expected-error{{definition of dllimport static field not allowed}}
    761 template<typename T> constexpr int ImportMemberTmpl::ConstexprFieldDef; // expected-error{{definition of dllimport static field not allowed}}
    762 #endif // __has_feature(cxx_variable_templates)
    763 
    764 
    765 // Redeclarations cannot add dllimport.
    766 struct MemTmplRedecl {
    767   template<typename T>               void normalDef();         // expected-note{{previous declaration is here}}
    768   template<typename T>        inline void normalInlineDecl();  // expected-note{{previous declaration is here}}
    769   template<typename T> static        void staticDef();         // expected-note{{previous declaration is here}}
    770   template<typename T> static inline void staticInlineDecl();  // expected-note{{previous declaration is here}}
    771 
    772 #ifdef MS
    773 // expected-note@+3{{previous declaration is here}}
    774 // expected-note@+3{{previous declaration is here}}
    775 #endif
    776   template<typename T>               void normalInlineDef();
    777   template<typename T> static        void staticInlineDef();
    778 
    779 #if __has_feature(cxx_variable_templates)
    780   template<typename T> static        int  StaticField;         // expected-note{{previous declaration is here}}
    781   template<typename T> static const  int  StaticConstField;    // expected-note{{previous declaration is here}}
    782   template<typename T> constexpr static int ConstexprField = 1; // expected-note{{previous declaration is here}}
    783 #endif // __has_feature(cxx_variable_templates)
    784 };
    785 
    786 template<typename T> __declspec(dllimport)        void MemTmplRedecl::normalDef() {}        // expected-error{{redeclaration of 'MemTmplRedecl::normalDef' cannot add 'dllimport' attribute}}
    787                                                                                             // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
    788 #ifdef MS
    789 template<typename T> __declspec(dllimport) inline void MemTmplRedecl::normalInlineDef() {}  // expected-error{{redeclaration of 'MemTmplRedecl::normalInlineDef' cannot add 'dllimport' attribute}}
    790 #else
    791 template<typename T> __declspec(dllimport) inline void MemTmplRedecl::normalInlineDef() {}  // expected-warning{{'dllimport' attribute ignored on inline function}}
    792 #endif
    793 template<typename T> __declspec(dllimport)        void MemTmplRedecl::normalInlineDecl() {} // expected-error{{redeclaration of 'MemTmplRedecl::normalInlineDecl' cannot add 'dllimport' attribute}}
    794 template<typename T> __declspec(dllimport)        void MemTmplRedecl::staticDef() {}        // expected-error{{redeclaration of 'MemTmplRedecl::staticDef' cannot add 'dllimport' attribute}}
    795                                                                                             // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
    796 #ifdef MS
    797 template<typename T> __declspec(dllimport) inline void MemTmplRedecl::staticInlineDef() {}  // expected-error{{redeclaration of 'MemTmplRedecl::staticInlineDef' cannot add 'dllimport' attribute}}
    798 #else
    799 template<typename T> __declspec(dllimport) inline void MemTmplRedecl::staticInlineDef() {}  // expected-warning{{'dllimport' attribute ignored on inline function}}
    800 #endif
    801 template<typename T> __declspec(dllimport)        void MemTmplRedecl::staticInlineDecl() {} // expected-error{{redeclaration of 'MemTmplRedecl::staticInlineDecl' cannot add 'dllimport' attribute}}
    802 
    803 #if __has_feature(cxx_variable_templates)
    804 template<typename T> __declspec(dllimport)        int  MemTmplRedecl::StaticField = 1;      // expected-error{{redeclaration of 'MemTmplRedecl::StaticField' cannot add 'dllimport' attribute}}
    805                                                                                             // expected-error@-1{{definition of dllimport static field not allowed}}
    806                                                                                             // expected-note@-2{{attribute is here}}
    807 template<typename T> __declspec(dllimport) const  int  MemTmplRedecl::StaticConstField = 1; // expected-error{{redeclaration of 'MemTmplRedecl::StaticConstField' cannot add 'dllimport' attribute}}
    808                                                                                             // expected-error@-1{{definition of dllimport static field not allowed}}
    809                                                                                             // expected-note@-2{{attribute is here}}
    810 template<typename T> __declspec(dllimport) constexpr int MemTmplRedecl::ConstexprField;     // expected-error{{redeclaration of 'MemTmplRedecl::ConstexprField' cannot add 'dllimport' attribute}}
    811                                                                                             // expected-error@-1{{definition of dllimport static field not allowed}}
    812                                                                                             // expected-note@-2{{attribute is here}}
    813 #endif // __has_feature(cxx_variable_templates)
    814 
    815 
    816 
    817 struct MemFunTmpl {
    818   template<typename T>                              void normalDef() {}
    819 #ifdef GNU
    820   // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    821 #endif
    822   template<typename T> __declspec(dllimport)        void importedNormal() {}
    823   template<typename T>                       static void staticDef() {}
    824 #ifdef GNU
    825   // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    826 #endif
    827   template<typename T> __declspec(dllimport) static void importedStatic() {}
    828 };
    829 
    830 // Import implicit instantiation of an imported member function template.
    831 void useMemFunTmpl() {
    832   MemFunTmpl().importedNormal<ImplicitInst_Imported>();
    833   MemFunTmpl().importedStatic<ImplicitInst_Imported>();
    834 }
    835 
    836 // Import explicit instantiation declaration of an imported member function
    837 // template.
    838 extern template void MemFunTmpl::importedNormal<ExplicitDecl_Imported>();
    839 extern template void MemFunTmpl::importedStatic<ExplicitDecl_Imported>();
    840 
    841 // Import explicit instantiation definition of an imported member function
    842 // template.
    843 // NB: MSVC fails this instantiation without explicit dllimport.
    844 template void MemFunTmpl::importedNormal<ExplicitInst_Imported>();
    845 template void MemFunTmpl::importedStatic<ExplicitInst_Imported>();
    846 
    847 // Import specialization of an imported member function template.
    848 template<> __declspec(dllimport) void MemFunTmpl::importedNormal<ExplicitSpec_Imported>();
    849 template<> __declspec(dllimport) void MemFunTmpl::importedNormal<ExplicitSpec_Def_Imported>() {} // error on mingw
    850 #ifdef GNU
    851   // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    852 #endif
    853 template<> __declspec(dllimport) inline void MemFunTmpl::importedNormal<ExplicitSpec_InlineDef_Imported>() {}
    854 #if 1
    855 // FIXME: This should not be an error when targeting MSVC. (PR21406)
    856 // expected-error@-7{{dllimport cannot be applied to non-inline function definition}}
    857 #endif
    858 
    859 template<> __declspec(dllimport) void MemFunTmpl::importedStatic<ExplicitSpec_Imported>();
    860 template<> __declspec(dllimport) void MemFunTmpl::importedStatic<ExplicitSpec_Def_Imported>() {} // error on mingw
    861 #ifdef GNU
    862   // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    863 #endif
    864 template<> __declspec(dllimport) inline void MemFunTmpl::importedStatic<ExplicitSpec_InlineDef_Imported>() {}
    865 #if 1
    866 // FIXME: This should not be an error when targeting MSVC. (PR21406)
    867 // expected-error@-7{{dllimport cannot be applied to non-inline function definition}}
    868 #endif
    869 
    870 // Not importing specialization of an imported member function template without
    871 // explicit dllimport.
    872 template<> void MemFunTmpl::importedNormal<ExplicitSpec_NotImported>() {}
    873 template<> void MemFunTmpl::importedStatic<ExplicitSpec_NotImported>() {}
    874 
    875 
    876 // Import explicit instantiation declaration of a non-imported member function
    877 // template.
    878 #ifdef GNU
    879 // expected-warning@+3{{'dllimport' attribute ignored on inline function}}
    880 // expected-warning@+3{{'dllimport' attribute ignored on inline function}}
    881 #endif
    882 extern template __declspec(dllimport) void MemFunTmpl::normalDef<ExplicitDecl_Imported>();
    883 extern template __declspec(dllimport) void MemFunTmpl::staticDef<ExplicitDecl_Imported>();
    884 
    885 // Import explicit instantiation definition of a non-imported member function
    886 // template.
    887 #ifdef GNU
    888 // expected-warning@+3{{'dllimport' attribute ignored on inline function}}
    889 // expected-warning@+3{{'dllimport' attribute ignored on inline function}}
    890 #endif
    891 template __declspec(dllimport) void MemFunTmpl::normalDef<ExplicitInst_Imported>();
    892 template __declspec(dllimport) void MemFunTmpl::staticDef<ExplicitInst_Imported>();
    893 
    894 // Import specialization of a non-imported member function template.
    895 template<> __declspec(dllimport) void MemFunTmpl::normalDef<ExplicitSpec_Imported>();
    896 template<> __declspec(dllimport) void MemFunTmpl::normalDef<ExplicitSpec_Def_Imported>() {} // error on mingw
    897 #ifdef GNU
    898   // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    899 #endif
    900 template<> __declspec(dllimport) inline void MemFunTmpl::normalDef<ExplicitSpec_InlineDef_Imported>() {}
    901 #if 1
    902 // FIXME: This should not be an error when targeting MSVC. (PR21406)
    903 // expected-error@-7{{dllimport cannot be applied to non-inline function definition}}
    904 #endif
    905 
    906 template<> __declspec(dllimport) void MemFunTmpl::staticDef<ExplicitSpec_Imported>();
    907 template<> __declspec(dllimport) void MemFunTmpl::staticDef<ExplicitSpec_Def_Imported>() {} // error on mingw
    908 #ifdef GNU
    909   // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
    910 #endif
    911 template<> __declspec(dllimport) inline void MemFunTmpl::staticDef<ExplicitSpec_InlineDef_Imported>() {}
    912 #if 1
    913 // FIXME: This should not be an error when targeting MSVC. (PR21406)
    914 // expected-error@-7{{dllimport cannot be applied to non-inline function definition}}
    915 #endif
    916 
    917 
    918 
    919 #if __has_feature(cxx_variable_templates)
    920 struct MemVarTmpl {
    921   template<typename T>                       static const int StaticVar = 1;
    922   template<typename T> __declspec(dllimport) static const int ImportedStaticVar = 1;
    923 };
    924 
    925 // Import implicit instantiation of an imported member variable template.
    926 int useMemVarTmpl() { return MemVarTmpl::ImportedStaticVar<ImplicitInst_Imported>; }
    927 
    928 // Import explicit instantiation declaration of an imported member variable
    929 // template.
    930 extern template const int MemVarTmpl::ImportedStaticVar<ExplicitDecl_Imported>;
    931 
    932 // An explicit instantiation definition of an imported member variable template
    933 // cannot be imported because the template must be defined which is illegal. The
    934 // in-class initializer does not count.
    935 
    936 // Import specialization of an imported member variable template.
    937 template<> __declspec(dllimport) const int MemVarTmpl::ImportedStaticVar<ExplicitSpec_Imported>;
    938 template<> __declspec(dllimport) const int MemVarTmpl::ImportedStaticVar<ExplicitSpec_Def_Imported> = 1;
    939                                                                                 // expected-error@-1{{definition of dllimport static field not allowed}}
    940                                                                                 // expected-note@-2{{attribute is here}}
    941 
    942 // Not importing specialization of a member variable template without explicit
    943 // dllimport.
    944 template<> const int MemVarTmpl::ImportedStaticVar<ExplicitSpec_NotImported>;
    945 
    946 
    947 // Import explicit instantiation declaration of a non-imported member variable
    948 // template.
    949 extern template __declspec(dllimport) const int MemVarTmpl::StaticVar<ExplicitDecl_Imported>;
    950 
    951 // An explicit instantiation definition of a non-imported member variable template
    952 // cannot be imported because the template must be defined which is illegal. The
    953 // in-class initializer does not count.
    954 
    955 // Import specialization of a non-imported member variable template.
    956 template<> __declspec(dllimport) const int MemVarTmpl::StaticVar<ExplicitSpec_Imported>;
    957 template<> __declspec(dllimport) const int MemVarTmpl::StaticVar<ExplicitSpec_Def_Imported> = 1;
    958                                                                                 // expected-error@-1{{definition of dllimport static field not allowed}}
    959                                                                                 // expected-note@-2{{attribute is here}}
    960 
    961 #endif // __has_feature(cxx_variable_templates)
    962 
    963 
    964 
    965 //===----------------------------------------------------------------------===//
    966 // Class template members
    967 //===----------------------------------------------------------------------===//
    968 
    969 // Import individual members of a class template.
    970 template<typename T>
    971 struct ImportClassTmplMembers {
    972   __declspec(dllimport)                void normalDecl();
    973   __declspec(dllimport)                void normalDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    974   __declspec(dllimport)                void normalInlineDef();
    975   __declspec(dllimport) virtual        void virtualDecl();
    976   __declspec(dllimport) virtual        void virtualDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    977   __declspec(dllimport) virtual        void virtualInlineDef();
    978   __declspec(dllimport) static         void staticDecl();
    979   __declspec(dllimport) static         void staticDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
    980   __declspec(dllimport) static         void staticInlineDef();
    981 
    982 #ifdef GNU
    983 // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    984 // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    985 // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    986 // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    987 // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    988 // expected-warning@+7{{'dllimport' attribute ignored on inline function}}
    989 #endif
    990   __declspec(dllimport)                void normalInclass() {}
    991   __declspec(dllimport)         inline void normalInlineDecl();
    992   __declspec(dllimport) virtual        void virtualInclass() {}
    993   __declspec(dllimport) virtual inline void virtualInlineDecl();
    994   __declspec(dllimport) static         void staticInclass() {}
    995   __declspec(dllimport) static  inline void staticInlineDecl();
    996 
    997 protected:
    998   __declspec(dllimport)                void protectedDecl();
    999 private:
   1000   __declspec(dllimport)                void privateDecl();
   1001 public:
   1002 
   1003   __declspec(dllimport)                int  Field; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
   1004   __declspec(dllimport) static         int  StaticField;
   1005   __declspec(dllimport) static         int  StaticFieldDef; // expected-note{{attribute is here}}
   1006   __declspec(dllimport) static  const  int  StaticConstField;
   1007   __declspec(dllimport) static  const  int  StaticConstFieldDef; // expected-note{{attribute is here}}
   1008   __declspec(dllimport) static  const  int  StaticConstFieldEqualInit = 1;
   1009   __declspec(dllimport) static  const  int  StaticConstFieldBraceInit{1};
   1010   __declspec(dllimport) constexpr static int ConstexprField = 1;
   1011   __declspec(dllimport) constexpr static int ConstexprFieldDef = 1; // expected-note{{attribute is here}}
   1012 };
   1013 
   1014 // NB: MSVC is inconsistent here and disallows *InlineDef on class templates,
   1015 // but allows it on classes. We allow both.
   1016 template<typename T>        void ImportClassTmplMembers<T>::normalDef() {} // expected-warning{{'ImportClassTmplMembers::normalDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
   1017 #ifdef GNU
   1018 // expected-warning@+2{{'ImportClassTmplMembers::normalInlineDef' redeclared inline; 'dllimport' attribute ignored}}
   1019 #endif
   1020 template<typename T> inline void ImportClassTmplMembers<T>::normalInlineDef() {}
   1021 template<typename T>        void ImportClassTmplMembers<T>::normalInlineDecl() {}
   1022 template<typename T>        void ImportClassTmplMembers<T>::virtualDef() {} // expected-warning{{'ImportClassTmplMembers::virtualDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
   1023 #ifdef GNU
   1024 // expected-warning@+2{{'ImportClassTmplMembers::virtualInlineDef' redeclared inline; 'dllimport' attribute ignored}}
   1025 #endif
   1026 template<typename T> inline void ImportClassTmplMembers<T>::virtualInlineDef() {}
   1027 template<typename T>        void ImportClassTmplMembers<T>::virtualInlineDecl() {}
   1028 template<typename T>        void ImportClassTmplMembers<T>::staticDef() {} // expected-warning{{'ImportClassTmplMembers::staticDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
   1029 #ifdef GNU
   1030 // expected-warning@+2{{'ImportClassTmplMembers::staticInlineDef' redeclared inline; 'dllimport' attribute ignored}}
   1031 #endif
   1032 template<typename T> inline void ImportClassTmplMembers<T>::staticInlineDef() {}
   1033 template<typename T>        void ImportClassTmplMembers<T>::staticInlineDecl() {}
   1034 
   1035 template<typename T>        int  ImportClassTmplMembers<T>::StaticFieldDef; // expected-warning{{definition of dllimport static field}}
   1036 template<typename T> const  int  ImportClassTmplMembers<T>::StaticConstFieldDef = 1; // expected-warning{{definition of dllimport static field}}
   1037 template<typename T> constexpr int ImportClassTmplMembers<T>::ConstexprFieldDef; // expected-warning{{definition of dllimport static field}}
   1038 
   1039 
   1040 // Redeclarations cannot add dllimport.
   1041 template<typename T>
   1042 struct CTMR /*ClassTmplMemberRedecl*/ {
   1043                  void normalDef();         // expected-note{{previous declaration is here}}
   1044           inline void normalInlineDecl();  // expected-note{{previous declaration is here}}
   1045   virtual        void virtualDef();        // expected-note{{previous declaration is here}}
   1046   virtual inline void virtualInlineDecl(); // expected-note{{previous declaration is here}}
   1047   static         void staticDef();         // expected-note{{previous declaration is here}}
   1048   static  inline void staticInlineDecl();  // expected-note{{previous declaration is here}}
   1049 
   1050 #ifdef MS
   1051 // expected-note@+4{{previous declaration is here}}
   1052 // expected-note@+4{{previous declaration is here}}
   1053 // expected-note@+4{{previous declaration is here}}
   1054 #endif
   1055                  void normalInlineDef();
   1056   virtual        void virtualInlineDef();
   1057   static         void staticInlineDef();
   1058 
   1059   static         int  StaticField;         // expected-note{{previous declaration is here}}
   1060   static  const  int  StaticConstField;    // expected-note{{previous declaration is here}}
   1061   constexpr static int ConstexprField = 1; // expected-note{{previous declaration is here}}
   1062 };
   1063 
   1064 template<typename T> __declspec(dllimport)        void CTMR<T>::normalDef() {}         // expected-error{{redeclaration of 'CTMR::normalDef' cannot add 'dllimport' attribute}}
   1065                                                                                        // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
   1066 template<typename T> __declspec(dllimport)        void CTMR<T>::normalInlineDecl() {}  // expected-error{{redeclaration of 'CTMR::normalInlineDecl' cannot add 'dllimport' attribute}}
   1067 template<typename T> __declspec(dllimport)        void CTMR<T>::virtualDef() {}        // expected-error{{redeclaration of 'CTMR::virtualDef' cannot add 'dllimport' attribute}}
   1068                                                                                        // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
   1069 template<typename T> __declspec(dllimport)        void CTMR<T>::virtualInlineDecl() {} // expected-error{{redeclaration of 'CTMR::virtualInlineDecl' cannot add 'dllimport' attribute}}
   1070 template<typename T> __declspec(dllimport)        void CTMR<T>::staticDef() {}         // expected-error{{redeclaration of 'CTMR::staticDef' cannot add 'dllimport' attribute}}
   1071                                                                                        // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
   1072 template<typename T> __declspec(dllimport)        void CTMR<T>::staticInlineDecl() {}  // expected-error{{redeclaration of 'CTMR::staticInlineDecl' cannot add 'dllimport' attribute}}
   1073 
   1074 #ifdef MS
   1075 template<typename T> __declspec(dllimport) inline void CTMR<T>::normalInlineDef() {}   // expected-error{{redeclaration of 'CTMR::normalInlineDef' cannot add 'dllimport' attribute}}
   1076 template<typename T> __declspec(dllimport) inline void CTMR<T>::virtualInlineDef() {}  // expected-error{{redeclaration of 'CTMR::virtualInlineDef' cannot add 'dllimport' attribute}}
   1077 template<typename T> __declspec(dllimport) inline void CTMR<T>::staticInlineDef() {}   // expected-error{{redeclaration of 'CTMR::staticInlineDef' cannot add 'dllimport' attribute}}
   1078 #else
   1079 template<typename T> __declspec(dllimport) inline void CTMR<T>::normalInlineDef() {}   // expected-warning{{'dllimport' attribute ignored on inline function}}
   1080 template<typename T> __declspec(dllimport) inline void CTMR<T>::virtualInlineDef() {}  // expected-warning{{'dllimport' attribute ignored on inline function}}
   1081 template<typename T> __declspec(dllimport) inline void CTMR<T>::staticInlineDef() {}   // expected-warning{{'dllimport' attribute ignored on inline function}}
   1082 #endif
   1083 
   1084 template<typename T> __declspec(dllimport)        int  CTMR<T>::StaticField = 1;       // expected-error{{redeclaration of 'CTMR::StaticField' cannot add 'dllimport' attribute}}
   1085                                                                                        // expected-warning@-1{{definition of dllimport static field}}
   1086                                                                                        // expected-note@-2{{attribute is here}}
   1087 template<typename T> __declspec(dllimport) const  int  CTMR<T>::StaticConstField = 1;  // expected-error{{redeclaration of 'CTMR::StaticConstField' cannot add 'dllimport' attribute}}
   1088                                                                                        // expected-warning@-1{{definition of dllimport static field}}
   1089                                                                                        // expected-note@-2{{attribute is here}}
   1090 template<typename T> __declspec(dllimport) constexpr int CTMR<T>::ConstexprField;      // expected-error{{redeclaration of 'CTMR::ConstexprField' cannot add 'dllimport' attribute}}
   1091                                                                                        // expected-warning@-1{{definition of dllimport static field}}
   1092                                                                                        // expected-note@-2{{attribute is here}}
   1093 
   1094 
   1095 
   1096 //===----------------------------------------------------------------------===//
   1097 // Class template member templates
   1098 //===----------------------------------------------------------------------===//
   1099 
   1100 template<typename T>
   1101 struct ImportClsTmplMemTmpl {
   1102   template<typename U> __declspec(dllimport)               void normalDecl();
   1103   template<typename U> __declspec(dllimport)               void normalDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
   1104   template<typename U> __declspec(dllimport)               void normalInlineDef();
   1105   template<typename U> __declspec(dllimport) static        void staticDecl();
   1106   template<typename U> __declspec(dllimport) static        void staticDef(); // expected-note{{previous declaration is here}} expected-note{{previous attribute is here}}
   1107   template<typename U> __declspec(dllimport) static        void staticInlineDef();
   1108 
   1109 #ifdef GNU
   1110   // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
   1111   // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
   1112   // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
   1113   // expected-warning@+5{{'dllimport' attribute ignored on inline function}}
   1114 #endif
   1115   template<typename U> __declspec(dllimport)               void normalInclass() {}
   1116   template<typename U> __declspec(dllimport)        inline void normalInlineDecl();
   1117   template<typename U> __declspec(dllimport) static        void staticInclass() {}
   1118   template<typename U> __declspec(dllimport) static inline void staticInlineDecl();
   1119 
   1120 #if __has_feature(cxx_variable_templates)
   1121   template<typename U> __declspec(dllimport) static        int  StaticField;
   1122   template<typename U> __declspec(dllimport) static        int  StaticFieldDef; // expected-note{{attribute is here}}
   1123   template<typename U> __declspec(dllimport) static const  int  StaticConstField;
   1124   template<typename U> __declspec(dllimport) static const  int  StaticConstFieldDef; // expected-note{{attribute is here}}
   1125   template<typename U> __declspec(dllimport) static const  int  StaticConstFieldEqualInit = 1;
   1126   template<typename U> __declspec(dllimport) static const  int  StaticConstFieldBraceInit{1};
   1127   template<typename U> __declspec(dllimport) constexpr static int ConstexprField = 1;
   1128   template<typename U> __declspec(dllimport) constexpr static int ConstexprFieldDef = 1; // expected-note{{attribute is here}}
   1129 #endif // __has_feature(cxx_variable_templates)
   1130 };
   1131 
   1132 template<typename T> template<typename U>        void ImportClsTmplMemTmpl<T>::normalDef() {} // expected-warning{{'ImportClsTmplMemTmpl::normalDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
   1133 template<typename T> template<typename U>        void ImportClsTmplMemTmpl<T>::normalInlineDecl() {}
   1134 template<typename T> template<typename U>        void ImportClsTmplMemTmpl<T>::staticDef() {} // expected-warning{{'ImportClsTmplMemTmpl::staticDef' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
   1135 template<typename T> template<typename U>        void ImportClsTmplMemTmpl<T>::staticInlineDecl() {}
   1136 
   1137 #ifdef GNU
   1138 // expected-warning@+3{{'ImportClsTmplMemTmpl::normalInlineDef' redeclared inline; 'dllimport' attribute ignored}}
   1139 // expected-warning@+3{{'ImportClsTmplMemTmpl::staticInlineDef' redeclared inline; 'dllimport' attribute ignored}}
   1140 #endif
   1141 template<typename T> template<typename U> inline void ImportClsTmplMemTmpl<T>::normalInlineDef() {}
   1142 template<typename T> template<typename U> inline void ImportClsTmplMemTmpl<T>::staticInlineDef() {}
   1143 
   1144 #if __has_feature(cxx_variable_templates)
   1145 template<typename T> template<typename U>        int  ImportClsTmplMemTmpl<T>::StaticFieldDef; // expected-warning{{definition of dllimport static field}}
   1146 template<typename T> template<typename U> const  int  ImportClsTmplMemTmpl<T>::StaticConstFieldDef = 1; // expected-warning{{definition of dllimport static field}}
   1147 template<typename T> template<typename U> constexpr int ImportClsTmplMemTmpl<T>::ConstexprFieldDef; // expected-warning{{definition of dllimport static field}}
   1148 #endif // __has_feature(cxx_variable_templates)
   1149 
   1150 
   1151 // Redeclarations cannot add dllimport.
   1152 template<typename T>
   1153 struct CTMTR /*ClassTmplMemberTmplRedecl*/ {
   1154   template<typename U>               void normalDef();         // expected-note{{previous declaration is here}}
   1155   template<typename U>        inline void normalInlineDecl();  // expected-note{{previous declaration is here}}
   1156   template<typename U> static        void staticDef();         // expected-note{{previous declaration is here}}
   1157   template<typename U> static inline void staticInlineDecl();  // expected-note{{previous declaration is here}}
   1158 
   1159 #ifdef MS
   1160   // expected-note@+3{{previous declaration is here}}
   1161   // expected-note@+3{{previous declaration is here}}
   1162 #endif
   1163   template<typename U>               void normalInlineDef();
   1164   template<typename U> static        void staticInlineDef();
   1165 
   1166 #if __has_feature(cxx_variable_templates)
   1167   template<typename U> static        int  StaticField;         // expected-note{{previous declaration is here}}
   1168   template<typename U> static const  int  StaticConstField;    // expected-note{{previous declaration is here}}
   1169   template<typename U> constexpr static int ConstexprField = 1; // expected-note{{previous declaration is here}}
   1170 #endif // __has_feature(cxx_variable_templates)
   1171 };
   1172 
   1173 template<typename T> template<typename U> __declspec(dllimport)        void CTMTR<T>::normalDef() {}         // expected-error{{redeclaration of 'CTMTR::normalDef' cannot add 'dllimport' attribute}}
   1174                                                                                                              // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
   1175 template<typename T> template<typename U> __declspec(dllimport)        void CTMTR<T>::normalInlineDecl() {}  // expected-error{{redeclaration of 'CTMTR::normalInlineDecl' cannot add 'dllimport' attribute}}
   1176 template<typename T> template<typename U> __declspec(dllimport)        void CTMTR<T>::staticDef() {}         // expected-error{{redeclaration of 'CTMTR::staticDef' cannot add 'dllimport' attribute}}
   1177                                                                                                              // expected-error@-1{{dllimport cannot be applied to non-inline function definition}}
   1178 template<typename T> template<typename U> __declspec(dllimport)        void CTMTR<T>::staticInlineDecl() {}  // expected-error{{redeclaration of 'CTMTR::staticInlineDecl' cannot add 'dllimport' attribute}}
   1179 
   1180 #ifdef MS
   1181 template<typename T> template<typename U> __declspec(dllimport) inline void CTMTR<T>::normalInlineDef() {}   // expected-error{{redeclaration of 'CTMTR::normalInlineDef' cannot add 'dllimport' attribute}}
   1182 template<typename T> template<typename U> __declspec(dllimport) inline void CTMTR<T>::staticInlineDef() {}   // expected-error{{redeclaration of 'CTMTR::staticInlineDef' cannot add 'dllimport' attribute}}
   1183 #else
   1184 template<typename T> template<typename U> __declspec(dllimport) inline void CTMTR<T>::normalInlineDef() {}   // expected-warning{{'dllimport' attribute ignored on inline function}}
   1185 template<typename T> template<typename U> __declspec(dllimport) inline void CTMTR<T>::staticInlineDef() {}   // expected-warning{{'dllimport' attribute ignored on inline function}}
   1186 #endif
   1187 
   1188 #if __has_feature(cxx_variable_templates)
   1189 template<typename T> template<typename U> __declspec(dllimport)        int  CTMTR<T>::StaticField = 1;       // expected-error{{redeclaration of 'CTMTR::StaticField' cannot add 'dllimport' attribute}}
   1190                                                                                                              // expected-warning@-1{{definition of dllimport static field}}
   1191                                                                                                              // expected-note@-2{{attribute is here}}
   1192 template<typename T> template<typename U> __declspec(dllimport) const  int  CTMTR<T>::StaticConstField = 1;  // expected-error{{redeclaration of 'CTMTR::StaticConstField' cannot add 'dllimport' attribute}}
   1193                                                                                                              // expected-warning@-1{{definition of dllimport static field}}
   1194                                                                                                              // expected-note@-2{{attribute is here}}
   1195 template<typename T> template<typename U> __declspec(dllimport) constexpr int CTMTR<T>::ConstexprField;      // expected-error{{redeclaration of 'CTMTR::ConstexprField' cannot add 'dllimport' attribute}}
   1196                                                                                                              // expected-warning@-1{{definition of dllimport static field}}
   1197                                                                                                              // expected-note@-2{{attribute is here}}
   1198 #endif // __has_feature(cxx_variable_templates)
   1199 
   1200 
   1201 
   1202 //===----------------------------------------------------------------------===//
   1203 // Classes
   1204 //===----------------------------------------------------------------------===//
   1205 
   1206 namespace {
   1207   struct __declspec(dllimport) AnonymousClass {}; // expected-error{{(anonymous namespace)::AnonymousClass' must have external linkage when declared 'dllimport'}}
   1208 }
   1209 
   1210 class __declspec(dllimport) ClassDecl;
   1211 
   1212 class __declspec(dllimport) ClassDef { };
   1213 
   1214 template <typename T> class ClassTemplate {};
   1215 
   1216 #ifdef MS
   1217 // expected-note@+5{{previous attribute is here}}
   1218 // expected-note@+4{{previous attribute is here}}
   1219 // expected-error@+4{{attribute 'dllexport' cannot be applied to member of 'dllimport' class}}
   1220 // expected-error@+4{{attribute 'dllimport' cannot be applied to member of 'dllimport' class}}
   1221 #endif
   1222 class __declspec(dllimport) ImportClassWithDllMember {
   1223   void __declspec(dllexport) foo();
   1224   void __declspec(dllimport) bar();
   1225 };
   1226 
   1227 #ifdef MS
   1228 // expected-note@+5{{previous attribute is here}}
   1229 // expected-note@+4{{previous attribute is here}}
   1230 // expected-error@+4{{attribute 'dllimport' cannot be applied to member of 'dllexport' class}}
   1231 // expected-error@+4{{attribute 'dllexport' cannot be applied to member of 'dllexport' class}}
   1232 #endif
   1233 template <typename T> class __declspec(dllexport) ExportClassWithDllMember {
   1234   void __declspec(dllimport) foo();
   1235   void __declspec(dllexport) bar();
   1236 };
   1237 
   1238 namespace ImportedExplicitSpecialization {
   1239 template <typename T> struct S { static int x; };
   1240 template <typename T> int S<T>::x = sizeof(T);
   1241 template <> struct __declspec(dllimport) S<int> { static int x; }; // expected-note{{attribute is here}}
   1242 int S<int>::x = -1; // expected-error{{definition of dllimport static field not allowed}}
   1243 }
   1244 
   1245 namespace PR19988 {
   1246 // Don't error about applying delete to dllimport member function when instantiating.
   1247 template <typename> struct __declspec(dllimport) S {
   1248   void foo() = delete;
   1249 };
   1250 S<int> s;
   1251 }
   1252 
   1253 #ifdef MS
   1254 // expected-warning@+3{{'dllimport' attribute ignored}}
   1255 #endif
   1256 template <typename T> struct PartiallySpecializedClassTemplate {};
   1257 template <typename T> struct __declspec(dllimport) PartiallySpecializedClassTemplate<T*> { void f() {} };
   1258 
   1259 template <typename T> struct ExpliciallySpecializedClassTemplate {};
   1260 template <> struct __declspec(dllimport) ExpliciallySpecializedClassTemplate<int> { void f() {} };
   1261 
   1262 
   1263 //===----------------------------------------------------------------------===//
   1264 // Classes with template base classes
   1265 //===----------------------------------------------------------------------===//
   1266 
   1267 template <typename T> class __declspec(dllexport) ExportedClassTemplate {};
   1268 
   1269 template <typename T> class __declspec(dllimport) ImportedClassTemplate {};
   1270 
   1271 // ClassTemplate<int> gets imported.
   1272 class __declspec(dllimport) DerivedFromTemplate : public ClassTemplate<int> {};
   1273 
   1274 // ClassTemplate<int> is already imported.
   1275 class __declspec(dllimport) DerivedFromTemplate2 : public ClassTemplate<int> {};
   1276 
   1277 // ImportedClassTemplate is expliitly imported.
   1278 class __declspec(dllimport) DerivedFromImportedTemplate : public ImportedClassTemplate<int> {};
   1279 
   1280 // ExportedClassTemplate is explicitly exported.
   1281 class __declspec(dllimport) DerivedFromExportedTemplate : public ExportedClassTemplate<int> {};
   1282 
   1283 class DerivedFromTemplateD : public ClassTemplate<double> {};
   1284 // Base class previously implicitly instantiated without attribute; it will get propagated.
   1285 class __declspec(dllimport) DerivedFromTemplateD2 : public ClassTemplate<double> {};
   1286 
   1287 // Base class has explicit instantiation declaration; the attribute will get propagated.
   1288 extern template class ClassTemplate<float>;
   1289 class __declspec(dllimport) DerivedFromTemplateF : public ClassTemplate<float> {};
   1290 
   1291 class __declspec(dllimport) DerivedFromTemplateB : public ClassTemplate<bool> {};
   1292 // The second derived class doesn't change anything, the attribute that was propagated first wins.
   1293 class __declspec(dllexport) DerivedFromTemplateB2 : public ClassTemplate<bool> {};
   1294 
   1295 template <typename T> struct ExplicitlySpecializedTemplate { void func() {} };
   1296 #ifdef MS
   1297 // expected-note@+2{{class template 'ExplicitlySpecializedTemplate<int>' was explicitly specialized here}}
   1298 #endif
   1299 template <> struct ExplicitlySpecializedTemplate<int> { void func() {} };
   1300 template <typename T> struct ExplicitlyExportSpecializedTemplate { void func() {} };
   1301 template <> struct __declspec(dllexport) ExplicitlyExportSpecializedTemplate<int> { void func() {} };
   1302 template <typename T> struct ExplicitlyImportSpecializedTemplate { void func() {} };
   1303 template <> struct __declspec(dllimport) ExplicitlyImportSpecializedTemplate<int> { void func() {} };
   1304 
   1305 template <typename T> struct ExplicitlyInstantiatedTemplate { void func() {} };
   1306 #ifdef MS
   1307 // expected-note@+2{{class template 'ExplicitlyInstantiatedTemplate<int>' was instantiated here}}
   1308 #endif
   1309 template struct ExplicitlyInstantiatedTemplate<int>;
   1310 template <typename T> struct ExplicitlyExportInstantiatedTemplate { void func() {} };
   1311 template struct __declspec(dllexport) ExplicitlyExportInstantiatedTemplate<int>;
   1312 template <typename T> struct ExplicitlyImportInstantiatedTemplate { void func() {} };
   1313 template struct __declspec(dllimport) ExplicitlyImportInstantiatedTemplate<int>;
   1314 
   1315 #ifdef MS
   1316 // expected-warning@+3{{propagating dll attribute to explicitly specialized base class template without dll attribute is not supported}}
   1317 // expected-note@+2{{attribute is here}}
   1318 #endif
   1319 struct __declspec(dllimport) DerivedFromExplicitlySpecializedTemplate : public ExplicitlySpecializedTemplate<int> {};
   1320 
   1321 // Base class already specialized with export attribute.
   1322 struct __declspec(dllimport) DerivedFromExplicitlyExportSpecializedTemplate : public ExplicitlyExportSpecializedTemplate<int> {};
   1323 
   1324 // Base class already specialized with import attribute.
   1325 struct __declspec(dllimport) DerivedFromExplicitlyImportSpecializedTemplate : public ExplicitlyImportSpecializedTemplate<int> {};
   1326 
   1327 #ifdef MS
   1328 // expected-warning@+3{{propagating dll attribute to already instantiated base class template without dll attribute is not supported}}
   1329 // expected-note@+2{{attribute is here}}
   1330 #endif
   1331 struct __declspec(dllimport) DerivedFromExplicitlyInstantiatedTemplate : public ExplicitlyInstantiatedTemplate<int> {};
   1332 
   1333 // Base class already instantiated with export attribute.
   1334 struct __declspec(dllimport) DerivedFromExplicitlyExportInstantiatedTemplate : public ExplicitlyExportInstantiatedTemplate<int> {};
   1335 
   1336 // Base class already instantiated with import attribute.
   1337 struct __declspec(dllimport) DerivedFromExplicitlyImportInstantiatedTemplate : public ExplicitlyImportInstantiatedTemplate<int> {};
   1338 
   1339 template <typename T> struct ExplicitInstantiationDeclTemplateBase { void func() {} };
   1340 extern template struct ExplicitInstantiationDeclTemplateBase<int>;
   1341 struct __declspec(dllimport) DerivedFromExplicitInstantiationDeclTemplateBase : public ExplicitInstantiationDeclTemplateBase<int> {};
   1342 
   1343 //===----------------------------------------------------------------------===//
   1344 // Lambdas
   1345 //===----------------------------------------------------------------------===//
   1346 // The MS ABI doesn't provide a stable mangling for lambdas, so they can't be imported or exported.
   1347 #ifdef MS
   1348 // expected-error@+4{{lambda cannot be declared 'dllimport'}}
   1349 #else
   1350 // expected-warning@+2{{'dllimport' attribute ignored on inline function}}
   1351 #endif
   1352 auto Lambda = []() __declspec(dllimport) -> bool { return true; };
   1353