Repository navigation
acpmux: a SIGTERM stop names its sender - #35147
Conversation
After a NIGHTLY update relaunch on macOS the old daemon sometimes got a SIGTERM about 1 s after the app quit, and its log said only "SIGTERM" (manaflow-ai/cmuxterm-hq#6338), so nothing named who sent it. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Agent-Session: https://cmux.com/deeplink/agent?id=aid-cb01117327fc358e9ba1
A SA_SIGINFO action beside tokio's own records si_pid; the stop line then says "stopping: SIGTERM from pid N (command), parent M (command)". After a NIGHTLY update relaunch on macOS the old daemon sometimes got a SIGTERM before the new app started and its agent host was lost with it (manaflow-ai/cmuxterm-hq#6338); nothing in its log named the sender. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Agent-Session: https://cmux.com/deeplink/agent?id=aid-cb01117327fc358e9ba1
Bugbot needs on-demand usage enabledBugbot uses usage-based billing for this team and requires on-demand usage to be enabled. A team admin can enable on-demand usage in the Cursor dashboard. |
|
cmux status (one comment, edited in place; each line is updated by the job that owns it) Review App of this head (app.zip, kept 1 day)
web and size checks: green Shipped in:
|
term_sender reads one pid, the one the kernel named as the SIGTERM's sender, once on the stop path, to name it and its parent on the stop line. It enumerates nothing. Review note: one kernel-named pid, read-only, off every hot path. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Agent-Session: https://cmux.com/deeplink/agent?id=aid-cb01117327fc358e9ba1
|
Found 2 test failures on Blacksmith runners: Failures
|
|
Review (codex, router-review): SHIP at 18057fe Reviewer: codex gpt-6-astra high, fast tier. Follow-ups: 1. They land as checklist items in this PR's one follow-up tracking issue in this repo ( SHIP at 18057fe Visual verdict: no images; Leo tries the build.
Focused tests were not runnable because this box has no Follow-ups:
|
Review finding F1 (Codex SHIP at 18057fe): with our action alone, SIGTERM's default action is replaced, so a daemon whose tokio stream failed to register would never stop on SIGTERM. The sender action is now added only after that stream exists. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Agent-Session: https://cmux.com/deeplink/agent?id=aid-cb01117327fc358e9ba1
|
Review (codex, router-review): SHIP at 4985441 Reviewer: codex gpt-6-astra high, fast tier. Follow-ups: 1. They land as checklist items in this PR's one follow-up tracking issue in this repo ( SHIP at 4985441
Rust tests could not run because Follow-ups:
|
A newer verdict blocks 9a2e1da (no independent SHIP at the head).
…on an update relaunch) (#35291) * test(acpmux): a host ended by SIGTERM names its sender (red) After an update relaunch on macOS the old daemon got a SIGTERM from loginwindow (#35147's stop line) and its agent host was lost; hosts log nothing, so nothing says whether the host got that signal too (manaflow-ai/cmuxterm-hq#6338). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Agent-Session: https://cmux.com/deeplink/agent?id=aid-cb01117327fc358e9ba1 * acpmux: hosts note their SIGTERM sender; the daemon carries none of the app's launch identity - An agent host that ends on SIGTERM appends who sent it (pid, command, parent) to the home's agent-host-signals.log; the daemon's stop line names its sender since #35147. - The sender is read once its action has stored it (#35147 review F1): tokio's action can wake the reader on another thread first. - The app spawns its daemon without its own launch identity (__CFBundleIdentifier, XPC_SERVICE_NAME, XPC_FLAGS, LaunchInstanceID). After an update relaunch, loginwindow sent the old daemon SIGTERM 1.08 s after the app quit, while the bundle was replaced (fleet run 85017cc90b72d8076d0e56ff), and its agent host was lost with it. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Agent-Session: https://cmux.com/deeplink/agent?id=aid-cb01117327fc358e9ba1 * acpmux: drop the launch-identity strip: loginwindow still ended the daemon and its hosts without it Fleet bench at 2faef0a (step ef77e027a15c52e8fa79ae10): with __CFBundleIdentifier, XPC_SERVICE_NAME, XPC_FLAGS and LaunchInstanceID stripped, update rounds 2 and 3 still logged a SIGTERM from loginwindow (pid 179) at the daemon, and agent-host-signals.log shows it reached agent hosts directly within 14 ms. So it is not the environment; the strip is taken out. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Agent-Session: https://cmux.com/deeplink/agent?id=aid-cb01117327fc358e9ba1 --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
|
Finding outcome: comment-6627533347/F1 fixed c9f0649 |
![Fix with [code]smith](https://pr-comments-assets.blacksmith.sh/codesmith/fix-with-codesmith-light-3x.png)
Leo, 2026-11-04: "i feel like the restarted after nightly update does too many layout shifts/flicker renderings and takes too long to reconnect acpmux or whatever". Data: manaflow-ai/cmuxterm-hq#6338 (comments 6597127823 and 6626332314), bench in #34697.
After an update relaunch on macOS the old acpmux daemon sometimes logs
stopping: SIGTERM (a restart handoff)about 1.1 s after the app quit and about 5 s before the new app starts. Its agent host is lost with it, so the next daemon resumes the streaming turn on a fresh agent. Nothing in the log says who sent the signal. The app, the bench and acpmux itself have no code that sends SIGTERM to the daemon on that path. The daemon and its hosts each lead their own session, so a process-group kill can't explain it.This PR makes the daemon say who sent it. A
SA_SIGINFOaction next to tokio's own recordssi_pid; both go throughsignal-hook-registry, which runs every action registered for the signal. The action does only an atomic store, so it is async-signal-safe. The stop line then readsstopping: SIGTERM from pid N (command), parent M (command) (a restart handoff). A fleet bench run at this head (relaunch-reconnect:warm+update:4) is collecting the sender for the fix that follows.Test
cargo test -p acpmux --test daemon_lifecycle a_sigterm_stop_names_its_senderfails at the red commit (no sender on the stop line) and passes at the head.daemon::term_sender::tests(ps row parsing; this process is described with its command).Observed / Not run
Performance
psreads on the stop pathRisk
Low: only the daemon's SIGTERM stop path changes, plus one extra signal action. If the action can't be registered, the daemon logs a warning and stops as before.
Changelog
none
Agent session: agent session
🤖 Generated with Claude Code
Open in [code]smith · Need help on this PR? Tag
@codesmith-botwith what you need.Summary by cubic
Names the SIGTERM sender on the acpmux daemon's stop line so an unexplained SIGTERM after a NIGHTLY update relaunch on macOS can be traced.
The daemon now logs
stopping: SIGTERM from pid N (command), parent M (command)instead of the plainstopping: SIGTERM (a restart handoff). ASA_SIGINFOaction records the sender's pid viasignal-hook-registry; the action only does an atomic store, so it is async-signal-safe. It is registered only after tokio's own stream exists, so SIGTERM's default action is never replaced. The sender's command and parent are read frompsat stop time. The lookup is a reviewed process-scan exception: it reads one kernel-named pid once on the stop path and enumerates nothing. If the action can't be registered, the daemon warns and stops as before.Low risk: only the SIGTERM stop path changes, plus one extra signal action.
Written for commit 9a2e1da. Summary will update on new commits.