Does lock-less queue wait on empty queue ?
Hello, I'm newbie of boost library. I would like to ask if the lockless queue waits on empty queue ? (I actually need it to wait). And another thing: Can the Pool library be build separately, so that I can use only the boost/pool files or do I need to use all boost sources in order to build just the pool. Thank you, Ran
Am 18.05.2015 um 13:51 schrieb Ran Shalit:
Hello,
I'm newbie of boost library.
I would like to ask if the lockless queue waits on empty queue ? (I actually need it to wait). You can easily wait yourself, and everyone would want to wait differently, so there is no point in putting into the queue's implementation. For instance you could give up your scheduler time-slice, or you might want to spin-lock
while(!queue.pop(my_data)) { boost::this_thread::yield(); //give up time slice } //tight waiting while(!queue.pop(my_data)) { //spin }
And another thing: Can the Pool library be build separately, so that I can use only the boost/pool files or do I need to use all boost sources in order to build just the pool.
Boost lockfree seems to be header only, but I'm not so sure about its dependencies. Maybe someone can drop in here. Cheers Sebastian
Thank you, Ran _______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users
On 19/05/2015 01:02, Sebastian Messerschmidt wrote:
Am 18.05.2015 um 13:51 schrieb Ran Shalit:
Hello,
I'm newbie of boost library.
I would like to ask if the lockless queue waits on empty queue ? (I actually need it to wait). You can easily wait yourself, and everyone would want to wait differently, so there is no point in putting into the queue's implementation. For instance you could give up your scheduler time-slice, or you might want to spin-lock
while(!queue.pop(my_data)) { boost::this_thread::yield(); //give up time slice }
You can also do a "real" wait until something has been pushed (which can be important as yield() does not let lower-priority threads run), but currently doing that requires using either Win32 events or using condition variables -- but the latter requires adding a mutex on both ends, which may defeat the point of using a lock-free queue in the first place.
On 19/05/2015 01:02, Sebastian Messerschmidt wrote:
Am 18.05.2015 um 13:51 schrieb Ran Shalit:
Hello,
I'm newbie of boost library.
I would like to ask if the lockless queue waits on empty queue ? (I actually need it to wait). You can easily wait yourself, and everyone would want to wait differently, so there is no point in putting into the queue's implementation. For instance you could give up your scheduler time-slice, or you might want to spin-lock
while(!queue.pop(my_data)) { boost::this_thread::yield(); //give up time slice }
You can also do a "real" wait until something has been pushed (which can be important as yield() does not let lower-priority threads run), but currently doing that requires using either Win32 events or using condition variables -- but the latter requires adding a mutex on both ends, which may defeat the point of using a lock-free queue in the first place.
_______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users It would be an interesting exercise to integrate lock-less queue with
On 19.05.2015 03:28, Gavin Lambert wrote: libdispatch or similar open source event library. But then again, with task queues like those of libdispatch around you may be able avoid multi-threading issues in first place. Leon
Using condition variables does require mutexes, but you only need to
grab the mutex when someone is actually waiting. So you can have a
separate (atomic) flag 'waiting' and then only grab the mutex when it
is true.
But that is an extra atomic op on every push (checking the flag). Of
course, it could probably be a relaxed atomic (I think), which is
almost free on many platforms.
And it gets tricky ensuring that you don't have a case where someone
is waiting but every pusher missed seeing the flag.
If the waiting is inside the queue implementation, you can possibly
hide the flag inside the head pointer, getting the extra atomic op for
free.
I touched on some of this in my Lock-free talk at BoostCon/C++Now last week.
Tony
On Mon, May 18, 2015 at 9:28 PM, Gavin Lambert
On 19/05/2015 01:02, Sebastian Messerschmidt wrote:
Am 18.05.2015 um 13:51 schrieb Ran Shalit:
Hello,
I'm newbie of boost library.
I would like to ask if the lockless queue waits on empty queue ? (I actually need it to wait).
You can easily wait yourself, and everyone would want to wait differently, so there is no point in putting into the queue's implementation. For instance you could give up your scheduler time-slice, or you might want to spin-lock
while(!queue.pop(my_data)) { boost::this_thread::yield(); //give up time slice }
You can also do a "real" wait until something has been pushed (which can be important as yield() does not let lower-priority threads run), but currently doing that requires using either Win32 events or using condition variables -- but the latter requires adding a mutex on both ends, which may defeat the point of using a lock-free queue in the first place.
_______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users
On Wed, May 20, 2015 at 5:15 PM, Gottlob Frege
Using condition variables does require mutexes, but you only need to grab the mutex when someone is actually waiting. So you can have a separate (atomic) flag 'waiting' and then only grab the mutex when it is true.
But that is an extra atomic op on every push (checking the flag). Of course, it could probably be a relaxed atomic (I think), which is almost free on many platforms.
And it gets tricky ensuring that you don't have a case where someone is waiting but every pusher missed seeing the flag.
If the waiting is inside the queue implementation, you can possibly hide the flag inside the head pointer, getting the extra atomic op for free.
I touched on some of this in my Lock-free talk at BoostCon/C++Now last week.
Aren't these tricky corner cases what "synchronic" is supposed to address? http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4195.pdf
On Wed, May 20, 2015 at 5:27 PM, Nat Goodspeed
On Wed, May 20, 2015 at 5:15 PM, Gottlob Frege
wrote: Using condition variables does require mutexes, but you only need to grab the mutex when someone is actually waiting. So you can have a separate (atomic) flag 'waiting' and then only grab the mutex when it is true.
But that is an extra atomic op on every push (checking the flag). Of course, it could probably be a relaxed atomic (I think), which is almost free on many platforms.
And it gets tricky ensuring that you don't have a case where someone is waiting but every pusher missed seeing the flag.
If the waiting is inside the queue implementation, you can possibly hide the flag inside the head pointer, getting the extra atomic op for free.
I touched on some of this in my Lock-free talk at BoostCon/C++Now last week.
Aren't these tricky corner cases what "synchronic" is supposed to address? http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4195.pdf
I think it was more of a way to wrap up "expert waiting" (spinning, exponential back-off, etc) without each developer needing to reimplement it. But it also looks like it could cover my tricky corner cases as well. (For the specific case of a queue it wouldn't allow me to hide the extra atomic within the head pointer, and would be an extra acquire/release, but oh well). Tony
_______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users
participants (6)
-
Gavin Lambert
-
Gottlob Frege
-
Leon Mlakar
-
Nat Goodspeed
-
Ran Shalit
-
Sebastian Messerschmidt