PR20625: Instantiate static constexpr member function of a local struct in a function template earlier.

This is necessary in order to allow the use of a constexpr member function, or
a member function with deduced return type, of a local class within a
surrounding instantiated function template specialization.

Patch by Michael Park!

llvm-svn: 236063
This commit is contained in:
Richard Smith 2015-04-29 00:07:09 +00:00
parent 5295793bca
commit 180b92168d
2 changed files with 21 additions and 0 deletions

View File

@ -1302,11 +1302,19 @@ Decl *TemplateDeclInstantiator::VisitCXXRecordDecl(CXXRecordDecl *D) {
// DR1484 clarifies that the members of a local class are instantiated as part
// of the instantiation of their enclosing entity.
if (D->isCompleteDefinition() && D->isLocalClass()) {
Sema::SavePendingLocalImplicitInstantiationsRAII
SavedPendingLocalImplicitInstantiations(SemaRef);
SemaRef.InstantiateClass(D->getLocation(), Record, D, TemplateArgs,
TSK_ImplicitInstantiation,
/*Complain=*/true);
SemaRef.InstantiateClassMembers(D->getLocation(), Record, TemplateArgs,
TSK_ImplicitInstantiation);
// This class may have local implicit instantiations that need to be
// performed within this scope.
SemaRef.PerformPendingInstantiations(/*LocalOnly=*/true);
}
SemaRef.DiagnoseUnusedNestedTypedefs(Record);

View File

@ -213,3 +213,16 @@ namespace PR23194 {
return make_seed_pair();
}
}
namespace PR20625 {
template <typename T>
void f() {
struct N {
static constexpr int get() { return 42; }
};
constexpr int n = N::get();
static_assert(n == 42, "n == 42");
}
void g() { f<void>(); }
}