acdream/tools/cdb/l2g-observer.cdb
Erik 97e098bf91 docs(L.2g-S2): verbatim inbound-funnel pseudocode + observer cdb trace script
Pseudocode for the S2 port (unpack_movement case 0 / move_to_interpreted_state
/ apply_current_movement / apply_interpreted_movement / DoInterpretedMotion),
anchored on decomp lines + validated against a LIVE cdb trace of a retail
observer (per-UM DIM order confirmed: style -> forward -> sidestep-stop ->
turn-stop; empty UM = wholesale Ready stop).

Also settles the packer question: RawMotionState::Pack (0x0051ed10) is pure
static-default-difference — outbound L.2b port already verbatim; the
empty-vs-explicit walk variance between captures is driver-client state,
handled identically by the wholesale apply.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-02 18:33:23 +02:00

42 lines
2.4 KiB
Text

* L.2g S2-blocker trace — what does a RETAIL OBSERVER do with ACE's
* flags=0 "empty" UpdateMotion while the actor toggles walk/run?
*
* Attach target: the retail OBSERVER client (standing still, watching).
* Driver: the user Shift-toggles + starts/stops the ACTOR from the other
* retail client.
*
* Expected chain per decomp (to confirm or refute):
* CPhysics::SetObjectMovement (gates, stamps) [SOM] + obj id
* MovementManager::unpack_movement (10-way dispatch) [UNPACK]
* CMotionInterp::move_to_interpreted_state (flat copy) [MTIS] + IMS dump
* CMotionInterp::apply_interpreted_movement [AIM]
* CMotionInterp::apply_raw_movement (local-player alt) [ARM]
* CMotionInterp::DoInterpretedMotion per axis [DIM] + motion id
*
* The [MTIS] InterpretedMotionState dump on an empty UM is THE answer:
* if forward_command=0x41000003 (Ready) is flat-applied and [DIM] shows
* Ready, retail really does stop the remote — and the observer's clean
* rendering must come from somewhere else. If the dump or the DIM stream
* shows something else (e.g. WalkForward), we found the mechanism.
*
* Auto-detach: after 600 SetObjectMovement hits via .detach (NOT qd —
* qd is silently ignored in bp actions, see project_retail_debugger.md).
.logopen C:\Users\erikn\source\repos\acdream\.claude\worktrees\vigorous-joliot-f0c3ad\l2g-observer-trace.log
.sympath C:\Users\erikn\source\repos\acdream\refs
.symopt+ 0x40
.reload /f acclient.exe
x acclient!CPhysics::SetObjectMovement
x acclient!MovementManager::unpack_movement
x acclient!CMotionInterp::move_to_interpreted_state
x acclient!CMotionInterp::DoInterpretedMotion
r $t0 = 0
bp acclient!CPhysics::SetObjectMovement "r $t0 = @$t0 + 1; .printf \"\\n[SOM %d] obj=%p movSeq=%x scSeq=%x auto=%x id: \", @$t0, poi(@esp+4), poi(@esp+10)&0xffff, poi(@esp+14)&0xffff, poi(@esp+18); dt acclient!CPhysicsObj poi(@esp+4) id; .if (@$t0 >= 250) { .detach } .else { gc }"
bp acclient!MovementManager::unpack_movement ".printf \"[UNPACK] mm=%p\\n\", @ecx; gc"
bp acclient!CMotionInterp::move_to_interpreted_state ".printf \"[MTIS] minterp=%p ims:\\n\", @ecx; dt acclient!InterpretedMotionState poi(@esp+4); gc"
bp acclient!CMotionInterp::apply_interpreted_movement ".printf \"[AIM] minterp=%p\\n\", @ecx; gc"
bp acclient!CMotionInterp::apply_raw_movement ".printf \"[ARM] minterp=%p\\n\", @ecx; gc"
bp acclient!CMotionInterp::DoInterpretedMotion ".printf \"[DIM] minterp=%p motion=%08x\\n\", @ecx, poi(@esp+4); gc"
g