cplusplus / sender-receiver

Issues list for P2300
Apache License 2.0
19 stars 3 forks source link

[exec.connect] operation-state-task exposition-only type does not need a move constructor #236

Open lewissbaker opened 4 months ago

lewissbaker commented 4 months ago

The definition of the operation-state-task exposition only type defines a move-constructor which can transfer ownership of the coroutine_handle to another instance.

namespace std::execution {
  struct operation-state-task {
    using operation_state_concept = operation_state_t;
    using promise_type = connect-awaitable-promise;
    coroutine_handle<> coro; // exposition only

    explicit operation-state-task(coroutine_handle<> h) noexcept : coro(h) {}
    operation-state-task(operation-state-task&& o) noexcept
      : coro(exchange(o.coro, {})) {}
    ~operation-state-task() { if (coro) coro.destroy(); }

    void start() & noexcept {
      coro.resume();
    }
  };
}

However, this type is implementing the operation_state concept, which doesn't require movability.

We could simplify this type by instead declaring the move-constructor deleted and then the destructor can unconditionally call coro.destroy().

Suggestion:

namespace std::execution {
  struct operation-state-task {
    using operation_state_concept = operation_state_t;
    using promise_type = connect-awaitable-promise;
    coroutine_handle<> coro; // exposition only

    explicit operation-state-task(coroutine_handle<> h) noexcept : coro(h) {}
    operation-state-task(operation-state-task&& o) = delete;
    ~operation-state-task() { coro.destroy(); }

    void start() & noexcept {
      coro.resume();
    }
  };
}