j142 retire the ADE+SBC gun (rack id 17): the owner watched it, it does not learn, throw it away

Remove guns/bitbrain_net.nim (+README), test_bitbrain_net.nim,
measure_bitbrain_scaling.nim, rack id 17 and all of its plumbing in
selector.nim / ModularBot.nim / env_report.nim, the TR_BITBRAIN_NET switch
and the NEW-NETWORK TR_BITBRAIN_* knobs, and the BitBrainNet arm of
run_prediction_quality.nim.

With id 17 gone there is nothing to disambiguate, so the legacy namespace
becomes the ONLY one: TR_RACK_BITBRAIN always selects id 16 LEADGAIN and
every TR_BITBRAIN_<X> in the frozen 14-suffix alias set always means
TR_LEADGAIN_<X>. The alias layer and its [depr] line stay.

KEPT: the common_libs/bitbrain/ SBC library (learned_surfer imports
bitbrain/sbc), lead_gain at id 16 with env TR_LEADGAIN_* and log tag [lg],
and the c9b6753 crash fix (NumRackGuns widths + test_rack_stat_width).

Tombstone: docs/bitbrain_campaign.md ## RETIRED and one cross-reference line
in docs/gun_campaign.md. Shipped defaults unchanged: clean env -> rack
active 1v1 = PATTERN, movement default strafe.
This commit is contained in:
2026-09-26 19:20:23 +02:00
parent c9b67530db
commit 5e32ec16df
18 changed files with 279 additions and 1732 deletions
+27 -48
View File
@@ -5,8 +5,10 @@
## but its ADE+SBC network was removed when it was rebuilt into what it actually
## is: **it learns a multiplier for Pattern's lead, separately per range band.**
## `LEADGAIN` says that; `BITBRAIN` (a neural network) did not. The rack id 16
## is UNCHANGED (many tests assert the id literals) and the real ADE+SBC gun is
## the separate `guns/bitbrain_net.nim` at rack id 17.
## is UNCHANGED (many tests assert the id literals) and the `BITBRAIN` name is
## the gun's to keep: the ADE+SBC gun that briefly held it (rack id 17,
## `guns/bitbrain_net.nim`) was RETIRED and removed — see
## `docs/bitbrain_campaign.md` §RETIRED.
##
## ── WHY THE FILE WAS REBUILT (Phase 0/1 evidence) ────────────────────────────
## The previous design was an ADDITIVE angular shift: an ADE+SBC network
@@ -66,30 +68,22 @@
## report (`env_report.nim`) and the registration guard tests keep working
## unchanged; they no longer affect the gain learner. The generic
## `common_libs/bitbrain/` library is untouched and still tested by
## `test_bitbrain.nim`, and the new ADE+SBC gun that actually uses it is
## `guns/bitbrain_net.nim` (rack id 17).
## `test_bitbrain.nim` — `movements/learned_surfer.nim` still imports
## `bitbrain/sbc`, so the library is NOT the gun.
##
## ── BACKWARD COMPATIBILITY: the `TR_BITBRAIN_*` legacy aliases ───────────────
## The owner's live `.env` predates the rename and contains `TR_RACK_BITBRAIN`,
## `TR_BITBRAIN_GAINS`, `TR_BITBRAIN_MEM`, `TR_BITBRAIN_LOG`, … Those names are
## the OLD corrector's knobs and MUST keep working unchanged. The
## `TR_BITBRAIN_*` prefix, however, now belongs to the NEW ADE+SBC gun
## (`guns/bitbrain_net.nim`). The two uses are separated by ONE deterministic
## switch, `TR_BITBRAIN_NET` (the new gun's master switch, default 0 = off):
## the OLD corrector's knobs and MUST keep working unchanged.
##
## * `TR_BITBRAIN_NET` UNSET / 0 → LEGACY MODE. Every `TR_BITBRAIN_<X>` name
## listed in `LegacyKnobEnvNames` is a legacy alias for this gun's
## `TR_LEADGAIN_<X>`, and the new ADE+SBC gun is OFF. This is the owner's
## current configuration, so its behaviour is unchanged.
## * `TR_BITBRAIN_NET=1` → NEW-NETWORK MODE. `TR_BITBRAIN_<X>` names
## the NEW gun's knobs (see `bitbrain_net.nim`) and this gun reads ONLY
## `TR_LEADGAIN_<X>`.
##
## The legacy sets are DISJOINT (see `legacyKnobEnvNames` / the new gun's
## `netKnobEnvNames`), so no name is ever claimed by both. `TR_RACK_BITBRAIN` is
## the one genuinely ambiguous name (the rack is keyed by gun name and the new
## gun is now the one called `BITBRAIN`); it is resolved by the SAME switch —
## see `selector.nim`'s `RackLegacyAliases`.
## The `TR_BITBRAIN_*` prefix was briefly shared with the ADE+SBC gun, which
## had a two-mode disambiguator, `TR_BITBRAIN_NET`. That gun was RETIRED and
## removed (it did not learn; the owner watched it live and threw it away), so
## the legacy namespace is now the ONLY namespace and the mapping is
## UNCONDITIONAL: every `TR_BITBRAIN_<X>` in the frozen `LegacyKnobEnvNames`
## set is an alias for `TR_LEADGAIN_<X>`, and `TR_RACK_BITBRAIN` always selects
## this gun (rack id 16). A stale `TR_BITBRAIN_NET=1` left in a `.env` is now an
## unrecognised variable: the boot report warns about it and ignores it.
##
## ── TR_LEADGAIN_GAINS (the candidate set as an env knob) ─────────────────────
## `TR_LEADGAIN_GAINS` is a comma-separated candidate list, e.g.
@@ -121,11 +115,10 @@ const
LG_NADE_ENV* = "TR_LEADGAIN_NADE" ## (legacy ADE count; inert)
LG_RANGE_ENV* = "TR_LEADGAIN_RANGE" ## (legacy class half-range; inert)
LG_LOG_ENV* = "TR_LEADGAIN_LOG" ## 1 = per-change [lg] log
## ── the one switch that disambiguates the legacy `TR_BITBRAIN_*` names ────
## Read by BOTH guns (see `bitbrain_net.nim`). Unset/0 => the `TR_BITBRAIN_*`
## names are LEGACY aliases for this gun; 1 => they belong to the new ADE+SBC
## gun. It is also the new gun's master on/off switch.
LG_NET_SWITCH_ENV* = "TR_BITBRAIN_NET"
## ── the legacy `TR_BITBRAIN_*` namespace ──────────────────────────────────
## This gun OWNS the `TR_BITBRAIN_*` prefix unconditionally (the ADE+SBC gun
## that briefly shared it was retired), so the frozen suffix set below maps
## every legacy name onto this gun's `TR_LEADGAIN_<X>` with no switch.
LG_MIN_OBS_ENV* = "TR_LEADGAIN_MIN_OBS" ## samples before a band is trusted
LG_WARMUP_ENV* = "TR_LEADGAIN_WARMUP" ## (legacy; inert)
LG_ADAPT_ENV* = "TR_LEADGAIN_ADAPT" ## (legacy; inert)
@@ -288,10 +281,9 @@ const
LegacyPrefix* = "TR_BITBRAIN_"
NewPrefix* = "TR_LEADGAIN_"
## The COMPLETE, FROZEN set of the old corrector's knob suffixes. A
## `TR_BITBRAIN_<X>` in this set is a legacy alias for `TR_LEADGAIN_<X>`; any
## other `TR_BITBRAIN_*` name belongs to the new ADE+SBC gun
## (`bitbrain_net.nim`). The two sets are DISJOINT by construction, so the
## mapping is total and deterministic — no name is claimed twice.
## `TR_BITBRAIN_<X>` in this set is a legacy alias for `TR_LEADGAIN_<X>`.
## This gun is the sole owner of the prefix (the ADE+SBC gun was retired), so
## the mapping is total and unconditional — no name is claimed twice.
LegacyKnobEnvNames* = [
"GAINS", "MEM", "MIN_OBS", "DECAY", "DECAY_FRAC", "LOG", "RESET_ON_TARGET",
"N", "NADE", "RANGE", "WARMUP", "ADAPT", "CALIB", "SEED"]
@@ -299,26 +291,16 @@ const
## for the boot report). A deprecation line is only worth printing for these
## plus the inert ones, because a stale inert name is still a stale name.
## The legacy rack knob, from `gun_harness/selector`'s alias table so the
## two can never drift apart. It is the CURRENT name of rack id 17, which is
## why it is not a distinct string.
## two can never drift apart. It is NOT a current rack name any more (it was
## `RackGunNames[RackNetGunId]` while the retired ADE+SBC gun existed).
LegacyRackEnvName* = RackLegacyAlias[0][0]
proc netSwitchOn*(): bool =
## `TR_BITBRAIN_NET` unset/0 => the `TR_BITBRAIN_*` names are LEGACY aliases
## for this gun. 1 => they belong to the new ADE+SBC gun. The same predicate
## is defined in `gun_harness/selector` (`netSwitchOwnsBitbrainName`), which
## cannot import a concrete gun module.
case getEnv(LG_NET_SWITCH_ENV, "").strip().toLowerAscii()
of "1", "true", "yes", "on": true
else: false
var deprecationShown = false
proc lgDeprecationLine*(): string =
## The single clear deprecation line the owner sees. Names every legacy
## `TR_BITBRAIN_*` knob that is actually set in the environment and the new
## name that now owns it. Empty when there is nothing to migrate.
if netSwitchOn(): return ""
var parts: seq[string]
for suffix in LegacyKnobEnvNames:
let old = LegacyPrefix & suffix
@@ -329,17 +311,14 @@ proc lgDeprecationLine*(): string =
if parts.len == 0: return ""
result = "[depr] " & LegacyPrefix & "* is the OLD lead-gain corrector's namespace; " &
"it was renamed to " & NewPrefix & "* (gun LEADGAIN, rack id 16). " &
"Still honoured: " & parts.join("; ") &
". The new ADE+SBC gun owns the " & LegacyPrefix &
"* names once " & LG_NET_SWITCH_ENV & "=1."
"Still honoured: " & parts.join("; ") & "."
proc lgEnv(name: string): string =
## Read a `TR_LEADGAIN_<X>` knob, falling back to the legacy
## `TR_BITBRAIN_<X>` alias while `TR_BITBRAIN_NET` is off. The NEW name always
## wins when both are set, so a migrated config is authoritative.
## `TR_BITBRAIN_<X>` alias. The NEW name always wins when both are set, so a
## migrated config is authoritative.
var v = getEnv(name, "")
if v.len > 0: return v
if netSwitchOn(): return ""
let suffix = if name.startsWith(NewPrefix): name[NewPrefix.len .. ^1] else: ""
if suffix.len == 0: return ""
for s in LegacyKnobEnvNames: