From 3e5085e06d3aac7a8e2f39e3ec7ca309b41866bd Mon Sep 17 00:00:00 2001 From: Matiq Date: Fri, 21 Aug 2026 19:29:21 +0300 Subject: [PATCH] phase A: reduction law found (affine in dB), canon unchanged; keep RT_DUMP tooling - Effective reduction is affine in dB(lvl): x_exp2 = -0.6646 - 0.05877*dB (mask ~ 0.8*lvl^-0.354, gamma ~= decomp 0.344); tones +-0.13 dB over 42 dB - Pre-IIR calibrated variant (X0=1.8/S=0.11): TOTAL 2.633 vs HEAD 2.286; wins t1kq/t1k/al/comb, loses res/dual -> gate fails, canon stays LUT - Grid search (X0,S,floor,CMAX) on validated trajectory model: no scalar law of the family fits tone+noise simultaneously (res tension) - Refuted: high-bin/IIR3-backward propagation, direct-affine bypass, positive floors, ceilings - Kept opt-in instrumentation RT_DUMP_BIN / RT_DUMP_ALL for Step 7 capture - Docs: NOTES_LEVEL 21d, BITEXACT_PLAN s.0 note, roadmap, AGENTS --- AGENTS.md | 4 +++ BITEXACT_PLAN.md | 10 +++++++ dsp/framed_model.cpp | 50 ++++++++++++++++++++++++++++++++ handoff/NOTES_LEVEL.md | 66 ++++++++++++++++++++++++++++++++++++++++++ roadmap.md | 7 ++++- 5 files changed, 136 insertions(+), 1 deletion(-) diff --git a/AGENTS.md b/AGENTS.md index 3aff070..e0001ec 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -97,6 +97,10 @@ scale → LUT level-domain (t^γ·MULT, γ=0.344 decomp / MULT=4.2 placeholder) exp2(−lvl) не ограничен (dual@500: константный −6.7 dB при всех q). Лечится Шагом 7 (live-захват A/B/γ) или статическим hunt'ом clamp'а в level-пути. Слепая подкрутка γ/MULT исчерпана (свип 21c). +- **21d — закон редукции найден, канон НЕ сменён**: эффективное ослабление аффинно + в dB(lvl) (маска ≈ 0.8·lvl^−0.354; al-свееп ±0.13 dB). Scalar-семейство (X0,S,floor, + CMAX) не закрывает тон+шум одновременно → res/dual регресс у любой точки; ищем + контент-зависимый механизм. Инструментарий RT_DUMP_BIN / RT_DUMP_ALL в коде (opt-in). ### Открытые bit-exact/структурные пробелы (см. NOTES_LEVEL.md) 1. Насыщение кривой редукции (см. выше) — приоритет №1. diff --git a/BITEXACT_PLAN.md b/BITEXACT_PLAN.md index bb35032..021a45b 100644 --- a/BITEXACT_PLAN.md +++ b/BITEXACT_PLAN.md @@ -26,6 +26,16 @@ comb 10 dB). Bit-exact ДОСТИЖИМ (F0 gate: плагин байт-дете (struct = структурная цепь на внутренней сетке 48000/4096 через `dsp/build/render48k`, прогон `scripts/corpus_structural.py`, NOTES_LEVEL:21c. Bridge = `framed_test` 44.1k.) +> **21d**: найден закон редукции — эффективное ослабление АФФИННО в dB(lvl): +> `x_exp2 = −0.6646 − 0.05877·dB` (маска ≈ 0.8·lvl^−0.354, γ≈decomp 0.344). +> На тонах al-свеепа линейность ±0.13 dB (42 dB диапазона!). Прекалибровка +> pre-IIR (X0=1.8/S=0.11) даёт TOTAL 2.633: t1kq/t1k/al/comb лучше, res/dual +> хуже. Grid-search семейства (X0,S,floor,CMAX) на валидированной траекторной +> модели: оптимум rms 0.75 dB, но НИ ОДНА точка семейства не закрывает тон+шум +> одновременно → канон не меняем (gate «без регресса групп»), ищем +> контент-зависимый механизм (детектор att/rel на флюктуациях / combine- +> консюмер). Инструментарий RT_DUMP_BIN/RT_DUMP_ALL оставлен opt-in. + **Корень проблемы**: активный канон — ЭМПИРИЧЕСКАЯ bridge-модель `C = G·LUT(xv) + W·warp(f)^A; gain = (1−C)·res^rp` (xv=log10(am/res)). Это ПОГОНА, не транскрипция. Структурная цепочка FUN_180529fe0 перенесена в C++ на внутренней сетке diff --git a/dsp/framed_model.cpp b/dsp/framed_model.cpp index af2f24c..83275d8 100644 --- a/dsp/framed_model.cpp +++ b/dsp/framed_model.cpp @@ -121,6 +121,13 @@ static void process_band_structural( mask_out[k] = static_cast(std::exp2(-static_cast(band_level[k])) * f6f8[k]); } + // RT_DUMP_BIN debug: capture pre-warp mask (opt-in, no cost when unset). + static std::vector dbg_prewarp; + const char* dbg_path = getenv("RT_DUMP_BIN"); + if (dbg_path) { + dbg_prewarp.assign(mask_out, mask_out + nbin); + } + fn529fe0::combine_acc(acc.data(), band_level.data(), f6f8.data(), kRTAtt, kRTRel, nfft); @@ -154,6 +161,49 @@ static void process_band_structural( for (size_t k = 0; k < nfft; k++) { mask_out[k] = mask_out[k] * (fVar30 * 1.0f) + (1.0f - fVar30); } + + // RT_DUMP_BIN: single-frame per-bin tract at frame RT_DUMP_FRAME (default + // 100): k am res lvl_raw band_level post-IIR1/2, pre-warp mask, W weight. + if (dbg_path && !dbg_prewarp.empty()) { + static int dbg_frames = 0; + int dbg_target = 100; + if (const char* fs = getenv("RT_DUMP_FRAME")) dbg_target = atoi(fs); + if (dbg_frames++ != dbg_target) return; + FILE* df = fopen(dbg_path, "wb"); + if (df) { + fprintf(df, "# fc=%g q=%g sens=%g rp=%.6f\n", band.fc, band.q, band.sens, rp); + for (size_t k = 0; k < nbin; k++) { + double res_k = std::max(static_cast(res[k]), 1e-12); + double lvl_raw = static_cast(am[k]) / res_k * scale_factor; + double w = kBand768[k] * kWarp[k] * std::pow(res_k, rp); + fprintf(df, "%zu %.9g %.9g %.9g %.9g %.9g %.9g\n", k, + static_cast(am[k]), res_k, lvl_raw, + static_cast(band_level[k]), + static_cast(dbg_prewarp[k]), w); + } + fclose(df); + } + } + + // RT_DUMP_ALL trajectory: append per-frame lvl_raw spectrum (binary: + // int32 frame, int32 nbin, float32 lvl_raw[nbin]). Single-band cases only. + // Detector path is law-independent -> one capture serves offline law fits. + if (const char* ap = getenv("RT_DUMP_ALL")) { + static FILE* af = fopen(ap, "ab"); + if (af) { + static int aframe = 0; + int32_t hdr[2] = {static_cast(aframe++), + static_cast(nbin)}; + fwrite(hdr, sizeof(int32_t), 2, af); + for (size_t k = 0; k < nbin; k++) { + double res_k = std::max(static_cast(res[k]), 1e-12); + float lv = static_cast( + static_cast(am[k]) / res_k * scale_factor); + fwrite(&lv, sizeof(float), 1, af); + } + fflush(af); + } + } } } // namespace diff --git a/handoff/NOTES_LEVEL.md b/handoff/NOTES_LEVEL.md index 3fd1b48..c441851 100644 --- a/handoff/NOTES_LEVEL.md +++ b/handoff/NOTES_LEVEL.md @@ -1296,3 +1296,69 @@ Do NOT tune MULT further — it is calibrated; the CURVE SHAPE is wrong. ### FFT-conv priority DOWNGRADED: NOTES:18c shows window 0x540658 tail is near-flat (0.8->1.0 plateau at N/2>=2048), FIR-construction effect on mask shape minimal for N=4096. Step 4 stays P3. + +## ============ UPDATE 2026-08-21d: REDUCTION-LAW DISCOVERY + Phase A closure ============ + +### Discovery: effective reduction is AFFINE in dB(level) +RT_DUMP_BIN tracts (frame 100) across al sweep fit: + x_exp2 = -0.6646 - 0.05877 * dB(lvl_raw) (mask ~ 0.8 * lvl^(-0.354)) +gamma_eff 0.354 ~= decomp BandConfig gamma 0.344 (NOTES:967) -> power law, +NOT the double-exp t^gamma->exp2 form (21c). Tone-levels verified +-0.13 dB. + +### Pre-IIR application calibrated through chain model +Python simulator (tables from rt_mask_tables.cpp; IIR1 fwd, IIR2 fwd, exp2*0.8, +W, IIR3 bidi x2): pre-IIR affine peak dilutes ~2.3x by spatial IIRs -> +X0=1.8, SLOPE=0.11 (max|x-resid| 0.09 ~= +-0.5 dB on tones). +FULL CORPUS fresh-build A/B (stale-binary protocol, both reproduce exactly): + group old(HEAD LUT) new(affine pre-IIR) + t1kq 0.768 0.460 v + t1k 2.114 1.196 v + al 0.986 0.132 v (all 6 levels |e|<=0.25) + res 0.437 2.046 x + dual 3.264 4.317 x + comb 6.116 5.718 v + TOTAL 2.286 2.633 + +### Phase A experiments (ALL on fresh builds / validated models) +1. res regression is REAL (not stale binary; reproduced both directions). +2. High-bin/IIR3-backward propagation hypothesis REFUTED: at frame-100 the + two laws give IDENTICAL masks on res_500 (<1e-4 everywhere); divergence + lives in other frames' level zone (-13..+15 dB) where old cuts more. +3. Direct-affine (bypass IIR1/2, raw constants) REFUTED: TOTAL 2.777. + Spatial IIRs are integral to the effective curve. +4. Offline trajectory model (RT_DUMP_ALL per-frame lvl_raw; chain sim; + metric-window frames [55,90)/[243,278) @48k/1024-hop; zero-pad frames + excluded — they are beyond the trimmed output!) VALIDATED: known-law + predictions within 0.09..0.19 dB on res_500/al_24/t1k_1000 (al_12 0.53). +5. Grid search over affine family (X0, SLOPE, floor F>=0, ceiling CMAX), + objective = sum pred_err^2 over anchored cases: + OPTIMUM X0=2.00 S=0.0825 F=0 CMAX=inf -> rms 0.75 dB with + res_500 +0.84 / al12 +0.29 / al24 -1.21 / t1k -0.02. + Ceiling never active in-grid; positive floors do NOT help (top all FL=0). + +### KEY NEGATIVE RESULT +NO law of the scalar affine family fits tone AND noise content +simultaneously (res tension +0.4..+1.1 unavoidable). Old Pchip "wins" on +res/dual/comb via error cancellation, not shape correctness; affine wins +tones decisively (al +-0.13 dB linearity over 42 dB!). The missing piece is +CONTENT-DEPENDENT behavior: detector dynamics (att/rel interplay with +fluctuating spectra), or combine/acc consumer (multiband feedback), or +saturation mechanism. => Gate "no group regression" FAILS for every family +member -> committed canon stays HEAD (LUT g=0.344/m=4.2). + +### Tooling kept (opt-in env, zero cost when unset) +- RT_DUMP_BIN= [RT_DUMP_FRAME=n]: single-frame tract dump (7 cols). +- RT_DUMP_ALL=: append per-frame binary lvl_raw spectra + [i32 frame][i32 nbin][f32 x nbin]. Use ONE env per run (BIN early-return + eats ALL frames if combined!). rm target first (append mode). + Captures live under /tmp/opencode/traj_*.bin (law-independent detector). +- Offline engine: /tmp/opencode/phaseA_grid_fast.py (combo-vectorized chain + sim + grid search); estimator zoo: phaseA_estimator_zoo.py. + +### NEXT (Phase B candidates, priority order) +1. Detector dynamics: att/rel on fluctuating spectra vs ref renders of + noise-like material (res group) — per-frame gain extraction protocol + ready (STFT ratio out/in at metric bin, see phaseA session notes). +2. Step 7 live capture ctx+0x188 (constants + possible content-dependent + branch), NOTES_CAPTURE.md method. +3. combine consumer hunt (multiband cascade) for dual/comb. diff --git a/roadmap.md b/roadmap.md index 6ccd772..929730e 100644 --- a/roadmap.md +++ b/roadmap.md @@ -20,7 +20,12 @@ > exp2(−lvl) нет → Шаг 7 захват A/B/γ или статический hunt clamp'а в level-пути. > Путь к байтам — `BITEXACT_PLAN.md` (8 шагов, пере-скоуп Шага 2: acc не имеет > однополосного консюмера; FUN_1805316e0 = writer коэффициентов, НЕ комбинер). -> Полный журнал — `handoff/NOTES_LEVEL.md` (апдейты 20j–21c). +> Полный журнал — `handoff/NOTES_LEVEL.md` (апдейты 20j–21d). + +> **21d**: закон редукции найден — АФФИННО в dB (маска≈0.8·lvl^−0.354, γ≈0.344 +> decomp); на тонах линейность ±0.13 dB. Но scalar-семейство не закрывает тон+шум +> одновременно (res-тенция) → канон не меняем; следующий рычаг — контент-зависимость +> (att/rel на флюктуациях, combine-консюмер). Инструментарий RT_DUMP_BIN/RT_DUMP_ALL. - **Статический декомп DSP-ядра — закрыт (~95%)**: twin-резонатор, генератор case8, level-path (0x529fe0/0x563440/0x563a60), mask-apply (FUN_180529fe0 mono-path), IIR-трекеры,