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-1173GitHub issuePublicReceived

Windows VM 4.0.2: launch fails silently after polkit auth (setgid chmod check can never pass)

Reported by bpidperygora · filed Aug 31, 2026Closed upstream on 2026-10-04 by the merge of PR #12323 (closed by dhh). 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

Windows VM 4.0.2: launch fails silently after polkit auth (setgid chmod check can never pass)revision 1 · captured 2026-09-28 21:24 UTC via poll
Edit: the original root-cause analysis below blamed a kernel regression. That was wrong, and I've rewritten this post. The bit is GNU chmod semantics, not the kernel — thanks to @murilocb for independently landing on the same conclusion in a comment. The failure itself and the code path are unchanged.

Windows VM launch silently fails after polkit auth on 4.0.2: the privileged mount-source check can never pass once the source dir has the setgid bit, because the chmod the script uses cannot clear it.

What happened

After upgrading 4.0.1 → 4.0.2, launching the Windows VM (Apps menu → Windows, omarchy-windows-vm launch) shows the polkit password dialog and then nothing happens. No error, no window. Every retry asks for the password again with no result.

The elevated step exits non-zero and all of its stderr is discarded, because the desktop entry runs with Terminal=false — so from the user's perspective the password is accepted and then nothing happens at all.

Root cause

prepare_caller_mounts() hardens both mount sources by running chmod 0700 on the pinned fds and then requires the resulting mode to be exactly 700:

chmod 0700 -- "/proc/$BASHPID/fd/$storage_fd" "/proc/$BASHPID/fd/$shared_fd" || { ...; return 1; }
storage_mode=$(stat -Lc '%a' "/proc/$BASHPID/fd/$storage_fd" 2>/dev/null) || storage_mode=""
shared_mode=$(stat -Lc '%a' "/proc/$BASHPID/fd/$shared_fd" 2>/dev/null) || shared_mode=""
[[ $storage_mode != 700 || $shared_mode != 700 ]] && { ...; return 1; }

GNU `chmod` preserves a directory's setuid/setgid bits for numeric modes shorter than five octal digits. This is documented, long-standing coreutils behavior. chmod 0700 is therefore incapable of producing 700 from 2700, and the check that follows can never pass. Measured on this box (chmod (GNU coreutils) 9.11, kernel 7.1.9-arch1-2, btrfs):

command on a 2777 directoryresulting mode
chmod 7002700
chmod 07002700 ← what the script does
chmod 00700700
chmod g-s777

It behaves the same through the /proc/$BASHPID/fd/N indirection the script actually uses:

$ exec {fd}<~/Windows                          # mode 2777
$ chmod 0700 -- "/proc/$BASHPID/fd/$fd"
$ stat -Lc %a "/proc/$BASHPID/fd/$fd"          # 2700  → != 700 → return 1

Deterministic on/off proof that this single bit is what kills the launch:

$ stat -c %a ~/Windows                                 # 2700
$ pkexec /usr/bin/omarchy-windows-vm __priv up; echo $?  # 1, no output at all
$ chmod g-s ~/Windows                                  # 700
$ pkexec /usr/bin/omarchy-windows-vm __priv up; echo $?  # 0, container comes up

This is not a one-off from an old install. dockurr/windows chmods the shared mount to 2777 on every container start — after a successful __priv up_wait here, ~/Windows is drwxrwsrwx. So the bit is re-applied by every launch, and since the same strict mode == 700 comparison also lives in mounted_leaf_matches() (and therefore mounts_ready), every launch after the first one fails identically. Recreating the directory buys exactly one launch.

Steps to reproduce

  1. Have a Windows VM whose ~/Windows carries the setgid bit — either from a ≤ 4.0.1 install (drwx--S---) or simply from having started the container once on 4.0.2 (drwxrwsrwx).
  2. Apps menu → Windows, enter the polkit password.
  3. Nothing happens, no error, no window.

Minimal repro of the underlying chmod behavior, no VM involved:

mkdir -m 2700 /tmp/sgdir
chmod 0700 /tmp/sgdir; stat -c %a /tmp/sgdir   # 2700
chmod 00700 /tmp/sgdir; stat -c %a /tmp/sgdir  # 700

Workaround

Strip the bit with a form of chmod that actually clears it, before every launch:

chmod 00700 ~/Windows ~/.windows

If a launch already failed once, the root-owned bind anchor still pins the old inode when you recreate the directory instead of chmod'ing it, and the next attempt dies with protected mount ... no longer matches its home source. In that case unmount the anchor first — see the follow-up comment below. Chmod'ing in place avoids that entirely, since the inode never changes.

This has to be repeated after every container run, so in practice it needs to be wrapped around the launch.

Expected

One or more of:

  • prepare_caller_mounts() and mounted_leaf_matches() clear the bit with a mode that works — chmod 00700, or chmod u-s,g-s followed by chmod 0700 — rather than chmod 0700.
  • Alternatively, relax the comparison to what the hardening actually cares about: correct owner and no group/other access bits, rather than a strict == 700.
  • The failure surfaces to the user (desktop notification, or a visible terminal) instead of dying silently after a successful password prompt. This is the part that makes it undiagnosable for a normal user.

System details

  • Omarchy 4.0.2-1 (upgraded from 4.0.1; VM originally installed in the 4.0.0 era)
  • Kernel: 7.1.9-arch1-2
  • coreutils 9.11
  • Hyprland 0.56.2, SDDM
  • Intel CoffeeLake-H (UHD Graphics 630)
  • Filesystem: btrfs (/@home subvolume, zstd)
