Observation
launchctl Override Rows Survive Userland Label Removal
launchctl Override Rows Survive Userland Label Removal
Context
FLT-0255 and FLT-0276 renamed the local fleet LaunchAgent mirror from com.orbit. labels to com.camberzero.fleet. labels. After the rename, launchctl print gui/501/com.orbit.<label> reported no live services, but launchctl print-disabled gui/501 still listed three stale labels as enabled:
com.orbit.shepherd-feed-watchcom.orbit.ops-deputy-loopcom.orbit.ops-command-churn-alarm
This observation captures the local launchd behavior verified during FLT-0279.
Observation
On this host/build, current macOS launchd keeps override-only rows in /private/var/db/com.apple.xpc.launchd/disabled.<uid>.plist, and ordinary userland lifecycle commands do not clear them once written.
Verified facts:
1. The stale com.orbit.* labels are not loaded services.
launchctl print gui/501/com.orbit.shepherd-feed-watch=>Could not find service- same for
ops-deputy-loopandops-command-churn-alarm /private/var/db/com.apple.xpc.launchd/disabled.501.plistbootstrapa temporary plistdisablethenenablethe labelbootoutthe labelprint-disabledstill shows the label as enabledlaunchctl removelaunchctl load -wlaunchctl unloadlaunchctl unload -w
2. The labels still exist as keys in the root-owned override DB:
3. Their stored values are boolean false, which launchctl print-disabled renders as enabled. 4. A throwaway probe label reproduced the same persistence pattern:
5. Alternate userland paths do not clear the row either:
6. This host's launchctl manpage/help exposes no reset-disabled or equivalent row-prune command.
Interpretation
There are two distinct states that look similar in launchd output but are not the same thing:
- live LaunchAgent state
- persisted override-row state
Renaming or removing a LaunchAgent label can leave the second behind even after the first is gone. Once that happens, the residue is no longer a launch-surface problem; it is a root-owned override-database problem.
That means future audits must not treat print-disabled entries alone as proof of a live service. First ask whether launchctl print gui/<uid>/<label> finds anything at all.
Countermeasure
FLT-0279 landed a mirrored helper:
scripts/fleet-runtime-helpers/launchd-disabled-prune
The helper is dry-run by default, creates a backup before mutation, and prunes only boolean-false rows unless forced. It exists because the supported launchctl surface can diagnose this state but not clear it.
Maturity Rationale
M2 rather than M1 because the behavior was reproduced with both:
- the real stale
com.orbit.*labels on the host - a fresh throwaway probe label created solely to test launchd semantics
That is enough to treat the pattern as observed and repeatable on this host.