summaryrefslogtreecommitdiffstats
path: root/clang
diff options
context:
space:
mode:
Diffstat (limited to 'clang')
-rw-r--r--clang/include/clang/Basic/DiagnosticSemaKinds.def2
-rw-r--r--clang/lib/AST/Type.cpp37
-rw-r--r--clang/lib/Sema/SemaTemplate.cpp3
-rw-r--r--clang/test/SemaTemplate/class-template-id-2.cpp2
-rw-r--r--clang/test/SemaTemplate/class-template-spec.cpp2
-rw-r--r--clang/test/SemaTemplate/instantiation-backtrace.cpp11
-rw-r--r--clang/test/SemaTemplate/instantiation-depth.cpp2
7 files changed, 43 insertions, 16 deletions
diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.def b/clang/include/clang/Basic/DiagnosticSemaKinds.def
index dbba5ab18ab..46d81445b67 100644
--- a/clang/include/clang/Basic/DiagnosticSemaKinds.def
+++ b/clang/include/clang/Basic/DiagnosticSemaKinds.def
@@ -643,7 +643,7 @@ DIAG(err_template_spec_redecl_global_scope, ERROR,
DIAG(err_template_recursion_depth_exceeded, ERROR,
"recursive template instantiation exceeded maximum depth of %0")
DIAG(note_template_recursion_depth, NOTE,
- "use -ftemplate-depth=N to increase recursive template "
+ "use -ftemplate-depth-N to increase recursive template "
"instantiation depth")
DIAG(err_template_implicit_instantiate_undefined, ERROR,
"implicit instantiation of undefined template %0")
diff --git a/clang/lib/AST/Type.cpp b/clang/lib/AST/Type.cpp
index f9cf847ee9e..205ebef20b5 100644
--- a/clang/lib/AST/Type.cpp
+++ b/clang/lib/AST/Type.cpp
@@ -1287,10 +1287,11 @@ void TemplateTypeParmType::getAsStringInternal(std::string &InnerString) const {
InnerString = Name->getName() + InnerString;
}
-void
-ClassTemplateSpecializationType::
-getAsStringInternal(std::string &InnerString) const {
- std::string SpecString = Template->getNameAsString();
+/// \brief Print a template argument list, including the '<' and '>'
+/// enclosing the template arguments.
+static std::string printTemplateArgumentList(const TemplateArgument *Args,
+ unsigned NumArgs) {
+ std::string SpecString;
SpecString += '<';
for (unsigned Arg = 0; Arg < NumArgs; ++Arg) {
if (Arg)
@@ -1298,22 +1299,22 @@ getAsStringInternal(std::string &InnerString) const {
// Print the argument into a string.
std::string ArgString;
- switch (getArg(Arg).getKind()) {
+ switch (Args[Arg].getKind()) {
case TemplateArgument::Type:
- getArg(Arg).getAsType().getAsStringInternal(ArgString);
+ Args[Arg].getAsType().getAsStringInternal(ArgString);
break;
case TemplateArgument::Declaration:
- ArgString = cast<NamedDecl>(getArg(Arg).getAsDecl())->getNameAsString();
+ ArgString = cast<NamedDecl>(Args[Arg].getAsDecl())->getNameAsString();
break;
case TemplateArgument::Integral:
- ArgString = getArg(Arg).getAsIntegral()->toString(10, true);
+ ArgString = Args[Arg].getAsIntegral()->toString(10, true);
break;
case TemplateArgument::Expression: {
llvm::raw_string_ostream s(ArgString);
- getArg(Arg).getAsExpr()->printPretty(s);
+ Args[Arg].getAsExpr()->printPretty(s);
break;
}
}
@@ -1335,6 +1336,14 @@ getAsStringInternal(std::string &InnerString) const {
SpecString += '>';
+ return SpecString;
+}
+
+void
+ClassTemplateSpecializationType::
+getAsStringInternal(std::string &InnerString) const {
+ std::string SpecString = Template->getNameAsString();
+ SpecString += printTemplateArgumentList(getArgs(), getNumArgs());
if (InnerString.empty())
InnerString.swap(SpecString);
else
@@ -1395,6 +1404,16 @@ void TagType::getAsStringInternal(std::string &InnerString) const {
} else
ID = "<anonymous>";
+ // If this is a class template specialization, print the template
+ // arguments.
+ if (ClassTemplateSpecializationDecl *Spec
+ = dyn_cast<ClassTemplateSpecializationDecl>(getDecl())) {
+ std::string TemplateArgs
+ = printTemplateArgumentList(Spec->getTemplateArgs(),
+ Spec->getNumTemplateArgs());
+ InnerString = TemplateArgs + InnerString;
+ }
+
if (Kind)
InnerString = std::string(Kind) + " " + ID + InnerString;
else
diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp
index 281984de2c9..fc1173d9d16 100644
--- a/clang/lib/Sema/SemaTemplate.cpp
+++ b/clang/lib/Sema/SemaTemplate.cpp
@@ -1006,7 +1006,8 @@ bool Sema::CheckTemplateArgument(TemplateTypeParmDecl *Param,
if (Tag && Tag->getDecl()->getDeclContext()->isFunctionOrMethod())
return Diag(ArgLoc, diag::err_template_arg_local_type)
<< QualType(Tag, 0);
- else if (Tag && !Tag->getDecl()->getDeclName()) {
+ else if (Tag && !Tag->getDecl()->getDeclName() &&
+ !Tag->getDecl()->getTypedefForAnonDecl()) {
Diag(ArgLoc, diag::err_template_arg_unnamed_type);
Diag(Tag->getDecl()->getLocation(), diag::note_template_unnamed_type_here);
return true;
diff --git a/clang/test/SemaTemplate/class-template-id-2.cpp b/clang/test/SemaTemplate/class-template-id-2.cpp
index 3014208b6ea..5499c50a949 100644
--- a/clang/test/SemaTemplate/class-template-id-2.cpp
+++ b/clang/test/SemaTemplate/class-template-id-2.cpp
@@ -4,7 +4,7 @@ namespace N {
template<> class A<int> { };
- template<> class A<float>; // expected-note{{forward declaration of 'class A'}}
+ template<> class A<float>; // expected-note{{forward declaration of 'class A<float>'}}
class B : public A<int> { };
}
diff --git a/clang/test/SemaTemplate/class-template-spec.cpp b/clang/test/SemaTemplate/class-template-spec.cpp
index 023ba381ec4..90ab39f32e9 100644
--- a/clang/test/SemaTemplate/class-template-spec.cpp
+++ b/clang/test/SemaTemplate/class-template-spec.cpp
@@ -19,7 +19,7 @@ int test_incomplete_specs(A<double, double> *a1,
A<double> *a2)
{
(void)a1->x; // expected-error{{incomplete definition of type 'A<double, double>'}}
- (void)a2->x; // expected-error{{implicit instantiation of undefined template 'struct A'}}
+ (void)a2->x; // expected-error{{implicit instantiation of undefined template 'struct A<double, int>'}}
}
typedef float FLOAT;
diff --git a/clang/test/SemaTemplate/instantiation-backtrace.cpp b/clang/test/SemaTemplate/instantiation-backtrace.cpp
index 4c8ea13a8d7..f8aabff0973 100644
--- a/clang/test/SemaTemplate/instantiation-backtrace.cpp
+++ b/clang/test/SemaTemplate/instantiation-backtrace.cpp
@@ -1,7 +1,8 @@
// RUN: clang -fsyntax-only -verify %s
-template<typename T> struct A; // expected-note{{template is declared here}}
+template<typename T> struct A; // expected-note 2{{template is declared here}}
-template<typename T> struct B : A<T*> { }; // expected-error{{implicit instantiation of undefined template}}
+template<typename T> struct B : A<T*> { }; // expected-error{{implicit instantiation of undefined template}} \
+// expected-error{{implicit instantiation of undefined template 'struct A<X *>'}}
template<typename T> struct C : B<T> { } ; // expected-note{{instantiation of template class}}
@@ -14,3 +15,9 @@ template<typename T> struct F : E<T(T)> { }; // expected-note{{instantiation of
void f() {
(void)sizeof(F<int>); // expected-note{{instantiation of template class}}
}
+
+typedef struct { } X;
+
+void g() {
+ (void)sizeof(B<X>); // expected-note{{in instantiation of template class 'struct B<X>' requested here}}
+}
diff --git a/clang/test/SemaTemplate/instantiation-depth.cpp b/clang/test/SemaTemplate/instantiation-depth.cpp
index 25c40fce4d1..06317d88d48 100644
--- a/clang/test/SemaTemplate/instantiation-depth.cpp
+++ b/clang/test/SemaTemplate/instantiation-depth.cpp
@@ -1,7 +1,7 @@
// RUN: clang -fsyntax-only -ftemplate-depth=5 -verify %s
template<typename T> struct X : X<T*> { }; // expected-error{{recursive template instantiation exceeded maximum depth of 5}} \
-// expected-note{{use -ftemplate-depth=N to increase recursive template instantiation depth}} \
+// expected-note{{use -ftemplate-depth-N to increase recursive template instantiation depth}} \
// expected-note 5 {{instantiation of template class}}
void test() {
OpenPOWER on IntegriCloud