re: close the ISL operand chain -- built-in result is special[0], via a vtable
Answers what the previous commit left open: naming the branches did not give a clear condition, because that needs the operand chain feeding each compare. First, a correction to my own work. isl-bytecode.md -- which OWNS the opcode table -- already named ops 21-24 push.i/push.f/pop.i/pop.f. isl-branches.md, which I wrote last iteration, said op21 and op23 were unread. The stale file was mine. Verified from the thunks rather than accepted: 21 pushes [phase+168] onto the deque at phase+44, 22 pushes [phase+184] onto phase+64, and the 23/24 handlers touch only r3+168 and r3+184. So pop.i lands in special[1]. New: the 147-entry built-in table is a thin DISPATCH LAYER, not implementations. Each stub resolves the local[] argument base and tail-calls a fixed ScriptPhase vtable slot. 112 of 147 dispatch that way; 17 write [phase+164] inline; 0 write +184. Every named predicate is in the vtable group -- unit_state 184, unit_alive 188, hp_pct_test 64, dist_lt 56, is_engaged 252, timer_elapsed 372 -- which is the control that the split separates engine queries from script bookkeeping. The vtable is 0x820A84BC, derived from a known implementation rather than a stride: MARK_LAST_PHASE is documented as [phase+300]=2; the function 0x8226B498 is exactly that stub; it appears as a data word at exactly one address, 0x820A8570; built-in 39 uses slot 180. The check NOT used in the derivation: built-in 40 mark_not_last uses slot 176, and slot 176 holds the [phase+300]=1 stub. Predicted and confirmed. The db's own vptr_writes independently lists 0x820A84BC, written at 0x82261B80. unit_state = slot 184 = 0x8226ADF0, which indexes [phase+324] by local[4] and writes its answer to [phase+164] = special[0] at both exits. The phase-3 poll loop now reads end to end: unit_state(ADT308) -> special[0]; pop.i -> special[1]; cmp.i; beq. isl.py names ops 21-24; the calls artefact regenerates with NO diff. Left open and said so: the other 111 vtable slots, which comparand each site pushes, the 35 non-vtable built-ins, and the vtable's length.
This commit is contained in:
@@ -123,12 +123,16 @@ describe by shape.
|
||||
|
||||
## 🟡 Not settled
|
||||
|
||||
* **`op23`** (`0x82271C30`) is left unnamed. It indexes a container at `r3+44`
|
||||
and stores a word to `[phase+168]`; it is almost certainly how a built-in's
|
||||
return value reaches `special[]`, but "almost certainly" is how this corpus
|
||||
acquired two names it later had to withdraw. Characterised, not named.
|
||||
* ~~**`op23`** (`0x82271C30`) is left unnamed.~~ 🔴 **My error — the corpus
|
||||
already had it.** [`isl-bytecode.md`](isl-bytecode.md), which owns the opcode
|
||||
table, names 21–24 `push.i`/`push.f`/`pop.i`/`pop.f`. `op23` is `pop.i`, into
|
||||
`[phase+168]` = `special[1]`. Verified from the thunks and closed in
|
||||
[isl-builtin-dispatch](isl-builtin-dispatch.md), which also settles where a
|
||||
built-in's result goes: `[phase+164]` = `special[0]`.
|
||||
* **`op21`** (`0x82175C20`) has a different shape from all of these — its thunk
|
||||
passes `phase+168` and `phase+44`, not the pc — and was not read.
|
||||
passes `phase+168` and `phase+44`, not the pc. That is `push.i`: it pushes
|
||||
`special[1]` onto the deque at `phase+44`. The generic deque helper itself is
|
||||
still unread.
|
||||
* **The bitset container at `phase+24`.** `op10` reaches it with `0x822749B0`
|
||||
(by address, `phase+24`) and `op13` with `0x82274CC0` (through a word loaded
|
||||
from `phase+32`). Both land on the same bits, but the exact container layout
|
||||
|
||||
Reference in New Issue
Block a user