breadcrumbs now speaks `org.freedesktop.NetworkManager` on the system
bus directly (new `zbus` dependency) — no `nmcli` subprocesses for
connect, scan, status, or the watch loop.
Why:
- Wi-Fi PSKs and 802.1x passwords no longer touch a command line. They
travel inside `AddAndActivateConnection2` / `Update2` settings
payloads, so they are never visible to other local users via
`/proc/<pid>/cmdline`. This fully supersedes the earlier
"feed the PSK to `nmcli --ask` on stdin" approach.
- The watch loop reacts to real `Device.StateChanged` / connectivity
signals instead of parsing `nmcli monitor` text.
- Connect waits on the device actually reaching the ACTIVATED state
rather than trusting `nmcli --wait`.
Config: `settings.nmcli_wait` is renamed to `connect_wait`; the old key
is still accepted via `#[serde(alias)]`. `status.rs` loses its private
`ipv4()` nmcli helper in favour of `nm::ipv4_address`. `util::run_with_stdin`
stays (tailscale still uses it) but no longer carries secrets.
The watch daemon publishes bread.crumbs.profile.changed and
bread.crumbs.health.changed on real transitions (not every poll tick)
and honors bread.command.crumbs.set_profile via the existing
state::set_profile path. BreadClient is fail-silent: if breadd is
down, breadcrumbs behaves exactly as before.
Document the contract in EVENTS.md. CLAUDE.md now points at
CONTRIBUTING (single-trunk, no three-branch model), bakery, and
EVENTS.md.