KB: full staleness audit + sweep -- 35 verified corrections across 16 topics, 15 new glossary terms
Adversarially-verified audit (18 agents) against the task #46-#56 landings: MP/current-state understatements, superseded punch readings, retired env gates, dead paths, line-cite drift; env-gate hub table completed. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Fable 5
parent
2abfd51350
commit
3c34ae6de6
+21
-15
@@ -3,7 +3,7 @@ id: combat-damage
|
||||
title: "Combat & Damage — targeting, firing, damage zones, death"
|
||||
status: established
|
||||
source_sections: "PROGRESS_LOG.md §10c; docs/HARD_PROBLEMS.md (P5)"
|
||||
related_topics: [subsystems, decomp-reference, reconstruction-gotchas, locomotion, rendering]
|
||||
related_topics: [subsystems, decomp-reference, reconstruction-gotchas, locomotion, rendering, translocation-warp, multiplayer]
|
||||
key_terms: [damage-zone, TakeDamage, viewpoint-entity, master, replicant]
|
||||
open_questions:
|
||||
- "Per-impact aim (cylinder lookup); collision damage application; DeathShutdown + collapse anim"
|
||||
@@ -200,8 +200,10 @@ Built + runtime-verified. Changes:
|
||||
the absorber bank — which stores NOTHING, so the whole unaimed path was inert until 2026-07-08 (the
|
||||
"can't kill the enemy" bug). See [[reconstruction-gotchas]] §2. [T2]
|
||||
- **`Mech::TakeDamageMessageHandler`** override registered (`MESSAGE_ENTRY(Mech, TakeDamage)`, overlays
|
||||
Entity's by ID): on `invalidDamageZone`, `msg->damageZone = table->ResolveHit(msg->damageData.impactPoint)`,
|
||||
clear the flag, then base-route. Aimed hits pass straight through.
|
||||
Entity's by ID): the handler FIRST feeds the raw `Damage` to the Gyroscope hit-bounce (`GyroApplyDamage`,
|
||||
@0x4a0264 hub, task #56) before zone resolution; then on `invalidDamageZone`, `msg->damageZone =
|
||||
table->ResolveHit(msg->damageData.impactPoint)`, clear the flag, then base-route. Aimed hits pass
|
||||
straight through.
|
||||
- **Named accessors (no databinding-trap raw reads):** `Mech::WorldToLocal` (`localToWorld.MultiplyByInverse`),
|
||||
`CylinderReferenceHeight` (`standingTemplateMaxY` = `collisionTemplate->maxY` = the binary `mech+0x2ec[+0xc]`),
|
||||
`TorsoHeading` (via the `BTGetTorsoTwist` bridge in `torso.cpp` → `Torso::CurrentTwist` = torso+0x1d8;
|
||||
@@ -220,7 +222,8 @@ Built + runtime-verified. Changes:
|
||||
invisible 1-shot kills (internal zones are soft; the binary never aims them — they die only via the
|
||||
destruction cascade `RecurseSegmentTable`/`SendSubsystemDamage`). On kill the wreck STAYS TARGETED
|
||||
(`gEnemyMech` is NOT nulled) so beams keep terminating on it — nulling it made every later beam a
|
||||
"free" ray that visibly passed through the wreck; scoring latches off via `gEnemyDestroyed`. [T2]
|
||||
"free" ray that visibly passed through the wreck; scoring latches off via `gEnemyDestroyed` — until
|
||||
the burial transition drops the lock (`gEnemyMech = 0` when the buried wreck goes INERT, mech4.cpp). [T2]
|
||||
`Mech__DamageZone::TakeDamage` → engine armor model (`damageLevel
|
||||
+= damageAmount*damageScale[type]`) → 1.0 = zone destroyed → death. The Mech ctor populates the
|
||||
inherited `damageZones[]` from the DamageZoneStream (type 0x14) resource. `class Damage{ damageType
|
||||
@@ -286,8 +289,9 @@ Full decomp map of the death path. Two tiers:
|
||||
(mech+0x120[mech+0x11c]); as a subsystem's damage crosses a descriptor-table threshold (`FUN_0042a5f4`
|
||||
detects the crossing, `FUN_0042a664` looks up the state) it applies the `GraphicState` ("Destroyed" = enum 1,
|
||||
parsed @part_003.c:9099) to the subsystem graphic (`sub+0xd4`) AND dispatches an effect-creation message
|
||||
(`FUN_0043663c`→`FUN_004364e4` to the effect mgr `app+0x38`). **Fully exported but a no-op STUB** in the
|
||||
recon (mech.cpp:221). Gamedata `DeathSplashDamage`/`Radius`/`Effect` load into a descriptor @ +0x74/78/7c
|
||||
(`FUN_0043663c`→`FUN_004364e4` to the effect mgr `app+0x38`). ✅ Fully exported; was a no-op stub
|
||||
(mech.cpp:221) — now fully RECONSTRUCTED (mechdmg.cpp — ctor @0042a984 / Tick @0042aa2c; wired in the
|
||||
Mech ctor, mech.cpp:1469) [T2]. Gamedata `DeathSplashDamage`/`Radius`/`Effect` load into a descriptor @ +0x74/78/7c
|
||||
(`FUN_004a2da8`). Destroyed-skin variant set (`destroyed`, `destroyeds`…`destroyedd`) @part_003.c:5720.
|
||||
**NOT EXPORTED (master-perf gap 0x4a9770-0x4ab188 + the un-exported TakeDamage) [T4]:**
|
||||
- The `movementMode` WRITER (sets 5-8 then 2/9 on death) + the fall-direction (5/6/7/8) selection.
|
||||
@@ -302,19 +306,21 @@ the RP analog and wired into the active path (mech4.cpp `PerformAndWatch`).
|
||||
### ✅ Death-STATE core DONE (2026-07-08) [T2]
|
||||
`Mech::UpdateDeathState()` + `IsMechDestroyed()` (mech4.cpp) reconstruct the un-exported death branch from
|
||||
its exported consumers + the RP analog, called for EVERY mech early in `PerformAndWatch`: on `graphicAlarm
|
||||
>= 9` it (1) sets `movementMode = 5` → the collapse clip's latch in `AdvanceBodyAnimation` (fall direction
|
||||
5-8 un-exported → 5 [T3]); (2) loops the roster calling `Subsystem::DeathShutdown(1)` (RP `VTV::DeathShutdown`
|
||||
analog; base is a no-op virtual, a SHUTDOWN not teardown → safe, wreck STAYS); (3) next frame settles to
|
||||
`movementMode = 9` → `IsDisabled` → locomotion frozen. The drive's lone `movementMode = 1` write (mech4.cpp
|
||||
>= 9` it (1) settles the death mode STRAIGHT to `movementMode = 9` (mech4.cpp:1183) — there is NO
|
||||
`movementMode = 5` collapse write (the only other writes are the drive's `= 1`, mech4.cpp:1044/1986); the
|
||||
fall latch 5-8 is never fired (task #32: no collapse anim exists in BT 4.11, see the VESTIGE proof above)
|
||||
[T1]; (2) loops the roster calling `Subsystem::DeathShutdown(1)` (RP `VTV::DeathShutdown`
|
||||
analog; base is a no-op virtual, a SHUTDOWN not teardown → safe, wreck STAYS); (3) `movementMode` 9 →
|
||||
`IsDisabled` → locomotion frozen. The drive's lone `movementMode = 1` write (mech4.cpp
|
||||
~1309) is guarded on `!IsMechDestroyed` so the death state isn't clobbered. **Runtime-verified** (forced kill):
|
||||
`[death] … collapse + subsystem shutdown` → `[death] … settled -> disabled (IsDisabled=1, frozen wreck)`,
|
||||
mech frozen in place (pos unchanged), subsystem tick + renderer keep running, **no crash, wreck stays**.
|
||||
Env gate `BT_DEATH_LOG=1`.
|
||||
**Deferred (honest):** (a) the visible **collapse ANIMATION** may not latch through the active path — the
|
||||
gait SM showed `state=0` post-death (the clip trigger via `AdvanceBodyAnimation` needs the death `movementMode`
|
||||
to reach its latch; and spawned NON-player mechs don't advance their body anim at all). (b) **`MechDeathHandler`**
|
||||
(the exported per-subsystem destroyed-skin + explosion engine, `FUN_0042a984`/`FUN_0042aa2c`) is still the
|
||||
no-op stub → no death explosions/skin-swaps yet. (c) the whole-mech **DeathSplash** radius damage (un-exported).
|
||||
**Deferred (honest):** (a) ✅ RESOLVED (task #32) — there IS no collapse animation to latch: the fall
|
||||
latch is a VESTIGE (see the proof above); the authentic death visual is the wreck-hulk swap, and the death
|
||||
mode settles straight to 9. (b) ✅ RESOLVED — **`MechDeathHandler`** is fully RECONSTRUCTED (mechdmg.cpp —
|
||||
ctor @0042a984 / Tick @0042aa2c; wired in the Mech ctor, mech.cpp:1469) [T2]; destroyed-skin swaps + zone
|
||||
explosions verified live (see STEP 6 above). (c) the whole-mech **DeathSplash** radius damage (un-exported).
|
||||
|
||||
### ⚠ Death-latch correction (2026-07-09, task #52) [T1→T2]
|
||||
`IsMechDestroyed()` originally tested **`graphicAlarm >= 9` alone** — a bring-up shortcut that made a
|
||||
|
||||
Reference in New Issue
Block a user