Merge pull request #60 from lucannez64/fix/proc-fdinfo-permissions

fix(launcher): prevent inherited MangoHud fdinfo aborts
This commit is contained in:
Kalah authored and GitHub committed 2026-10-25 19:28:41 +01:00
commit ea74dfff65
3 files changed
+47 -1

No files matched your search

+33
View File
@@ -732,3 +732,36 @@ install the QuartzCore and OpenGL changes. Until updated, disable in-game
VSync to use the game's frame cap, as the issue reporter confirmed. Physical
scanout timing still depends on the driver and desktop compositor; the fix
has standalone regression coverage but needs an in-game timing retest.
## Installer aborts on `/proc/<pid>/fdinfo`
[Issue #38](https://github.com/lucannez64/darling-lol/issues/38) reports an
uncaught `ghc::filesystem::filesystem_error` with `Permission denied` on
`/proc/<pid>/fdinfo`. `ghc::filesystem` is a C++ filesystem library, not evidence
that the Riot installer is written in Haskell.
An independent guest/native Vulkan probe reproduced this exact exception with
MangoHud 0.8.4 enabled on 2026-10-18. MangoHud's `GPU_fdinfo::find_fd()` builds
`/proc/<getpid()>/fdinfo` and uses a throwing directory iterator. Inside Darling,
the native library's PID is in the guest PID namespace while its native `/proc`
view can still refer to host processes: the probe's native PID 35 resolved to an
inaccessible host process. The same probe completed Vulkan instance, device and
swapchain creation with MangoHud disabled. This does not establish the cause of
every installer abort; confirmation from the original reporter remains pending.
The normal launcher now unsets `MANGOHUD` and exports `DISABLE_MANGOHUD=1` before
runtime helpers start, including first-time installation. This disables inherited
implicit MangoHud activation for the launched session without changing the host
configuration. Do not wrap the launcher in `mangohud` or explicitly force its
Vulkan layer. Updating these launcher scripts needs no Darling rebuild. For an
older checkout, use:
```sh
env -u MANGOHUD DISABLE_MANGOHUD=1 ./scripts/installer.sh euw
```
Do not run the installer as root or change `/proc` permissions. If it still
fails, include the exception and whether a host overlay was enabled; redact
account tokens from logs.
Upstream source: [MangoHud 0.8.4 fdinfo scan](https://github.com/flightlessmango/MangoHud/blob/v0.8.4/src/gpu_fdinfo.cpp#L9).
+9 -1
View File
@@ -38,6 +38,7 @@ if record["command"] == "darling":
record["flags"] = {{key: os.environ.get(key) for key in
("RCLOL_APP_ARG3", "RCLOL_APP_ARG3_SLOT", "RCLOL_UX_ARG2", "RCLOL_UX_ARG2_SLOT", "RCLOL_UX_ARG1", "RCLOL_APP_ARGS", "RCLOL_APP_ARG2", "DYLD_INSERT_LIBRARIES", "DYLD_LIBRARY_PATH", "DYLD_FRAMEWORK_PATH", "DARLING_XSHM_LIBRARY",
"WAYLAND_DISPLAY", "XAUTHORITY", "DRI_PRIME", "MESA_NO_ERROR", "__GL_THREADED_OPTIMIZATIONS", "SHELL")}}
record["hud"] = {{key: os.environ.get(key) for key in ("MANGOHUD", "DISABLE_MANGOHUD")}}
with open({str(log)!r}, "a") as output:
output.write(json.dumps(record) + "\\n")
'''
@@ -59,6 +60,8 @@ with open({str(log)!r}, "a") as output:
env["DYLD_INSERT_LIBRARIES"] = "/Users/offline-check/zzlogdir.dylib:/tmp/inherited.dylib"
env["RCLOL_APP_ARGS"] = "--inherited-shim-argument"
env["RCLOL_APP_ARG2"] = "--inherited-shim-argument-2"
env["MANGOHUD"] = "1"
env.pop("DISABLE_MANGOHUD", None)
env["RCLOL_NATIVE_VPX"] = "1"
env["RCLOL_LEAGUE_UX_TUNING"] = "1"
# Inherited legacy settings must not re-enable inspection or unlimited frames.
@@ -90,6 +93,8 @@ with open({str(log)!r}, "a") as output:
], "unexpected automatic helper"
launches = [r for r in records if r["command"] == "darling"]
assert len(launches) == 1, "unexpected launch count"
for record in records:
assert record["hud"] == {"MANGOHUD": None, "DISABLE_MANGOHUD": "1"}, "MangoHud survived before a runtime helper"
launch = launches[0]
assert launch["fds"] == [0, 1, 2], f"inherited descriptors reached the guest: {launch['fds']}"
assert all(launch["flags"][key] is None for key in (
@@ -106,17 +111,20 @@ with open({str(log)!r}, "a") as output:
assert "--log-dir=/Users/offline-check/Library/Logs/Riot Games/Riot Client" in launch["args"], "absolute log directory lost"
# An inherited injection must also be absent for first-time installation.
env["RIOT_LAUNCHER_HOST"] = str(folder / "Install Riot.app/Contents/MacOS/RiotClientServices")
env["DISABLE_MANGOHUD"] = "0" # Inherited settings cannot override launcher policy.
subprocess.run(["sh", str(launcher)], env=env, check=True, capture_output=True, text=True)
install = json.loads(log.read_text().splitlines()[-1])
assert install["args"][0] == env["RIOT_LAUNCHER_HOST"]
assert "--skip-to-install" in install["args"]
assert not any(arg.startswith("--app-root=") for arg in install["args"])
assert install["flags"]["DYLD_INSERT_LIBRARIES"] is None
assert install["hud"] == {"MANGOHUD": None, "DISABLE_MANGOHUD": "1"}
env.pop("RIOT_LAUNCHER_HOST")
env.pop("DYLD_INSERT_LIBRARIES")
subprocess.run(["sh", str(launcher)], env=env, check=True, capture_output=True, text=True)
clean = json.loads(log.read_text().splitlines()[-1])
assert clean["flags"]["DYLD_INSERT_LIBRARIES"] is None
assert clean["hud"] == {"MANGOHUD": None, "DISABLE_MANGOHUD": "1"}
# The opt-in host environment filter drops session metadata but never the launcher's GPU tuning.
env.update({"RCLOL_FILTER_HOST_ENV": "1", "WAYLAND_DISPLAY": "wayland-0", "XAUTHORITY": "/tmp/xauth",
"DRI_PRIME": "1", "SHELL": "/bin/fish"})
@@ -127,7 +135,7 @@ with open({str(log)!r}, "a") as output:
assert filtered["WAYLAND_DISPLAY"] is None and filtered["SHELL"] == "/bin/zsh", "host session metadata survived"
assert (filtered["XAUTHORITY"], filtered["DRI_PRIME"]) == ("/tmp/xauth", "1"), "X11/GPU selection lost"
assert (filtered["MESA_NO_ERROR"], filtered["__GL_THREADED_OPTIMIZATIONS"]) == ("1", "0"), "launcher GPU tuning lost"
print("LAUNCHER_OFFLINE pass=1 installed=PASS installer=PASS inherited_injection=absent runtime=preserved inherited_fds=closed host_env_filter=PASS")
print("LAUNCHER_OFFLINE pass=1 installed=PASS installer=PASS inherited_injection=absent runtime=preserved inherited_fds=closed host_env_filter=PASS mangohud=disabled")
if __name__ == "__main__":
+5
View File
@@ -2,6 +2,11 @@
# Launch Riot Client using the Darling runtime, without library injection.
# Darling supplies Xlib Display pointers to EGL, so select X11 explicitly.
set -eu
# Native MangoHud uses the guest PID against the host /proc view and can abort
# in GPU_fdinfo::find_fd (issue #38). Disable inherited implicit activation
# before any helper can start Darling, including first-time installation.
unset MANGOHUD
export DISABLE_MANGOHUD=1
# Native guest crashes created large system core files and exhausted this disk.
# Address-only diagnostics suffice; bound this runner and its new namespace.
if [ "${RCLOL_CORE_DUMPS:-0}" != 1 ]; then