Is it safe to call a std::move_only_function
object in one thread and replace the function it points to in another thread?
My code:
#include <future>
#include <functional>
int main() {
std::move_only_function<void()> fn = []{};
auto future1 = std::async(std::launch::async, [&]{ fn(); });
auto future2 = std::async(std::launch::async, [&]{ fn = []{}; });
future1.get();
future2.get();
}
I don't care if the old or the new function is called. Also I know that fn
always holds a valid function.
No it is not safe.
The assignment operator (std::move_only_function::operator=
) is not guaranteed to be atomic.
Therefore you can have a context switch in the middle of it, leaving the std::move_only_function
object in an invalid state which the other thread will attempt to invoke leading to undefined-behavior.