Workaround for friend template instantiation crash in PR5848, from Keir Mierle!

llvm-svn: 95517
This commit is contained in:
Douglas Gregor 2010-02-07 10:31:35 +00:00
parent b65a913c35
commit 0e027fb32b
2 changed files with 26 additions and 3 deletions

View File

@ -411,9 +411,17 @@ Decl *TemplateDeclInstantiator::VisitFriendDecl(FriendDecl *D) {
Decl *NewND; Decl *NewND;
// Hack to make this work almost well pending a rewrite. // Hack to make this work almost well pending a rewrite.
if (ND->getDeclContext()->isRecord()) if (ND->getDeclContext()->isRecord()) {
NewND = SemaRef.FindInstantiatedDecl(ND, TemplateArgs); if (!ND->getDeclContext()->isDependentContext()) {
else if (D->wasSpecialization()) { NewND = SemaRef.FindInstantiatedDecl(ND, TemplateArgs);
} else {
// FIXME: Hack to avoid crashing when incorrectly trying to instantiate
// templated friend declarations. This doesn't produce a correct AST;
// however this is sufficient for some AST analysis. The real solution
// must be put in place during the pending rewrite. See PR5848.
return 0;
}
} else if (D->wasSpecialization()) {
// Totally egregious hack to work around PR5866 // Totally egregious hack to work around PR5866
return 0; return 0;
} else } else

View File

@ -0,0 +1,15 @@
// RUN: %clang_cc1 %s
template <typename T>
struct Foo {
template <typename U>
struct Bar {};
// The templated declaration for class Bar should not be instantiated when
// Foo<int> is. This is to protect against PR5848; for now, this "parses" but
// requires a rewrite of the templated friend code to be properly fixed.
template <typename U>
friend struct Bar;
};
Foo<int> x;