Findings from the physiological-signal suite, written up so they need not be rediscovered. Each paper regenerates its tables and figures deterministically from a named, local analysis tool: open the tool, set N, and Run. Synthetic cohorts are seeded (CohortGen.patient(k) per index; synth-gen default seed 424242), so a rerun reproduces the numbers within sampling error at the stated N — on the current generator synth-gen 2.1 / cohort-gen 1.9. Standardized format: paper.css. Drafts — not peer-reviewed, not for clinical use.
rmssd-equivalence), and autonomic rMSSD now localizes the CPAP-start night better than respiratory ODI-4 (treatment-response). Read together, rmssd-equivalence (bias-inert optical error) and qrs-yield (yield-driven optical error) now tell one story: the optical arm's disagreement is a variance/yield penalty, not a bias. Full log in the open-findings section below.
The production OxyDex ODI-4 detector recovered only ≈¼ of scored respiratory events (slope 0.23, R² 0.93), under-counting most in severe disease (≈−30 events/h). The shipped AHI ≈ ODI-4 × 1.1 surrogate has LOO-RMSE 15.2/h; a re-fit linear correction halves it to 7.2/h. Now corrected (v22.36): traced to trailing-mean baseline self-suppression and fixed with a p90 ceiling baseline — roughly halving the severe-stratum bias (≈−31→−16 events/h) and lifting the ODI-4↔AHI slope ≈0.42→0.69. Includes a closed-form sample-size analysis: a real-PSG validation needs ≈150–300 paired nights, bound by the severe-stratum count.
PAPERS-ROADMAP §2.2. A structured, citable account of what does not survive scrutiny — seven walls with the evidence that felled each and its disposition: optical PRV unbiased but ~22× wider LoA (not a drop-in for ECG HRV); a green SQI while optical beat-yield fails, +83% rMSSD inflation; daily CGM-CV ICC₁≈0 (state, not trait); a glucose↔HRV coupling collapsing −0.11→+0.01 under a shared apnea driver; rolling-baseline ODI-4 under-count (slope 0.23) — traced and fixed; and vendor composites fabricating a 0 on missing input; and cross-device wearable PAT unrecoverable on real data (0 of 54 pairings). Wall 2.7 was corrected 2026-07-29 and the correction is the eighth wall: the "~48 ppm / ~1147 ms per night" drift was one cardiac cycle admitted by an unenforced coupling window — the real inter-device rate is ~1.5 ppm and v1's figure is excluded on 51 of 54 nights — the prescribed single-clock remedy is unnecessary (the capture host holds 0.008 ppm against a local stratum-1), and the ~96 ms "true limit" named in v2 is withdrawn in v3 (2026-08-13) as an artifact of the analysis window and two mis-derived sample rates; whether the wall exists is open. Wall 2.8 generalises it: a negative result from an uncalibrated search is not evidence — the chance-maximum correlation (≈0.41) exceeded the threshold it had been lowered to (0.35). Framing + honesty, including about our own error.
v2 corrects v1's central claim. The negative result stands — beat-level cross-device PAT is not recoverable, 0 of 54 pairings — but every stated cause fails. The "~1.1 s/night at a fixed 47.7 ppm" drift was one RR interval, admitted by a coupler searching 2,000 ms (> 1 RR) while only displaying its 200–650 ms window. v1's own Table 1 refutes it: the drift does not scale with recording duration (r = +0.17, where a fixed ppm requires ≈ +1), the ms value is more stable than the ppm rate (CV 8.1 % vs 10.8 %), and 1,156 ms = RR at 51.9 bpm against a stated ~50 bpm. Measured directly the rate is 1.46 ppm (long nights), so the prescribed single-clock remedy is unnecessary — the capture host holds 0.008 ppm against a local stratum-1. The 89 % / 48 ms figures are artifacts of the same defect, and the IQR provably cannot move under it. The accelerometer re-sync failure reproduces but its anatomical cause is withdrawn: on a known-zero pair the same search misses a planted −39 min offset 12 times in 13. v2's ~96 ms "real limit" is withdrawn in v3 — it is the SD of the 450 ms acceptance window, not physiology. §3.3 (phone timestamp = start + device-elapsed) and the beat-parity result survive unchanged. §7 carries the full correction record.
A positive claim is checked by the world; a null is only ever checked by the instrument that produced it — so a null is consistent both with "the effect is absent" and with "this method could never have found it", and nothing in normal reporting separates the two. This note gives the arithmetic that predicts when a maximising search enters that regime, and demonstrates it on two of this suite's own nulls. For a search over N candidate lags with n samples per comparison, the expected largest spurious correlation is ≈ (1/√n)·√(2 ln N); widening a cross-correlation from ±1.6 s to ±50 min takes N from 65 to 24,001 at n = 121, giving ≈0.41 against a threshold that had been lowered to 0.35 — inoperative, so chance always wins and the noise median regresses to the centre of the search range, which reads as "no effect found". A known-answer control confirms it: on two accelerometers sharing one acquisition clock, the search recovers a planted −39 min offset on 1 night of 13 while the same code at design range aligns 13/13. Lengthening the window restores recovery monotonically. Casualties: one withdrawn causal claim, one void null, one companion metric that cannot move under the failure it was trusted to catch, and one remedy adopted without measuring the quantity it removes. Five cheap recommendations, none of which we ran at the time.
PAPERS-ROADMAP §2.1 — “the narrowest first paper.” States the floating wall-clock tMs model as a citable method and benchmarks the production Clock Contract parser against the consumer-export format zoo (DMY/MDY ambiguity, zoned vs floating, 14-digit compact, time-only midnight-roll, bare epoch) plus adversarial edge cases. The shipping parser resolves 24/24 corpus cases and upholds 6/6 contract invariants — viewer-timezone independence, zoned≡floating, deterministic DMY/MDY, monotonic overnight roll, never-fabricate-on-miss, epoch determinism — regenerated live from the real code. Plumbing, not a discovery: the correctness surface every other result stands on.
v2 supersedes the four-night v1 and revises its headline downward. 20 paired H10 + Verity Sense overnights, 1,477 five-minute epochs, 121.5 h, one subject. Beat detection is at ceiling (sensitivity and PPV both median 1.0000); what the optical arm loses is timing — jitter 5.92 ms, bias +0.01 ms. rMSSD runs +4.24% high (18/20 nights within ±10%), not the −0.6% v1 reported on its two best-of-four nights. The central result is mechanistic: rMSSD²ppg = rMSSD²ecg + kσ² fits at per-night R² = 0.964, k = 2.39 — so accuracy collapses to one scalar and the design budget inverts in closed form (σ ≤ 3.51 ms → 1% bias). Catastrophic epochs (10.6%) are just high-jitter epochs (35.0 vs 5.5 ms). Also documents why a single global affine clock map fails (PTT of −1 ms, F1 0.26) and records two negative results: waveform fusion of the 3 LEDs loses to best-single-channel, and the literature's preferred middle-amplitude fiducial is worse here than the shipped tangent.
Choosing a signal-quality gate by pooling every epoch from every night is the obvious experiment, and on this corpus it gives the wrong answer decisively. Pooled over 1,488 ECG-referenced epochs, beat coverage wins (AUC 0.737, p=7×10⁻²³) and the shipped per-beat SQI looks like a coin flip (0.556). Clustered within nights — the analysis matching how a gate is actually deployed — the ranking exactly reverses: shipped SQI best (0.763, p=0.014), coverage worst and non-significant (0.629, p=0.106). The mechanism is an ecological fallacy: coverage varies between nights and tracks which nights are bad, so pooling lets between-night variation masquerade as within-night discrimination. Used as a real gate, SQI cuts p90 error 25.8%→21.4% at 70% retention while coverage makes the median worse (4.43%→4.89%). Acting on the pooled result would have deleted a working feature and replaced it with a harmful one. Honest coda: no gate here is transformative — error is governed by jitter, which none of them measures.
Validating a wearable respiratory algorithm normally needs a sleep lab. But a ResMed CPAP already writes a calibrated 25 Hz flow signal to its SD card every night, plus AASM-typed scored events. This is the recipe for promoting that to a working reference: breath detection from the flow trace; validating the reference before scoring anything against it (two independent flow-derived estimators agree to MAE 0.70 brpm — the floor no algorithm can honestly beat); and recovering the clock relationship, which is neither known nor stable. The wearable and CPAP clocks differed by ≈39 minutes, recovered by cross-correlation to a ±4 s peak, and that offset drifts +0.589 s/day (residual SD 1.03 s over 37 days). Key practical finding: drift-consistency is a better validity test than correlation magnitude — a correlation gate would have discarded four good nights, non-randomly biased toward the hardest ones.
The H10 streams a tri-axial accelerometer alongside its ECG, and it has apparently never been evaluated for respiration — the H10 literature is entirely HR/HRV. Nor has any published chest-accelerometer respiration study recorded treated nights. On 26 nights / 19,193 epochs against CPAP flow: MAE 1.01 brpm (95% CI 0.91–1.12), 91.6% within 2 brpm; on event-free epochs 0.77. Confidence-gated it reaches MAE 0.56 at 70% coverage (97.8% within 2 brpm) — the reference's own noise floor. Spectral ridge tracking by Viterbi across epochs, plus a time-domain blend (Charlton's 314-algorithm result put all top performers in the time domain). The shipped predecessor scores 3.59 — worse than predicting a constant. Runs in 0.17 s/night in dependency-free ES5. An explicit tilt-angle channel is measurably redundant (spectrum correlation +1.000). Dominant limitation is exposure, not accuracy: one subject, and — measured — essentially one posture.
Central-vs-obstructive typing rests on effort being absent in central events. On 22 nights (370 central, 31 obstructive), accelerometer effort during central apneas sits at 0.99× its own night baseline — not absent, normal. Only 16.5% fall below half baseline, where a single RIP belt achieves 84% recall. Best discrimination is AUC 0.691 (p=0.0002) — real but far below useful. A methodological finding of independent interest: including each event's termination destroys the effect entirely (AUC 0.573, p=0.089), because the terminating arousal injects motion exactly where effort should look absent. Advanced as a hypothesis, not a conclusion: positive airway pressure may drive chest motion without respiratory effort — every prior study recorded untreated nights. Parked pending that test, obstructive n=31, device-scored labels, and an unresolved contrary report.
A three-rung recipe for stating a sensor's uncertainty when you own no calibrated reference: repeatability (no reference), transfer-standard Bland–Altman/Arms (promote the H10 ECG strap to ≈truth), and the three-cornered hat (three devices, none assumed canonical). On 291,561 co-recorded 1-Hz seconds (twenty-six nights) the O2Ring pulse is unbiased vs ECG (−0.20 bpm) but carries a random σ ≈ 3.2 bpm at rest (one motion night hit 9.9). The Verity Sense's onboard HR was dead — but its HR recovered cleanly from raw PPG (SQI ≈1.0), and with the H10 leg re-derived from raw ECG, the tool folder-ingests each night and solves a fused-weight artifact-robust hat across the full twenty-six-night corpus → 2.41 / 1.28 / 1.42 bpm (O2Ring / H10 / Verity). Per-second beat-confidence weighting down-weights transient artifacts in place (a spurious-QRS burst on 06-12 that detonates the plain hat to σH10 ≈9.6 is kept and cleaned to ≈2.6). The raw-ECG H10 is the quietest corner (the gold leg), the O2Ring pulse the noisiest — an earlier 6-window hand-picked hat had instead put Verity noisiest (3.50), a small-sample artefact the full corpus corrects. SpO₂ trueness stays out of reach (no arterial reference). v2 (Aug 2026) adds window length as a stated parameter — σ rises monotonically with window on every corner, so a σ quoted without its window is incomplete — and records that, window-matched, the O2Ring corner reproduces across both analysis pipelines while the H10 and Verity corners await a per-corner cross-pipeline reconciliation. Headline σ unchanged in both revisions.
Test–retest ICC(1,1) of three metrics measured per occasion by the real detectors on stable (flat-arc) patients. rMSSD is a reliable individual trait from a single night (ICC₁ 0.93 — a variance ratio, unchanged by the texture rescale). ODI-4 is trait-like but noisier on cohort-gen 1.9 (ICC₁ 0.75, down from 0.89 on 1.6 after the AHI-ceiling revision compressed the between-subject apnea spread) — it needs two nights for ICC≥0.80, four for ≥0.90. Daily CGM-CV shows negligible between-subject variance (ICC≈0) — a day-level state, not a one-number trait. Spearman–Brown → minimum occasions; latent-target ANOVA confirms the detector preserves the reliability structure.
Measured (real PulseDex) rMSSD falls ≈3.8 ms/decade of age and ≈2.4 ms per 10 AHI — comparable independent weights, effectively additive (age×AHI interaction significant at n=112k but negligible, ≈+7×10⁻⁴ ms·yr⁻¹·event⁻¹; R² 0.599). A single-metric rMSSD screen for moderate+ OSA scores AUC 0.69 with 29% of flags being old-and-healthy; an age-adjustment recovers it to 0.77. Re-run on the v2.1/1.9 texture surfaced two real deltas from the earlier draft: the detector now reads through the realistic texture (slope recovery vs planted inputs ~10% off) and misattribution rose 25%→29%.
A single change-point detector on the per-night ODI-4 (OxyDex) and rMSSD (PulseDex) trajectory recovers the planted CPAP-start night with median error 0 nights. Fusing the respiratory and autonomic channels is best — exact 91%, within ±1 night 97%, detection AUC 0.99 vs flat-arc controls — beating either alone. Reversal on v1.9: the shallower ODI step drops ODI-4 exact localization to 73% while rMSSD holds at 87%, so the autonomic channel now localizes better than the respiratory one (a device without oximetry is the stronger single arm). Notes the free-split step-R² is inflated under the null (≈24–27% on flat controls), so detection must be read against a control distribution.
GlucoDex (CGM) and PulseDex (RR→HRV) — sharing no code, parser, or input — recover a coherent negative coupling on co-generated nights: higher nocturnal glucose ↔ lower rMSSD (within-patient r −0.11; pooled −0.13). It is a shared-driver effect, not direct: partialling out apnea burden collapses it to +0.01, while the driver legs are strong and opposite-signed (apnea→glucose +0.42, apnea→rMSSD −0.32). The raw coupling weakened from the v1.6 draft's −0.18 (richer texture adds glucose-uncoupled rMSSD variance) but the shared-driver attribution is unchanged. Nocturnal-hypo detection now recovers every planted dip through the standard flag (recall 1.00, the in-detector fix).
Scoring rMSSD with all three real detectors on the same co-generated beats (one ~9-min window/patient): ECGDex ≡ PulseDex — bias −0.02 ms, 95% LoA ±0.4 ms, r 0.9999 (two detectors sharing no code, signal, or sampling rate recover the identical tachogram). PpgDex is now essentially unbiased — bias +0.3 ms (+0.7%), r 0.93 — but several-fold noisier (95% LoA −7.5…+8.1 ms, ≈22× wider; PAT-jitter dispersion ≈4.0 ms). Thesis flipped from the v1 draft (which read +12.6 ms / +32% / r 0.57): the realistic broadband texture shrinks the relative PAT-jitter offset, so optical PRV is a usable HRV estimate that must be down-weighted by its wider variance, not treated as a foreign quantity.
Every timing number in this suite was validated only against itself — estimator, Allan curve and closure check are mutually consistent but were never compared to a defect known in advance, so a shared error would leave all three green. We injected exactly-known defects against criteria hashed before any run, on two substrates: 61 BLE arrival streams (395 sidecars, 21 nights) for clock defects, and 101 real H10 RR trains for beat defects. The clock estimator is excellent — frequency recovery unbiased across ±1…±500 ppm at 0.03–0.09 %, contiguous 50 % packet loss moving the rate by exactly 0.0000 ppm, constant offset unidentifiable by construction — yet σy(τ) at each recording's own span exceeds the rate quoted for 100 % of streams under 300 s and 42 % beyond an hour. Then the beat substrate turned the paper: one missed beat in a thousand inflates rMSSD 20.8 % while mean RR moves 0.06 %, against ~0.003 % for a 30 ppm clock error — four orders of magnitude, and only the smaller had instruments. A common-mode test across simultaneous device pairs puts the host at r = 0.036 of the residual; the worst noise belongs to one stream (Verity acc, 7.7× its own device's optical stream at matched span), not a device. A second, aperiodic route to the offset also fails here (peak prominence 0.002 vs a null control of 0.002; the peak rides the search range) — and the obvious validation for such methods is vacuous: four injected constant offsets were recovered with error exactly 0 from a method locating nothing, because a constant shift translates the whole correlation surface rigidly. Also: a drawn O2Ring counter returning a confident 2765.5 ppm with the independence flag set; a ≥99 % drawn detector missing 5 of 25; allan.py agreeing with allantools to 4.8 × 10⁻¹⁴. v4 measures the beat detector itself: capture–recapture across three detectors is unidentifiable on clean data (they agree on 935 of 986 beats) and refuses; an artificial-star completeness test does work, putting ~1 % of real beats at risk — and attenuating beats in situ then showed gap-planting overstates the detector by ~3× via its adaptive threshold, a correction opposite in sign to the one we published; and one claim of our own that this work withdrew.
On the FULL-lane waveform harness, ECGDex (Pan–Tompkins QRS) recovers the beat train apnea-invariantly (≈100% clean ≈ apnea, precision ≈100%), while PpgDex optical pulse recovery is lower (≈96%) and now roughly equal in clean and apnea — the earlier apnea-specific dip washed out on the richer texture (the foot-detector's baseline miss/false-positive rate rises in both states); precision 89%. The correlation-based SQI stays above its gate throughout (dipping 0.90→0.78 in apnea), under-representing both misses and false positives — and the imperfect optical train inflates rMSSD a median +83% (was +16%). Conclusion: use the electrical arm as the HRV reference and weight optical HRV by event-state and its own uncertainty, not SQI.
20,000 frozen-seed synthetic patients (all 16 severity×arc strata, ≥1,092 each) run end-to-end through the unmodified production detectors + real Integrator fusion, harvesting a per-patient failure ledger. Zero fatals, throws, out-of-bounds metrics, or kernel mismatches; 99.7% cross-node fusion overlap; OxyDex worst-case 1.21 s/night (no hang). The one systematic failure is soft: ODI-4 desaturation recall collapses (cohort median 4%) and trips the severe-recall flag across the severe stratum, with the ODI→truth-AHI under-count deepening monotonically (−1.4/−5.1/−12.3/−30.8 events/h none→severe) while calibration tightens (R² 0.77→0.92) — proportional and predictable, not random. That under-count has since been corrected and the same 20,000-patient instrument re-run on v1.7: the OxyDex ceiling-baseline fix (v22.36) + generator de-pile collapse the severe bias −30.8→−17.2 events/h, flatten the gradient (none/mild/mod −1.0/−3.7/−8.1), and lift the ODI→AHI slope 0.14→0.38 (R² 0.92→0.96), with no inflation of the non-apneic stratum and the hard-failure ledger unchanged. RR/HRV companion arm refreshed on synth-gen 2.1 / cohort-gen 1.9 (2,400-pt validation): rMSSD absolute error 0.57→0.80 ms (still tight) and GlucoDex nocturnal-hypo recall 0.00→1.00 (the in-detector Somogyi-discriminator fix); the oxy calibration, coverage matrix and hard-failure ledger are texture-independent (separate RNG stream) and retained from the committed 20k run.
The metrology twin of nights-icc: how many co-recorded O2Ring + H10 + Verity windows pin each device's reference-free error σ? Monte-Carlo (720 trials/cell, Web-Worker pool) over the same three-cornered-hat kernel with planted σ 2.7 / 1.9 / 1.9 bpm shows one ~1-hour window pins the whole trio to ±0.5 bpm; ±0.25 needs ~5–8, ±0.15 ~12–20. The hat couples the corners, so the noisiest corner (the O2Ring on this corpus) sets a shared floor (not "the noisy device needs far more data"), while the quietest corner is hardest to pin tight. The regime cost is bias, not N: a resting night under-states the instantaneous devices because the TCH strips shared HRV — a dynamic session recovers the full σ. Validated on a real 26-night tri-device corpus (folder-ingested, raw-ECG gold leg, fused-weight artifact-robust hat; O2Ring σ̂ ≈ 2.41, H10 ≈ 1.28, Verity ≈ 1.42 bpm; the quiet-order regime + motion premise confirmed) — modestly below the planted σ (kept at 2.7 / 1.9 / 1.9, the pre-fused seed), with the O2Ring the noisiest corner (an earlier hand-picked hat had put Verity noisiest, a small-sample artefact).
A parking note, not a result. Single-channel waveform synthesis is solved elsewhere; the open frontier the harness exposes is timestamp pathology, cross-node temporal coherence, and provenance metadata — three of which need no learned generator. Records the agenda so it isn't rediscovered later, and names the narrowest first paper (a deterministic timestamp-pathology benchmark).
PAPERS-ROADMAP-2026-06-24-BRIEF.md)The series is lopsided toward simulation scored by real detectors; the planned stack (vendor-adapter layer + multi-vendor unifier, OverDex, EEGDex, Ultrahuman/Spiro nodes) opens the real-world validation front. Each candidate is tagged with its stack dependency. Honest sim/real labelling and a named regeneration tool remain mandatory.
Buildable now — no new node
tMs model stated as a citable method. The narrowest first paper already named by synthetic-data-frontier; corpus mostly exists in the parseTimestamp tests. methods/repro LOW effort · now0 when inputs are absent); daily CGM-CV ICC≈0; SQI green while beat-yield fails under apnea; rolling-mean ODI self-suppression. A citable "map of the walls in the maze" — the manifesto made into an artifact. synthesis LOW–MED · nowUnlocked by the planned stack — the real-validation front
rmssd-equivalence: pool real co-recorded consumer devices across vendors (Polar, Coospo, Wahoo, Garmin…) and test rMSSD/SDNN agreement reference-free via the three-cornered hat. A hat across N consumer vendors is genuinely rare. real data needs adapter Phase 1 · MEDsigma-no-reference pinned σ from one ~2 h hat; OverDex auto-detects every co-recording in an archive → track each device's σ over months (does consumer-sensor error drift, caught with no reference?). sensor-trio-nights already did the power analysis. real data needs OverDex · MEDcgm-hrv-coupling: the first real test of the synthetically-predicted glucose↔HRV shared-driver effect on co-worn data. real data needs UltrahumanDex · MEDnights-icc). real data needs SpiroDex · MED–HIGHPAPERS-ROADMAP-2026-06-24-BRIEF.md (above). The earlier batched re-bundle pass (Integrator sample fix + OxyDex hardening) is DONE — both gates green; see the resolved findings below. (buildHash has since been retired as a provenance signal — manifestHash, a deterministic projection of the actual inlined code, is now the sole executed-code identity, so the once-mooted “what does buildHash certify?” note is moot.)Material conclusion changes from the synth-gen 2.1 / cohort-gen 1.9 re-texture rerun (July 2026)
rmssd-equivalence thesis flipped on the realistic texture. On the broadband v2.1 RR texture the PPG−Pulse bias collapsed from +12.6 ms (+32%, r 0.57) to +0.3 ms (+0.7%, r 0.93): with richer true beat-to-beat variance the fixed pulse-arrival-time jitter adds a far smaller relative offset (√(true²+PAT²)−true shrinks as true grows). The surviving optical signature is a precision penalty — ~22× wider limits of agreement (PAT-jitter dispersion ≈4.0 ms) — not a bias. Reframes the fusion rule from "never substitute optical PRV" to "usable HRV estimate, down-weight by its wider variance." Demonstrates a bias that looked like a fixed sensor property was an artifact of how much true variability the reference carried. Paper rewritten (Draft v2); needs author sign-off on the reframed claim.qrs-yield. The apnea-specific recall dip washed out (clean 96.4% ≈ apnea 96.3%, was a 0.9% gap): the richer texture raises the optical foot-detector's baseline miss/false-positive rate in both states, so the shortfall is real but no longer localized to events. Downstream rMSSD inflation rose +16% → +83%; precision 92%→89%; SQI now dips more in apnea (0.90→0.78). The modality asymmetry (robust QRS vs fragile optical) is unchanged and stronger. Paper rewritten (Draft v2).nights-icc now needs two nights for ODI-4. On cohort-gen 1.9 (the earlier draft was 1.6) the AHI-ceiling revision compressed the between-subject apnea spread, dropping ODI-4 ICC₁ 0.885 → 0.745 (now 2 nights for ICC≥0.80, 4 for ≥0.90). rMSSD is unchanged (ICC₁ 0.93 — a variance ratio, robust to the texture rescale) and CGM-CV still ≈0. The two-regime (trait vs state) finding holds; the trait/noise split within the trait-like metrics moved. Paper rewritten (Draft v2).treatment-response. The shallower v1.9 ODI step dropped ODI-4 exact-night localization 95% → 73% while rMSSD held (87%), so the autonomic channel overtook the respiratory one (was the other way in the v1.5 draft). Fusion remains best (exact 91%, AUC 0.99). Strengthens the "a device without oximetry is not blind to therapy response" point. Paper rewritten (Draft v2); cohort smaller (912 tx / 918 flat — the ≥10-night population attrits on coverage in a time-bounded run).cgm-hrv-coupling. At 6,000 pt / 48,471 nights the within-patient coupling weakened −0.18 → −0.11 (the richer texture adds night-to-night rMSSD variance carrying no glucose signal, diluting the raw correlation), and the glucose↔AHI driver leg eased +0.54→+0.42. The core conclusion is untouched: partialling out apnea burden still collapses the coupling to ≈0 (shared-driver, not direct). Also confirms the nocturnal-hypo detector fix at scale (flag recall 0.008→1.00). Paper updated (Draft v2).robustness-benchmark. On the 2,400-pt v2.1/1.9 refresh the rMSSD absolute error eased 0.57 → 0.80 ms (still tight) and GlucoDex nocturnal-hypo recall rose 0.00 → 1.00 (the in-detector Somogyi-discriminator fix). The oxy ODI↔AHI calibration, coverage matrix, and hard-failure ledger are texture-independent (separate RNG stream) and retained from the committed 20,000-patient run. Paper updated (Draft v2).synth-gen.js (the demo synthetic-cohort generator) is inlined into OxyDex, PulseDex, GlucoDex, PpgDex, HRVDex, and Integrator — all six moved manifestHash on the owned re-bundle; ECGDex and CPAPDex do not inline it and are byte-identical (the brief's Part 3 named PulseDex/ECGDex/HRVDex). Because every provenance fixture runs compute({committed static input}) with unchanged DSP code, the re-bundle is EXPORT-INERT: all outputHashes are byte-identical, only manifestHash re-recorded. Both gates green post-update (verify-provenance GATE A/B; Dex-Test-Suite?full). Release (tools/release.mjs) intentionally left for the owner.detectODI's baseline. It measured each dip against a trailing 5-min MEAN SpO₂ (computeBaselineArr); in severe OSA the closely-spaced dips drag that mean down, sinking the baseline−4% threshold so later events of equal depth fall below it and go uncounted — the worse the apnea, the more it self-suppresses. Fix: a new O(n) trailing p90 ceiling baseline (computeCeilingBaselineArr in oxydex-util.js, sliding 101-bin SpO₂ histogram) wired into detectODI only; brief dips sit in the lower tail and can't suppress a high percentile, so the ceiling tracks the resting SpO₂ a desaturation is clinically defined against. Representative re-run (N=220, same generator, identical SpO₂ both ways): severe bias −30.6→−15.7, gradient flattened (none −1.3→−0.9, mild −7.9→−6.2, mod −14.2→−10.3), ODI↔AHI slope 0.42→0.69, non-apneic stratum not inflated. The full-pipeline SubjectA pilot rises in step (severe night ODI-4 7.6→14.9). This is a genuine real-world oximetry improvement (documented trailing-mean-baseline behavior), not overfitting to the simulator — the percentile/window are defensible clinical constants (p90, 5-min), untuned. The ODI-4 × 1.1 AHI surrogate was re-examined and retained (corrected ODI still under-represents AHI, slope-to-truth ≈1.4 > 1, so ×1.1 does not over-shoot). JS-only change → buildHash unchanged (09c77b53517c), verify-provenance.html all-green; Dex-Test-Suite green (545/34) with a new ceiling-baseline contract assertion. Papers updated: odi4-ahi-bias (characterized→corrected), robustness-benchmark §3.3. Re-bundled OxyDex.html. See OXYDEX-ODI-CEILING-FIX-BRIEF.md.CohortGen.VERSION → 1.6-pilot. Because chance() consumes one RNG draw regardless of its probability, the RNG stream is unchanged → rMSSD / ODI / age / AHI are byte-identical to v1.5 (the hrv and treatment-response results are untouched); only which patients carry a CGM shifts. nights-icc re-run on v1.6: CGM-CV now has 4,059 subjects (was 1,818), near parity with ODI/rMSSD — and its ICC₁ is still ≈0, confirming the “daily glycemic variability is a state, not a trait” finding was never a coverage artifact.N≥1000 crashed the tab during generation. Root cause was isolated to hrv-confound-analysis.js: its progress-counting first pass built the entire cohort up front — patients.push(CohortGen.patient(s)) with no only filter, so every patient's OxyDex CSV + RR + CGM + HRV files for all 1–12 nights were rendered and retained in memory simultaneously. Fine at the ~250-patient default; fatal at 1k+. Fix: stream. Count nights from sampleProfile alone (no rendering), then generate one patient at a time with only:['rr'] (PulseDex's sole input), score it, and discard before the next. Memory is now flat at any N. Verified: 1000 patients (5699 nights) in ~3 min, no crash — and the tighter estimates replace the 626-night pilot (see hrv-age-confound.html).hrv-confound had the fatal pattern. The other FAST analysis tools (nights-icc, treatment-response, cgm-hrv-coupling) already stream one patient per loop iteration and accumulate only small numeric per-night/per-subject records — no crash at scale. cohort-runner.html persists each result to IndexedDB as it goes (refresh/crash-resumable) and was already built for N≤20000. The FULL-lane workers (qrs-yield-worker.js, qrs-equiv-worker.js) keep the 176 Hz waveforms inside the worker realm, returning only per-window stats — memory-safe per job (though FULL-lane runtime at 20k is hours, not minutes). The only remaining 20k blocker was non-memory: hard input caps of 5000 and profile-scan ceilings (100k–200k) that bind before a selective-arc target (flat / intervention) can fill. Raised all six analysis tools to max=20000 and scan CAP=2,000,000. The suite can now be driven to 20k without code changes; the practical limit is wall-clock (serial real-detector round-trips), not memory.cohort-gen.js applied therapy residual as ahi = Math.min(ahi, clamp(ahi*0.6, 0, 15)). For any treated night with baseline AHI ≥ 25, ahi*0.6 ≥ 15, so the clamp returned exactly 15.0 — pinning every such night onto one x-value. Measured over 2,480 sampled nights: 9.7% sat at exactly AHI = 15.0 (≈22% of all CPAP nights), drawing a hard vertical line with a sharp right edge on the low-AHI block (a secondary cause of the dense left wall is per-patient vertical streaks — a flat-arc patient's nights share a near-constant AHI while rMSSD varies night-to-night). A generator artifact, not a detector/render bug, but it distorted the AHI distribution (an unrealistic therapy-night spike that also carried the +6 ms CPAP rMSSD bump). Fix: proportional, jittered residual ahi = clamp(ahi*(0.15 + rng()*0.25), 0, ahi) — 15–40% of baseline, never above it, no pileup — and bumped CohortGen.VERSION 1.0-pilot → 1.1-pilot. Ripple: changes every synthetic-pilot AHI distribution, so all simulation pilots are being re-run on v1.1; buildHash provenance is unaffected (it fingerprints each app's bundle template, and cohort-gen.js is in no app bundle), and Dex-Test-Suite stays green (no test asserts an exact cohort AHI or the generator version).cohort-gen.js: (v1.2) worsening-arc severe nights overshot the hard clamp(ahi·jitter, 0, 90) and stacked a vertical line at exactly AHI=90 → replaced with a jittered ceiling (0 … 80+rng()·12, i.e. 80–92) so overshoot fades out instead of piling; (v1.3) the per-night rMSSD clamp(…, 9, 72) and per-patient baseline clamp(…, 12, 62) stacked horizontal lines at the rMSSD floor (~13 ms, low-HRV nights) and ceiling → replaced with jittered bounds (floor 5+rng()·5, ceiling 70+rng()·6; baseline 9+rng()·5 … 58+rng()·8). General rule established: a hard clamp() to a constant in a rendered quantity draws a pileup line on any scatter of that quantity — jitter the bound. CohortGen.VERSION → 1.3-pilot. Effect on results is trivial (the clamps bind only in the distribution tails; the age/AHI slopes and AUCs move within rounding), provenance unaffected (cohort-gen is in no app bundle), and the suite stays green. Figures re-rendered at high resolution.baseAHI·(1+0.7·t) ≈ 136, and the hard clamp clamp(ahi·jitter, 0, 80+rng()·12) collapsed that whole over-shooting mass into the narrow 80–92 band. The jitter softened the original razor line but not the pileup. Fix: replaced the hard ceiling with a soft asymptotic saturation (same approach as the v1.5 rMSSD floor): ahi = 95·(1 − exp(−jit/95)), so AHI fades smoothly toward ~95 instead of stacking at the cap. CohortGen.VERSION → 1.7-pilot. Cosmetic for the fit (R²≈0.98 unchanged) but removes the last clamp-pileup; AHI-dependent pilots are re-run on v1.7.integrator-app.js bindSamples() fetched two hardcoded paths — uploads/ecgdex_2026-06-07 (4).json and uploads/OxyDex_2026-06-09_0529_summary.json — neither of which existed any more, so both 404'd, a warning was pushed, and the button silently did nothing. Fix: repointed the two filenames at the surviving exports uploads/ecgdex-2026-06-12.node-export.json + uploads/oxydex-2026-06-12.summary.json (no Integrator.src.html change needed — the paths live only in the app JS). Re-bundled Integrator.html. Verified post-fix: both load through the real normalizeFile path and fuse — 360 min overlap across 2 recordings, confirmed-events panel populated, desat match rate 100%.cleanArtifactHR defensive hardening — applied June 2026. The processNight hang originally surfaced while bootstrapping the ODI pool does not reproduce through the real pipeline: parseCSV already drops --,--,0 rows (line ~727), so processNight never sees them, and the one infinite-loop path in cleanArtifactHR (i = j with a non-advancing inner while) is unreachable with the shipped constants (HARD 20 · RECOV 10 · SOFT 15 → a soft rise always exceeds RECOV, so j always advances). It stays gated by tests/oxy-hang.worker.js (real parseCSV→processNight on a heavy-dropout pool, watchdog-timed — green, 15 nights, worst 316 ms). The previously-deferred defensive 1-liner is now applied: the index advance is i = j > i ? j : i + 1, guaranteeing progress even if SOFT ≤ RECOV is ever configured. Signature and return shape unchanged (the shared assertions in tests/dex-tests.js are the public contract — pure internal guard). Re-bundled OxyDex.html; suite green pre- and post-bundle (508 passed / 31 groups).renderPPG) drove the real detector into 2:1 beat-halving — fixed June 2026. On the ≤500 FULL lane the real PPGDSP recovered only ~0.60× of the beats ECGDex did (which is ~1.00× truth) at meanSQI 0.92–0.98 — a 2:1 lock (every other equal-amplitude pulse), not perfusion loss. Bisected to a single ingredient (clean-room control: clean pulses, real buildRR timing, wander, hi-freq noise, and motion bursts all tracked 1:1; only the contact-loss dropout halved). The dropout jumped the channel from its ≈−481000 DC baseline to ≈−10 — a ~490k step (≈200× the 2300-unit pulse) that, after the detector's 0.5–8 Hz band-pass, rang as a low-frequency transient large enough to hijack the beat-detector's autocorrelation period estimate (locking T≈274 samp / 39 bpm vs the true 162/65) → oversized search window → halving. The shipped PPGDSP was exonerated throughout (tracks REAL Polar PPG cleanly). Fix: model contact-loss as the pulsatile AC vanishing at the held DC baseline (a true flatline — still trips the SQI/flatline QC gate) instead of a 490k step. Result: beat recovery 0.60→1.03–1.10, recall 96–98%, real PPG unaffected, Dex-Test-Suite green (495/495). Residual: PpgDex mildly over-detected (~3–10% on synthetic vs ~1% on real). That residual is now FIXED (June 2026, renderPPG tuning — see the PpgDex-over-detection entry below): FULL-lane beat recovery 1.06→1.05, precision 0.90→0.92, synthetic PPG rMSSD inflation +38%→+16%. The genuine apnea-perfusion yield signal (low-amplitude apnea beats missed while SQI stays high) is now cleanly isolated → written up in qrs-yield.html.renderPPG) — fixed June 2026. The optical detector recovered slightly too many beats on the FULL-lane synthetic PPG (~6% net / ~10% false-positive), inflating PPG rMSSD ≈+38% and contaminating any cross-modality HRV comparison. Diagnosed with the new qrs-yield-analysis.html harness (beat-level recall/precision vs ground truth): the clean-window excess was the dicrotic shoulder being re-detected at faster heart rates, and the apnea-window excess was an oversized motion artifact (≈4× pulse amplitude) leaking through (the FULL lane runs PPGDSP without its ACC motion gate). Fix (all in renderPPG, synth-gen.js — cheap, no bundle/provenance impact): dicrotic 0.12→0.04 and blended onto the diastolic decay; per-sample optical noise 60→30; motion artifact 9000→950 (realistic ≈1× pulse, no longer detector-dominating); apnea perfusion attenuation deepened 0.55→0.30 so a genuine low-amplitude yield dip survives (SQI is correlation-based, so it stays green — the real effect the QRS-yield paper reports). Result: FULL-lane beat recovery 1.06→1.05, precision 0.90→0.92, synthetic PPG rMSSD inflation +38%→+16% (PAT-jitter-dominated). Dex-Test-Suite.html green; FULL-lane fidelity gate seeds 1.03 / 1.07.renderECGInt16) under-rendered beat-to-beat timing — fixed June 2026. The renderer measured pulse phase from each beat's ONSET with the R lobe at template phase 0.41, so every R landed at bcur.tMs + 0.41·RR and the rendered R-to-R interval became RR + 0.41·ΔRR — a low-pass of the true tachogram that attenuated reconstructed ECG rMSSD ≈26% (surfaced by qrs-yield-analysis.html; it is a renderer artifact, not an ECGDex property — ECGDex is validated on real ECG). Fix (in cohort-full.js — cheap, no bundle/provenance impact): pick the NEAREST beat per sample and offset phase so template 0.41 sits exactly on nb.tMs, placing every R at its true instant. Result: ECG beat recovery now exactly 1.00, ECG rMSSD bias −26%→≈0 (faithful). This unblocked the three-way rMSSD equivalence (rmssd-equivalence.html), where ECGDex now matches PulseDex to ±0.6 ms (r 0.9997). Dex-Test-Suite.html green.buildHash certifies the bundle template, not the code that runs — surfaced June 2026 during the re-bundle pass; the resulting gate gap is now closed. The re-bundle brief (and CLAUDE.md) assumed re-bundling an app changes its buildHash and so flips its committed uploads/*.json provenance fixtures to stale. It did not: editing only the external oxydex-dsp.js / integrator-app.js (leaving each *.src.html untouched) and re-bundling left OxyDex.html at 09c77b53517c and Integrator.html at eb0454c3431b — unchanged — so verify-provenance.html stayed all-green with no fixture regeneration needed. Mechanism: the inliner stores the app as a <script type="__bundler/template"> (pristine HTML skeleton, assets referenced by stable UUID) plus a <script type="__bundler/manifest"> (the actual *.js/fonts, gzip+base64 — which is why cleanArtifactHR appears nowhere as plain text in the 453 KB bundle). ganglior-provenance.js buildSource() hashes only the template; the manifest where the executable code lives is excluded. So a code-only re-bundle is invisible to buildHash. This contradicts the gate's stated guarantee ("the hash always tracks the shipped code … forces a re-bundle whenever source changes"): provenance currently certifies the bundle skeleton, not the executed code, and cannot detect external-*.js drift. Resolved by decision (June 2026): buildHash is kept deliberately coarse (a true fix needs owning the inliner — re-hashing to include the manifest would flip every committed fixture at once), and executed-code provenance was moved off it onto a stronger signal. verify-provenance.html GATE A now compares each bundle's statically-computed manifestHash (SHA-256 of the __bundler/manifest — which does move on any bundled-module change) against the committed BUILD-MANIFEST.json, and GATE B reads a FIXTURE-PROVENANCE.json sidecar that code-gates each fixture to its producing bundle's manifestHash, turning red the moment the code that made it changes. So buildHash still only certifies the skeleton, but the gate no longer relies on it for code identity. Standing guidance: regenerate a node's fixtures (re-run + re-export) whenever you change its code, and record the producing manifestHash in the sidecar.nocturnalHypo flag drops sharp nocturnal hypos — root cause re-diagnosed (June 2026): it's compression-artifact rejection, not slice-truncation. First seen as the coupling pilot's hypo flag firing on ~0/4 sleep-window slices and assumed to be loss of full-day context. Probing the actual slice (seed 6) disproved that: the planted hypo genuinely reaches ~56 mg/dL for ~50 min (10 cells < 70) in the raw CGM — the dip is right there. The flag misses it because a sharp drop-and-recover excursion (insulin hypo + Somogyi rebound) carries the same bracketing signature as a positional sensor-pressure artifact, so GlucoDex's computeBaselineArr/compression rejection flags those cells (f===3) and excludes them from hypo events. Fix (pilot + fusion): score nocturnal hypos with a flag-independent window-local time-below-70 on the raw slice (any ≥15-min run < 70 mg/dL). In the Integrator this is glucoseMetricsInWindow() (integrator-dsp.js); in the coupling tool it's the new raw-CSV scorer in cohort-worker.js's cgmcouple branch, exposed as a hypo-enrichment knob. Hypo-enriched re-run (479 planted hypo-nights): window-local recall 1.00 (479/479) vs the cleaned-series flag 0.008 — a clean before/after, written up in cgm-hrv-coupling.html §3.3. Now fixed in-detector (June 2026): the shipped GlucoDex detector itself is fixed too, not just the pilot + fusion workaround. glucodex-dsp.js gained a _looksLikeGenuineHypo() discriminator that guards the compression-rejection pass: a sustained sub-70 run (≥15 min) that reaches a real nadir (≤~60 mg/dL) and is entered/left gradually (descent & rebound over multiple cells) is no longer marked f===3, so it survives into nocturnalHypo() — while a near-vertical single-cell drop-and-recover (true positional artifact) is still rejected. A permanent two-directional assertion (GlucoDex hypo ≠ compression artifact) locks both in tests/dex-tests.js: a hand-built ~56 mg/dL / ~50 min Somogyi-rebound hypo fires nocturnalHypo (was 0), and a vertical-edged plateau still does not. Signatures/returns unchanged (back-compat; new logic is additive).