public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet
@ 2023-05-23 19:12 aemseemann at gmail dot com
  2023-05-23 23:32 ` [Bug libstdc++/109947] " redi at gcc dot gnu.org
                   ` (9 more replies)
  0 siblings, 10 replies; 11+ messages in thread
From: aemseemann at gmail dot com @ 2023-05-23 19:12 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

            Bug ID: 109947
           Summary: std::expected monadic operations do not support
                    move-only error types yet
           Product: gcc
           Version: 13.1.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: libstdc++
          Assignee: unassigned at gcc dot gnu.org
          Reporter: aemseemann at gmail dot com
  Target Milestone: ---

GCC13 introduce monadic operations for `std::expected`, including r-value
ref-qualified overloads, which suggests that it should be possible to use an
expected with a move-only value or error type.

However, the following [example](https://godbolt.org/z/aoWeaqoGz) does not
compile due to an attempt to use unique_ptr's the deleted copy constructor:

```cpp
#include <expected>
#include <memory>

int main() 
{   
    using expected = std::expected<int, std::unique_ptr<int>>;

    expected e{42};
    std::move(e).and_then([](auto&&) -> expected {
        return 0;
    });

    return 0;
}

```

The issue seems to be the use of `std::move(value())` in the &&-qualified
overloads of the monadic operations (e.g.
[here](https://github.com/gcc-mirror/gcc/blob/master/libstdc%2B%2B-v3/include/std/expected#L880)
which selects the `value() &` overload that in turn attempts a copy of the
error type in the  [exception
path](https://github.com/gcc-mirror/gcc/blob/master/libstdc%2B%2B-v3/include/std/expected#L740).

When replacing the value access with `std::move(*this).value()` the example
compiles successfully.

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
@ 2023-05-23 23:32 ` redi at gcc dot gnu.org
  2023-05-23 23:36 ` redi at gcc dot gnu.org
                   ` (8 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: redi at gcc dot gnu.org @ 2023-05-23 23:32 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

--- Comment #1 from Jonathan Wakely <redi at gcc dot gnu.org> ---
(In reply to Martin Seemann from comment #0)
> GCC13 introduce monadic operations for `std::expected`, including r-value
> ref-qualified overloads, which suggests that it should be possible to use an
> expected with a move-only value or error type.

No, see https://cplusplus.github.io/LWG/issue3843

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
  2023-05-23 23:32 ` [Bug libstdc++/109947] " redi at gcc dot gnu.org
@ 2023-05-23 23:36 ` redi at gcc dot gnu.org
  2023-05-24 19:34 ` aemseemann at gmail dot com
                   ` (7 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: redi at gcc dot gnu.org @ 2023-05-23 23:36 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

--- Comment #2 from Jonathan Wakely <redi at gcc dot gnu.org> ---
To be clear, a move-only value type is OK. A move-only error type is not.

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
  2023-05-23 23:32 ` [Bug libstdc++/109947] " redi at gcc dot gnu.org
  2023-05-23 23:36 ` redi at gcc dot gnu.org
@ 2023-05-24 19:34 ` aemseemann at gmail dot com
  2023-05-24 20:25 ` redi at gcc dot gnu.org
                   ` (6 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: aemseemann at gmail dot com @ 2023-05-24 19:34 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

--- Comment #3 from Martin Seemann <aemseemann at gmail dot com> ---
Thanks for pointing me to the LWG issue. It makes sense that the error type
must be copyable for the `value()` overloads due to potentially throwing a
`bad_expected_access` with the embedded error embedded.

However, the monadic operations will never throw this exception.
Consequently, the standard draft for the monadic operations
(https://eel.is/c++draft/expected.object.monadic) does not contain any
"Throws:" clause nor is copyability of the error type included in the
"Constraints:" clause.

So it comes down to how to interpret the "Effects:" clause: Does "Equivalent to
<statements involving std::move(value())>" mean  that all restrictions of
`value()` apply transitively or is it merely an implementation hint?

(Strangely enough, in the "Effects:" clause of `value_or()&&` the expression
`std::move(**this)` is used  instead of `std::move(value())`. Maybe this is an
oversight/inconsistency of the standard.)

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
                   ` (2 preceding siblings ...)
  2023-05-24 19:34 ` aemseemann at gmail dot com
@ 2023-05-24 20:25 ` redi at gcc dot gnu.org
  2023-05-24 21:16 ` aemseemann at gmail dot com
                   ` (5 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: redi at gcc dot gnu.org @ 2023-05-24 20:25 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

--- Comment #4 from Jonathan Wakely <redi at gcc dot gnu.org> ---
(In reply to Martin Seemann from comment #3)
> So it comes down to how to interpret the "Effects:" clause: Does "Equivalent
> to <statements involving std::move(value())>" mean  that all restrictions of
> `value()` apply transitively or is it merely an implementation hint?

The former.  The standard says:

Whenever the Effects element specifies that the semantics of some function F
are Equivalent to some code sequence, then the various elements are interpreted
as follows. If F’s semantics specifies any Constraints or Mandates elements,
then those requirements are logically imposed prior to the equivalent-to
semantics. Next, the semantics of the code sequence are determined by the
Constraints, Mandates, Preconditions, Effects, Synchronization, Postconditions,
Returns, Throws, Complexity, Remarks, and Error conditions specified for the
function invocations contained in the code sequence. The value returned from F
is specified by F’s Returns element, or if F has no Returns element, a non-void
return from F is specified by the return statements (8.7.4) in the code
sequence. If F’s semantics contains a Throws, Postconditions, or Complexity
element, then that supersedes any occurrences of that element in the code
sequence.


> (Strangely enough, in the "Effects:" clause of `value_or()&&` the expression
> `std::move(**this)` is used  instead of `std::move(value())`. Maybe this is
> an oversight/inconsistency of the standard.)

Yes. The spec were written by different people at different times.

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
                   ` (3 preceding siblings ...)
  2023-05-24 20:25 ` redi at gcc dot gnu.org
@ 2023-05-24 21:16 ` aemseemann at gmail dot com
  2023-05-25  8:06 ` redi at gcc dot gnu.org
                   ` (4 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: aemseemann at gmail dot com @ 2023-05-24 21:16 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

Martin Seemann <aemseemann at gmail dot com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|UNCONFIRMED                 |RESOLVED
         Resolution|---                         |INVALID

--- Comment #5 from Martin Seemann <aemseemann at gmail dot com> ---
Thanks for the clarification! Now I am convinced that it is not a bug in
libstdc++ (although I still doubt that the side-effects were intended when the
committee formulated the "Effects" for monadic operations, but that's not
relevant here).

Marking as resolved and sorry for the noise.

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
                   ` (4 preceding siblings ...)
  2023-05-24 21:16 ` aemseemann at gmail dot com
@ 2023-05-25  8:06 ` redi at gcc dot gnu.org
  2023-05-25 16:03 ` redi at gcc dot gnu.org
                   ` (3 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: redi at gcc dot gnu.org @ 2023-05-25  8:06 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

--- Comment #6 from Jonathan Wakely <redi at gcc dot gnu.org> ---
(In reply to Martin Seemann from comment #5)
> Thanks for the clarification! Now I am convinced that it is not a bug in
> libstdc++ (although I still doubt that the side-effects were intended when
> the committee formulated the "Effects" for monadic operations, but that's
> not relevant here).

LWG 3843 was resolved after the monadic ops had been specified, and it's
possible that we should have altered the monadic ops to use operator*() instead
of value().

I'll raise this with the committee.

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
                   ` (5 preceding siblings ...)
  2023-05-25  8:06 ` redi at gcc dot gnu.org
@ 2023-05-25 16:03 ` redi at gcc dot gnu.org
  2023-06-01 22:54 ` redi at gcc dot gnu.org
                   ` (2 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: redi at gcc dot gnu.org @ 2023-05-25 16:03 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

Jonathan Wakely <redi at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|RESOLVED                    |SUSPENDED
         Resolution|INVALID                     |---
     Ever confirmed|0                           |1
   Last reconfirmed|                            |2023-05-25

--- Comment #7 from Jonathan Wakely <redi at gcc dot gnu.org> ---
I've created https://cplusplus.github.io/LWG/issue3938 for this, let's see
where that goes.

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
                   ` (6 preceding siblings ...)
  2023-05-25 16:03 ` redi at gcc dot gnu.org
@ 2023-06-01 22:54 ` redi at gcc dot gnu.org
  2023-06-06 19:11 ` aemseemann at gmail dot com
  2023-06-06 22:59 ` redi at gcc dot gnu.org
  9 siblings, 0 replies; 11+ messages in thread
From: redi at gcc dot gnu.org @ 2023-06-01 22:54 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

Jonathan Wakely <redi at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|SUSPENDED                   |ASSIGNED
           Assignee|unassigned at gcc dot gnu.org      |redi at gcc dot gnu.org
   Target Milestone|---                         |13.2

--- Comment #8 from Jonathan Wakely <redi at gcc dot gnu.org> ---
The LWG issue has been moved to Tentatively Ready status by LWG, and should get
approved by the full committee in two weeks.

I've implemented the proposed resolution in GCC trunk as
r14-1471-gfe94f8b7e022b7 and will backport that to the gcc-13 branch too.

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
                   ` (7 preceding siblings ...)
  2023-06-01 22:54 ` redi at gcc dot gnu.org
@ 2023-06-06 19:11 ` aemseemann at gmail dot com
  2023-06-06 22:59 ` redi at gcc dot gnu.org
  9 siblings, 0 replies; 11+ messages in thread
From: aemseemann at gmail dot com @ 2023-06-06 19:11 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

--- Comment #9 from Martin Seemann <aemseemann at gmail dot com> ---
That's great news, looking forward to the next point release.
Thank you very much for taking this to the committee and getting the process in
motion so quickly!

^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug libstdc++/109947] std::expected monadic operations do not support move-only error types yet
  2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
                   ` (8 preceding siblings ...)
  2023-06-06 19:11 ` aemseemann at gmail dot com
@ 2023-06-06 22:59 ` redi at gcc dot gnu.org
  9 siblings, 0 replies; 11+ messages in thread
From: redi at gcc dot gnu.org @ 2023-06-06 22:59 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109947

Jonathan Wakely <redi at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
         Resolution|---                         |FIXED
             Status|ASSIGNED                    |RESOLVED

--- Comment #10 from Jonathan Wakely <redi at gcc dot gnu.org> ---
Backported as r13-7423-gff58310f274e49 for 13.2

^ permalink raw reply	[flat|nested] 11+ messages in thread

end of thread, other threads:[~2023-06-06 22:59 UTC | newest]

Thread overview: 11+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-05-23 19:12 [Bug libstdc++/109947] New: std::expected monadic operations do not support move-only error types yet aemseemann at gmail dot com
2023-05-23 23:32 ` [Bug libstdc++/109947] " redi at gcc dot gnu.org
2023-05-23 23:36 ` redi at gcc dot gnu.org
2023-05-24 19:34 ` aemseemann at gmail dot com
2023-05-24 20:25 ` redi at gcc dot gnu.org
2023-05-24 21:16 ` aemseemann at gmail dot com
2023-05-25  8:06 ` redi at gcc dot gnu.org
2023-05-25 16:03 ` redi at gcc dot gnu.org
2023-06-01 22:54 ` redi at gcc dot gnu.org
2023-06-06 19:11 ` aemseemann at gmail dot com
2023-06-06 22:59 ` redi at gcc dot gnu.org

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).