Home | History | Annotate | Download | only in SemaCXX
      1 // RUN: %clang_cc1 -triple i686-win32     -fsyntax-only -verify -std=c++11 -DMS %s
      2 // RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -verify -std=c++1y -DMS %s
      3 // RUN: %clang_cc1 -triple i686-mingw32   -fsyntax-only -verify -std=c++1y %s
      4 // RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -verify -std=c++11 %s
      5 
      6 // Helper structs to make templates more expressive.
      7 struct ImplicitInst_Exported {};
      8 struct ExplicitDecl_Exported {};
      9 struct ExplicitInst_Exported {};
     10 struct ExplicitSpec_Exported {};
     11 struct ExplicitSpec_Def_Exported {};
     12 struct ExplicitSpec_InlineDef_Exported {};
     13 struct ExplicitSpec_NotExported {};
     14 namespace { struct Internal {}; }
     15 struct External { int v; };
     16 
     17 
     18 // Invalid usage.
     19 __declspec(dllexport) typedef int typedef1; // expected-warning{{'dllexport' attribute only applies to variables, functions and classes}}
     20 typedef __declspec(dllexport) int typedef2; // expected-warning{{'dllexport' attribute only applies to variables, functions and classes}}
     21 typedef int __declspec(dllexport) typedef3; // expected-warning{{'dllexport' attribute only applies to variables, functions and classes}}
     22 typedef __declspec(dllexport) void (*FunTy)(); // expected-warning{{'dllexport' attribute only applies to variables, functions and classes}}
     23 enum __declspec(dllexport) Enum {}; // expected-warning{{'dllexport' attribute only applies to variables, functions and classes}}
     24 #if __has_feature(cxx_strong_enums)
     25   enum class __declspec(dllexport) EnumClass {}; // expected-warning{{'dllexport' attribute only applies to variables, functions and classes}}
     26 #endif
     27 
     28 
     29 
     30 //===----------------------------------------------------------------------===//
     31 // Globals
     32 //===----------------------------------------------------------------------===//
     33 
     34 // Export declaration.
     35 __declspec(dllexport) extern int ExternGlobalDecl;
     36 
     37 // dllexport implies a definition.
     38 __declspec(dllexport) int GlobalDef;
     39 
     40 // Export definition.
     41 __declspec(dllexport) int GlobalInit1 = 1;
     42 int __declspec(dllexport) GlobalInit2 = 1;
     43 
     44 // Declare, then export definition.
     45 __declspec(dllexport) extern int GlobalDeclInit;
     46 int GlobalDeclInit = 1;
     47 
     48 // Redeclarations
     49 __declspec(dllexport) extern int GlobalRedecl1;
     50 __declspec(dllexport)        int GlobalRedecl1;
     51 
     52 __declspec(dllexport) extern int GlobalRedecl2;
     53                              int GlobalRedecl2;
     54 
     55                       extern int GlobalRedecl3; // expected-note{{previous declaration is here}}
     56 __declspec(dllexport) extern int GlobalRedecl3; // expected-error{{redeclaration of 'GlobalRedecl3' cannot add 'dllexport' attribute}}
     57 
     58 // External linkage is required.
     59 __declspec(dllexport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllexport'}}
     60 __declspec(dllexport) Internal InternalTypeGlobal; // expected-error{{'InternalTypeGlobal' must have external linkage when declared 'dllexport'}}
     61 namespace    { __declspec(dllexport) int InternalGlobal; } // expected-error{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllexport'}}
     62 namespace ns { __declspec(dllexport) int ExternalGlobal; }
     63 
     64 __declspec(dllexport) auto InternalAutoTypeGlobal = Internal(); // expected-error{{'InternalAutoTypeGlobal' must have external linkage when declared 'dllexport'}}
     65 __declspec(dllexport) auto ExternalAutoTypeGlobal = External();
     66 
     67 // Export in local scope.
     68 void functionScope() {
     69   __declspec(dllexport)        int LocalVarDecl; // expected-error{{'LocalVarDecl' must have external linkage when declared 'dllexport'}}
     70   __declspec(dllexport)        int LocalVarDef = 1; // expected-error{{'LocalVarDef' must have external linkage when declared 'dllexport'}}
     71   __declspec(dllexport) extern int ExternLocalVarDecl;
     72   __declspec(dllexport) static int StaticLocalVar; // expected-error{{'StaticLocalVar' must have external linkage when declared 'dllexport'}}
     73 }
     74 
     75 
     76 
     77 //===----------------------------------------------------------------------===//
     78 // Variable templates
     79 //===----------------------------------------------------------------------===//
     80 #if __has_feature(cxx_variable_templates)
     81 
     82 // Export declaration.
     83 template<typename T> __declspec(dllexport) extern int ExternVarTmplDecl;
     84 
     85 // dllexport implies a definition.
     86 template<typename T> __declspec(dllexport) int VarTmplDef;
     87 
     88 // Export definition.
     89 template<typename T> __declspec(dllexport) int VarTmplInit1 = 1;
     90 template<typename T> int __declspec(dllexport) VarTmplInit2 = 1;
     91 
     92 // Declare, then export definition.
     93 template<typename T> __declspec(dllexport) extern int VarTmplDeclInit;
     94 template<typename T>                              int VarTmplDeclInit = 1;
     95 
     96 // Redeclarations
     97 template<typename T> __declspec(dllexport) extern int VarTmplRedecl1;
     98 template<typename T> __declspec(dllexport)        int VarTmplRedecl1 = 1;
     99 
    100 template<typename T> __declspec(dllexport) extern int VarTmplRedecl2;
    101 template<typename T>                              int VarTmplRedecl2 = 1;
    102 
    103 template<typename T>                       extern int VarTmplRedecl3; // expected-note{{previous declaration is here}}
    104 template<typename T> __declspec(dllexport) extern int VarTmplRedecl3; // expected-error{{redeclaration of 'VarTmplRedecl3' cannot add 'dllexport' attribute}}
    105 
    106 // External linkage is required.
    107 template<typename T> __declspec(dllexport) static int StaticVarTmpl; // expected-error{{'StaticVarTmpl' must have external linkage when declared 'dllexport'}}
    108 template<typename T> __declspec(dllexport) Internal InternalTypeVarTmpl; // expected-error{{'InternalTypeVarTmpl' must have external linkage when declared 'dllexport'}}
    109 namespace    { template<typename T> __declspec(dllexport) int InternalVarTmpl; } // expected-error{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllexport'}}
    110 namespace ns { template<typename T> __declspec(dllexport) int ExternalVarTmpl = 1; }
    111 
    112 template<typename T> __declspec(dllexport) auto InternalAutoTypeVarTmpl = Internal(); // expected-error{{'InternalAutoTypeVarTmpl' must have external linkage when declared 'dllexport'}}
    113 template<typename T> __declspec(dllexport) auto ExternalAutoTypeVarTmpl = External();
    114 template External ExternalAutoTypeVarTmpl<ExplicitInst_Exported>;
    115 
    116 
    117 template<typename T> int VarTmpl = 1;
    118 template<typename T> __declspec(dllexport) int ExportedVarTmpl = 1;
    119 
    120 // Export implicit instantiation of an exported variable template.
    121 int useVarTmpl() { return ExportedVarTmpl<ImplicitInst_Exported>; }
    122 
    123 // Export explicit instantiation declaration of an exported variable template.
    124 extern template int ExportedVarTmpl<ExplicitDecl_Exported>;
    125        template int ExportedVarTmpl<ExplicitDecl_Exported>;
    126 
    127 // Export explicit instantiation definition of an exported variable template.
    128 template __declspec(dllexport) int ExportedVarTmpl<ExplicitInst_Exported>;
    129 
    130 // Export specialization of an exported variable template.
    131 template<> __declspec(dllexport) int ExportedVarTmpl<ExplicitSpec_Exported>;
    132 template<> __declspec(dllexport) int ExportedVarTmpl<ExplicitSpec_Def_Exported> = 1;
    133 
    134 // Not exporting specialization of an exported variable template without
    135 // explicit dllexport.
    136 template<> int ExportedVarTmpl<ExplicitSpec_NotExported>;
    137 
    138 
    139 // Export explicit instantiation declaration of a non-exported variable template.
    140 extern template __declspec(dllexport) int VarTmpl<ExplicitDecl_Exported>;
    141        template __declspec(dllexport) int VarTmpl<ExplicitDecl_Exported>;
    142 
    143 // Export explicit instantiation definition of a non-exported variable template.
    144 template __declspec(dllexport) int VarTmpl<ExplicitInst_Exported>;
    145 
    146 // Export specialization of a non-exported variable template.
    147 template<> __declspec(dllexport) int VarTmpl<ExplicitSpec_Exported>;
    148 template<> __declspec(dllexport) int VarTmpl<ExplicitSpec_Def_Exported> = 1;
    149 
    150 #endif // __has_feature(cxx_variable_templates)
    151 
    152 
    153 
    154 //===----------------------------------------------------------------------===//
    155 // Functions
    156 //===----------------------------------------------------------------------===//
    157 
    158 // Export function declaration. Check different placements.
    159 __attribute__((dllexport)) void decl1A(); // Sanity check with __attribute__
    160 __declspec(dllexport)      void decl1B();
    161 
    162 void __attribute__((dllexport)) decl2A();
    163 void __declspec(dllexport)      decl2B();
    164 
    165 // Export function definition.
    166 __declspec(dllexport) void def() {}
    167 
    168 // extern "C"
    169 extern "C" __declspec(dllexport) void externC() {}
    170 
    171 // Export inline function.
    172 __declspec(dllexport) inline void inlineFunc1() {}
    173 inline void __attribute__((dllexport)) inlineFunc2() {}
    174 
    175 __declspec(dllexport) inline void inlineDecl();
    176                              void inlineDecl() {}
    177 
    178 __declspec(dllexport) void inlineDef();
    179                inline void inlineDef() {}
    180 
    181 // Redeclarations
    182 __declspec(dllexport) void redecl1();
    183 __declspec(dllexport) void redecl1() {}
    184 
    185 __declspec(dllexport) void redecl2();
    186                       void redecl2() {}
    187 
    188                       void redecl3(); // expected-note{{previous declaration is here}}
    189 __declspec(dllexport) void redecl3(); // expected-error{{redeclaration of 'redecl3' cannot add 'dllexport' attribute}}
    190 
    191                       void redecl4(); // expected-note{{previous declaration is here}}
    192 __declspec(dllexport) inline void redecl4() {} // expected-error{{redeclaration of 'redecl4' cannot add 'dllexport' attribute}}
    193 
    194 // Friend functions
    195 struct FuncFriend {
    196   friend __declspec(dllexport) void friend1();
    197   friend __declspec(dllexport) void friend2();
    198   friend                       void friend3(); // expected-note{{previous declaration is here}}
    199   friend                       void friend4(); // expected-note{{previous declaration is here}}
    200 };
    201 __declspec(dllexport) void friend1() {}
    202                       void friend2() {}
    203 __declspec(dllexport) void friend3() {} // expected-error{{redeclaration of 'friend3' cannot add 'dllexport' attribute}}
    204 __declspec(dllexport) inline void friend4() {} // expected-error{{redeclaration of 'friend4' cannot add 'dllexport' attribute}}
    205 
    206 // Implicit declarations can be redeclared with dllexport.
    207 __declspec(dllexport) void* operator new(__SIZE_TYPE__ n);
    208 
    209 // External linkage is required.
    210 __declspec(dllexport) static int staticFunc(); // expected-error{{'staticFunc' must have external linkage when declared 'dllexport'}}
    211 __declspec(dllexport) Internal internalRetFunc(); // expected-error{{'internalRetFunc' must have external linkage when declared 'dllexport'}}
    212 namespace    { __declspec(dllexport) void internalFunc() {} } // expected-error{{'(anonymous namespace)::internalFunc' must have external linkage when declared 'dllexport'}}
    213 namespace ns { __declspec(dllexport) void externalFunc() {} }
    214 
    215 // Export deleted function.
    216 __declspec(dllexport) void deletedFunc() = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    217 __declspec(dllexport) inline void deletedInlineFunc() = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    218 
    219 
    220 
    221 //===----------------------------------------------------------------------===//
    222 // Function templates
    223 //===----------------------------------------------------------------------===//
    224 
    225 // Export function template declaration. Check different placements.
    226 template<typename T> __declspec(dllexport) void funcTmplDecl1();
    227 template<typename T> void __declspec(dllexport) funcTmplDecl2();
    228 
    229 // Export function template definition.
    230 template<typename T> __declspec(dllexport) void funcTmplDef() {}
    231 
    232 // Export inline function template.
    233 template<typename T> __declspec(dllexport) inline void inlineFuncTmpl1() {}
    234 template<typename T> inline void __attribute__((dllexport)) inlineFuncTmpl2() {}
    235 
    236 template<typename T> __declspec(dllexport) inline void inlineFuncTmplDecl();
    237 template<typename T>                              void inlineFuncTmplDecl() {}
    238 
    239 template<typename T> __declspec(dllexport) void inlineFuncTmplDef();
    240 template<typename T>                inline void inlineFuncTmplDef() {}
    241 
    242 // Redeclarations
    243 template<typename T> __declspec(dllexport) void funcTmplRedecl1();
    244 template<typename T> __declspec(dllexport) void funcTmplRedecl1() {}
    245 
    246 template<typename T> __declspec(dllexport) void funcTmplRedecl2();
    247 template<typename T>                       void funcTmplRedecl2() {}
    248 
    249 template<typename T>                       void funcTmplRedecl3(); // expected-note{{previous declaration is here}}
    250 template<typename T> __declspec(dllexport) void funcTmplRedecl3(); // expected-error{{redeclaration of 'funcTmplRedecl3' cannot add 'dllexport' attribute}}
    251 
    252 template<typename T>                       void funcTmplRedecl4(); // expected-note{{previous declaration is here}}
    253 template<typename T> __declspec(dllexport) inline void funcTmplRedecl4() {} // expected-error{{redeclaration of 'funcTmplRedecl4' cannot add 'dllexport' attribute}}
    254 
    255 // Function template friends
    256 struct FuncTmplFriend {
    257   template<typename T> friend __declspec(dllexport) void funcTmplFriend1();
    258   template<typename T> friend __declspec(dllexport) void funcTmplFriend2();
    259   template<typename T> friend                       void funcTmplFriend3(); // expected-note{{previous declaration is here}}
    260   template<typename T> friend                       void funcTmplFriend4(); // expected-note{{previous declaration is here}}
    261 };
    262 template<typename T> __declspec(dllexport) void funcTmplFriend1() {}
    263 template<typename T>                       void funcTmplFriend2() {}
    264 template<typename T> __declspec(dllexport) void funcTmplFriend3() {} // expected-error{{redeclaration of 'funcTmplFriend3' cannot add 'dllexport' attribute}}
    265 template<typename T> __declspec(dllexport) inline void funcTmplFriend4() {} // expected-error{{redeclaration of 'funcTmplFriend4' cannot add 'dllexport' attribute}}
    266 
    267 // External linkage is required.
    268 template<typename T> __declspec(dllexport) static int staticFuncTmpl(); // expected-error{{'staticFuncTmpl' must have external linkage when declared 'dllexport'}}
    269 template<typename T> __declspec(dllexport) Internal internalRetFuncTmpl(); // expected-error{{'internalRetFuncTmpl' must have external linkage when declared 'dllexport'}}
    270 namespace    { template<typename T> __declspec(dllexport) void internalFuncTmpl(); } // expected-error{{'(anonymous namespace)::internalFuncTmpl' must have external linkage when declared 'dllexport'}}
    271 namespace ns { template<typename T> __declspec(dllexport) void externalFuncTmpl(); }
    272 
    273 
    274 template<typename T> void funcTmpl() {}
    275 template<typename T> __declspec(dllexport) void exportedFuncTmplDecl();
    276 template<typename T> __declspec(dllexport) void exportedFuncTmpl() {}
    277 
    278 // Export implicit instantiation of an exported function template.
    279 void useFunTmplDecl() { exportedFuncTmplDecl<ImplicitInst_Exported>(); }
    280 void useFunTmplDef() { exportedFuncTmpl<ImplicitInst_Exported>(); }
    281 
    282 // Export explicit instantiation declaration of an exported function template.
    283 extern template void exportedFuncTmpl<ExplicitDecl_Exported>();
    284        template void exportedFuncTmpl<ExplicitDecl_Exported>();
    285 
    286 // Export explicit instantiation definition of an exported function template.
    287 template void exportedFuncTmpl<ExplicitInst_Exported>();
    288 
    289 // Export specialization of an exported function template.
    290 template<> __declspec(dllexport) void exportedFuncTmpl<ExplicitSpec_Exported>();
    291 template<> __declspec(dllexport) void exportedFuncTmpl<ExplicitSpec_Def_Exported>() {}
    292 template<> __declspec(dllexport) inline void exportedFuncTmpl<ExplicitSpec_InlineDef_Exported>() {}
    293 
    294 // Not exporting specialization of an exported function template without
    295 // explicit dllexport.
    296 template<> void exportedFuncTmpl<ExplicitSpec_NotExported>() {}
    297 
    298 
    299 // Export explicit instantiation declaration of a non-exported function template.
    300 extern template __declspec(dllexport) void funcTmpl<ExplicitDecl_Exported>();
    301        template __declspec(dllexport) void funcTmpl<ExplicitDecl_Exported>();
    302 
    303 // Export explicit instantiation definition of a non-exported function template.
    304 template __declspec(dllexport) void funcTmpl<ExplicitInst_Exported>();
    305 
    306 // Export specialization of a non-exported function template.
    307 template<> __declspec(dllexport) void funcTmpl<ExplicitSpec_Exported>();
    308 template<> __declspec(dllexport) void funcTmpl<ExplicitSpec_Def_Exported>() {}
    309 template<> __declspec(dllexport) inline void funcTmpl<ExplicitSpec_InlineDef_Exported>() {}
    310 
    311 
    312 
    313 //===----------------------------------------------------------------------===//
    314 // Classes
    315 //===----------------------------------------------------------------------===//
    316 
    317 class __declspec(dllexport) ClassDecl;
    318 
    319 class __declspec(dllexport) ClassDef {};
    320 
    321 #ifdef MS
    322 // expected-warning@+3{{'dllexport' attribute ignored}}
    323 #endif
    324 template <typename T> struct PartiallySpecializedClassTemplate {};
    325 template <typename T> struct __declspec(dllexport) PartiallySpecializedClassTemplate<T*> { void f() {} };
    326 
    327 template <typename T> struct ExpliciallySpecializedClassTemplate {};
    328 template <> struct __declspec(dllexport) ExpliciallySpecializedClassTemplate<int> { void f() {} };
    329 
    330 
    331 //===----------------------------------------------------------------------===//
    332 // Classes with template base classes
    333 //===----------------------------------------------------------------------===//
    334 
    335 template <typename T> class ClassTemplate {};
    336 template <typename T> class __declspec(dllexport) ExportedClassTemplate {};
    337 template <typename T> class __declspec(dllimport) ImportedClassTemplate {};
    338 
    339 template <typename T> struct ExplicitlySpecializedTemplate { void func() {} };
    340 #ifdef MS
    341 // expected-note@+2{{class template 'ExplicitlySpecializedTemplate<int>' was explicitly specialized here}}
    342 #endif
    343 template <> struct ExplicitlySpecializedTemplate<int> { void func() {} };
    344 template <typename T> struct ExplicitlyExportSpecializedTemplate { void func() {} };
    345 template <> struct __declspec(dllexport) ExplicitlyExportSpecializedTemplate<int> { void func() {} };
    346 template <typename T> struct ExplicitlyImportSpecializedTemplate { void func() {} };
    347 template <> struct __declspec(dllimport) ExplicitlyImportSpecializedTemplate<int> { void func() {} };
    348 
    349 template <typename T> struct ExplicitlyInstantiatedTemplate { void func() {} };
    350 #ifdef MS
    351 // expected-note@+2{{class template 'ExplicitlyInstantiatedTemplate<int>' was instantiated here}}
    352 #endif
    353 template struct ExplicitlyInstantiatedTemplate<int>;
    354 template <typename T> struct ExplicitlyExportInstantiatedTemplate { void func() {} };
    355 template struct __declspec(dllexport) ExplicitlyExportInstantiatedTemplate<int>;
    356 template <typename T> struct ExplicitlyImportInstantiatedTemplate { void func() {} };
    357 template struct __declspec(dllimport) ExplicitlyImportInstantiatedTemplate<int>;
    358 
    359 // ClassTemplate<int> gets exported.
    360 class __declspec(dllexport) DerivedFromTemplate : public ClassTemplate<int> {};
    361 
    362 // ClassTemplate<int> is already exported.
    363 class __declspec(dllexport) DerivedFromTemplate2 : public ClassTemplate<int> {};
    364 
    365 // ExportedTemplate is explicitly exported.
    366 class __declspec(dllexport) DerivedFromExportedTemplate : public ExportedClassTemplate<int> {};
    367 
    368 // ImportedTemplate is explicitly imported.
    369 class __declspec(dllexport) DerivedFromImportedTemplate : public ImportedClassTemplate<int> {};
    370 
    371 #ifdef MS
    372 // expected-note@+4{{class template 'ClassTemplate<double>' was instantiated here}}
    373 // expected-warning@+4{{propagating dll attribute to already instantiated base class template without dll attribute is unsupported}}
    374 // expected-note@+3{{attribute is here}}
    375 #endif
    376 class DerivedFromTemplateD : public ClassTemplate<double> {};
    377 class __declspec(dllexport) DerivedFromTemplateD2 : public ClassTemplate<double> {};
    378 
    379 #ifdef MS
    380 // expected-note@+4{{class template 'ClassTemplate<bool>' was instantiated here}}
    381 // expected-warning@+4{{propagating dll attribute to already instantiated base class template with different dll attribute is unsupported}}
    382 // expected-note@+3{{attribute is here}}
    383 #endif
    384 class __declspec(dllimport) DerivedFromTemplateB : public ClassTemplate<bool> {};
    385 class __declspec(dllexport) DerivedFromTemplateB2 : public ClassTemplate<bool> {};
    386 
    387 #ifdef MS
    388 // expected-warning@+3{{propagating dll attribute to explicitly specialized base class template without dll attribute is unsupported}}
    389 // expected-note@+2{{attribute is here}}
    390 #endif
    391 struct __declspec(dllexport) DerivedFromExplicitlySpecializedTemplate : public ExplicitlySpecializedTemplate<int> {};
    392 
    393 // Base class alredy specialized with export attribute.
    394 struct __declspec(dllexport) DerivedFromExplicitlyExportSpecializedTemplate : public ExplicitlyExportSpecializedTemplate<int> {};
    395 
    396 // Base class already specialized with import attribute.
    397 struct __declspec(dllexport) DerivedFromExplicitlyImportSpecializedTemplate : public ExplicitlyImportSpecializedTemplate<int> {};
    398 
    399 #ifdef MS
    400 // expected-warning@+3{{propagating dll attribute to already instantiated base class template without dll attribute is unsupported}}
    401 // expected-note@+2{{attribute is here}}
    402 #endif
    403 struct __declspec(dllexport) DerivedFromExplicitlyInstantiatedTemplate : public ExplicitlyInstantiatedTemplate<int> {};
    404 
    405 // Base class already instantiated with export attribute.
    406 struct __declspec(dllexport) DerivedFromExplicitlyExportInstantiatedTemplate : public ExplicitlyExportInstantiatedTemplate<int> {};
    407 
    408 // Base class already instantiated with import attribute.
    409 struct __declspec(dllexport) DerivedFromExplicitlyImportInstantiatedTemplate : public ExplicitlyImportInstantiatedTemplate<int> {};
    410 
    411 
    412 //===----------------------------------------------------------------------===//
    413 // Precedence
    414 //===----------------------------------------------------------------------===//
    415 
    416 // dllexport takes precedence over dllimport if both are specified.
    417 __attribute__((dllimport, dllexport))       extern int PrecedenceExternGlobal1A; // expected-warning{{'dllimport' attribute ignored}}
    418 __declspec(dllimport) __declspec(dllexport) extern int PrecedenceExternGlobal1B; // expected-warning{{'dllimport' attribute ignored}}
    419 
    420 __attribute__((dllexport, dllimport))       extern int PrecedenceExternGlobal2A; // expected-warning{{'dllimport' attribute ignored}}
    421 __declspec(dllexport) __declspec(dllimport) extern int PrecedenceExternGlobal2B; // expected-warning{{'dllimport' attribute ignored}}
    422 
    423 __attribute__((dllimport, dllexport))       int PrecedenceGlobal1A; // expected-warning{{'dllimport' attribute ignored}}
    424 __declspec(dllimport) __declspec(dllexport) int PrecedenceGlobal1B; // expected-warning{{'dllimport' attribute ignored}}
    425 
    426 __attribute__((dllexport, dllimport))       int PrecedenceGlobal2A; // expected-warning{{'dllimport' attribute ignored}}
    427 __declspec(dllexport) __declspec(dllimport) int PrecedenceGlobal2B; // expected-warning{{'dllimport' attribute ignored}}
    428 
    429 __declspec(dllexport) extern int PrecedenceExternGlobalRedecl1;
    430 __declspec(dllimport) extern int PrecedenceExternGlobalRedecl1; // expected-warning{{'dllimport' attribute ignored}}
    431 
    432 __declspec(dllimport) extern int PrecedenceExternGlobalRedecl2; // expected-warning{{'dllimport' attribute ignored}}
    433 __declspec(dllexport) extern int PrecedenceExternGlobalRedecl2;
    434 
    435 __declspec(dllexport) extern int PrecedenceGlobalRedecl1;
    436 __declspec(dllimport)        int PrecedenceGlobalRedecl1; // expected-warning{{'dllimport' attribute ignored}}
    437 
    438 __declspec(dllimport) extern int PrecedenceGlobalRedecl2; // expected-warning{{'dllimport' attribute ignored}}
    439 __declspec(dllexport)        int PrecedenceGlobalRedecl2;
    440 
    441 void __attribute__((dllimport, dllexport))       precedence1A() {} // expected-warning{{'dllimport' attribute ignored}}
    442 void __declspec(dllimport) __declspec(dllexport) precedence1B() {} // expected-warning{{'dllimport' attribute ignored}}
    443 
    444 void __attribute__((dllexport, dllimport))       precedence2A() {} // expected-warning{{'dllimport' attribute ignored}}
    445 void __declspec(dllexport) __declspec(dllimport) precedence2B() {} // expected-warning{{'dllimport' attribute ignored}}
    446 
    447 void __declspec(dllimport) precedenceRedecl1(); // expected-warning{{'dllimport' attribute ignored}}
    448 void __declspec(dllexport) precedenceRedecl1() {}
    449 
    450 void __declspec(dllexport) precedenceRedecl2();
    451 void __declspec(dllimport) precedenceRedecl2() {} // expected-warning{{'dllimport' attribute ignored}}
    452 
    453 
    454 
    455 //===----------------------------------------------------------------------===//
    456 // Class members
    457 //===----------------------------------------------------------------------===//
    458 
    459 // Export individual members of a class.
    460 struct ExportMembers {
    461   struct Nested {
    462     __declspec(dllexport) void normalDef();
    463   };
    464 
    465   __declspec(dllexport)                void normalDecl();
    466   __declspec(dllexport)                void normalDef();
    467   __declspec(dllexport)                void normalInclass() {}
    468   __declspec(dllexport)                void normalInlineDef();
    469   __declspec(dllexport)         inline void normalInlineDecl();
    470   __declspec(dllexport) virtual        void virtualDecl();
    471   __declspec(dllexport) virtual        void virtualDef();
    472   __declspec(dllexport) virtual        void virtualInclass() {}
    473   __declspec(dllexport) virtual        void virtualInlineDef();
    474   __declspec(dllexport) virtual inline void virtualInlineDecl();
    475   __declspec(dllexport) static         void staticDecl();
    476   __declspec(dllexport) static         void staticDef();
    477   __declspec(dllexport) static         void staticInclass() {}
    478   __declspec(dllexport) static         void staticInlineDef();
    479   __declspec(dllexport) static  inline void staticInlineDecl();
    480 
    481 protected:
    482   __declspec(dllexport)                void protectedDef();
    483 private:
    484   __declspec(dllexport)                void privateDef();
    485 public:
    486 
    487   __declspec(dllexport)                int  Field; // expected-warning{{'dllexport' attribute only applies to variables, functions and classes}}
    488   __declspec(dllexport) static         int  StaticField;
    489   __declspec(dllexport) static         int  StaticFieldDef;
    490   __declspec(dllexport) static  const  int  StaticConstField;
    491   __declspec(dllexport) static  const  int  StaticConstFieldDef;
    492   __declspec(dllexport) static  const  int  StaticConstFieldEqualInit = 1;
    493   __declspec(dllexport) static  const  int  StaticConstFieldBraceInit{1};
    494   __declspec(dllexport) constexpr static int ConstexprField = 1;
    495   __declspec(dllexport) constexpr static int ConstexprFieldDef = 1;
    496 };
    497 
    498        void ExportMembers::Nested::normalDef() {}
    499        void ExportMembers::normalDef() {}
    500 inline void ExportMembers::normalInlineDef() {}
    501        void ExportMembers::normalInlineDecl() {}
    502        void ExportMembers::virtualDef() {}
    503 inline void ExportMembers::virtualInlineDef() {}
    504        void ExportMembers::virtualInlineDecl() {}
    505        void ExportMembers::staticDef() {}
    506 inline void ExportMembers::staticInlineDef() {}
    507        void ExportMembers::staticInlineDecl() {}
    508        void ExportMembers::protectedDef() {}
    509        void ExportMembers::privateDef() {}
    510 
    511        int  ExportMembers::StaticFieldDef;
    512 const  int  ExportMembers::StaticConstFieldDef = 1;
    513 constexpr int ExportMembers::ConstexprFieldDef;
    514 
    515 
    516 // Export on member definitions.
    517 struct ExportMemberDefs {
    518   __declspec(dllexport)                void normalDef();
    519   __declspec(dllexport)                void normalInlineDef();
    520   __declspec(dllexport)         inline void normalInlineDecl();
    521   __declspec(dllexport) virtual        void virtualDef();
    522   __declspec(dllexport) virtual        void virtualInlineDef();
    523   __declspec(dllexport) virtual inline void virtualInlineDecl();
    524   __declspec(dllexport) static         void staticDef();
    525   __declspec(dllexport) static         void staticInlineDef();
    526   __declspec(dllexport) static  inline void staticInlineDecl();
    527 
    528   __declspec(dllexport) static         int  StaticField;
    529   __declspec(dllexport) static  const  int  StaticConstField;
    530   __declspec(dllexport) constexpr static int ConstexprField = 1;
    531 };
    532 
    533 __declspec(dllexport)        void ExportMemberDefs::normalDef() {}
    534 __declspec(dllexport) inline void ExportMemberDefs::normalInlineDef() {}
    535 __declspec(dllexport)        void ExportMemberDefs::normalInlineDecl() {}
    536 __declspec(dllexport)        void ExportMemberDefs::virtualDef() {}
    537 __declspec(dllexport) inline void ExportMemberDefs::virtualInlineDef() {}
    538 __declspec(dllexport)        void ExportMemberDefs::virtualInlineDecl() {}
    539 __declspec(dllexport)        void ExportMemberDefs::staticDef() {}
    540 __declspec(dllexport) inline void ExportMemberDefs::staticInlineDef() {}
    541 __declspec(dllexport)        void ExportMemberDefs::staticInlineDecl() {}
    542 
    543 __declspec(dllexport)        int  ExportMemberDefs::StaticField;
    544 __declspec(dllexport) const  int  ExportMemberDefs::StaticConstField = 1;
    545 __declspec(dllexport) constexpr int ExportMemberDefs::ConstexprField;
    546 
    547 
    548 // Export special member functions.
    549 struct ExportSpecials {
    550   __declspec(dllexport) ExportSpecials() {}
    551   __declspec(dllexport) ~ExportSpecials();
    552   __declspec(dllexport) inline ExportSpecials(const ExportSpecials&);
    553   __declspec(dllexport) ExportSpecials& operator=(const ExportSpecials&);
    554   __declspec(dllexport) ExportSpecials(ExportSpecials&&);
    555   __declspec(dllexport) ExportSpecials& operator=(ExportSpecials&&);
    556 };
    557 
    558 ExportSpecials::~ExportSpecials() {}
    559 ExportSpecials::ExportSpecials(const ExportSpecials&) {}
    560 inline ExportSpecials& ExportSpecials::operator=(const ExportSpecials&) { return *this; }
    561 ExportSpecials::ExportSpecials(ExportSpecials&&) {}
    562 ExportSpecials& ExportSpecials::operator=(ExportSpecials&&) { return *this; }
    563 
    564 
    565 // Export allocation functions.
    566 extern "C" void* malloc(__SIZE_TYPE__ size);
    567 extern "C" void free(void* p);
    568 struct ExportAlloc {
    569   __declspec(dllexport) void* operator new(__SIZE_TYPE__);
    570   __declspec(dllexport) void* operator new[](__SIZE_TYPE__);
    571   __declspec(dllexport) void operator delete(void*);
    572   __declspec(dllexport) void operator delete[](void*);
    573 };
    574 void* ExportAlloc::operator new(__SIZE_TYPE__ n) { return malloc(n); }
    575 void* ExportAlloc::operator new[](__SIZE_TYPE__ n) { return malloc(n); }
    576 void ExportAlloc::operator delete(void* p) { free(p); }
    577 void ExportAlloc::operator delete[](void* p) { free(p); }
    578 
    579 
    580 // Export deleted member functions.
    581 struct ExportDeleted {
    582   __declspec(dllexport) ExportDeleted() = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    583   __declspec(dllexport) ~ExportDeleted() = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    584   __declspec(dllexport) ExportDeleted(const ExportDeleted&) = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    585   __declspec(dllexport) ExportDeleted& operator=(const ExportDeleted&) = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    586   __declspec(dllexport) ExportDeleted(ExportDeleted&&) = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    587   __declspec(dllexport) ExportDeleted& operator=(ExportDeleted&&) = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    588   __declspec(dllexport) void deleted() = delete; // expected-error{{attribute 'dllexport' cannot be applied to a deleted function}}
    589 };
    590 
    591 
    592 // Export defaulted member functions.
    593 struct ExportDefaulted {
    594   __declspec(dllexport) ExportDefaulted() = default;
    595   __declspec(dllexport) ~ExportDefaulted() = default;
    596   __declspec(dllexport) ExportDefaulted(const ExportDefaulted&) = default;
    597   __declspec(dllexport) ExportDefaulted& operator=(const ExportDefaulted&) = default;
    598   __declspec(dllexport) ExportDefaulted(ExportDefaulted&&) = default;
    599   __declspec(dllexport) ExportDefaulted& operator=(ExportDefaulted&&) = default;
    600 };
    601 
    602 
    603 // Export defaulted member function definitions.
    604 struct ExportDefaultedDefs {
    605   __declspec(dllexport) ExportDefaultedDefs();
    606   __declspec(dllexport) ~ExportDefaultedDefs();
    607 
    608   __declspec(dllexport) inline ExportDefaultedDefs(const ExportDefaultedDefs&);
    609   __declspec(dllexport) ExportDefaultedDefs& operator=(const ExportDefaultedDefs&);
    610 
    611   __declspec(dllexport) ExportDefaultedDefs(ExportDefaultedDefs&&);
    612   __declspec(dllexport) ExportDefaultedDefs& operator=(ExportDefaultedDefs&&);
    613 };
    614 
    615 // Export definitions.
    616 __declspec(dllexport) ExportDefaultedDefs::ExportDefaultedDefs() = default;
    617 ExportDefaultedDefs::~ExportDefaultedDefs() = default;
    618 
    619 // Export inline declaration and definition.
    620 __declspec(dllexport) ExportDefaultedDefs::ExportDefaultedDefs(const ExportDefaultedDefs&) = default;
    621 inline ExportDefaultedDefs& ExportDefaultedDefs::operator=(const ExportDefaultedDefs&) = default;
    622 
    623 __declspec(dllexport) ExportDefaultedDefs::ExportDefaultedDefs(ExportDefaultedDefs&&) = default;
    624 ExportDefaultedDefs& ExportDefaultedDefs::operator=(ExportDefaultedDefs&&) = default;
    625 
    626 
    627 // Redeclarations cannot add dllexport.
    628 struct MemberRedecl {
    629                  void normalDef();         // expected-note{{previous declaration is here}}
    630                  void normalInlineDef();   // expected-note{{previous declaration is here}}
    631           inline void normalInlineDecl();  // expected-note{{previous declaration is here}}
    632   virtual        void virtualDef();        // expected-note{{previous declaration is here}}
    633   virtual        void virtualInlineDef();  // expected-note{{previous declaration is here}}
    634   virtual inline void virtualInlineDecl(); // expected-note{{previous declaration is here}}
    635   static         void staticDef();         // expected-note{{previous declaration is here}}
    636   static         void staticInlineDef();   // expected-note{{previous declaration is here}}
    637   static  inline void staticInlineDecl();  // expected-note{{previous declaration is here}}
    638 
    639   static         int  StaticField;         // expected-note{{previous declaration is here}}
    640   static  const  int  StaticConstField;    // expected-note{{previous declaration is here}}
    641   constexpr static int ConstexprField = 1; // expected-note{{previous declaration is here}}
    642 };
    643 
    644 __declspec(dllexport)        void MemberRedecl::normalDef() {}         // expected-error{{redeclaration of 'MemberRedecl::normalDef' cannot add 'dllexport' attribute}}
    645 __declspec(dllexport) inline void MemberRedecl::normalInlineDef() {}   // expected-error{{redeclaration of 'MemberRedecl::normalInlineDef' cannot add 'dllexport' attribute}}
    646 __declspec(dllexport)        void MemberRedecl::normalInlineDecl() {}  // expected-error{{redeclaration of 'MemberRedecl::normalInlineDecl' cannot add 'dllexport' attribute}}
    647 __declspec(dllexport)        void MemberRedecl::virtualDef() {}        // expected-error{{redeclaration of 'MemberRedecl::virtualDef' cannot add 'dllexport' attribute}}
    648 __declspec(dllexport) inline void MemberRedecl::virtualInlineDef() {}  // expected-error{{redeclaration of 'MemberRedecl::virtualInlineDef' cannot add 'dllexport' attribute}}
    649 __declspec(dllexport)        void MemberRedecl::virtualInlineDecl() {} // expected-error{{redeclaration of 'MemberRedecl::virtualInlineDecl' cannot add 'dllexport' attribute}}
    650 __declspec(dllexport)        void MemberRedecl::staticDef() {}         // expected-error{{redeclaration of 'MemberRedecl::staticDef' cannot add 'dllexport' attribute}}
    651 __declspec(dllexport) inline void MemberRedecl::staticInlineDef() {}   // expected-error{{redeclaration of 'MemberRedecl::staticInlineDef' cannot add 'dllexport' attribute}}
    652 __declspec(dllexport)        void MemberRedecl::staticInlineDecl() {}  // expected-error{{redeclaration of 'MemberRedecl::staticInlineDecl' cannot add 'dllexport' attribute}}
    653 
    654 __declspec(dllexport)        int  MemberRedecl::StaticField = 1;       // expected-error{{redeclaration of 'MemberRedecl::StaticField' cannot add 'dllexport' attribute}}
    655 __declspec(dllexport) const  int  MemberRedecl::StaticConstField = 1;  // expected-error{{redeclaration of 'MemberRedecl::StaticConstField' cannot add 'dllexport' attribute}}
    656 __declspec(dllexport) constexpr int MemberRedecl::ConstexprField;      // expected-error{{redeclaration of 'MemberRedecl::ConstexprField' cannot add 'dllexport' attribute}}
    657 
    658 
    659 
    660 //===----------------------------------------------------------------------===//
    661 // Class member templates
    662 //===----------------------------------------------------------------------===//
    663 
    664 struct ExportMemberTmpl {
    665   template<typename T> __declspec(dllexport)               void normalDecl();
    666   template<typename T> __declspec(dllexport)               void normalDef();
    667   template<typename T> __declspec(dllexport)               void normalInclass() {}
    668   template<typename T> __declspec(dllexport)               void normalInlineDef();
    669   template<typename T> __declspec(dllexport)        inline void normalInlineDecl();
    670   template<typename T> __declspec(dllexport) static        void staticDecl();
    671   template<typename T> __declspec(dllexport) static        void staticDef();
    672   template<typename T> __declspec(dllexport) static        void staticInclass() {}
    673   template<typename T> __declspec(dllexport) static        void staticInlineDef();
    674   template<typename T> __declspec(dllexport) static inline void staticInlineDecl();
    675 
    676 #if __has_feature(cxx_variable_templates)
    677   template<typename T> __declspec(dllexport) static        int  StaticField;
    678   template<typename T> __declspec(dllexport) static        int  StaticFieldDef;
    679   template<typename T> __declspec(dllexport) static const  int  StaticConstField;
    680   template<typename T> __declspec(dllexport) static const  int  StaticConstFieldDef;
    681   template<typename T> __declspec(dllexport) static const  int  StaticConstFieldEqualInit = 1;
    682   template<typename T> __declspec(dllexport) static const  int  StaticConstFieldBraceInit{1};
    683   template<typename T> __declspec(dllexport) constexpr static int ConstexprField = 1;
    684   template<typename T> __declspec(dllexport) constexpr static int ConstexprFieldDef = 1;
    685 #endif // __has_feature(cxx_variable_templates)
    686 };
    687 
    688 template<typename T>        void ExportMemberTmpl::normalDef() {}
    689 template<typename T> inline void ExportMemberTmpl::normalInlineDef() {}
    690 template<typename T>        void ExportMemberTmpl::normalInlineDecl() {}
    691 template<typename T>        void ExportMemberTmpl::staticDef() {}
    692 template<typename T> inline void ExportMemberTmpl::staticInlineDef() {}
    693 template<typename T>        void ExportMemberTmpl::staticInlineDecl() {}
    694 
    695 #if __has_feature(cxx_variable_templates)
    696 template<typename T>        int  ExportMemberTmpl::StaticFieldDef;
    697 template<typename T> const  int  ExportMemberTmpl::StaticConstFieldDef = 1;
    698 template<typename T> constexpr int ExportMemberTmpl::ConstexprFieldDef;
    699 #endif // __has_feature(cxx_variable_templates)
    700 
    701 
    702 // Redeclarations cannot add dllexport.
    703 struct MemTmplRedecl {
    704   template<typename T>               void normalDef();         // expected-note{{previous declaration is here}}
    705   template<typename T>               void normalInlineDef();   // expected-note{{previous declaration is here}}
    706   template<typename T>        inline void normalInlineDecl();  // expected-note{{previous declaration is here}}
    707   template<typename T> static        void staticDef();         // expected-note{{previous declaration is here}}
    708   template<typename T> static        void staticInlineDef();   // expected-note{{previous declaration is here}}
    709   template<typename T> static inline void staticInlineDecl();  // expected-note{{previous declaration is here}}
    710 
    711 #if __has_feature(cxx_variable_templates)
    712   template<typename T> static        int  StaticField;         // expected-note{{previous declaration is here}}
    713   template<typename T> static const  int  StaticConstField;    // expected-note{{previous declaration is here}}
    714   template<typename T> constexpr static int ConstexprField = 1; // expected-note{{previous declaration is here}}
    715 #endif // __has_feature(cxx_variable_templates)
    716 };
    717 
    718 template<typename T> __declspec(dllexport)        void MemTmplRedecl::normalDef() {}        // expected-error{{redeclaration of 'MemTmplRedecl::normalDef' cannot add 'dllexport' attribute}}
    719 template<typename T> __declspec(dllexport) inline void MemTmplRedecl::normalInlineDef() {}  // expected-error{{redeclaration of 'MemTmplRedecl::normalInlineDef' cannot add 'dllexport' attribute}}
    720 template<typename T> __declspec(dllexport)        void MemTmplRedecl::normalInlineDecl() {} // expected-error{{redeclaration of 'MemTmplRedecl::normalInlineDecl' cannot add 'dllexport' attribute}}
    721 template<typename T> __declspec(dllexport)        void MemTmplRedecl::staticDef() {}        // expected-error{{redeclaration of 'MemTmplRedecl::staticDef' cannot add 'dllexport' attribute}}
    722 template<typename T> __declspec(dllexport) inline void MemTmplRedecl::staticInlineDef() {}  // expected-error{{redeclaration of 'MemTmplRedecl::staticInlineDef' cannot add 'dllexport' attribute}}
    723 template<typename T> __declspec(dllexport)        void MemTmplRedecl::staticInlineDecl() {} // expected-error{{redeclaration of 'MemTmplRedecl::staticInlineDecl' cannot add 'dllexport' attribute}}
    724 
    725 #if __has_feature(cxx_variable_templates)
    726 template<typename T> __declspec(dllexport)        int  MemTmplRedecl::StaticField = 1;      // expected-error{{redeclaration of 'MemTmplRedecl::StaticField' cannot add 'dllexport' attribute}}
    727 template<typename T> __declspec(dllexport) const  int  MemTmplRedecl::StaticConstField = 1; // expected-error{{redeclaration of 'MemTmplRedecl::StaticConstField' cannot add 'dllexport' attribute}}
    728 template<typename T> __declspec(dllexport) constexpr int MemTmplRedecl::ConstexprField;     // expected-error{{redeclaration of 'MemTmplRedecl::ConstexprField' cannot add 'dllexport' attribute}}
    729 #endif // __has_feature(cxx_variable_templates)
    730 
    731 
    732 
    733 struct MemFunTmpl {
    734   template<typename T>                              void normalDef() {}
    735   template<typename T> __declspec(dllexport)        void exportedNormal() {}
    736   template<typename T>                       static void staticDef() {}
    737   template<typename T> __declspec(dllexport) static void exportedStatic() {}
    738 };
    739 
    740 // Export implicit instantiation of an exported member function template.
    741 void useMemFunTmpl() {
    742   MemFunTmpl().exportedNormal<ImplicitInst_Exported>();
    743   MemFunTmpl().exportedStatic<ImplicitInst_Exported>();
    744 }
    745 
    746 // Export explicit instantiation declaration of an exported member function
    747 // template.
    748 extern template void MemFunTmpl::exportedNormal<ExplicitDecl_Exported>();
    749        template void MemFunTmpl::exportedNormal<ExplicitDecl_Exported>();
    750 
    751 extern template void MemFunTmpl::exportedStatic<ExplicitDecl_Exported>();
    752        template void MemFunTmpl::exportedStatic<ExplicitDecl_Exported>();
    753 
    754 // Export explicit instantiation definition of an exported member function
    755 // template.
    756 template void MemFunTmpl::exportedNormal<ExplicitInst_Exported>();
    757 template void MemFunTmpl::exportedStatic<ExplicitInst_Exported>();
    758 
    759 // Export specialization of an exported member function template.
    760 template<> __declspec(dllexport) void MemFunTmpl::exportedNormal<ExplicitSpec_Exported>();
    761 template<> __declspec(dllexport) void MemFunTmpl::exportedNormal<ExplicitSpec_Def_Exported>() {}
    762 template<> __declspec(dllexport) inline void MemFunTmpl::exportedNormal<ExplicitSpec_InlineDef_Exported>() {}
    763 
    764 template<> __declspec(dllexport) void MemFunTmpl::exportedStatic<ExplicitSpec_Exported>();
    765 template<> __declspec(dllexport) void MemFunTmpl::exportedStatic<ExplicitSpec_Def_Exported>() {}
    766 template<> __declspec(dllexport) inline void MemFunTmpl::exportedStatic<ExplicitSpec_InlineDef_Exported>() {}
    767 
    768 // Not exporting specialization of an exported member function template without
    769 // explicit dllexport.
    770 template<> void MemFunTmpl::exportedNormal<ExplicitSpec_NotExported>() {}
    771 template<> void MemFunTmpl::exportedStatic<ExplicitSpec_NotExported>() {}
    772 
    773 
    774 // Export explicit instantiation declaration of a non-exported member function
    775 // template.
    776 extern template __declspec(dllexport) void MemFunTmpl::normalDef<ExplicitDecl_Exported>();
    777        template __declspec(dllexport) void MemFunTmpl::normalDef<ExplicitDecl_Exported>();
    778 
    779 extern template __declspec(dllexport) void MemFunTmpl::staticDef<ExplicitDecl_Exported>();
    780        template __declspec(dllexport) void MemFunTmpl::staticDef<ExplicitDecl_Exported>();
    781 
    782 // Export explicit instantiation definition of a non-exported member function
    783 // template.
    784 template __declspec(dllexport) void MemFunTmpl::normalDef<ExplicitInst_Exported>();
    785 template __declspec(dllexport) void MemFunTmpl::staticDef<ExplicitInst_Exported>();
    786 
    787 // Export specialization of a non-exported member function template.
    788 template<> __declspec(dllexport) void MemFunTmpl::normalDef<ExplicitSpec_Exported>();
    789 template<> __declspec(dllexport) void MemFunTmpl::normalDef<ExplicitSpec_Def_Exported>() {}
    790 template<> __declspec(dllexport) inline void MemFunTmpl::normalDef<ExplicitSpec_InlineDef_Exported>() {}
    791 
    792 template<> __declspec(dllexport) void MemFunTmpl::staticDef<ExplicitSpec_Exported>();
    793 template<> __declspec(dllexport) void MemFunTmpl::staticDef<ExplicitSpec_Def_Exported>() {}
    794 template<> __declspec(dllexport) inline void MemFunTmpl::staticDef<ExplicitSpec_InlineDef_Exported>() {}
    795 
    796 
    797 
    798 #if __has_feature(cxx_variable_templates)
    799 struct MemVarTmpl {
    800   template<typename T>                       static const int StaticVar = 1;
    801   template<typename T> __declspec(dllexport) static const int ExportedStaticVar = 1;
    802 };
    803 template<typename T> const int MemVarTmpl::StaticVar;
    804 template<typename T> const int MemVarTmpl::ExportedStaticVar;
    805 
    806 // Export implicit instantiation of an exported member variable template.
    807 int useMemVarTmpl() { return MemVarTmpl::ExportedStaticVar<ImplicitInst_Exported>; }
    808 
    809 // Export explicit instantiation declaration of an exported member variable
    810 // template.
    811 extern template const int MemVarTmpl::ExportedStaticVar<ExplicitDecl_Exported>;
    812        template const int MemVarTmpl::ExportedStaticVar<ExplicitDecl_Exported>;
    813 
    814 // Export explicit instantiation definition of an exported member variable
    815 // template.
    816 template const int MemVarTmpl::ExportedStaticVar<ExplicitInst_Exported>;
    817 
    818 // Export specialization of an exported member variable template.
    819 template<> __declspec(dllexport) const int MemVarTmpl::ExportedStaticVar<ExplicitSpec_Exported>;
    820 template<> __declspec(dllexport) const int MemVarTmpl::ExportedStaticVar<ExplicitSpec_Def_Exported> = 1;
    821 
    822 // Not exporting specialization of an exported member variable template without
    823 // explicit dllexport.
    824 template<> const int MemVarTmpl::ExportedStaticVar<ExplicitSpec_NotExported>;
    825 
    826 
    827 // Export explicit instantiation declaration of a non-exported member variable
    828 // template.
    829 extern template __declspec(dllexport) const int MemVarTmpl::StaticVar<ExplicitDecl_Exported>;
    830        template __declspec(dllexport) const int MemVarTmpl::StaticVar<ExplicitDecl_Exported>;
    831 
    832 // Export explicit instantiation definition of a non-exported member variable
    833 // template.
    834 template __declspec(dllexport) const int MemVarTmpl::StaticVar<ExplicitInst_Exported>;
    835 
    836 // Export specialization of a non-exported member variable template.
    837 template<> __declspec(dllexport) const int MemVarTmpl::StaticVar<ExplicitSpec_Exported>;
    838 template<> __declspec(dllexport) const int MemVarTmpl::StaticVar<ExplicitSpec_Def_Exported> = 1;
    839 
    840 #endif // __has_feature(cxx_variable_templates)
    841 
    842 
    843 
    844 //===----------------------------------------------------------------------===//
    845 // Class template members
    846 //===----------------------------------------------------------------------===//
    847 
    848 // Export individual members of a class template.
    849 template<typename T>
    850 struct ExportClassTmplMembers {
    851   __declspec(dllexport)                void normalDecl();
    852   __declspec(dllexport)                void normalDef();
    853   __declspec(dllexport)                void normalInclass() {}
    854   __declspec(dllexport)                void normalInlineDef();
    855   __declspec(dllexport)         inline void normalInlineDecl();
    856   __declspec(dllexport) virtual        void virtualDecl();
    857   __declspec(dllexport) virtual        void virtualDef();
    858   __declspec(dllexport) virtual        void virtualInclass() {}
    859   __declspec(dllexport) virtual        void virtualInlineDef();
    860   __declspec(dllexport) virtual inline void virtualInlineDecl();
    861   __declspec(dllexport) static         void staticDecl();
    862   __declspec(dllexport) static         void staticDef();
    863   __declspec(dllexport) static         void staticInclass() {}
    864   __declspec(dllexport) static         void staticInlineDef();
    865   __declspec(dllexport) static  inline void staticInlineDecl();
    866 
    867 protected:
    868   __declspec(dllexport)                void protectedDef();
    869 private:
    870   __declspec(dllexport)                void privateDef();
    871 public:
    872 
    873   __declspec(dllexport)                int  Field; // expected-warning{{'dllexport' attribute only applies to variables, functions and classes}}
    874   __declspec(dllexport) static         int  StaticField;
    875   __declspec(dllexport) static         int  StaticFieldDef;
    876   __declspec(dllexport) static  const  int  StaticConstField;
    877   __declspec(dllexport) static  const  int  StaticConstFieldDef;
    878   __declspec(dllexport) static  const  int  StaticConstFieldEqualInit = 1;
    879   __declspec(dllexport) static  const  int  StaticConstFieldBraceInit{1};
    880   __declspec(dllexport) constexpr static int ConstexprField = 1;
    881   __declspec(dllexport) constexpr static int ConstexprFieldDef = 1;
    882 };
    883 
    884 template<typename T>        void ExportClassTmplMembers<T>::normalDef() {}
    885 template<typename T> inline void ExportClassTmplMembers<T>::normalInlineDef() {}
    886 template<typename T>        void ExportClassTmplMembers<T>::normalInlineDecl() {}
    887 template<typename T>        void ExportClassTmplMembers<T>::virtualDef() {}
    888 template<typename T> inline void ExportClassTmplMembers<T>::virtualInlineDef() {}
    889 template<typename T>        void ExportClassTmplMembers<T>::virtualInlineDecl() {}
    890 template<typename T>        void ExportClassTmplMembers<T>::staticDef() {}
    891 template<typename T> inline void ExportClassTmplMembers<T>::staticInlineDef() {}
    892 template<typename T>        void ExportClassTmplMembers<T>::staticInlineDecl() {}
    893 template<typename T>        void ExportClassTmplMembers<T>::protectedDef() {}
    894 template<typename T>        void ExportClassTmplMembers<T>::privateDef() {}
    895 
    896 template<typename T>        int  ExportClassTmplMembers<T>::StaticFieldDef;
    897 template<typename T> const  int  ExportClassTmplMembers<T>::StaticConstFieldDef = 1;
    898 template<typename T> constexpr int ExportClassTmplMembers<T>::ConstexprFieldDef;
    899 
    900 template struct ExportClassTmplMembers<ImplicitInst_Exported>;
    901 
    902 
    903 // Redeclarations cannot add dllexport.
    904 template<typename T>
    905 struct CTMR /*ClassTmplMemberRedecl*/ {
    906                  void normalDef();         // expected-note{{previous declaration is here}}
    907                  void normalInlineDef();   // expected-note{{previous declaration is here}}
    908           inline void normalInlineDecl();  // expected-note{{previous declaration is here}}
    909   virtual        void virtualDef();        // expected-note{{previous declaration is here}}
    910   virtual        void virtualInlineDef();  // expected-note{{previous declaration is here}}
    911   virtual inline void virtualInlineDecl(); // expected-note{{previous declaration is here}}
    912   static         void staticDef();         // expected-note{{previous declaration is here}}
    913   static         void staticInlineDef();   // expected-note{{previous declaration is here}}
    914   static  inline void staticInlineDecl();  // expected-note{{previous declaration is here}}
    915 
    916   static         int  StaticField;         // expected-note{{previous declaration is here}}
    917   static  const  int  StaticConstField;    // expected-note{{previous declaration is here}}
    918   constexpr static int ConstexprField = 1; // expected-note{{previous declaration is here}}
    919 };
    920 
    921 template<typename T> __declspec(dllexport)        void CTMR<T>::normalDef() {}         // expected-error{{redeclaration of 'CTMR::normalDef' cannot add 'dllexport' attribute}}
    922 template<typename T> __declspec(dllexport) inline void CTMR<T>::normalInlineDef() {}   // expected-error{{redeclaration of 'CTMR::normalInlineDef' cannot add 'dllexport' attribute}}
    923 template<typename T> __declspec(dllexport)        void CTMR<T>::normalInlineDecl() {}  // expected-error{{redeclaration of 'CTMR::normalInlineDecl' cannot add 'dllexport' attribute}}
    924 template<typename T> __declspec(dllexport)        void CTMR<T>::virtualDef() {}        // expected-error{{redeclaration of 'CTMR::virtualDef' cannot add 'dllexport' attribute}}
    925 template<typename T> __declspec(dllexport) inline void CTMR<T>::virtualInlineDef() {}  // expected-error{{redeclaration of 'CTMR::virtualInlineDef' cannot add 'dllexport' attribute}}
    926 template<typename T> __declspec(dllexport)        void CTMR<T>::virtualInlineDecl() {} // expected-error{{redeclaration of 'CTMR::virtualInlineDecl' cannot add 'dllexport' attribute}}
    927 template<typename T> __declspec(dllexport)        void CTMR<T>::staticDef() {}         // expected-error{{redeclaration of 'CTMR::staticDef' cannot add 'dllexport' attribute}}
    928 template<typename T> __declspec(dllexport) inline void CTMR<T>::staticInlineDef() {}   // expected-error{{redeclaration of 'CTMR::staticInlineDef' cannot add 'dllexport' attribute}}
    929 template<typename T> __declspec(dllexport)        void CTMR<T>::staticInlineDecl() {}  // expected-error{{redeclaration of 'CTMR::staticInlineDecl' cannot add 'dllexport' attribute}}
    930 
    931 template<typename T> __declspec(dllexport)        int  CTMR<T>::StaticField = 1;       // expected-error{{redeclaration of 'CTMR::StaticField' cannot add 'dllexport' attribute}}
    932 template<typename T> __declspec(dllexport) const  int  CTMR<T>::StaticConstField = 1;  // expected-error{{redeclaration of 'CTMR::StaticConstField' cannot add 'dllexport' attribute}}
    933 template<typename T> __declspec(dllexport) constexpr int CTMR<T>::ConstexprField;      // expected-error{{redeclaration of 'CTMR::ConstexprField' cannot add 'dllexport' attribute}}
    934 
    935 
    936 
    937 //===----------------------------------------------------------------------===//
    938 // Class template member templates
    939 //===----------------------------------------------------------------------===//
    940 
    941 template<typename T>
    942 struct ExportClsTmplMemTmpl {
    943   template<typename U> __declspec(dllexport)               void normalDecl();
    944   template<typename U> __declspec(dllexport)               void normalDef();
    945   template<typename U> __declspec(dllexport)               void normalInclass() {}
    946   template<typename U> __declspec(dllexport)               void normalInlineDef();
    947   template<typename U> __declspec(dllexport)        inline void normalInlineDecl();
    948   template<typename U> __declspec(dllexport) static        void staticDecl();
    949   template<typename U> __declspec(dllexport) static        void staticDef();
    950   template<typename U> __declspec(dllexport) static        void staticInclass() {}
    951   template<typename U> __declspec(dllexport) static        void staticInlineDef();
    952   template<typename U> __declspec(dllexport) static inline void staticInlineDecl();
    953 
    954 #if __has_feature(cxx_variable_templates)
    955   template<typename U> __declspec(dllexport) static        int  StaticField;
    956   template<typename U> __declspec(dllexport) static        int  StaticFieldDef;
    957   template<typename U> __declspec(dllexport) static const  int  StaticConstField;
    958   template<typename U> __declspec(dllexport) static const  int  StaticConstFieldDef;
    959   template<typename U> __declspec(dllexport) static const  int  StaticConstFieldEqualInit = 1;
    960   template<typename U> __declspec(dllexport) static const  int  StaticConstFieldBraceInit{1};
    961   template<typename U> __declspec(dllexport) constexpr static int ConstexprField = 1;
    962   template<typename U> __declspec(dllexport) constexpr static int ConstexprFieldDef = 1;
    963 #endif // __has_feature(cxx_variable_templates)
    964 };
    965 
    966 template<typename T> template<typename U>        void ExportClsTmplMemTmpl<T>::normalDef() {}
    967 template<typename T> template<typename U> inline void ExportClsTmplMemTmpl<T>::normalInlineDef() {}
    968 template<typename T> template<typename U>        void ExportClsTmplMemTmpl<T>::normalInlineDecl() {}
    969 template<typename T> template<typename U>        void ExportClsTmplMemTmpl<T>::staticDef() {}
    970 template<typename T> template<typename U> inline void ExportClsTmplMemTmpl<T>::staticInlineDef() {}
    971 template<typename T> template<typename U>        void ExportClsTmplMemTmpl<T>::staticInlineDecl() {}
    972 
    973 #if __has_feature(cxx_variable_templates)
    974 template<typename T> template<typename U>        int  ExportClsTmplMemTmpl<T>::StaticFieldDef;
    975 template<typename T> template<typename U> const  int  ExportClsTmplMemTmpl<T>::StaticConstFieldDef = 1;
    976 template<typename T> template<typename U> constexpr int ExportClsTmplMemTmpl<T>::ConstexprFieldDef;
    977 #endif // __has_feature(cxx_variable_templates)
    978 
    979 
    980 // Redeclarations cannot add dllexport.
    981 template<typename T>
    982 struct CTMTR /*ClassTmplMemberTmplRedecl*/ {
    983   template<typename U>               void normalDef();         // expected-note{{previous declaration is here}}
    984   template<typename U>               void normalInlineDef();   // expected-note{{previous declaration is here}}
    985   template<typename U>        inline void normalInlineDecl();  // expected-note{{previous declaration is here}}
    986   template<typename U> static        void staticDef();         // expected-note{{previous declaration is here}}
    987   template<typename U> static        void staticInlineDef();   // expected-note{{previous declaration is here}}
    988   template<typename U> static inline void staticInlineDecl();  // expected-note{{previous declaration is here}}
    989 
    990 #if __has_feature(cxx_variable_templates)
    991   template<typename U> static        int  StaticField;         // expected-note{{previous declaration is here}}
    992   template<typename U> static const  int  StaticConstField;    // expected-note{{previous declaration is here}}
    993   template<typename U> constexpr static int ConstexprField = 1; // expected-note{{previous declaration is here}}
    994 #endif // __has_feature(cxx_variable_templates)
    995 };
    996 
    997 template<typename T> template<typename U> __declspec(dllexport)        void CTMTR<T>::normalDef() {}         // expected-error{{redeclaration of 'CTMTR::normalDef' cannot add 'dllexport' attribute}}
    998 template<typename T> template<typename U> __declspec(dllexport) inline void CTMTR<T>::normalInlineDef() {}   // expected-error{{redeclaration of 'CTMTR::normalInlineDef' cannot add 'dllexport' attribute}}
    999 template<typename T> template<typename U> __declspec(dllexport)        void CTMTR<T>::normalInlineDecl() {}  // expected-error{{redeclaration of 'CTMTR::normalInlineDecl' cannot add 'dllexport' attribute}}
   1000 template<typename T> template<typename U> __declspec(dllexport)        void CTMTR<T>::staticDef() {}         // expected-error{{redeclaration of 'CTMTR::staticDef' cannot add 'dllexport' attribute}}
   1001 template<typename T> template<typename U> __declspec(dllexport) inline void CTMTR<T>::staticInlineDef() {}   // expected-error{{redeclaration of 'CTMTR::staticInlineDef' cannot add 'dllexport' attribute}}
   1002 template<typename T> template<typename U> __declspec(dllexport)        void CTMTR<T>::staticInlineDecl() {}  // expected-error{{redeclaration of 'CTMTR::staticInlineDecl' cannot add 'dllexport' attribute}}
   1003 
   1004 #if __has_feature(cxx_variable_templates)
   1005 template<typename T> template<typename U> __declspec(dllexport)        int  CTMTR<T>::StaticField = 1;       // expected-error{{redeclaration of 'CTMTR::StaticField' cannot add 'dllexport' attribute}}
   1006 template<typename T> template<typename U> __declspec(dllexport) const  int  CTMTR<T>::StaticConstField = 1;  // expected-error{{redeclaration of 'CTMTR::StaticConstField' cannot add 'dllexport' attribute}}
   1007 template<typename T> template<typename U> __declspec(dllexport) constexpr int CTMTR<T>::ConstexprField;      // expected-error{{redeclaration of 'CTMTR::ConstexprField' cannot add 'dllexport' attribute}}
   1008 #endif // __has_feature(cxx_variable_templates)
   1009 
   1010 // FIXME: Precedence rules seem to be different for classes.
   1011