MangoHud logs one GPU. On a hybrid box (discrete NVIDIA/AMD beside an AMD/Intel iGPU) its default often latches onto the idle iGPU, so every gpu_* column reads ~0 while the discrete card does the rendering. Detect the actual gaming GPU — any vendor, single- or multi-GPU — and pin it via gpu_list. Selection: single GPU -> that one; discrete NVIDIA preferred; otherwise the card with the most VRAM. Override with MANGOHUD_LOGGER_GPU. Verified against MangoHud's own enumeration (gpu_list=0 -> renderD128, RTX 5060 Ti) and 7 synthetic layouts incl. NVIDIA as the second node. Also make CPU telemetry work across AMD and Intel. cpu_power was logging 0 because the RAPL energy counters are root-only since CVE-2020-8694 (same intel-rapl powercap path on both vendors). Add: - doctor: read-only GPU/CPU telemetry readiness report - fix-cpu-power: install a udev rule making RAPL counters user-readable - enable-time warnings pointing at the fix CPU temp already works via hwmon (k10temp/zenpower/coretemp). Default no-arg behavior (toggle on/off) is unchanged. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
10 KiB
Executable file
mangohud-logger
One-touch toggle for MangoHud CSV logging on Linux gaming-launcher systems
(SteamOS Game Mode, DeckShift, super-alt-S, plain gamescope-session-plus, or
any setup that already uses MangoHud).
Run the script — it switches logging on if it's off, off if it's on. CSV
samples land in ~/Downloads/mango-logs/. That's the entire interface.
Why this exists
Getting MangoHud to actually write logs from a Steam-via-gamescope game turns out to be a multi-step setup, and every step has a non-obvious gotcha. Worse, the right setup differs depending on which gamescope session manager your distro ships. This script detects that and handles it so you don't have to.
What it changes
The script writes marker-tagged files (so it can clean them up on disable, and won't trample anything you wrote by hand):
-
~/.config/MangoHud/MangoHud.conf— appends a marker-bracketed block withoutput_folder,autostart_log=1,log_duration=0(= until you quit),log_interval=100,toggle_logging=Shift_L+F2, ano_display=0override, and agpu_list=<index>pin (see GPU selection). (Also serves as the on/off state marker.) -
~/.config/environment.d/95-mangohud-logger.conf— contains:MANGOHUD=1so the Vulkan loader auto-injects MangoHud into every game.MANGOHUD_CONFIG=<inline copy of the logging keys>. This is the important one for SteamOS Game Mode — see Game Mode below.
Requires a logout/login to take effect (systemd-user only reads
environment.d/*.confat session start). -
~/.config/gamescope-session-plus/sessions.d/steam— only written on thegamescope-session-plussession flavor (see flavor detection below). A user-level override that unsets the system'sMANGOHUD_CONFIGFILEand turns offSTEAM_USE_MANGOAPP. Not written on stock SteamOS.
When you toggle it off, the script removes everything it wrote.
GPU selection
MangoHud logs stats for one GPU. On a hybrid machine — a discrete
NVIDIA/AMD card alongside an AMD/Intel iGPU (common on modern AMD desktops,
laptops, and handhelds) — MangoHud's default frequently latches onto the idle
iGPU, so every gpu_* column in the CSV reads ~0 (0 % load, idle clocks, idle
power) even while the discrete card does all the rendering.
On enable, the script auto-detects the GPU that's actually rendering games and
pins MangoHud to it with gpu_list=<index>. It's vendor-agnostic:
- Single GPU (any vendor) → that GPU.
- Discrete NVIDIA present → the NVIDIA card.
- Two AMD/Intel GPUs → the one with the most VRAM (the discrete card; iGPUs report little or none).
It works by mapping DRM render nodes (renderD128, renderD129, …) to
MangoHud's gpu_list index order. The chosen GPU is printed on enable:
:: gpu logged: gpu_list=0 → renderD128 (NVIDIA), 2 GPU(s) detected
If the guess is wrong, override it:
MANGOHUD_LOGGER_GPU=amd ./mangohud-logger.sh # or: nvidia | intel
MANGOHUD_LOGGER_GPU=1 ./mangohud-logger.sh # or an explicit gpu_list index
NVIDIA note: MangoHud reads NVIDIA load/power/clocks via NVML. If NVML (
libnvidia-ml, shipped withnvidia-utils) is missing, the script warns you — without it the NVIDIAgpu_*columns stay at 0.
Session-flavor detection
Game Mode is launched differently on different distros, and the fix differs
too. On enable, the script detects which one you have (detect_gs_flavor):
| Flavor | Detected by | What the script does |
|---|---|---|
plus |
/usr/share/gamescope-session-plus/sessions.d/steam exists |
Writes the sessions.d/steam override (file #3). |
steamos |
/usr/lib/steamos/gamescope-session exists |
Skips file #3; relies on MANGOHUD_CONFIG (file #2). See below. |
none |
neither | Desktop-only; MANGOHUD=1 is enough for Vulkan games. |
SteamOS Game Mode
Stock SteamOS (e.g. 3.x "holo") launches Game Mode via
/usr/lib/steamos/gamescope-session, not gamescope-session-plus. That
session script unconditionally does:
export STEAM_USE_MANGOAPP=1
export MANGOHUD_CONFIGFILE="$tmpdir/mangohud.config" # written with just "no_display"
and it sources no user override file — so the old sessions.d/steam trick
does nothing here, and you can't override STEAM_USE_MANGOAPP from
environment.d (the session exports it afterwards).
How logging actually works here: the on-screen overlay in Game Mode is
mangoapp (a compositor overlay), and mangoapp is MangoHud — it can write
CSV logs itself. Steam launches mangoapp with your systemd user environment, so
it inherits the MANGOHUD_CONFIG from file #2. MANGOHUD_CONFIG takes
precedence over the session's no_display MANGOHUD_CONFIGFILE, so mangoapp
picks up autostart_log/output_folder and logs every game — no per-game
launch options needed.
Notes:
- Logs are named
mangoapp_<timestamp>.csv(the logger is mangoapp, not the in-game layer), so a file spans a Game Mode session rather than one-per-game. - You must fully restart into Game Mode once after enabling (log out/in or
reboot) so mangoapp inherits
MANGOHUD_CONFIG. If you enable while already in Game Mode, that session won't have it and nothing logs. - Verified on SteamOS 3.9 with MangoHud 0.8.3-rc1: a Proton game (DREDGE) in
Game Mode produced a 1039-row
mangoapp_*.csvof real fps/frametime data.
Per-game fallback (if you don't want to restart the session, or want the in-game Vulkan layer instead of mangoapp): set this in a game's Steam → Properties → Launch Options:
MANGOHUD_CONFIGFILE=$HOME/.config/MangoHud/MangoHud.conf mangohud %command%
Gotchas it works around
-
no_displayblocksautostart_log. MangoHud'sautostart_logrides on the render hook thatno_displaydisables, so the log never starts. The script's block ends withno_display=0. Tradeoff: while logging is on, the HUD is visible during games. -
The system session forces a
no_displayconfig file. Both session flavors exportMANGOHUD_CONFIGFILEpointing at a temp file containing onlyno_display, which would suppress your real config. Onplusthe script unsets that var; onsteamostheMANGOHUD_CONFIGenv var overrides it. -
Steam uses
mangoappinstead of the in-game Vulkan layer in Game Mode.STEAM_USE_MANGOAPP=1. Onsteamosyou can't turn this off globally — so the script leans into it and lets mangoapp do the logging (see above). Onplusthe override setsSTEAM_USE_MANGOAPP=0to use the in-game layer. -
log_duration=0means "log forever". Empirically0= log until you quit or hit the toggle key. -
MANGOHUD=1only injects the Vulkan layer. OpenGL-only games still needmangohud %command%in Steam launch options or anLD_PRELOADwrapper.
Install
Requires mangohud (and lib32-mangohud for 32-bit games). On Arch / SteamOS:
sudo pacman -S mangohud lib32-mangohud
Then:
git clone https://github.com/28allday/mangohud-logger-steamos.git
cd mangohud-logger-steamos
chmod +x mangohud-logger.sh
./mangohud-logger.sh
Or copy the script anywhere on $PATH:
install -Dm755 mangohud-logger.sh ~/.local/bin/mangohud-logger
mangohud-logger
Usage
./mangohud-logger.sh # toggle logging on/off (default)
./mangohud-logger.sh doctor # report GPU/CPU telemetry readiness (no changes)
./mangohud-logger.sh fix-cpu-power # make RAPL CPU-power counters readable (sudo)
./mangohud-logger.sh help # usage
Run with no argument to toggle: first run enables, second disables. After the first enable, log out and back in (Game Mode users: fully restart into Game Mode) so the env vars become effective. You only need to do that once.
Before your first benchmark, run doctor — it tells you exactly which columns
will hold real data and what (if anything) needs fixing:
:: GPUs (DRM render nodes):
renderD128 (NVIDIA)
renderD129 (AMD)
✓ will log: gpu_list=0 → renderD128 (NVIDIA), 2 GPU(s) detected
✓ NVML present → NVIDIA load/power/clocks will log
:: CPU: AMD
✓ temp source: hwmon 'k10temp' → cpu_temp will log
! power (RAPL): root-only → cpu_power = 0. Fix: mangohud-logger.sh fix-cpu-power
In-game keys (set by the script's MangoHud block):
| Key | Action |
|---|---|
Shift+F2 |
Toggle logging on/off mid-game |
Your existing toggle_hud key |
Hide the HUD overlay (logging keeps running) |
CSV files appear in ~/Downloads/mango-logs/. Drop them into
https://flightlessmango.com/ for graphs, or open in a spreadsheet.
CPU power (cpu_power column reads 0?)
MangoHud reads CPU package power from the RAPL powercap energy counters. Since
CVE-2020-8694 those counters are root-only (mode 0400), so user-mode
MangoHud can't read them and cpu_power logs as 0. This is the same on AMD
and Intel — the powercap interface is named intel-rapl on both (it's the
framework name; on AMD intel_rapl_msr feeds it from the Zen RAPL MSRs).
fix-cpu-power installs a udev rule
(/etc/udev/rules.d/60-mangohud-logger-rapl.rules) that makes energy_uj
user-readable, and applies it immediately:
./mangohud-logger.sh fix-cpu-power
Security note: this re-exposes the low-severity PLATYPUS power side-channel. Fine for a personal gaming/benchmark box; skip it on shared or multi-user machines. Remove the rule file to revert.
CPU temperature needs no fix — it comes from hwmon (k10temp/zenpower on
AMD, coretemp on Intel) and works out of the box.
Compatibility
- SteamOS Game Mode (
/usr/lib/steamos/gamescope-session) — logs via mangoapp; see Game Mode. - DeckShift (28allday/DeckShift) — gamescope-session-plus based.
- super-alt-S (28allday/super-alt-S-cachy-deckmode) — KDE-Plasma gaming mode on CachyOS.
- Plain
gamescope-session-pluson any Arch-based distro. - Steam without gamescope — works too; the gamescope override becomes a no-op.
- Non-systemd distros — the
environment.dfile won't be read; setMANGOHUD=1(andMANGOHUD_CONFIG) via your distro's env-var mechanism.
Honours XDG
Log folder is $XDG_DOWNLOAD_DIR/mango-logs (resolved via xdg-user-dir),
config dir is $XDG_CONFIG_HOME — works on non-English locales.
License
MIT