Fix for random deadlocks

This fix compensates for std::atomic<>::compare_exchange_XX() modifying the 'expected' value when the function fails.  Without this threads are released after one iteration through the synchronizing loop and then release before values are guaranteed to be initialized.  Other threads will start consuming these uninitialized values and threads initializing values will deadlock on the synchronization loop.  Also due to the use of update fail loops we can use std::atomic<>::compare_exchange_weak() to improve speed.