r188249 - variable templates updated for PCH serialization... Still working on test cases...
Larisse Voufo
lvoufo at google.com
Mon Aug 12 19:02:26 PDT 2013
Author: lvoufo
Date: Mon Aug 12 21:02:26 2013
New Revision: 188249
URL: http://llvm.org/viewvc/llvm-project?rev=188249&view=rev
Log:
variable templates updated for PCH serialization... Still working on test cases...
Added:
cfe/trunk/test/PCH/cxx1y-variable-templates.cpp
Modified:
cfe/trunk/include/clang/AST/DeclTemplate.h
cfe/trunk/lib/AST/DeclTemplate.cpp
cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp
cfe/trunk/lib/Serialization/ASTWriterDecl.cpp
cfe/trunk/test/SemaCXX/cxx1y-variable-templates_top_level.cpp
Modified: cfe/trunk/include/clang/AST/DeclTemplate.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/DeclTemplate.h?rev=188249&r1=188248&r2=188249&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/DeclTemplate.h (original)
+++ cfe/trunk/include/clang/AST/DeclTemplate.h Mon Aug 12 21:02:26 2013
@@ -2722,6 +2722,8 @@ public:
return getTemplatedDecl()->isThisDeclarationADefinition();
}
+ VarTemplateDecl *getDefinition();
+
/// \brief Create a variable template node.
static VarTemplateDecl *Create(ASTContext &C, DeclContext *DC,
SourceLocation L, DeclarationName Name,
Modified: cfe/trunk/lib/AST/DeclTemplate.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclTemplate.cpp?rev=188249&r1=188248&r2=188249&view=diff
==============================================================================
--- cfe/trunk/lib/AST/DeclTemplate.cpp (original)
+++ cfe/trunk/lib/AST/DeclTemplate.cpp Mon Aug 12 21:02:26 2013
@@ -963,6 +963,16 @@ void VarTemplateDecl::DeallocateCommon(v
static_cast<Common *>(Ptr)->~Common();
}
+VarTemplateDecl *VarTemplateDecl::getDefinition() {
+ VarTemplateDecl *CurD = this;
+ while (CurD) {
+ if (CurD->isThisDeclarationADefinition())
+ return CurD;
+ CurD = CurD->getPreviousDecl();
+ }
+ return 0;
+}
+
VarTemplateDecl *VarTemplateDecl::Create(ASTContext &C, DeclContext *DC,
SourceLocation L, DeclarationName Name,
TemplateParameterList *Params,
Modified: cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp?rev=188249&r1=188248&r2=188249&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp (original)
+++ cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp Mon Aug 12 21:02:26 2013
@@ -3481,11 +3481,22 @@ void Sema::InstantiateVariableDefinition
llvm::PointerUnion<VarTemplateDecl *,
VarTemplatePartialSpecializationDecl *> PatternPtr =
VarSpec->getSpecializedTemplateOrPartial();
- if (PatternPtr.is<VarTemplatePartialSpecializationDecl *>())
+ if (PatternPtr.is<VarTemplatePartialSpecializationDecl *>()) {
PatternDecl = cast<VarDecl>(
PatternPtr.get<VarTemplatePartialSpecializationDecl *>());
- else
- PatternDecl = (PatternPtr.get<VarTemplateDecl *>())->getTemplatedDecl();
+
+ // Find actual definition
+ if (VarDecl *Def = PatternDecl->getDefinition(getASTContext()))
+ PatternDecl = Def;
+ } else {
+ VarTemplateDecl *PatternTemplate = PatternPtr.get<VarTemplateDecl *>();
+
+ // Find actual definition
+ if (VarTemplateDecl *Def = PatternTemplate->getDefinition())
+ PatternTemplate = Def;
+
+ PatternDecl = PatternTemplate->getTemplatedDecl();
+ }
assert(PatternDecl && "instantiating a non-template");
}
Modified: cfe/trunk/lib/Serialization/ASTWriterDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTWriterDecl.cpp?rev=188249&r1=188248&r2=188249&view=diff
==============================================================================
--- cfe/trunk/lib/Serialization/ASTWriterDecl.cpp (original)
+++ cfe/trunk/lib/Serialization/ASTWriterDecl.cpp Mon Aug 12 21:02:26 2013
@@ -735,6 +735,7 @@ void ASTDeclWriter::VisitVarDecl(VarDecl
D->getInitStyle() == VarDecl::CInit &&
D->getInit() == 0 &&
!isa<ParmVarDecl>(D) &&
+ !isa<VarTemplateSpecializationDecl>(D) &&
!D->isConstexpr() &&
!SpecInfo)
AbbrevToUse = Writer.getDeclVarAbbrev();
Added: cfe/trunk/test/PCH/cxx1y-variable-templates.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/PCH/cxx1y-variable-templates.cpp?rev=188249&view=auto
==============================================================================
--- cfe/trunk/test/PCH/cxx1y-variable-templates.cpp (added)
+++ cfe/trunk/test/PCH/cxx1y-variable-templates.cpp Mon Aug 12 21:02:26 2013
@@ -0,0 +1,172 @@
+// No PCH:
+// RUN: %clang_cc1 -pedantic -std=c++1y -include %s -include %s -verify %s -DNONPCH
+// RUN: %clang_cc1 -pedantic -std=c++1y -include %s -include %s -verify %s -DNONPCH -DERROR
+//
+// With PCH:
+// RUN: %clang_cc1 -pedantic -std=c++1y -emit-pch %s -o %t.a -DHEADER1
+// RUN: %clang_cc1 -pedantic -std=c++1y -include-pch %t.a -emit-pch %s -o %t.b -DHEADER2
+// RUN: %clang_cc1 -pedantic -std=c++1y -include-pch %t.b -verify %s -DHEADERUSE
+
+#ifndef ERROR
+// expected-no-diagnostics
+#endif
+
+#ifdef NONPCH
+#if !defined(HEADER1)
+#define HEADER1
+#undef HEADER2
+#undef HEADERUSE
+#elif !defined(HEADER2)
+#define HEADER2
+#undef HEADERUSE
+#else
+#define HEADERUSE
+#undef HEADER1
+#undef HEADER2
+#endif
+#endif
+
+
+// *** HEADER1: First header file
+#if defined(HEADER1) && !defined(HEADER2) && !defined(HEADERUSE)
+
+template<typename T> T var0a = T();
+template<typename T> extern T var0b;
+
+namespace join {
+ template<typename T> T va = T(100);
+ template<typename T> extern T vb;
+
+ namespace diff_types {
+#ifdef ERROR
+ template<typename T> extern float err0;
+ template<typename T> extern T err1;
+#endif
+ template<typename T> extern T def;
+ }
+
+}
+
+namespace spec {
+ template<typename T> constexpr T va = T(10);
+ template<> constexpr float va<float> = 1.5;
+ template constexpr int va<int>;
+
+ template<typename T> T vb = T();
+ template<> constexpr float vb<float> = 1.5;
+
+ template<typename T> T vc = T();
+
+ template<typename T> constexpr T vd = T(10);
+ template<typename T> T* vd<T> = new T();
+}
+
+namespace spec_join1 {
+ template<typename T> T va = T(10);
+ template<> extern float va<float>;
+ extern template int va<int>;
+
+ template<typename T> T vb = T(10);
+ template<> extern float vb<float>;
+
+ template<typename T> T vc = T(10);
+
+ template<typename T> T vd = T(10);
+ template<typename T> extern T* vd<T>;
+}
+
+#endif
+
+
+// *** HEADER2: Second header file -- including HEADER1
+#if defined(HEADER2) && !defined(HEADERUSE)
+
+namespace join {
+ template<typename T> extern T va;
+ template<> constexpr float va<float> = 2.5;
+
+ template<typename T> T vb = T(100);
+
+ namespace diff_types {
+#ifdef ERROR
+ template<typename T> extern T err0; // expected-error {{redefinition of 'err0' with a different type: 'T' vs 'float'}} // expected-note at 42 {{previous definition is here}}
+ template<typename T> extern float err1; // expected-error {{redefinition of 'err1' with a different type: 'float' vs 'T'}} // expected-note at 43 {{previous definition is here}}
+#endif
+ template<typename T> extern T def;
+ }
+}
+
+namespace spec_join1 {
+ template<typename T> extern T va;
+ template<> float va<float> = 1.5;
+ extern template int va<int>;
+
+ template<> float vb<float> = 1.5;
+ template int vb<int>;
+
+ template<> float vc<float> = 1.5;
+ template int vc<int>;
+
+ template<typename T> extern T vd;
+ template<typename T> T* vd<T> = new T();
+}
+
+#endif
+
+// *** HEADERUSE: File using both header files -- including HEADER2
+#ifdef HEADERUSE
+
+template int var0a<int>;
+float fvara = var0a<float>;
+
+template<typename T> extern T var0a;
+
+template<typename T> T var0b = T();
+template int var0b<int>;
+float fvarb = var0b<float>;
+
+namespace join {
+ template const int va<const int>;
+ template<> const int va<int> = 50;
+ static_assert(va<float> == 2.5, "");
+ static_assert(va<int> == 50, "");
+
+ template<> constexpr float vb<float> = 2.5;
+ template const int vb<const int>;
+ static_assert(vb<float> == 2.5, "");
+ static_assert(vb<const int> == 100, "");
+
+ namespace diff_types {
+ template<typename T> T def = T();
+ }
+
+}
+
+namespace spec {
+ static_assert(va<float> == 1.5, "");
+ static_assert(va<int> == 10, "");
+
+ template<typename T> T* vb<T> = new T();
+ int* intpb = vb<int>;
+ static_assert(vb<float> == 1.5, "");
+
+ template<typename T> T* vc<T> = new T();
+ template<> constexpr float vc<float> = 1.5;
+ int* intpc = vc<int>;
+ static_assert(vc<float> == 1.5, "");
+
+ char* intpd = vd<char>;
+}
+
+namespace spec_join1 {
+ template int va<int>;
+ int a = va<int>;
+
+ template<typename T> extern T vb;
+ int b = vb<int>;
+
+ int* intpb = vd<int>;
+}
+
+
+#endif
Modified: cfe/trunk/test/SemaCXX/cxx1y-variable-templates_top_level.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaCXX/cxx1y-variable-templates_top_level.cpp?rev=188249&r1=188248&r2=188249&view=diff
==============================================================================
--- cfe/trunk/test/SemaCXX/cxx1y-variable-templates_top_level.cpp (original)
+++ cfe/trunk/test/SemaCXX/cxx1y-variable-templates_top_level.cpp Mon Aug 12 21:02:26 2013
@@ -14,6 +14,11 @@ T pi = T(3.1415926535897932385); // expe
template<typename T>
CONST T cpi = T(3.1415926535897932385); // expected-note {{template is declared here}}
+template<typename T> extern CONST T vc;
+#ifdef CXX11
+// expected-error at -2 {{constexpr variable declaration must be a definition}}
+#endif
+
namespace use_in_top_level_funcs {
void good() {
More information about the cfe-commits
mailing list