From 9d575ddba0ff55f49d10b5048c593ad3ea66f0e8 Mon Sep 17 00:00:00 2001 From: Reid Kleckner Date: Fri, 29 Apr 2016 18:06:53 +0000 Subject: [PATCH] Fix crash in BuildCXXDefaultInitExpr. Fix crash in BuildCXXDefaultInitExpr when member of template class has same name as the class itself. Based on patch by Raphael "Teemperor" Isemann! Differential Revision: http://reviews.llvm.org/D19721 git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@268082 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Sema/SemaDeclCXX.cpp | 15 +++++++++++++-- .../pr27047-default-init-expr-name-conflict.cpp | 8 ++++++++ 2 files changed, 21 insertions(+), 2 deletions(-) create mode 100644 test/SemaCXX/pr27047-default-init-expr-name-conflict.cpp diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp index 40be8d6456..21db3be3cc 100644 --- a/lib/Sema/SemaDeclCXX.cpp +++ b/lib/Sema/SemaDeclCXX.cpp @@ -11412,8 +11412,19 @@ ExprResult Sema::BuildCXXDefaultInitExpr(SourceLocation Loc, FieldDecl *Field) { CXXRecordDecl *ClassPattern = ParentRD->getTemplateInstantiationPattern(); DeclContext::lookup_result Lookup = ClassPattern->lookup(Field->getDeclName()); - assert(Lookup.size() == 1); - FieldDecl *Pattern = cast(Lookup[0]); + + // Lookup can return at most two results: the pattern for the field, or the + // injected class name of the parent record. No other member can have the + // same name as the field. + assert(!Lookup.empty() && Lookup.size() <= 2 && + "more than two lookup results for field name"); + FieldDecl *Pattern = dyn_cast(Lookup[0]); + if (!Pattern) { + assert(isa(Lookup[0]) && + "cannot have other non-field member with same name"); + Pattern = cast(Lookup[1]); + } + if (InstantiateInClassInitializer(Loc, Field, Pattern, getTemplateInstantiationArgs(Field))) return ExprError(); diff --git a/test/SemaCXX/pr27047-default-init-expr-name-conflict.cpp b/test/SemaCXX/pr27047-default-init-expr-name-conflict.cpp new file mode 100644 index 0000000000..772db9935c --- /dev/null +++ b/test/SemaCXX/pr27047-default-init-expr-name-conflict.cpp @@ -0,0 +1,8 @@ +// RUN: %clang_cc1 -fsyntax-only -std=c++11 %s + +template +struct A { + // Used to crash when field was named after class. + int A = 0; +}; +A a; -- 2.40.0