diff --git a/docs/superpowers/specs/2026-05-20-continuous-reasoning-trader-design.md b/docs/superpowers/specs/2026-05-20-continuous-reasoning-trader-design.md index 4aa0eeaa6..917cd0e58 100644 --- a/docs/superpowers/specs/2026-05-20-continuous-reasoning-trader-design.md +++ b/docs/superpowers/specs/2026-05-20-continuous-reasoning-trader-design.md @@ -1,9 +1,92 @@ # Continuous-Reasoning Trader — Architecture Design **Date:** 2026-05-20 -**Branch context:** `ml-alpha-phase-a` (S2 closed at `8828e8ab1`) -**Status:** Design v2 (amended from v1 after self-critical review — 12 issues addressed inline) -**Supersedes scope of:** `2026-05-19-isv-driven-stop-controller-design.md` (that spec ships clean stops; this spec replaces the rule-based policy that consumes those stops) +**Branch context:** `ml-alpha-phase-a` (S2 closed at `8828e8ab1`; Phase A attempt fe2498769 RED on Gate 1) +**Status:** Design v3 — phase split collapsed after empirical Gate 1 failure + architectural clarification +**Supersedes scope of:** `2026-05-19-isv-driven-stop-controller-design.md` + +--- + +## v3 ARCHITECTURE RESET (the section that supersedes everything below) + +**Date:** 2026-05-20 (same day as v2; cluster smoke evidence forced the reset) + +**Empirical trigger.** Phase A as designed in v2 (continuous controller with scalar conviction-EMA on `max(|p−0.5|)`, rescale on target magnitude) failed Gate 1 catastrophically. Smokes `vjmwc` (commit `3d8f12deb`) and `lkrdf` (commit `fe2498769` — with the amplification-clamp fix) both produced: +- 155k+ trades (62× baseline 2,511) +- max-drawdown 9,100% (175× baseline 53.5%) +- Sharpe-ann −15.7 (vs baseline −6.6) +- ~83% of realized loss = round-trip cost (155k × $12.50) + +The clamp fix `min(scale, 1.0)` prevented the most pathological amplification but had effectively zero impact on the catastrophic outcome — confirming the bug is structural, not in the scalar EMA formula. + +**Architectural finding.** The phase split v2 made (A: continuous control / B: signal-driven position management) is artificial. The two are the same mechanism. A scalar EMA on `max(|p−0.5|)` cannot smooth a controller that's churning on direction flips between horizons; only the multi-horizon ISV-weighted conviction (was §4.4, deferred to Phase B in v2) is structurally coherent. + +**The user-validated mental model.** The agent should reason like a discretionary trader: the multi-horizon signal vector at any moment IS a forward prediction of the trade trajectory; the optimal position is the inventory implied by current beliefs; trade actions are sparse because most events produce only fractional adjustments to a stable optimum. Continuous evaluation; discrete action. + +### v3 phase structure (REPLACES v2's A/B/C/D) + +``` +CRT.1 Unified Inventory Controller (was Phase A + Phase B merged) + - forward_step every event (already shipped: A0.5 / commit a0e81fbdf, 92f8b10ed) + - decision_stride deleted (already shipped: A1 / commit 045850e8f) + - Multi-horizon ISV-weighted conviction (v2 §4.4 formula — promoted from Phase B) + - Wiener-α EMA on the multi-horizon conviction (v2 §4.2 — promoted) + - target_lots = round(direction × |conviction_ema| × envelope_max) + - No-trade band in seed_inflight: skip if |delta| < δ + - open_trade_state 24→64 byte expansion (v2 §7 — promoted from Phase B) + - Conviction-degradation exit (v2 §4.3): EMERGENT from target→0 when conviction collapses, + plus a composite-signal safety layer matching v2 §4.3 + +CRT.2 Adaptive Risk Envelope (was Layer C) + - ISV-derived max_lots, threshold, target_vol (unchanged from v2 §5) + +CRT.3 Online Weight Adaptation (was Layer D) + - LoRA adapter + EWC++ + shadow eval (unchanged from v2 §6) +``` + +### Why the v2 phase split was wrong + +1. **Direction jitter, not magnitude noise, is the dominant source of hyperactivity.** Scalar EMA on `max(|p − 0.5|)` smooths magnitude only; doesn't smooth direction. The multi-horizon ISV-weighted conviction formula `weight_h × magnitude_h × direction_h` summed across horizons — particularly with ISV weights that down-weight low-SNR horizons — naturally smooths direction because disagreeing horizons partially cancel. + +2. **A target-position controller without a no-trade band cannot work at event rate.** Even with perfect smoothing, target moves fractionally every event; with target-delta seed_inflight semantics, every fractional move generates an order. The no-trade band (skip seeding if |Δ| < δ) is structurally required; deferring it to "Phase B" left Phase A unrunnable. + +3. **Conviction-degradation exit is not a separate exit policy — it emerges from `target_lots → 0` when conviction collapses.** Splitting "continuous control" from "signal-driven exit" doubly-implements what's actually one mechanism. + +### Inheritance from v2 + +- §4.4 conviction formula (with ε-floor net_edge; not the v1 backwards-fallback): **promoted, unchanged.** +- §4.2 Wiener-α adaptive EMA: **promoted, applied to the multi-horizon conviction scalar instead of `max(|p−0.5|)`.** +- §4.3 composite exit signal: **emergent + safety.** The unified target-→-zero path handles the common case; the v2 §4.3 composite formula remains as a safety layer for cases where target-derivation hits an edge (e.g., conviction stuck above zero but trade is deep in loss). +- §5 (CRT.2) and §6 (CRT.3): **unchanged.** +- §7 (open_trade_state 64-byte layout): **promoted to CRT.1.** +- §8 hardcoded-vs-adaptive boundary: **unchanged.** + +### Gate restructure (v3) + +| v2 Gate | v3 status | +|---|---| +| Gate 1 (Layer A continuous controller) | REMOVED — A and B are co-shipped as CRT.1 | +| Gate 2 (Layer B multi-horizon + exit + state expansion) | **REPROMOTED as Gate CRT.1**, with the v2 §9 Gate 2 tiered MUST/WIN criteria intact | +| Gate 3 (Layer C envelope) | unchanged → Gate CRT.2 | +| Gate 4 (Layer D online) | unchanged → Gate CRT.3 | + +### What survives from v1/v2 commits + +The following commits are load-bearing and STAY on the branch: +- `a0e81fbdf` — forward_step incremental SSM (A0.5) +- `92f8b10ed` — forward_step_into eliminates GPU↔CPU round-trip (A0.5 corrective) +- `045850e8f` — delete decision_stride field (A1; greenfields atomic) +- `3d8f12deb` — buffer-level seed bit-identity test (A0.5 polish) + +What gets REPLACED in CRT.1 implementation: +- `1d889d2de` (A2 scalar conviction-EMA with aggregate rescale) — **superseded** by the multi-horizon §4.4 formula +- `fe2498769` (A2.1 clamp on the broken rescale) — **superseded** for the same reason + +The amplification clamp in `fe2498769` and the scalar EMA infrastructure in `1d889d2de` are not load-bearing for CRT.1; the multi-horizon formula replaces the scalar approach end-to-end. Code-wise: the three conviction-EMA device slots (`conviction_ema_d`, `conviction_diff_var_ema_d`, `conviction_sample_var_ema_d`) STAY in `LobSimCuda` — the EMA mechanism is reused on the multi-horizon conviction scalar. What gets deleted: the `final_size *= scale` rescale step in both decision kernels. + +--- + +## v2 changelog (retained for audit trail; superseded by v3 above) **v2 changelog** (vs v1 commit `0f3484325`): 1. §4.4 conviction: removed backwards cold-start fallback; replaced with ε floor on net_edge for smooth bootstrap. No regime switch when model has zero edge. @@ -36,41 +119,50 @@ This spec specifies the rebuild. --- -## 2. Architectural Vision +## 2. Architectural Vision (v3 — see "v3 ARCHITECTURE RESET" section above) -Four layers, sequenced. Each independently validatable. Each addresses a specific failure mode visible in the S2 baseline. +**Three phases, sequenced.** The original v2 four-layer split has been merged into three because the empirical Gate-1 evidence + user clarification showed that v2 Layer A (continuous control) and Layer B (signal-driven position management) are the same mechanism. ``` ┌────────────────────────────────────────────────────────────────────┐ -│ LAYER A: Continuous Control Loop │ -│ Controller runs every event. decision_stride deprecated. │ -│ Failure addressed: stale-state decisions. │ +│ CRT.1 Unified Inventory Controller │ +│ Continuous evaluation (every event), discrete action. │ +│ │ +│ - forward_step every event (already shipped via A0.5) │ +│ - Multi-horizon ISV-weighted conviction (§4.4) │ +│ - target_lots = direction × |conviction_ema| × envelope_max │ +│ - Wiener-α EMA on the multi-horizon conviction (§4.2) │ +│ - No-trade band on |target − current| in seed_inflight │ +│ - open_trade_state 24→64 expansion for trajectory (§7) │ +│ - Conviction-degradation exit emergent (target→0) + │ +│ composite-signal safety circuit-breaker (§4.3) │ +│ │ +│ Addresses: stale-state decisions, magnitude noise, direction │ +│ jitter, fixed-time exits, spread-cost death-spiral. │ ├────────────────────────────────────────────────────────────────────┤ -│ LAYER B: Signal-Driven Position Management │ -│ Multi-horizon action fusion (h100/h500/h1500/h6000). │ -│ Continuous sizing: target_lots = conviction × envelope. │ -│ Conviction-degradation exit: replaces max_hold. │ -│ open_trade_state expanded 24 → 128 bytes for trajectory. │ -│ Failure addressed: cap-binding holds, no mid-trade adjustment. │ +│ CRT.2 Adaptive Risk Envelope │ +│ ISV-derived max_lots / threshold / target_vol from rolling │ +│ Sharpe × drawdown × regime-vol. │ +│ Addresses: fixed risk in regime-varying market. │ ├────────────────────────────────────────────────────────────────────┤ -│ LAYER C: Adaptive Risk Envelope │ -│ max_lots: ISV-derived from rolling Sharpe × drawdown × regime-vol.│ -│ threshold: conviction-percentile gate. │ -│ target_annual_vol: regime-vol-inverse. │ -│ Failure addressed: fixed risk in regime-varying market. │ -├────────────────────────────────────────────────────────────────────┤ -│ LAYER D: Online Weight Adaptation │ -│ LoRA adapter on frozen base. Trajectory-batch offline updates. │ -│ EWC++ regularizer. Shadow eval + circuit-breaker revert. │ -│ Failure addressed: static model in non-stationary market. │ +│ CRT.3 Online Weight Adaptation │ +│ LoRA + EWC++ + offline-batch trajectory updates + shadow │ +│ eval + circuit-breaker revert. │ +│ Addresses: static model in non-stationary market. │ └────────────────────────────────────────────────────────────────────┘ ``` -Sequencing rationale: A unlocks event-rate consumption needed by B. B is where alpha lives. C amplifies B by shaping when and how much B trades. D amplifies whatever's working in B+C. Each gate's lift is conditional on the prior gate being green — [no-deferrals-for-complementary-fixes](../../../../home/jgrusewski/.claude/projects/-home-jgrusewski-Work-foxhunt/memory/feedback_no_deferrals_for_complementary_fixes.md) doesn't apply because the layers are amplifications of one another, not independent fixes for orthogonal mechanisms. +**Sequencing rationale (v3):** CRT.1 unifies the signal-to-action mechanism — without it, neither CRT.2 nor CRT.3 has a coherent base to amplify. The v2 phased validation gates collapse one tier: CRT.1's gate is what was Gate 2 (Layer B) in v2; Gate 1 (Layer A) is gone because A standalone is incoherent. The "every gate green before the next" discipline survives. + +**The mental model.** Every event: the signal vector is a forward prediction; ISV state tells us how much to trust each horizon; the unified conviction is the weighted aggregate; the target is the optimal inventory given current beliefs. Most events: target moves fractionally from prior — the no-trade band absorbs the noise, no order seeded. When the signal genuinely shifts (or the trade thesis breaks): target moves enough to cross the band, an order seeds, the position adjusts. Continuous evaluation, discrete action. No fixed cadence — the signal IS the cadence. + +The detailed sections below were authored in v2 and remain accurate for the mechanisms they describe; the only structural change is that v2 §3 (Layer A) is absorbed into CRT.1, v2 §4 (Layer B) is renamed CRT.1, v2 §5 → CRT.2, v2 §6 → CRT.3. --- -## 3. Layer A — Continuous Control Loop +## 3. Layer A — Continuous Control Loop (v2; ABSORBED INTO CRT.1 IN v3) + +**v3 status:** the components of this layer are part of CRT.1. A0.5 (forward_step every event, commits `a0e81fbdf` + `92f8b10ed`) and A1 (decision_stride deletion, commit `045850e8f`) are load-bearing for CRT.1 and stay. The original "Gate 1" for Layer A alone is dropped; validation moves to Gate CRT.1. ### 3.1 Current state @@ -112,9 +204,16 @@ At event-rate, consecutive decisions see nearly-identical state. If the state→ --- -## 4. Layer B — Signal-Driven Position Management +## 4. CRT.1 — Unified Inventory Controller (was "Layer B" in v2) -This is the heart of the rebuild. Three sub-components. +This is the unified architecture in v3. Continuous evaluation, discrete action. + +### 4.0 Required additions in v3 vs v2 §4 + +- **No-trade band**: `seed_inflight_limits_batched` must skip seeding when `|target_lots − effective_position| < delta_floor`. `delta_floor` is small (1 lot default for the bootstrap; CRT.2 may make it ISV-derived later). Without this, every fractional target change generates a fill — the v2 Gate-1 empirical failure mode. +- **Multi-horizon conviction promoted from §4.4**: this is the ONLY conviction formula in v3. The scalar `max(|p−0.5|)` approach used in v2's A2 commits is dead — it cannot smooth direction jitter and is structurally insufficient. + +Everything else in v2 §4.1–§4.5 below is retained. ### 4.1 Multi-horizon action fusion