passages: exact density-aware outer bound skips passage work beyond its reach (L81, v214)

The carve is max(source, -roughSDF/Q), so its reach grows with -source; the outer test uses
-d*Q + 0.24 m (wall relief 0.21 + margin) beyond the route radius, disabled in mouth-support
and column-overlap tiles. Skips 16% of passage iterations on the highest-activity tiles and
all of them on ordinary tiles. 84 candidate/full pairs identical in every hash; 0 changed samples.
Evaluator 214 for cache invalidation only. Cold LOD0-2 (L80 protocol): SW 1.30->1.25,
FI 3.59->2.93, TN 3.18->3.51 (noise?), VS 1.33->1.22 s. Fast tier PASS.

Note: the export's legacy 26-point root route owner_world.passages[0] fails a full-view
pre-audit (65 solid samples, unchanged since L70); the canonical 211-point route used by the
plan passes. Stale data to clean up.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016dhxM43dnWvUu2B5Ph1iG1
This commit is contained in:
Fr0zkaandClaude Opus 5.5 committed 2026-10-27 22:58:34 +01:00
1 parent b06397df9c
commit 9cb5e53b17
8 files changed
+615 -2

No files matched your search

@@ -140,6 +140,9 @@ namespace VoxelForgeCore
std::uint64_t passageTileMouthSegmentCandidates = 0;
std::uint64_t passageComposerQueries = 0;
std::uint64_t passageIterations = 0;
std::uint64_t passageTileBoundChecks = 0;
std::uint64_t passageTileBoundRejects = 0;
std::uint64_t passageTileBoundSkippedIterations = 0;
std::uint64_t passageUpperMouthFilterChecks = 0;
std::uint64_t passageColumnCandidates = 0;
std::uint64_t passageColumnDistanceCalls = 0;
@@ -456,7 +459,7 @@ namespace VoxelForgeCore
// Version 210 keeps bulk native-cave sampling on the scalar field path at strata edges.
// Version 211 makes coordinate biasing in the shared cell hash unsigned, removing signed-overflow UB.
// Version 212 balances generated entry routes against existing walk lanes and preserves their shared treads.
inline constexpr std::uint32_t WorldAssemblyEvaluatorVersion = 213;
inline constexpr std::uint32_t WorldAssemblyEvaluatorVersion = 214;
enum class FieldChannel : std::uint32_t
{
+75
View File
@@ -1045,6 +1045,81 @@ public:
&&!passageTileQueries->hasColumnZOverlap()
&&!passageTileQueries->hasAnyMouthSupport()
&&!passageTileQueries->mayContainUpperMouthSupport())return density;
// On solid samples, the SDF carve can still move the scalar density far outside the
// physical tunnel. The per-passage test below already accounts for this tail using the
// incoming density plus the bounded relief allowance. Apply that same proof before
// entering the passage loop for points outside the scalar influence reach. Columns and
// both mouth-support paths keep their own tile envelopes and therefore disable this
// cut. Optional extra padding is only for research sweeps; zero is the exact bound.
// Invalid values fail open.
static const double PassageBoundPaddingVoxels=[]
{
constexpr double DefaultPaddingVoxels=0.0;
const char* Value=std::getenv(
"VOXELFORGE_L81_PASSAGE_BOUND_PADDING_VOXELS");
if(!Value||!*Value)return DefaultPaddingVoxels;
char* End=nullptr;
const double Parsed=std::strtod(Value,&End);
if(End==Value||*End!='\0'||!std::isfinite(Parsed)||Parsed<0.0)
return std::numeric_limits<double>::infinity();
return Parsed;
}();
if(passageTileScopeMatches&&density<0.0f
&&std::isfinite(PassageBoundPaddingVoxels)
&&!passageTileQueries->hasColumnZOverlap()
&&!passageTileQueries->hasAnyMouthSupport()
&&!passageTileQueries->mayContainUpperMouthSupport())
{
if(passageProfile)++passageProfile->passageTileBoundChecks;
bool bAnyPassageWithinBound=false;
const double ExtraPadding=PassageBoundPaddingVoxels*Q;
for(std::size_t PassageIndex=0;
PassageIndex<ResolvedLayout->passages.size();++PassageIndex)
{
const auto& Passage=ResolvedLayout->passages[PassageIndex];
if(Passage.controlPoints.size()<2)continue;
const auto& Constants=PassageComposerConstants[PassageIndex];
if(qz>Constants.firstFloorQ+2.0*Passage.mouthRadiusSubvoxels
||qz<Constants.lastFloorQ-2.0*Passage.mouthRadiusSubvoxels)
continue;
const std::ptrdiff_t LowerMouthIndex=Constants.lowerMouthIndex;
const auto FloorProfile=[&](const auto& Point)
{return Point.positionSubvoxels[2]-Point.radiusSubvoxels
+1.13*qPerMetre;};
const auto CarveHigh=std::lower_bound(Passage.controlPoints.begin(),
Passage.controlPoints.begin()+LowerMouthIndex+1,
qz+Constants.carveSearchMargin,
[&](const auto& Point,double Value){return FloorProfile(Point)>Value;});
const auto CarveLow=std::lower_bound(Passage.controlPoints.begin(),
Passage.controlPoints.begin()+LowerMouthIndex+1,
qz-Constants.carveSearchMargin,
[&](const auto& Point,double Value){return FloorProfile(Point)>Value;});
const std::ptrdiff_t CarveBegin=std::max<std::ptrdiff_t>(0,
(CarveHigh-Passage.controlPoints.begin())-1);
const std::ptrdiff_t CarveEnd=std::min<std::ptrdiff_t>(LowerMouthIndex-1,
(CarveLow-Passage.controlPoints.begin())+1);
const double SignedDistanceLimit=-static_cast<double>(density)*Q
+0.24*qPerMetre+ExtraPadding;
if(PassageMayAffectDensity(PassageIndex,CarveBegin,CarveEnd,
LowerMouthIndex,Constants.mouthSearchBegin,Constants.mouthSearchEnd,
Constants.lastIndex,qx,qy,qz,SignedDistanceLimit))
{
bAnyPassageWithinBound=true;
break;
}
}
if(!bAnyPassageWithinBound)
{
if(passageProfile)
{
++passageProfile->passageTileBoundRejects;
passageProfile->passageTileBoundSkippedIterations
+=ResolvedLayout->passages.size();
}
return density;
}
}
bool queryNearUpperMouthSupport=false;
const auto checkUpperMouth=[&](const auto& passage)
{
@@ -0,0 +1,103 @@
# Linux81 — passage reach bound
## Reach derived from the code
The owner core voxel is 0.25 m. The passage carve is `max(source, -roughSignedDistance / Q)`. For a negative source value `d`, it can change the scalar as far as `-d` voxels outside the route radius. The outer test therefore uses `-d * Q + 0.24 m`; the extra sweep padding is added beyond that. The 0.24 m allowance covers the ±0.21 m wall relief plus 0.03 m margin; the mouth floor relief is bounded by ±0.20 m.
| Term | Reach and gate in the implementation |
|---|---|
| Route carve and wall relief | Route radius plus the density-dependent `-d` tail and 0.24 m allowance. A fixed geometric pad cannot bound arbitrary negative source values. |
| Smooth joins | Catmull–Rom replaces the chord only on eligible route segments no longer than 8 m; it is a local centerline change, not a long-distance fade. Mouth-support SDF blending has a separate 0.45 m width. |
| Ordinary support | Route tread half-width is at most 1.25 m; the support field extends at most 1 m below its tread and 0.35 m above. Short-span decks are a separate wider term: at most 3.75 m half-width and 5 m thickness, ending 4.87 m below the bore bottom because the deck floor is raised 0.13 m. Crossing-column Z ranges are separately bounded. |
| Mouth shaping and fades | Upper-mouth shaping uses the first three route segments, within 2 m in plan, 8 m along the route, and 4 m of the floor. Carve fade is 8 m along the route; floor relief fades over 11 m. The lower-mouth support blend is gated by a 20 m distance with a 12 m transition. |
| Mouth-route support | The query is limited to 13 m from the upper mouth. Its route cross-section reaches at most 1.01 m from the centerline (0.56 m half-width plus 0.45 m blend); the tile filter uses 15 m XY and 8 m vertical bounds. The outer cut is disabled in mouth-support and column-overlap tiles. |
| Strata/cave smooth minimum | The downstream 12-voxel blend acts on the composed cave field. It does not create a passage difference where the passage field is unchanged. |
| Transition passage fade | Separate seam path: mouth radius + 1 m protected margin + 2 m fade, evaluated by its own XY tile test. |
The old L80 geometric pad 0 missed the negative-density tail: its worst S0 sample had source density −18.1745 voxels, so the scalar reach was about 4.54 m + 0.24 m beyond the route radius (about 19.1 core voxels). It produced 19,604 changed samples across S0–S3 (19,434 / 63 / 86 / 21), no sign flips, and 6.64 cm maximum displacement. The large density deltas came from the carve’s `max(source, -SDF)` tail, not a far-field fade.
For L81, **0 extra voxels** is the exact tested point: the density-aware predicate retains the `-d` tail, while the 0.24 m relief margin is already in the bound. No single fixed geometric pad under 8 voxels can cover that tail for all source values.
## Padding sweep
Three interleaved runs per padding and stratum compared against the full path (`inf`). Work counts cover 17 L80 high-activity tiles (51 tile/run pairs) and 16 ordinary tiles (48 pairs). Paired time is candidate minus full worker time; negative is faster.
| Extra pad (voxels) | High skipped / total passage iterations | High share | Ordinary skipped / total | Ordinary share | Median paired tile Δms (high / ordinary) |
|---:|---:|---:|---:|---:|---:|
| 0 | 994,563 / 6,101,982 | 16.30% | 5,421,969 / 5,421,969 | 100.00% | −10.637 / +0.392 |
| 1 | 955,026 / 6,101,982 | 15.65% | 5,421,969 / 5,421,969 | 100.00% | −9.080 / +1.136 |
| 2 | 893,484 / 6,101,982 | 14.64% | 5,421,969 / 5,421,969 | 100.00% | −5.193 / −0.439 |
| 4 | 791,568 / 6,101,982 | 12.97% | 5,421,969 / 5,421,969 | 100.00% | −3.730 / +1.080 |
| 8 | 622,278 / 6,101,982 | 10.20% | 5,420,835 / 5,421,969 | 99.98% | −4.813 / +1.092 |
| 16 | 409,590 / 6,101,982 | 6.71% | 5,382,720 / 5,421,969 | 99.28% | −7.350 / +1.046 |
| 48 | 29,889 / 6,101,982 | 0.49% | 4,070,151 / 5,421,969 | 75.07% | +3.728 / +3.882 |
All 84 candidate/full pairs matched in density, mesh, payload, topology, material, whole-view, full-detail, and per-LOD hashes. The compared set has 0 changed density samples, 0 sign flips, and 0 maximum/mean surface displacement at every padding. The clean run contains 960 LOD0–1 tiles per stratum per run; verification is recorded in `Saved/Linux/l81/sweep/hash-verification.json`.
## Decision and readiness
Ship the density-aware bound at 0 extra voxels. It skips real loop iterations, gives the best work saving in this sweep, and is hash-identical in the measured tile set. Captures and cross-compiler peer runs were not needed under the exact-bound branch of the owner rule; no captures were taken.
Cold readiness used three interleaved measured full/exact pairs per stratum. Values are medians in seconds.
| Stratum | LOD0–2 full → exact | Whole view full → exact |
|---|---:|---:|
| SurfaceWorld | 1.304 → 1.246 | 2.738 → 2.749 |
| FloatingIslands | 3.592 → 2.926 | 4.982 → 4.368 |
| TunnelNetwork | 3.177 → 3.505 | 4.612 → 5.022 |
| VerticalShafts | 1.326 → 1.222 | 2.405 → 2.315 |
All 24 measured runs completed every readiness tile: LOD0–2 counts were 1,408 / 1,216 / 1,344 / 1,344 and whole-view counts were 2,850 / 2,249 / 2,233 / 2,329 in stratum order.
Readiness is mixed by stratum; the tile work counters and hashes, rather than a broad timing claim, support the decision.
The L77 LOD0–2 passage-share baseline was 65.9% FI and 65.4% TN. In the matched L81 profiler runs, full → exact means were 64.34% → 64.56% FI and 64.41% → 65.35% TN (two runs each). These small sampled-share changes are within the census variation.
## Version, hashes, and failed runs
- Evaluator version: 214. Source stamp: `8edc0292f2df6d279aa7e1d5c9c8c420ed36a9a138e17eed5310463e33e6146d`. Resolved layout identity: `resolved-layout-v3-fnv64:0589300eb07dfe06`.
- Exact outputs were checked over all four strata and the full 960-tile LOD0–1 target set. Captures: none, because the compared outputs are identical.
- The first sweep set mixed source stamps `6db4108c`, `f33a01da`, and `8edc0292`; it is excluded and preserved under `Saved/Linux/l81/sweep-mixed-stale/`. The final 96-run sweep is uniform at `8edc0292`.
- The first sweep parser attempt rejected `key=` as numeric; the parser was corrected before the clean sweep. No final sweep or readiness/census run timed out.
- The optional surface-world passage audit reported 65 solid centerline samples on passage 0, segment 15. The same failure and first sample (`−172, −138, −1794`) occurred with the L81 bound disabled (`inf`), so it is not caused by this bound; it remains a baseline audit failure.
- The floating-islands audit invocation stopped during setup because the selected recipe had no finite SurfaceWorld stratum; it produced no passage-audit result.
## Follow-up: passage 0 audit and fast tier
The surface-world audit used `Standalone/data/owner_world.json`, not a recipe fixture. It imported manifest
`bcc0d0d33ea39435` and resolved layout `resolved-layout-v3-fnv64:0589300eb07dfe06` with four strata. The
`--recipe=surface-world` flag selects the generator request. The imported manifest has one SurfaceWorld plan
and no native FloatingIslands plan, while the serialized owner layout still contains all four strata and
the SW→FI interface.
There are two passage representations in this input. The full-view run (`--max-level=-1`, force-generated)
fails before the resolved-layout audit on the 26-point root `owner_world.passages[0]` route: 65/5,310
centerline samples are solid, first at `(-172,-138,-1794)`. The canonical serialized SW→FI route has 211
control points; its resolved-layout audit passes with 4,151 center samples, zero blocked capsule samples,
and all three interfaces passing. So the full-view failure is real for the legacy owner route data, while
the canonical route used by the L70 plan-parity audit is walkable.
| Checkpoint | Canonical resolved route | Full-view root route |
|---|---|---|
| L70 `bd68aee`; verifier-only `018c0e1`; L71 `971206c` (same standalone runtime source) | PASS | 65 blockers |
| L72 `d970d75` (exact source build) | PASS | 65 blockers |
| L73–L76 `bd1b2a8`, `c67b200`, `9d5455e`, `90378a5` | PASS each | 65 blockers each |
| L77 `5e091d2` | Profiling-only change; no saved standalone binary | No field-evaluation change |
| L78–L79 `ec20994`, `2c8a26c` | PASS each | 65 blockers each |
| HEAD L80 `b06397d` (exact source build) | PASS | 65 blockers |
| L81 candidate | PASS | 65 blockers |
The 65-sample result therefore predates L81 and is present in the exact L70 source build; no later commit in
this range introduced it. The L70 report's 3/3 result is for the canonical resolved route, which is a
different check from the full-view pre-audit against the root route data. L71 changes tracing scripts but not
the standalone runtime; `2dfe599` and `68cba5a` are read-only research commits. The floating-islands companion
invocation still stops during setup because that selected recipe has no finite SurfaceWorld stratum; it gives
no passage result. No source fix was made.
`verify.py fast` passed on the L81 candidate in 321.2 s: 80 steps, zero unexpected failures. The four-strate
owner passage stage passed the 3/3 arrival/departure chain and W1/W8 per-stratum hash checks. Full logs and
summary are under `Saved/Linux/l81/verify-fast/`; the summary is `fast-summary.json`.
Evaluator version 214 was an intentional cache invalidation. The evaluator version is serialized into and
hashed with the Core recipe; advancing it prevents results cached under the previous passage evaluator from
being reused. The measured density and tile hashes remain identical.
@@ -0,0 +1,83 @@
#!/usr/bin/env python3
"""Repeat the L77 phase census on FI/TN with the L81 exact cut enabled."""
from __future__ import annotations
import json
import re
import subprocess
import time
from pathlib import Path
ROOT = Path(__file__).resolve().parents[4]
OUT = ROOT / "Saved/Linux/l81/census"
DATA = ROOT / "Standalone/data/owner_world.json"
BINARY = ROOT / "Saved/Linux/l81/profile-bin/VoxelForgeCoreHeadless-l81-profile-clang"
CAMERAS = {
"FI": (25.8369140625, 3.19921875, -737.0),
"TN": (19.166015625, -14.2001953125, -753.3740234375),
}
SAMPLE = re.compile(r"^\[L77Sample\] .*?lod=(\d+) .*?phase=(\S+) .*?weight=(\d+)$", re.M)
SAMPLER = re.compile(r"^\[L77Sampler\] action=stop .*?samples=(\d+).*?status=PASS$", re.M)
def run(world: str, rep: int, mode: str, padding: str) -> dict:
OUT.mkdir(parents=True, exist_ok=True)
log = OUT / f"l77-phase-{world.lower()}-{mode}-r{rep}.log"
camera = ",".join(f"{value:.12f}" for value in CAMERAS[world]) + ",0,0"
command = [
"taskset", "-c", "0-11", "prlimit", "--as=6442450944", "--",
"env", f"VOXELFORGE_L81_PASSAGE_BOUND_PADDING_VOXELS={padding}", "timeout", "1740s",
str(BINARY), str(DATA), "--world-assembler-prototype", "--stream-benchmark",
"--stream-pipeline", "--workers=8", "--clip-radius=3", "--max-clip-level=8",
"--max-level=8", f"--camera={camera}", "--profile-lod-work", "--linux77-profile",
]
start = time.monotonic()
try:
with log.open("w", encoding="utf-8") as stream:
proc = subprocess.run(command, cwd=ROOT, stdout=stream,
stderr=subprocess.STDOUT, check=False, timeout=1740)
except subprocess.TimeoutExpired as exc:
raise RuntimeError(f"census run exceeded 1,740 seconds: {log}") from exc
content = log.read_text(encoding="utf-8", errors="replace")
matches = [(int(lod), phase, int(weight)) for lod, phase, weight in SAMPLE.findall(content)]
sampler = SAMPLER.search(content)
if proc.returncode or not matches or not sampler:
raise RuntimeError(f"census failed exit={proc.returncode}: {log}")
near = [row for row in matches if row[0] <= 2]
passage = sum(weight for _, phase, weight in near if phase == "passages")
total = sum(weight for _, _, weight in near)
row = {
"world": world, "mode": mode, "padding_voxels": padding,
"replicate": rep, "exit_code": proc.returncode,
"wall_s": round(time.monotonic() - start, 3),
"sampler_samples": int(sampler.group(1)), "near_lod_samples": len(near),
"near_lod_weighted_ticks": total, "near_lod_passage_weighted_ticks": passage,
"near_lod_passage_share_pct": 100.0 * passage / total if total else 0.0,
"log": str(log.relative_to(ROOT)),
}
print("[L81CensusRun] " + json.dumps(row, sort_keys=True), flush=True)
return row
def main() -> int:
if not BINARY.is_file() or not DATA.is_file():
raise SystemExit(f"missing input: {BINARY} or {DATA}")
rows = [run(world, rep, mode, padding)
for mode, padding in (("full", "inf"), ("exact", "0"))
for rep in (1, 2) for world in ("FI", "TN")]
by_world = {}
for world in CAMERAS:
by_world[world] = {}
for mode in ("full", "exact"):
values = [row["near_lod_passage_share_pct"] for row in rows
if row["world"] == world and row["mode"] == mode]
by_world[world][mode] = {
"runs_pct": values, "mean_pct": sum(values) / len(values)}
(OUT / "l77-phase-summary.json").write_text(
json.dumps({"runs": rows, "near_lod_passage_share": by_world}, indent=2) + "\n",
encoding="utf-8")
return 0
if __name__ == "__main__":
raise SystemExit(main())
@@ -0,0 +1,63 @@
#!/usr/bin/env python3
"""Run the resolved owner passage audit for both owner recipes."""
from __future__ import annotations
import json
import re
import subprocess
import time
from pathlib import Path
ROOT = Path(__file__).resolve().parents[4]
OUT = ROOT / "Saved/Linux/l81/audits"
DATA = ROOT / "Standalone/data/owner_world.json"
BINARY = ROOT / "Saved/Linux/l81/bin/VoxelForgeCoreHeadless-l81-clang"
RECIPE = re.compile(r"^\[WorldAssemblerRecipeAudit\] requested=([^ ]+) actual=([^ ]+).*status=PASS$", re.M)
PASSAGE = re.compile(r"^\[ResolvedPassageAudit\].*walkability=PASS$", re.M)
MOUTH = re.compile(r"^\[PassageMouthProfileAudit\].*status=PASS$", re.M)
SUMMARY = re.compile(r"^\[ResolvedPassageAuditSummary\].*status=PASS$", re.M)
def run(recipe: str) -> dict:
OUT.mkdir(parents=True, exist_ok=True)
log = OUT / f"owner-{recipe}.log"
command = [
"taskset", "-c", "0-11", "prlimit", "--as=6442450944", "--",
"env", "VOXELFORGE_L81_PASSAGE_BOUND_PADDING_VOXELS=0", "timeout", "1740s",
str(BINARY), str(DATA), "--workers=12", "--world-assembler-prototype",
"--stream-benchmark", "--stream-pipeline", "--force-generate", "--clip-radius=3",
"--max-clip-level=8", "--max-level=-1", f"--recipe={recipe}",
"--audit-resolved-layout-passages",
]
start = time.monotonic()
try:
with log.open("w", encoding="utf-8") as stream:
proc = subprocess.run(command, cwd=ROOT, stdout=stream,
stderr=subprocess.STDOUT, check=False, timeout=1740)
except subprocess.TimeoutExpired as exc:
raise RuntimeError(f"passage audit exceeded 1,740 seconds: {log}") from exc
content = log.read_text(encoding="utf-8", errors="replace")
passages = len(PASSAGE.findall(content))
mouths = len(MOUTH.findall(content))
passed = (proc.returncode == 0 and RECIPE.findall(content) == [(recipe, recipe)]
and passages >= 1 and mouths == passages and SUMMARY.search(content) is not None)
row = {"recipe": recipe, "exit_code": proc.returncode, "passages": passages,
"mouth_profiles": mouths, "status": "PASS" if passed else "FAIL",
"wall_s": round(time.monotonic() - start, 3), "log": str(log.relative_to(ROOT))}
print("[L81PassageAuditRun] " + json.dumps(row, sort_keys=True), flush=True)
if not passed:
raise RuntimeError(f"owner passage audit failed: {log}")
return row
def main() -> int:
if not BINARY.is_file() or not DATA.is_file():
raise SystemExit(f"missing input: {BINARY} or {DATA}")
rows = [run(recipe) for recipe in ("surface-world", "floating-islands")]
(OUT / "summary.json").write_text(json.dumps(rows, indent=2) + "\n",
encoding="utf-8")
return 0
if __name__ == "__main__":
raise SystemExit(main())
@@ -0,0 +1,181 @@
#!/usr/bin/env python3
"""Interleaved exact passage-bound padding sweep on the L80 tile census."""
from __future__ import annotations
import json
import math
import re
import statistics
import subprocess
import time
from pathlib import Path
ROOT = Path(__file__).resolve().parents[4]
OUT = ROOT / "Saved/Linux/l81/sweep"
DATA = ROOT / "Standalone/data/owner_world.json"
BINARY = ROOT / "Saved/Linux/l81/bin/VoxelForgeCoreHeadless-l81-clang"
CAMERAS = {
0: (8.0, 16.0, -372.2626953125),
1: (25.8369140625, 3.19921875, -737.0),
2: (19.166015625, -14.2001953125, -753.3740234375),
3: (-20.0625, -5.068359375, -900.353515625),
}
PADS = ("0", "1", "2", "4", "8", "16", "48", "inf")
REPS = 3
TILE = re.compile(r"^\[PassageComposerTile\] (.*)$", re.M)
FIELD = re.compile(r"([a-zA-Z0-9_]+)=([^ ]+)")
KEY = re.compile(r"key=\((-?\d+),(-?\d+),(-?\d+),lod(\d+)\)")
HASH = re.compile(r"^\[PipelineTileHash\] lod=(\d+) x=(-?\d+) y=(-?\d+) z=(-?\d+) "
r"density=(\S+) mesh=(\S+) payload=(\S+) topology=(\S+)$", re.M)
def parse(log: Path, strate: int, pad: str, rep: int) -> dict:
content = log.read_text(encoding="utf-8", errors="replace")
tiles = []
for match in TILE.finditer(content):
values = dict(FIELD.findall(match.group(1)))
key = KEY.search(match.group(1))
if not key:
continue
row = {name: int(value) for name, value in values.items()
if name not in ("key", "worker_ms")}
row["worker_ms"] = float(values["worker_ms"])
row["key"] = tuple(int(key.group(i)) for i in range(1, 5))
tiles.append(row)
hashes = {}
for m in HASH.finditer(content):
key = (int(m.group(2)), int(m.group(3)), int(m.group(4)), int(m.group(1)))
hashes[key] = m.group(5, 6, 7, 8)
if not tiles or not hashes:
raise RuntimeError(f"missing passage rows or tile hashes in {log}")
return {"strate": strate, "pad": pad, "replicate": rep, "log": str(log.relative_to(ROOT)),
"tiles": tiles, "hashes": hashes}
def run(strate: int, pad: str, rep: int) -> dict:
OUT.mkdir(parents=True, exist_ok=True)
log = OUT / f"s{strate}-p{pad}-r{rep}.log"
camera = ",".join(f"{v:.12f}" for v in CAMERAS[strate]) + ",0,0"
command = [
"taskset", "-c", "0-11", "prlimit", "--as=6442450944", "--",
"env", f"VOXELFORGE_L81_PASSAGE_BOUND_PADDING_VOXELS={pad}", "timeout", "1740s",
str(BINARY), str(DATA), "--world-assembler-prototype", "--stream-benchmark",
"--stream-pipeline", "--workers=8", "--clip-radius=3", "--max-clip-level=8",
"--max-level=1", f"--camera={camera}", "--profile-lod-work",
"--profile-passage-composer", "--stream-hash-tiles",
]
start = time.monotonic()
try:
with log.open("w", encoding="utf-8") as stream:
result = subprocess.run(command, cwd=ROOT, stdout=stream,
stderr=subprocess.STDOUT, check=False, timeout=1740)
except subprocess.TimeoutExpired as exc:
raise RuntimeError(f"run exceeded 1,740 seconds: {log}") from exc
if result.returncode:
raise RuntimeError(f"run failed exit={result.returncode}: {log}")
parsed = parse(log, strate, pad, rep)
parsed["wall_s"] = round(time.monotonic() - start, 3)
parsed["exit_code"] = result.returncode
print("[L81PassageSweepRun] " + json.dumps(
{k: v for k, v in parsed.items() if k not in ("tiles", "hashes")}, sort_keys=True),
flush=True)
return parsed
def main() -> int:
if not BINARY.is_file() or not DATA.is_file():
raise SystemExit(f"missing input: {BINARY} or {DATA}")
old = json.loads((ROOT / "Saved/Linux/l80/passage-census/candidate-pad4.json")
.read_text(encoding="utf-8"))
high = {int(run["strate"]): {tuple(key) for key in run["keys"]} for run in old}
results = []
ordinary: dict[int, set[tuple[int, int, int, int]]] = {}
for strate in range(4):
for rep in range(1, REPS + 1):
offset = (strate + rep - 1) % len(PADS)
order = PADS[offset:] + PADS[:offset]
for pad in order:
run_data = run(strate, pad, rep)
if strate not in ordinary:
candidates = [row for row in run_data["tiles"]
if row["key"] not in high[strate]
and row.get("features", 0) == 0
and row.get("tile_bound_checks", 0) > 0]
candidates.sort(key=lambda row: (
row.get("tile_bound_rejects", 0), row.get("worker_ms", 0)),
reverse=True)
ordinary[strate] = {row["key"] for row in candidates[:4]}
results.append(run_data)
indexed = {(r["strate"], r["pad"], r["replicate"]): r for r in results}
pad_rows = []
failures = []
for strate in range(4):
high_keys = high[strate]
ordinary_keys = ordinary[strate]
for pad in PADS[:-1]:
pair_deltas = {"high": [], "ordinary": []}
sums = {name: {key: 0 for key in ("tile_bound_checks", "tile_bound_rejects",
"tile_bound_skipped_iterations", "passage_iterations", "samples")}
for name in pair_deltas}
all_hashes_equal = True
for rep in range(1, REPS + 1):
candidate = indexed[(strate, pad, rep)]
baseline = indexed[(strate, "inf", rep)]
base_tiles = {row["key"]: row for row in baseline["tiles"]}
for row in candidate["tiles"]:
key = row["key"]
if key in high_keys:
group = "high"
elif key in ordinary_keys:
group = "ordinary"
else:
continue
base = base_tiles[key]
pair_deltas[group].append(row["worker_ms"] - base["worker_ms"])
for metric in sums[group]:
sums[group][metric] += row.get(metric, 0)
if candidate["hashes"].get(key) != baseline["hashes"].get(key):
all_hashes_equal = False
failures.append({"strate": strate, "pad": pad, "replicate": rep,
"key": key, "candidate_hash": candidate["hashes"].get(key),
"baseline_hash": baseline["hashes"].get(key)})
entry = {"strate": strate, "pad": pad, "replicates": REPS,
"high_keys": len(high_keys), "ordinary_keys": len(ordinary_keys),
"hashes_equal_to_full": all_hashes_equal}
for group in ("high", "ordinary"):
n = len(pair_deltas[group])
count_denominator = sums[group]["tile_bound_skipped_iterations"] \
+ sums[group]["passage_iterations"]
entry[group] = {
**sums[group],
"skipped_iteration_fraction": (
sums[group]["tile_bound_skipped_iterations"] / count_denominator
if count_denominator else 0.0),
"paired_tile_ms_delta_median": statistics.median(pair_deltas[group])
if n else 0.0,
"paired_tile_ms_delta_mean": statistics.mean(pair_deltas[group])
if n else 0.0,
}
pad_rows.append(entry)
payload = {
"pads_voxels_extra": list(PADS[:-1]), "baseline": "infinite extra pad (fail-open full passage path)",
"high_tile_keys_from_l80": {str(k): [list(v) for v in sorted(keys)]
for k, keys in high.items()},
"ordinary_tile_keys": {str(k): [list(v) for v in sorted(keys)]
for k, keys in ordinary.items()},
"sweep_rows": pad_rows,
"hash_mismatches": failures,
"runs": [{k: v for k, v in r.items() if k not in ("tiles", "hashes")}
for r in results],
}
(OUT / "summary.json").write_text(json.dumps(payload, indent=2) + "\n",
encoding="utf-8")
print(f"[L81PassageSweepSummary] runs={len(results)} hash_mismatches={len(failures)} "
f"summary={OUT / 'summary.json'}", flush=True)
return 1 if failures else 0
if __name__ == "__main__":
raise SystemExit(main())
@@ -0,0 +1,102 @@
#!/usr/bin/env python3
"""L80-protocol cold readiness comparison for the exact passage cut."""
from __future__ import annotations
import json
import re
import statistics
import subprocess
import time
from pathlib import Path
ROOT = Path(__file__).resolve().parents[4]
OUT = ROOT / "Saved/Linux/l81/readiness"
DATA = ROOT / "Standalone/data/owner_world.json"
BINARY = ROOT / "Saved/Linux/l81/bin/VoxelForgeCoreHeadless-l81-clang"
CAMERAS = {
0: (8.0, 16.0, -372.2626953125),
1: (25.8369140625, 3.19921875, -737.0),
2: (19.166015625, -14.2001953125, -753.3740234375),
3: (-20.0625, -5.068359375, -900.353515625),
}
MODES = (("full", "inf"), ("exact", "0"))
PIPELINE = re.compile(r"^\[StreamPipeline\] (.*)$", re.M)
FIELDS = re.compile(r"([a-zA-Z0-9_]+)=([^ ]+)")
NEAR = re.compile(r"^\[WorldAssemblerNearLODReady\] lods=0-2 tiles=(\d+)/(\d+) "
r"cold_ready_s=([0-9.]+)$", re.M)
def run(strate: int, mode: str, padding: str, phase: str, rep: int) -> dict:
OUT.mkdir(parents=True, exist_ok=True)
label = f"s{strate}-{mode}-{phase}{rep}"
log = OUT / f"{label}.log"
camera = ",".join(f"{value:.12f}" for value in CAMERAS[strate]) + ",0,0"
command = [
"taskset", "-c", "0-11", "prlimit", "--as=6442450944", "--",
"env", f"VOXELFORGE_L81_PASSAGE_BOUND_PADDING_VOXELS={padding}", "timeout", "1740s",
str(BINARY), str(DATA), "--world-assembler-prototype", "--stream-benchmark",
"--stream-pipeline", "--workers=8", "--clip-radius=3", "--max-clip-level=8",
"--max-level=8", f"--camera={camera}", "--profile-lod-work",
"--stream-scheduler-policy=3",
]
start = time.monotonic()
try:
with log.open("w", encoding="utf-8") as stream:
proc = subprocess.run(command, cwd=ROOT, stdout=stream,
stderr=subprocess.STDOUT, check=False, timeout=1740)
except subprocess.TimeoutExpired as exc:
raise RuntimeError(f"readiness run exceeded 1,740 seconds: {log}") from exc
content = log.read_text(encoding="utf-8", errors="replace")
pipeline_match = PIPELINE.search(content)
near_match = NEAR.search(content)
if proc.returncode or not pipeline_match or not near_match:
raise RuntimeError(f"readiness run failed exit={proc.returncode}: {log}")
pipeline = dict(FIELDS.findall(pipeline_match.group(1)))
row = {
"strate": strate, "mode": mode, "padding_voxels": padding,
"phase": phase, "replicate": rep, "exit_code": proc.returncode,
"wall_s": round(time.monotonic() - start, 3),
"lod02_ready_s": float(near_match.group(3)),
"whole_view_ready_s": float(pipeline["whole_view_ready"].removesuffix("s")),
"whole_tiles": int(pipeline["whole_tiles"].split("/")[0]),
"log": str(log.relative_to(ROOT)),
}
print("[L81ReadinessRun] " + json.dumps(row, sort_keys=True), flush=True)
return row
def main() -> int:
if not BINARY.is_file() or not DATA.is_file():
raise SystemExit(f"missing input: {BINARY} or {DATA}")
rows = []
for strate in range(4):
for mode, padding in MODES:
run(strate, mode, padding, "warmup", 0)
orders = (("full", "exact"), ("exact", "full"), ("full", "exact"))
for strate in range(4):
for rep, order in enumerate(orders, 1):
for mode in order:
padding = dict(MODES)[mode]
rows.append(run(strate, mode, padding, "measured", rep))
(OUT / "runs-partial.json").write_text(json.dumps(rows, indent=2) + "\n",
encoding="utf-8")
summary = []
for strate in range(4):
group = [row for row in rows if row["strate"] == strate]
item = {"strate": strate, "measured_pairs": 3}
for mode, _ in MODES:
subset = [row for row in group if row["mode"] == mode]
item[f"{mode}_lod02_s"] = [row["lod02_ready_s"] for row in subset]
item[f"{mode}_lod02_median_s"] = statistics.median(
row["lod02_ready_s"] for row in subset)
item[f"{mode}_whole_s"] = [row["whole_view_ready_s"] for row in subset]
item[f"{mode}_whole_median_s"] = statistics.median(
row["whole_view_ready_s"] for row in subset)
summary.append(item)
(OUT / "summary.json").write_text(json.dumps({"runs": rows, "summary": summary},
indent=2) + "\n", encoding="utf-8")
return 0
if __name__ == "__main__":
raise SystemExit(main())
+4 -1
View File
@@ -1306,7 +1306,7 @@ private:
static_cast<unsigned long long>(D.islandSharedCacheConflictReplacements),
static_cast<double>(D.islandSharedCacheLockWaitNanoseconds)/1000.0);
if(D.passageComposerProfiled)
std::printf("[PassageComposerTile] key=(%d,%d,%d,lod%d) worker_ms=%.3f samples=%llu native_field_calls=%llu features=%llu route_candidates=%llu mouth_candidates=%llu queries=%llu passage_iterations=%llu upper_mouth_checks=%llu column_candidates=%llu column_distance_calls=%llu negative_bounds=%llu negative_rejects=%llu positive_bounds=%llu positive_rejects=%llu carve_segment_visits=%llu smooth_carve_joins=%llu support_segment_visits=%llu smooth_support_joins=%llu support_capsule_checks=%llu later_bore_checks=%llu other_capsule_checks=%llu mouth_support_calls=%llu mouth_route_segment_checks=%llu relief_field_calls=%llu smoothstep_evaluations=%llu\n",
std::printf("[PassageComposerTile] key=(%d,%d,%d,lod%d) worker_ms=%.3f samples=%llu native_field_calls=%llu features=%llu route_candidates=%llu mouth_candidates=%llu queries=%llu passage_iterations=%llu tile_bound_checks=%llu tile_bound_rejects=%llu tile_bound_skipped_iterations=%llu upper_mouth_checks=%llu column_candidates=%llu column_distance_calls=%llu negative_bounds=%llu negative_rejects=%llu positive_bounds=%llu positive_rejects=%llu carve_segment_visits=%llu smooth_carve_joins=%llu support_segment_visits=%llu smooth_support_joins=%llu support_capsule_checks=%llu later_bore_checks=%llu other_capsule_checks=%llu mouth_support_calls=%llu mouth_route_segment_checks=%llu relief_field_calls=%llu smoothstep_evaluations=%llu\n",
Event.Key.Coord.X,Event.Key.Coord.Y,Event.Key.Coord.Z,Event.Key.Level,
Event.WorkerMilliseconds,static_cast<unsigned long long>(Event.DensitySamples),
static_cast<unsigned long long>(D.fieldCalls),
@@ -1315,6 +1315,9 @@ private:
static_cast<unsigned long long>(D.passageTileMouthSegmentCandidates),
static_cast<unsigned long long>(D.passageComposerQueries),
static_cast<unsigned long long>(D.passageIterations),
static_cast<unsigned long long>(D.passageTileBoundChecks),
static_cast<unsigned long long>(D.passageTileBoundRejects),
static_cast<unsigned long long>(D.passageTileBoundSkippedIterations),
static_cast<unsigned long long>(D.passageUpperMouthFilterChecks),
static_cast<unsigned long long>(D.passageColumnCandidates),
static_cast<unsigned long long>(D.passageColumnDistanceCalls),