Message ID | 20240219143942.680773-1-ppalka@redhat.com |
---|---|
State | New |
Headers | show |
Series | c++: compound-requirement partial substitution [PR113966] | expand |
On 2/19/24 09:39, Patrick Palka wrote: > Bootstrapped and regtested on x86_64-pc-linux-gnu, does this look OK for > trunk? OK. > -- >8 -- > > When partially substituting a requires-expr, we don't want to perform > any additional checks beyond the substitution itself, so as to minimize > checking requirements out of order. So when partially substituting > a compound-requirement don't check its return-type-requirement. Don't > check the noexcept condition either since we can't do that on templated > trees. > > PR c++/113966 > > gcc/cp/ChangeLog: > > * constraint.cc (tsubst_compound_requirement): Don't check > the noexcept condition or the return-type-requirement when > partially substituting. > > gcc/testsuite/ChangeLog: > > * g++.dg/cpp2a/concepts-friend17.C: New test. > --- > gcc/cp/constraint.cc | 5 +++-- > gcc/testsuite/g++.dg/cpp2a/concepts-friend17.C | 15 +++++++++++++++ > 2 files changed, 18 insertions(+), 2 deletions(-) > create mode 100644 gcc/testsuite/g++.dg/cpp2a/concepts-friend17.C > > diff --git a/gcc/cp/constraint.cc b/gcc/cp/constraint.cc > index d9569013bd3..49de3211d4c 100644 > --- a/gcc/cp/constraint.cc > +++ b/gcc/cp/constraint.cc > @@ -2134,7 +2134,8 @@ tsubst_compound_requirement (tree t, tree args, sat_info info) > > /* Check the noexcept condition. */ > bool noexcept_p = COMPOUND_REQ_NOEXCEPT_P (t); > - if (noexcept_p && !expr_noexcept_p (expr, quiet.complain)) > + if (noexcept_p && !processing_template_decl > + && !expr_noexcept_p (expr, quiet.complain)) > { > if (info.diagnose_unsatisfaction_p ()) > inform (loc, "%qE is not %<noexcept%>", expr); > @@ -2148,7 +2149,7 @@ tsubst_compound_requirement (tree t, tree args, sat_info info) > return error_mark_node; > > /* Check expression against the result type. */ > - if (type) > + if (type && !processing_template_decl) > { > if (tree placeholder = type_uses_auto (type)) > { > diff --git a/gcc/testsuite/g++.dg/cpp2a/concepts-friend17.C b/gcc/testsuite/g++.dg/cpp2a/concepts-friend17.C > new file mode 100644 > index 00000000000..9b5091f14a8 > --- /dev/null > +++ b/gcc/testsuite/g++.dg/cpp2a/concepts-friend17.C > @@ -0,0 +1,15 @@ > +// PR c++/113966 > +// { dg-do compile { target c++20 } } > + > +template<class T> concept C = T::value; > + > +template<class T> > +struct A { > + template<class U> requires U::value || requires { { T() } -> C; } > + friend void f(A, U) { } > + > + template<class U> requires requires { { g(U()) } noexcept; } > + friend void f(A, U, U) { } > +}; > + > +template struct A<int>;
diff --git a/gcc/cp/constraint.cc b/gcc/cp/constraint.cc index d9569013bd3..49de3211d4c 100644 --- a/gcc/cp/constraint.cc +++ b/gcc/cp/constraint.cc @@ -2134,7 +2134,8 @@ tsubst_compound_requirement (tree t, tree args, sat_info info) /* Check the noexcept condition. */ bool noexcept_p = COMPOUND_REQ_NOEXCEPT_P (t); - if (noexcept_p && !expr_noexcept_p (expr, quiet.complain)) + if (noexcept_p && !processing_template_decl + && !expr_noexcept_p (expr, quiet.complain)) { if (info.diagnose_unsatisfaction_p ()) inform (loc, "%qE is not %<noexcept%>", expr); @@ -2148,7 +2149,7 @@ tsubst_compound_requirement (tree t, tree args, sat_info info) return error_mark_node; /* Check expression against the result type. */ - if (type) + if (type && !processing_template_decl) { if (tree placeholder = type_uses_auto (type)) { diff --git a/gcc/testsuite/g++.dg/cpp2a/concepts-friend17.C b/gcc/testsuite/g++.dg/cpp2a/concepts-friend17.C new file mode 100644 index 00000000000..9b5091f14a8 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp2a/concepts-friend17.C @@ -0,0 +1,15 @@ +// PR c++/113966 +// { dg-do compile { target c++20 } } + +template<class T> concept C = T::value; + +template<class T> +struct A { + template<class U> requires U::value || requires { { T() } -> C; } + friend void f(A, U) { } + + template<class U> requires requires { { g(U()) } noexcept; } + friend void f(A, U, U) { } +}; + +template struct A<int>;