[clang] Implement lifetime analysis for lifetime_capture_by(X) (#115921)
[llvm-project.git] / clang / test / SemaTemplate / pr52970.cpp
blob7aac5ee8565934919b71d0ffca9c798b90b56bbb
1 // RUN: %clang_cc1 -fsyntax-only -std=c++11 -verify %s
2 // RUN: %clang_cc1 -fsyntax-only -std=c++14 -verify %s
3 // RUN: %clang_cc1 -fsyntax-only -std=c++17 -verify %s
4 // RUN: %clang_cc1 -fsyntax-only -std=c++20 -verify=cxx20 %s
5 // expected-no-diagnostics
7 struct Incomplete;
8 template <class T> struct Holder { T t; };
10 namespace DotFollowingFunctionName {
11 struct Good {
12 struct Nested {
13 int b;
14 } a;
17 struct Bad {
18 Holder<Incomplete> a();
21 template <class T>
22 constexpr auto f(T t) -> decltype((t.a.b, true)) { return true; }
23 constexpr bool f(...) { return false; }
25 static_assert(DotFollowingFunctionName::f(Good{}), "");
26 static_assert(!DotFollowingFunctionName::f(Bad{}), "");
28 #if __cplusplus >= 202002L
29 template <class T>
30 concept C = requires(T t) { t.a.b; };
31 // cxx20-note@-1 {{because 't.a.b' would be invalid: reference to non-static member function must be called}}
33 static_assert(C<Good>);
34 static_assert(!C<Bad>);
35 static_assert(C<Bad>); // cxx20-error {{static assertion failed}}
36 // cxx20-note@-1 {{because 'Bad' does not satisfy 'C'}}
37 #endif
38 } // namespace DotFollowingFunctionName
40 namespace DotFollowingPointer {
41 struct Good {
42 int begin();
44 using Bad = Holder<Incomplete> *;
46 template <class T>
47 constexpr auto f(T t) -> decltype((t.begin(), true)) { return true; }
48 constexpr bool f(...) { return false; }
50 static_assert(DotFollowingPointer::f(Good{}), "");
51 static_assert(!DotFollowingPointer::f(Bad{}), "");
53 #if __cplusplus >= 202002L
54 template <class T>
55 concept C = requires(T t) { t.begin(); };
56 // cxx20-note@-1 {{because 't.begin()' would be invalid: member reference type 'Holder<Incomplete> *' is a pointer}}
58 static_assert(C<Good>);
59 static_assert(!C<Bad>);
60 static_assert(C<Bad>); // cxx20-error {{static assertion failed}}
61 // cxx20-note@-1 {{because 'Bad' (aka 'Holder<Incomplete> *') does not satisfy 'C'}}
62 #endif
63 } // namespace DotFollowingPointer