157 lines · cpp
1// RUN: %clang_cc1 -fsyntax-only -verify -std=c++2c %s2 3struct A;4struct B;5struct C;6 7struct S {};8template <typename> struct TS {};9 10template <typename ...Pack>11class X {12 friend Pack...;13 static void f() { } // expected-note {{declared private here}}14};15 16class Y {17 friend A, B, C;18 static void g() { } // expected-note {{declared private here}}19};20 21struct A {22 A() {23 X<A>::f();24 Y::g();25 };26};27 28struct B {29 B() {30 X<B, C>::f();31 Y::g();32 };33};34 35struct C {36 C() {37 X<A, B, C>::f();38 Y::g();39 };40};41 42struct D {43 D() {44 X<A, B, C>::f(); // expected-error {{'f' is a private member of 'X<A, B, C>'}}45 Y::g(); // expected-error {{'g' is a private member of 'Y'}}46 };47};48 49void f1() {50 A a;51 B b;52 C c;53 D d;54}55 56template <typename ...Pack>57struct Z {58 template <template <typename> class Template>59 struct Inner {60 friend Template<Pack>...;61 };62};63 64void f2() {65 Z<int, long, char> z;66 Z<int, long, char>::Inner<TS> inner;67}68 69namespace p2893r3_examples {70template<class... Ts>71class Passkey {72 friend Ts...;73 Passkey() {} // expected-note {{declared private here}}74};75 76class Foo;77class Bar;78class Baz;79 80class C {81public:82 void f(Passkey<Foo, Bar, Baz>);83};84 85class Foo {86 Foo() { C c; c.f({}); }87};88 89class Bar {90 Bar() { C c; c.f({}); }91};92 93class Baz {94 Baz() { C c; c.f({}); }95};96 97class Quux {98 Quux() { C c; c.f({}); } // expected-error {{calling a private constructor of class 'p2893r3_examples::Passkey<p2893r3_examples::Foo, p2893r3_examples::Bar, p2893r3_examples::Baz>'}}99};100 101template<class Derived, class MsgT>102struct Receiver {103 void receive(MsgT) {104 static_cast<Derived*>(this)->private_ += 1;105 }106};107 108template<class... MsgTs>109struct Dispatcher : Receiver<Dispatcher<MsgTs...>, MsgTs>... {110 using Receiver<Dispatcher, MsgTs>::receive...;111 friend Receiver<Dispatcher, MsgTs>...;112 113private:114 int private_;115};116 117void f() {118 Dispatcher<int, float> d;119 d.receive(0);120 d.receive(0.0f);121}122} // namespace p2893r3_examples123 124namespace p2893r3_note {125template <class... Ts> class R {126 friend Ts...;127};128 129template <class... Ts, class... Us>130class R<R<Ts...>, R<Us...>> {131 friend Ts::Nested..., Us...;132};133 134struct E { struct Nested; };135R<R<E>, R<C, int>> rr;136} // namespace p2893r3_note137 138namespace template_template {139template <typename U, template <typename> typename... Friend>140class S {141 friend class Friend<U>...;142 static constexpr int a = 42;143};144 145template <typename U>146struct T {147 static_assert(S<U, T>::a == 42);148 static_assert(S<U, T>::a == 43); // expected-error {{static assertion failed due to requirement 'template_template::S<int, template_template::T>::a == 43'}} \149 // expected-note {{expression evaluates to '42 == 43'}}150};151 152void f() {153 T<int> t; // expected-note {{in instantiation of}}154}155}156 157