View raw text
> **Edit:** the original root-cause analysis below blamed a kernel regression. That was wrong, and I've rewritten this post. The bit is GNU `chmod` semantics, not the kernel — thanks to @murilocb for independently landing on the same conclusion in [a comment](https://github.com/omacom/omarchy/issues/9334). The failure itself and the code path are unchanged.

Windows VM launch silently fails after polkit auth on 4.0.2: the privileged mount-source check can never pass once the source dir has the setgid bit, because the `chmod` the script uses cannot clear it.

## What happened

After upgrading 4.0.1 → 4.0.2, launching the Windows VM (Apps menu → Windows, `omarchy-windows-vm launch`) shows the polkit password dialog and then nothing happens. No error, no window. Every retry asks for the password again with no result.

The elevated step exits non-zero and all of its stderr is discarded, because the desktop entry runs with `Terminal=false` — so from the user's perspective the password is accepted and then nothing happens at all.

## Root cause

`prepare_caller_mounts()` hardens both mount sources by running `chmod 0700` on the pinned fds and then requires the resulting mode to be exactly `700`:

```bash
chmod 0700 -- "/proc/$BASHPID/fd/$storage_fd" "/proc/$BASHPID/fd/$shared_fd" || { ...; return 1; }
storage_mode=$(stat -Lc '%a' "/proc/$BASHPID/fd/$storage_fd" 2>/dev/null) || storage_mode=""
shared_mode=$(stat -Lc '%a' "/proc/$BASHPID/fd/$shared_fd" 2>/dev/null) || shared_mode=""
[[ $storage_mode != 700 || $shared_mode != 700 ]] && { ...; return 1; }
```

**GNU `chmod` preserves a directory's setuid/setgid bits for numeric modes shorter than five octal digits.** This is documented, long-standing coreutils behavior. `chmod 0700` is therefore incapable of producing `700` from `2700`, and the check that follows can never pass. Measured on this box (`chmod (GNU coreutils) 9.11`, kernel `7.1.9-arch1-2`, btrfs):

| command on a `2777` directory | resulting mode |
| --- | --- |
| `chmod 700` | `2700` |
| `chmod 0700` | `2700` ← what the script does |
| `chmod 00700` | `700` |
| `chmod g-s` | `777` |

It behaves the same through the `/proc/$BASHPID/fd/N` indirection the script actually uses:

```
$ exec {fd}<~/Windows                          # mode 2777
$ chmod 0700 -- "/proc/$BASHPID/fd/$fd"
$ stat -Lc %a "/proc/$BASHPID/fd/$fd"          # 2700  → != 700 → return 1
```

Deterministic on/off proof that this single bit is what kills the launch:

```
$ stat -c %a ~/Windows                                 # 2700
$ pkexec /usr/bin/omarchy-windows-vm __priv up; echo $?  # 1, no output at all
$ chmod g-s ~/Windows                                  # 700
$ pkexec /usr/bin/omarchy-windows-vm __priv up; echo $?  # 0, container comes up
```

**This is not a one-off from an old install.** `dockurr/windows` chmods the shared mount to `2777` on every container start — after a successful `__priv up_wait` here, `~/Windows` is `drwxrwsrwx`. So the bit is re-applied by every launch, and since the same strict `mode == 700` comparison also lives in `mounted_leaf_matches()` (and therefore `mounts_ready`), *every* launch after the first one fails identically. Recreating the directory buys exactly one launch.

## Steps to reproduce

1. Have a Windows VM whose `~/Windows` carries the setgid bit — either from a ≤ 4.0.1 install (`drwx--S---`) or simply from having started the container once on 4.0.2 (`drwxrwsrwx`).
2. Apps menu → Windows, enter the polkit password.
3. Nothing happens, no error, no window.

Minimal repro of the underlying `chmod` behavior, no VM involved:

```bash
mkdir -m 2700 /tmp/sgdir
chmod 0700 /tmp/sgdir; stat -c %a /tmp/sgdir   # 2700
chmod 00700 /tmp/sgdir; stat -c %a /tmp/sgdir  # 700
```

## Workaround

Strip the bit with a form of `chmod` that actually clears it, before every launch:

```bash
chmod 00700 ~/Windows ~/.windows
```

If a launch already failed once, the root-owned bind anchor still pins the old inode when you recreate the directory instead of chmod'ing it, and the next attempt dies with `protected mount ... no longer matches its home source`. In that case unmount the anchor first — see the follow-up comment below. Chmod'ing in place avoids that entirely, since the inode never changes.

This has to be repeated after every container run, so in practice it needs to be wrapped around the launch.

## Expected

One or more of:

- `prepare_caller_mounts()` and `mounted_leaf_matches()` clear the bit with a mode that works — `chmod 00700`, or `chmod u-s,g-s` followed by `chmod 0700` — rather than `chmod 0700`.
- Alternatively, relax the comparison to what the hardening actually cares about: correct owner and no group/other access bits, rather than a strict `== 700`.
- The failure surfaces to the user (desktop notification, or a visible terminal) instead of dying silently *after* a successful password prompt. This is the part that makes it undiagnosable for a normal user.

## System details

- Omarchy 4.0.2-1 (upgraded from 4.0.1; VM originally installed in the 4.0.0 era)
- Kernel: 7.1.9-arch1-2
- coreutils 9.11
- Hyprland 0.56.2, SDDM
- Intel CoffeeLake-H (UHD Graphics 630)
- Filesystem: btrfs (`/@home` subvolume, zstd)

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.