Fix Linux signal stderr cleanup - #208
Conversation
Codex reviewer (cross-vendor, read-only)Reviewed-head: cfd0218 Posted verbatim by The patch avoids the Bash trap-table mutation but weakens cleanup under repeated process-group signals, potentially leaving child processes and scratch state behind. Review comment:
|
Deploying ystack with
|
| Latest commit: |
50b24b5
|
| Status: | ✅ Deploy successful! |
| Preview URL: | https://769e9815.fabrica-6yx.pages.dev |
| Branch Preview URL: | https://codex-fix-adapter-signal-std.fabrica-6yx.pages.dev |
Codex reviewer (cross-vendor, read-only)Reviewed-head: 50b24b5 Posted verbatim by The changes preserve the runner's timeout and descendant handling while making signal cleanup more robust. The updated focused test appropriately exercises repeated process-group termination and cleanup behavior. |
Follow-up to #207.
Unblocks #206.
Repeated TERM exposed two Linux Bash signal races. First, changing live signal traps while TERM was pending made Bash write an internal warning. Second, a signal sent to the whole runner process group could kill polling or cleanup commands before the runner finished reaping children and removing scratch state.
This keeps one permanent guarded signal handler and does not change its live trap table. Cleanup now tolerates interrupted waits and sleeps, retries removal for a bounded time, covers dangling links, and fails closed if final removal cannot finish. The one-second child timeout now uses a private unlinked pipe and a Bash built-in wait, so a group signal cannot kill a polling sleep or leak a job message. The adapter cannot reopen the pipe and closes its inherited descriptor.
The regression starts the runner in its own process group, proves a registered child group is live, and sends TERM to the whole runner group at least twice. It still requires exit 143, empty stdout and stderr, no scratch, and no surviving child. Failure output reports only counts, SHA-256, and fixed classes.
Proof on 50b24b5:
This is inactive, repo-only test-runner behavior. It does not use a real target, credential, network adapter, release, install, activation, or deployment.