Commit d81b9a9f by PLN (Algolia)

perf: the cap is thermal-pilot's rung-1 floor, and gig-up now reads knobs not wishes

Proven with the rig's own hand at 01:12, after being wrong about it twice.
thermal-mode-apply performance wrote cap=100 and EPP=balance_performance; six
seconds later thermal-pilot logged 'drift: live knobs no longer match rung 1
-- reasserted' and put back 65 and balance_power. thermald was already STOPPED
at the time and the cap still moved, so thermald is innocent and I owe it a
restart -- the box has had no thermal daemon since 00:40 on my bad call.

It is not a leftover, it is the design: rung_knobs 1 is '0
balance_power' with RUNG1_PCT defaulting to 65, and profile_params performance
is '1 2 2600' -- floor rung 1, ceiling rung 2, noise brake at 2600 rpm. The
fan idles near 2800, so the brake is always armed: six climbs to rung 2
tonight, six brakes back within five seconds. Under this profile 65% is the
floor and no hand-written value survives it, which means the mangled paste
cost nothing.

Suspected upstream cause, and it may close for a cable: the helper reported
PL1=25W PL2=50W on a '45W USB-C PD source' while thermal-mode.conf records
STOCK PL1=45W/PL2=90W. Half the power budget means hotter for the same work,
which is what keeps the fan over the brake. Test the Dell barrel charger
first.

ensure_perf used to print 'thermal-mode performance holding' sourced from
MODE= in the conf file, while the gate twelve lines below in the same log
FAILED on max_perf_pct=65. Both were correct -- the file records the last
intent, not the live posture. It now asserts the gear, waits out the pilot's
reassert, reads the four knobs, and either says VERIFIED or names the owner
and the reason. No sudo line to paste and no memory to rely on, which is what
was asked for.

