Skip to content

probe: run the CLAP prober under the interposer beside it (#109) - #114

Merged
linuxnow merged 6 commits into
mainfrom
fix/109-clap-interposer
Oct 19, 2026
Merged

linuxnow merged 6 commits into
mainfrom
fix/109-clap-interposer

Conversation

@linuxnow

@linuxnow linuxnow commented Oct 19, 2026 •

Copy link
Copy Markdown
Contributor

Closes #109

What changes. plugin-hostd-probe run now starts the CLAP prober under plugin-qualify's interposer, using the same rule the LV2 measurement uses: rt_interpose.so beside the child goes into LD_PRELOAD. One lookup serves both children. A --child given as a bare name is looked for on PATH, as execvp finds it.

What the record says.

  • run.tools.interposer names the interposer only when the child says it counted under it.

  • With no interposer beside the child, or one that did not load, rtSafety is {"interposer": false} with no counts. The rt-safety step is probe.not-attempted with the reason: no rt_interpose.so beside the child in <dir>, <child> is not on PATH, ..., or <path> was preloaded and the child says no interposer was loaded.

  • A note sweep's counts are copied only when the interposer took them. A sweep played without one is probe.not-attempted with the same reason. Before this change it read probe.ok "counts are totals" and carried no counts.

  • A preload the runner had is dropped for the measured child. The child gets the interposer and nothing else. The dropped value is named in run.tools.droppedPreload and in the rt-safety step ("dropped LD_PRELOAD= for the measurement"). The runner then puts its own LD_PRELOAD back. A preload that is the interposer itself is not called dropped.

  • A bare --child is found as execvp finds it. README and the man page say to name the child by path when PATH is unset or holds a directory of its name.

Proofs (omx-contract ORACLE_FLOOR_RATES 44100, 48000, 96000, 192000; plugin-qualify origin/main b384573 native/build; plugin-qualify judge, host openmixer-console)

fixture this branch origin/main runner
rt-safe.clap interposer true, allocations 0, blocks 2048: suitable, hosting.rt-safety.clean-under-sweep unknown, hosting.rt-safety.unmeasured
rt-unsafe.clap allocations 4096: unsuitable, hosting.rt-safety.violations-in-run unknown, hosting.rt-safety.unmeasured
synth.clap --probe-notes 32 note sweep allocations 0: suitable, clean-under-notes unknown, hosting.rt-safety.unmeasured
synth-alloc.clap --probe-notes 32 note sweep allocations 18432: unsuitable, hosting.rt-safety.violations-under-notes unknown, hosting.rt-safety.unmeasured

Tests.

  • The fake CLAP child now detects the stub interposer by its symbol, as clap-qualify detects the real one.
  • Four new runner tests:
    • the child runs under the interposer beside it;
    • a bare child is found on PATH;
    • with no interposer beside the child, the record is unmeasured and says why;
    • an interposer that does not load is not named.
  • One new test runs the real prober with PLUGIN_QUALIFY_BUILD.
  • Ten new sabotage entries, each red. Four of them cover the dropped preload. The LV2 interposer and stimulus entries now point at the shared lookup.
  • make test (176 ok), make test-jack (11 ok, both LV2 steps ran), make sabotage (197 caught, 0 survived) and make private-refs are all green.

Codes: none. run.tools.droppedPreload is a new free-form tools entry, which the schema's additionalProperties string already allows. No hosting.* code is added or changed, and no probe-output enum or schema changes. The runner uses the existing probe.ok and probe.not-attempted.

The LV2 measurement ran under plugin-qualify's rt_interpose.so, the
file of that name beside the child, but the CLAP prober ran with no
interposer. Its line then said rtSafety interposer false with no
counts, and plugin-qualify judged every CLAP plugin measured through
the runner unknown, hosting.rt-safety.unmeasured.

Both children now get the interposer from one lookup. A child given
as a bare name is looked for on PATH, as execvp finds it. The run
names the interposer only when the child says it counted under it.
When no interposer is beside the child, or the one preloaded did not
load, the rt-safety step is probe.not-attempted and says which. A
note sweep's counts are copied only when the interposer took them,
and a sweep played without one is not-attempted with the same reason,
where it used to read probe.ok with no counts.
…109)

The fake CLAP child reported interposer false always and printed note
sweep counts as if counted. It now looks for the stub's symbol, as
clap-qualify looks for the interposer's own. Under the stub it prints
rtSafety counts. Its note sweep prints counts either way, so a runner
that copies counts no interposer took is caught.

New tests: the child runs under the interposer beside it, a bare
child is found on PATH, a child with none beside it is unmeasured and
says why, and an interposer that does not load is not named. With
PLUGIN_QUALIFY_BUILD, the real prober runs over omx-contract's floor
rates. rt-safe.clap and synth.clap must read 0 allocations,
rt-unsafe.clap must read more than 0, and synth-alloc.clap must read
more than 0 under the note sweep.
The CLAP prober started without the interposer, a bare child not
looked for on PATH, the allocations a CLAP point drops, note counts
kept when the interposer did not take them, an unmeasured rt-safety
that does not say why, and an interposer named although it did not
load: each turns its test red. The LV2 interposer and stimulus
entries follow the shared lookup. make sabotage builds the CLAP fake
child and the stress plugin it runs.
The measured child gets the interposer and nothing else, since another
malloc interposer would hide its allocations. The runner used to
overwrite LD_PRELOAD for the child without saying so, then unset it in
its own environment. Now a preload the runner was started with is
named in run.tools.droppedPreload and in the rt-safety step, and the
runner's own LD_PRELOAD is put back after the child. A preload that is
the interposer itself, as plugin-qualify starts the runner, is not
called dropped.

README and the man page say this, and say how a bare --child is found:
as execvp finds it. Name the child by path when PATH is unset or holds
a directory of its name.
…orded (#109)

The fake CLAP child writes its environment where PROBE_CHILD_ENV says.
The new test starts the runner under a foreign LD_PRELOAD. The child
must get only the interposer beside it, or no preload when there is
none, and the CLAP and LV2 records must name what was dropped. The
interposer itself, already preloaded, must not be called dropped.

Four sabotages go red on it: the child keeps the foreign preload, the
drop is not recorded, it is left out of the run's tools, and the
interposer is called dropped. The LV2 and CLAP "runs without the
interposer" entries now cite the call sites of the shared function,
and the unmeasured-reason entry cites the new detail.
@linuxnow
linuxnow merged commit 2c1da1a into main Oct 19, 2026
35 checks passed
@linuxnow
linuxnow deleted the fix/109-clap-interposer branch October 19, 2026 23:59
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Probe runner: run the CLAP prober under the interposer beside it, as the LV2 measurement is

1 participant