[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 Jonathan Wakely changed: What|Removed |Added Status|UNCONFIRMED |NEW Last reconfirmed||2018-03-12 Ever confirmed|0 |1 --- Comment #1 from Jonathan Wakely --- Reduced: struct c { static constexpr bool value = false; }; template a declval(); template () = 1)> // #1 void h(int); template c h(...); template using i = decltype(h(0)); struct k { k(const k &) = default; void operator=(k &&) = delete; }; struct l : k { using k::operator=; // #2 }; struct G { G(const G &); l q; }; int j = i::value; G::G(const G &) = default; x.cc:28:1: note: ‘G::G(const G&)’ is implicitly deleted because the default definition would be ill-formed: G::G(const G &) = default; ^ x.cc:28:1: error: use of deleted function ‘constexpr l::l(const l&)’ x.cc:17:7: note: ‘constexpr l::l(const l&)’ is implicitly declared as deleted because ‘l’ declares a move constructor or move assignment operator class l : k { ^ The error is malformed for a start, we issue a note that doesn't follow any error. There seem to be two things involved here. The error is apparently triggered by the SFINAE check at #1 which should silently fail instead of giving an error. It seems to be an error because of the "using k::operator=;" line at #2 which should have no effect.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #2 from Jonathan Wakely --- Slight correction: the using-declaration doesn't have no effect in general, but it shouldn't change the result of this program.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 Raphael Kubo da Costa changed: What|Removed |Added CC||raphael.kubo.da.costa@intel ||.com --- Comment #3 from Raphael Kubo da Costa --- Given the file name used in the original report and how this bug was mentioned in the chromium-packager mailing list, I think this is a duplicate of bug 70431.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #4 from Jonathan Wakely --- They don't look like duplicates to me. PR 70431 involves a union, no SFINAE, and a completely different error message.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #5 from Raphael Kubo da Costa --- Sorry if my comment was too coarse-grained. My hypothesis that this is a duplicate comes from playback_image_provider.ii looking like Chromium's playback_image_provider.cc, which was failing to build with GCC when a copy constructor was not defined inline (just like the union from bug 70431). My reduced testcase from the original Chromium code (without templates) looks like this: - struct S1 { S1& operator=(const S1&) = default; S1& operator=(S1&&) = default; }; struct S2 { S2() = default; S2(const S2&); S1 m; }; S2::S2(const S2&) = default; - x.cc:12:1: note: ‘S2::S2(const S2&)’ is implicitly deleted because the default definition would be ill-formed: S2::S2(const S2&) = default; ^~ x.cc:12:1: error: use of deleted function ‘constexpr S1::S1(const S1&)’ x.cc:1:8: note: ‘constexpr S1::S1(const S1&)’ is implicitly declared as deleted because ‘S1’ declares a move constructor or move assignment operator struct S1 { ^~ The error goes away if S2's copy constructor is declared inline.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #6 from Jonathan Wakely --- (In reply to Raphael Kubo da Costa from comment #5) > Sorry if my comment was too coarse-grained. My hypothesis that this is a > duplicate comes from playback_image_provider.ii looking like Chromium's > playback_image_provider.cc, which was failing to build with GCC when a copy > constructor was not defined inline (just like the union from bug 70431). Not every example with a non-inline copy constructor is the same though. > My reduced testcase from the original Chromium code (without templates) > looks like this: > > - > struct S1 { > S1& operator=(const S1&) = default; > S1& operator=(S1&&) = default; > }; > > struct S2 { > S2() = default; > S2(const S2&); > S1 m; > }; > > S2::S2(const S2&) = default; > - > > x.cc:12:1: note: ‘S2::S2(const S2&)’ is implicitly deleted because the > default definition would be ill-formed: > S2::S2(const S2&) = default; > ^~ > x.cc:12:1: error: use of deleted function ‘constexpr S1::S1(const S1&)’ > x.cc:1:8: note: ‘constexpr S1::S1(const S1&)’ is implicitly declared as > deleted because ‘S1’ declares a move constructor or move assignment operator > struct S1 { > ^~ > > The error goes away if S2's copy constructor is declared inline. Because that's what the C++ standard requires. A copy constructor that is defined as defaulted outside the class body is ill-formed if it would be implicitly deleted. If it's defaulted on its first declaration (i.e. inside the class body) then it is defined as deleted. Your example is not valid, and is rejected by GCC and Clang and EDG.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #7 from Raphael Kubo da Costa --- (In reply to Jonathan Wakely from comment #6) > Your example is not valid, and is rejected by GCC and Clang and EDG. Ugh, I forgot to test it with clang before posting my comment. I stand corrected. Is it relevant that your testcase builds fine when G's copy constructor is inlined?
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #8 from Jonathan Wakely --- (In reply to Raphael Kubo da Costa from comment #7) > Is it relevant that your testcase builds fine when G's copy constructor is > inlined? Yes, it seems to be. The checks done for the out-of-class defaulted definition fail for bogus reasons.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #9 from Martin Liška --- I can confirm that the PR is blocking Chromium build in openSUSE. Do I understand that correctly Jonathan that it's an issue in GCC? Or is it an invalid code snippet?
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #10 from Raphael Kubo da Costa --- (In reply to Martin Liška from comment #9) > I can confirm that the PR is blocking Chromium build in openSUSE. >From a Chromium perspective (where I'm coming from), it shouldn't be. The problematic bits were changed in Chromium in https://chromium-review.googlesource.com/c/chromium/src/+/944403 because of this bug and the commit just be backported to unblock your package builds.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #11 from Jonathan Wakely --- (In reply to Martin Liška from comment #9) > Do I understand that correctly Jonathan that it's an issue in GCC? Or is it > an invalid code snippet? This is a GCC bug. The code should be accepted without an error.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 --- Comment #12 from Raphael Kubo da Costa --- FWIW, the snippet from comment #1 builds fine with GCC >= 9.1 at least.
[Bug c++/84782] Rejects a maybe C++ code snippet
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84782 Jonathan Wakely changed: What|Removed |Added Status|NEW |RESOLVED Resolution|--- |DUPLICATE --- Comment #13 from Jonathan Wakely --- It was fixed by: PR c++/89381 - implicit copy and using-declaration. Here the used base::operator= gets into the list of foo's bindings for operator=, but it shouldn't make the copy ctor deleted. * class.c (classtype_has_move_assign_or_move_ctor_p): Don't consider op= brought in by a using-declaration. From-SVN: r269442 Looks like a dup of PR c++/89381. That fix has also been backported for GCC 8.4 *** This bug has been marked as a duplicate of bug 89381 ***