forked from OSchip/llvm-project
Reorganize and improve semantic tests for dllexport/import
llvm-svn: 201947
This commit is contained in:
parent
28671403bf
commit
6047866232
|
@ -3786,7 +3786,7 @@ static void handleX86ForceAlignArgPointerAttr(Sema &S, Decl *D,
|
|||
DLLImportAttr *Sema::mergeDLLImportAttr(Decl *D, SourceRange Range,
|
||||
unsigned AttrSpellingListIndex) {
|
||||
if (D->hasAttr<DLLExportAttr>()) {
|
||||
Diag(Range.getBegin(), diag::warn_attribute_ignored) << "dllimport";
|
||||
Diag(Range.getBegin(), diag::warn_attribute_ignored) << "'dllimport'";
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@ -3834,7 +3834,7 @@ static void handleDLLImportAttr(Sema &S, Decl *D, const AttributeList &Attr) {
|
|||
DLLExportAttr *Sema::mergeDLLExportAttr(Decl *D, SourceRange Range,
|
||||
unsigned AttrSpellingListIndex) {
|
||||
if (DLLImportAttr *Import = D->getAttr<DLLImportAttr>()) {
|
||||
Diag(Import->getLocation(), diag::warn_attribute_ignored) << "dllimport";
|
||||
Diag(Import->getLocation(), diag::warn_attribute_ignored) << Import;
|
||||
D->dropAttr<DLLImportAttr>();
|
||||
}
|
||||
|
||||
|
|
|
@ -10,7 +10,7 @@ typedef __declspec(dllimport) int CB(void);
|
|||
void bar() { return 1; }
|
||||
|
||||
// CHECK-NEG: error: void function 'bar' should not return a value
|
||||
// CHECK-NEG: 1 error generated
|
||||
// CHECK-NEG: {{^}}1 error generated
|
||||
// CHECK-POS: warning: 'dllimport' attribute only applies to variables and functions
|
||||
// CHECK-POS: error: void function 'bar' should not return a value
|
||||
// CHECK-POS: 1 warning and 1 error generated
|
||||
|
|
|
@ -0,0 +1,113 @@
|
|||
// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -verify -std=c99 %s
|
||||
// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -verify -std=c11 %s
|
||||
// RUN: %clang_cc1 -triple i686-mingw32 -fsyntax-only -verify -std=c11 %s
|
||||
// RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -verify -std=c99 %s
|
||||
|
||||
// Invalid usage.
|
||||
__declspec(dllexport) typedef int typedef1; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
typedef __declspec(dllexport) int typedef2; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
typedef int __declspec(dllexport) typedef3; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
typedef __declspec(dllexport) void (*FunTy)(); // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
enum __declspec(dllexport) Enum { EnumVal }; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
struct __declspec(dllexport) Record {}; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Globals
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Export declaration.
|
||||
__declspec(dllexport) extern int ExternGlobalDecl;
|
||||
|
||||
// dllexport implies a definition.
|
||||
__declspec(dllexport) int GlobalDef;
|
||||
|
||||
// Export definition.
|
||||
__declspec(dllexport) int GlobalInit1 = 1;
|
||||
int __declspec(dllexport) GlobalInit2 = 1;
|
||||
|
||||
// Declare, then export definition.
|
||||
__declspec(dllexport) extern int GlobalDeclInit;
|
||||
int GlobalDeclInit = 1;
|
||||
|
||||
// Export in local scope.
|
||||
void functionScope() {
|
||||
__declspec(dllexport) extern int ExternLocalVarDecl;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Functions
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Export function declaration. Check different placements.
|
||||
__attribute__((dllexport)) void decl1A(); // Sanity check with __attribute__
|
||||
__declspec(dllexport) void decl1B();
|
||||
|
||||
void __attribute__((dllexport)) decl2A();
|
||||
void __declspec(dllexport) decl2B();
|
||||
|
||||
// Export function definition.
|
||||
__declspec(dllexport) void def() {}
|
||||
|
||||
// Export inline function.
|
||||
__declspec(dllexport) inline void inlineFunc1() {} // expected-warning{{'dllexport' attribute ignored}}
|
||||
extern void inlineFunc1();
|
||||
|
||||
inline void __attribute__((dllexport)) inlineFunc2() {} // expected-warning{{'dllexport' attribute ignored}}
|
||||
extern void inlineFunc2();
|
||||
|
||||
// Redeclarations
|
||||
__declspec(dllexport) void redecl1();
|
||||
__declspec(dllexport) void redecl1();
|
||||
|
||||
__declspec(dllexport) void redecl2();
|
||||
void redecl2();
|
||||
|
||||
__declspec(dllexport) void redecl3();
|
||||
void redecl3() {}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Precedence
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// dllexport takes precedence over dllimport if both are specified.
|
||||
__attribute__((dllimport, dllexport)) extern int PrecedenceExternGlobal1A; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllimport) __declspec(dllexport) extern int PrecedenceExternGlobal1B; // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
__attribute__((dllexport, dllimport)) extern int PrecedenceExternGlobal2A; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllexport) __declspec(dllimport) extern int PrecedenceExternGlobal2B; // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
__attribute__((dllimport, dllexport)) int PrecedenceGlobal1A; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllimport) __declspec(dllexport) int PrecedenceGlobal1B; // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
__attribute__((dllexport, dllimport)) int PrecedenceGlobal2A; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
__declspec(dllexport) __declspec(dllimport) int PrecedenceGlobal2B; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
__declspec(dllexport) extern int PrecedenceExternGlobalRedecl1;
|
||||
__declspec(dllimport) extern int PrecedenceExternGlobalRedecl1; // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
__declspec(dllimport) extern int PrecedenceExternGlobalRedecl2; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllexport) extern int PrecedenceExternGlobalRedecl2;
|
||||
|
||||
__declspec(dllexport) extern int PrecedenceGlobalRedecl1;
|
||||
__declspec(dllimport) int PrecedenceGlobalRedecl1; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
__declspec(dllimport) extern int PrecedenceGlobalRedecl2; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllexport) int PrecedenceGlobalRedecl2;
|
||||
|
||||
void __attribute__((dllimport, dllexport)) precedence1A() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
void __declspec(dllimport) __declspec(dllexport) precedence1B() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
void __attribute__((dllexport, dllimport)) precedence2A() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
void __declspec(dllexport) __declspec(dllimport) precedence2B() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
void __declspec(dllimport) precedenceRedecl1(); // expected-warning{{'dllimport' attribute ignored}}
|
||||
void __declspec(dllexport) precedenceRedecl1() {}
|
||||
|
||||
void __declspec(dllexport) precedenceRedecl2();
|
||||
void __declspec(dllimport) precedenceRedecl2() {} // expected-warning{{'dllimport' attribute ignored}}
|
|
@ -1,48 +0,0 @@
|
|||
// RUN: %clang_cc1 -triple i386-mingw32 -fsyntax-only -verify %s
|
||||
// RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -verify %s
|
||||
|
||||
inline void __attribute__((dllexport)) foo1(){} // expected-warning{{'dllexport' attribute ignored}}
|
||||
inline void __attribute__((dllimport)) foo2(){} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
void __attribute__((dllimport)) foo3(){} // expected-error{{'dllimport' attribute can be applied only to symbol declaration}}
|
||||
|
||||
void __attribute__((dllimport, dllexport)) foo4(); // expected-warning{{dllimport attribute ignored}}
|
||||
|
||||
void __attribute__((dllexport)) foo5();
|
||||
void __attribute__((dllimport)) foo5(); // expected-warning{{dllimport attribute ignored}}
|
||||
|
||||
typedef int __attribute__((dllexport)) type6; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
|
||||
typedef int __attribute__((dllimport)) type7; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
|
||||
void __attribute__((dllimport)) foo6();
|
||||
void foo6(){} // expected-warning {{'foo6' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
|
||||
|
||||
// PR6269
|
||||
inline void __declspec(dllexport) foo7(){} // expected-warning{{'dllexport' attribute ignored}}
|
||||
inline void __declspec(dllimport) foo8(){} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
void __declspec(dllimport) foo9(){} // expected-error{{'dllimport' attribute can be applied only to symbol declaration}}
|
||||
|
||||
void __declspec(dllimport) __declspec(dllexport) foo10(); // expected-warning{{dllimport attribute ignored}}
|
||||
|
||||
void __declspec(dllexport) foo11();
|
||||
void __declspec(dllimport) foo11(); // expected-warning{{dllimport attribute ignored}}
|
||||
|
||||
typedef int __declspec(dllexport) type1; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
|
||||
typedef int __declspec(dllimport) type2; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
|
||||
void __declspec(dllimport) foo12();
|
||||
void foo12(){} // expected-warning {{'foo12' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
|
||||
|
||||
void __attribute__((dllimport)) foo13(); // expected-warning{{dllimport attribute ignored}}
|
||||
void __attribute__((dllexport)) foo13();
|
||||
|
||||
extern int foo14 __attribute__((dllexport));
|
||||
extern int foo14 __attribute__((dllimport)); // expected-warning{{dllimport attribute ignored}}
|
||||
|
||||
__declspec(dllimport) int foo15 = 54; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
extern __declspec(dllimport) int foo17;
|
||||
int foo17 = 54; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
|
@ -0,0 +1,68 @@
|
|||
// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -verify -std=c99 %s
|
||||
// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -verify -std=c11 %s
|
||||
// RUN: %clang_cc1 -triple i686-mingw32 -fsyntax-only -verify -std=c11 %s
|
||||
// RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -verify -std=c99 %s
|
||||
|
||||
// Invalid usage.
|
||||
__declspec(dllimport) typedef int typedef1; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
typedef __declspec(dllimport) int typedef2; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
typedef int __declspec(dllimport) typedef3; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
typedef __declspec(dllimport) void (*FunTy)(); // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
enum __declspec(dllimport) Enum { EnumVal }; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
struct __declspec(dllimport) Record {}; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Globals
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Import declaration.
|
||||
__declspec(dllimport) extern int ExternGlobalDecl;
|
||||
|
||||
// dllimport implies a declaration. FIXME: This should not warn.
|
||||
__declspec(dllimport) int GlobalDecl; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
// Not allowed on definitions.
|
||||
__declspec(dllimport) int GlobalInit1 = 1; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
int __declspec(dllimport) GlobalInit2 = 1; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
// Declare, then reject definition.
|
||||
__declspec(dllimport) extern int ExternGlobalDeclInit;
|
||||
int ExternGlobalDeclInit = 1; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
// Redeclarations
|
||||
__declspec(dllimport) extern int GlobalRedecl1;
|
||||
__declspec(dllimport) extern int GlobalRedecl1;
|
||||
|
||||
// Import in local scope.
|
||||
void functionScope() {
|
||||
__declspec(dllimport) extern int ExternLocalVarDecl;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Functions
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Import function declaration. Check different placements.
|
||||
__attribute__((dllimport)) void decl1A(); // Sanity check with __attribute__
|
||||
__declspec(dllimport) void decl1B();
|
||||
|
||||
void __attribute__((dllimport)) decl2A();
|
||||
void __declspec(dllimport) decl2B();
|
||||
|
||||
// Not allowed on function definitions.
|
||||
__declspec(dllimport) void def() {} // expected-error{{'dllimport' attribute can be applied only to symbol declaration}}
|
||||
|
||||
// Import inline function.
|
||||
__declspec(dllimport) inline void inlineFunc1() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
inline void __attribute__((dllimport)) inlineFunc2() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
// Redeclarations
|
||||
__declspec(dllimport) void redecl1();
|
||||
__declspec(dllimport) void redecl1();
|
||||
|
||||
__declspec(dllimport) void redecl3();
|
||||
void redecl3() {} // expected-warning{{'redecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
|
|
@ -0,0 +1,189 @@
|
|||
// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -verify -std=c++11 %s
|
||||
// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -verify -std=c++1y %s
|
||||
// RUN: %clang_cc1 -triple i686-mingw32 -fsyntax-only -verify -std=c++1y %s
|
||||
// RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -verify -std=c++11 %s
|
||||
|
||||
// Helper structs to make templates more expressive.
|
||||
struct ImplicitInst_Exported {};
|
||||
struct ExplicitDecl_Exported {};
|
||||
struct ExplicitInst_Exported {};
|
||||
struct ExplicitSpec_Exported {};
|
||||
struct ExplicitSpec_Def_Exported {};
|
||||
struct ExplicitSpec_InlineDef_Exported {};
|
||||
struct ExplicitSpec_NotExported {};
|
||||
|
||||
|
||||
// Invalid usage.
|
||||
__declspec(dllexport) typedef int typedef1; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
typedef __declspec(dllexport) int typedef2; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
typedef int __declspec(dllexport) typedef3; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
typedef __declspec(dllexport) void (*FunTy)(); // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
enum __declspec(dllexport) Enum {}; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
#if __has_feature(cxx_strong_enums)
|
||||
enum class __declspec(dllexport) EnumClass {}; // expected-warning{{'dllexport' attribute only applies to variables and functions}}
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Globals
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Export declaration.
|
||||
__declspec(dllexport) extern int ExternGlobalDecl;
|
||||
|
||||
// dllexport implies a definition.
|
||||
__declspec(dllexport) int GlobalDef;
|
||||
|
||||
// Export definition.
|
||||
__declspec(dllexport) int GlobalInit1 = 1;
|
||||
int __declspec(dllexport) GlobalInit2 = 1;
|
||||
|
||||
// Declare, then export definition.
|
||||
__declspec(dllexport) extern int GlobalDeclInit;
|
||||
int GlobalDeclInit = 1;
|
||||
|
||||
// Export in local scope.
|
||||
void functionScope() {
|
||||
__declspec(dllexport) extern int ExternLocalVarDecl;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Functions
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Export function declaration. Check different placements.
|
||||
__attribute__((dllexport)) void decl1A(); // Sanity check with __attribute__
|
||||
__declspec(dllexport) void decl1B();
|
||||
|
||||
void __attribute__((dllexport)) decl2A();
|
||||
void __declspec(dllexport) decl2B();
|
||||
|
||||
// Export function definition.
|
||||
__declspec(dllexport) void def() {}
|
||||
|
||||
// extern "C"
|
||||
extern "C" __declspec(dllexport) void externC() {}
|
||||
|
||||
// Export inline function.
|
||||
__declspec(dllexport) inline void inlineFunc1() {} // expected-warning{{'dllexport' attribute ignored}}
|
||||
inline void __attribute__((dllexport)) inlineFunc2() {} // expected-warning{{'dllexport' attribute ignored}}
|
||||
|
||||
__declspec(dllexport) inline void inlineDecl(); // expected-warning{{'dllexport' attribute ignored}}
|
||||
void inlineDecl() {}
|
||||
|
||||
__declspec(dllexport) void inlineDef();
|
||||
inline void inlineDef() {}
|
||||
|
||||
// Redeclarations
|
||||
__declspec(dllexport) void redecl1();
|
||||
__declspec(dllexport) void redecl1() {}
|
||||
|
||||
__declspec(dllexport) void redecl2();
|
||||
void redecl2() {}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Function templates
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Export function template declaration. Check different placements.
|
||||
template<typename T> __declspec(dllexport) void funcTmplDecl1();
|
||||
template<typename T> void __declspec(dllexport) funcTmplDecl2();
|
||||
|
||||
// Export function template definition.
|
||||
template<typename T> __declspec(dllexport) void funcTmplDef() {}
|
||||
|
||||
// Redeclarations
|
||||
template<typename T> __declspec(dllexport) void funcTmplRedecl1();
|
||||
template<typename T> __declspec(dllexport) void funcTmplRedecl1() {}
|
||||
|
||||
template<typename T> __declspec(dllexport) void funcTmplRedecl2();
|
||||
template<typename T> void funcTmplRedecl2() {}
|
||||
|
||||
template<typename T> __declspec(dllexport) void funcTmplRedecl3();
|
||||
template<typename T> void funcTmplRedecl3() {}
|
||||
|
||||
|
||||
template<typename T> void funcTmpl() {}
|
||||
template<typename T> __declspec(dllexport) void exportedFuncTmplDecl();
|
||||
template<typename T> __declspec(dllexport) void exportedFuncTmpl() {}
|
||||
|
||||
// Export implicit instantiation of an exported function template.
|
||||
void useFunTmplDecl() { exportedFuncTmplDecl<ImplicitInst_Exported>(); }
|
||||
void useFunTmplDef() { exportedFuncTmpl<ImplicitInst_Exported>(); }
|
||||
|
||||
// Export explicit instantiation declaration of an exported function template.
|
||||
extern template void exportedFuncTmpl<ExplicitDecl_Exported>();
|
||||
template void exportedFuncTmpl<ExplicitDecl_Exported>();
|
||||
|
||||
// Export explicit instantiation definition of an exported function template.
|
||||
template void exportedFuncTmpl<ExplicitInst_Exported>();
|
||||
|
||||
// Export specialization of an exported function template.
|
||||
template<> __declspec(dllexport) void exportedFuncTmpl<ExplicitSpec_Exported>();
|
||||
template<> __declspec(dllexport) void exportedFuncTmpl<ExplicitSpec_Def_Exported>() {}
|
||||
template<> __declspec(dllexport) inline void exportedFuncTmpl<ExplicitSpec_InlineDef_Exported>() {} // expected-warning{{'dllexport' attribute ignored}}
|
||||
|
||||
// Not exporting specialization of an exported function template without
|
||||
// explicit dllexport.
|
||||
template<> void exportedFuncTmpl<ExplicitSpec_NotExported>() {}
|
||||
|
||||
|
||||
// Export explicit instantiation declaration of a non-exported function template.
|
||||
extern template __declspec(dllexport) void funcTmpl<ExplicitDecl_Exported>();
|
||||
template __declspec(dllexport) void funcTmpl<ExplicitDecl_Exported>();
|
||||
|
||||
// Export explicit instantiation definition of a non-exported function template.
|
||||
template __declspec(dllexport) void funcTmpl<ExplicitInst_Exported>();
|
||||
|
||||
// Export specialization of a non-exported function template.
|
||||
template<> __declspec(dllexport) void funcTmpl<ExplicitSpec_Exported>();
|
||||
template<> __declspec(dllexport) void funcTmpl<ExplicitSpec_Def_Exported>() {}
|
||||
template<> __declspec(dllexport) inline void funcTmpl<ExplicitSpec_InlineDef_Exported>() {} // expected-warning{{'dllexport' attribute ignored}}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Precedence
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// dllexport takes precedence over dllimport if both are specified.
|
||||
__attribute__((dllimport, dllexport)) extern int PrecedenceExternGlobal1A; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllimport) __declspec(dllexport) extern int PrecedenceExternGlobal1B; // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
__attribute__((dllexport, dllimport)) extern int PrecedenceExternGlobal2A; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllexport) __declspec(dllimport) extern int PrecedenceExternGlobal2B; // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
__attribute__((dllimport, dllexport)) int PrecedenceGlobal1A; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllimport) __declspec(dllexport) int PrecedenceGlobal1B; // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
__attribute__((dllexport, dllimport)) int PrecedenceGlobal2A; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
__declspec(dllexport) __declspec(dllimport) int PrecedenceGlobal2B; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
__declspec(dllexport) extern int PrecedenceExternGlobalRedecl1;
|
||||
__declspec(dllimport) extern int PrecedenceExternGlobalRedecl1; // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
__declspec(dllimport) extern int PrecedenceExternGlobalRedecl2; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllexport) extern int PrecedenceExternGlobalRedecl2;
|
||||
|
||||
__declspec(dllexport) extern int PrecedenceGlobalRedecl1;
|
||||
__declspec(dllimport) int PrecedenceGlobalRedecl1; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
__declspec(dllimport) extern int PrecedenceGlobalRedecl2; // expected-warning{{'dllimport' attribute ignored}}
|
||||
__declspec(dllexport) int PrecedenceGlobalRedecl2;
|
||||
|
||||
void __attribute__((dllimport, dllexport)) precedence1A() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
void __declspec(dllimport) __declspec(dllexport) precedence1B() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
void __attribute__((dllexport, dllimport)) precedence2A() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
void __declspec(dllexport) __declspec(dllimport) precedence2B() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
void __declspec(dllimport) precedenceRedecl1(); // expected-warning{{'dllimport' attribute ignored}}
|
||||
void __declspec(dllexport) precedenceRedecl1() {}
|
||||
|
||||
void __declspec(dllexport) precedenceRedecl2();
|
||||
void __declspec(dllimport) precedenceRedecl2() {} // expected-warning{{'dllimport' attribute ignored}}
|
|
@ -0,0 +1,127 @@
|
|||
// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -verify -std=c++11 %s
|
||||
// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -verify -std=c++1y %s
|
||||
// RUN: %clang_cc1 -triple i686-mingw32 -fsyntax-only -verify -std=c++1y %s
|
||||
// RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -verify -std=c++11 %s
|
||||
|
||||
// Helper structs to make templates more expressive.
|
||||
struct ImplicitInst_Imported {};
|
||||
struct ExplicitDecl_Imported {};
|
||||
struct ExplicitInst_Imported {};
|
||||
struct ExplicitSpec_Imported {};
|
||||
struct ExplicitSpec_Def_Imported {};
|
||||
struct ExplicitSpec_InlineDef_Imported {};
|
||||
struct ExplicitSpec_NotImported {};
|
||||
|
||||
|
||||
// Invalid usage.
|
||||
__declspec(dllimport) typedef int typedef1; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
typedef __declspec(dllimport) int typedef2; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
typedef int __declspec(dllimport) typedef3; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
typedef __declspec(dllimport) void (*FunTy)(); // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
enum __declspec(dllimport) Enum {}; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
#if __has_feature(cxx_strong_enums)
|
||||
enum class __declspec(dllimport) EnumClass {}; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Globals
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Import declaration.
|
||||
__declspec(dllimport) extern int ExternGlobalDecl;
|
||||
|
||||
// dllimport implies a declaration. FIXME: This should not warn.
|
||||
__declspec(dllimport) int GlobalDecl; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
// Not allowed on definitions.
|
||||
__declspec(dllimport) int GlobalInit1 = 1; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
int __declspec(dllimport) GlobalInit2 = 1; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
// Declare, then reject definition.
|
||||
__declspec(dllimport) extern int ExternGlobalDeclInit;
|
||||
int ExternGlobalDeclInit = 1; // expected-warning{{'dllimport' attribute cannot be specified on a definition}}
|
||||
|
||||
// Redeclarations
|
||||
__declspec(dllimport) extern int GlobalRedecl1;
|
||||
__declspec(dllimport) extern int GlobalRedecl1;
|
||||
|
||||
// Import in local scope.
|
||||
void functionScope() {
|
||||
__declspec(dllimport) extern int ExternLocalVarDecl;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Functions
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Import function declaration. Check different placements.
|
||||
__attribute__((dllimport)) void decl1A(); // Sanity check with __attribute__
|
||||
__declspec(dllimport) void decl1B();
|
||||
|
||||
void __attribute__((dllimport)) decl2A();
|
||||
void __declspec(dllimport) decl2B();
|
||||
|
||||
// Not allowed on function definitions.
|
||||
__declspec(dllimport) void def() {} // expected-error{{'dllimport' attribute can be applied only to symbol declaration}}
|
||||
|
||||
// extern "C"
|
||||
extern "C" __declspec(dllexport) void externC();
|
||||
|
||||
// Import inline function.
|
||||
__declspec(dllimport) inline void inlineFunc1() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
inline void __attribute__((dllimport)) inlineFunc2() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
// Redeclarations
|
||||
__declspec(dllimport) void redecl1();
|
||||
__declspec(dllimport) void redecl1();
|
||||
|
||||
__declspec(dllimport) void redecl3();
|
||||
void redecl3() {} // expected-warning{{'redecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Function templates
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
// Import function template declaration. Check different placements.
|
||||
template<typename T> __declspec(dllimport) void funcTmplDecl1();
|
||||
template<typename T> void __declspec(dllimport) funcTmplDecl2();
|
||||
|
||||
// Redeclarations
|
||||
template<typename T> __declspec(dllimport) void funcTmplRedecl1();
|
||||
template<typename T> __declspec(dllimport) void funcTmplRedecl1();
|
||||
|
||||
template<typename T> __declspec(dllimport) void funcTmplRedecl2();
|
||||
template<typename T> void funcTmplRedecl2();
|
||||
|
||||
template<typename T> __declspec(dllimport) void funcTmplRedecl3();
|
||||
template<typename T> void funcTmplRedecl3() {} // expected-warning{{'funcTmplRedecl3' redeclared without 'dllimport' attribute: previous 'dllimport' ignored}}
|
||||
|
||||
|
||||
template<typename T> void funcTmpl() {}
|
||||
template<typename T> __declspec(dllimport) void importedFuncTmpl();
|
||||
|
||||
// Import specialization of an imported function template. A definition must be
|
||||
// declared inline.
|
||||
template<> __declspec(dllimport) void importedFuncTmpl<ExplicitSpec_Imported>();
|
||||
template<> __declspec(dllimport) void importedFuncTmpl<ExplicitSpec_Def_Imported>() {} // expected-error{{'dllimport' attribute can be applied only to symbol declaration}}
|
||||
template<> __declspec(dllimport) inline void importedFuncTmpl<ExplicitSpec_InlineDef_Imported>() {} // expected-warning{{'dllimport' attribute ignored}}
|
||||
|
||||
// Not importing specialization of an imported function template without
|
||||
// explicit dllimport.
|
||||
template<> void importedFuncTmpl<ExplicitSpec_NotImported>() {}
|
||||
|
||||
|
||||
// Import explicit instantiation declaration of a non-imported function template.
|
||||
extern template __declspec(dllimport) void funcTmpl<ExplicitDecl_Imported>();
|
||||
|
||||
// Import specialization of a non-imported function template. A definition must
|
||||
// be declared inline.
|
||||
template<> __declspec(dllimport) void funcTmpl<ExplicitSpec_Imported>();
|
||||
template<> __declspec(dllimport) void funcTmpl<ExplicitSpec_Def_Imported>() {} // expected-error{{'dllimport' attribute can be applied only to symbol declaration}}
|
||||
template<> __declspec(dllimport) inline void funcTmpl<ExplicitSpec_InlineDef_Imported>() {} // expected-warning{{'dllimport' attribute ignored}}
|
Loading…
Reference in New Issue