Async: Drop-in SyncCancelerForAsyncWork without execUncancelableSegment*

We're doing this to prep for the coro port
This commit is contained in:
2026-05-30 10:52:15 -04:00
parent c7dee57072
commit f100764bd8
9 changed files with 72 additions and 91 deletions
@@ -59,7 +59,6 @@ IoUringAssemblyEngine::IoUringAssemblyEngine(
frameAssemblyDesc(nullptr), ring{},
eventfdFd(-1), eventfdDesc(nullptr), eventfd_value(0),
stallTimer(parent_.device->componentThread->getIoService()),
shouldAcceptRequests(false),
nDgramsPerStagingBufferFrame(nDgramsPerStagingBufferFrame_),
assembledSlotsTracker(nDgramsPerStagingBufferFrame_),
randomDevice(), randomGenerator(randomDevice())
@@ -68,13 +67,10 @@ randomDevice(), randomGenerator(randomDevice())
bool IoUringAssemblyEngine::setup()
{
// Defensive check to prevent double-calling
if (!ioUringAssemblyEngnCanceler.isCancellationRequested())
{
sscl::SpinLock::Guard lock(shouldAcceptRequestsLock);
if (shouldAcceptRequests)
{
throw std::runtime_error(std::string(__func__) + ": setup() called "
"while already set up");
}
throw std::runtime_error(std::string(__func__) + ": setup() called "
"while already set up");
}
// Get FrameAssemblyDesc from staging buffer
@@ -156,7 +152,7 @@ bool IoUringAssemblyEngine::setup()
if (ret < 0)
{ goto cleanup_eventfd; }
shouldAcceptRequests = true;
ioUringAssemblyEngnCanceler.startAcceptingWork();
return true;
cleanup_eventfd:
@@ -229,7 +225,7 @@ void IoUringAssemblyEngine::resetAndAssembleFrame(
+ ": onCqeReady callback is invalid");
}
if (!shouldAcceptRequests)
if (ioUringAssemblyEngnCanceler.isCancellationRequestedUnlocked())
{
throw std::runtime_error(std::string(__func__)
+ ": engine is not accepting requests");
@@ -321,11 +317,7 @@ void IoUringAssemblyEngine::resetAndAssembleFrame(
bool IoUringAssemblyEngine::stop()
{
// Acquire and release lock tightly around setting the flag
sscl::SpinLock::Guard lock(shouldAcceptRequestsLock);
bool wasAcceptingRequests = shouldAcceptRequests;
shouldAcceptRequests = false;
return wasAcceptingRequests;
return ioUringAssemblyEngnCanceler.requestStop();
}
void IoUringAssemblyEngine::assemblyCycleComplete()
@@ -444,9 +436,9 @@ public:
void assembleFrameReq1_posted(
std::shared_ptr<AssembleFrameReq> context)
{
sscl::SpinLock::Guard lock(engine.shouldAcceptRequestsLock);
sscl::SpinLock::Guard guard(engine.ioUringAssemblyEngnCanceler.s.lock);
if (!engine.shouldAcceptRequests)
if (engine.ioUringAssemblyEngnCanceler.isCancellationRequestedUnlocked())
{
context->callOriginalCallback(false, sscl::AsynchronousLoop(0));
return;
@@ -498,9 +490,11 @@ public:
* indeed seen a SEGFAULT even in the current code with locking, so
* I'm going to hold the lock here for now.
*/
sscl::SpinLock::Guard lock(context->engine.shouldAcceptRequestsLock);
sscl::SpinLock::Guard guard(
context->engine.ioUringAssemblyEngnCanceler.s.lock);
if (!context->engine.shouldAcceptRequests)
if (context->engine.ioUringAssemblyEngnCanceler
.isCancellationRequestedUnlocked())
{
context->engine.assemblyCycleComplete();
context->loop.setRemainingIterationsToFailure();
@@ -518,7 +512,8 @@ public:
void *user_data, int cqe_result)
{
// NB: The lock was acquired by onEventFdRead before calling this func
if (!context->engine.shouldAcceptRequests)
if (context->engine.ioUringAssemblyEngnCanceler
.isCancellationRequestedUnlocked())
{
context->engine.assemblyCycleComplete();
context->loop.setRemainingIterationsToFailure();
@@ -549,7 +544,7 @@ public:
{
/** EXPLANATION:
* All branch paths that invoke this unifyig oracle function are
* expected to already hold the shouldAcceptRequestsLock before calling
* expected to already hold ioUringAssemblyEngnCanceler.s.lock before calling
* it.
*/
// Ensure we only execute once using atomic exchange
@@ -638,8 +633,8 @@ void IoUringAssemblyEngine::assembleFrameReq(
sscl::cps::Callback<assembleFrameReqCbFn> cb)
{
{
sscl::SpinLock::Guard lock(shouldAcceptRequestsLock);
if (!shouldAcceptRequests)
sscl::SpinLock::Guard guard(ioUringAssemblyEngnCanceler.s.lock);
if (ioUringAssemblyEngnCanceler.isCancellationRequestedUnlocked())
{
cb.callbackFn(false, sscl::AsynchronousLoop(0));
return;
@@ -670,7 +665,7 @@ void IoUringAssemblyEngine::onEventfdRead(
* IoUringAssemblyEngine's per-assembly state isn't destroyed while this
* handler is running.
*/
sscl::SpinLock::Guard lock(shouldAcceptRequestsLock);
sscl::SpinLock::Guard guard(ioUringAssemblyEngnCanceler.s.lock);
/** EXPLANATION:
* You'd think we should put check for shouldAcceptRequests here and
* `return` here if !shouldAcceptRequests, but we shouldn't because
@@ -722,7 +717,7 @@ void IoUringAssemblyEngine::onEventfdRead(
* But we do put a `return` here because we know that at this point, the
* caller's callback has already been invoked.
*/
if (!shouldAcceptRequests
if (ioUringAssemblyEngnCanceler.isCancellationRequestedUnlocked()
|| eventfdDesc == nullptr || !eventfdDesc->is_open())
{
return;