summaryrefslogtreecommitdiffstats
path: root/clang
diff options
context:
space:
mode:
authorDouglas Gregor <dgregor@apple.com>2011-10-09 20:59:17 +0000
committerDouglas Gregor <dgregor@apple.com>2011-10-09 20:59:17 +0000
commite9d075e4341fd50f699b54adff57cd3efe86d4d5 (patch)
treecde0066a31bc55ff266e311b7629aa542651aadb /clang
parent668d3625030b37a340af05da9c8da0d79179698c (diff)
downloadbcm5719-llvm-e9d075e4341fd50f699b54adff57cd3efe86d4d5.tar.gz
bcm5719-llvm-e9d075e4341fd50f699b54adff57cd3efe86d4d5.zip
A friend template specialization is also dependent if any of its
template arguments are dependent. Fixes PR10913. llvm-svn: 141515
Diffstat (limited to 'clang')
-rw-r--r--clang/lib/Sema/SemaDecl.cpp6
-rw-r--r--clang/test/CXX/temp/temp.decls/temp.friend/p1.cpp24
2 files changed, 29 insertions, 1 deletions
diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp
index 451751f1430..5ba38ee9f23 100644
--- a/clang/lib/Sema/SemaDecl.cpp
+++ b/clang/lib/Sema/SemaDecl.cpp
@@ -4987,8 +4987,12 @@ Sema::ActOnFunctionDeclarator(Scope *S, Declarator &D, DeclContext *DC,
// that either the specialized function type or the specialized
// template is dependent, and therefore matching will fail. In
// this case, don't check the specialization yet.
+ bool InstantiationDependent = false;
if (isFunctionTemplateSpecialization && isFriend &&
- (NewFD->getType()->isDependentType() || DC->isDependentContext())) {
+ (NewFD->getType()->isDependentType() || DC->isDependentContext() ||
+ TemplateSpecializationType::anyDependentTemplateArguments(
+ TemplateArgs.getArgumentArray(), TemplateArgs.size(),
+ InstantiationDependent))) {
assert(HasExplicitTemplateArgs &&
"friend function specialization without template args");
if (CheckDependentFunctionTemplateSpecialization(NewFD, TemplateArgs,
diff --git a/clang/test/CXX/temp/temp.decls/temp.friend/p1.cpp b/clang/test/CXX/temp/temp.decls/temp.friend/p1.cpp
index 578de2952d9..63f569be086 100644
--- a/clang/test/CXX/temp/temp.decls/temp.friend/p1.cpp
+++ b/clang/test/CXX/temp/temp.decls/temp.friend/p1.cpp
@@ -332,3 +332,27 @@ namespace test15 {
template class B<int>; // expected-note {{in instantiation}}
}
+
+namespace PR10913 {
+ template<class T> class X;
+
+ template<class T> void f(X<T> *x) {
+ x->member = 0;
+ }
+
+ template<class U, class T> void f2(X<T> *x) {
+ x->member = 0; // expected-error{{'member' is a protected member of 'PR10913::X<int>'}}
+ }
+
+ template<class T> class X {
+ friend void f<T>(X<T> *x);
+ friend void f2<T>(X<int> *x);
+
+ protected:
+ int member; // expected-note{{declared protected here}}
+ };
+
+ template void f(X<int> *);
+ template void f2<int>(X<int> *);
+ template void f2<float>(X<int> *); // expected-note{{in instantiation of function template specialization 'PR10913::f2<float, int>' requested here}}
+}
OpenPOWER on IntegriCloud