This is the mail archive of the
gcc-bugs@gcc.gnu.org
mailing list for the GCC project.
[Bug c++/82740] New: [concepts] requires clause evaluated early
- From: "Casey at Carter dot net" <gcc-bugzilla at gcc dot gnu dot org>
- To: gcc-bugs at gcc dot gnu dot org
- Date: Thu, 26 Oct 2017 23:15:53 +0000
- Subject: [Bug c++/82740] New: [concepts] requires clause evaluated early
- Auto-submitted: auto-generated
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82740
Bug ID: 82740
Summary: [concepts] requires clause evaluated early
Product: gcc
Version: 8.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: c++
Assignee: unassigned at gcc dot gnu.org
Reporter: Casey at Carter dot net
Target Milestone: ---
Created attachment 42483
--> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42483&action=edit
Repro
Trunk as of 20170825 miscompiles this program
(https://wandbox.org/permlink/70zH8c8JMQZMDUas):
template<class T>
concept bool C = requires(const T& t) { t.foo(); };
template<class T>
struct Base {
constexpr T const& derived() const { return static_cast<T const&>(*this); }
constexpr bool bar() const requires
#ifndef WORKAROUND
requires(const T& t) { t.foo(); }
#else
C<T>
#endif
{ derived().foo(); return true; }
};
template<class T>
struct Derived : Base<Derived<T>> {
constexpr void foo() const {}
};
int main() {
static_assert(Derived<int>{}.bar());
}
with diagnostics:
prog.cc: In instantiation of 'struct Base<Derived<int> >':
prog.cc:17:8: required from 'struct Derived<int>'
prog.cc:22:32: required from here
prog.cc:9:34: error: invalid use of incomplete type 'const struct Derived<int>'
requires(const T& t) { t.foo(); }
~~^~~
prog.cc:17:8: note: declaration of 'struct Derived<int>'
struct Derived : Base<Derived<T>> {
^~~~~~~
despite that N4700 [temp.inst]/16
(http://eel.is/c++draft/temp.spec#temp.inst-16) specifies that:
The partial-concept-ids and requires-clause of a template specialization or
member function are not instantiated along with the specialization or function
itself, even for a member function of a local class; substitution into the
atomic constraints formed from them is instead performed as specified in
[temp.constr.decl] and [temp.constr.atomic] when determining whether the
constraints are satisfied. [ Note: The satisfaction of constraints is
determined during name lookup or overload resolution ([over.match]). — end note
]
(Note that the text of [temp.inst]/16 in the Concepts TS is similar.)
If WORKAROUND is defined, replacing the ad hoc requirement with an identical
named concept, the program compiles without diagnostics.