From 35e7582287ab5a82bf57561895b5a095dc9b6e24 Mon Sep 17 00:00:00 2001 From: Yuren Hao Date: Thu, 16 Jul 2026 04:33:29 -0500 Subject: RESULT 29: qcomp8 tax-free (+0.0018) = T64 8-bit compute green light; --centmirror ships (cos 1.000000000, 1.72x -> 1.39x) Co-Authored-By: Claude Fable 5 Claude-Session: https://claude.ai/code/session_014FAPDWQ49M5Ye3NpTndTpn --- docs/campaign/CASCADE_ABLATION_PLAN.md | 19 +++++++++++++++++++ ep_run/casc_eq_train.py | 30 +++++++++++++++++++++++++++--- 2 files changed, 46 insertions(+), 3 deletions(-) diff --git a/docs/campaign/CASCADE_ABLATION_PLAN.md b/docs/campaign/CASCADE_ABLATION_PLAN.md index 12751d9..1502ed2 100644 --- a/docs/campaign/CASCADE_ABLATION_PLAN.md +++ b/docs/campaign/CASCADE_ABLATION_PLAN.md @@ -568,6 +568,25 @@ direction), not training-under-fault; wave-2 = co-training with faults injected +### RESULT 29 (2026-07-16): qcomp VERDICT — 8-bit COMPUTE quantization is FREE (T64 green light); centmirror ships (1.39x). +qcomp arms (compute on DAC-grid weights, fp32 master = word-streaming / shadow accumulation), +same protocol, vs ctl 1.2678: +| bits | qcomp (T64 scenario) | qup (naked resident) | +|---|---|---| +| 8 | **1.2696 (+0.0018 = ZERO)** | 1.3096 (+0.042) | +| 6 | 1.3026 (+0.035) | 1.3598 (+0.092) | +| 4 | 1.4077 (+0.140) | — | +- 8-bit DACs + digital master = tax-free at 42M: the Y3/pc AD7528 line and the T64 word-streaming + architecture pass gate #1b. 6-bit compute has a real but moderate tax; 4-bit heavy. +- BP mirror suite RUNNING (bp_qctl 49.5k, then qup10/8/6 + qcomp8/6/4): the Delta-vs-Delta verdict + (EP-specific or generic) lands tonight; RESULT 28's naked-cell reading stays provisional till then. +- ESTIMATOR COST ENGINEERING sealed: --centmirror (the -beta pass initialized as the MIRROR of the + +beta solution at the shared free anchor + 1 polish sweep; second free pass and K-1 sweeps + deleted). Gradtest cos 1.000000000 vs sequential centered (relerr 2.2e-5). Quiet bench B12/amp: + plain 4.389 it/s | sequential centered 2.547 (1.72x) | centfast 2.684 (1.64x) | **centmirror + 3.169 (1.39x)**. With est_late@80%: amortized ~1.08x — centered is now essentially free at scale + (8B ledger: 3.2x -> ~3.45x vs BP). + ### RESULT 28 (2026-07-16): STAGE-0 HW GATE #1 — naked analog-resident updates need >10 bits; T64's word-streaming scenario measured next. Protocol: arms7 (resume s45000 -> 55000, ctl 1.2678). --qup_bits = weights snapped to an ABSOLUTE per-tensor grid after every update, stochastic rounding (= analog-resident cells, NO shadow). diff --git a/ep_run/casc_eq_train.py b/ep_run/casc_eq_train.py index 17a0c70..8e246d1 100644 --- a/ep_run/casc_eq_train.py +++ b/ep_run/casc_eq_train.py @@ -71,6 +71,9 @@ ap.add_argument('--qcomp_bits', type=int, default=0) # STAGE-0 T64 scenario ap.add_argument('--qup_bits', type=int, default=0) # STAGE-0: quantize weights to an absolute # per-tensor grid after each update (stochastic # rounding); emulates finite analog cell levels +ap.add_argument('--centmirror', action='store_true') # centered's -beta pass initialized as the MIRROR + # of the +beta solution (d- = -d+ at shared anchor) + # + one polish sweep; skips its free pass entirely ap.add_argument('--centfast', action='store_true') # centered via ONE doubled batch [x;x], +beta/-beta halves # (shared kernels; math identical to sequential centered) args = ap.parse_args() @@ -369,6 +372,7 @@ def relax(z0, zs, ins, outs, y, beta, K, x, bmask=None): GOV['rho'] = rlist[-1] / rlist[-2] # per-sweep contraction ratio = live loop-gain meter GOV['res'] = rlist[-1] GOV['kuse'] = K + GOV['_last_d'] = d return zs, outs prev_res, k = None, 0 @@ -386,6 +390,7 @@ def relax(z0, zs, ins, outs, y, beta, K, x, bmask=None): forces(True) # final graphed round at the settled state (theta-read) rebuild(True) GOV['kuse'] = k + 1 + GOV['_last_d'] = d return zs, outs def dFdtheta(zs, x, y, beta): @@ -496,9 +501,28 @@ def ep_step(x, y): gsC = torch.autograd.grad(obj_loss(readout(zp[-1].detach()).reshape(-1, vocab), y.reshape(-1)), all_params, allow_unused=True) b2 = -beta_t if EST == 'centered' else 2.0 * beta_t - z0b, zsb, insb, outsb = free_states_graphed(x) - zsb_free = [z.clone() for z in zsb] - zpb, lob = relax(z0b, zsb, insb, outsb, y, b2, GOV['K'], x) + if EST == 'centered' and args.centmirror: + # MIRROR WARM-START: d-(free anchor) = -d+ exactly (linear in beta); init the -beta + # states as the mirror of the settled +beta solution, then ONE polish sweep corrects + # the O(beta^2) even part. Skips the second free pass and K-1 sweeps. + dm = [(-di).detach() for di in GOV['_last_d']] + zsb_free = zs_free + prev = z0 + zsb, insb, outsb = [], [], [] + with torch.autocast('cuda', dtype=torch.bfloat16, enabled=args.amp): + for l in range(args.L): + i = prev.detach().requires_grad_(True) + o = blocks[l](i, mask) + zsb.append(o.detach().float() + dm[l]) + insb.append(i); outsb.append(o) + prev = zsb[l] + _k1 = GOV.get('kuse') + zpb, lob = relax(z0, zsb, insb, outsb, y, b2, 1, x) + GOV['kuse'] = _k1 # telemetry: report the +beta pass's K, not the mirror polish + else: + z0b, zsb, insb, outsb = free_states_graphed(x) + zsb_free = [z.clone() for z in zsb] + zpb, lob = relax(z0b, zsb, insb, outsb, y, b2, GOV['K'], x) with torch.no_grad(): drift2 = sum(float((a - b).norm()) for a, b in zip(zpb, zsb_free)) / max( sum(float(b.norm()) for b in zsb_free), 1e-9) -- cgit v1.2.3