brintos

brintos / llvm-project-archived public Read only

0
0
Text · 8.6 KiB · 5e1bce5 Raw
365 lines · cpp
1// RUN: %clang_cc1 -std=c++20 -verify %s2namespace GH53213 {3template<typename T>4concept c = requires(T t) { f(t); }; // #CDEF5 6auto f(c auto); // #FDEF7 8void g() {9  f(0);10  // expected-error@-1{{no matching function for call to 'f'}}11  // expected-note@#FDEF{{constraints not satisfied}}12  // expected-note@#FDEF{{because 'int' does not satisfy 'c'}}13  // expected-note@#CDEF{{because 'f(t)' would be invalid: no matching function for call to 'f'}}14}15} // namespace GH5321316 17namespace GH45736 {18struct constrained;19 20template<typename T>21  struct type {22  };23template<typename T>24  constexpr bool f(type<T>) {25      return true;26  }27 28template<typename T>29  concept matches = f(type<T>());30 31 32struct constrained {33    template<typename U> requires matches<U>34        explicit constrained(U value) {35            }36};37 38bool f(constrained const &) {39    return true;40}41 42struct outer {43    constrained state;44};45 46bool f(outer const & x) {47    return f(x.state);48}49} // namespace GH4573650 51namespace DirectRecursiveCheck {52template<class T>53concept NotInf = true;54template<class T>55concept Inf = requires(T& v){ // #INF_REQ56  {begin(v)}; // #INF_BEGIN_EXPR57};58 59void begin(NotInf auto& v){ } // #NOTINF_BEGIN60// This lookup should fail, since it results in a recursive check.61// However, this is a 'hard failure'(not a SFINAE failure or constraints62// violation), so it needs to cause the entire lookup to fail.63void begin(Inf auto& v){ } // #INF_BEGIN64 65struct my_range{66} rng;67 68void baz() {69auto it = begin(rng); // #BEGIN_CALL70// expected-error-re@#INF_REQ {{satisfaction of constraint {{.*}} depends on itself}}71// expected-note@#INF_BEGIN {{while checking the satisfaction of concept 'Inf<DirectRecursiveCheck::my_range>' requested here}}72// expected-note@#INF_BEGIN_EXPR {{while checking constraint satisfaction for template 'begin<DirectRecursiveCheck::my_range>' required here}}73// expected-note@#INF_BEGIN_EXPR {{while substituting deduced template arguments into function template 'begin'}}74// expected-note@#INF_BEGIN_EXPR {{in instantiation of requirement here}}75// expected-note@#INF_REQ {{while substituting template arguments into constraint expression here}}76// expected-note@#INF_BEGIN {{while checking the satisfaction of concept 'Inf<struct my_range>' requested here}}77// expected-note@#BEGIN_CALL {{while checking constraint satisfaction for template 'begin<struct my_range>' required here}}78// expected-note@#BEGIN_CALL {{while substituting deduced template arguments into function template}}79 80// Fallout of the failure is failed lookup, which is necessary to stop odd81// cascading errors.82// expected-error@#BEGIN_CALL {{no matching function for call to 'begin'}}83// expected-note@#NOTINF_BEGIN {{candidate function}}84// expected-note@#INF_BEGIN{{candidate template ignored: constraints not satisfied}}85}86} // namespace DirectRecursiveCheck87 88namespace GH50891 {89  template <typename T>90  concept Numeric = requires(T a) { // #NUMERIC91      foo(a); // #FOO_CALL92    };93 94  struct Deferred {95    friend void foo(Deferred);96    template <Numeric TO> operator TO(); // #OP_TO97  };98 99  static_assert(Numeric<Deferred>); // #STATIC_ASSERT100  // expected-error@#NUMERIC{{satisfaction of constraint 'requires (T a) { foo(a); }' depends on itself}}101  // expected-note@#NUMERIC {{while substituting template arguments into constraint expression here}}102  // expected-note@#OP_TO {{while checking the satisfaction of concept 'Numeric<Deferred>' requested here}}103  // expected-note@#OP_TO {{skipping 1 context}}104  // expected-note@#FOO_CALL 2{{while checking constraint satisfaction for template}}105  // expected-note@#FOO_CALL 2{{while substituting deduced template arguments into function template}}106  // expected-note@#FOO_CALL 2{{in instantiation of requirement here}}107  // expected-note@#NUMERIC {{while substituting template arguments into constraint expression here}}108 109  // expected-error@#STATIC_ASSERT {{static assertion failed}}110  // expected-note@#STATIC_ASSERT{{while checking the satisfaction of concept 'Numeric<Deferred>' requested here}}111  // expected-note@#STATIC_ASSERT{{because 'Deferred' does not satisfy 'Numeric'}}112  // expected-note@#FOO_CALL{{because 'foo(a)' would be invalid}}113 114} // namespace GH50891115 116 117namespace GH60323 {118  // This should not diagnose, as it does not depend on itself.119  struct End {120        template<class T>121              void go(T t) { }122 123            template<class T>124                  auto endparens(T t)125                          requires requires { go(t); }126                { return go(t); }127  };128 129  struct Size {130        template<class T>131              auto go(T t)132                  { return End().endparens(t); }133 134            template<class T>135                  auto sizeparens(T t)136                          requires requires { go(t); }137                { return go(t); }138  };139 140  int f()141  {142        int i = 42;143            Size().sizeparens(i);144  }145}146 147namespace CWG2369_Regressions {148 149// https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109397150namespace GCC_103997 {151 152template<typename _type, typename _stream>153concept streamable = requires(_stream &s, _type &&v) {154  s << static_cast<_type &&>(v);155};156 157struct type_a {158  template<typename _arg>159  type_a &operator<<(_arg &&) {160    // std::clog << "type_a" << std::endl;161    return *this;162  }163};164 165struct type_b {166  type_b &operator<<(type_a const &) {167    // std::clog << "type_b" << std::endl;168    return *this;169  }170};171 172struct type_c {173  type_b b;174  template<typename _arg>175  requires streamable<_arg, type_b>176  friend type_c &operator<<(type_c &c, _arg &&a) {177    // std::clog << "type_c" << std::endl;178    c.b << static_cast<_arg &&>(a);179    return c;180  }181};182 183void foo() {184  type_a a;185  type_c c;186  a << c; // "type_a\n" (gcc gives error here)187  c << a; // "type_c\ntype_b\n"188}189 190}191 192// https://gcc.gnu.org/bugzilla/show_bug.cgi?id=108393193namespace GCC_108393 {194 195template<class>196struct iterator_traits197{};198 199template<class T>200  requires requires(T __t, T __u) { __t == __u; }201struct iterator_traits<T>202{};203 204template<class T>205concept C = requires { typename iterator_traits<T>::A; };206 207struct unreachable_sentinel_t208{209  template<C _Iter>210  friend constexpr bool operator==(unreachable_sentinel_t, const _Iter&) noexcept;211};212 213template<class T>214struct S215{};216 217static_assert(!C<S<unreachable_sentinel_t>>);218 219}220 221// https://gcc.gnu.org/bugzilla/show_bug.cgi?id=107429222namespace GCC_107429 {223 224struct tag_foo { } inline constexpr foo;225struct tag_bar { } inline constexpr bar;226 227template<typename... T>228auto f(tag_foo, T... x)229{230  return (x + ...);231}232 233template<typename... T>234concept fooable = requires (T... x) { f(foo, x...); };235 236template<typename... T> requires (fooable<T...>)237auto f(tag_bar, T... x)238{239  return f(foo, x...);240}241 242auto test()243{244  return f(bar, 1, 2, 3);245}246 247}248 249namespace GCC_99599 {250 251struct foo_tag {};252struct bar_tag {};253 254template <class T>255concept fooable = requires(T it) {256  invoke_tag(foo_tag{}, it); // <-- here257};258 259template <class T> auto invoke_tag(foo_tag, T in) { return in; }260 261template <fooable T> auto invoke_tag(bar_tag, T it) { return it; }262 263int main() {264  // Neither line below compiles in GCC 11, independently of the other265  return invoke_tag(foo_tag{}, 2) + invoke_tag(bar_tag{}, 2);266}267 268}269 270// https://gcc.gnu.org/bugzilla/show_bug.cgi?id=99599#c22271namespace GCC_99599_2 {272 273template<typename T> class indirect {274public:275  template<typename U> requires276    requires (const T& t, const U& u) { t == u; }277  friend constexpr bool operator==(const indirect&, const U&) { return false; }278 279private:280  T* _M_ptr{};281};282 283indirect<int> i;284bool b = i == 1;285 286}287 288namespace GCC_99599_3 {289 290template<typename T>291struct S { T t; };292 293template<typename T>294concept C = sizeof(S<T>) > 0;295 296struct I;297 298struct from_range_t {299    explicit from_range_t() = default;300};301inline constexpr from_range_t from_range;302 303template<typename T>304concept FromRange = __is_same_as (T, from_range_t);305 306//#define WORKAROUND307#ifdef WORKAROUND308template<FromRange U, C T>309void f(U, T*);310#else311template<C T>312void f(from_range_t, T*);313#endif314 315void f(...);316 317void g(I* p) {318  f(0, p);319}320 321}322 323namespace GCC_99599_4 {324 325struct A {326  A(...);327};328 329template <class T> void f(A, T) { }330 331int main()332{333  f(42, 24);334}335 336}337 338namespace FAILED_GCC_110160 {339// https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110160340// Current heuristic FAILED; GCC trunk also failed341// https://godbolt.org/z/r3Pz9Tehz342#if 0343#include <sstream>344#include <string>345 346template <class T>347concept StreamCanReceiveString = requires(T& t, std::string s) {348    { t << s };349};350 351struct NotAStream {};352struct UnrelatedType {};353 354template <StreamCanReceiveString S>355S& operator<<(S& s, UnrelatedType) {356    return s;357}358 359static_assert(!StreamCanReceiveString<NotAStream>);360 361static_assert(StreamCanReceiveString<std::stringstream>);362#endif363}364}365