C++ Template friend odd behavior -
i'm seeing can't explain in following code. under vs6, vs9, , gcc t2::foo2() gives error: 'bar' : cannot access protected member declared in class 'c1'. if remove c1::bar(), compiles , runs correctly, though t2 still accessing protected c1b:bar(), think same problem.
note, in t2::foo2() cast 'pt1' 't1*' , fine, still not explain why c1b::bar() allowed, c1::bar() not.
template<class s> class t2; template<class t> class t1 { //template<class t> friend class t2; --> doesn't compile under vs6 friend class t2<t>; protected: virtual void bar() { printf("t1\n"); } }; template<class s> class t2 { public: void foo1(t1<s> *pt1) { pt1->bar(); } // --> ok, makes sense, works either way void foo2(s *pt1) { pt1->bar(); } // --> fails compile if c1::bar() defined, works c1b::foo() ??? }; class c1 : public t1<c1> { protected: virtual void bar() { printf("c1\n"); } // --> comment out , foo2 compile }; class c1b : public c1 { protected: virtual void bar() { printf("c1b\n"); } }; class c2 : public t2<c1> { }; void test(void) { c1b c1b; c2 c2; c2.foo1(&c1b); c2.foo2(&c1b); // --> fails compile if c1::bar() exists }
in example, type of parameter s
in foo2
c1
. friend relationship exists between t2<s>
, t1<s>
. although c1
derives t1<c1>
not become friend of friends of t1<c1>
.
in expression pt1->bar
, bar
found in c1
and, friendship not passed down derived class, private.
your example using virtual functions can addressed explicitly referring bar
is friend of our class:
void foo2(s *pt1) { pt1->template t1<s>::bar(); }
the access check succeeds.
the reference in '03 c++ standard in 11.4/10, says:
friendship neither inherited nor transitive.
thanks potatoswatter comment. using qualified-id
id-expession
, disable virtual dispatch (5.2.2/1):
if selected function non-virtual, or if id-expression in class member access expression qualified-id, function called.
we can add non-virtual dispatcher, or can first convert parameter base type , make call:
void foo2(s *pt1) { static_cast< t1<s>* > (pt1)->bar(); }
virtual dispatch takes place required.
Comments
Post a Comment