Production smoke panicked at trunk.rs:mamba2_l1() during
PerceptionTrainer::from_checkpoint. Root cause: load_checkpoint
called new_random which left mamba2_stack_1/2 = None, then tried
to upload weights into None blocks.
PerceptionTrainer::new was the only caller that populated the
Mamba2 stacks (X3/X5 migrations stopped at the accessor methods
but never moved construction). Inference paths that didn't go
through PerceptionTrainer::new — exactly what fxt-backtest does
via from_checkpoint → load_checkpoint — hit the gap.
Move Mamba2Block::new + state allocation into CfcTrunk::new_random.
PerceptionTrainer::new now sets up its optimizer + scratches against
the trunk-owned blocks via existing accessors (mamba2_l1/mamba2_l2).
Extends the trunk roundtrip test to:
- assert mamba2 weight slices are non-empty (catches empty-buffer
regressions that would let bit-equivalence pass trivially)
- bit-equivalence-check Mamba2 stack 1 + stack 2 weights through
save -> load, reproducing the exact failure path that hit prod.
Verified locally on RTX 3050 Ti — full workspace cargo check passes,
test passes with non-empty weight slices.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>