From 638da0d121764c86113d14f12ef22cdb105c41a8 Mon Sep 17 00:00:00 2001 From: Todd Schulman Date: Mon, 20 Jul 2026 13:30:48 -0400 Subject: [PATCH 1/2] docs: cover recovery and refresh the CLI in README The Usage block predated several shipped subcommands and still listed the removed `blackoutd --config`. Add `verbosity`, `recovery`, and `diagnose`, point a note at the experimental `recover`/`repro` tooling, replace the `defaults write ... && killall -HUP` verbosity recipe with `blackoutd verbosity `, rename `--config` to `diagnose` in the tech notes, and add a short "How it works" paragraph on the post-wake cursor-on-black auto-recovery and the `recoveryStrategy` preference (see ADR 0010). Co-Authored-By: Claude Opus 4.8 --- README.md | 43 ++++++++++++++++++++++++++----------------- 1 file changed, 26 insertions(+), 17 deletions(-) diff --git a/README.md b/README.md index f36e9fc..ddc05db 100644 --- a/README.md +++ b/README.md @@ -94,11 +94,18 @@ blackoutd on Black out built-in display blackoutd off Restore built-in display blackoutd status Show daemon and display status blackoutd auto on|off Enable/disable auto-blackout on external connect -blackoutd --config Print diagnostic info for bug reports +blackoutd verbosity <0|1|2> Set daemon log verbosity +blackoutd recovery + Set post-wake cursor-on-black auto-recovery +blackoutd diagnose Collect a diagnostic bundle for bug reports blackoutd daemon start Start daemon via launchctl blackoutd daemon stop Stop daemon and restore built-in display ``` +Run `blackoutd` with no arguments for the full list, including the +experimental `recover` and `repro` tooling used to investigate the +cursor-on-black failure (maintainer-run). + ## Upgrade For end users upgrading an existing installation: @@ -209,18 +216,12 @@ Verbosity is level 1 by default (semantic logs only). Level 2 adds `[verbose=2]`-tagged lines with raw CGDisplayChangeSummaryFlags values and decoded connectivity details, useful for diagnosing unexpected display events. -Enable verbose logging at runtime without restarting the daemon: - -```sh -defaults write blackoutd verbosityLevel -int 2 -killall -HUP blackoutd -``` - -Reset to default: +Set verbosity at runtime without restarting the daemon; the value persists +and the daemon reloads it immediately: ```sh -defaults delete blackoutd verbosityLevel -killall -HUP blackoutd +blackoutd verbosity 2 # verbose +blackoutd verbosity 1 # back to the default ``` ## How it works @@ -234,6 +235,13 @@ On external display disconnect, the built-in is unconditionally restored regardless of user intent. Leaving a Mac with no usable display is never acceptable. +After a sleep/wake cycle the daemon re-applies the blackout and, when the +external wakes to a cursor-on-black state (a macOS DCP/scanout stall it +detects from a WindowServer signal), recovers it with a display-sleep cycle. +This runs at wake-settle and is controlled by the `recoveryStrategy` +preference (default `displaysleep`); disable it with `blackoutd recovery +none`. See [ADR 0010](docs/decisions/0010-cursor-on-black-detection-and-recovery.md). + ## Known issues **Username change**: The LaunchAgent plist and log path are hardcoded to the @@ -316,12 +324,13 @@ NSUserDefaults. When the daemon is not running it reports "not running" and exits with code 1; when running it prints the PID, display state, and auto-blackout setting. -`blackoutd --config` prints diagnostic info for bug reports: daemon state, -macOS version, per-display CoreGraphics info (vendor, model, resolution, -physical size), and hardware info via system_profiler. Log data (daemon log, -system log filtered by the blackoutd predicate, pmset sleep/wake events) is -collected into a timestamped directory under `/tmp/blackoutd-diag-*/` to -avoid flooding the terminal. The output prints the path to this directory. +`blackoutd diagnose` collects a diagnostic bundle for bug reports into a +timestamped directory under `/tmp/blackoutd-diag-*/`: daemon state, macOS +version, per-display CoreGraphics info (vendor, model, resolution, physical +size), hardware info via system_profiler, the DCP/framebuffer and connection +state used by the cursor-on-black investigation, and log data (daemon log, +system log filtered by the blackoutd predicate, pmset sleep/wake events). The +output prints the path to this directory. ## Contributing From d2956f873cacb4db13beb8c6625a7580e74603d5 Mon Sep 17 00:00:00 2001 From: Todd Schulman Date: Mon, 20 Jul 2026 13:35:03 -0400 Subject: [PATCH 2/2] chore: bump version to 0.5.1 --- src/Info.plist | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/Info.plist b/src/Info.plist index d5ac44a..9d6228a 100644 --- a/src/Info.plist +++ b/src/Info.plist @@ -7,9 +7,9 @@ CFBundleName blackoutd CFBundleShortVersionString - 0.5.0 + 0.5.1 CFBundleVersion - 5 + 6 LSUIElement NSPrincipalClass