Proof Portal

Project overview

Omarchy

ProbeLabs65 findings · 95 requirements

A proof layer — requirements, tests and verified fixes — for two of Omarchy's subsystems: the application menu (launcher scripts, QML model, JSONC config, search and selection) and the lock screen (lock scripts, QML, PAM authentication). Scope is deliberately limited to those components of omacom/omarchy; the rest of the distribution is not covered.

Inbox
ReportR-5058GitHub issuePublicReceived

omarchy-windows-vm: launch fails silently after the first success (setgid re-chmod loop on ~/Windows)

Reported by ZuluPilgrim · filed Sep 12, 2026Closed upstream on 2026-09-20 by bjarneo via an automated message, as a duplicate of #9334 (R-1173). GitHub close reason: completed.

Received and recorded verbatim. Nothing has been checked yet.

At a glance

1 · What is claimed?
Only the report text below — no validator has restated it as checkable claims yet.
2 · What does it affect?
Not yet mapped to any requirement or component.
3 · Is it reproducible?
No validation has been run yet.
4 · What remains unclear?
  • Not validated yet: no claims, no reproducer.
5 · What happens next?
Our staff decide whether the report is valid. Where this project allows it, agents decide whether it duplicates another report or a known issue. No decision has been recorded yet.

Original report

omarchy-windows-vm: launch fails silently after the first success (setgid re-chmod loop on ~/Windows)revision 1 · captured 2026-10-04 12:10 UTC via poll

What happened

After the compose file is migrated to the new root-owned location (/var/lib/omarchy/windows/docker-compose.yml), every subsequent `omarchy-windows-vm launch`/`up`/`up_wait` call keeps re-validating and re-`chmod`ing the legacy shared-folder source directory (`~/Windows`), and that re-validation reliably fails after the first successful launch — with the VM's own critical desktop notification "Failed to start Windows VM" and no diagnostic text printed anywhere (not on the terminal, not in the journal for the launching scope).

Root cause chain, confirmed by tracing with bash -x through pkexec omarchy-windows-vm __priv up_wait:

  1. assert_mounts_safe() unconditionally calls prepare_caller_mounts() on every privileged action when EUID == 0 (i.e. on every up/up_wait, not just the first-time migration):
   if ((EUID == 0)); then
     prepare_caller_mounts || return 1
   fi
  1. prepare_caller_mounts() re-opens the legacy source directories (~/.windows, ~/Windows) and requires their mode to read back as exactly 700 after doing chmod 0700 on them:
   chmod 0700 -- "/proc/$BASHPID/fd/$storage_fd" "/proc/$BASHPID/fd/$shared_fd" || { ...; return 1; }
   storage_mode=$(stat -Lc '%a' ...)
   shared_mode=$(stat -Lc '%a' ...)
   if [[ $storage_mode != 700 || $shared_mode != 700 ]]; then
     ...
     return 1
   fi

This branch has no `echo` on failure — a silent return 1 that bubbles all the way up to "Failed to start Windows VM" with zero explanation.
3. In my case ~/Windows had (and, more importantly, kept getting) a setgid bit (2700 instead of 0700) — something tied to the running VM's live shared-folder passthrough (this directory is bind-mounted through to the dockurr/windows container as /shared for the whole time the VM runs) keeps re-adding the setgid bit shortly after it's cleared.
4. chmod 0700 <path> (a 3-significant-digit numeric mode) does not clear a pre-existing setgid bit — only chmod 2700/chmod g-s/symbolic notation does. So the script's own remediation chmod 0700 call in step 2 is a silent no-op against a directory that already has setgid set, and the mode check keeps failing.

Net effect

  • The first launch after migration succeeds (the source dirs happen to be clean at that moment).
  • Every launch after that fails, silently, with only a generic "Failed to start Windows VM" notification — because the always-on re-validation in step 1 keeps re-discovering the setgid bit that something (very likely the VM's own SMB/9p sharing of /shared with the Windows guest) keeps restoring.
  • There is no way for a user to know why it failed short of bash -x-tracing the privileged helper — none of omarchy-windows-vm status, launch, or the desktop notification give any hint.

Expected behavior

  • prepare_caller_mounts's remediation chmod should actually clear pre-existing special bits (e.g. chmod -- 0700 numeric mode doesn't do this — use chmod g-s,u-s,-t or an explicit non-abbreviated form, or just retry with chmod 2700 ... && chmod 0700 ...).
  • More importantly: re-verifying/re-establishing the legacy-source bind mounts on every single launch (even when the compose is already fully migrated and the container/mounts are already up and healthy) seems unnecessary and is what turns a one-off permission quirk into a permanent failure loop. Consider skipping prepare_caller_mounts when the expected protected mounts are already active and healthy (mounts_ready already exists and is checked separately).
  • At minimum, any failure branch that can end in "Failed to start Windows VM" should surface the actual reason (even just to the journal) instead of a bare return 1.

Steps to reproduce

  1. Have an existing Windows VM installed under the older ~/.config/windows/docker-compose.yml layout with a ~/Windows shared-folder directory that has (or acquires) a setgid bit.
  2. Upgrade Omarchy to a version that migrates the compose to /var/lib/omarchy/windows/docker-compose.yml and adds the assert_mounts_safe/prepare_caller_mounts re-validation on every launch.
  3. Launch the Windows VM once — it migrates and starts successfully.
  4. Launch it again while it's still running — it fails with "Failed to start Windows VM" and no further explanation.
  5. chmod g-s ~/Windows and launch again — succeeds. Wait a few minutes while the VM keeps running, launch a third time — fails again, and stat -c '%a' ~/Windows shows 2700 again.

