https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86646
Arthur O'Dwyer <arthur.j.odwyer at gmail dot com> changed: What |Removed |Added ---------------------------------------------------------------------------- CC| |arthur.j.odwyer at gmail dot com --- Comment #4 from Arthur O'Dwyer <arthur.j.odwyer at gmail dot com> --- I just ran into this (it's one of the examples of vendor divergence in P2953R0). https://isocpp.org/files/papers/P2953R0.html#corner-cases // https://godbolt.org/z/sxv5rvn8o template<class> struct C { C& operator=(std::add_lvalue_reference_t<const C>) = default; }; C<int> cl; GCC 13 says: error: 'C< <template-parameter-1-1> >& C< <template-parameter-1-1> >::operator=(std::add_lvalue_reference_t<const C< <template-parameter-1-1> > >)' cannot be defaulted 5 | C& operator=(std::add_lvalue_reference_t<const C>) = default; | ^~~~~~~ I confirm Andrew's observation that Clang is the odd one out in accepting this code (GCC, MSVC, EDG all reject). But it also seems pretty obvious that it should be accepted. Brian Bi concurs: "I couldn't figure out any reason why this shouldn't be valid." Or again something like this: template<bool B> struct C { C(std::conditional_t<B, const C&, C&&>) = default; C(std::conditional_t<B, C&&, const C&>); }; static_assert(std::is_trivially_copy_constructible_v<C<true>>); static_assert(std::is_trivially_move_constructible_v<C<false>>); GCC+EDG+MSVC reject; Clang accepts; and I think Clang is the conforming one. A related situation is // https://godbolt.org/z/1bhEx1Gr1 template<class... Ts> struct C { template<class T> using A = const C&; C(A<Ts>...) = default; // this is a default ctor or a copy ctor, depending on sizeof...(Ts) }; static_assert(std::is_trivially_constructible_v<C<>>); static_assert(std::is_trivially_copy_constructible_v<C<int>>); GCC rejects; Clang+EDG+MSVC accept; and I think Clang+EDG+MSVC are conforming.