Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Chapter 13: attempting to reference a deleted function #3

Open
puhach opened this issue Jul 30, 2021 · 1 comment
Open

Chapter 13: attempting to reference a deleted function #3

puhach opened this issue Jul 30, 2021 · 1 comment

Comments

@puhach
Copy link

puhach commented Jul 30, 2021

The Promise struct in Chapter13\sync_wait.h causes the following compilation errors:

3>C:\temp\Cpp-High-Performance-Second-Edition-master\Chapter13\task_ex.cpp(31): error C2280: 'detail::SyncWaitTask::Promise::Promise(void)': attempting to reference a deleted function
3>C:\temp\Cpp-High-Performance-Second-Edition-master\Chapter13\sync_wait.h(65): message : compiler has generated 'detail::SyncWaitTask::Promise::Promise' here
4>C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Tools\MSVC\14.29.30037\include\execution(1222,5): error C2338: Parallel algorithms require forward iterators or stronger.
3>C:\temp\Cpp-High-Performance-Second-Edition-master\Chapter13\sync_wait.h(65,1): message : 'detail::SyncWaitTask::Promise::Promise(void)': function was implicitly deleted because a data member 'detail::SyncWaitTask::Promise::semaphore_' has either no appropriate default constructor or overload resolution was ambiguous
3>C:\temp\Cpp-High-Performance-Second-Edition-master\Chapter13\sync_wait.h(59): message : see declaration of 'detail::SyncWaitTask::Promise::semaphore_'
3>C:\temp\Cpp-High-Performance-Second-Edition-master\Chapter13\task_ex.cpp(26): message : see reference to function template instantiation 'int sync_wait<Task&>(T)' being compiled
3> with
3> [
3> T=Task &
3> ]
3>Done building project "Chapter13-Asynchronous_Programming_With_Coroutines.vcxproj" -- FAILED.

I believe the issue is caused by std::binary_semaphore, which is used incorrectly. According to the documentation, this class has to be initialized with the internal counter. Here it is used without any parameters:

  struct Promise {
    SyncWaitTask get_return_object() noexcept { return SyncWaitTask{*this}; }
    auto initial_suspend() noexcept { return std::suspend_always{}; }
    void unhandled_exception() noexcept { error_ = std::current_exception(); }
    auto yield_value(T&& x) noexcept { // Result has arrived
      value_ = std::addressof(x);
      return final_suspend();
    }

    auto final_suspend() noexcept {
      struct Awaitable {
        bool await_ready() noexcept { return false; }
        void await_suspend(std::coroutine_handle<Promise> h) noexcept {

#if defined(__cpp_lib_semaphore)
          h.promise().semaphore_.release(); // Signal!
#else
          {
            auto lock = std::unique_lock{h.promise().mtx_};
            h.promise().ready_ = true;
          }
          h.promise().cv_.notify_one();
#endif
        }
        void await_resume() noexcept {}
      };
      return Awaitable{};
    }

    void return_void() noexcept { assert(false); }

    T* value_ = nullptr;
    std::exception_ptr error_;

#if defined(__cpp_lib_semaphore)
    std::binary_semaphore semaphore_; // !!
#else
    bool ready_{false};
    std::mutex mtx_;
    std::condition_variable cv_;
#endif
  };
@zhaohui0923
Copy link

@puhach just change "std::binary_semaphore semaphore_;" to "std::binary_semaphore semaphore_{1};" will fix the issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

No branches or pull requests

2 participants