Repository navigation
Prevent worker-pool re-entry with Fiber.blocking - #232
Merged
Merged
Conversation
…block`. If the scheduler's `block` hook performs a nested `WorkerPool#call` on the same fiber before suspending (as a GC finalizer can, e.g. `Tempfile` unlinking its file), the outer operation's wakeup resumes the nested wait instead. The nested operation is cancelled and the outer wait never wakes again. Also record whether the `busy` test operation actually executed, since an operation cancelled before it starts is otherwise reported as completed. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
GC finalizers can run inside the scheduler's
blockhook and start another blocking operation on the same fiber. The nested worker-pool wait can consume the outer operation's completion notification, cancelling the nested work and leaving the outer wait stuck.This is an alternative to #230: prevent implicit re-entry into the worker pool instead of tracking nested operations and replaying wakeups.
Fiber.blockingbefore submitting work. Keep waiting, cancellation, and draining inside that scope.The implementation uses the existing
Fiber.blockingAPI and requires no Ruby changes. Its tradeoff is that an incidental nested operation blocks the event-loop thread until it finishes, including delaying scheduler-driven timeouts during that operation. The change applies toWorkerPool#call; it does not change Ruby's scheduler-hook contract globally.The original regression-test commit from #229/#230 is retained with attribution. The helper classes are at file scope, and the regression now also verifies that only the outer operation reaches the pool. Additional checks cover independent fibers, synchronous operations during cancellation cleanup, restoration of blocking state after normal completion, exceptions and
throw, and spurious wakeups.Validation on macOS with Ruby 4.0.6:
ASYNC_SCHEDULER_WORKER_POOL=true, using Async 2.46.0 and the local io-event extension: 101 passed (219 assertions).block: all 20 Tempfile finalizers removed their files, 20 file writes completed, and maximum blocking-operation hook depth stayed at 1.