test: the Maze residue is /fp:fast, not port drift — encode the real bar
The bisect settled it. The difference survives every stage removal down to
"corridors + carve ONLY", which is character-for-character transcribed code, so
it is not in anything the decomposition added.
Cause, read out of the engine rather than assumed (VCToolChain.cs):
case FPSemanticsMode.Default: // Default is imprecise FP semantics.
case FPSemanticsMode.Imprecise: Arguments.Add("/fp:fast"); break;
with UBT's own doc: "the compiler is allowed to transform math expressions in
ways that might result in differently rounded results". Identical source in two
translation units may reassociate differently, worth ~1 ULP. It shows up on
exactly the ~2% of samples inside the SDF blend shell, where Blend - Sdf
catastrophically cancels; outside it Carve is exactly 0 or 1 and both agree.
So MazeEquivalence now grades what it can actually assert:
- hard fail : any isosurface crossing (geometry moves)
- info : differences at ULP scale (the unavoidable floor)
- warn : anything larger, which IS port drift, and runs the bisect
A test that warns on every port would get ignored by the port that matters.
Recorded in OPSTACK-PLAN 2.6, and as AUDIT C9 for the part that outlives this
refactor: ARCHITECTURE 9.1's "every peer regenerates identically" holds only
between bit-identical binaries under /fp:fast. Fine for one build on one
platform; a real desync source for a Linux server plus Windows clients both
regenerating authoritative geometry. The FPSemantics::Precise knob exists but
must not be turned speculatively -- it blocks the vectorisation T2.a was chasing,
on the hot loop, for an unmeasured cost.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
@@ -196,6 +196,20 @@ strategically:** if bit-identity were required, the cheap path would be to wrap
|
||||
as one monolithic op — 8 opaque ops that don't compose, i.e. **the switch with extra steps and zero
|
||||
gain.** Releasing that constraint is what permits *real* decomposition into the primitives in §2.5.
|
||||
|
||||
> **✅ CONFIRMED THE HARD WAY, 2026-07-27 — and it turns out bit-identity was never available anyway.**
|
||||
> The Maze port reproduced `GetMazeDensity` to within 1 ULP on 2.3% of samples, with **zero
|
||||
> isosurface crossings**. A four-stage bisect showed the residue surviving into code that is
|
||||
> character-for-character transcribed, which pointed at the toolchain: the plugin compiles with
|
||||
> **`/fp:fast`** (UnrealBuildTool's Windows default), which explicitly licenses the compiler to
|
||||
> reassociate the same expression differently per translation unit. So **no port of this kind can be
|
||||
> bit-identical, at any level of care.** See `AUDIT-2026-07.md §C9` — which also flags the part that
|
||||
> matters more than this plan does: the multiplayer model's "every peer regenerates identically"
|
||||
> holds only between bit-identical binaries.
|
||||
>
|
||||
> **The operational bar for every remaining archetype port, encoded in
|
||||
> `VoxelForge.OpStack.MazeEquivalence`:** hard-fail on any isosurface crossing (that moves geometry);
|
||||
> tolerate ULP-scale deltas (unavoidable); warn on anything larger (that is real port drift).
|
||||
|
||||
**The bar instead:** for each ported archetype, an authored op stack must reproduce the *character* of the
|
||||
old one — same scale, same navigability, same feel, recognisably the same kind of place. Judged by Jahni
|
||||
on a screenshot at a fixed seed, not by a diff. Expect and accept a one-time re-tune, exactly as the T2.a
|
||||
|
||||
Reference in New Issue
Block a user