Is std :: prom <T> thread safe?
Is it safe, for example, in the case of std::mutex for std::promise<T> to make mutable , or does it depend on T ? How in:
using Data = std::tuple<bool, int, int>; struct X { std::future<Data> prepare() const { return m_promise.get_future(); } void asyncHandler(int a, int b) const { m_promise.set_value({true, a, b}); } void cancel() const { m_promise.set_value({false, 0, 0}); } mutable std::promise<Data> m_promise; // Is this safe? }; void performAsyncOp(const X& x) { std::future<Data> fut = x.prepare(); dispatch(x); std::future_status result = fut.wait_for(std::chrono::milliseconds(150)); if (result == std::future_status::timeout) { x.cancel(); } handleResult(fut.get()); } Let's take a closer look at the API:
// retrieving the result future<R> get_future(); // setting the result void set_value(see below); void set_exception(exception_ptr p); // setting the result with deferred notification void set_value_at_thread_exit(see below); void set_exception_at_thread_exit(exception_ptr p); None of the methods are marked with const , so we cannot derive any knowledge about this constant from this knowledge. However, the standard provides thread safety using the following methods (cf 33.6.6.2 ): set_value , set_exception , set_value_at_thread_exit , and set_exception_at_thread_exit .
This leaves get_future unspecified with respect to thread safety. However, get_future throws an exception if called more than once, cf 33.6.6.14.1 . Therefore, calling get_future from multiple threads does not really make sense from a practical point of view.
There is no guarantee of thread safety when calling get_future and any set and get_future (whether it will come out or not) at the same time, as far as I can see.