Fr0zka f3faa3b5c2 perf: the column memo threw itself away every chunk
Jahni measured what I had only flagged: generation is slower on the op-stack path.
Two compounding causes.

The memo was keyed on InstanceId, which changes on every stack rebuild — every chunk.
GSurfColCache, the cache this path replaced, is keyed on (XY box, StrateKey, Seed,
LayoutVersion) with no ChunkZ, deliberately shared down the whole vertical strate
stack. So a 4-chunk strate recomputed every column four times, including the cliff's
four extra structural samples per column.

And the table held 256 entries where a chunk is CHUNK_SIZE^2 = 1024 columns, so it
thrashed against itself within a single tile before any cross-chunk question arose.

PrepareChunk now derives a shared ColumnKey from (StrateBottomWorldZ, LayoutVersion,
Seed) — the same identity GSurfColCache uses — and the table is 4096 entries
(~150 KB/worker, in line with GSurfColCache's 6 x 59 KB). The memo is thread_local so
it already survived rebuilds; only the key was discarding the contents.

Sharing across chunk Z is sound because heights are XY-pure by type and the biome
field is documented Z-independent — the same justification GSurfColCache rests on.

ColumnKey starts at InstanceId rather than 0: slots initialise to Key = 0, so a zero
key would falsely hit the pristine slot at (0,0). Without PrepareChunk you get
per-instance caching, which is less sharing but still correct.

This may not close the gap entirely and I am not claiming it does. Virtual dispatch
and the hashed lookup vs a direct-indexed box both remain; they are smaller than a 4x
column recompute, but "smaller" is a guess until measured.

UNVERIFIED: not compiled.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-27 16:59:37 +02:00
S
Description
No description provided
6.6 MiB
Languages
C++ 97.6%
C 2.3%
C# 0.1%