diff options
| author | Richard Smith <richard-llvm@metafoo.co.uk> | 2014-01-25 21:32:06 +0000 |
|---|---|---|
| committer | Richard Smith <richard-llvm@metafoo.co.uk> | 2014-01-25 21:32:06 +0000 |
| commit | 72db563280cf1686d6861c3f6d21cf35bd402998 (patch) | |
| tree | 31659550892202a3156f6832fda466d70dd3946e | |
| parent | f137f9317b530f63904699e6dd4d3a9714b2d825 (diff) | |
| download | bcm5719-llvm-72db563280cf1686d6861c3f6d21cf35bd402998.tar.gz bcm5719-llvm-72db563280cf1686d6861c3f6d21cf35bd402998.zip | |
PR18530: Don't assert when performing error recovery after a missing 'template<>' on a variable template explicit specialization.
llvm-svn: 200099
| -rw-r--r-- | clang/lib/Sema/SemaDecl.cpp | 19 | ||||
| -rw-r--r-- | clang/test/SemaCXX/cxx1y-variable-templates_top_level.cpp | 5 |
2 files changed, 12 insertions, 12 deletions
diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp index 33cb77fa14f..d4be61a2276 100644 --- a/clang/lib/Sema/SemaDecl.cpp +++ b/clang/lib/Sema/SemaDecl.cpp @@ -5129,7 +5129,7 @@ Sema::ActOnVariableDeclarator(Scope *S, Declarator &D, DeclContext *DC, << SourceRange(TemplateId->LAngleLoc, TemplateId->RAngleLoc) << FixItHint::CreateInsertion(D.getDeclSpec().getLocStart(), "template<> "); - IsVariableTemplateSpecialization = true; + IsExplicitSpecialization = true; TemplateParams = TemplateParameterList::Create(Context, SourceLocation(), SourceLocation(), 0, 0, SourceLocation()); @@ -5206,18 +5206,13 @@ Sema::ActOnVariableDeclarator(Scope *S, Declarator &D, DeclContext *DC, SetNestedNameSpecifier(NewVD, D); - // FIXME: Do we need D.getCXXScopeSpec().isSet()? - if (TemplateParams && TemplateParamLists.size() > 1 && - (!IsVariableTemplateSpecialization || D.getCXXScopeSpec().isSet())) { + // If we have any template parameter lists that don't directly belong to + // the variable (matching the scope specifier), store them. + unsigned VDTemplateParamLists = TemplateParams ? 1 : 0; + if (TemplateParamLists.size() > VDTemplateParamLists) NewVD->setTemplateParameterListsInfo( - Context, TemplateParamLists.size() - 1, TemplateParamLists.data()); - } else if (IsVariableTemplateSpecialization || - (!TemplateParams && TemplateParamLists.size() > 0 && - (D.getCXXScopeSpec().isSet()))) { - NewVD->setTemplateParameterListsInfo(Context, - TemplateParamLists.size(), - TemplateParamLists.data()); - } + Context, TemplateParamLists.size() - VDTemplateParamLists, + TemplateParamLists.data()); if (D.getDeclSpec().isConstexprSpecified()) NewVD->setConstexpr(true); diff --git a/clang/test/SemaCXX/cxx1y-variable-templates_top_level.cpp b/clang/test/SemaCXX/cxx1y-variable-templates_top_level.cpp index d2c42941347..526bef00787 100644 --- a/clang/test/SemaCXX/cxx1y-variable-templates_top_level.cpp +++ b/clang/test/SemaCXX/cxx1y-variable-templates_top_level.cpp @@ -436,3 +436,8 @@ namespace nested_name { class a<int> {}; // expected-error {{identifier followed by '<' indicates a class template specialization but 'a' refers to a variable template}} enum a<int> {}; // expected-error {{expected identifier or '{'}} expected-warning {{does not declare anything}} } + +namespace PR18530 { + template<typename T> int a; + int a<int>; // expected-error {{requires 'template<>'}} +} |

