Commit d5be302c authored by Maged Michael's avatar Maged Michael Committed by Facebook Github Bot

LifoSemMPMCQueue: Throw only when queue is full not when consumer is in progress.

Summary:
This change ensures that LifoSemMPMCQueue and PriorityLifoSemMPMCQueue do not throw unless the queue is full.

Before this change it was possible for an add operation to throw even when the queue is not full, if a consumer operation is delayed while in progress.

Example:
Queue of size N.
T1: Producer completes N add operations.
T2: Consumer starts a take operation and gets delayed.
T3: Consumer completes N-1 take operations.
T1: Tries an add operation. If using MPMCQueue::write (which returns false) throws even though the queue is not full (has N-1 empty slots). If using MPMCQueue::writeIfNotFull() returns true after waiting for T2's take to complete.

This is somewhat similar to BugD3527722.

Reviewed By: djwatson

Differential Revision: D13701978

fbshipit-source-id: a799353c41d0dc6e673b5fe0ad2a64fd5440fbe8
parent 4ab37c83
......@@ -31,7 +31,7 @@ class LifoSemMPMCQueue : public BlockingQueue<T> {
BlockingQueueAddResult add(T item) override {
switch (kBehavior) { // static
case QueueBehaviorIfFull::THROW:
if (!queue_.write(std::move(item))) {
if (!queue_.writeIfNotFull(std::move(item))) {
throw QueueFullException("LifoSemMPMCQueue full, can't add item");
}
break;
......
......@@ -64,7 +64,7 @@ class PriorityLifoSemMPMCQueue : public BlockingQueue<T> {
CHECK_LT(queue, queues_.size());
switch (kBehavior) { // static
case QueueBehaviorIfFull::THROW:
if (!queues_[queue].write(std::move(item))) {
if (!queues_[queue].writeIfNotFull(std::move(item))) {
throw QueueFullException("LifoSemMPMCQueue full, can't add item");
}
break;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment