The effective context of a friend function is its lexical

context. Fixes PR9103.

llvm-svn: 141520
This commit is contained in:
Douglas Gregor 2011-10-09 22:38:36 +00:00
parent f892c7fe60
commit 56636589ff
3 changed files with 19 additions and 2 deletions

View File

@ -103,7 +103,11 @@ struct EffectiveContext {
} else if (isa<FunctionDecl>(DC)) {
FunctionDecl *Function = cast<FunctionDecl>(DC)->getCanonicalDecl();
Functions.push_back(Function);
DC = Function->getDeclContext();
if (Function->getFriendObjectKind())
DC = Function->getLexicalDeclContext();
else
DC = Function->getDeclContext();
} else if (DC->isFileContext()) {
break;
} else {

View File

@ -341,3 +341,16 @@ namespace test12 {
void *var = static_cast<B*>(this)->mem;
}
}
namespace PR9103 {
struct base {
protected:
static void foo(void) {}
};
struct cls: base {
friend void bar(void) {
base::foo();
}
};
}

View File

@ -423,7 +423,7 @@ namespace test12 {
// This friendship is not considered because a public member of A is
// inaccessible in C.
namespace test13 {
class A { protected: int foo(); }; // expected-note {{declared protected here}}
class A { protected: int foo(); }; // expected-note {{object type 'test13::D' must derive from context type 'test13::C'}}
class B : private virtual A {};
class C : private B { friend void test(); };
class D : public virtual A {};