Distilled from #738: the watcher now prunes a watched project whose root
directory has genuinely disappeared - deleting the cached DB (+wal/shm,
validated name, cache-dir-only paths) and removing the watch entry - so
vanished worktrees stop being watched forever (#286).
Hardened beyond the original PR to remove a data-loss hazard (the cached
DB can hold user-authored data such as the ADR, unrecoverable once
deleted):
- Only ENOENT/ENOTDIR stat failures count as missing. Any other failure
(EACCES, EIO, transient mounts, macOS TCC revocation) resets the
streak and logs watcher.root_stat_error with the errno; Windows
(mingw/UCRT) maps not-found to ENOENT so the check holds there.
- Pruning requires BOTH >=3 consecutive missing polls AND a sustained-
absence grace window since the streak's first miss (default 600s,
override via CBM_WATCHER_PRUNE_GRACE_S), tracked with monotonic
cbm_now_ms.
- Root reappearance resets streak + timestamp (watcher.root_restored).
- The pruned entry is released via the deferred-free list poll_once
drains (one freeing model shared with cbm_watcher_unwatch).
Limitation: only currently-watched projects are pruned; stale DBs left
by older sessions are out of scope.
Co-authored-by: pcristin <xxxokzxxx@protonmail.com>
Signed-off-by: Martin Vogel <martin.vogel.tech@gmail.com>