System details

  • Omarchy 4.0.3-1
  • Hyprland 0.56.2-2
  • Docker 29.7.2 / Docker Compose plugin 5.5.1
  • CPU: Intel Xeon E5-1660 v4
  • GPU: NVIDIA GeForce GTX 1080 Ti (nvidia driver)
  • ~ filesystem: btrfs
View raw text
## What happened

After the compose file is migrated to the new root-owned location (`/var/lib/omarchy/windows/docker-compose.yml`), **every subsequent `omarchy-windows-vm launch`/`up`/`up_wait` call keeps re-validating and re-`chmod`ing the legacy shared-folder source directory (`~/Windows`)**, and that re-validation reliably fails after the first successful launch — with the VM's own critical desktop notification "Failed to start Windows VM" and **no diagnostic text printed anywhere** (not on the terminal, not in the journal for the launching scope).

Root cause chain, confirmed by tracing with `bash -x` through `pkexec omarchy-windows-vm __priv up_wait`:

1. `assert_mounts_safe()` unconditionally calls `prepare_caller_mounts()` on every privileged action when `EUID == 0` (i.e. on every `up`/`up_wait`, not just the first-time migration):
   ```
   if ((EUID == 0)); then
     prepare_caller_mounts || return 1
   fi
   ```
2. `prepare_caller_mounts()` re-opens the legacy source directories (`~/.windows`, `~/Windows`) and requires their mode to read back as exactly `700` after doing `chmod 0700` on them:
   ```
   chmod 0700 -- "/proc/$BASHPID/fd/$storage_fd" "/proc/$BASHPID/fd/$shared_fd" || { ...; return 1; }
   storage_mode=$(stat -Lc '%a' ...)
   shared_mode=$(stat -Lc '%a' ...)
   if [[ $storage_mode != 700 || $shared_mode != 700 ]]; then
     ...
     return 1
   fi
   ```
   This branch has **no `echo` on failure** — a silent `return 1` that bubbles all the way up to "Failed to start Windows VM" with zero explanation.
3. In my case `~/Windows` had (and, more importantly, *kept getting*) a setgid bit (`2700` instead of `0700`) — something tied to the running VM's live shared-folder passthrough (this directory is bind-mounted through to the dockurr/windows container as `/shared` for the whole time the VM runs) keeps re-adding the setgid bit shortly after it's cleared.
4. `chmod 0700 <path>` (a **3-significant-digit** numeric mode) does **not** clear a pre-existing setgid bit — only `chmod 2700`/`chmod g-s`/symbolic notation does. So the script's own remediation `chmod 0700` call in step 2 is a silent no-op against a directory that already has setgid set, and the mode check keeps failing.

## Net effect

- The **first** launch after migration succeeds (the source dirs happen to be clean at that moment).
- **Every launch after that** fails, silently, with only a generic "Failed to start Windows VM" notification — because the always-on re-validation in step 1 keeps re-discovering the setgid bit that something (very likely the VM's own SMB/9p sharing of `/shared` with the Windows guest) keeps restoring.
- There is no way for a user to know *why* it failed short of `bash -x`-tracing the privileged helper — none of `omarchy-windows-vm status`, `launch`, or the desktop notification give any hint.

## Expected behavior

- `prepare_caller_mounts`'s remediation chmod should actually clear pre-existing special bits (e.g. `chmod -- 0700` numeric mode doesn't do this — use `chmod g-s,u-s,-t` or an explicit non-abbreviated form, or just retry with `chmod 2700 ... && chmod 0700 ...`).
- More importantly: re-verifying/re-establishing the legacy-source bind mounts on *every single launch* (even when the compose is already fully migrated and the container/mounts are already up and healthy) seems unnecessary and is what turns a one-off permission quirk into a permanent failure loop. Consider skipping `prepare_caller_mounts` when the expected protected mounts are already active and healthy (`mounts_ready` already exists and is checked separately).
- At minimum, any failure branch that can end in "Failed to start Windows VM" should surface the actual reason (even just to the journal) instead of a bare `return 1`.

## Steps to reproduce

1. Have an existing Windows VM installed under the older `~/.config/windows/docker-compose.yml` layout with a `~/Windows` shared-folder directory that has (or acquires) a setgid bit.
2. Upgrade Omarchy to a version that migrates the compose to `/var/lib/omarchy/windows/docker-compose.yml` and adds the `assert_mounts_safe`/`prepare_caller_mounts` re-validation on every launch.
3. Launch the Windows VM once — it migrates and starts successfully.
4. Launch it again while it's still running — it fails with "Failed to start Windows VM" and no further explanation.
5. `chmod g-s ~/Windows` and launch again — succeeds. Wait a few minutes while the VM keeps running, launch a third time — fails again, and `stat -c '%a' ~/Windows` shows `2700` again.

## System details

- Omarchy 4.0.3-1
- Hyprland 0.56.2-2
- Docker 29.7.2 / Docker Compose plugin 5.5.1
- CPU: Intel Xeon E5-1660 v4
- GPU: NVIDIA GeForce GTX 1080 Ti (nvidia driver)
- `~` filesystem: btrfs

Validation

Not checked yet. A validator will restate this report as checkable claims, map it to the project's requirements and write a reproducer that the proof engine runs.

Linked

Not linked to any known issue, other report or change yet.

Decision

Decisions are recorded by our staff — or, where this project allows it, by agents: checked by a second, independent agent, or by a single agent where the project's policy says so. Any decision reached so far is shown below.

No decision has been recorded yet.