From 867a57f96e8598bff4ddb5cc2f7a8183708508aa Mon Sep 17 00:00:00 2001 From: Claude Date: Tue, 25 Aug 2026 20:56:25 +0000 Subject: [PATCH] =?UTF-8?q?board+plan:=20W0=20is=20live=20on=20the=206502?= =?UTF-8?q?=20=E2=80=94=20its=20main=20memory=20is=20not=20SpaceId::Ram?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The arch census over the real SLEIGH specs, run because W0 predicted the 6502 arc would fire first and that arc landed the same day: the 6502 declares five spaces and mints two custom ones. OTHER becomes Custom(0) on both architectures, and the 6502's own main memory RAM becomes Custom(1) because the alias map is seeded with lowercase names and resolved by exact HashMap hit. Every load and store on that architecture touches a space that is not SpaceId::Ram. Also corrects W0's own accounting in two places. Its census counted rows and found zero custom spaces; the arch always had one, since no row in those four binaries referenced OTHER. Both numbers are right and answer different questions. And W0 named two Custom sources where there are three: disasm.rs mints Custom from a wrapping byte-sum of the space name, so the chain loses identity to hash collisions before any ordering enters. The address consequence is stated conditionally on purpose. Whether a lifted 6502 varnode carries Custom(1) or Ram depends on which of two disagreeing translation paths produced it, and that half is read from source rather than observed. The unrun measurement that settles it is named. Verdict unchanged, urgency changed. The defect is upstream in r2sleigh, recorded here because it is the falsifier for a lance-graph verdict. --- .claude/board/EPIPHANIES.md | 109 ++++++++++++++++++ .../r2il-machine-semantic-contract-v1.md | 9 +- 2 files changed, 117 insertions(+), 1 deletion(-) diff --git a/.claude/board/EPIPHANIES.md b/.claude/board/EPIPHANIES.md index 2d6c19cc2..888dfad05 100644 --- a/.claude/board/EPIPHANIES.md +++ b/.claude/board/EPIPHANIES.md @@ -1,3 +1,112 @@ +## 2026-08-25 — E-W0-IS-LIVE-ON-THE-6502-AND-ITS-MAIN-MEMORY-IS-NOT-SpaceId-Ram-1 — the arch census: 6502 mints TWO custom spaces, one of them its own RAM, because the alias map is case-sensitive + +**Status:** FINDING — [MEASURED] (ArchSpec census over the real 6502 and +x86-64 SLEIGH specs, via `build_arch_spec`; instrument written, run, +deleted — no source change landed) + [CODE-READ, NOT RUN] for the +path-divergence half, graded separately below. +**Sharpens** `E-W0-THE-SPACE-ORDINAL-IS-A-RANK-RELATIVE-TO-A-TABLE-THE-CLASSID-NEVER-NAMES-1` +from **latent** to **live**. Does not change its verdict — it removes the +"there is time" half of it. + +### What W0 said, and what changed under it + +W0's census found **0 custom spaces in 94,536 rows across 4 x86 binaries** +and concluded: latent on x86, *"fires first on the 6502/C64 arc"*. That +arc landed the same day — `r2sleigh` PRs #2–#4 registered the 6502 family, +wired the CLI, and fetched the conformance corpus. So the prediction was +testable within hours, and was tested. + +### The census — MEASURED + +`build_arch_spec` over the real SLEIGH data for both architectures, +reporting the `SpaceId` each declared space maps to: + +| | 6502 | x86-64 | +|---|---|---| +| `const` | Const | Const | +| `OTHER` | **CUSTOM(0)** | **CUSTOM(0)** | +| `unique` | Unique | Unique | +| RAM | **`RAM` → CUSTOM(1)** | `ram` → Ram | +| `register` | Register | Register | +| **custom count** | **2** | **1** | + +x86 was never zero-custom at the ARCH level — `OTHER` was always +`Custom(0)`. W0's corpus census counted **rows**, and no row in those four +binaries ever referenced `OTHER`. Both numbers are correct; they answer +different questions, and this entry is the reason to keep them apart. + +### The mechanism — a case-sensitive alias map + +`context.rs:54-58` seeds the alias map with lowercase names only +(`"ram"`, `"register"`, `"unique"`, `"const"`, `"constant"`), and +`add_space_with_endianness` resolves via `space_map.get(name)` — an exact +`HashMap` hit. The 6502 SLEIGH spec names its main memory **`RAM`**, +uppercase. It misses, falls through to `SpaceId::Custom(next_custom_space++)`, +and lands as `Custom(1)`. + +**The 6502's main memory is therefore not `SpaceId::Ram`.** Not a corner +case, not an exotic space — the space every load and store on that +architecture touches. + +### The consequence for the address, stated conditionally + +`CustomSpaceTable::from_arch` interns `{0, 1}` for the 6502, so +`ordinal_of(1) = CUSTOM_ORDINAL_BASE + 1 = 5`. **IF** a varnode reaches +`facet::project` carrying `Custom(1)`, its classid lo-u16 is **5**, while +the same concept on x86 is **0** (`SPACE_RAM`) — one kind of thing, two +readings, and nothing in the 16 bytes says which arch. That is exactly +W0's collision, now on real processor specifications rather than a +constructed pair of tables. + +The "IF" is load-bearing and is the next thing to measure — see below. + +### ⊘ A THIRD `Custom` source, missed by W0's entry + +W0 named two (`context.rs:147`'s counter, `disasm.rs:91`'s raw index). +There is a third, and it is the worst: `disasm.rs:770-775` mints +`Custom(hash)` where `hash = name.bytes().fold(0u32, wrapping_add)` — a +**wrapping byte-sum of the space name**. Any two names with equal byte +sums collide (every anagram, trivially). W0's entry says *"two stages of +order-dependence, zero of identity"*; corrected, the chain is + +``` +space name → byte-sum hash (COLLIDING) → Custom(n) → sorted rank → classid lo-u16 +``` + +— three stages, and the first loses identity before any ordering enters. + +### [CODE-READ, NOT RUN] The two paths disagree about this very space + +`translate_space` (`disasm.rs:757-765`) classifies by `space_type`, not by +name: a `Processor` space whose name does not contain `"register"` becomes +`SpaceId::Ram`. So for the 6502's `RAM` the ArchSpec path yields +`Custom(1)` while the lift-time path yields `Ram` — the same space, two +different `SpaceId`s depending on which code path produced the varnode. + +**This half is read from source, not observed.** Whether a lifted 6502 +memory access actually carries `Custom(1)` or `Ram` decides whether the +address consequence above fires at all, and it is the one measurement this +entry does not have. Naming it as unrun rather than implying it. + +### What this does and does not change + +- **Does not change the W0 verdict.** Fixed spaces 0–3 stay; the custom + axis stays blocked from the `0xC4` mint as carved. The three repair + options remain OGAR's to choose. +- **Does change the urgency.** W0 said *"the census says there is time; the + mechanism says the time is before the mint."* The census now says the + time is shorter than it looked: a second ArchSpec exists, in-tree, today. +- **Is not a lance-graph defect.** The case-sensitive alias map and the two + divergent translation paths are `r2sleigh`'s, upstream of everything this + plan owns. Recorded here because it is the falsifier for a lance-graph + verdict, not because the fix belongs here. + +**Next measurement (unrun, cheap):** lift one 6502 memory access through +the real path and read the `SpaceId` off the varnode. That settles the +conditional, and it is the difference between "the 6502 addresses wrongly" +and "the 6502 addresses correctly by accident, through the path that +disagrees with its own ArchSpec." + ## 2026-08-25 — E-W0-THE-SPACE-ORDINAL-IS-A-RANK-RELATIVE-TO-A-TABLE-THE-CLASSID-NEVER-NAMES-1 — W0 run: zero custom spaces in 94,536 rows, so the defect is LATENT; but the mechanism is worse than the conjecture and blocks the mint's space axis anyway **Status:** FINDING — [MEASURED] (census over the full 4-binary corpus) diff --git a/.claude/plans/r2il-machine-semantic-contract-v1.md b/.claude/plans/r2il-machine-semantic-contract-v1.md index 141679b7e..3f5d66b61 100644 --- a/.claude/plans/r2il-machine-semantic-contract-v1.md +++ b/.claude/plans/r2il-machine-semantic-contract-v1.md @@ -128,7 +128,14 @@ that it does not belong. **CONJECTURE** — the falsifier is in §6. > registration-order counter. Two facets from two arches are byte-identical > while denoting different spaces (demonstrated against the shipped API). > Census: **0 custom spaces in 94,536 rows across all four binaries** — the -> case is LATENT on x86 and fires first on the 6502/C64 arc. Verdict: fixed +> case is LATENT on x86 and fires first on the 6502/C64 arc. +> **⊘ AND IT NOW FIRES (same day):** the arch census over the real SLEIGH +> specs finds the 6502 minting TWO custom spaces — `OTHER` → `Custom(0)` +> and, because the alias map is case-SENSITIVE, its own main memory `RAM` +> → `Custom(1)`. The 6502's RAM is not `SpaceId::Ram`. Latent → live; +> verdict unchanged, urgency changed. See +> `E-W0-IS-LIVE-ON-THE-6502-AND-ITS-MAIN-MEMORY-IS-NOT-SpaceId-Ram-1`. +> Verdict: fixed > spaces 0–3 stay; the custom axis is BLOCKED from the `0xC4` mint as > carved. Full entry: > `E-W0-THE-SPACE-ORDINAL-IS-A-RANK-RELATIVE-TO-A-TABLE-THE-CLASSID-NEVER-NAMES-1`.