feat(physics): C4 route 4b-2 — remote far snap through the canonical placement

Flips the SetPositionSimple classification (contact, PlayerDistance >= 96 m) for
remotes onto 4b-1's drive controller and deletes both legacy far blocks, both
duplicated 96f/4f constant pairs, and both `?? Vector3.Zero` fabrications. The
4 m constant now exists exactly once. Teleport and cell-less stay legacy for
4b-3.

Retail: MoveOrTeleport @0x00516330's far branch runs StopInterpolating
@0x005163CB before SetPositionSimple @0x005163D9 and returns 1 @0x005163E8
regardless — the SetPositionError is discarded — so HandleReceivedPosition arms
ConstrainTo @0x00454272 post-move on commit AND on failure. The x87 parity
decode at @0x00516393-@0x0051639E puts exactly 96.0 on the far branch.
SetPositionSimple @0x005162B0 builds flags 0x1012 at @0x005162C4.

Non-commit outcomes still advance the body, because retail's SetPositionInternal
@0x00515BD0 commits the destination via store_position @0x00515CE2 when no cell
resolves. The partition is by STAGE, not heuristic, enforced by an exhaustive
switch: Refused/Contention/NotApplicable/RejectedPreparation store (the placement
never executed); Committed/Deferred/RejectedByPlacement do not (the engine ran
and refused, matching retail's non-storing returns @0x00515CB2 and @0x00515CD5).
Without this a refused far snap froze the remote with an emptied queue.

Also fixes a shipped defect this route made live: ParkDeferred's quiescence parks
withdrew the entity (InWorld=false, clock suspended, residency removed) and were
never restorable, while Forget(restoreCancelledPark: true) runs for every
accepted Position on every entity. The restorable decision now lives inside
ParkDeferred AFTER SnapToCell, reading body.CellPosition.ObjCellId — the value
RestoreParkWithdrawal actually restores at — against every live quiescence
rather than one minimum-OperationId token. The three pre-snap fields are hoisted
into locals because SnapToCell ends with InWorld = true. ParkCollisionResidents
passes restorableOnCancel: false explicitly; the plain unplaceable park is
provably unchanged. RestoreParkWithdrawal re-tests the prefix at restore time so
a retained route-2 park cannot re-admit into a prefix that began quiescing
during the park.

CanAttemptDestination is retained as an OPTIMISATION only, with the two Core
predicates it cannot reproduce written down at the pre-flight, plus the two
properties that depend on it staying there.

Four fix rounds and eight Opus reviews. The slice was fully green at 10,990,
10,997 and 11,004 while containing real defects — a frozen remote pinned as
correct by its own test, a fallback that over-wrote on the exact retail paths
that decline to store, and a park guard incomplete on two independent axes.

Register: AP-137 (leftover classifications take AP-87's catch-up; states the
cell-less enqueue-vs-place delta deferred to 4b-3, that RejectedData is applied
anyway, and the headless divergence), AP-138 (the refusable far placement),
AP-136 narrowed to match the relocation. #309's acceptance steps rewritten —
step 5 previously asserted a recovery the code does not perform — and gated on a
new ACDREAM_PROBE_PARK=1 signal so the check cannot pass while broken.

Suite 11,009 passed / 4 skipped / 0 failed against a measured 10,968 baseline.
The 10,973 figure recorded earlier was wrong and is corrected here.

Connected gate outstanding: the two-client far-snap walk and #309.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Erik 2026-08-04 07:55:56 +02:00
parent 1b631f127d
commit 7f1c1f5aa6
24 changed files with 5234 additions and 375 deletions

View file

@ -84,9 +84,28 @@ route 4b-1 contract's "no connected gate" line does not apply to the park fix.
core behind EVERY production placement, and the merge-time
`restoreCancelledPark: true` is on the accepted-Position path every remote and
the local player traverse. So shipped behaviour changes for any entity whose
placement parks.
placement parks — including the local player, whose route-2 ForcePosition
corrections now roll a cancelled quiescence park back instead of leaving the
character withdrawn for the rest of the session.
Proposed connected check (two clients, local ACE). Scope widened 2026-08-04 at
C4 route 4b-2 round 3: the slice made `SubmitPreparedPlacementCore`'s two
collision-prefix QUIESCENCE parks restorable as well, which the original steps
(the plain unplaceable-destination park only) never exercised, and made the
LOCAL PLAYER traverse the same restore rather than only remotes.
**Run the whole gate with `ACDREAM_PROBE_PARK=1`** (added 2026-08-04, round 4).
Steps 4 and 5 both need a ForcePosition to land INSIDE a transient
collision-prefix quiescence window, which the tester cannot synchronise with a
teleport or portal arrival — so without a signal a clean teleport and a
correctly-parked one look identical and those steps pass while broken. The flag
emits one `[park]` line per park (guid, cause, the caller's pre-snap
`resultCell`, the POST-snap `restoreCell` the rollback would use, `eligible` =
the caller's half, `captured` = the final decision) and one `[park-restore]`
line per rollback (`residency` = whether canonical residency was re-taken).
Nothing is emitted for an ordinary committing placement, so an empty log means
the window was never entered — retry the step; do not record a pass.
Proposed connected check (two clients, local ACE):
1. Walk the observed character to a landblock boundary so a remote sits in a
landblock the observer has not streamed, forcing a `DeferredCell` park.
2. Confirm the remote no longer vanishes permanently — the pre-fix symptom was
@ -94,9 +113,45 @@ Proposed connected check (two clients, local ACE):
3. Confirm it appears at the SERVER-authoritative destination pose, not at a
stale pre-park pose, and that it becomes collidable once the landblock
publishes.
4. Confirm the local player's own ForcePosition corrections (route 2) still
land unchanged — that path shares the same cancel.
Steps 1-3 are the user-visible acceptance for AP-136's residual.
4. **Quiescing swept NEIGHBOUR (new).** Stand/run within about a metre of a
landblock seam while the neighbouring landblock across that seam is being
retired or republished by streaming (recentre by travelling, then provoke a
server ForcePosition — a `/teleport`-class correction or a portal arrival —
at the seam). The sweep footprint reaches the quiescing neighbour, so the
placement parks even though neither the source nor the destination is
quiescing. Confirm the LOCAL PLAYER is not left frozen/invisible after the
next server Position: it must stay in the world, keep simulating, and stay
collidable. **Performed only when the log shows BOTH** `[park] …
cause=quiescence:0x<neighbour-prefix> … eligible=True captured=True` **and a
later** `[park-restore] … residency=True` for the same guid. This is the
shape round 3 measured as reachable; the "quiescing source landblock" shape
is NOT reachable through either accepted-Position caller on a first submit,
because both commit the accepted wire cell to `record.FullCellId` before
submitting.
5. **Quiescing DESTINATION (new).** Provoke a ForcePosition into a landblock
that is mid-retirement. The park is deliberately NOT restored here (AP-136's
reason applies exactly): the character is left withdrawn — out of world,
object clock suspended, not a spatial root.
**Corrected 2026-08-04 (round 4).** The earlier text asked the tester to
confirm the player "recovers on the next server Position rather than staying
withdrawn indefinitely". It does not recover on that packet, and
`QuiescingDestinationPrefix_ForcePositionParkIsNotRestored` pins the
opposite: route 2 dispatches only for `ForcePosition`, so the ordinary
`Apply` that follows merges behind the drive and cancels the park WITHOUT
restoring it. Recovery needs a later packet that actually runs a placement
and commits — another accepted ForcePosition (correction, teleport, or
portal arrival) once that landblock's quiescence has released. Confirm
exactly that, and confirm streaming's retirement of that landblock still
COMPLETES rather than stalling; the retirement is the thing the
non-restorable park exists to protect. **Performed only when the log shows**
`[park] … cause=quiescence:0x<destination-prefix> … eligible=True
captured=False` (eligible-but-declined is the decision under test) **and no**
`[park-restore]` **line for that guid until the recovering ForcePosition.**
6. Confirm the local player's own ordinary ForcePosition corrections (route 2)
still land unchanged — that path shares the same cancel — including the
case where the correction lands in a landblock that is NOT quiescing, which
must be indistinguishable from pre-slice behaviour.
Steps 1-5 are the user-visible acceptance for AP-136's residual.
## #310 — Retained preparation retry stalls landblock retirement with no bound