Give silent baseline probes stimuli and fix the model bugs they exposed #8

Merged
peterswimm merged 8 commits from baseline-stimuli into main 2026-10-21 14:09:34 +00:00
Owner

Scope

Make the remaining baseline probes observe something, and fix the model bugs that surfaced once they did. Eight commits on top of #7:

  • Parameter ranges. Plans read parameter.get("maximum"), which the catalog never carries (it uses max). Every parameter-maximum probe drove 127 and enum midpoints sat at 64, e.g. a four-way waveform switch. 191 parameters declare a range; an audit against the public Nomad2026 module descriptor found all 515 catalog parameters match it, so the key was the only range defect.
  • Stimuli (baseline_fixture_patch). trig/trigger inputs are clocked from a ClkGen; Vocoder's control gets a saw OscA modulator; a module whose out selector spans its outputs selects the probed output; master-slave inputs get an OscA cabled from its slave output.
  • Faust model fixes found by one-sided silence:
    • NoteSeqA steps now centre on 64 (were raw 0..127, driving the observer ultrasonic).
    • KeybSplit's note output is treated as a note, not modulation (cable_carries_note).
    • OscSlvFM reads mute from index 4 (was fmb's index 3); OscA's slave output is a phasor, not 0.
    • 1Output/2Output honour dest (measured on G1-Emu: only the main pair reaches the captured outputs for most settings).
    • 1to2Fade/2to1Fade use the measured G1 fader law; the centre position is silent on G1.
  • Faust export: negation was emitted as (-(x)), which Faust reads as an operator section, so ControlMixer inversion (and module 57) failed to compile. Now (0.0 - (x)). All 1,788 parameter min/max combinations compile.
  • OscA triangle exports at unity gain; the uncalibrated 0.25 scale was 3.96× too quiet against G1 (rms 0.0181 vs 0.0715).
  • Docs: LFOB high-range endpoint findings in docs/G1_CONTROL_EVENT_CALIBRATION.md, including what is not established.

Testing

  • 92 tests pass (python3 -m unittest discover -s tests); new tests cover the range bounds, trigger and modulator cabling, selector routing, ControlMixer compilation, NoteSeqA/KeybSplit/OscSlvFM/output/fader fixes, and unity triangle and sine export.
  • Full probe sweep against the private G1-Emu adapter, 1,489 probes per plan:
verdict v21 (before) v22 (ranges only) v23 (this PR)
pass 207 151 541
peak-only 307 7 23
level 300 688 361
pitch 371 347 426
shape-or-phase 50 30 54
silence-mismatch 118 159 29
both-silent 134 100 55
faust-error 2 7 0

v22 shows the range fix alone exposing the triangle gain; pitch rises in v23 because newly audible probes (mostly DrumSynth) are now measured.

Impact Statement

  • Existing features: baseline fixtures change, so plans v1–v22 no longer match regenerated fixtures; create a new plan. Faust output changes for OscA triangle, OscA slave output, OscSlvFM, NoteSeqA, KeybSplit-to-OscA routing, 1Output/2Output dest, 1to2Fade/2to1Fade, ControlMixer inversion and the other negation sites.
  • Public APIs / contracts: none.
  • Schemas: none.
  • Data / artifacts: docs/G1_BASELINE_STATUS.json was generated from v21 and is not regenerated here.
  • Integrations: none; target renders still need the separately installed G1-Emu adapter profile.
  • Mappings: no expected impact.
  • Backward compatibility: no reference evidence or module status changes; sweep verdicts remain triage only.

Docs

docs/G1_CONTROL_EVENT_CALIBRATION.md gains the LFOB endpoint section. Remaining work: level/pitch calibration (OscSineBank, FilterBank, Mixer (8), envelopes), and better midpoints for the output and fade modules, whose midpoint is legitimately silent on G1.

## Scope Make the remaining baseline probes observe something, and fix the model bugs that surfaced once they did. Eight commits on top of #7: - **Parameter ranges.** Plans read `parameter.get("maximum")`, which the catalog never carries (it uses `max`). Every parameter-maximum probe drove 127 and enum midpoints sat at 64, e.g. a four-way waveform switch. 191 parameters declare a range; an audit against the public Nomad2026 module descriptor found all 515 catalog parameters match it, so the key was the only range defect. - **Stimuli** (`baseline_fixture_patch`). `trig`/`trigger` inputs are clocked from a ClkGen; Vocoder's `control` gets a saw OscA modulator; a module whose `out` selector spans its outputs selects the probed output; `master-slave` inputs get an OscA cabled from its slave output. - **Faust model fixes found by one-sided silence:** - NoteSeqA steps now centre on 64 (were raw 0..127, driving the observer ultrasonic). - KeybSplit's note output is treated as a note, not modulation (`cable_carries_note`). - OscSlvFM reads `mute` from index 4 (was `fmb`'s index 3); OscA's slave output is a phasor, not 0. - 1Output/2Output honour `dest` (measured on G1-Emu: only the main pair reaches the captured outputs for most settings). - 1to2Fade/2to1Fade use the measured G1 fader law; the centre position is silent on G1. - **Faust export:** negation was emitted as `(-(x))`, which Faust reads as an operator section, so ControlMixer inversion (and module 57) failed to compile. Now `(0.0 - (x))`. All 1,788 parameter min/max combinations compile. - **OscA triangle** exports at unity gain; the uncalibrated 0.25 scale was 3.96× too quiet against G1 (rms 0.0181 vs 0.0715). - **Docs:** LFOB high-range endpoint findings in `docs/G1_CONTROL_EVENT_CALIBRATION.md`, including what is not established. ## Testing - 92 tests pass (`python3 -m unittest discover -s tests`); new tests cover the range bounds, trigger and modulator cabling, selector routing, ControlMixer compilation, NoteSeqA/KeybSplit/OscSlvFM/output/fader fixes, and unity triangle and sine export. - Full probe sweep against the private G1-Emu adapter, 1,489 probes per plan: | verdict | v21 (before) | v22 (ranges only) | v23 (this PR) | |---|---|---|---| | pass | 207 | 151 | **541** | | peak-only | 307 | 7 | 23 | | level | 300 | 688 | 361 | | pitch | 371 | 347 | 426 | | shape-or-phase | 50 | 30 | 54 | | silence-mismatch | 118 | 159 | **29** | | both-silent | 134 | 100 | **55** | | faust-error | 2 | 7 | **0** | v22 shows the range fix alone exposing the triangle gain; pitch rises in v23 because newly audible probes (mostly DrumSynth) are now measured. ## Impact Statement - Existing features: baseline fixtures change, so plans v1–v22 no longer match regenerated fixtures; create a new plan. Faust output changes for OscA triangle, OscA slave output, OscSlvFM, NoteSeqA, KeybSplit-to-OscA routing, 1Output/2Output `dest`, 1to2Fade/2to1Fade, ControlMixer inversion and the other negation sites. - Public APIs / contracts: none. - Schemas: none. - Data / artifacts: `docs/G1_BASELINE_STATUS.json` was generated from v21 and is not regenerated here. - Integrations: none; target renders still need the separately installed G1-Emu adapter profile. - Mappings: no expected impact. - Backward compatibility: no reference evidence or module status changes; sweep verdicts remain triage only. ## Docs `docs/G1_CONTROL_EVENT_CALIBRATION.md` gains the LFOB endpoint section. Remaining work: level/pitch calibration (OscSineBank, FilterBank, Mixer (8), envelopes), and better midpoints for the output and fade modules, whose midpoint is legitimately silent on G1.
Baseline plans looked up "maximum", which the catalog never carries, so every
parameter-maximum probe drove 127 and enum midpoints sat at 64 even for a
four-way waveform switch. 191 catalog parameters declare a range.
Faust parses (-(x)) as a two-input operator section, so inverted
ControlMixer inputs (and other negations) failed to compile. Emit
(0.0 - (x)) instead.
Trigger inputs get a periodic ClkGen, the Vocoder gets a saw modulator,
and 1-N switch probes select the output they observe.
NoteSeqA steps are centred +/-1 control signals, KeybSplit note output
is a pitch note source, OscSlvFM mute is parameter 4, OscA/OscB slv
outputs carry phase, 1/2Output destinations route to outs 1/2 only, and
1to2Fade/2to1Fade are silent at the centre as in G1-Emu. The slave
master-port baseline probe now cables an OscA slv output.
Export OscA triangle at unity gain
All checks were successful
PR policy check / policy-gate (pull_request) Successful in 0s
d45e1ed747
The triangle was scaled by an uncalibrated 0.25. Once baseline plans read
parameter ranges, every enum midpoint put OscA observers on the triangle and
G1 measured about 3.96x the candidate level (rms 0.0715 vs 0.0181), i.e.
unity. NoteSeqB now passes 48 of 49 probes and CtrlSeq 39 of 44.
peterswimm deleted branch baseline-stimuli 2026-10-21 14:09:35 +00:00
Sign in to join this conversation.
No reviewers
No labels
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
peter-swimm/nardwahl!8
No description provided.