aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/Parse/ParseExprCXX.cpp8
-rw-r--r--test/SemaCXX/invalid-template-specifier.cpp12
2 files changed, 20 insertions, 0 deletions
diff --git a/lib/Parse/ParseExprCXX.cpp b/lib/Parse/ParseExprCXX.cpp
index d97bc2d028..e9cca9fe1d 100644
--- a/lib/Parse/ParseExprCXX.cpp
+++ b/lib/Parse/ParseExprCXX.cpp
@@ -65,6 +65,12 @@ bool Parser::ParseOptionalCXXScopeSpecifier(CXXScopeSpec &SS,
// Parse the optional 'template' keyword, then make sure we have
// 'identifier <' after it.
if (Tok.is(tok::kw_template)) {
+ // If we don't have a scope specifier, this isn't a
+ // nested-name-specifier, since they aren't allowed to start with
+ // 'template'.
+ if (!HasScopeSpecifier)
+ break;
+
SourceLocation TemplateKWLoc = ConsumeToken();
if (Tok.isNot(tok::identifier)) {
@@ -86,6 +92,8 @@ bool Parser::ParseOptionalCXXScopeSpecifier(CXXScopeSpec &SS,
= Actions.ActOnDependentTemplateName(TemplateKWLoc,
*Tok.getIdentifierInfo(),
Tok.getLocation(), SS);
+ if (!Template)
+ break;
if (AnnotateTemplateIdToken(Template, TNK_Dependent_template_name,
&SS, TemplateKWLoc, false))
break;
diff --git a/test/SemaCXX/invalid-template-specifier.cpp b/test/SemaCXX/invalid-template-specifier.cpp
new file mode 100644
index 0000000000..a3f081ff60
--- /dev/null
+++ b/test/SemaCXX/invalid-template-specifier.cpp
@@ -0,0 +1,12 @@
+// RUN: clang-cc %s -verify -fsyntax-only
+// PR4809
+// This test is primarily checking that this doesn't crash, not the particular
+// diagnostics.
+
+const template basic_istream<char>; // expected-error {{expected unqualified-id}}
+
+namespace S {}
+template <class X> class Y {
+ void x() { S::template y<char>(1); } // expected-error {{does not refer to a template}} \
+ // expected-error {{no member named 'y'}}
+};