tools/fix-ardour-rt.sh closes the Ardour item as a script rather than
instructions: dry-run default, --apply, --revert, idempotent, backs up, and it
patches BOTH writers because perf-audio:565/573 re-arms what parvagues-protect
stops. Verified against the live root files (all four patterns match exactly
once) and applied to copies first: both still parse, the prio>0 guard is in,
and scsynth/sclang/pipewire priorities are untouched.
parent 2ecba716
......@@ -763,3 +763,116 @@ records. Bound once at 10:38 and deaf for fourteen hours.
**Verify by the records, never by the header**: `"midi": true` has been
lying for ten sessions because `available()` only asks whether aseqdump is
installed.
## Thu 24, 01:20 — the cap is thermal-pilot's rung-1 FLOOR, proven by the rig's own hand
I told PLN to stop `thermald` and lift the cap by hand. **Both halves of that were
wrong, and the correction matters more than the advice.**
**thermald is innocent.** It is `--adaptive` and its
`/etc/thermald/thermal-cpu-cdev-order.xml` does list `intel_pstate`, which is why
it looked guilty. But it was **stopped** at 00:40 and `max_perf_pct` stayed at 65
for the next forty minutes. A writer that is not running is not the writer.
**Restart it** (`sudo systemctl start thermald`) — the box has been sitting with
no thermal daemon since 00:40 for no reason, and that one is on me.
**The writer is `thermal-pilot.service`**, the rig's own ladder, and the proof is
its own log. At 01:12, using the sanctioned NOPASSWD helper:
```
BEFORE cap=65 epp=balance_power
sudo -n thermal-mode-apply performance -> cap=100 epp=balance_performance
t+6s thermal-pilot: drift: live knobs no longer match rung 1 -- reasserted
AFTER cap=65 epp=balance_power
```
**Six seconds.** So the mangled paste cost nothing: `echo 100 | sudo tee` would
have been undone before the prompt came back.
**And it is not a leftover to clear — it is the design.** From the sources:
- `thermal-pilot`: `rung_knobs 1` = `"0 $RUNG1_PCT balance_power"`, and
`RUNG1_PCT=${RUNG1_PCT:-65}`. **65 is rung 1's definition.**
- `thermal-pilot`: `profile_params performance` = `"1 2 ${PERF_FAN_SOFT:-2600}"` —
floor **rung 1**, ceiling rung 2, noise brake **2600 rpm**. Its own header says
it plainly: *"performance: floor of capped turbo, braked at 2600 rpm"*.
- The fan idles near **2800 rpm**, so the brake is always armed. Tonight the pilot
climbed `1 -> 2` **six times** and was braked back within 5 s every single time:
`rung 2 -> 1 (noise brake: fan 2802 rpm > 2600 for 30s)`.
Under `MODE=performance`, **65 % is the best this box will hold while the fan sits
above 2600 rpm.** No hand-written value survives it.
### The upstream cause is probably the CHARGER, and TODO already said so
`thermal-mode-apply performance` reported `PL1=25W PL2=50W … budget: 45W USB-C PD
source`, while `/etc/thermal-mode.conf` records `STOCK_intel_rapl_0_PL1=45000000`
(45 W) and `PL2=90000000`. So the box is on the **USB-C travel charger**, running
at roughly half its stock power budget. A halved PL1 means the same work is done
slower and hotter, the fan climbs past 2600, the noise brake fires, and the pilot
pins rung 1. *"Bring the proper Dell charger"* was already on the 5pm list as a
measurement-hygiene item; it is now a suspected **cause** of the cap.
**Test it first thing, because it may cost nothing:** plug the Dell barrel
charger, `sudo -n /usr/local/sbin/thermal-mode-apply performance`, wait 30 s, read
`max_perf_pct`. If PL1 reads 45 W and the fan settles under 2600, the cap holds by
itself and the whole item closes with a cable.
### If the charger is not enough, it is a choice — and it is PLN's, not mine
I have been wrong about this writer twice tonight. So: the options, with the
trade, and no pick.
- **(a) Raise the brake.** `PERF_FAN_SOFT` is an env default in `thermal-pilot`,
so a root drop-in on `thermal-pilot.service` with
`Environment=PERF_FAN_SOFT=3400` lets rung 2 hold. Cost: a louder laptop. At a
gig with a PA, fan noise is free — this is the cheapest real fix.
- **(b) Raise the floor.** A drop-in with `Environment=RUNG1_PCT=100` makes rung 1
harmless. Cost: the ladder loses its middle step everywhere, including on
battery at a café. Blunter than (a).
- **(c) Stop the pilot for the set.** Its exit trap writes rung 0, which is
`"1 100 power"` — **cap 100 but TURBO OFF**, which is not what a set wants.
Read the table before reaching for this one; it is not "uncapped".
- **(d) Leave it at 65 %.** Measured tonight: with Ardour's GUI threads demoted,
xruns went to **0 in 14 minutes** *at 65 %*. The cap may simply not be the
binding constraint once the RT bug is gone. Cheapest of all, if the rehearsal
agrees.
`gig-up.sh` no longer has an opinion here, but it now tells the truth (see below).
### Landed tonight, no root needed
- [x] **`gig-up.sh ensure_perf` reads the KNOBS, never the mode file.** It used to
print *"thermal-mode performance holding"* from `MODE=` in
`/etc/thermal-mode.conf` while the gate, twelve lines later in the same log,
FAILED on `max_perf_pct=65`. Both were right: the file records the last
intent, not the live posture. It now asserts the gear, sleeps 8 s so the
pilot has reasserted, reads `max_perf_pct` / EPP / `no_turbo` / PL1, and
either says **VERIFIED** or names the owner — *"owner = thermal-pilot
(profile 'performance'), and it reasserts within ~6s"* — plus the PL1-vs-45W
charger hint. **No sudo line to paste, and no memory to rely on.**
- [x] **`tools/fix-ardour-rt.sh`** — the #1 blocker, as a script instead of
instructions. Dry-run by default, `--apply` to write, `--revert` to undo,
idempotent, backs both files up, refuses any file whose expected text it
cannot find, and `bash -n`s the result before restarting anything. It patches
**both** writers (`parvagues-protect`'s `ardour:80` -> `ardour:0` plus the
`prio > 0` guard that a 0 requires, and `perf-audio`'s two Ardour `chrt`
calls at ~565/573), restarts `parvagues-protect`, restarts `thermald`, and
prints the acceptance test. Ardour keeps its OOM shield, its ionice and its
memlock; scsynth/90, sclang/85 and pipewire/95 are untouched.
**Verified before you run it:** all four patch patterns match the live root
files exactly once, and the patch was applied to *copies* — both files still
`bash -n` clean, the guard is in place, and nothing else moved.
### Thursday morning, in order
1. `sudo systemctl start thermald` — my mistake, 30 seconds.
2. `sudo tools/fix-ardour-rt.sh` (read the diff) then `--apply`. Then the
acceptance test it prints: **launch Ardour from the DESKTOP ICON**, because a
terminal or Bridge launch inherits `unlimited` and proves nothing.
3. **`sudo systemctl start parvagues-protect`** — it is OFF right now, on purpose,
which means scsynth currently has **no OOM shield and no FIFO/90**. Step 2 is
what makes it safe to turn back on.
4. Plug the **Dell barrel charger**, re-assert the gear, read the cap. Decide (a)
or (d) above with the rehearsal's ears.
5. `systemctl --user start midiviz` if you want the lens.
......@@ -107,17 +107,60 @@ ensure_perf(){
# The gig posture is thermal-mode `performance`: turbo on, governor POWERSAVE +
# EPP balance_performance, RT audio. NOT governor=performance: that pins EPP and
# runs every idle wakeup at ~4-5 GHz (package 96 C at 5 % load, 2026-09-23).
local mode noturbo
mode=$(sed -n 's/^MODE=//p' /etc/thermal-mode.conf 2>/dev/null)
# READ THE KNOBS, NEVER THE MODE FILE.
#
# 2026-09-24, 00:00: this function printed "thermal-mode performance holding —
# turbo headroom for MIDI bursts" while the gate, twelve lines later in the
# same log, read `max_perf_pct=65` and FAILED on it. Both were correct.
# `/etc/thermal-mode.conf` says `MODE=performance` because the mode WAS
# applied; it records the last intent, not the live posture, and no file can
# know what wrote the sysfs node afterwards. So a green line sourced from that
# file is a green line about a wish.
#
# And something does write it afterwards, every time. Measured with the rig's
# own hand at 01:12: `thermal-mode-apply performance` set cap 100 / EPP
# balance_performance, and SIX SECONDS later `thermal-pilot` logged "drift:
# live knobs no longer match rung 1 -- reasserted" and put back 65 /
# balance_power. Not thermald (stopped at the time, and the cap still moved) —
# the rig's OWN ladder. `thermal-pilot`'s `performance` profile is
# "floor 1, ceiling 2, brake 2600rpm", rung 1 IS `RUNG1_PCT=65`, and the fan
# idles near 2800, so the noise brake yanks every climb back within seconds.
# Under this profile 65% is not a leftover to clear: it is the floor, by
# design, and no amount of `echo 100 | sudo tee` survives it.
#
# Therefore: assert the mode (idempotent, and the only sanctioned writer),
# then LOOK, then say what is true and name who owns it. A launcher that
# cannot fix something must at least never claim it did.
local pct epp noturbo pl1 pilot rung
info "perf: asserting the gig gear, then verifying the live knobs…"
PYTHONPATH="$DIR/tools/bridge" python3 -c \
"import perf,sys; ok,m=perf.set_mode('performance'); print(m); sys.exit(0 if ok else 1)" \
>/dev/null 2>&1 \
|| warn "perf: could not assert the gear — pick Performance in the Thermal panel yourself."
# The pilot reasserts within ~6s, so settle before reading or we grade the
# write instead of the posture.
sleep 8
pct=$(cat /sys/devices/system/cpu/intel_pstate/max_perf_pct 2>/dev/null || echo '?')
epp=$(cat /sys/devices/system/cpu/cpu0/cpufreq/energy_performance_preference 2>/dev/null || echo '?')
noturbo=$(cat /sys/devices/system/cpu/intel_pstate/no_turbo 2>/dev/null || echo 1)
if [ "$mode" = performance ] && [ "$noturbo" = 0 ]; then
ok "perf: thermal-mode performance holding — turbo headroom for MIDI bursts."; return
fi
info "perf: thermal-mode is '${mode:-unset}' → switching to performance for the set…"
if PYTHONPATH="$DIR/tools/bridge" python3 -c "import perf,sys; ok,m=perf.set_mode('performance'); print(m); sys.exit(0 if ok else 1)" 2>/dev/null; then
ok "perf: performance set (thermal-mode owns it; resume/charger reassert included). Back to quiet after: Thermal panel → Silent."
pl1=$(awk '{printf "%dW", $1/1000000}' /sys/class/powercap/intel-rapl:0/constraint_0_power_limit_uw 2>/dev/null || echo '?')
pilot=$(systemctl is-active thermal-pilot.service 2>/dev/null)
rung=$(cat /run/thermal-pilot.policy 2>/dev/null)
if [ "$pct" = 100 ] && [ "$noturbo" = 0 ]; then
ok "perf: VERIFIED — clock uncapped (100%), turbo on, EPP $epp, PL1 $pl1."
else
warn "perf: CAP IS LIVE — max_perf_pct=${pct}%, EPP=$epp, turbo=$([ "$noturbo" = 0 ] && echo on || echo OFF), PL1 $pl1."
if [ "$pilot" = active ]; then
warn "perf: owner = thermal-pilot (profile '${rung:-?}'), and it reasserts within ~6s."
warn "perf: its 'performance' profile FLOORS at rung 1 = 65% whenever the fan"
warn "perf: passes 2600 rpm, which it does at idle. Writing the node by hand"
warn "perf: cannot win this; the profile has to change, or the box has to run"
warn "perf: cooler. PL1 $pl1 vs 45W stock usually means the USB-C travel"
warn "perf: charger — the Dell barrel raises the budget and lowers the fan."
else
warn "perf: auto-set failed — pick Performance in the Thermal panel yourself."
warn "perf: thermal-pilot is not running, so something ELSE holds the cap. Investigate before the set."
fi
fi
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment