1*f4a2713aSLionel Sambuc // RUN: %clang_cc1 -fsyntax-only -verify %s 2*f4a2713aSLionel Sambuc 3*f4a2713aSLionel Sambuc namespace test0 { 4*f4a2713aSLionel Sambuc class A { 5*f4a2713aSLionel Sambuc protected: int x; // expected-note 3 {{declared}} \ 6*f4a2713aSLionel Sambuc // expected-note {{member is declared here}} 7*f4a2713aSLionel Sambuc static int sx; // expected-note 3 {{declared}} \ 8*f4a2713aSLionel Sambuc // expected-note {{member is declared here}} 9*f4a2713aSLionel Sambuc }; 10*f4a2713aSLionel Sambuc class B : public A { 11*f4a2713aSLionel Sambuc }; 12*f4a2713aSLionel Sambuc class C : protected A { // expected-note {{declared}} 13*f4a2713aSLionel Sambuc }; 14*f4a2713aSLionel Sambuc class D : private B { // expected-note 3 {{constrained}} 15*f4a2713aSLionel Sambuc }; 16*f4a2713aSLionel Sambuc test(A & a)17*f4a2713aSLionel Sambuc void test(A &a) { 18*f4a2713aSLionel Sambuc (void) a.x; // expected-error {{'x' is a protected member}} 19*f4a2713aSLionel Sambuc (void) a.sx; // expected-error {{'sx' is a protected member}} 20*f4a2713aSLionel Sambuc } test(B & b)21*f4a2713aSLionel Sambuc void test(B &b) { 22*f4a2713aSLionel Sambuc (void) b.x; // expected-error {{'x' is a protected member}} 23*f4a2713aSLionel Sambuc (void) b.sx; // expected-error {{'sx' is a protected member}} 24*f4a2713aSLionel Sambuc } test(C & c)25*f4a2713aSLionel Sambuc void test(C &c) { 26*f4a2713aSLionel Sambuc (void) c.x; // expected-error {{'x' is a protected member}} expected-error {{protected base class}} 27*f4a2713aSLionel Sambuc (void) c.sx; // expected-error {{'sx' is a protected member}} 28*f4a2713aSLionel Sambuc } test(D & d)29*f4a2713aSLionel Sambuc void test(D &d) { 30*f4a2713aSLionel Sambuc (void) d.x; // expected-error {{'x' is a private member}} expected-error {{private base class}} 31*f4a2713aSLionel Sambuc (void) d.sx; // expected-error {{'sx' is a private member}} 32*f4a2713aSLionel Sambuc } 33*f4a2713aSLionel Sambuc } 34*f4a2713aSLionel Sambuc 35*f4a2713aSLionel Sambuc namespace test1 { 36*f4a2713aSLionel Sambuc class A { 37*f4a2713aSLionel Sambuc protected: int x; 38*f4a2713aSLionel Sambuc static int sx; 39*f4a2713aSLionel Sambuc static void test(A&); 40*f4a2713aSLionel Sambuc }; 41*f4a2713aSLionel Sambuc class B : public A { 42*f4a2713aSLionel Sambuc static void test(B&); 43*f4a2713aSLionel Sambuc }; 44*f4a2713aSLionel Sambuc class C : protected A { 45*f4a2713aSLionel Sambuc static void test(C&); 46*f4a2713aSLionel Sambuc }; 47*f4a2713aSLionel Sambuc class D : private B { 48*f4a2713aSLionel Sambuc static void test(D&); 49*f4a2713aSLionel Sambuc }; 50*f4a2713aSLionel Sambuc test(A & a)51*f4a2713aSLionel Sambuc void A::test(A &a) { 52*f4a2713aSLionel Sambuc (void) a.x; 53*f4a2713aSLionel Sambuc (void) a.sx; 54*f4a2713aSLionel Sambuc } test(B & b)55*f4a2713aSLionel Sambuc void B::test(B &b) { 56*f4a2713aSLionel Sambuc (void) b.x; 57*f4a2713aSLionel Sambuc (void) b.sx; 58*f4a2713aSLionel Sambuc } test(C & c)59*f4a2713aSLionel Sambuc void C::test(C &c) { 60*f4a2713aSLionel Sambuc (void) c.x; 61*f4a2713aSLionel Sambuc (void) c.sx; 62*f4a2713aSLionel Sambuc } test(D & d)63*f4a2713aSLionel Sambuc void D::test(D &d) { 64*f4a2713aSLionel Sambuc (void) d.x; 65*f4a2713aSLionel Sambuc (void) d.sx; 66*f4a2713aSLionel Sambuc } 67*f4a2713aSLionel Sambuc } 68*f4a2713aSLionel Sambuc 69*f4a2713aSLionel Sambuc namespace test2 { 70*f4a2713aSLionel Sambuc class A { 71*f4a2713aSLionel Sambuc protected: int x; // expected-note 3 {{can only access this member on an object of type}} 72*f4a2713aSLionel Sambuc static int sx; 73*f4a2713aSLionel Sambuc static void test(A&); 74*f4a2713aSLionel Sambuc }; 75*f4a2713aSLionel Sambuc class B : public A { 76*f4a2713aSLionel Sambuc static void test(A&); 77*f4a2713aSLionel Sambuc }; 78*f4a2713aSLionel Sambuc class C : protected A { 79*f4a2713aSLionel Sambuc static void test(A&); 80*f4a2713aSLionel Sambuc }; 81*f4a2713aSLionel Sambuc class D : private B { 82*f4a2713aSLionel Sambuc static void test(A&); 83*f4a2713aSLionel Sambuc }; 84*f4a2713aSLionel Sambuc test(A & a)85*f4a2713aSLionel Sambuc void A::test(A &a) { 86*f4a2713aSLionel Sambuc (void) a.x; 87*f4a2713aSLionel Sambuc (void) a.sx; 88*f4a2713aSLionel Sambuc } test(A & a)89*f4a2713aSLionel Sambuc void B::test(A &a) { 90*f4a2713aSLionel Sambuc (void) a.x; // expected-error {{'x' is a protected member}} 91*f4a2713aSLionel Sambuc (void) a.sx; 92*f4a2713aSLionel Sambuc } test(A & a)93*f4a2713aSLionel Sambuc void C::test(A &a) { 94*f4a2713aSLionel Sambuc (void) a.x; // expected-error {{'x' is a protected member}} 95*f4a2713aSLionel Sambuc (void) a.sx; 96*f4a2713aSLionel Sambuc } test(A & a)97*f4a2713aSLionel Sambuc void D::test(A &a) { 98*f4a2713aSLionel Sambuc (void) a.x; // expected-error {{'x' is a protected member}} 99*f4a2713aSLionel Sambuc (void) a.sx; 100*f4a2713aSLionel Sambuc } 101*f4a2713aSLionel Sambuc } 102*f4a2713aSLionel Sambuc 103*f4a2713aSLionel Sambuc namespace test3 { 104*f4a2713aSLionel Sambuc class B; 105*f4a2713aSLionel Sambuc class A { 106*f4a2713aSLionel Sambuc protected: int x; //expected-note {{declared protected}} // expected-note {{can only access this member on an object of type}} 107*f4a2713aSLionel Sambuc static int sx; 108*f4a2713aSLionel Sambuc static void test(B&); 109*f4a2713aSLionel Sambuc }; 110*f4a2713aSLionel Sambuc class B : public A { 111*f4a2713aSLionel Sambuc static void test(B&); 112*f4a2713aSLionel Sambuc }; 113*f4a2713aSLionel Sambuc class C : protected A { 114*f4a2713aSLionel Sambuc static void test(B&); 115*f4a2713aSLionel Sambuc }; 116*f4a2713aSLionel Sambuc class D : private B { 117*f4a2713aSLionel Sambuc static void test(B&); 118*f4a2713aSLionel Sambuc }; 119*f4a2713aSLionel Sambuc test(B & b)120*f4a2713aSLionel Sambuc void A::test(B &b) { 121*f4a2713aSLionel Sambuc (void) b.x; 122*f4a2713aSLionel Sambuc (void) b.sx; 123*f4a2713aSLionel Sambuc } test(B & b)124*f4a2713aSLionel Sambuc void B::test(B &b) { 125*f4a2713aSLionel Sambuc (void) b.x; 126*f4a2713aSLionel Sambuc (void) b.sx; 127*f4a2713aSLionel Sambuc } test(B & b)128*f4a2713aSLionel Sambuc void C::test(B &b) { 129*f4a2713aSLionel Sambuc (void) b.x; // expected-error {{'x' is a protected member}} 130*f4a2713aSLionel Sambuc (void) b.sx; 131*f4a2713aSLionel Sambuc } test(B & b)132*f4a2713aSLionel Sambuc void D::test(B &b) { 133*f4a2713aSLionel Sambuc (void) b.x; // expected-error {{'x' is a protected member}} 134*f4a2713aSLionel Sambuc (void) b.sx; 135*f4a2713aSLionel Sambuc } 136*f4a2713aSLionel Sambuc } 137*f4a2713aSLionel Sambuc 138*f4a2713aSLionel Sambuc namespace test4 { 139*f4a2713aSLionel Sambuc class C; 140*f4a2713aSLionel Sambuc class A { 141*f4a2713aSLionel Sambuc protected: int x; // expected-note 2{{declared protected here}} expected-note{{member is declared here}} 142*f4a2713aSLionel Sambuc static int sx; // expected-note 3{{member is declared here}} 143*f4a2713aSLionel Sambuc static void test(C&); 144*f4a2713aSLionel Sambuc }; 145*f4a2713aSLionel Sambuc class B : public A { 146*f4a2713aSLionel Sambuc static void test(C&); 147*f4a2713aSLionel Sambuc }; 148*f4a2713aSLionel Sambuc class C : protected A { // expected-note 4 {{constrained}} expected-note 3 {{declared}} 149*f4a2713aSLionel Sambuc static void test(C&); 150*f4a2713aSLionel Sambuc }; 151*f4a2713aSLionel Sambuc class D : private B { 152*f4a2713aSLionel Sambuc static void test(C&); 153*f4a2713aSLionel Sambuc }; 154*f4a2713aSLionel Sambuc test(C & c)155*f4a2713aSLionel Sambuc void A::test(C &c) { 156*f4a2713aSLionel Sambuc (void) c.x; // expected-error {{'x' is a protected member}} \ 157*f4a2713aSLionel Sambuc // expected-error {{protected base class}} 158*f4a2713aSLionel Sambuc (void) c.sx; // expected-error {{'sx' is a protected member}} 159*f4a2713aSLionel Sambuc } test(C & c)160*f4a2713aSLionel Sambuc void B::test(C &c) { 161*f4a2713aSLionel Sambuc (void) c.x; // expected-error {{'x' is a protected member}} \ 162*f4a2713aSLionel Sambuc // expected-error {{protected base class}} 163*f4a2713aSLionel Sambuc (void) c.sx; // expected-error {{'sx' is a protected member}} 164*f4a2713aSLionel Sambuc } test(C & c)165*f4a2713aSLionel Sambuc void C::test(C &c) { 166*f4a2713aSLionel Sambuc (void) c.x; 167*f4a2713aSLionel Sambuc (void) c.sx; 168*f4a2713aSLionel Sambuc } test(C & c)169*f4a2713aSLionel Sambuc void D::test(C &c) { 170*f4a2713aSLionel Sambuc (void) c.x; // expected-error {{'x' is a protected member}} \ 171*f4a2713aSLionel Sambuc // expected-error {{protected base class}} 172*f4a2713aSLionel Sambuc (void) c.sx; // expected-error {{'sx' is a protected member}} 173*f4a2713aSLionel Sambuc } 174*f4a2713aSLionel Sambuc } 175*f4a2713aSLionel Sambuc 176*f4a2713aSLionel Sambuc namespace test5 { 177*f4a2713aSLionel Sambuc class D; 178*f4a2713aSLionel Sambuc class A { 179*f4a2713aSLionel Sambuc protected: int x; // expected-note 3{{member is declared here}} 180*f4a2713aSLionel Sambuc static int sx; // expected-note 3{{member is declared here}} 181*f4a2713aSLionel Sambuc static void test(D&); 182*f4a2713aSLionel Sambuc }; 183*f4a2713aSLionel Sambuc class B : public A { 184*f4a2713aSLionel Sambuc static void test(D&); 185*f4a2713aSLionel Sambuc }; 186*f4a2713aSLionel Sambuc class C : protected A { 187*f4a2713aSLionel Sambuc static void test(D&); 188*f4a2713aSLionel Sambuc }; 189*f4a2713aSLionel Sambuc class D : private B { // expected-note 9 {{constrained}} 190*f4a2713aSLionel Sambuc static void test(D&); 191*f4a2713aSLionel Sambuc }; 192*f4a2713aSLionel Sambuc test(D & d)193*f4a2713aSLionel Sambuc void A::test(D &d) { 194*f4a2713aSLionel Sambuc (void) d.x; // expected-error {{'x' is a private member}} \ 195*f4a2713aSLionel Sambuc // expected-error {{cannot cast}} 196*f4a2713aSLionel Sambuc (void) d.sx; // expected-error {{'sx' is a private member}} 197*f4a2713aSLionel Sambuc } test(D & d)198*f4a2713aSLionel Sambuc void B::test(D &d) { 199*f4a2713aSLionel Sambuc (void) d.x; // expected-error {{'x' is a private member}} \ 200*f4a2713aSLionel Sambuc // expected-error {{cannot cast}} 201*f4a2713aSLionel Sambuc (void) d.sx; // expected-error {{'sx' is a private member}} 202*f4a2713aSLionel Sambuc } test(D & d)203*f4a2713aSLionel Sambuc void C::test(D &d) { 204*f4a2713aSLionel Sambuc (void) d.x; // expected-error {{'x' is a private member}} \ 205*f4a2713aSLionel Sambuc // expected-error {{cannot cast}} 206*f4a2713aSLionel Sambuc (void) d.sx; // expected-error {{'sx' is a private member}} 207*f4a2713aSLionel Sambuc } test(D & d)208*f4a2713aSLionel Sambuc void D::test(D &d) { 209*f4a2713aSLionel Sambuc (void) d.x; 210*f4a2713aSLionel Sambuc (void) d.sx; 211*f4a2713aSLionel Sambuc } 212*f4a2713aSLionel Sambuc } 213*f4a2713aSLionel Sambuc 214*f4a2713aSLionel Sambuc namespace test6 { 215*f4a2713aSLionel Sambuc class Static {}; 216*f4a2713aSLionel Sambuc class A { 217*f4a2713aSLionel Sambuc protected: 218*f4a2713aSLionel Sambuc void foo(int); // expected-note 3 {{can only access this member on an object of type}} 219*f4a2713aSLionel Sambuc void foo(long); 220*f4a2713aSLionel Sambuc static void foo(Static); 221*f4a2713aSLionel Sambuc 222*f4a2713aSLionel Sambuc static void test(A&); 223*f4a2713aSLionel Sambuc }; 224*f4a2713aSLionel Sambuc class B : public A { 225*f4a2713aSLionel Sambuc static void test(A&); 226*f4a2713aSLionel Sambuc }; 227*f4a2713aSLionel Sambuc class C : protected A { 228*f4a2713aSLionel Sambuc static void test(A&); 229*f4a2713aSLionel Sambuc }; 230*f4a2713aSLionel Sambuc class D : private B { 231*f4a2713aSLionel Sambuc static void test(A&); 232*f4a2713aSLionel Sambuc }; 233*f4a2713aSLionel Sambuc test(A & a)234*f4a2713aSLionel Sambuc void A::test(A &a) { 235*f4a2713aSLionel Sambuc a.foo(10); 236*f4a2713aSLionel Sambuc a.foo(Static()); 237*f4a2713aSLionel Sambuc } test(A & a)238*f4a2713aSLionel Sambuc void B::test(A &a) { 239*f4a2713aSLionel Sambuc a.foo(10); // expected-error {{'foo' is a protected member}} 240*f4a2713aSLionel Sambuc a.foo(Static()); 241*f4a2713aSLionel Sambuc } test(A & a)242*f4a2713aSLionel Sambuc void C::test(A &a) { 243*f4a2713aSLionel Sambuc a.foo(10); // expected-error {{'foo' is a protected member}} 244*f4a2713aSLionel Sambuc a.foo(Static()); 245*f4a2713aSLionel Sambuc } test(A & a)246*f4a2713aSLionel Sambuc void D::test(A &a) { 247*f4a2713aSLionel Sambuc a.foo(10); // expected-error {{'foo' is a protected member}} 248*f4a2713aSLionel Sambuc a.foo(Static()); 249*f4a2713aSLionel Sambuc } 250*f4a2713aSLionel Sambuc } 251*f4a2713aSLionel Sambuc 252*f4a2713aSLionel Sambuc namespace test7 { 253*f4a2713aSLionel Sambuc class Static {}; 254*f4a2713aSLionel Sambuc class A { 255*f4a2713aSLionel Sambuc protected: 256*f4a2713aSLionel Sambuc void foo(int); // expected-note 3 {{must name member using the type of the current context}} 257*f4a2713aSLionel Sambuc void foo(long); 258*f4a2713aSLionel Sambuc static void foo(Static); 259*f4a2713aSLionel Sambuc 260*f4a2713aSLionel Sambuc static void test(); 261*f4a2713aSLionel Sambuc }; 262*f4a2713aSLionel Sambuc class B : public A { 263*f4a2713aSLionel Sambuc static void test(); 264*f4a2713aSLionel Sambuc }; 265*f4a2713aSLionel Sambuc class C : protected A { 266*f4a2713aSLionel Sambuc static void test(); 267*f4a2713aSLionel Sambuc }; 268*f4a2713aSLionel Sambuc class D : private B { 269*f4a2713aSLionel Sambuc static void test(); 270*f4a2713aSLionel Sambuc }; 271*f4a2713aSLionel Sambuc test()272*f4a2713aSLionel Sambuc void A::test() { 273*f4a2713aSLionel Sambuc void (A::*x)(int) = &A::foo; 274*f4a2713aSLionel Sambuc void (*sx)(Static) = &A::foo; 275*f4a2713aSLionel Sambuc } test()276*f4a2713aSLionel Sambuc void B::test() { 277*f4a2713aSLionel Sambuc void (A::*x)(int) = &A::foo; // expected-error {{'foo' is a protected member}} 278*f4a2713aSLionel Sambuc void (*sx)(Static) = &A::foo; 279*f4a2713aSLionel Sambuc } test()280*f4a2713aSLionel Sambuc void C::test() { 281*f4a2713aSLionel Sambuc void (A::*x)(int) = &A::foo; // expected-error {{'foo' is a protected member}} 282*f4a2713aSLionel Sambuc void (*sx)(Static) = &A::foo; 283*f4a2713aSLionel Sambuc } test()284*f4a2713aSLionel Sambuc void D::test() { 285*f4a2713aSLionel Sambuc void (A::*x)(int) = &A::foo; // expected-error {{'foo' is a protected member}} 286*f4a2713aSLionel Sambuc void (*sx)(Static) = &A::foo; 287*f4a2713aSLionel Sambuc } 288*f4a2713aSLionel Sambuc } 289*f4a2713aSLionel Sambuc 290*f4a2713aSLionel Sambuc namespace test8 { 291*f4a2713aSLionel Sambuc class Static {}; 292*f4a2713aSLionel Sambuc class A { 293*f4a2713aSLionel Sambuc protected: 294*f4a2713aSLionel Sambuc void foo(int); // expected-note 3 {{must name member using the type of the current context}} 295*f4a2713aSLionel Sambuc void foo(long); 296*f4a2713aSLionel Sambuc static void foo(Static); 297*f4a2713aSLionel Sambuc 298*f4a2713aSLionel Sambuc static void test(); 299*f4a2713aSLionel Sambuc }; 300*f4a2713aSLionel Sambuc class B : public A { 301*f4a2713aSLionel Sambuc static void test(); 302*f4a2713aSLionel Sambuc }; 303*f4a2713aSLionel Sambuc class C : protected A { 304*f4a2713aSLionel Sambuc static void test(); 305*f4a2713aSLionel Sambuc }; 306*f4a2713aSLionel Sambuc class D : private B { 307*f4a2713aSLionel Sambuc static void test(); 308*f4a2713aSLionel Sambuc }; 309*f4a2713aSLionel Sambuc void call(void (A::*)(int)); 310*f4a2713aSLionel Sambuc void calls(void (*)(Static)); 311*f4a2713aSLionel Sambuc test()312*f4a2713aSLionel Sambuc void A::test() { 313*f4a2713aSLionel Sambuc call(&A::foo); 314*f4a2713aSLionel Sambuc calls(&A::foo); 315*f4a2713aSLionel Sambuc } test()316*f4a2713aSLionel Sambuc void B::test() { 317*f4a2713aSLionel Sambuc call(&A::foo); // expected-error {{'foo' is a protected member}} 318*f4a2713aSLionel Sambuc calls(&A::foo); 319*f4a2713aSLionel Sambuc } test()320*f4a2713aSLionel Sambuc void C::test() { 321*f4a2713aSLionel Sambuc call(&A::foo); // expected-error {{'foo' is a protected member}} 322*f4a2713aSLionel Sambuc calls(&A::foo); 323*f4a2713aSLionel Sambuc } test()324*f4a2713aSLionel Sambuc void D::test() { 325*f4a2713aSLionel Sambuc call(&A::foo); // expected-error {{'foo' is a protected member}} 326*f4a2713aSLionel Sambuc calls(&A::foo); 327*f4a2713aSLionel Sambuc } 328*f4a2713aSLionel Sambuc } 329*f4a2713aSLionel Sambuc 330*f4a2713aSLionel Sambuc namespace test9 { 331*f4a2713aSLionel Sambuc class A { // expected-note {{member is declared here}} 332*f4a2713aSLionel Sambuc protected: int foo(); // expected-note 4 {{declared}} expected-note 3 {{can only access this member on an object of type}} expected-note 2 {{member is declared here}} 333*f4a2713aSLionel Sambuc }; 334*f4a2713aSLionel Sambuc 335*f4a2713aSLionel Sambuc class B : public A { // expected-note {{member is declared here}} 336*f4a2713aSLionel Sambuc friend class D; 337*f4a2713aSLionel Sambuc }; 338*f4a2713aSLionel Sambuc 339*f4a2713aSLionel Sambuc class C : protected B { // expected-note {{declared}} \ 340*f4a2713aSLionel Sambuc // expected-note 9 {{constrained}} 341*f4a2713aSLionel Sambuc }; 342*f4a2713aSLionel Sambuc 343*f4a2713aSLionel Sambuc class D : public A { test(A & a)344*f4a2713aSLionel Sambuc static void test(A &a) { 345*f4a2713aSLionel Sambuc a.foo(); // expected-error {{'foo' is a protected member}} 346*f4a2713aSLionel Sambuc a.A::foo(); // expected-error {{'foo' is a protected member}} 347*f4a2713aSLionel Sambuc a.B::foo(); // expected-error {{'foo' is a protected member}} 348*f4a2713aSLionel Sambuc a.C::foo(); // expected-error {{'foo' is a protected member}} 349*f4a2713aSLionel Sambuc a.D::foo(); // expected-error {{'foo' is a protected member}} 350*f4a2713aSLionel Sambuc } 351*f4a2713aSLionel Sambuc test(B & b)352*f4a2713aSLionel Sambuc static void test(B &b) { 353*f4a2713aSLionel Sambuc b.foo(); 354*f4a2713aSLionel Sambuc b.A::foo(); 355*f4a2713aSLionel Sambuc b.B::foo(); // accessible as named in A 356*f4a2713aSLionel Sambuc b.C::foo(); // expected-error {{'foo' is a protected member}} 357*f4a2713aSLionel Sambuc } 358*f4a2713aSLionel Sambuc test(C & c)359*f4a2713aSLionel Sambuc static void test(C &c) { 360*f4a2713aSLionel Sambuc c.foo(); // expected-error {{'foo' is a protected member}} \ 361*f4a2713aSLionel Sambuc // expected-error {{cannot cast}} 362*f4a2713aSLionel Sambuc c.A::foo(); // expected-error {{'A' is a protected member}} \ 363*f4a2713aSLionel Sambuc // expected-error {{cannot cast}} 364*f4a2713aSLionel Sambuc c.B::foo(); // expected-error {{'B' is a protected member}} \ 365*f4a2713aSLionel Sambuc // expected-error {{cannot cast}} 366*f4a2713aSLionel Sambuc c.C::foo(); // expected-error {{'foo' is a protected member}} \ 367*f4a2713aSLionel Sambuc // expected-error {{cannot cast}} 368*f4a2713aSLionel Sambuc } 369*f4a2713aSLionel Sambuc test(D & d)370*f4a2713aSLionel Sambuc static void test(D &d) { 371*f4a2713aSLionel Sambuc d.foo(); 372*f4a2713aSLionel Sambuc d.A::foo(); 373*f4a2713aSLionel Sambuc d.B::foo(); 374*f4a2713aSLionel Sambuc d.C::foo(); // expected-error {{'foo' is a protected member}} 375*f4a2713aSLionel Sambuc } 376*f4a2713aSLionel Sambuc }; 377*f4a2713aSLionel Sambuc } 378*f4a2713aSLionel Sambuc 379*f4a2713aSLionel Sambuc namespace test10 { 380*f4a2713aSLionel Sambuc template<typename T> class A { 381*f4a2713aSLionel Sambuc protected: 382*f4a2713aSLionel Sambuc int foo(); 383*f4a2713aSLionel Sambuc int foo() const; 384*f4a2713aSLionel Sambuc ~A()385*f4a2713aSLionel Sambuc ~A() { foo(); } 386*f4a2713aSLionel Sambuc }; 387*f4a2713aSLionel Sambuc 388*f4a2713aSLionel Sambuc template class A<int>; 389*f4a2713aSLionel Sambuc } 390*f4a2713aSLionel Sambuc 391*f4a2713aSLionel Sambuc // rdar://problem/8360285: class.protected friendship 392*f4a2713aSLionel Sambuc namespace test11 { 393*f4a2713aSLionel Sambuc class A { 394*f4a2713aSLionel Sambuc protected: 395*f4a2713aSLionel Sambuc int foo(); 396*f4a2713aSLionel Sambuc }; 397*f4a2713aSLionel Sambuc 398*f4a2713aSLionel Sambuc class B : public A { 399*f4a2713aSLionel Sambuc friend class C; 400*f4a2713aSLionel Sambuc }; 401*f4a2713aSLionel Sambuc 402*f4a2713aSLionel Sambuc class C { test()403*f4a2713aSLionel Sambuc void test() { 404*f4a2713aSLionel Sambuc B b; 405*f4a2713aSLionel Sambuc b.A::foo(); 406*f4a2713aSLionel Sambuc } 407*f4a2713aSLionel Sambuc }; 408*f4a2713aSLionel Sambuc } 409*f4a2713aSLionel Sambuc 410*f4a2713aSLionel Sambuc // This friendship is considered because a public member of A would be 411*f4a2713aSLionel Sambuc // a private member of C. 412*f4a2713aSLionel Sambuc namespace test12 { 413*f4a2713aSLionel Sambuc class A { protected: int foo(); }; 414*f4a2713aSLionel Sambuc class B : public virtual A {}; 415*f4a2713aSLionel Sambuc class C : private B { friend void test(); }; 416*f4a2713aSLionel Sambuc class D : private C, public virtual A {}; 417*f4a2713aSLionel Sambuc test()418*f4a2713aSLionel Sambuc void test() { 419*f4a2713aSLionel Sambuc D d; 420*f4a2713aSLionel Sambuc d.A::foo(); 421*f4a2713aSLionel Sambuc } 422*f4a2713aSLionel Sambuc } 423*f4a2713aSLionel Sambuc 424*f4a2713aSLionel Sambuc // This friendship is not considered because a public member of A is 425*f4a2713aSLionel Sambuc // inaccessible in C. 426*f4a2713aSLionel Sambuc namespace test13 { 427*f4a2713aSLionel Sambuc class A { protected: int foo(); }; // expected-note {{declared protected here}} 428*f4a2713aSLionel Sambuc class B : private virtual A {}; 429*f4a2713aSLionel Sambuc class C : private B { friend void test(); }; 430*f4a2713aSLionel Sambuc class D : public virtual A {}; 431*f4a2713aSLionel Sambuc test()432*f4a2713aSLionel Sambuc void test() { 433*f4a2713aSLionel Sambuc D d; 434*f4a2713aSLionel Sambuc d.A::foo(); // expected-error {{protected member}} 435*f4a2713aSLionel Sambuc } 436*f4a2713aSLionel Sambuc } 437*f4a2713aSLionel Sambuc 438*f4a2713aSLionel Sambuc // PR8058 439*f4a2713aSLionel Sambuc namespace test14 { 440*f4a2713aSLionel Sambuc class A { 441*f4a2713aSLionel Sambuc protected: 442*f4a2713aSLionel Sambuc template <class T> void temp(T t); // expected-note {{must name member using the type of the current context}} 443*f4a2713aSLionel Sambuc 444*f4a2713aSLionel Sambuc void nontemp(int); // expected-note {{must name member using the type of the current context}} 445*f4a2713aSLionel Sambuc 446*f4a2713aSLionel Sambuc template <class T> void ovl_temp(T t); // expected-note {{must name member using the type of the current context}} 447*f4a2713aSLionel Sambuc void ovl_temp(float); 448*f4a2713aSLionel Sambuc 449*f4a2713aSLionel Sambuc void ovl_nontemp(int); // expected-note {{must name member using the type of the current context}} 450*f4a2713aSLionel Sambuc void ovl_nontemp(float); 451*f4a2713aSLionel Sambuc 452*f4a2713aSLionel Sambuc template <class T> void ovl_withtemp(T); 453*f4a2713aSLionel Sambuc void ovl_withtemp(int); // expected-note {{must name member using the type of the current context}} 454*f4a2713aSLionel Sambuc }; 455*f4a2713aSLionel Sambuc 456*f4a2713aSLionel Sambuc class B : public A { use()457*f4a2713aSLionel Sambuc void use() { 458*f4a2713aSLionel Sambuc void (A::*ptr)(int); 459*f4a2713aSLionel Sambuc ptr = &A::temp; // expected-error {{protected member}} 460*f4a2713aSLionel Sambuc ptr = &A::nontemp; // expected-error {{protected member}} 461*f4a2713aSLionel Sambuc ptr = &A::ovl_temp; // expected-error {{protected member}} 462*f4a2713aSLionel Sambuc ptr = &A::ovl_nontemp; // expected-error {{protected member}} 463*f4a2713aSLionel Sambuc ptr = &A::ovl_withtemp; // expected-error {{protected member}} 464*f4a2713aSLionel Sambuc } 465*f4a2713aSLionel Sambuc }; 466*f4a2713aSLionel Sambuc } 467*f4a2713aSLionel Sambuc 468*f4a2713aSLionel Sambuc namespace test15 { 469*f4a2713aSLionel Sambuc class A { 470*f4a2713aSLionel Sambuc protected: 471*f4a2713aSLionel Sambuc A(); // expected-note 2 {{protected constructor can only be used to construct a base class subobject}} 472*f4a2713aSLionel Sambuc A(const A &); // expected-note {{protected constructor can only be used to construct a base class subobject}} 473*f4a2713aSLionel Sambuc ~A(); // expected-note 3 {{protected destructor can only be used to destroy a base class subobject}} 474*f4a2713aSLionel Sambuc }; 475*f4a2713aSLionel Sambuc 476*f4a2713aSLionel Sambuc class B : public A { 477*f4a2713aSLionel Sambuc // The uses here are fine. B()478*f4a2713aSLionel Sambuc B() {} B(int i)479*f4a2713aSLionel Sambuc B(int i) : A() {} ~B()480*f4a2713aSLionel Sambuc ~B() {} 481*f4a2713aSLionel Sambuc 482*f4a2713aSLionel Sambuc // All these uses are bad. 483*f4a2713aSLionel Sambuc test0()484*f4a2713aSLionel Sambuc void test0() { 485*f4a2713aSLionel Sambuc A a; // expected-error {{protected constructor}} expected-error {{protected destructor}} 486*f4a2713aSLionel Sambuc } 487*f4a2713aSLionel Sambuc test1()488*f4a2713aSLionel Sambuc A *test1() { 489*f4a2713aSLionel Sambuc return new A(); // expected-error {{protected constructor}} 490*f4a2713aSLionel Sambuc } 491*f4a2713aSLionel Sambuc test2(A * a)492*f4a2713aSLionel Sambuc void test2(A *a) { 493*f4a2713aSLionel Sambuc delete a; // expected-error {{protected destructor}} 494*f4a2713aSLionel Sambuc } 495*f4a2713aSLionel Sambuc test3(A * a)496*f4a2713aSLionel Sambuc A test3(A *a) { 497*f4a2713aSLionel Sambuc return *a; // expected-error {{protected constructor}} 498*f4a2713aSLionel Sambuc } 499*f4a2713aSLionel Sambuc test4(A * a)500*f4a2713aSLionel Sambuc void test4(A *a) { 501*f4a2713aSLionel Sambuc a->~A(); // expected-error {{protected member}} 502*f4a2713aSLionel Sambuc } 503*f4a2713aSLionel Sambuc }; 504*f4a2713aSLionel Sambuc } 505*f4a2713aSLionel Sambuc 506*f4a2713aSLionel Sambuc namespace test16 { 507*f4a2713aSLionel Sambuc class A { 508*f4a2713aSLionel Sambuc protected: 509*f4a2713aSLionel Sambuc ~A(); 510*f4a2713aSLionel Sambuc }; 511*f4a2713aSLionel Sambuc 512*f4a2713aSLionel Sambuc class B : public virtual A { 513*f4a2713aSLionel Sambuc public: ~B()514*f4a2713aSLionel Sambuc ~B() {} 515*f4a2713aSLionel Sambuc }; 516*f4a2713aSLionel Sambuc 517*f4a2713aSLionel Sambuc class C : public B { ~C()518*f4a2713aSLionel Sambuc ~C() {} 519*f4a2713aSLionel Sambuc }; 520*f4a2713aSLionel Sambuc } 521