fix(chat): Campaign CH user-gate round 2 -- portal notice rerouted to SpewBox, verbatim /help extraction, jump-in-air evidence
Item 2: retail's portal-space "In Portal Space..." notice is the SpewBox (ECM_UI::SendNotice_DisplayStringInfo(0x1A,...) -> AddTextToScroll(str, 0x1A, 1, 0), hardcoded to the SpewBox per the decomp), not a dedicated centered overlay. PortalWaitNoticeController and its lease are deleted; PortalTunnelPresentation's per-rotation-segment cadence now writes straight into RuntimeCommunicationState.AddText(ClientLocal) -- the SpewBox's own dedupe-at-index-0 handles the repetition exactly as retail's does. Register row AP-184 records the surface fix and the AP-178 scope extension. Items 4+5: /help text was partially fabricated -- the user caught the "/help death" meta-message. Generalized tools/pdb-extract/sweep_weenie_strings.py to decode narrow PStringBase<char> literals (the ClientCommunicationSystem::Help* family's shape) alongside its original UTF-16LE support, then swept every HelpXxxGroup function's exact byte extent against the PDB-paired acclient.exe. 4 of 7 group topics (death/status/text/allegiances) are now complete verbatim listings; the other 3 (channels/chatting/commands) keep an honest UNVERIFIED note citing HelpStupidChannelHack @0x0056f290 (a genuinely undecodable BN-mislabeled-fragment mechanism) instead of the old fabricated sentinel. 7 of ~35 channel one-liners are also now verbatim. ISSUES.md #364 tracks the remainder; RetailCommandHelpTableTests.cs pins every result byte-exact. Item 1: jump-in-air refusal still silent live is NOT reproduced and NOT speculatively fixed. Exhaustive static re-audit found the mechanism correct by construction (single-writer OnWalkable, exactly-once-per-frame Update()/Capture(), no interfering edge-history resets). A live headless repro (new jump-probe bot policy, real ACE connect) was blocked -- probeaccount2 has no character, and the graphical client already owned testaccount this session so the task's own fallback rule forbade using it. Two temporary probes are left behind ACDREAM_PROBE_JUMP=1 (blocked entirely in Headless by the existing multi-session static-state guard -- graphical-only for the next round). Item 3 confirmed fixed, no regression. Item 6 (resize: no diagonal cursors, cannot grow Y from bottom-right) folded into CH6a's existing scope. Full Release suite: 12,267 passed / 4 skipped / 0 failed (up from 12,221/4/0). Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
parent
a485425743
commit
c1f1582576
14 changed files with 788 additions and 254 deletions
|
|
@ -121,6 +121,38 @@ than a REJECT-review fix batch; CH5-or-later.
|
|||
**Campaign:** `docs/plans/2026-08-09-chat-parity-campaign.md` (Campaign CH,
|
||||
CH4 REJECT-review).
|
||||
|
||||
## #364 — Three `/help` group topics still partial: HelpStupidChannelHack unresolved
|
||||
|
||||
**Status:** OPEN — filed 2026-08-09, Campaign CH user-gate round 2, item 3.
|
||||
The user caught `/help death` printing an acdream meta-message instead of
|
||||
retail's real listing; all 7 `ClientCommunicationSystem::HelpXxxGroup`
|
||||
nodes were re-extracted verbatim from the PDB-paired binary via a
|
||||
generalized `tools/pdb-extract/sweep_weenie_strings.py --ascii-only`.
|
||||
4 of 7 (death/status/text/allegiances) are now COMPLETE verbatim listings
|
||||
(`RetailCommandHelpTable.DeathGroupDetail` etc.). 3 remain PARTIAL
|
||||
(`ChannelsGroupDetail`, `ChattingGroupDetail`, `CommandsGroupDetail`):
|
||||
their detail text is built (in full or in part) by
|
||||
`ClientCommunicationSystem::HelpStupidChannelHack @0x0056f290`, which
|
||||
constructs its output from three string fragments Binary Ninja
|
||||
mis-attributes to unrelated vtable slots (the classic BN pooled/
|
||||
mislabeled-data artifact — `&ClientCommunicationSystem::\`vftable'.
|
||||
RecvNotice_StartBarberNotice` etc. are NOT real vtable dispatch)
|
||||
concatenated around a live `ChannelSystem::GetChannelName` call —
|
||||
genuinely not decodable from a static string sweep. Each partial group
|
||||
keeps its own summary line (fully verbatim) and an explicit UNVERIFIED
|
||||
note citing the address; `chatting` additionally resolves 7 of its 8
|
||||
detail entries (only the 5 HelpStupidChannelHack-delegated channel-alias
|
||||
lines are missing). The same mechanism also blocks 5 of ~35 channel
|
||||
one-liners in `ByVerb` (fellowship/monarch/patron/vassals/covassal
|
||||
family), which stay acdream-authored summaries. Resolving
|
||||
HelpStupidChannelHack requires reading the three mislabeled string
|
||||
fragments directly out of `.rdata` by address (not by BN symbol name) and
|
||||
confirming the channel-name substring logic — a focused follow-up, not
|
||||
guessed.
|
||||
|
||||
**Campaign:** `docs/plans/2026-08-09-chat-parity-campaign.md` (Campaign CH,
|
||||
user gate round 2).
|
||||
|
||||
## Note — six invented chat verbs removed for registry parity (2026-08-09)
|
||||
|
||||
Campaign CH slice CH4 deleted `/gen`, `/cv`, `/lookingforgroup`, `/tr`,
|
||||
|
|
|
|||
File diff suppressed because one or more lines are too long
|
|
@ -18,11 +18,21 @@ rows TS-68/TS-69/TS-70), and 9 are retail's own null-handler help-only
|
|||
nodes. CH5 (this closeout sweep) is COMPLETE — plan/register/ISSUES/
|
||||
CLAUDE.md/roadmap ledger flip plus the chat memory digest. **User gate
|
||||
round 1 ran 2026-08-09 and found ten live defects; see "User gate —
|
||||
round 1" below.** Items A–G are fixed in this round's commit; the three
|
||||
round 1" below.** Items A–G are fixed in round 1's commit; the three
|
||||
remaining findings (extra chat windows on 1/2/3/4, resize only working in
|
||||
one corner, transparency/artifacts) are out of this round's scope and
|
||||
filed as a new slice, CH6. Status stays CODE-COMPLETE pending the next
|
||||
user gate round.
|
||||
one corner, transparency/artifacts) are out of round 1's scope and filed
|
||||
as a new slice, CH6. **User gate round 2 ran 2026-08-09 and found six
|
||||
more findings; see "User gate — round 2" below.** Items 2 ("In Portal
|
||||
Space…" on the wrong surface) and 4+5 (`/help` text fabricated/misaligned)
|
||||
are fixed in this round's commit; item 3 is confirmed-fixed with no
|
||||
regression; item 6 is folded into CH6a's existing scope. Item 1
|
||||
(jump-in-air still silent live) is NOT reproduced and NOT speculatively
|
||||
fixed — round 1's press-edge logic is provably correct by construction
|
||||
from source, a live headless repro was attempted and blocked (no
|
||||
character on the probe account), and two temporary graphical-only probes
|
||||
are left behind for the next round. Status stays CODE-COMPLETE pending
|
||||
the next user gate round (still needed for item 1, CH6, and a final
|
||||
in-client visual pass on everything fixed so far).
|
||||
|
||||
**Why now:** first track of the alpha-release program (chat is the most
|
||||
visible daily surface for the friend-alpha). User-directed 2026-08-09.
|
||||
|
|
@ -117,7 +127,14 @@ implementer per slice against a pinned contract (per
|
|||
teach `LayoutImporter` element type 9 (`UIElement_Resizebar`, 8
|
||||
authored grips: 4 edges + 4 corners via bools 0x2A–0x2D); fix the
|
||||
resize mask that excludes Top. Expected to also clear the round-1
|
||||
artifact report.
|
||||
artifact report. **User gate round 2 (2026-08-09) added two more
|
||||
symptoms to fold into this same slice:** resize has no diagonal
|
||||
(corner) cursor feedback — only edge cursors show, the 4 corner grips
|
||||
from the 8-grip authored set above have no matching cursor affordance
|
||||
yet; and the window cannot grow in the Y axis when dragging from the
|
||||
bottom-right corner (a corner-grip axis-composition bug, likely the
|
||||
same resize-mask gap already scoped for the Top edge above, now
|
||||
confirmed to also affect corner grips specifically).
|
||||
- **CH6b — floating windows 1–4.** Mount `0x2100005B` ×4 as
|
||||
always-resident children per `gmGamePlayUI::SetupChildren
|
||||
@0x004E9EC0` (ids 0x10000505/0x1000050E/0x1000050F/0x10000510);
|
||||
|
|
@ -158,6 +175,7 @@ implementer per slice against a pinned contract (per
|
|||
| CH5 closeout | (this commit) | — (docs/memory only, no build) | — | pending (connected gate — see test script) |
|
||||
| User gate round 1 | (this commit) | 12,221 passed / 4 skipped / 0 failed (baseline; items A–G fixed this commit) | — | items A–G user-gate round 1 fixed; ten findings total, see "User gate — round 1" below |
|
||||
| CH6 chat-window shell parity | not started | — | — | filed 2026-08-09 at user gate round 1; research first |
|
||||
| User gate round 2 | (this commit) | 12,267 passed / 4 skipped / 0 failed | — | items 2/4/5 fixed this commit, item 3 confirmed-fixed, item 6 folded into CH6a's spec, item 1 NOT reproduced (see "User gate — round 2" below) |
|
||||
|
||||
### CH4 closeout (2026-08-09)
|
||||
|
||||
|
|
@ -512,3 +530,26 @@ Release suite green (see the commit message for the exact count). Items
|
|||
H/I/J need the next visual round once CH6 lands; A–G still want a final
|
||||
in-client eyes-on pass to confirm the fix reads correctly on screen (build
|
||||
+ test green is necessary, not sufficient, for a presentation change).
|
||||
|
||||
## User gate — round 2 (2026-08-09)
|
||||
|
||||
The user tested round 1's fixes live and reported six more findings.
|
||||
|
||||
| # | User finding (condensed) | Disposition |
|
||||
|---|---|---|
|
||||
| 1 | Jumping while already airborne is STILL silent live — round 1's press-edge branch (`PlayerMovementController._prevJumpHeld`) has a passing unit test but never visibly fires in the running client. | **NOT REPRODUCED; NO SPECULATIVE FIX SHIPPED.** Exhaustive static re-audit of the whole live path (branch logic, `_body.OnWalkable`'s single writer — the quantum-loop resolve, driven only by real physics results, never anything else — the exact-once-per-frame `Update()`/`Capture()` call site, `TakeControlFromServer`'s edge-history reset scope, mouse-look's extra `Capture()` calls) found no bug: the mechanism is provably correct BY CONSTRUCTION from source. Attempted a live headless repro (new `jump-probe` bot policy exercising the SAME typed `commands.Movement.SetIntent` surface, real ACE connect at 127.0.0.1:9000) — blocked: `probeaccount2` connects but has NO CHARACTER ("no available characters on account"), and per the task's own constraint the fallback to `testaccount` is refused because the graphical client (PID confirmed running this session) owns that account. Left TWO temporary probes behind a `PhysicsDiagnostics`-family flag (`ACDREAM_PROBE_JUMP=1`, blocked entirely in Headless by the existing multi-session static-state guard, so this is a GRAPHICAL-client-only diagnostic for the next round): `[jump]` in `ReportJumpRefusal` (prints unconditionally, even when `OnInterfaceText` is null, to separate "branch never evaluated true" from "callback dropped it"), and `[jump-tick]` (per-tick trace bracketing every frame where Jump is/was held). Next round: launch with `ACDREAM_PROBE_JUMP=1`, reproduce, and read the console trace — it will show exactly which of the three jump branches fires and what `OnWalkable`/`_prevJumpHeld` were at that instant. |
|
||||
| 2 | Retail shows "In Portal Space…" at the TOP of the screen, SMALL font, tell-yellow (the SpewBox) — acdream renders a big centered white/yellow overlay instead. | **FIXED this SHA.** Verified in the decomp: `gmSmartBoxUI::UseTime`'s notice emits via `ECM_UI::SendNotice_DisplayStringInfo(0x1A, ...)`, which forwards to `AddTextToScroll(str, 0x1A, 1, 0)` — type `0x1A` is HARDCODED to the SpewBox (`docs/research/2026-08-09-chat-retail-interface-text.md` §1.1/§4.2), the same surface every other `ClientLocal` refusal (jump-in-air, etc.) already uses. `PortalWaitNoticeController` (the dedicated centered-overlay presentation) and its lease are DELETED outright; `PortalTunnelPresentation`'s round-1 per-rotation-segment emission cadence is unchanged, now writing straight into `RuntimeCommunicationState.AddText(text, RetailLogTextType.ClientLocal)` — the SpewBox's own dedupe-at-index-0 (`SpewBoxState.Tick`) collapses the per-segment repetition exactly as retail's `gmSpewBoxUI::Update` does. No conflict with the decomp — the fix and the user's report agree exactly. |
|
||||
| 3 | (Round 1 item B, `[System] ` prefix) | **CONFIRMED FIXED** — no regression, no further action. |
|
||||
| 4+5 | `/help` output differs from retail; `/help death` prints an acdream META-MESSAGE ("This is a retail help-topic group; acdream has not yet extracted its exact retail listing text…"); spacing/alignment is off. | **FIXED this SHA via verbatim extraction, not authorship.** `tools/pdb-extract/sweep_weenie_strings.py` generalized to decode narrow `PStringBase<char>` literals (the Help* family's shape) alongside its original UTF-16LE support, then swept every `ClientCommunicationSystem::HelpXxxGroup` function's exact byte extent (read from the pseudo-C's own function-header addresses) against the PDB-paired `C:\Users\erikn\Downloads\acclient.exe` (verified MATCH). 4 of 7 groups (death/status/text/allegiances) are now COMPLETE verbatim listings — `/help death` now prints retail's real 8-line text, byte-exact including the retail-authentic trailing space on the `@day` line. The other 3 (channels/chatting/commands) delegate part or all of their detail text to `ClientCommunicationSystem::HelpStupidChannelHack @0x0056f290`, which builds its output from BN-mislabeled data fragments around a live channel-name lookup — genuinely not decodable with confidence; each keeps its own verbatim summary line plus an explicit UNVERIFIED note citing the address, never a fabricated meta-message. 7 of the ~35 channel one-liners are also now verbatim (a/guild/gu, general/cg, trade/ct, lfg/clfg, roleplay/crp, society/soc, olthoi/o), each including retail's own "Also: @alias" text — this is also the alignment/spacing fix, since the fabricated summaries never matched retail's exact wording. Register row AP-184 filed; ISSUES.md #364 tracks the remaining 3-group gap. `RetailCommandHelpTableTests.cs` (new) pins every complete listing and the partial/UNVERIFIED shape byte-exact. |
|
||||
| 6 | Resize is still buggy: missing diagonal (corner) cursor feedback, and the window cannot grow in the Y axis when dragging from the bottom-right corner. | **FOLDED into CH6a's spec** (not fixed this SHA — CH6a itself has not started; see the slice list above, now carrying these two symptoms alongside the pre-existing resize-mask/LayoutDesc-import scope). |
|
||||
|
||||
Evidence for items 2, 4, and 5: this commit's diff + `tests/AcDream.UI.Abstractions.Tests/Panels/Chat/RetailCommandHelpTableTests.cs` (new) + the deletion of
|
||||
`tests/AcDream.App.Tests/UI/PortalWaitNoticeControllerTests.cs` (its subject
|
||||
class no longer exists) + `PortalTunnelAssetTests.cs` (unchanged; verified by
|
||||
inspection — its `CreateRequired` call never passed the removed
|
||||
`displayNoticeLifetime` parameter, so it needed no update). Item 1's evidence
|
||||
is negative: no code changed in the jump branch logic itself, only
|
||||
diagnostics; the two temporary probes and the `jump-probe` headless bot
|
||||
policy are the round's deliverable for item 1, pending either a successful
|
||||
next-round repro or a character created on `probeaccount2`. Full Release
|
||||
suite green (see the commit message for the exact count).
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue