thread_pool: replace assert with runtime check in enqueue_work_autoscale

The assert guarding against BoundedQueue::try_enqueue moving the
callable on failure is compiled out in release builds (-DNDEBUG).
If the queue implementation ever changed to move-from on failure,
the empty Func would be enqueued as a poison pill, silently causing
a worker thread to exit — a subtle, hard-to-diagnose pool corruption.

Replace both assert() calls with a std::logic_error throw that
remains active in all build configurations.  This makes the
invariant violation immediately visible rather than silently
dangerous.

Also remove the now-unused <cassert> include.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
Antonio S. Musumeci 2026-04-10 16:44:18 -04:00
parent bc3a0ed8d6
commit f9e36b3889

View file

@ -24,7 +24,6 @@
#include "mutex.hpp"
#include <algorithm>
#include <cassert>
#include <atomic>
#include <cerrno>
#include <csignal>
@ -1042,8 +1041,12 @@ ThreadPool::enqueue_work_autoscale(ThreadPool::PToken &ptok_,
return;
}
assert(static_cast<bool>(f) &&
"BoundedQueue::try_enqueue moved the callable despite returning false");
// If try_enqueue moved the callable despite returning false, the
// Func is empty and would act as a poison pill — re-enqueuing it
// could cause a worker to exit. Throw so the caller notices
// immediately rather than silently corrupting the pool.
if(!static_cast<bool>(f))
throw std::logic_error("BoundedQueue::try_enqueue moved the callable despite returning false");
_maybe_grow_on_pressure();
@ -1067,8 +1070,8 @@ ThreadPool::enqueue_work_autoscale(FuncType &&func_)
return;
}
assert(static_cast<bool>(f) &&
"BoundedQueue::try_enqueue moved the callable despite returning false");
if(!static_cast<bool>(f))
throw std::logic_error("BoundedQueue::try_enqueue moved the callable despite returning false");
_maybe_grow_on_pressure();