← Files ModRetro Chromatic PluginARCHIVED FILE

dist/wrecklight-dependencies.js

136 KB · Oct 2, 2026 · 00:37 UTC

↓ Download file

import path from "node:path";
import { isDeepStrictEqual } from "node:util";
import { decodeResourceBytes } from "./resource-codec.js";
import { WRECKLIGHT_PACING_SOURCE_REVIEW, WRECKLIGHT_BUSYROOM_SOURCE_REVIEW, WRECKLIGHT_DOOR_REVIEW, WRECKLIGHT_PERFORMANCE_SOURCE_REVIEW, WRECKLIGHT_REMIX_SOURCE_REVIEW, WRECKLIGHT_REVIEW } from "./wrecklight/profiles/base.js";
import { WRECKLIGHT_CURRENT_REVIEW } from "./wrecklight/profiles/current.js";
import { WRECKLIGHT_CHAMBERS_REVIEW } from "./wrecklight/profiles/chambers.js";
import { WRECKLIGHT_SEP17_REVIEW } from "./wrecklight/profiles/sep17.js";
import { WRECKLIGHT_COMBINED_SOURCE_REVIEW } from "./wrecklight/profiles/combined.js";
import { WRECKLIGHT_PAYOFF_SOURCE_REVIEW } from "./wrecklight/profiles/payoff.js";
import { WRECKLIGHT_OVERLAY_SOURCE_REVIEW } from "./wrecklight/profiles/overlay.js";
import { WRECKLIGHT_CAPTURE_SOURCE_REVIEW } from "./wrecklight/profiles/capture.js";
import { WRECKLIGHT_RENDER_SOURCE_REVIEW } from "./wrecklight/profiles/render.js";
import { WRECKLIGHT_SCROLL_SOURCE_REVIEW } from "./wrecklight/profiles/scroll.js";
import { WRECKLIGHT_SAMPLING_SOURCE_REVIEW } from "./wrecklight/profiles/sampling.js";
import { WRECKLIGHT_CHAMBER_CACHE_SOURCE_REVIEW } from "./wrecklight/profiles/chamber-cache.js";
import { WRECKLIGHT_FLAT_PROJECTILE_SOURCE_REVIEW } from "./wrecklight/profiles/flat-projectile.js";
import { WRECKLIGHT_DRIVE_PERFORMANCE_SOURCE_REVIEW } from "./wrecklight/profiles/drive-performance.js";
import { WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW } from "./wrecklight/profiles/boss-three-phase.js";
import { WRECKLIGHT_BOSS_CUE_SOURCE_REVIEW } from "./wrecklight/profiles/boss-cue.js";
import { WRECKLIGHT_BOSS_LOOP_SOURCE_REVIEW } from "./wrecklight/profiles/boss-loop.js";
import { WRECKLIGHT_BOSS_CAPTURE_PREFIX_SOURCE_REVIEW } from "./wrecklight/profiles/boss-capture-prefix.js";
import { WRECKLIGHT_SCHEDULER_COUNTDOWN_SOURCE_REVIEW } from "./wrecklight/profiles/scheduler-countdown.js";
import { WRECKLIGHT_BRAKEMAW_TIMERS_SOURCE_REVIEW } from "./wrecklight/profiles/brakemaw-timers.js";
import { WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW } from "./wrecklight/profiles/opening-direction.js";
import { WRECKLIGHT_OPENING_CORRECTION_SOURCE_REVIEW } from "./wrecklight/profiles/opening-correction.js";
import { WRECKLIGHT_COMBINED_PERFORMANCE_SOURCE_REVIEW } from "./wrecklight/profiles/combined-performance.js";
import { WRECKLIGHT_KEEP_VIEW_MAP_SOURCE_REVIEW } from "./wrecklight/profiles/keep-view-map.js";
import { WRECKLIGHT_GAMEPLAY_POLISH_SOURCE_REVIEW } from "./wrecklight/profiles/gameplay-polish.js";
import { WRECKLIGHT_WARDEN_ROW_SOURCE_REVIEW } from "./wrecklight/profiles/warden-row.js";
import { WRECKLIGHT_COMPOSED_GAMEPLAY_SOURCE_REVIEW } from "./wrecklight/profiles/composed-gameplay.js";
import { WRECKLIGHT_BRAKEMAW_FINISH_SOURCE_REVIEW } from "./wrecklight/profiles/brakemaw-finish.js";
import { WRECKLIGHT_CROWN_MOTION_SOURCE_REVIEW } from "./wrecklight/profiles/crown-motion.js";
import { WRECKLIGHT_BRAKEMAW_CAPTURE_LAYOUT_SOURCE_REVIEW } from "./wrecklight/profiles/brakemaw-capture-layout.js";
import { WRECKLIGHT_CARGO_CONTACT_SOURCE_REVIEW as cargoContact } from "./wrecklight/profiles/cargo-contact.js";
import { WRECKLIGHT_PROJECTILE_SPAWN_CONTACT_SOURCE_REVIEW as projectileSpawnContact } from "./wrecklight/profiles/projectile-spawn-contact.js";
import { WRECKLIGHT_WARDEN_CONDENSER_REVIEW, WRECKLIGHT_WARDEN_CUE_REVIEW, WRECKLIGHT_WARDEN_DYNAMO_BEAM_REVIEW, WRECKLIGHT_WARDEN_FEEDBACK_REVIEW, WRECKLIGHT_WARDEN_REVIEW, WRECKLIGHT_WARDEN_ROM44_REVIEW } from "./wrecklight/profiles/warden.js";
function immutable(value) {
    if (value && typeof value === "object" && !Object.isFrozen(value)) {
        for (const child of Object.values(value))
            immutable(child);
        Object.freeze(value);
    }
    return value;
}
const range = (first, last) => Array.from({ length: last - first + 1 }, (_, i) => String(first + i));
const incomplete = (reason) => ({ status: "incomplete", reason });
// Each alternative owns its complete bindings AND semantics. A successor must
// never inherit the old room table merely because a handler's bytes stayed the same.
function nativeContracts(source, idSuffix, version = 2) {
    const review = immutable(source);
    const MAP_WORDS = review.runtime?.mapWords ?? range(223, 582);
    const SEEN = review.runtime?.seen ?? range(223, 398);
    const VISITED = review.runtime?.visited ?? range(399, 574);
    const ROOM_WORDS = review.runtime?.roomWords ?? ["579"];
    const HUD_READS = ["81", "36", "80", "86", "98", "94", "95", "21", "221", "8", "77", "587", "586", "585", ...(review.runtime?.hudReads ?? [])];
    const VERIFY_READS = [...MAP_WORDS, "143", "8", "88", "585", "586", "587", "588", ...(review.runtime?.verifyReads ?? [])];
    const wardenEventBranches = [...new Set(Object.values(review.warden?.operations ?? {})
            .flatMap((operation) => operation.children))];
    /** This review covers a fixed native extension, not arbitrary C or handlers.
     * Preserve the compiler's slice-then-filter actor order. Missing sprites and
     * prefab expansion are refused instead of guessing the fallback actor index.
     * Actor positions, scripts and scene collision edits remain ordinary resources
     * unless a successor explicitly binds a compiler-sensitive actor resource. */
    function layoutReason(context) {
        const { inventory, resourceFiles } = context;
        if (inventory.format !== "distributed" || inventory.descriptor._version !== "4.2.0"
            || inventory.descriptor._release !== "10"
            || path.relative(inventory.projectRoot, inventory.projectPath) !== "project.gbsproj") {
            return "The reviewed distributed project descriptor is required";
        }
        if (review.fixedRemixDescriptor) {
            const descriptor = inventory.descriptor;
            const fixed = review.fixedRemixDescriptor;
            if (typeof descriptor.name !== "string" || typeof descriptor.author !== "string"
                || Object.keys(descriptor).length !== Object.keys(fixed).length + 2
                || Object.entries(fixed).some(([key, value]) => descriptor[key] !== value)
                || Object.keys(descriptor).some((key) => key !== "name" && key !== "author" && !Object.hasOwn(fixed, key))) {
                return "The reviewed remix descriptor permits only string name and author changes";
            }
        }
        if (!resourceFiles)
            return "The complete compiler-visible resource classification is required";
        // The ordinary loader uses each resource's _resourceType and its immediate
        // folder. The index's filename-based projection must not hide another loaded
        // actor/scene/asset or associate a nested actor with a different scene.
        for (const file of resourceFiles) {
            if (file.type === "scene") {
                const matches = inventory.scenes.filter((scene) => scene.resourcePath === file.path && scene.id === file.id);
                if (matches.length !== 1)
                    return "A compiler-visible scene is missing or ambiguous in the inventory";
            }
            else if (file.type === "actor" || file.type === "trigger") {
                const family = file.type === "actor" ? "actors" : "triggers";
                const directory = path.posix.dirname(file.path);
                if (path.posix.basename(directory) !== family)
                    return "A compiler-visible owner has an unsupported folder association";
                const scenes = inventory.scenes.filter((scene) => path.posix.dirname(scene.resourcePath) === path.posix.dirname(directory));
                if (scenes.length !== 1 || scenes[0][family].filter((owner) => owner.resourcePath === file.path && owner.id === file.id).length !== 1) {
                    return "Compiler and index owner membership differ";
                }
            }
            else if (file.type === "sprite" || file.type === "sound" || (file.type === "background" && review.backgrounds)) {
                if (inventory.assets.filter((asset) => asset.type === file.type && asset.metadataPath === file.path && asset.id === file.id).length !== 1) {
                    return "A compiler-visible native asset is missing or ambiguous in the inventory";
                }
            }
        }
        for (const room of review.rooms) {
            const scenes = inventory.scenes.filter((scene) => scene.id === room.id);
            if (scenes.length !== 1)
                return "A native room ID is missing or ambiguous";
            const scene = scenes[0];
            if (scene._resourceType !== "scene" || scene.symbol !== room.symbol || scene.type !== "PLATFORM"
                || (room.resourcePath !== undefined && scene.resourcePath !== room.resourcePath)
                || inventory.scenes.filter((other) => other.symbol === room.symbol).length !== 1) {
                return "A native room symbol or platform selection changed";
            }
            if (scene.actors.length !== room.actors.length || scene.actors.length > 20
                || scene.actors.some((actor) => !Number.isSafeInteger(actor._index) || actor.prefabId)
                || new Set(scene.actors.map((actor) => actor._index)).size !== scene.actors.length) {
                return "Native actor membership, unique ordering or prefab selection changed";
            }
            const actors = [...scene.actors].sort((a, b) => Number(a._index) - Number(b._index));
            for (let i = 0; i < actors.length; i++) {
                const actor = actors[i], expected = room.actors[i];
                if (actor._resourceType !== "actor" || actor.id !== expected.id || actor._index !== expected.index
                    || actor.resourcePath !== path.posix.join(path.posix.dirname(scene.resourcePath), "actors", expected.filename)
                    || scene.actors.filter((other) => other.id === actor.id).length !== 1) {
                    return "An authored actor no longer has the reviewed native slot";
                }
                const sprites = inventory.assets.filter((asset) => asset.type === "sprite" && asset.id === actor.spriteSheetId);
                if (typeof actor.spriteSheetId !== "string" || sprites.length !== 1 || !sprites[0].hasMetadata) {
                    return "The compiler's actor sprite inclusion is missing or ambiguous";
                }
                if (resourceFiles.filter((file) => file.path === sprites[0].metadataPath && file.type === "sprite" && file.id === sprites[0].id).length !== 1) {
                    return "The actor sprite is not uniquely present in the compiler's resource inputs";
                }
            }
        }
        for (const expected of [review.sound, ...(review.extendedEvents?.sounds ?? []), ...(review.warden?.sounds ?? [])]) {
            const sounds = inventory.assets.filter((asset) => asset.type === "sound"
                && (asset.id === expected.id || asset.symbol === expected.symbol));
            if (sounds.length !== 1 || sounds[0].id !== expected.id || sounds[0].symbol !== expected.symbol
                || sounds[0].filename !== expected.filename || sounds[0].plugin) {
                return "A native ceremony or reward sound association changed";
            }
        }
        if (review.warden) {
            const expected = review.warden;
            const room = review.rooms.find((room) => room.id === expected.sceneId);
            const binding = room?.actors.find((actor) => actor.id === expected.actorId);
            const scene = inventory.scenes.find((scene) => scene.id === expected.sceneId);
            const actor = scene?.actors.find((actor) => actor.id === expected.actorId);
            const sprite = inventory.assets.find((asset) => asset.id === expected.spriteId && asset.type === "sprite");
            if (!scene || scene.width !== 40 || scene.height !== 24
                || (scene.tilesetId !== undefined && scene.tilesetId !== "")) {
                return "The Warden requires the reviewed 40 by 24 resident background without an extra tileset";
            }
            if (!actor || !binding || binding.slot !== expected.actorSlot || actor._index !== expected.actorIndex
                || actor.resourcePath !== expected.actorPath || actor.spriteSheetId !== expected.spriteId || !sprite) {
                return "The Warden requires its exact Deck actor, compiled slot and sprite association";
            }
            const states = sprite.states;
            const state = Array.isArray(states) ? states[0] : undefined;
            if (!state || typeof state !== "object" || Array.isArray(state) || state.id !== expected.stateId
                || state.name !== "" || state.animationType !== "fixed" || state.flipLeft !== false
                || !Array.isArray(state.animations) || !state.animations[0]
                || !Array.isArray(state.animations[0].frames) || state.animations[0].frames.length !== expected.frameCount) {
                return "The Warden requires its reviewed default fixed animation and frame offsets";
            }
            for (const sound of expected.sounds) {
                const asset = inventory.assets.find((asset) => asset.id === sound.id && asset.type === "sound");
                if (!asset?.hasMetadata || asset.metadataPath !== sound.metadataPath
                    || resourceFiles.filter((file) => file.path === sound.metadataPath && file.type === "sound" && file.id === sound.id).length !== 1) {
                    return "A Warden sound is missing its reviewed compiler-visible metadata";
                }
            }
        }
        for (const expected of [...(review.nativeSprites ?? []), ...(review.player ? [review.player] : [])]) {
            const matches = inventory.assets.filter((asset) => asset.type === "sprite"
                && (asset.id === expected.id || asset.symbol === expected.symbol));
            if (matches.length !== 1 || matches[0].id !== expected.id || matches[0].symbol !== expected.symbol
                || matches[0].filename !== expected.filename || matches[0].metadataPath !== expected.metadataPath
                || !matches[0].hasMetadata || matches[0].plugin
                || resourceFiles.filter((file) => file.path === expected.metadataPath && file.type === "sprite" && file.id === expected.id).length !== 1) {
                return "A native compiled sprite association changed";
            }
        }
        if (review.player) {
            const defaults = inventory.settings.defaultPlayerSprites;
            if (!defaults || typeof defaults !== "object" || Array.isArray(defaults)
                || defaults.PLATFORM !== review.player.id
                || inventory.scenes.some((scene) => scene.type === "PLATFORM"
                    && scene.playerSpriteSheetId !== undefined && scene.playerSpriteSheetId !== review.player.id)) {
                return "The native presentation player sprite selection changed";
            }
            const player = inventory.assets.find((asset) => asset.id === review.player.id);
            const states = player.states;
            if (!Array.isArray(states) || review.player.states.some((expected) => states.filter((state) => state && typeof state === "object" && !Array.isArray(state)
                && (state.id === expected.id || state.name === expected.name)).length !== 1
                || !states.some((state) => state && typeof state === "object" && !Array.isArray(state)
                    && state.id === expected.id && state.name === expected.name))) {
                return "A native player animation state is missing or ambiguous";
            }
        }
        for (const expected of review.backgrounds ?? []) {
            const scene = inventory.scenes.find((candidate) => candidate.id === expected.sceneId);
            const choices = [expected, ...(expected.alternatives ?? [])].filter((choice) => choice.id === scene?.backgroundId);
            const selected = choices[0];
            const backgrounds = inventory.assets.filter((asset) => asset.type === "background" && asset.id === selected?.id);
            if (!scene || choices.length !== 1 || !selected
                || (scene.parallax !== undefined && (!Array.isArray(scene.parallax) || scene.parallax.length !== 0))
                || scene.parallaxLayers !== undefined
                || backgrounds.length !== 1 || backgrounds[0].metadataPath !== selected.metadataPath
                || !backgrounds[0].hasMetadata || backgrounds[0].width !== expected.width || backgrounds[0].height !== expected.height
                || resourceFiles.filter((file) => file.path === selected.metadataPath && file.type === "background" && file.id === selected.id).length !== 1) {
                return "The native door renderer requires its reviewed background association without parallax";
            }
        }
        if (review.extendedEvents) {
            const expected = review.extendedEvents.title;
            const scenes = inventory.scenes.filter((scene) => scene.id === expected.id || scene.symbol === expected.symbol);
            const scene = scenes[0];
            const choices = [expected.background, ...(expected.backgroundAlternatives ?? [])]
                .filter((background) => background.id === scene?.backgroundId);
            const background = choices[0];
            if (choices.length !== 1 || !background)
                return "The reviewed title background association is required";
            const assets = inventory.assets.filter((asset) => asset.type === "background" && asset.id === background.id);
            if (scenes.length !== 1 || !scene || scene.id !== expected.id || scene.symbol !== expected.symbol
                || scene.resourcePath !== expected.resourcePath || scene._resourceType !== "scene" || scene.type !== "LOGO"
                || scene.actors.length !== 0 || scene.backgroundId !== background.id
                || ![expected.paletteIds, ...(expected.paletteAlternatives ?? [])]
                    .some((paletteIds) => JSON.stringify(scene.paletteIds) === JSON.stringify(paletteIds))
                || (scene.parallax !== undefined && (!Array.isArray(scene.parallax) || scene.parallax.length !== 0))
                || scene.parallaxLayers !== undefined || assets.length !== 1 || !assets[0].hasMetadata
                || assets[0].metadataPath !== background.metadataPath || assets[0].width !== background.width
                || assets[0].height !== background.height
                || resourceFiles.filter((file) => file.path === background.metadataPath && file.type === "background" && file.id === background.id).length !== 1) {
                return "The reviewed actor-free LOGO scene and title background/palette associations are required";
            }
            if ("preserveUiFromRow" in background) {
                const preserveUiFromRow = background.preserveUiFromRow;
                if (typeof preserveUiFromRow !== "number" || !Number.isInteger(preserveUiFromRow)) {
                    return "The reviewed title UI row binding must be an integer";
                }
                const asset = assets[0];
                if (asset.autoColor !== false || typeof asset.tileColors !== "string" || asset.tileColors.length === 0) {
                    return "Replacement title art requires explicit manual-color attributes including its reviewed startup rows";
                }
                try {
                    const width = background.width / 8, height = background.height / 8;
                    const cells = decodeResourceBytes(asset.tileColors, { maximumValues: width * height });
                    // These are compiler-preloaded background attributes. The exact
                    // native header supplies the visible menu's palette-7 strip later.
                    // Keep each reviewed startup strip uniform; mixed strips are invalid.
                    const uiValues = background.startupUiValues ?? [7];
                    if (cells.length !== width * height || !uiValues.some((value) => cells.every((cell, index) => index >= preserveUiFromRow * width ? cell === value : cell <= 6))) {
                        return "Replacement title attributes must match a reviewed startup strip and ordinary palette slots";
                    }
                }
                catch {
                    return "Replacement title attributes are not a complete native palette grid";
                }
            }
        }
        if (review.engineLocalReads) {
            const reason = nativeLocalOwnerReason(context, review.engineLocalReads, "The Crown frame hooks");
            if (reason)
                return reason;
        }
        if (review.crownPress) {
            const expected = review.crownPress;
            const core = inventory.scenes.find((scene) => scene.id === expected.sceneId)?.actors.find((actor) => actor.id === expected.coreId);
            const binding = review.rooms.find((room) => room.id === expected.sceneId)?.actors.find((actor) => actor.id === expected.coreId);
            const sprite = inventory.assets.find((asset) => asset.type === "sprite" && asset.id === expected.spriteId);
            const states = sprite?.states;
            if (binding?.slot !== expected.coreSlot || core?.spriteSheetId !== expected.spriteId || !sprite
                || sprite.canvasWidth !== 32 || sprite.canvasHeight !== 32 || !Array.isArray(states) || states.length !== 1
                || states[0]?.id !== expected.stateId || states[0]?.name !== "" || states[0]?.animationType !== "fixed"
                || states[0]?.flipLeft !== false || !Array.isArray(states[0]?.animations?.[0]?.frames)
                || states[0].animations[0].frames.length !== 11)
                return "The Crown core requires its reviewed sprite and eleven fixed frames";
        }
        if (review.crownMotion) {
            const expected = review.crownMotion;
            // Early motion publishes poses to both relays; the existing core check
            // above establishes the shared eleven-frame sprite layout.
            if (expected.spriteId !== review.crownPress?.spriteId || expected.stateId !== review.crownPress?.stateId) {
                return "The Crown relays require the reviewed core frame layout";
            }
            const room = review.rooms.find((room) => room.id === expected.sceneId);
            const scene = inventory.scenes.find((scene) => scene.id === expected.sceneId);
            for (const relay of expected.relays) {
                if (room?.actors.find((actor) => actor.id === relay.id)?.slot !== relay.slot
                    || scene?.actors.find((actor) => actor.id === relay.id)?.spriteSheetId !== expected.spriteId) {
                    return "The Crown relays require their reviewed physical slots and sprite association";
                }
            }
        }
        return undefined;
    }
    class Effects {
        resources = [];
        variables = new Map();
        access(ids, access) {
            for (const id of ids) {
                const previous = this.variables.get(id);
                this.variables.set(id, previous && previous !== access ? "read-write" : access);
            }
        }
        constructor(context) {
            // Native translation units and inline compiler alias registrations need
            // these definitions even when this particular operation never reads them.
            // They are structural compile/link dependencies, NOT runtime accesses.
            for (const variable of review.variables)
                this.resources.push({ kind: "resource", type: "variable",
                    id: variable.id, relation: "native-compile-symbol" });
            for (const room of review.rooms) {
                this.resources.push({ kind: "resource", type: "scene", id: room.id, relation: "native-room-symbol" });
                for (const actor of room.actors)
                    this.resources.push({ kind: "resource", type: "actor", id: actor.id,
                        sceneId: room.id, relation: "native-actor-slot" });
            }
            this.resources.push({ kind: "resource", type: "asset", id: review.sound.id, relation: "native-reward-sound" });
            for (const sprite of review.nativeSprites ?? [])
                this.resources.push({ kind: "resource", type: "asset",
                    id: sprite.id, relation: "native-compiled-sprite" });
            if (review.player)
                this.resources.push({ kind: "resource", type: "asset",
                    id: review.player.id, relation: "native-player-presentation" });
            for (const background of review.backgrounds ?? []) {
                // layoutReason has already accepted exactly one maintained association.
                const selectedId = context.inventory.scenes.find((scene) => scene.id === background.sceneId).backgroundId;
                this.resources.push({ kind: "resource", type: "asset", id: selectedId, relation: "native-door-background" });
            }
            for (const sound of review.extendedEvents?.sounds ?? [])
                this.resources.push({ kind: "resource", type: "asset",
                    id: sound.id, relation: "native-ceremony-sound" });
            for (const sound of review.warden?.sounds ?? [])
                this.resources.push({ kind: "resource", type: "asset",
                    id: sound.id, relation: "native-warden-sound" });
            // Frame hooks execute independently of an event's direct VM accesses.
            // Keep these verified dependencies distinct from operation read/write sets.
            for (const id of review.warden?.renderReads ?? [])
                this.resources.push({ kind: "resource", type: "variable",
                    id, relation: "native-engine-render-read" });
            for (const id of review.engineRenderReads ?? [])
                if (!review.warden?.renderReads.includes(id)) {
                    this.resources.push({ kind: "resource", type: "variable", id, relation: "native-engine-render-read" });
                }
            for (const id of review.combatContactReads ?? [])
                this.resources.push({ kind: "resource", type: "variable",
                    id, relation: "native-engine-contact-read" });
            if (review.engineLocalReads) {
                const owner = review.engineLocalReads;
                for (const [relation, ids] of [
                    ["native-engine-render-read", owner.render], ["native-engine-contact-read", owner.contact],
                ])
                    for (const id of ids)
                        this.resources.push({ kind: "resource", type: "variable", id,
                            ownerId: owner.actorId, sceneId: owner.sceneId, relation });
            }
            if (review.extendedEvents) {
                this.resources.push({ kind: "resource", type: "scene", id: review.extendedEvents.title.id, relation: "native-title-scene" });
                this.resources.push({ kind: "resource", type: "asset", id: context.inventory.scenes.find((scene) => scene.id === review.extendedEvents.title.id).backgroundId,
                    relation: "native-title-background" });
            }
        }
        result(childBranches = []) {
            return { status: "complete", childBranches, effects: [...this.resources,
                    ...[...this.variables].map(([id, access]) => ({ kind: "variable", id, access }))] };
        }
    }
    function actorSlot(input, context) {
        const room = review.rooms.find((item) => item.id === context.owner.sceneId);
        if (!room)
            return undefined;
        const id = input.actorId === "$self$"
            ? (context.owner.resourceType === "actor" ? context.owner.resourceId : undefined) : input.actorId;
        return typeof id === "string" ? room.actors.find((actor) => actor.id === id)?.slot : undefined;
    }
    function markerEffects(effects, marker, visible) {
        effects.access(["582"], "read"); // schema is checked even for an unused marker
        if (marker >= 16)
            return; // pinned table rows 16..31 have room=255
        const seen = String(575 + (marker >> 4)), collected = String(577 + (marker >> 4));
        effects.access([seen], "read-write");
        effects.access([collected], visible ? "read" : "read-write");
        if (visible)
            effects.access(SEEN, "read-write"); // dynamic cell; bounded union, not an observed cell
    }
    function modalEffects(effects, opening) {
        // Modal input may choose any page. These are possible accesses across its
        // branches, not a promise that every word is touched during a given call.
        effects.access([...MAP_WORDS, "8", "77", "88", "585", "586", "587", ...HUD_READS, ...(review.runtime?.modalReads ?? [])], "read");
        effects.access(["89"], "write");
        effects.access(["586"], "read-write");
        if (opening) {
            effects.access(["76"], "read");
            effects.access([...SEEN, ...VISITED, ...ROOM_WORDS, "580", "581"], "read-write");
        }
    }
    function extractCombat(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const effects = new Effects(context);
        const header = review.brakemawCaptureHeader;
        if (header && input.operation === header.operation) {
            const reason = brakemawCaptureHeaderReason(input, context, header);
            if (reason)
                return incomplete(reason);
            effects.access(header.writes, "write");
            const owner = review.brakemawGuards;
            effects.resources.push({ kind: "resource", type: "actor", id: owner.actorId,
                sceneId: owner.sceneId, relation: "actor" });
            // Admission may execute all captures natively; refusal executes the
            // original compiled children. Both possible paths retain dependencies.
            return effects.result(["fallback"]);
        }
        const operation = review.brakemawOperations && typeof input.operation === "string"
            && Object.hasOwn(review.brakemawOperations, input.operation)
            ? review.brakemawOperations[input.operation] : undefined;
        if (operation) {
            const owner = review.brakemawGuards;
            if (!owner)
                return incomplete("The Brakemaw operation requires its reviewed owner");
            if (Object.keys(input).some((key) => key !== "operation" && key !== "__comment")) {
                return incomplete("The Brakemaw operation accepts no arguments or child actions");
            }
            const reason = brakemawGuardReason(context, owner, operation.aliases, "EVENT_WRECKLIGHT_COMBAT");
            if (reason)
                return incomplete(reason);
            if (!operation.sites.includes(context.event?.id ?? "")) {
                return incomplete("The Brakemaw operation requires its original event ID");
            }
            effects.access(operation.reads, "read");
            effects.access(operation.writes, "write");
            // The player is compiler slot zero, not an inventory actor. The shared
            // player-presentation binding remains structural; the boss is an actor.
            if (operation.actor === "owner")
                effects.resources.push({ kind: "resource", type: "actor",
                    id: owner.actorId, sceneId: owner.sceneId, relation: "actor" });
            return effects.result();
        }
        switch (input.operation) {
            case "crownWaitTick": {
                const expected = review.crownCountdown;
                if (!expected)
                    return incomplete("The Crown countdown requires its opted-in source profile");
                if (!Number.isInteger(input.expectedPhase) || !Number.isInteger(input.maxFrames)
                    || !expected.pairs.some((pair) => pair.phase === input.expectedPhase && pair.maxFrames === input.maxFrames)) {
                    return incomplete("The Crown countdown requires one reviewed explicit integer phase/maximum pair");
                }
                const reason = crownCountdownReason(context, expected);
                if (reason)
                    return incomplete(reason);
                effects.access([...expected.reads, ...expected.locals.map((local) => local.local)], "read");
                if (Number(input.expectedPhase) >= 7)
                    effects.access(["97"], "read");
                // The live path decrements L5; cancellation writes maximum + 1.
                // Actor movement, captures and yielding remain authored events.
                effects.access(["L5"], "write");
                return effects.result();
            }
            case "grace":
                if (!review.combatGrace)
                    return incomplete("The combat operation is absent or outside the reviewed native dispatch");
                // A signed positive check may decrement this global; no child is compiled.
                effects.access(["9"], "read-write");
                return effects.result();
            case "hit":
            case "defeated": {
                const slot = actorSlot(input, context);
                if (!slot)
                    return incomplete("Combat requires an explicit, uniquely bound scene actor; fallback-to-self is not reviewed");
                // The compiled argument is a slot; native find_target also checks the
                // current scene. Do not assume a script owner's scene is runtime state.
                const targets = review.targets.filter((target) => target.slot === slot);
                effects.access(targets.map((target) => target.dead), "read");
                if (input.operation === "hit") {
                    effects.access(targets.flatMap((target) => target.hp ? [target.hp] : []), "read-write");
                    effects.access(targets.flatMap((target) => target.hitReadWrites ?? []), "read-write");
                    return effects.result(["false", "true"]);
                }
                if (targets.some((target) => target.armor !== 3)) {
                    effects.access(["585", "8", "587", "77"], "read");
                    effects.access(["588"], "read-write");
                }
                return effects.result();
            }
            case "entry":
                effects.access(review.runtime?.entryReads ?? [], "read");
                effects.access(review.targets.filter((target) => target.armor !== 3)
                    .flatMap((target) => [target.dead, ...(target.phase ? [target.phase] : [])]), "write");
                // entry calls loaded: equipment normalization reads the original ammo.
                effects.access(["585", "587"], "read");
                effects.access(["586"], "read-write");
                return effects.result();
            case "loaded":
                effects.access(["585", "587"], "read");
                effects.access(["586"], "read-write");
                return effects.result();
            case "newGame":
                effects.access(["585", "586", "587", "588"], "write");
                return effects.result();
            case "ready": return effects.result(); // private native flag only
            case "station":
                effects.access(["585"], "read");
                effects.access(["587"], "write");
                return effects.result();
            case "collect": {
                if (!Number.isInteger(input.rewardId) || Number(input.rewardId) < 0 || Number(input.rewardId) > 6) {
                    return incomplete("Only an explicit integer reward 0..6 is reviewed; editor defaults and Number coercion are not applied");
                }
                const reward = Number(input.rewardId);
                effects.access(["8"], "read");
                effects.access(review.runtime?.collectReads ?? [], "read");
                effects.access(["585"], "read-write");
                if (reward === 2)
                    effects.access(["587"], "write");
                else if (reward >= 3 && reward <= 5)
                    effects.access(["587"], "read-write");
                markerEffects(effects, reward + 9, false);
                return effects.result();
            }
            default: return incomplete("The combat operation is absent or outside the reviewed native dispatch");
        }
    }
    function directNativeOwnerReason(context, expected, command, label) {
        if (context.owner.resourceType !== "actor" || context.owner.resourceId !== expected.actorId
            || context.owner.sceneId !== expected.sceneId || context.owner.resourcePath !== expected.actorPath
            || context.owner.definitionPath !== undefined || context.event?.scriptKey !== "updateScript"
            || context.event.command !== command) {
            return `${label} requires its direct reviewed actor update owner`;
        }
        return nativeOwnerLayoutReason(context, expected, label);
    }
    function nativeOwnerLayoutReason(context, expected, label) {
        const scenes = context.inventory.scenes;
        if (scenes.some((scene) => scene._resourceType !== "scene" || typeof scene.type !== "string"
            || context.resourceFiles.filter((file) => file.type === "scene" && file.id === scene.id
                && file.path === scene.resourcePath).length !== 1)) {
            return `${label} requires actual compiler-visible scenes with string scene types`;
        }
        if (scenes.some((scene) => !Number.isSafeInteger(scene._index) || Number(scene._index) < 0)
            || new Set(scenes.map((scene) => scene._index)).size !== scenes.length
            || new Set(scenes.map((scene) => scene.id)).size !== scenes.length
            || new Set(scenes.map((scene) => scene.resourcePath)).size !== scenes.length) {
            return `${label} requires unique scene identities and explicit integer ordering`;
        }
        const disabled = context.inventory.settings.disabledSceneTypeIds ?? [];
        if (!Array.isArray(disabled) || disabled.some((type) => typeof type !== "string")) {
            return `${label} requires the reviewed compiler scene-type filtering`;
        }
        const compiledScenes = [...scenes].sort((a, b) => Number(a._index) - Number(b._index))
            .filter((scene) => expected.enabledSceneTypes.includes(String(scene.type)) && !disabled.includes(scene.type));
        if (compiledScenes.findIndex((scene) => scene.id === expected.sceneId) !== expected.sceneIndex) {
            return `${label} changed the compiled scene ordinal used by its local aliases`;
        }
        // getVariableAlias caches locals by entity ID, without a scene qualifier.
        const owners = context.resourceFiles.filter((file) => file.id === expected.actorId
            && ["scene", "actor", "trigger", "script"].includes(String(file.type)));
        if (owners.length !== 1 || owners[0].type !== "actor" || owners[0].path !== expected.actorPath) {
            return `${label} requires a unique compiler-visible local-variable owner`;
        }
        // layoutReason proves the whole actor cohort, its slice/filter order and
        // sprite inclusion. The bound variables resource fixes local names and
        // global aliases; ordinary edits to the update event tree stay editable.
        const actors = [...compiledScenes[expected.sceneIndex].actors]
            .sort((a, b) => Number(a._index) - Number(b._index));
        const entityIndex = actors.findIndex((actor) => actor.id === expected.actorId);
        if (entityIndex !== expected.entityIndex)
            return `${label} changed the compiled actor ordinal used by its local aliases`;
        return undefined;
    }
    function nativeLocalOwnerReason(context, expected, label) {
        const reason = nativeOwnerLayoutReason(context, expected, label);
        if (reason)
            return reason;
        if (expected.locals.some(({ local, alias }) => !/^L[0-5]$/.test(local)
            || alias !== `VAR_S${expected.sceneIndex}A${expected.entityIndex}_LOCAL_${local.slice(1)}`)
            || new Set(expected.locals.map(({ local }) => local)).size !== expected.locals.length
            || expected.globalAliases.some(({ id, alias }) => review.variables.filter((variable) => variable.id === id && variable.symbol.toUpperCase() === alias).length !== 1)) {
            return `${label} changed a reviewed local or global alias`;
        }
        return undefined;
    }
    function crownCountdownReason(context, expected) {
        const reason = directNativeOwnerReason(context, expected, "EVENT_WRECKLIGHT_COMBAT", "The Crown countdown");
        if (reason)
            return reason;
        if (expected.locals.length !== 6
            || ["L0", "L1", "L2", "L3", "L4", "L5"].some((local) => expected.locals.filter((entry) => entry.local === local).length !== 1)
            || expected.locals.some((entry) => entry.alias !== `VAR_${`S${expected.sceneIndex}A${expected.entityIndex}_${entry.localName}`
                .toUpperCase().replace(/[^A-Z0-9]/g, "_")}`)
            || expected.globalAliases.some(({ id, alias }) => review.variables.filter((variable) => variable.id === id && variable.symbol.toUpperCase() === alias).length !== 1)) {
            return "The Crown countdown changed an owning local or global alias";
        }
        return undefined;
    }
    function brakemawGuardReason(context, expected, aliases, command = "EVENT_WRECKLIGHT_ENEMY_CONDITION") {
        const reason = directNativeOwnerReason(context, expected, command, "The Brakemaw guard");
        if (reason)
            return reason;
        const slot = review.rooms.find((room) => room.id === expected.sceneId)?.actors
            .find((actor) => actor.id === expected.actorId)?.slot;
        if (slot !== expected.actorSlot || slot !== expected.entityIndex + 1
            || aliases.some(({ id, alias }) => /^L[0-5]$/.test(id)
                ? alias !== `VAR_S${expected.sceneIndex}A${expected.entityIndex}_LOCAL_${id.slice(1)}`
                : review.variables.filter((variable) => variable.id === id && variable.symbol.toUpperCase() === alias).length !== 1)) {
            return "The Brakemaw guard changed an owning slot or local/global alias";
        }
        return undefined;
    }
    const isObject = (value) => value !== null && typeof value === "object" && !Array.isArray(value);
    function brakemawCaptureHeaderReason(input, context, expected) {
        const owner = review.brakemawGuards;
        if (!owner)
            return "The Brakemaw capture header requires its reviewed owner";
        const reason = brakemawGuardReason(context, owner, expected.aliases, "EVENT_WRECKLIGHT_COMBAT");
        if (reason)
            return reason;
        if (!isDeepStrictEqual(input, { operation: expected.operation, fallback: expected.fallback })) {
            return "The Brakemaw capture header requires all seven original captures in order";
        }
        const actor = context.inventory.scenes.find((scene) => scene.id === owner.sceneId).actors
            .find((actor) => actor.id === owner.actorId);
        const life = Array.isArray(actor.updateScript) ? actor.updateScript[0] : undefined;
        const branch = isObject(life) && isObject(life.children) ? life.children.true : undefined;
        const event = Array.isArray(branch) ? branch[0] : undefined;
        if (context.event?.id !== expected.eventId
            || !isDeepStrictEqual(context.event.branchPath, [{ eventId: expected.lifeEventId, branch: "true", index: 0 }])
            || !isObject(life) || life.id !== expected.lifeEventId
            || life.command !== "EVENT_WRECKLIGHT_ENEMY_CONDITION" || !isObject(life.args)
            || life.args.kind !== "brakemawLife" || life.args.__comment
            || !isDeepStrictEqual(event, { id: expected.eventId, command: "EVENT_WRECKLIGHT_COMBAT",
                args: { operation: expected.operation }, children: { fallback: expected.fallback } })) {
            return "The Brakemaw capture header must be first under its original life predicate";
        }
        // Exact engine.json and variables.gbsres bindings establish field widths,
        // signed-byte conversions, local names and the global allocation guards.
        return undefined;
    }
    function fixedPhaseGuard(value, id, kind, trueCount, falseCount) {
        if (!isObject(value) || !isDeepStrictEqual(Object.keys(value).sort(), ["args", "children", "command", "id"])
            || value.id !== id || value.command !== "EVENT_WRECKLIGHT_ENEMY_CONDITION"
            || !isDeepStrictEqual(value.args, { kind }) || !isObject(value.children)
            || !isDeepStrictEqual(Object.keys(value.children).sort(), ["false", "true"])
            || !Array.isArray(value.children.true) || value.children.true.length !== trueCount
            || !Array.isArray(value.children.false) || value.children.false.length !== falseCount)
            return undefined;
        return { event: value, true: value.children.true, false: value.children.false };
    }
    function brakemawPhasePrefixReason(input, context, expected, prefix) {
        const owner = review.brakemawGuards;
        const actor = context.inventory.scenes.find((scene) => scene.id === owner.sceneId).actors
            .find((actor) => actor.id === owner.actorId);
        const update = actor.updateScript;
        if (!Array.isArray(update) || update.length !== 1)
            return "The Brakemaw phase prefix requires its original update root";
        const life = fixedPhaseGuard(update[0], expected.lifeEventId, "brakemawLife", 2, 0);
        const lt10 = life && fixedPhaseGuard(life.true[1], expected.lessThan10EventId, "brakemawPhaseLt10", 1, 1);
        const lt20 = lt10 && fixedPhaseGuard(lt10.false[0], expected.lessThan20EventId, "brakemawPhaseLt20", 1, 1);
        if (!lt20 || !isDeepStrictEqual(context.event?.branchPath, [
            { eventId: expected.lifeEventId, branch: "true", index: 0 },
            { eventId: expected.lessThan10EventId, branch: "false", index: 1 },
            { eventId: expected.lessThan20EventId, branch: prefix.branch, index: 0 },
        ]))
            return "The Brakemaw phase prefix requires its original outer phase gates";
        let event = lt20[prefix.branch][0];
        let first;
        for (let index = 0; index < prefix.phases.length; index++) {
            const node = fixedPhaseGuard(event, prefix.sites[index], `brakemawPhaseEq${prefix.phases[index]}`, 1, 1);
            if (!node)
                return "The Brakemaw phase prefix requires its complete original source span";
            if (index === 0)
                first = node;
            event = node.false[0];
        }
        if (!first || !isDeepStrictEqual(input, { kind: input.kind, true: first.true, false: first.false })) {
            return "The Brakemaw phase prefix input differs from its authored event";
        }
        const counts = new Map(prefix.sites.map((id) => [id, 0]));
        const visit = (value) => {
            if (Array.isArray(value)) {
                for (const item of value)
                    visit(item);
            }
            else if (isObject(value)) {
                if (typeof value.id === "string" && counts.has(value.id))
                    counts.set(value.id, counts.get(value.id) + 1);
                for (const item of Object.values(value))
                    visit(item);
            }
        };
        visit(update);
        if ([...counts.values()].some((count) => count !== 1))
            return "The Brakemaw phase prefix event identity must be unique";
        return undefined;
    }
    function brakemawCountdownReason(input, context, expected, entry) {
        const owner = review.brakemawGuards;
        const reason = brakemawGuardReason(context, owner, expected.aliases);
        if (reason)
            return reason;
        const actor = context.inventory.scenes.find((scene) => scene.id === owner.sceneId).actors
            .find((actor) => actor.id === owner.actorId);
        const update = actor.updateScript;
        if (!Array.isArray(update))
            return "The Brakemaw countdown requires its original owner update";
        const counts = new Map();
        let duplicate = false, source;
        const visit = (value, callback) => {
            if (Array.isArray(value)) {
                for (const child of value)
                    visit(child, callback);
            }
            else if (isObject(value)) {
                callback(value);
                for (const child of Object.values(value))
                    visit(child, callback);
            }
        };
        visit(entry.graph, (value) => {
            if (typeof value.id !== "string")
                return;
            if (counts.has(value.id))
                duplicate = true;
            counts.set(value.id, 0);
        });
        visit(update, (value) => {
            if (typeof value.id !== "string")
                return;
            if (counts.has(value.id))
                counts.set(value.id, counts.get(value.id) + 1);
            if (value.id === entry.eventId)
                source = value;
        });
        if (duplicate || [...counts.values()].some((count) => count !== 1)) {
            return "The Brakemaw countdown source identities must be unique";
        }
        // Join the graph walker's current invocation to the same node inspected by
        // the compiler, rather than accepting another occurrence or a stale path.
        if (!context.event || (entry.path && !isDeepStrictEqual(context.event.branchPath, entry.path))) {
            return "The Brakemaw countdown invocation has a different source path";
        }
        let current = update;
        for (const segment of context.event.branchPath) {
            const parent = Array.isArray(current) && Number.isSafeInteger(segment.index)
                && segment.index >= 0 ? current[segment.index] : undefined;
            if (!isObject(parent) || parent.id !== segment.eventId || !isObject(parent.children)) {
                return "The Brakemaw countdown invocation has a different source path";
            }
            current = parent.children[segment.branch];
        }
        if (context.event.id !== entry.eventId || entry.graph.id !== entry.eventId
            || !Array.isArray(current) || (entry.index === undefined ? !current.includes(source) : current[entry.index] !== source)
            || !isDeepStrictEqual(source, entry.graph) || !isObject(entry.graph.args) || !isObject(entry.graph.children)
            || !isDeepStrictEqual(input, { kind: entry.graph.args.kind,
                true: entry.graph.children.true, false: entry.graph.children.false })) {
            return "The Brakemaw countdown requires its complete original source graph";
        }
        return undefined;
    }
    function extractMap(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const effects = new Effects(context);
        switch (input.operation) {
            case "pause":
            case "map":
                modalEffects(effects, true);
                return effects.result();
            case "saved":
                effects.access(VERIFY_READS, "read");
                modalEffects(effects, false);
                return effects.result();
            case "verifySave":
                effects.access(VERIFY_READS, "read");
                return effects.result(["false", "true"]);
            case "saveReady":
            case "loadVerified":
            case "loadRejected": return effects.result(["false", "true"]);
            case "abort":
            case "loaded": return effects.result(); // controls/private flags, no VM-global write
            case "newGame":
                effects.access(review.runtime?.newGameWrites ?? range(223, 584), "write");
                return effects.result();
            case "visible":
            case "collected":
                if (!Number.isInteger(input.markerId) || Number(input.markerId) < 0 || Number(input.markerId) > 31) {
                    return incomplete("The map marker must be an explicit integer 0..31");
                }
                if (input.operation === "visible" && !actorSlot(input, context)) {
                    return incomplete("Visible marker requires an explicit actual scene actor; no helper fallback is allowed");
                }
                markerEffects(effects, Number(input.markerId), input.operation === "visible");
                return effects.result();
            default: return incomplete("The map operation is absent or outside the reviewed native dispatch");
        }
    }
    // The two current Drive handlers pass the owning actor's sampled local INDEXES
    // on the VM stack. Local reads stay L0..L4 here so the graph binds the actual
    // owner; the temporary stack result is not a write to one of those variables.
    function enemyOwnerReason(context, actorId) {
        const reason = layoutReason(context);
        if (reason)
            return reason;
        const sceneId = review.enemyScenes?.[actorId];
        const room = review.rooms.find((room) => sceneId ? room.id === sceneId : room.symbol === "scene_drive_hall");
        if (!room)
            return "The native enemy's reviewed owning scene is missing";
        const scene = context.inventory.scenes.find((scene) => scene.id === room.id);
        const actor = scene.actors.find((actor) => actor.id === actorId);
        if (context.owner.resourceType !== "actor" || context.owner.sceneId !== room.id
            || context.owner.resourceId !== actorId || context.owner.resourcePath !== actor?.resourcePath) {
            return "The native enemy handler requires its exact reviewed owning scene actor";
        }
        return undefined;
    }
    function extractEnemyCondition(input, context) {
        const guards = review.brakemawGuards;
        if (guards && typeof input.kind === "string" && Object.hasOwn(guards.kinds, input.kind)) {
            if ((input.true !== undefined && !Array.isArray(input.true))
                || (input.false !== undefined && !Array.isArray(input.false))
                || (input.__disableElse !== undefined && typeof input.__disableElse !== "boolean")) {
                return incomplete("The Brakemaw guard requires event arrays and a boolean else control");
            }
            const guard = guards.kinds[input.kind];
            const reason = layoutReason(context) ?? brakemawGuardReason(context, guards, guard.aliases);
            if (reason)
                return incomplete(reason);
            if (guard.sites && !guard.sites.includes(context.event?.id ?? "")) {
                return incomplete("The Brakemaw predicate requires its original countdown event ID");
            }
            const prefixes = review.brakemawPhasePrefixes;
            const prefix = prefixes && Object.hasOwn(prefixes.entries, input.kind) ? prefixes.entries[input.kind] : undefined;
            if (prefix && context.event?.id === prefix.sites[0]) {
                const reason = brakemawPhasePrefixReason(input, context, prefixes, prefix);
                if (reason)
                    return incomplete(reason);
            }
            const countdowns = review.brakemawCountdownBatches;
            const countdown = countdowns?.entries.find((entry) => entry.eventId === context.event?.id);
            if (countdown) {
                const reason = brakemawCountdownReason(input, context, countdowns, countdown);
                if (reason)
                    return incomplete(reason);
            }
            const continuations = review.brakemawContinuations;
            const continuation = continuations?.entries.find((entry) => entry.eventId === context.event?.id);
            if (continuation) {
                const reason = brakemawCountdownReason(input, context, continuations, continuation);
                if (reason)
                    return incomplete(reason);
            }
            const effects = new Effects(context);
            effects.access(guard.aliases.map(({ id }) => id), "read");
            if (countdown)
                effects.access(countdowns.aliases.map(({ id }) => id), "read-write");
            if (continuation)
                effects.access(continuations.aliases.map(({ id }) => id), "read-write");
            // The result word is temporary. Only the source-bound batches above add a
            // persistent timer write; ordinary predicates remain read-only.
            return effects.result(input.__disableElse ? ["true"] : ["false", "true"]);
        }
        let actor, reads;
        const sampled = ["L0", "L1", "L3", "L4"];
        switch (input.kind) {
            case "sentryKeep":
                actor = "drive_guard";
                reads = ["0", "59", "92", ...sampled];
                break;
            case "sentryCommitted":
                actor = "drive_guard";
                reads = ["0", "59", "92", "150", "182", ...sampled];
                break;
            case "sentryTell":
                actor = "drive_guard";
                reads = ["0", "59", "92", "150", "181", "182", ...sampled];
                break;
            case "sentryArm":
                actor = "drive_guard";
                reads = ["0", "1", "181", "L2"];
                break;
            case "sentryReady":
                actor = "drive_guard";
                reads = ["0", "1", "60", "61", "150", "181", "182", "183"];
                break;
            case "skimmerKeep":
                actor = "drive_skimmer";
                reads = ["0", "53", "92", ...sampled];
                break;
            case "skimmerCommitted":
                actor = "drive_skimmer";
                reads = ["0", "53", "92", "150", "185", ...sampled];
                break;
            case "skimmerTell":
                actor = "drive_skimmer";
                reads = ["0", "53", "92", "150", "184", "185", ...sampled];
                break;
            case "skimmerArm":
                actor = "drive_skimmer";
                reads = ["0", "1", "184", "L2"];
                break;
            default: return incomplete("The Drive predicate kind is absent or outside the reviewed native dispatch");
        }
        const reason = enemyOwnerReason(context, actor);
        if (reason)
            return incomplete(reason);
        const effects = new Effects(context);
        effects.access(reads, "read");
        return effects.result(["false", "true"]);
    }
    function extractEnemyTick(input, context) {
        let actor, reads, writes;
        switch (input.kind) {
            case "sentry":
                actor = "drive_guard";
                reads = ["0", "1", "59", "60", "61", "92", "150"];
                writes = ["62", "63", "181", "182", "183", "209"];
                break;
            case "skimmer":
                actor = "drive_skimmer";
                reads = ["0", "1", "53", "54", "92", "150"];
                writes = ["56", "57", "184", "185", "210"];
                break;
            default: return incomplete("The Drive controller kind is absent or outside the reviewed native dispatch");
        }
        const reason = enemyOwnerReason(context, actor);
        if (reason)
            return incomplete(reason);
        if (review.driveCaptures) {
            const operation = input.operation === undefined ? "tick" : input.operation;
            if (operation !== "tick") {
                const expected = review.driveCaptures;
                if (input.kind !== "skimmer" || typeof operation !== "string" || !expected.order.includes(operation)) {
                    return incomplete("The Drive sampling operation is outside its reviewed skimmer dispatch");
                }
                const captureReason = driveCaptureReason(context, operation, expected);
                if (captureReason)
                    return incomplete(captureReason);
                if (operation !== "tick_packed") {
                    if (input.true !== undefined && (!Array.isArray(input.true) || input.true.length !== 0)) {
                        return incomplete("Drive samples cannot own an external action branch");
                    }
                    const effects = new Effects(context);
                    if (operation === "sample_player")
                        effects.access(["0", "1"], "write");
                    else if (operation === "sample_skimmer") {
                        effects.access(["54", "55"], "write");
                        effects.resources.push({ kind: "resource", type: "actor", id: expected.actorId,
                            sceneId: expected.sceneId, relation: "actor" });
                    }
                    else
                        effects.access([expected.fields[operation].local], "write");
                    return effects.result();
                }
            }
        }
        const effects = new Effects(context);
        if (review.skimmerProwl && input.kind === "skimmer")
            reads.push("55");
        effects.access([...reads, "L0", "L1", "L2", "L3", "L4"], "read");
        effects.access(writes, "read-write");
        // Direction/frame changes address the compiled actor slot. The existing
        // all-room actor union remains conservative when runtime scene differs.
        // Projectile launch/shot count and yielding MoveTo are authored child code,
        // not hidden direct native effects, and only the true branch is compiled.
        return effects.result(["true"]);
    }
    function driveCaptureReason(context, operation, expected) {
        const isObject = (value) => value !== null && typeof value === "object" && !Array.isArray(value);
        const event = context.event;
        if (context.owner.resourceId !== expected.actorId || context.owner.sceneId !== expected.sceneId
            || context.owner.resourcePath !== expected.actorPath || context.owner.definitionPath !== undefined
            || event?.scriptKey !== "updateScript" || event.command !== "EVENT_WRECKLIGHT_ENEMY_TICK"
            || !Array.isArray(event.branchPath) || event.branchPath.length !== 1
            || event.branchPath[0]?.eventId !== expected.guardId || event.branchPath[0]?.branch !== "true"
            || event.branchPath[0]?.index !== 0) {
            return "Drive sampling requires the original dead guard in its direct actor update script";
        }
        const scene = context.inventory.scenes.find((scene) => scene.id === expected.sceneId);
        const actor = scene.actors.find((actor) => actor.id === expected.actorId);
        const guard = Array.isArray(actor.updateScript) ? actor.updateScript[0] : undefined;
        const branch = isObject(guard) && isObject(guard.children) ? guard.children.true : undefined;
        if (!isObject(guard) || guard.id !== expected.guardId || guard.command !== "EVENT_IF_EXPRESSION"
            || !isObject(guard.args) || guard.args.expression !== expected.guardExpression || guard.args.__comment
            || !Array.isArray(branch) || branch.length !== expected.order.length
            || branch.some((entry, index) => !isObject(entry) || typeof entry.id !== "string" || !entry.id
                || entry.command !== "EVENT_WRECKLIGHT_ENEMY_TICK" || !isObject(entry.args)
                || entry.args.kind !== "skimmer" || entry.args.operation !== expected.order[index] || entry.args.__comment)
            || new Set(branch.map((entry) => entry.id)).size !== branch.length
            || branch[expected.order.indexOf(operation)]?.id !== event.id) {
            return "Drive sampling must retain the original dead guard and eight-command sample order";
        }
        const scenes = context.inventory.scenes;
        if (scenes.some((scene) => scene._resourceType !== "scene" || typeof scene.type !== "string"
            || context.resourceFiles.filter((file) => file.type === "scene" && file.id === scene.id
                && file.path === scene.resourcePath).length !== 1)) {
            return "Drive sampling requires actual compiler-visible scenes with string scene types";
        }
        if (scenes.some((scene) => !Number.isSafeInteger(scene._index) || Number(scene._index) < 0)
            || new Set(scenes.map((scene) => scene._index)).size !== scenes.length
            || new Set(scenes.map((scene) => scene.id)).size !== scenes.length
            || new Set(scenes.map((scene) => scene.resourcePath)).size !== scenes.length) {
            return "Drive sampling requires unique scene identities and explicit nonnegative integer ordering";
        }
        const compiledScenes = [...scenes].sort((a, b) => Number(a._index) - Number(b._index))
            .filter((scene) => expected.enabledSceneTypes.includes(String(scene.type)));
        if (compiledScenes.findIndex((scene) => scene.id === expected.sceneId) !== expected.sceneIndex) {
            return "Drive sampling changed the compiled scene ordinal used by its local aliases";
        }
        const owners = context.resourceFiles.filter((file) => file.id === expected.actorId
            && ["scene", "actor", "trigger", "script"].includes(String(file.type)));
        if (owners.length !== 1 || owners[0].type !== "actor" || owners[0].path !== expected.actorPath) {
            return "Drive sampling requires a unique compiler-visible local-variable owner";
        }
        const actors = [...scene.actors].sort((a, b) => Number(a._index) - Number(b._index));
        const entityIndex = actors.findIndex((actor) => actor.id === expected.actorId);
        const fields = Object.values(expected.fields);
        // The exact engine.json and variables.gbsres bindings fix all five field
        // types, signed conversions, default local names and global aliases. Extra
        // engine/variable inputs are refused by the closed source profile. Check
        // every local here, as the compiler does even for a position-only sample.
        if (entityIndex !== expected.entityIndex || entityIndex + 1 !== expected.actorSlot || fields.length !== 5
            || ["L0", "L1", "L2", "L3", "L4"].some((local) => fields.filter((field) => field.local === local).length !== 1)
            || fields.some((field) => field.alias !== `VAR_${`S${expected.sceneIndex}A${entityIndex}_${field.localName}`
                .toUpperCase().replace(/[^A-Z0-9]/g, "_")}`)
            || expected.globalAliases.some(({ id, alias }) => review.variables.filter((variable) => variable.id === id && variable.symbol.toUpperCase() === alias).length !== 1)) {
            return "Drive sampling changed an owning local or sampled global alias";
        }
        return undefined;
    }
    function boundedNumber(value, first, last) {
        // These two handlers explicitly call Number; they do not receive editor
        // defaults. The immutable JSON input cannot supply executable coercions.
        try {
            const number = Number(value);
            return Number.isInteger(number) && number >= first && number <= last ? number : undefined;
        }
        catch {
            return undefined;
        }
    }
    function extractTitle(_input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const title = review.extendedEvents.title;
        if (context.owner.resourceType !== "scene" || context.owner.resourceId !== title.id
            || context.owner.sceneId !== title.id || context.owner.resourcePath !== title.resourcePath) {
            return incomplete("The title event requires its reviewed LOGO scene owner");
        }
        // Flags use JavaScript truthiness. Both branches compile regardless of the
        // flags; native choice stays on the stack. Load/reset belongs to children.
        return new Effects(context).result(["false", "true"]);
    }
    function extractAcquisition(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        if (boundedNumber(input.kind, 1, 17) === undefined)
            return incomplete("Acquisition requires an explicit reward kind 1..17");
        const sounds = review.extendedEvents.sounds;
        const references = input.references;
        // Extra discovery inputs are outside this maintained native asset closure.
        if (!Array.isArray(references) || references.length !== sounds.length
            || references.some((ref) => !ref || typeof ref !== "object" || Array.isArray(ref)
                || Object.keys(ref).some((key) => key !== "id" && key !== "type")
                || ref.type !== "sound" || !sounds.some((sound) => sound.id === ref.id))
            || sounds.some((sound) => references.filter((ref) => ref && typeof ref === "object"
                && !Array.isArray(ref) && ref.id === sound.id).length !== 1)) {
            return incomplete("Acquisition requires exactly its five reviewed sound references");
        }
        const effects = new Effects(context);
        effects.access(["8", "76", ...HUD_READS], "read");
        return effects.result(); // post-commit presentation, never a reward grant
    }
    function extractChamberPoll(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        if (boundedNumber(input.doorId, 51, 62) === undefined)
            return incomplete("Chamber polling requires an explicit door 51..62");
        const effects = new Effects(context);
        // The native call precedes the authored-ID comparison; do not narrow these
        // reads to a particular door. Pending-entry mutation is private, not VM state.
        effects.access(["8", "92", "59", "137"], "read");
        return effects.result(["false", "true"]);
    }
    function extractChamberVariables(_input, context) {
        const reason = layoutReason(context);
        return reason ? incomplete(reason) : new Effects(context).result();
    }
    const idleProfiles = {
        cargo_sentry: { room: 5, actor: "cargo_guard", slot: 5, reads: ["0", "65", "68", "92", "150"], phase: "69", writes: ["189", "190", "212"] },
        reactor_sentry: { room: 6, actor: "3fd19a9d-aa24-58ff-87b3-aa44b7f6960d", slot: 5,
            reads: ["92", "107", "110", "150", "155"], phase: "111", writes: ["195", "196", "197", "215"] },
        reactor_skimmer: { room: 6, actor: "be82ae00-8c09-53b3-bae0-887a6b3fc6d8", slot: 6,
            reads: ["92", "113", "116", "150", "155"], phase: "117", writes: ["198", "199", "216"] },
        lower_induction_sentinel: { room: 6, actor: "62cc5954-087c-57db-b5b7-054b83dd1660", slot: 10,
            reads: ["92", "150", "155", "166", "168"], phase: "167", writes: ["200", "201", "202", "217"] },
    };
    function extractIdle(input, context, cargo) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const profile = typeof input.profile === "string" && Object.hasOwn(idleProfiles, input.profile)
            ? idleProfiles[input.profile] : undefined;
        if (!profile || (profile.room === 5) !== cargo)
            return incomplete("The idle profile is absent or outside its reviewed dispatch");
        const room = review.rooms.find((room) => room.room === profile.room);
        const actor = context.inventory.scenes.find((scene) => scene.id === room.id).actors.find((actor) => actor.id === profile.actor);
        if (input.actorId !== profile.actor || actorSlot(input, context) !== profile.slot
            || context.owner.resourceType !== "actor" || context.owner.sceneId !== room.id
            || context.owner.resourceId !== profile.actor || context.owner.resourcePath !== actor?.resourcePath) {
            return incomplete("The idle handler requires its exact reviewed actor, native slot and owner");
        }
        const effects = new Effects(context);
        effects.access(profile.reads, "read");
        effects.access([profile.phase], "read-write");
        effects.access(profile.writes, "write");
        return effects.result(["false", "true"]);
    }
    function extractAirworksTick(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const expected = review.airworks;
        const profile = expected && typeof input.profile === "string" && Object.hasOwn(expected.profiles, input.profile)
            ? expected.profiles[input.profile] : undefined;
        if (!expected || !profile)
            return incomplete("The Airworks profile is absent or outside its reviewed dispatch");
        const actor = context.inventory.scenes.find((scene) => scene.id === expected.sceneId)
            ?.actors.find((actor) => actor.id === profile.actorId);
        if (input.actorId !== profile.actorId || actorSlot(input, context) !== profile.actorSlot
            || context.owner.resourceType !== "actor" || context.owner.sceneId !== expected.sceneId
            || context.owner.resourceId !== profile.actorId || context.owner.resourcePath !== actor?.resourcePath) {
            return incomplete("The Airworks handler requires its exact reviewed actor, native slot and owner");
        }
        const effects = new Effects(context);
        // Unlike the Drive tick, this call publishes the position/engine samples
        // itself before reading them. These are the owning actor's allocated locals,
        // not shared scratch. The action result stays on the six-word argument stack.
        const locals = ["L0", "L1", "L2", "L3", "L4"];
        effects.access([...profile.reads, ...locals], "read");
        effects.access([...profile.writes, ...locals], "write");
        // All continuations compile. Native dispatch can enter either movement,
        // then afterMove; the zero/unknown action skips all three. Movement, speed
        // and fresh post-yield death checks belong to the authored child events.
        return effects.result(["moveLeft", "moveRight", "afterMove"]);
    }
    function extractService(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        if (typeof input.panel !== "string" || !["service", "newGame", "saveError"].includes(input.panel))
            return incomplete("The service panel is absent or unreviewed");
        const effects = new Effects(context);
        if (input.panel !== "saveError")
            effects.access(["89"], "write");
        // Stock modal/menu loops render actors. The pinned actor patch records
        // visible markers: only the seen plane/marker word can change, no grants.
        effects.access(["582", "577"], "read");
        effects.access([...SEEN, "575"], "read-write");
        return effects.result();
    }
    function nativeActorReason(context, expected, command, scripts, label) {
        if (context.owner.resourceType !== "actor" || context.owner.resourceId !== expected.actorId
            || context.owner.resourcePath !== expected.actorPath || context.owner.sceneId !== expected.sceneId
            || context.owner.definitionPath !== undefined || context.event?.command !== command
            || !scripts.includes(context.event.scriptKey))
            return `${label} requires its direct reviewed actor script`;
        return nativeLocalOwnerReason(context, expected, label);
    }
    function paletteEffects(input, context, expected, owner, label) {
        if (input.paletteId !== expected.id || context.owner.resourceType !== "scene"
            || context.owner.resourceId !== owner.sceneId || context.owner.sceneId !== owner.sceneId
            || context.owner.resourcePath !== expected.scenePath || context.owner.definitionPath !== undefined
            || context.event?.scriptKey !== "script")
            return incomplete(`${label} requires its exact scene-start palette context`);
        const palettes = context.inventory.palettes.filter((palette) => palette.id === expected.id);
        const palette = palettes[0];
        if (palettes.length !== 1 || !palette || !Array.isArray(palette.colors) || palette.colors.length !== 4
            || palette.colors.some((color) => typeof color !== "string" || !/^[0-9a-f]{6}$/i.test(color))
            || context.resourceFiles.filter((file) => file.type === "palette" && file.id === expected.id
                && file.path === palette.resourcePath).length !== 1)
            return incomplete(`${label} requires one complete four-color palette`);
        const reason = nativeOwnerLayoutReason(context, owner, label);
        if (reason)
            return incomplete(reason);
        const effects = new Effects(context);
        effects.resources.push({ kind: "resource", type: "palette", id: expected.id, relation: "native-entry-palette" });
        return effects.result();
    }
    function nativeSpriteReason(context, owner, spriteId, frames, names) {
        const actor = context.inventory.scenes.find((scene) => scene.id === owner.sceneId)?.actors
            .find((entry) => entry.id === owner.actorId);
        const sprites = context.inventory.assets.filter((asset) => asset.id === spriteId && asset.type === "sprite");
        const sprite = sprites[0];
        const states = sprite?.states;
        if (actor?.spriteSheetId !== spriteId || sprites.length !== 1 || !sprite || sprite.canvasWidth !== 16 || sprite.canvasHeight !== 16
            || !Array.isArray(states) || states.length !== names.length
            || names.some((name) => states.filter((state) => state.name === name).length !== 1)
            || states.some((state) => state.animationType !== "fixed" || state.flipLeft !== false
                || !Array.isArray(state.animations) || !Array.isArray(state.animations[0]?.frames)
                || state.animations[0].frames.length !== frames)) {
            return "The native actor requires its reviewed sprite, directional states and frame layout";
        }
        return undefined;
    }
    function operationEffects(context, selected, owner) {
        const effects = new Effects(context);
        effects.access(selected.reads, "read");
        effects.access(selected.writes, "write");
        effects.resources.push({ kind: "resource", type: "actor", id: owner.actorId,
            sceneId: owner.sceneId, relation: "native-operation-actor" });
        return effects.result(selected.children);
    }
    function extractCargoCrawler(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const expected = review.cargoCrawler;
        if (!expected || input.actorId !== expected.actorId)
            return incomplete("The Cargo crawler requires its explicit actor");
        const spriteReason = nativeSpriteReason(context, expected, expected.spriteId, 16, [""]);
        if (spriteReason)
            return incomplete(spriteReason);
        if (input.operation === "palette_init")
            return paletteEffects(input, context, expected.palette, expected, "The Cargo crawler");
        if (typeof input.operation !== "string" || !Object.hasOwn(expected.operations, input.operation)) {
            return incomplete("The Cargo crawler operation is absent or unreviewed");
        }
        const ownerReason = nativeActorReason(context, expected, "EVENT_WRECKLIGHT_CARGO_CRAWLER", input.operation === "contact" ? ["script"]
            : input.operation === "hit" || input.operation === "pose" ? ["hit1Script"] : ["updateScript"], "The Cargo crawler");
        if (ownerReason)
            return incomplete(ownerReason);
        return operationEffects(context, expected.operations[input.operation], expected);
    }
    function extractReactorHunter(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const expected = review.reactorHunter;
        if (!expected)
            return incomplete("The Reactor hunter requires its opted-in source profile");
        const spriteReason = nativeSpriteReason(context, expected.hunter, expected.spriteId, 7, ["", "Left"]);
        if (spriteReason)
            return incomplete(spriteReason);
        if (input.operation === "palette_init")
            return paletteEffects(input, context, expected.palette, expected.hunter, "The Reactor hunter");
        if (typeof input.operation !== "string" || !Object.hasOwn(expected.operations, input.operation)) {
            return incomplete("The Reactor hunter operation is absent or unreviewed");
        }
        const owner = input.operation === "sentinel_claim" ? expected.sentinel : expected.hunter;
        if (input.actorId !== owner.actorId)
            return incomplete("The Reactor operation requires its explicit Hunter or Sentinel actor");
        for (const boundOwner of [expected.hunter, expected.sentinel]) {
            const reason = nativeLocalOwnerReason(context, boundOwner, "The Reactor hunter");
            if (reason)
                return incomplete(reason);
        }
        const scripts = input.operation === "hit_restore" ? ["hit1Script"]
            : input.operation === "present" ? ["startScript", "updateScript"] : ["updateScript"];
        const ownerReason = nativeActorReason(context, owner, "EVENT_WRECKLIGHT_REACTOR_HUNTER", scripts, "The Reactor hunter");
        if (ownerReason)
            return incomplete(ownerReason);
        return operationEffects(context, expected.operations[input.operation], owner);
    }
    function extractCrownPress(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const expected = review.crownPress;
        if (!expected || typeof input.operation !== "string" || !Object.hasOwn(expected.operations, input.operation)) {
            return incomplete("The Crown press operation is absent or unreviewed");
        }
        const ownerReason = nativeActorReason(context, expected, "EVENT_WRECKLIGHT_CROWN_PRESS", ["updateScript"], "The Crown press");
        if (ownerReason)
            return incomplete(ownerReason);
        const core = review.rooms.find((room) => room.id === expected.sceneId)?.actors.find((actor) => actor.id === expected.coreId);
        if (core?.slot !== expected.coreSlot)
            return incomplete("The Crown press requires its physical core actor");
        if (input.operation === "guard") {
            if (![7, 8, 9].includes(input.expectedPhase))
                return incomplete("The Crown press guard requires phase 7, 8 or 9");
        }
        else if (input.expectedPhase !== undefined || input.true !== undefined || input.false !== undefined) {
            return incomplete("Crown motion operations accept no phase or child branches");
        }
        const effects = operationEffects(context, expected.operations[input.operation], expected);
        if (effects.status === "complete")
            return { ...effects, effects: [...effects.effects,
                    { kind: "resource", type: "actor", id: expected.coreId, sceneId: expected.sceneId, relation: "native-moving-core" }] };
        return effects;
    }
    function extractCrownMotion(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const expected = review.crownMotion;
        if (!expected || typeof input.operation !== "string" || !Object.hasOwn(expected.operations, input.operation)
            || Object.keys(input).some((key) => key !== "operation" && key !== "__comment")) {
            return incomplete("The Crown early-motion operation is absent or unreviewed");
        }
        const ownerReason = nativeActorReason(context, expected, "EVENT_WRECKLIGHT_CROWN_MOTION", ["updateScript"], "The Crown early motion");
        if (ownerReason)
            return incomplete(ownerReason);
        const selected = expected.operations[input.operation];
        const effects = operationEffects(context, selected, expected);
        if (effects.status === "complete")
            return { ...effects, effects: [...effects.effects,
                    ...expected.relays.filter((relay) => selected.movingSlots.includes(relay.slot)).map((relay) => ({ kind: "resource", type: "actor", id: relay.id, sceneId: expected.sceneId, relation: "native-moving-relay" })),
                ] };
        return effects;
    }
    function extractWarden(input, context) {
        const reason = layoutReason(context);
        if (reason)
            return incomplete(reason);
        const expected = review.warden;
        const operation = input.operation;
        if (!expected || typeof operation !== "string" || !Object.hasOwn(expected.operations, operation)) {
            return incomplete("The Warden operation is absent or outside the reviewed operations");
        }
        const selected = expected.operations[operation];
        for (const key of selected.requiredChildren ?? []) {
            if (!Array.isArray(input[key]) || input[key].length === 0) {
                return incomplete(`The Warden committed action requires a nonempty authored child path: ${key}`);
            }
        }
        if (context.owner.sceneId !== expected.sceneId || (operation !== "init"
            && (context.owner.resourceType !== "actor" || context.owner.resourceId !== expected.actorId
                || context.owner.resourcePath !== expected.actorPath))) {
            return incomplete("The Warden operation requires its exact reviewed Deck scene and actor owner");
        }
        if ((operation === "sample_player" || operation === "sample_boss")
            && (context.event?.scriptKey !== "updateScript" || context.owner.definitionPath !== undefined)) {
            // Shared scripts retain the caller's graph context but are compiled and
            // cached separately. Only the direct actor-update context was reviewed.
            return incomplete("Warden position sampling requires its direct actor update script");
        }
        const captures = expected.captureBindings;
        const capture = captures && Object.hasOwn(captures.operations, operation) ? captures.operations[operation] : undefined;
        const packedTick = operation === "tick" && captures?.packTickArguments === true;
        const compositeTick = operation === "sample_and_tick" && captures?.sampleAndTick === true;
        if (operation === "sample_and_tick" && !compositeTick) {
            return incomplete("The Warden composite sampling operation requires its opted-in source profile");
        }
        const allCaptures = packedTick || compositeTick;
        const boundLocals = capture ? [capture] : allCaptures && captures ? Object.values(captures.operations) : [];
        if (captures && (capture || allCaptures)) {
            const bindingLabel = compositeTick ? "Warden composite sampling" : packedTick ? "Warden argument pack" : "Warden field sampling";
            if (allCaptures && (boundLocals.length !== 5
                || ["L0", "L1", "L2", "L3", "L4"].some((local) => !boundLocals.some((binding) => binding.local === local)))) {
                return incomplete("The Warden argument pack requires exactly the five owning local bindings");
            }
            if (context.event?.scriptKey !== "updateScript" || context.owner.definitionPath !== undefined
                || !Array.isArray(context.event.branchPath) || context.event.branchPath.length !== 0) {
                return incomplete(`${bindingLabel} requires the root of its direct actor update script`);
            }
            if (capture && wardenEventBranches.some((key) => input[key] !== undefined && !Array.isArray(input[key]))) {
                return incomplete(`${bindingLabel} has a malformed unused event branch`);
            }
            const scenes = context.inventory.scenes;
            // Inventory also recognizes scene.gbsres by filename, while the
            // compiler requires the resource discriminator. Such an inventory-only
            // entry must not pad the ordinal of the actual compiled scenes.
            if (scenes.some((scene) => scene._resourceType !== "scene" || typeof scene.type !== "string"
                || context.resourceFiles.filter((file) => file.type === "scene" && file.id === scene.id
                    && file.path === scene.resourcePath).length !== 1)) {
                return incomplete(`${bindingLabel} requires actual compiler-visible scenes with string scene types`);
            }
            // The compiler sorts loaded scenes, then removes disabled scene types.
            // Refuse coercions and ties instead of guessing its path-order fallback.
            if (scenes.some((scene) => !Number.isSafeInteger(scene._index) || Number(scene._index) < 0)
                || new Set(scenes.map((scene) => scene._index)).size !== scenes.length
                || new Set(scenes.map((scene) => scene.id)).size !== scenes.length
                || new Set(scenes.map((scene) => scene.resourcePath)).size !== scenes.length) {
                return incomplete(`${bindingLabel} requires unique scene identities and explicit nonnegative integer ordering`);
            }
            const compiledScenes = [...scenes].sort((a, b) => Number(a._index) - Number(b._index))
                .filter((scene) => captures.enabledSceneTypes.some((type) => type === scene.type));
            if (compiledScenes.findIndex((scene) => scene.id === expected.sceneId) !== captures.sceneIndex) {
                return incomplete(`${bindingLabel} changed the compiled scene ordinal used by its local aliases`);
            }
            // Local alias IDs use the entity ID without a scene qualifier. A second
            // owner could register an incompatible alias before this actor compiles.
            const owners = context.resourceFiles.filter((file) => file.id === expected.actorId
                && (file.type === "scene" || file.type === "actor" || file.type === "trigger" || file.type === "script"));
            if (owners.length !== 1 || owners[0].type !== "actor" || owners[0].path !== expected.actorPath) {
                return incomplete(`${bindingLabel} requires a unique compiler-visible local-variable owner`);
            }
            // layoutReason already proves the complete actor cohort and sprite
            // inclusion, so no actor is truncated or filtered from this ordering.
            const actors = [...compiledScenes[captures.sceneIndex].actors]
                .sort((a, b) => Number(a._index) - Number(b._index));
            const entityIndex = actors.findIndex((actor) => actor.id === expected.actorId);
            const aliasesMatch = boundLocals.every((binding) => {
                const alias = `VAR_${`S${captures.sceneIndex}A${entityIndex}_${binding.localName}`
                    .toUpperCase().replace(/[^A-Z0-9]/g, "_")}`;
                return alias === binding.alias;
            });
            // The exact bound variables file fixes the local names and excludes
            // global symbol collisions; inspection never runs the project compiler.
            if (entityIndex !== expected.actorSlot - 1 || !aliasesMatch) {
                return incomplete(`${bindingLabel} changed its owning local alias`);
            }
        }
        const effects = new Effects(context);
        effects.access([...selected.reads, ...selected.locals], "read");
        effects.access(selected.writes, "write");
        if (operation === "sample_boss" || compositeTick)
            effects.resources.push({ kind: "resource", type: "actor",
                id: expected.actorId, sceneId: expected.sceneId, relation: "actor" });
        return effects.result(selected.children);
    }
    const shared = {
        version,
        resolutionProfile: "gb-studio-4.3.2/project-event-exports/v1",
        compilerProfile: review.compiler,
        ...(review.compilerDependencies ? { compilerDependencies: review.compilerDependencies } : {}),
        closedDependencyPrefixes: ["plugins/", "assets/engine/"],
        closedResourceTypes: ["settings", "variables", "engineFieldValues"],
    };
    function contract(command, suffix, fields, extract) {
        const handler = review.project.find((binding) => binding.path.endsWith(suffix));
        if (!handler)
            throw new Error("Missing maintained Wrecklight handler binding");
        const id = `wrecklight-${command.slice("EVENT_WRECKLIGHT_".length).toLowerCase().replaceAll("_", "-")}${idSuffix}`;
        return { ...shared, id,
            command, handler, dependencies: review.project.filter((binding) => binding.path !== handler.path), fields, extract };
    }
    const contracts = [
        contract("EVENT_WRECKLIGHT_COMBAT", "/eventWrecklightCombat.js", [
            { key: "operation", type: "select", editorDefault: "hit" },
            ...(review.brakemawCaptureHeader ? [{ key: "fallback", type: "events" }] : []),
            ...(review.crownCountdown ? [
                { key: "expectedPhase", type: "number", editorDefault: 1 },
                { key: "maxFrames", type: "number", editorDefault: 32 },
            ] : []),
            { key: "actorId", type: "actor", editorDefault: "$self$" },
            { key: "rewardId", type: "number", editorDefault: 0 },
            { key: "true", type: "events" }, { key: "false", type: "events" },
        ], extractCombat),
        contract("EVENT_WRECKLIGHT_MAP", "/eventWrecklightMap.js", [
            { key: "operation", type: "select", editorDefault: "map" },
            { key: "markerId", type: "number", editorDefault: 0 },
            { key: "actorId", type: "actor", editorDefault: "$self$" },
            { key: "true", type: "events" }, { key: "false", type: "events" },
        ], extractMap),
        contract("EVENT_WRECKLIGHT_ENEMY_CONDITION", "/eventWrecklightEnemyCondition.js", [
            { key: "kind", type: "select", editorDefault: "sentryKeep" },
            ...(review.brakemawGuards ? [
                { key: "__disableElse", type: "checkbox" }, { key: "__collapseElse", type: "checkbox" },
                { key: "__label", type: "text" },
            ] : []),
            { key: "true", type: "events" }, { key: "false", type: "events" },
        ], extractEnemyCondition),
        contract("EVENT_WRECKLIGHT_ENEMY_TICK", "/eventWrecklightEnemyTick.js", [
            { key: "kind", type: "select", editorDefault: "sentry" },
            ...(review.driveCaptures ? [{ key: "operation", type: "select", editorDefault: "tick" }] : []),
            { key: "true", type: "events" },
        ], extractEnemyTick),
    ];
    if (review.extendedEvents)
        contracts.push(contract("EVENT_WRECKLIGHT_TITLE", "/eventWrecklightTitle.js", [
            { key: "hasSave", type: "checkbox", editorDefault: false }, { key: "loadRejected", type: "checkbox", editorDefault: false },
            { key: "true", type: "events" }, { key: "false", type: "events" },
        ], extractTitle), contract("EVENT_WRECKLIGHT_ACQUISITION", "/eventWrecklightAcquisition.js", [
            { key: "kind", type: "select", editorDefault: 1 }, { key: "references", type: "references" },
        ], extractAcquisition), contract("EVENT_WRECKLIGHT_CHAMBER_POLL", "/eventWrecklightChamberPoll.js", [
            { key: "doorId", type: "number", editorDefault: 51 }, { key: "true", type: "events" }, { key: "false", type: "events" },
        ], extractChamberPoll), contract("EVENT_WRECKLIGHT_CHAMBER_VARIABLES", "/eventWrecklightChamberVariables.js", [], extractChamberVariables), ...["CARGO", "REACTOR"].map((family) => contract(`EVENT_WRECKLIGHT_${family}_IDLE`, `/eventWrecklight${family === "CARGO" ? "Cargo" : "Reactor"}Idle.js`, [
            { key: "profile", type: "select" }, { key: "actorId", type: "actor", editorDefault: "$self$" },
            { key: "true", type: "events" }, { key: "false", type: "events" },
        ], (input, context) => extractIdle(input, context, family === "CARGO"))), contract("EVENT_WRECKLIGHT_SERVICE_UI", "/eventWrecklightService.js", [{ key: "panel", type: "select", editorDefault: "service" }], extractService));
    if (review.warden)
        contracts.push(contract("EVENT_WRECKLIGHT_WARDEN", "/eventWrecklightWarden.js", [
            { key: "operation", type: "select", editorDefault: "tick" },
            ...wardenEventBranches.map((key) => ({ key, type: "events" })),
        ], extractWarden));
    if (review.airworks)
        contracts.push(contract("EVENT_WRECKLIGHT_AIRWORKS_TICK", "/eventWrecklightAirworksTick.js", [
            { key: "profile", type: "select", editorDefault: "bellows" },
            { key: "actorId", type: "actor", editorDefault: "$self$" },
            { key: "moveLeft", type: "events" }, { key: "moveRight", type: "events" }, { key: "afterMove", type: "events" },
        ], extractAirworksTick));
    if (review.cargoCrawler)
        contracts.push(contract("EVENT_WRECKLIGHT_CARGO_CRAWLER", "/eventWrecklightCargoCrawler.js", [
            { key: "operation", type: "select", editorDefault: "tick" },
            { key: "actorId", type: "actor", editorDefault: "$self$" },
            { key: "paletteId", type: "palette", editorDefault: review.cargoCrawler.palette.id },
            { key: "lunge", type: "events" },
        ], extractCargoCrawler));
    if (review.reactorHunter)
        contracts.push(contract("EVENT_WRECKLIGHT_REACTOR_HUNTER", "/eventWrecklightReactorHunter.js", [
            { key: "operation", type: "select", editorDefault: "tick" },
            { key: "actorId", type: "actor", editorDefault: "$self$" },
            { key: "paletteId", type: "palette", editorDefault: review.reactorHunter.palette.id },
            ...review.reactorHunter.operations.tick.children.map((key) => ({ key, type: "events" })),
        ], extractReactorHunter));
    if (review.crownPress)
        contracts.push(contract("EVENT_WRECKLIGHT_CROWN_PRESS", "/eventWrecklightCrownPress.js", [
            { key: "operation", type: "select", editorDefault: "tick" },
            { key: "expectedPhase", type: "number", editorDefault: 7 },
            { key: "true", type: "events" }, { key: "false", type: "events" },
        ], extractCrownPress));
    if (review.crownMotion)
        contracts.push(contract("EVENT_WRECKLIGHT_CROWN_MOTION", "/eventWrecklightCrownMotion.js", [
            { key: "operation", type: "select", editorDefault: "tick" },
        ], extractCrownMotion));
    return contracts;
}
// r06 changes drawing/release order without changing native13's effect model.
// r31 separately binds its expanded map state, room/actor associations and combat
// effects. Share extractor logic, never alternative hashes or profile state.
const remixRemovedBindings = new Set(WRECKLIGHT_REMIX_SOURCE_REVIEW.removedProjectBindings);
export const WRECKLIGHT_REMIX_REVIEW = {
    ...WRECKLIGHT_CHAMBERS_REVIEW,
    project: [
        ...WRECKLIGHT_CHAMBERS_REVIEW.project.filter((binding) => !remixRemovedBindings.has(binding.path))
            .map((binding) => WRECKLIGHT_REMIX_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
        ...WRECKLIGHT_REMIX_SOURCE_REVIEW.additions,
    ],
    fixedRemixDescriptor: WRECKLIGHT_REMIX_SOURCE_REVIEW.fixedDescriptor,
    variables: [...WRECKLIGHT_CHAMBERS_REVIEW.variables, ...WRECKLIGHT_REMIX_SOURCE_REVIEW.additionalVariables],
    airworks: WRECKLIGHT_REMIX_SOURCE_REVIEW.airworks,
};
export const WRECKLIGHT_PERFORMANCE_REVIEW = {
    ...WRECKLIGHT_REMIX_REVIEW,
    project: WRECKLIGHT_REMIX_REVIEW.project.map((binding) => WRECKLIGHT_PERFORMANCE_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    combatGrace: true,
};
export const WRECKLIGHT_BUSYROOM_REVIEW = {
    ...WRECKLIGHT_PERFORMANCE_REVIEW,
    project: WRECKLIGHT_PERFORMANCE_REVIEW.project.map((binding) => WRECKLIGHT_BUSYROOM_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_BUSYROOM_SOURCE_REVIEW.fixedDescriptor,
};
export const WRECKLIGHT_PACING_REVIEW = {
    ...WRECKLIGHT_BUSYROOM_REVIEW,
    compilerDependencies: [
        ...WRECKLIGHT_BUSYROOM_REVIEW.compilerDependencies,
        ...WRECKLIGHT_PACING_SOURCE_REVIEW.compilerAdditions,
    ],
    project: [
        ...WRECKLIGHT_BUSYROOM_REVIEW.project.map((binding) => WRECKLIGHT_PACING_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
        ...WRECKLIGHT_PACING_SOURCE_REVIEW.additions,
    ],
    fixedRemixDescriptor: WRECKLIGHT_PACING_SOURCE_REVIEW.fixedDescriptor,
};
// Preserve the owner's semantic associations; only the reviewed Airworks and
// grace callbacks extend them. This is one complete source set, not hash alternatives.
const combinedRemovedBindings = new Set(WRECKLIGHT_COMBINED_SOURCE_REVIEW.removedProjectBindings);
export const WRECKLIGHT_COMBINED_REVIEW = {
    ...WRECKLIGHT_SEP17_REVIEW,
    project: [
        ...WRECKLIGHT_SEP17_REVIEW.project.filter((binding) => !combinedRemovedBindings.has(binding.path))
            .map((binding) => WRECKLIGHT_COMBINED_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
        ...WRECKLIGHT_COMBINED_SOURCE_REVIEW.additions,
    ],
    compilerDependencies: [
        ...WRECKLIGHT_SEP17_REVIEW.compilerDependencies,
        ...WRECKLIGHT_PACING_SOURCE_REVIEW.compilerAdditions,
    ],
    variables: [...WRECKLIGHT_SEP17_REVIEW.variables, ...WRECKLIGHT_REMIX_SOURCE_REVIEW.additionalVariables],
    airworks: WRECKLIGHT_REMIX_SOURCE_REVIEW.airworks,
    combatGrace: true,
    fixedRemixDescriptor: WRECKLIGHT_COMBINED_SOURCE_REVIEW.fixedDescriptor,
};
// The payoff keeps the combined native effects and structural associations.
// Source variants differ only in the exact inactive backup omitted by the sample.
export const WRECKLIGHT_PAYOFF_REVIEW = {
    ...WRECKLIGHT_COMBINED_REVIEW,
    project: WRECKLIGHT_COMBINED_REVIEW.project.map((binding) => WRECKLIGHT_PAYOFF_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_PAYOFF_SOURCE_REVIEW.fixedDescriptor,
};
const payoffCuratedOmittedBindings = new Set(WRECKLIGHT_PAYOFF_SOURCE_REVIEW.curatedOmittedBindings);
export const WRECKLIGHT_PAYOFF_CURATED_REVIEW = {
    ...WRECKLIGHT_PAYOFF_REVIEW,
    project: WRECKLIGHT_PAYOFF_REVIEW.project.filter((binding) => !payoffCuratedOmittedBindings.has(binding.path)),
};
// Position capture remains in the actor update's original VM slots. The two
// converters write only their named outputs; engine-render reads stay separate.
export const WRECKLIGHT_OVERLAY_REVIEW = {
    ...WRECKLIGHT_PAYOFF_REVIEW,
    project: WRECKLIGHT_PAYOFF_REVIEW.project.map((binding) => WRECKLIGHT_OVERLAY_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    compilerDependencies: [
        ...WRECKLIGHT_PAYOFF_REVIEW.compilerDependencies,
        ...WRECKLIGHT_OVERLAY_SOURCE_REVIEW.compilerAdditions,
    ],
    warden: {
        ...WRECKLIGHT_PAYOFF_REVIEW.warden,
        operations: {
            ...WRECKLIGHT_PAYOFF_REVIEW.warden.operations,
            sample_player: { reads: [], writes: ["0", "1"], locals: [], children: [] },
            sample_boss: { reads: [], writes: ["60", "61"], locals: [], children: [] },
        },
    },
    fixedRemixDescriptor: WRECKLIGHT_OVERLAY_SOURCE_REVIEW.fixedDescriptor,
};
const overlayCuratedOmittedBindings = new Set(WRECKLIGHT_OVERLAY_SOURCE_REVIEW.curatedOmittedBindings);
export const WRECKLIGHT_OVERLAY_CURATED_REVIEW = {
    ...WRECKLIGHT_OVERLAY_REVIEW,
    project: WRECKLIGHT_OVERLAY_REVIEW.project.filter((binding) => !overlayCuratedOmittedBindings.has(binding.path)),
};
// Preserve each engine-field read at its original VM command boundary. The
// native callbacks write only the one owning local described by each capture.
export const WRECKLIGHT_CAPTURE_REVIEW = {
    ...WRECKLIGHT_OVERLAY_REVIEW,
    project: WRECKLIGHT_OVERLAY_REVIEW.project.map((binding) => WRECKLIGHT_CAPTURE_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    warden: {
        ...WRECKLIGHT_OVERLAY_REVIEW.warden,
        captureBindings: WRECKLIGHT_CAPTURE_SOURCE_REVIEW.captureBindings,
        operations: {
            ...WRECKLIGHT_OVERLAY_REVIEW.warden.operations,
            sample_scroll_x: { reads: [], writes: ["L0"], locals: [], children: [] },
            sample_scroll_y: { reads: [], writes: ["L1"], locals: [], children: [] },
            sample_grounded: { reads: [], writes: ["L2"], locals: [], children: [] },
            sample_hud: { reads: [], writes: ["L3"], locals: [], children: [] },
            sample_death: { reads: [], writes: ["L4"], locals: [], children: [] },
        },
    },
    fixedRemixDescriptor: WRECKLIGHT_CAPTURE_SOURCE_REVIEW.fixedDescriptor,
};
const captureCuratedOmittedBindings = new Set(WRECKLIGHT_CAPTURE_SOURCE_REVIEW.curatedOmittedBindings);
export const WRECKLIGHT_CAPTURE_CURATED_REVIEW = {
    ...WRECKLIGHT_CAPTURE_REVIEW,
    project: WRECKLIGHT_CAPTURE_REVIEW.project.filter((binding) => !captureCuratedOmittedBindings.has(binding.path)),
};
// Renderer-only changes keep the exact capture callbacks, packed tick bindings
// and semantic associations. Partial source transfers match neither profile.
export const WRECKLIGHT_RENDER_REVIEW = {
    ...WRECKLIGHT_CAPTURE_REVIEW,
    project: WRECKLIGHT_CAPTURE_REVIEW.project.map((binding) => WRECKLIGHT_RENDER_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_RENDER_SOURCE_REVIEW.fixedDescriptor,
};
const renderCuratedOmittedBindings = new Set(WRECKLIGHT_RENDER_SOURCE_REVIEW.curatedOmittedBindings);
export const WRECKLIGHT_RENDER_CURATED_REVIEW = {
    ...WRECKLIGHT_RENDER_REVIEW,
    project: WRECKLIGHT_RENDER_REVIEW.project.filter((binding) => !renderCuratedOmittedBindings.has(binding.path)),
};
export const WRECKLIGHT_SCROLL_REVIEW = {
    ...WRECKLIGHT_RENDER_REVIEW,
    project: WRECKLIGHT_RENDER_REVIEW.project.map((binding) => WRECKLIGHT_SCROLL_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_SCROLL_SOURCE_REVIEW.fixedDescriptor,
};
const scrollCuratedOmittedBindings = new Set(WRECKLIGHT_SCROLL_SOURCE_REVIEW.curatedOmittedBindings);
export const WRECKLIGHT_SCROLL_CURATED_REVIEW = {
    ...WRECKLIGHT_SCROLL_REVIEW,
    project: WRECKLIGHT_SCROLL_REVIEW.project.filter((binding) => !scrollCuratedOmittedBindings.has(binding.path)),
};
// A single event owns the budgeted sampling prefix and separate native tick.
// Keep the older operations and profiles unchanged for existing authored games.
export const WRECKLIGHT_SAMPLING_REVIEW = {
    ...WRECKLIGHT_SCROLL_REVIEW,
    project: WRECKLIGHT_SCROLL_REVIEW.project.map((binding) => WRECKLIGHT_SAMPLING_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_SAMPLING_SOURCE_REVIEW.fixedDescriptor,
    warden: {
        ...WRECKLIGHT_SCROLL_REVIEW.warden,
        captureBindings: {
            ...WRECKLIGHT_SCROLL_REVIEW.warden.captureBindings,
            sampleAndTick: true,
        },
        operations: {
            ...WRECKLIGHT_SCROLL_REVIEW.warden.operations,
            sample_and_tick: {
                ...WRECKLIGHT_SCROLL_REVIEW.warden.operations.tick,
                writes: [
                    ...WRECKLIGHT_SCROLL_REVIEW.warden.operations.tick.writes,
                    ...WRECKLIGHT_SCROLL_REVIEW.warden.operations.sample_player.writes,
                    ...WRECKLIGHT_SCROLL_REVIEW.warden.operations.sample_boss.writes,
                    "L0", "L1", "L2", "L3", "L4",
                ],
            },
        },
    },
};
const samplingCuratedOmittedBindings = new Set(WRECKLIGHT_SAMPLING_SOURCE_REVIEW.curatedOmittedBindings);
export const WRECKLIGHT_SAMPLING_CURATED_REVIEW = {
    ...WRECKLIGHT_SAMPLING_REVIEW,
    project: WRECKLIGHT_SAMPLING_REVIEW.project.filter((binding) => !samplingCuratedOmittedBindings.has(binding.path)),
};
// Chamber caching changes only the exact C binding and save marker.
// The complete sampling contract and all historical profiles stay intact.
export const CHAMBER_CACHE_NATIVE = {
    ...WRECKLIGHT_SAMPLING_REVIEW,
    project: WRECKLIGHT_SAMPLING_REVIEW.project.map((binding) => WRECKLIGHT_CHAMBER_CACHE_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_CHAMBER_CACHE_SOURCE_REVIEW.fixedDescriptor,
};
const chamberCacheCuratedOmittedBindings = new Set(WRECKLIGHT_CHAMBER_CACHE_SOURCE_REVIEW.curatedOmittedBindings);
export const CHAMBER_CACHE_CURATED = {
    ...CHAMBER_CACHE_NATIVE,
    project: CHAMBER_CACHE_NATIVE.project.filter((binding) => !chamberCacheCuratedOmittedBindings.has(binding.path)),
};
// Bind the combined compiler override and projectile renderer with their own
// native save marker, directly preserving the released chamber-cache contract.
export const FLAT_PROJECTILE_NATIVE = {
    ...CHAMBER_CACHE_NATIVE,
    project: CHAMBER_CACHE_NATIVE.project.map((binding) => WRECKLIGHT_FLAT_PROJECTILE_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_FLAT_PROJECTILE_SOURCE_REVIEW.fixedDescriptor,
};
export const FLAT_PROJECTILE_CURATED = {
    ...CHAMBER_CACHE_CURATED,
    project: CHAMBER_CACHE_CURATED.project.map((binding) => WRECKLIGHT_FLAT_PROJECTILE_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_FLAT_PROJECTILE_SOURCE_REVIEW.fixedDescriptor,
};
function drivePerformanceBindings(base) {
    const replacements = WRECKLIGHT_DRIVE_PERFORMANCE_SOURCE_REVIEW.replacements;
    return [...base.map((binding) => replacements.find((next) => next.path === binding.path) ?? binding),
        // Earlier profiles did not freeze this actor resource. This successor does
        // because the compiler's sample-order guard reads its complete update tree.
        ...replacements.filter((next) => !base.some((binding) => binding.path === next.path))];
}
export const DRIVE_PERFORMANCE_NATIVE = {
    ...FLAT_PROJECTILE_NATIVE,
    project: drivePerformanceBindings(FLAT_PROJECTILE_NATIVE.project),
    variables: [...FLAT_PROJECTILE_NATIVE.variables, ...WRECKLIGHT_DRIVE_PERFORMANCE_SOURCE_REVIEW.additionalVariables],
    fixedRemixDescriptor: WRECKLIGHT_DRIVE_PERFORMANCE_SOURCE_REVIEW.fixedDescriptor,
    driveCaptures: WRECKLIGHT_DRIVE_PERFORMANCE_SOURCE_REVIEW.captureBindings,
};
export const DRIVE_PERFORMANCE_CURATED = {
    ...FLAT_PROJECTILE_CURATED,
    project: drivePerformanceBindings(FLAT_PROJECTILE_CURATED.project),
    variables: DRIVE_PERFORMANCE_NATIVE.variables,
    fixedRemixDescriptor: WRECKLIGHT_DRIVE_PERFORMANCE_SOURCE_REVIEW.fixedDescriptor,
    driveCaptures: WRECKLIGHT_DRIVE_PERFORMANCE_SOURCE_REVIEW.captureBindings,
};
function bossThreePhaseBindings(base) {
    const source = WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW;
    return [...base.map((binding) => source.replacements.find((next) => next.path === binding.path) ?? binding),
        ...source.additions];
}
// The boss source adds committed Warden actions and changes the synchronous
// combat predicates. Keep those semantics separate from released Drive games.
export const BOSS_THREE_PHASE_NATIVE = {
    ...DRIVE_PERFORMANCE_NATIVE,
    project: bossThreePhaseBindings(DRIVE_PERFORMANCE_NATIVE.project),
    variables: [...DRIVE_PERFORMANCE_NATIVE.variables, ...WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.additionalVariables],
    fixedRemixDescriptor: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.fixedDescriptor,
    targets: DRIVE_PERFORMANCE_NATIVE.targets.map((target) => target.room === 9 && target.slot === 5
        ? { ...target, hitReadWrites: ["141"] }
        : target.room === 11 && target.slot === 7 ? { ...target, dead: "98" } : target),
    combatContactReads: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.combatContactReads,
    crownCountdown: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.crownCountdown,
    brakemawGuards: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.brakemawGuards,
    nativeSprites: [...DRIVE_PERFORMANCE_NATIVE.nativeSprites, WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.warden.sprite],
    warden: {
        ...DRIVE_PERFORMANCE_NATIVE.warden,
        spriteId: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.warden.sprite.id,
        stateId: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.warden.stateId,
        frameCount: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.warden.frameCount,
        operations: {
            ...DRIVE_PERFORMANCE_NATIVE.warden.operations,
            tick: {
                ...DRIVE_PERFORMANCE_NATIVE.warden.operations.tick,
                children: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.warden.requiredChildren,
                requiredChildren: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.warden.requiredChildren,
            },
            sample_and_tick: {
                ...DRIVE_PERFORMANCE_NATIVE.warden.operations.sample_and_tick,
                children: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.warden.requiredChildren,
                requiredChildren: WRECKLIGHT_BOSS_THREE_PHASE_SOURCE_REVIEW.warden.requiredChildren,
            },
        },
    },
};
export const BOSS_THREE_PHASE_CURATED = {
    ...BOSS_THREE_PHASE_NATIVE,
    project: bossThreePhaseBindings(DRIVE_PERFORMANCE_CURATED.project),
};
function bossCueBindings(base) {
    const replacements = WRECKLIGHT_BOSS_CUE_SOURCE_REVIEW.replacements;
    return [...base.map((binding) => replacements.find((next) => next.path === binding.path) ?? binding),
        // Freeze the accepted six sites as well as their C and event handler.
        ...replacements.filter((next) => !base.some((binding) => binding.path === next.path))];
}
export const BOSS_CUE_NATIVE = {
    ...BOSS_THREE_PHASE_NATIVE,
    project: bossCueBindings(BOSS_THREE_PHASE_NATIVE.project),
    fixedRemixDescriptor: WRECKLIGHT_BOSS_CUE_SOURCE_REVIEW.fixedDescriptor,
    brakemawGuards: {
        ...BOSS_THREE_PHASE_NATIVE.brakemawGuards,
        kinds: { ...BOSS_THREE_PHASE_NATIVE.brakemawGuards.kinds, ...WRECKLIGHT_BOSS_CUE_SOURCE_REVIEW.kinds },
    },
};
export const BOSS_CUE_CURATED = {
    ...BOSS_CUE_NATIVE,
    project: bossCueBindings(BOSS_THREE_PHASE_CURATED.project),
};
function bossLoopBindings(base) {
    const source = WRECKLIGHT_BOSS_LOOP_SOURCE_REVIEW;
    return [...base.map((binding) => source.replacements.find((next) => next.path === binding.path) ?? binding),
        ...source.additions];
}
// This separately selected source profile describes the prospective combined
// loop. It does not replace the released cue profile or imply native acceptance.
export const BOSS_LOOP_NATIVE = {
    ...BOSS_CUE_NATIVE,
    project: bossLoopBindings(BOSS_CUE_NATIVE.project),
    fixedRemixDescriptor: WRECKLIGHT_BOSS_LOOP_SOURCE_REVIEW.fixedDescriptor,
    brakemawGuards: {
        ...BOSS_CUE_NATIVE.brakemawGuards,
        kinds: { ...BOSS_CUE_NATIVE.brakemawGuards.kinds, ...WRECKLIGHT_BOSS_LOOP_SOURCE_REVIEW.kinds },
    },
    brakemawOperations: WRECKLIGHT_BOSS_LOOP_SOURCE_REVIEW.operations,
};
export const BOSS_LOOP_CURATED = {
    ...BOSS_LOOP_NATIVE,
    project: bossLoopBindings(BOSS_CUE_CURATED.project),
};
function bossCapturePrefixBindings(base) {
    return base.map((binding) => WRECKLIGHT_BOSS_CAPTURE_PREFIX_SOURCE_REVIEW.replacements
        .find((next) => next.path === binding.path) ?? binding);
}
// Additive implementation preparation: earlier loop/cue contracts keep their
// exact source identities. This profile makes no runtime acceptance claim.
export const BOSS_CAPTURE_PREFIX_NATIVE = {
    ...BOSS_LOOP_NATIVE,
    project: bossCapturePrefixBindings(BOSS_LOOP_NATIVE.project),
    variables: [...BOSS_LOOP_NATIVE.variables, ...WRECKLIGHT_BOSS_CAPTURE_PREFIX_SOURCE_REVIEW.additionalVariables],
    fixedRemixDescriptor: WRECKLIGHT_BOSS_CAPTURE_PREFIX_SOURCE_REVIEW.fixedDescriptor,
    brakemawCaptureHeader: WRECKLIGHT_BOSS_CAPTURE_PREFIX_SOURCE_REVIEW.captureHeader,
    brakemawPhasePrefixes: WRECKLIGHT_BOSS_CAPTURE_PREFIX_SOURCE_REVIEW.phasePrefixes,
};
export const BOSS_CAPTURE_PREFIX_CURATED = {
    ...BOSS_CAPTURE_PREFIX_NATIVE,
    project: bossCapturePrefixBindings(BOSS_LOOP_CURATED.project),
};
function schedulerCountdownBindings(base) {
    return base.map((binding) => WRECKLIGHT_SCHEDULER_COUNTDOWN_SOURCE_REVIEW.replacements
        .find((next) => next.path === binding.path) ?? binding);
}
// Isolated five-file tuple; prior capture/prefix profiles remain exact. Keep the
// production descriptor and startup until a separately accepted release binds them.
export const BOSS_SCHEDULER_COUNTDOWN_NATIVE = {
    ...BOSS_CAPTURE_PREFIX_NATIVE,
    project: schedulerCountdownBindings(BOSS_CAPTURE_PREFIX_NATIVE.project),
    brakemawCountdownBatches: WRECKLIGHT_SCHEDULER_COUNTDOWN_SOURCE_REVIEW.countdown,
};
export const BOSS_SCHEDULER_COUNTDOWN_CURATED = {
    ...BOSS_SCHEDULER_COUNTDOWN_NATIVE,
    project: schedulerCountdownBindings(BOSS_CAPTURE_PREFIX_CURATED.project),
};
function brakemawTimerBindings(base) {
    return base.map((binding) => WRECKLIGHT_BRAKEMAW_TIMERS_SOURCE_REVIEW.replacements
        .find((next) => next.path === binding.path) ?? binding);
}
function withTimerSites(prior, added) {
    return { ...prior, sites: [...prior.sites, ...added] };
}
// These ordinary calls preserve their individual branches and variable effects.
// The existing three countdown batches and every historical tuple stay intact.
export const BRAKEMAW_TIMERS_NATIVE = {
    ...BOSS_SCHEDULER_COUNTDOWN_NATIVE,
    project: brakemawTimerBindings(BOSS_SCHEDULER_COUNTDOWN_NATIVE.project),
    brakemawGuards: {
        ...BOSS_SCHEDULER_COUNTDOWN_NATIVE.brakemawGuards,
        kinds: {
            ...BOSS_SCHEDULER_COUNTDOWN_NATIVE.brakemawGuards.kinds,
            brakemawCueContinue: withTimerSites(BOSS_SCHEDULER_COUNTDOWN_NATIVE.brakemawGuards.kinds.brakemawCueContinue, WRECKLIGHT_BRAKEMAW_TIMERS_SOURCE_REVIEW.ordinarySites.brakemawCueContinue),
            brakemawCueFlash: withTimerSites(BOSS_SCHEDULER_COUNTDOWN_NATIVE.brakemawGuards.kinds.brakemawCueFlash, WRECKLIGHT_BRAKEMAW_TIMERS_SOURCE_REVIEW.ordinarySites.brakemawCueFlash),
            brakemawCuePose: withTimerSites(BOSS_SCHEDULER_COUNTDOWN_NATIVE.brakemawGuards.kinds.brakemawCuePose, WRECKLIGHT_BRAKEMAW_TIMERS_SOURCE_REVIEW.ordinarySites.brakemawCuePose),
        },
    },
    brakemawOperations: {
        ...BOSS_SCHEDULER_COUNTDOWN_NATIVE.brakemawOperations,
        brakemawCueDecrement: withTimerSites(BOSS_SCHEDULER_COUNTDOWN_NATIVE.brakemawOperations.brakemawCueDecrement, WRECKLIGHT_BRAKEMAW_TIMERS_SOURCE_REVIEW.ordinarySites.brakemawCueDecrement),
    },
};
export const BRAKEMAW_TIMERS_CURATED = {
    ...BRAKEMAW_TIMERS_NATIVE,
    project: brakemawTimerBindings(BOSS_SCHEDULER_COUNTDOWN_CURATED.project),
};
// The opening-direction freeze is one complete curated successor, including
// both its original and new room artwork associations. Historical tuples retain
// their own handler, descriptor, room membership, and event semantics.
export const OPENING_DIRECTION_NATIVE = {
    ...BRAKEMAW_TIMERS_CURATED,
    project: BRAKEMAW_TIMERS_CURATED.project.map((binding) => WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.fixedDescriptor,
    variables: [...BRAKEMAW_TIMERS_CURATED.variables, ...WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.additionalVariables],
    rooms: BRAKEMAW_TIMERS_CURATED.rooms.map((room) => {
        const added = WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.rooms.find((addition) => addition.sceneId === room.id);
        return added ? { ...room, actors: [...room.actors, added.actor] } : room;
    }),
    targets: [...BRAKEMAW_TIMERS_CURATED.targets, ...WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.targets],
    combatContactReads: [...BRAKEMAW_TIMERS_CURATED.combatContactReads,
        ...WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.combatContactReads],
    backgrounds: BRAKEMAW_TIMERS_CURATED.backgrounds.map((background) => {
        const added = WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.backgrounds.find((addition) => addition.sceneId === background.sceneId);
        return added ? { ...background, alternatives: [...(background.alternatives ?? []),
                { id: added.id, metadataPath: added.metadataPath }] } : background;
    }),
    brakemawGuards: {
        ...BRAKEMAW_TIMERS_CURATED.brakemawGuards,
        kinds: {
            ...BRAKEMAW_TIMERS_CURATED.brakemawGuards.kinds,
            brakemawPhaseEq14: { ...BRAKEMAW_TIMERS_CURATED.brakemawGuards.kinds.brakemawPhaseEq14,
                sites: WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.phaseSites.brakemawPhaseEq14 },
            brakemawPhaseEq24: { ...BRAKEMAW_TIMERS_CURATED.brakemawGuards.kinds.brakemawPhaseEq24,
                sites: WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.phaseSites.brakemawPhaseEq24 },
        },
    },
    brakemawContinuations: WRECKLIGHT_OPENING_DIRECTION_SOURCE_REVIEW.continuations,
};
// Keep the original opening tuple intact. This successor binds the corrected
// presentation and descriptor, and admits only the named Airworks alternative.
export const OPENING_CORRECTION_NATIVE = {
    ...OPENING_DIRECTION_NATIVE,
    project: OPENING_DIRECTION_NATIVE.project.map((binding) => WRECKLIGHT_OPENING_CORRECTION_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    fixedRemixDescriptor: WRECKLIGHT_OPENING_CORRECTION_SOURCE_REVIEW.fixedDescriptor,
    backgrounds: OPENING_DIRECTION_NATIVE.backgrounds.map((background) => {
        const added = WRECKLIGHT_OPENING_CORRECTION_SOURCE_REVIEW.backgrounds.find((entry) => entry.sceneId === background.sceneId);
        return added ? { ...background, alternatives: [...(background.alternatives ?? []),
                { id: added.id, metadataPath: added.metadataPath }] } : background;
    }),
};
// This source tuple adds the reviewed native cache/rendering changes without
// changing the opening layout, descriptor, compiler or authored VM effects.
export const COMBINED_PERFORMANCE_NATIVE = {
    ...OPENING_CORRECTION_NATIVE,
    project: OPENING_CORRECTION_NATIVE.project.map((binding) => WRECKLIGHT_COMBINED_PERFORMANCE_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
    engineRenderReads: WRECKLIGHT_COMBINED_PERFORMANCE_SOURCE_REVIEW.engineRenderReads,
};
// Retain the exact-scroll Lens invariant and clearer map legend without
// changing event effects, scene ownership, the compiler or earlier copies.
export const KEEP_VIEW_MAP_NATIVE = {
    ...COMBINED_PERFORMANCE_NATIVE,
    project: COMBINED_PERFORMANCE_NATIVE.project.map((binding) => WRECKLIGHT_KEEP_VIEW_MAP_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
};
// Source-contract review only: keep the compiler, capture order, VM effects,
// layout checks and all previous source tuples unchanged. Native review is separate.
export const GAMEPLAY_POLISH_NATIVE = {
    ...KEEP_VIEW_MAP_NATIVE,
    project: KEEP_VIEW_MAP_NATIVE.project.map((binding) => WRECKLIGHT_GAMEPLAY_POLISH_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
};
// Full authored source keeps one exact historical backup that the compact
// sample omits. Neither shape accepts an arbitrary additional engine input.
export const GAMEPLAY_POLISH_SOURCE_NATIVE = {
    ...GAMEPLAY_POLISH_NATIVE,
    project: [...GAMEPLAY_POLISH_NATIVE.project, ...WRECKLIGHT_GAMEPLAY_POLISH_SOURCE_REVIEW.sourceAdditions],
};
// Preserve the released gameplay tuple. Only the complete reviewed Warden/row
// successor is admitted; event semantics, compiler and metadata guards stay fixed.
export const WARDEN_ROW_NATIVE = {
    ...GAMEPLAY_POLISH_NATIVE,
    project: GAMEPLAY_POLISH_NATIVE.project.map((binding) => WRECKLIGHT_WARDEN_ROW_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
};
export const WARDEN_ROW_SOURCE_NATIVE = {
    ...WARDEN_ROW_NATIVE,
    project: [...WARDEN_ROW_NATIVE.project, ...WRECKLIGHT_GAMEPLAY_POLISH_SOURCE_REVIEW.sourceAdditions],
};
// The composed sample is a distinct source tuple. Preserve the historical P
// profiles; no unselected backup-file variant is introduced for this snapshot.
const composed = WRECKLIGHT_COMPOSED_GAMEPLAY_SOURCE_REVIEW;
const composedBindings = [...composed.replacements, ...composed.additions];
export const COMPOSED_GAMEPLAY_NATIVE = {
    ...WARDEN_ROW_NATIVE,
    project: [
        ...WARDEN_ROW_NATIVE.project.map((binding) => composedBindings.find((next) => next.path === binding.path) ?? binding),
        ...composed.additions.filter((next) => !WARDEN_ROW_NATIVE.project.some((binding) => binding.path === next.path)),
    ],
    variables: [...WARDEN_ROW_NATIVE.variables,
        ...composed.additionalVariables.filter((next) => !WARDEN_ROW_NATIVE.variables.some((variable) => variable.id === next.id))],
    nativeSprites: [...WARDEN_ROW_NATIVE.nativeSprites, ...composed.nativeSprites],
    cargoCrawler: composed.cargoCrawler,
    reactorHunter: composed.reactorHunter,
    crownPress: composed.crownPress,
    engineLocalReads: composed.engineLocalReads,
    engineRenderReads: [...new Set([...WARDEN_ROW_NATIVE.engineRenderReads, ...composed.engineRenderReads])],
    combatContactReads: [...new Set([...WARDEN_ROW_NATIVE.combatContactReads, ...composed.combatContactReads])],
    skimmerProwl: true,
    warden: {
        ...WARDEN_ROW_NATIVE.warden,
        operations: {
            ...WARDEN_ROW_NATIVE.warden.operations,
            ...composed.wardenOperations,
            tick: { ...WARDEN_ROW_NATIVE.warden.operations.tick,
                children: composed.wardenBranches, requiredChildren: composed.wardenBranches },
            sample_and_tick: { ...WARDEN_ROW_NATIVE.warden.operations.sample_and_tick,
                children: composed.wardenBranches, requiredChildren: composed.wardenBranches },
            after_move: { ...WARDEN_ROW_NATIVE.warden.operations.after_move, reads: ["8", "21", "58", "59", "62", "63"] },
            contact: { ...WARDEN_ROW_NATIVE.warden.operations.contact, reads: ["8", "21", "58", "59", "63"] },
            hit: { ...WARDEN_ROW_NATIVE.warden.operations.hit, reads: ["8", "21", "58", "59", "63"] },
        },
    },
};
// Camera and warning follow-up. Event operations and authored branches are
// unchanged; only the complete native tuple and camera-hook reads differ.
const brakemawFinish = WRECKLIGHT_BRAKEMAW_FINISH_SOURCE_REVIEW;
export const BRAKEMAW_FINISH_NATIVE = {
    ...COMPOSED_GAMEPLAY_NATIVE,
    project: [
        ...COMPOSED_GAMEPLAY_NATIVE.project.map((binding) => brakemawFinish.bindings.find((next) => next.path === binding.path) ?? binding),
        ...brakemawFinish.bindings.filter((next) => !COMPOSED_GAMEPLAY_NATIVE.project.some((binding) => binding.path === next.path)),
    ],
    engineRenderReads: [...new Set([...COMPOSED_GAMEPLAY_NATIVE.engineRenderReads, ...brakemawFinish.engineRenderReads])],
};
// The new motion hook owns only its added native accesses and relay guards.
// Earlier profiles and the stage-III press contract retain their exact source.
const crownMotion = WRECKLIGHT_CROWN_MOTION_SOURCE_REVIEW;
export const CROWN_MOTION_NATIVE = {
    ...BRAKEMAW_FINISH_NATIVE,
    project: [
        ...BRAKEMAW_FINISH_NATIVE.project.map((binding) => crownMotion.bindings.find((next) => next.path === binding.path) ?? binding),
        ...crownMotion.bindings.filter((next) => !BRAKEMAW_FINISH_NATIVE.project.some((binding) => binding.path === next.path)),
    ],
    crownMotion: {
        ...BRAKEMAW_FINISH_NATIVE.crownPress,
        globalAliases: BRAKEMAW_FINISH_NATIVE.crownPress.globalAliases.filter(({ id }) => id !== "97"),
        relays: crownMotion.relays,
        operations: crownMotion.operations,
    },
};
// Permit relocated Brakemaw locals only with both reviewed guard replacements.
// Keep the Crown motion tuple and all earlier profiles unchanged.
export const BRAKEMAW_CAPTURE_LAYOUT_NATIVE = {
    ...CROWN_MOTION_NATIVE,
    project: CROWN_MOTION_NATIVE.project.map((binding) => WRECKLIGHT_BRAKEMAW_CAPTURE_LAYOUT_SOURCE_REVIEW.replacements.find((next) => next.path === binding.path) ?? binding),
};
export const CARGO_CONTACT_NATIVE = {
    ...BRAKEMAW_CAPTURE_LAYOUT_NATIVE,
    project: BRAKEMAW_CAPTURE_LAYOUT_NATIVE.project.map((binding) => cargoContact.replacements.find((next) => next.path === binding.path) ?? binding),
    cargoCrawler: {
        ...BRAKEMAW_CAPTURE_LAYOUT_NATIVE.cargoCrawler,
        globalAliases: [...BRAKEMAW_CAPTURE_LAYOUT_NATIVE.cargoCrawler.globalAliases, ...cargoContact.additionalGlobalAliases],
        operations: { ...BRAKEMAW_CAPTURE_LAYOUT_NATIVE.cargoCrawler.operations, contact: cargoContact.contact },
    },
};
// Spawn and endpoint contacts use the same Combat routine and native read sets.
// Deferred hit consumption stays on the authored event; contact adds no VM writes.
// Preserve Cargo and every earlier tuple as independently selectable history.
export const PROJECTILE_SPAWN_CONTACT_NATIVE = {
    ...CARGO_CONTACT_NATIVE,
    project: CARGO_CONTACT_NATIVE.project.map((binding) => projectileSpawnContact.replacements.find((next) => next.path === binding.path) ?? binding),
};
const nativeContractGroups = [
    { review: WRECKLIGHT_REVIEW, contracts: nativeContracts(WRECKLIGHT_REVIEW, "-native-v1") },
    { review: WRECKLIGHT_DOOR_REVIEW, contracts: nativeContracts(WRECKLIGHT_DOOR_REVIEW, "-native-r06-v1") },
    { review: WRECKLIGHT_CURRENT_REVIEW, contracts: nativeContracts(WRECKLIGHT_CURRENT_REVIEW, "-native-r31-v1") },
    { review: WRECKLIGHT_WARDEN_REVIEW, contracts: nativeContracts(WRECKLIGHT_WARDEN_REVIEW, "-native-r36-v1") },
    { review: WRECKLIGHT_WARDEN_CUE_REVIEW, contracts: nativeContracts(WRECKLIGHT_WARDEN_CUE_REVIEW, "-native-r37-v1") },
    { review: WRECKLIGHT_WARDEN_FEEDBACK_REVIEW, contracts: nativeContracts(WRECKLIGHT_WARDEN_FEEDBACK_REVIEW, "-native-feedback-v1") },
    { review: WRECKLIGHT_WARDEN_CONDENSER_REVIEW, contracts: nativeContracts(WRECKLIGHT_WARDEN_CONDENSER_REVIEW, "-native-condenser-v1") },
    { review: WRECKLIGHT_WARDEN_ROM44_REVIEW, contracts: nativeContracts(WRECKLIGHT_WARDEN_ROM44_REVIEW, "-native-r44-v1") },
    { review: WRECKLIGHT_WARDEN_DYNAMO_BEAM_REVIEW, contracts: nativeContracts(WRECKLIGHT_WARDEN_DYNAMO_BEAM_REVIEW, "-native-dynamo-beam-v1") },
    { review: WRECKLIGHT_CHAMBERS_REVIEW, contracts: nativeContracts(WRECKLIGHT_CHAMBERS_REVIEW, "-native-chambers-v1") },
    { review: WRECKLIGHT_SEP17_REVIEW, contracts: nativeContracts(WRECKLIGHT_SEP17_REVIEW, "-native-sep17-v1", 3) },
    { review: WRECKLIGHT_REMIX_REVIEW, contracts: nativeContracts(WRECKLIGHT_REMIX_REVIEW, "-native-remix-v1") },
    { review: WRECKLIGHT_PERFORMANCE_REVIEW, contracts: nativeContracts(WRECKLIGHT_PERFORMANCE_REVIEW, "-native-performance-v1") },
    { review: WRECKLIGHT_BUSYROOM_REVIEW, contracts: nativeContracts(WRECKLIGHT_BUSYROOM_REVIEW, "-native-busyroom-v1") },
    { review: WRECKLIGHT_PACING_REVIEW, contracts: nativeContracts(WRECKLIGHT_PACING_REVIEW, "-native-pacing-v1") },
    { review: WRECKLIGHT_COMBINED_REVIEW, contracts: nativeContracts(WRECKLIGHT_COMBINED_REVIEW, "-native-combined-v1", 3) },
    { review: WRECKLIGHT_PAYOFF_REVIEW, contracts: nativeContracts(WRECKLIGHT_PAYOFF_REVIEW, "-native-payoff-v1", 3) },
    { review: WRECKLIGHT_PAYOFF_CURATED_REVIEW, contracts: nativeContracts(WRECKLIGHT_PAYOFF_CURATED_REVIEW, "-native-payoff-curated-v1", 3) },
    { review: WRECKLIGHT_OVERLAY_REVIEW, contracts: nativeContracts(WRECKLIGHT_OVERLAY_REVIEW, "-native-overlay-v1", 3) },
    { review: WRECKLIGHT_OVERLAY_CURATED_REVIEW, contracts: nativeContracts(WRECKLIGHT_OVERLAY_CURATED_REVIEW, "-native-overlay-curated-v1", 3) },
    { review: WRECKLIGHT_CAPTURE_REVIEW, contracts: nativeContracts(WRECKLIGHT_CAPTURE_REVIEW, "-native-capture-v1", 3) },
    { review: WRECKLIGHT_CAPTURE_CURATED_REVIEW, contracts: nativeContracts(WRECKLIGHT_CAPTURE_CURATED_REVIEW, "-native-capture-curated-v1", 3) },
    { review: WRECKLIGHT_RENDER_REVIEW, contracts: nativeContracts(WRECKLIGHT_RENDER_REVIEW, "-native-render-v1", 3) },
    { review: WRECKLIGHT_RENDER_CURATED_REVIEW, contracts: nativeContracts(WRECKLIGHT_RENDER_CURATED_REVIEW, "-native-render-curated-v1", 3) },
    { review: WRECKLIGHT_SCROLL_REVIEW, contracts: nativeContracts(WRECKLIGHT_SCROLL_REVIEW, "-native-scroll-v1", 3) },
    { review: WRECKLIGHT_SCROLL_CURATED_REVIEW, contracts: nativeContracts(WRECKLIGHT_SCROLL_CURATED_REVIEW, "-native-scroll-curated-v1", 3) },
    { review: WRECKLIGHT_SAMPLING_REVIEW, contracts: nativeContracts(WRECKLIGHT_SAMPLING_REVIEW, "-native-sampling-v1", 3) },
    { review: WRECKLIGHT_SAMPLING_CURATED_REVIEW, contracts: nativeContracts(WRECKLIGHT_SAMPLING_CURATED_REVIEW, "-native-sampling-curated-v1", 3) },
    { review: CHAMBER_CACHE_NATIVE, contracts: nativeContracts(CHAMBER_CACHE_NATIVE, "-native-chamber-cache-v1", 3) },
    { review: CHAMBER_CACHE_CURATED, contracts: nativeContracts(CHAMBER_CACHE_CURATED, "-native-chamber-cache-curated-v1", 3) },
    { review: FLAT_PROJECTILE_NATIVE, contracts: nativeContracts(FLAT_PROJECTILE_NATIVE, "-native-flat-projectile-v1", 3) },
    { review: FLAT_PROJECTILE_CURATED, contracts: nativeContracts(FLAT_PROJECTILE_CURATED, "-native-flat-projectile-curated-v1", 3) },
    { review: DRIVE_PERFORMANCE_NATIVE, contracts: nativeContracts(DRIVE_PERFORMANCE_NATIVE, "-native-drive-performance-v1", 3) },
    { review: DRIVE_PERFORMANCE_CURATED, contracts: nativeContracts(DRIVE_PERFORMANCE_CURATED, "-native-drive-performance-curated-v1", 3) },
    { review: BOSS_THREE_PHASE_NATIVE, contracts: nativeContracts(BOSS_THREE_PHASE_NATIVE, "-native-boss-three-phase-v1", 3) },
    { review: BOSS_THREE_PHASE_CURATED, contracts: nativeContracts(BOSS_THREE_PHASE_CURATED, "-native-boss-three-phase-curated-v1", 3) },
    { review: BOSS_CUE_NATIVE, contracts: nativeContracts(BOSS_CUE_NATIVE, "-native-boss-cue-v1", 3) },
    { review: BOSS_CUE_CURATED, contracts: nativeContracts(BOSS_CUE_CURATED, "-native-boss-cue-curated-v1", 3) },
    { review: BOSS_LOOP_NATIVE, contracts: nativeContracts(BOSS_LOOP_NATIVE, "-native-boss-loop-v1", 3) },
    { review: BOSS_LOOP_CURATED, contracts: nativeContracts(BOSS_LOOP_CURATED, "-native-boss-loop-curated-v1", 3) },
    { review: BOSS_CAPTURE_PREFIX_NATIVE, contracts: nativeContracts(BOSS_CAPTURE_PREFIX_NATIVE, "-native-boss-capture-prefix-v1", 3) },
    { review: BOSS_CAPTURE_PREFIX_CURATED, contracts: nativeContracts(BOSS_CAPTURE_PREFIX_CURATED, "-native-boss-capture-prefix-curated-v1", 3) },
    { review: BOSS_SCHEDULER_COUNTDOWN_NATIVE, contracts: nativeContracts(BOSS_SCHEDULER_COUNTDOWN_NATIVE, "-native-boss-scheduler-countdown-v1", 3) },
    { review: BOSS_SCHEDULER_COUNTDOWN_CURATED, contracts: nativeContracts(BOSS_SCHEDULER_COUNTDOWN_CURATED, "-native-boss-scheduler-countdown-curated-v1", 3) },
    { review: BRAKEMAW_TIMERS_NATIVE, contracts: nativeContracts(BRAKEMAW_TIMERS_NATIVE, "-native-brakemaw-timers-v1", 3) },
    { review: BRAKEMAW_TIMERS_CURATED, contracts: nativeContracts(BRAKEMAW_TIMERS_CURATED, "-native-brakemaw-timers-curated-v1", 3) },
    { review: OPENING_DIRECTION_NATIVE, contracts: nativeContracts(OPENING_DIRECTION_NATIVE, "-native-opening-direction-v1", 3) },
    { review: OPENING_CORRECTION_NATIVE, contracts: nativeContracts(OPENING_CORRECTION_NATIVE, "-native-opening-correction-v1", 3) },
    { review: COMBINED_PERFORMANCE_NATIVE, contracts: nativeContracts(COMBINED_PERFORMANCE_NATIVE, "-native-combined-performance-v1", 3) },
    { review: KEEP_VIEW_MAP_NATIVE, contracts: nativeContracts(KEEP_VIEW_MAP_NATIVE, "-native-keep-view-map-v1", 3) },
    { review: GAMEPLAY_POLISH_NATIVE, contracts: nativeContracts(GAMEPLAY_POLISH_NATIVE, "-native-gameplay-polish-v1", 3) },
    { review: GAMEPLAY_POLISH_SOURCE_NATIVE, contracts: nativeContracts(GAMEPLAY_POLISH_SOURCE_NATIVE, "-native-gameplay-polish-source-v1", 3) },
    { review: WARDEN_ROW_NATIVE, contracts: nativeContracts(WARDEN_ROW_NATIVE, "-native-warden-row-v1", 3) },
    { review: WARDEN_ROW_SOURCE_NATIVE, contracts: nativeContracts(WARDEN_ROW_SOURCE_NATIVE, "-native-warden-row-source-v1", 3) },
    { review: COMPOSED_GAMEPLAY_NATIVE, contracts: nativeContracts(COMPOSED_GAMEPLAY_NATIVE, "-native-composed-gameplay-v1", 3) },
    { review: BRAKEMAW_FINISH_NATIVE, contracts: nativeContracts(BRAKEMAW_FINISH_NATIVE, "-native-brakemaw-finish-v1", 3) },
    { review: CROWN_MOTION_NATIVE, contracts: nativeContracts(CROWN_MOTION_NATIVE, "-native-crown-motion-v1", 3) },
    { review: BRAKEMAW_CAPTURE_LAYOUT_NATIVE, contracts: nativeContracts(BRAKEMAW_CAPTURE_LAYOUT_NATIVE, "-native-brakemaw-capture-layout-v1", 3) },
    { review: CARGO_CONTACT_NATIVE, contracts: nativeContracts(CARGO_CONTACT_NATIVE, "-native-cargo-contact-v1", 3) },
    { review: PROJECTILE_SPAWN_CONTACT_NATIVE, contracts: nativeContracts(PROJECTILE_SPAWN_CONTACT_NATIVE, "-native-projectile-spawn-contact-v1", 3) },
];
export const WRECKLIGHT_CONTRACTS = nativeContractGroups.flatMap(({ contracts }) => contracts);
/** The fixed door renderer compiles all room symbols into each invoking event.
 * Those references still prevent deletion, but their output belongs to the
 * reviewed room, not every actor that invokes the native translation unit.
 * Call only after complete current dependency coverage has been established. */
export function reviewedNativeBackgroundOwner(reference, metadataPath) {
    if (reference.confidence !== "verified" || reference.relation !== "native-door-background"
        || reference.target.type !== "asset" || !reference.reviewedContract)
        return undefined;
    for (const { review, contracts } of nativeContractGroups) {
        const contract = contracts.find((candidate) => candidate.id === reference.reviewedContract.id
            && candidate.version === reference.reviewedContract.version && candidate.handler.path === reference.resourcePath);
        if (!contract)
            continue;
        const backgrounds = review.backgrounds?.filter((background) => [background, ...(background.alternatives ?? [])]
            .some((choice) => choice.id === reference.target.id && choice.metadataPath === metadataPath
            && choice.metadataPath.replace(/\.gbsres$/u, "") === reference.target.resourcePath)) ?? [];
        if (backgrounds.length === 1)
            return backgrounds[0].sceneId;
    }
    return undefined;
}
//# sourceMappingURL=wrecklight-dependencies.js.map

SHA-256: 48f370bb6f9cec0bdddd9a323356c9fac282fb6baccb61047086916e42d9f662