Reputation: 5039
General question: Is std::shared_future::operator= atomic?
For example
struct object {
object() {
sf = std::async(std::launch::async, &async_func).share();
}
void change(){
sf = std::async(std::launch::async, &other_async_func).share();
}
void read(){
while (true){ sf.get(); }
}
std::shared_future<int> sf;
};
Question Part 1 Is it OK to call std::shared_future::operator=
while the left, e.g. old shared_future
, has not been waited on/asynchronous provider still running? Like in object::change()
.
Question Part 2 Is it OK to call std::shared_future::operator=
while other asynchronous return objects / threads that are concurrent calling std::shared_future.get()
? Like in object::read()
?
Edit: Forget object::read()
, I mean of course with their own std::shared_future
but the same shared state.
After reading of C++11 draft N3485 §30.6.7:12
shared_future& operator=(shared_future&& rhs) noexcept; 12 Effects:
— releases any shared state (30.6.4);
— move assigns the contents of rhs to *this
Question Part 1 depends solely on releasing a shared state, e.g. after reading of §30.6.4, destroying a shared state, so I guess that means Part 1 should be true, but I'm not sure.
Question Part 2 seems to be false, because these are two steps and I neither know if the move part is atomic nor if what happens if the shared state is destroyed while other threads are in shared_future::get()
.
Upvotes: 3
Views: 988
Reputation: 303027
These are only notes in [futures.shared_future], but they're relevant:
[ Note: Member functions of shared_future do not synchronize with themselves, but they synchronize with the shared shared state. —end note ]
[...]
const R& shared_future::get() const; R& shared_future<R&>::get() const; void shared_future<void>::get() const;
Note: access to a value object stored in the shared state is unsynchronized, so programmers should apply only those operations on
R
that do not introduce a data race (1.10).
So calling change()
is fine as long as nobody is calling read()
or otherwise accessing sf
.
Upvotes: 2