libpetri 4.0.0 → 5.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/core/in.ts","../src/core/out.ts","../src/core/transition-action.ts","../src/verification/marking-state.ts","../src/verification/smt-property.ts","../src/verification/encoding/flat-transition.ts","../src/verification/analysis/environment-analysis-mode.ts","../src/verification/encoding/net-flattener.ts","../src/verification/encoding/incidence-matrix.ts","../src/verification/invariant/p-invariant.ts","../src/verification/invariant/p-invariant-computer.ts","../src/verification/invariant/structural-check.ts","../src/verification/z3/z3-process.ts","../src/verification/z3/smt-text.ts","../src/verification/z3/spacer-runner.ts","../src/verification/z3/smt-encoder.ts","../src/verification/z3/certificate-checker.ts","../src/verification/analysis/dbm.ts","../src/verification/analysis/state-class.ts","../src/core/internal/output-action-check.ts","../src/verification/analysis/state-class-graph.ts","../src/verification/z3/counterexample-decoder.ts","../src/verification/encoding/flat-net.ts","../src/verification/z3/abstract-replayer.ts","../src/verification/z3/name-coloured-encoder.ts","../src/verification/analysis/name-fragment.ts","../src/verification/analysis/name-marking.ts","../src/verification/analysis/name-state-class.ts","../src/verification/analysis/name-state-class-graph.ts","../src/verification/nu-scg-verifier.ts","../src/verification/smt-verifier.ts","../src/verification/smt-verification-result.ts"],"sourcesContent":["import type { Place } from './place.js';\n\n/**\n * Input specification with cardinality. Purely structural (IO-006): cardinality\n * determines how many tokens to consume; there is no per-token predicate.\n *\n * Conditional token selection is modeled with multiple conflicting transitions\n * and XOR-on-input semantics rather than a predicate coupled to the enablement\n * check.\n *\n * Inputs are always AND-joined (all must be satisfied to enable transition).\n * XOR on inputs is modeled via multiple transitions (conflict).\n */\nexport type In = InOne | InExactly | InAll | InAtLeast;\n\nexport interface InOne<T = any> {\n readonly type: 'one';\n readonly place: Place<T>;\n}\n\nexport interface InExactly<T = any> {\n readonly type: 'exactly';\n readonly place: Place<T>;\n readonly count: number;\n}\n\nexport interface InAll<T = any> {\n readonly type: 'all';\n readonly place: Place<T>;\n}\n\nexport interface InAtLeast<T = any> {\n readonly type: 'at-least';\n readonly place: Place<T>;\n readonly minimum: number;\n}\n\n// ==================== Factory Functions ====================\n\n/** Consume exactly 1 token (standard CPN semantics). */\nexport function one<T>(place: Place<T>): InOne<T> {\n return { type: 'one', place };\n}\n\n/** Consume exactly N tokens (batching). */\nexport function exactly<T>(count: number, place: Place<T>): InExactly<T> {\n if (count < 1) {\n throw new Error(`count must be >= 1, got: ${count}`);\n }\n return { type: 'exactly', place, count };\n}\n\n/** Consume all available tokens (must be 1+). */\nexport function all<T>(place: Place<T>): InAll<T> {\n return { type: 'all', place };\n}\n\n/** Wait for N+ tokens, consume all when enabled. */\nexport function atLeast<T>(minimum: number, place: Place<T>): InAtLeast<T> {\n if (minimum < 1) {\n throw new Error(`minimum must be >= 1, got: ${minimum}`);\n }\n return { type: 'at-least', place, minimum };\n}\n\n// ==================== Helper Functions ====================\n\n/** Returns the minimum number of tokens required to enable. */\nexport function requiredCount(spec: In): number {\n switch (spec.type) {\n case 'one': return 1;\n case 'exactly': return spec.count;\n case 'all': return 1;\n case 'at-least': return spec.minimum;\n }\n}\n\n/**\n * Returns the actual number of tokens to consume given the available count.\n * - One: always consumes 1\n * - Exactly: always consumes exactly count\n * - All: consumes all available\n * - AtLeast: consumes all available (when enabled, i.e., >= minimum)\n */\nexport function consumptionCount(spec: In, available: number): number {\n if (available < requiredCount(spec)) {\n throw new Error(\n `Cannot consume from '${spec.place.name}': available=${available}, required=${requiredCount(spec)}`\n );\n }\n switch (spec.type) {\n case 'one': return 1;\n case 'exactly': return spec.count;\n case 'all': return available;\n case 'at-least': return available;\n }\n}\n","import type { Place } from './place.js';\n\n/**\n * Output specification with explicit split semantics.\n * Supports composite structures (XOR of ANDs, AND of XORs, etc.)\n *\n * - And: ALL children must receive tokens\n * - Xor: EXACTLY ONE child receives token\n * - Place: Leaf node representing a single output place\n * - Timeout: Timeout branch that activates if action exceeds duration\n * - ForwardInput: Forward consumed input to output on timeout\n */\nexport type Out = OutAnd | OutXor | OutPlace | OutTimeout | OutForwardInput;\n\nexport interface OutAnd {\n readonly type: 'and';\n readonly children: readonly Out[];\n}\n\nexport interface OutXor {\n readonly type: 'xor';\n readonly children: readonly Out[];\n}\n\nexport interface OutPlace {\n readonly type: 'place';\n readonly place: Place<any>;\n}\n\nexport interface OutTimeout {\n readonly type: 'timeout';\n /** Timeout duration in milliseconds. */\n readonly afterMs: number;\n readonly child: Out;\n}\n\nexport interface OutForwardInput {\n readonly type: 'forward-input';\n readonly from: Place<any>;\n readonly to: Place<any>;\n}\n\n// ==================== Factory Functions ====================\n\n/**\n * AND-split: all children must receive tokens.\n *\n * @example\n * ```ts\n * // AND of XOR branches: one of (A,B) AND one of (C,D)\n * and(xorPlaces(placeA, placeB), xorPlaces(placeC, placeD))\n *\n * // AND with a fixed place + XOR branch\n * and(outPlace(always), xorPlaces(left, right))\n * ```\n */\nexport function and(...children: Out[]): OutAnd {\n if (children.length === 0) {\n throw new Error('AND requires at least 1 child');\n }\n return { type: 'and', children };\n}\n\n/** AND-split from places: all places must receive tokens. */\nexport function andPlaces(...places: Place<any>[]): OutAnd {\n return and(...places.map(outPlace));\n}\n\n/** XOR-split: exactly one child receives token. */\nexport function xor(...children: Out[]): OutXor {\n if (children.length < 2) {\n throw new Error('XOR requires at least 2 children');\n }\n return { type: 'xor', children };\n}\n\n/** XOR-split from places: exactly one place receives token. */\nexport function xorPlaces(...places: Place<any>[]): OutXor {\n return xor(...places.map(outPlace));\n}\n\n/** Leaf output spec for a single place. */\nexport function outPlace(p: Place<any>): OutPlace {\n return { type: 'place', place: p };\n}\n\n/** Timeout output: activates if action exceeds duration. */\nexport function timeout(afterMs: number, child: Out): OutTimeout {\n if (afterMs <= 0) {\n throw new Error(`Timeout must be positive: ${afterMs}`);\n }\n return { type: 'timeout', afterMs, child };\n}\n\n/** Timeout output pointing to a single place. */\nexport function timeoutPlace(afterMs: number, p: Place<any>): OutTimeout {\n return timeout(afterMs, outPlace(p));\n}\n\n/** Forward consumed input value to output place on timeout. */\nexport function forwardInput(from: Place<any>, to: Place<any>): OutForwardInput {\n return { type: 'forward-input', from, to };\n}\n\n// ==================== Helper Functions ====================\n\n/** Collects all leaf places from this output spec (flattened). */\nexport function allPlaces(out: Out): Set<Place<any>> {\n const result = new Set<Place<any>>();\n collectPlaces(out, result);\n return result;\n}\n\nfunction collectPlaces(out: Out, result: Set<Place<any>>): void {\n switch (out.type) {\n case 'place':\n result.add(out.place);\n break;\n case 'forward-input':\n result.add(out.to);\n break;\n case 'and':\n case 'xor':\n for (const child of out.children) {\n collectPlaces(child, result);\n }\n break;\n case 'timeout':\n collectPlaces(out.child, result);\n break;\n }\n}\n\n/**\n * Enumerates all possible output branches for structural analysis.\n *\n * - AND = single branch containing all child places (Cartesian product)\n * - XOR = one branch per alternative child\n * - Nested = Cartesian product for AND, union for XOR\n */\nexport function enumerateBranches(out: Out): ReadonlyArray<ReadonlySet<Place<any>>> {\n switch (out.type) {\n case 'place':\n return [new Set([out.place])];\n\n case 'forward-input':\n return [new Set<Place<any>>([out.to])];\n\n case 'and': {\n let result: Set<Place<any>>[] = [new Set()];\n for (const child of out.children) {\n result = crossProduct(result, enumerateBranches(child) as Set<Place<any>>[]);\n }\n return result;\n }\n\n case 'xor': {\n const result: Set<Place<any>>[] = [];\n for (const child of out.children) {\n result.push(...(enumerateBranches(child) as Set<Place<any>>[]));\n }\n return result;\n }\n\n case 'timeout':\n return enumerateBranches(out.child);\n }\n}\n\nfunction crossProduct(\n a: Set<Place<any>>[],\n b: ReadonlyArray<ReadonlySet<Place<any>>>,\n): Set<Place<any>>[] {\n const result: Set<Place<any>>[] = [];\n for (const setA of a) {\n for (const setB of b) {\n const merged = new Set<Place<any>>(setA);\n for (const p of setB) merged.add(p);\n result.push(merged);\n }\n }\n return result;\n}\n","import type { Place } from './place.js';\nimport type { TransitionContext } from './transition-context.js';\n\n/**\n * The action executed when a transition fires.\n * Receives a TransitionContext providing filtered I/O and structure access.\n */\nexport type TransitionAction = (ctx: TransitionContext) => Promise<void>;\n\n// ==================== Built-in Actions ====================\n\n/**\n * Identity action: produces no outputs.\n * For transitions that only consume tokens without producing any.\n *\n * Returns a stable singleton reference (CORE-051), so {@link isPassthrough}\n * can recognise it.\n */\nexport function passthrough(): TransitionAction {\n return PASSTHROUGH;\n}\n\n/** @internal Stable passthrough action — see {@link passthrough}. */\nconst PASSTHROUGH: TransitionAction = async () => {};\n\n/**\n * Whether `action` is the built-in {@link passthrough} — i.e. provably produces\n * no output tokens. Identity-based, so a hand-written no-op is not claimed.\n *\n * @param action the action to test; `null` / `undefined` is not passthrough\n */\nexport function isPassthrough(action: TransitionAction | null | undefined): boolean {\n return action === PASSTHROUGH;\n}\n\n/**\n * Transform action: applies function to context, copies result to ALL output places.\n *\n * @example\n * ```ts\n * const action = transform(ctx => ctx.input(inputPlace).toUpperCase());\n * // Result is copied to every declared output place\n * ```\n */\nexport function transform(fn: (ctx: TransitionContext) => unknown): TransitionAction {\n return async (ctx) => {\n const result = fn(ctx);\n for (const outputPlace of ctx.outputPlaces()) {\n ctx.output(outputPlace, result);\n }\n };\n}\n\n/**\n * Fork action: copies single input token to all outputs.\n * Requires exactly one input place (derived from structure).\n */\nexport function fork(): TransitionAction {\n return transform((ctx) => {\n const inputPlaces = ctx.inputPlaces();\n if (inputPlaces.size !== 1) {\n throw new Error(`Fork requires exactly 1 input place, found ${inputPlaces.size}`);\n }\n const inputPlace = inputPlaces.values().next().value as Place<any>;\n return ctx.input(inputPlace);\n });\n}\n\n/**\n * Transform with explicit input place.\n */\nexport function transformFrom<I>(inputPlace: Place<I>, fn: (value: I) => unknown): TransitionAction {\n return transform((ctx) => fn(ctx.input(inputPlace)));\n}\n\n/**\n * Async transform: applies async function, copies result to all outputs.\n */\nexport function transformAsync(fn: (ctx: TransitionContext) => Promise<unknown>): TransitionAction {\n return async (ctx) => {\n const result = await fn(ctx);\n for (const outputPlace of ctx.outputPlaces()) {\n ctx.output(outputPlace, result);\n }\n };\n}\n\n/** Produce action: produces a single token with the given value to the specified place. */\nexport function produce<T>(place: Place<T>, value: T): TransitionAction {\n return async (ctx) => {\n ctx.output(place, value);\n };\n}\n\n/**\n * Wraps an action with timeout handling.\n * If the action completes within the timeout, normal completion.\n * If the timeout expires, the timeoutValue is produced to the timeoutPlace.\n *\n * @example\n * ```ts\n * const action = withTimeout(\n * async (ctx) => { ctx.output(resultPlace, await fetchData()); },\n * 5000,\n * timeoutPlace,\n * 'timed-out',\n * );\n * ```\n */\nexport function withTimeout<T>(\n action: TransitionAction,\n timeoutMs: number,\n timeoutPlace: Place<T>,\n timeoutValue: T,\n): TransitionAction {\n return (ctx) => {\n return new Promise<void>((resolve, reject) => {\n let completed = false;\n const timer = setTimeout(() => {\n if (!completed) {\n completed = true;\n ctx.output(timeoutPlace, timeoutValue);\n resolve();\n }\n }, timeoutMs);\n action(ctx).then(\n () => {\n if (!completed) {\n completed = true;\n clearTimeout(timer);\n resolve();\n }\n },\n (err) => {\n if (!completed) {\n completed = true;\n clearTimeout(timer);\n reject(err);\n }\n },\n );\n });\n };\n}\n","import type { Place } from '../core/place.js';\n\n/** @internal Symbol key restricting construction to the builder and factory methods. */\nconst MARKING_STATE_KEY = Symbol('MarkingState.internal');\n\n/**\n * Immutable snapshot of a Petri net marking for state space analysis.\n *\n * Maps places (by name) to integer token counts. Only stores places with count > 0.\n * Used for invariant computation and structural verification, not runtime execution.\n */\nexport class MarkingState {\n private readonly tokenCounts: ReadonlyMap<string, number>;\n private readonly placesByName: ReadonlyMap<string, Place<any>>;\n\n /** @internal Use {@link MarkingState.builder} or {@link MarkingState.empty} to create instances. */\n constructor(key: symbol, tokenCounts: Map<string, number>, placesByName: Map<string, Place<any>>) {\n if (key !== MARKING_STATE_KEY) throw new Error('Use MarkingState.builder() to create instances');\n this.tokenCounts = tokenCounts;\n this.placesByName = placesByName;\n }\n\n /** Returns the token count for a place (0 if absent). */\n tokens(place: Place<any>): number {\n return this.tokenCounts.get(place.name) ?? 0;\n }\n\n /** Checks if a place has at least one token. */\n hasTokens(place: Place<any>): boolean {\n return this.tokens(place) > 0;\n }\n\n /** Checks if any of the given places has tokens. */\n hasTokensInAny(places: Iterable<Place<any>>): boolean {\n for (const p of places) {\n if (this.hasTokens(p)) return true;\n }\n return false;\n }\n\n /** Returns all places with tokens > 0. */\n placesWithTokens(): Place<any>[] {\n return [...this.placesByName.values()];\n }\n\n /** Returns the total number of tokens. */\n totalTokens(): number {\n let sum = 0;\n for (const count of this.tokenCounts.values()) sum += count;\n return sum;\n }\n\n /** Checks if no tokens exist anywhere. */\n isEmpty(): boolean {\n return this.tokenCounts.size === 0;\n }\n\n toString(): string {\n if (this.tokenCounts.size === 0) return '{}';\n const entries = [...this.tokenCounts.entries()]\n .sort(([a], [b]) => a.localeCompare(b))\n .map(([name, count]) => `${name}:${count}`);\n return `{${entries.join(', ')}}`;\n }\n\n static empty(): MarkingState {\n return new MarkingState(MARKING_STATE_KEY, new Map(), new Map());\n }\n\n static builder(): MarkingStateBuilder {\n return new MarkingStateBuilder();\n }\n}\n\nexport class MarkingStateBuilder {\n private readonly tokenCounts = new Map<string, number>();\n private readonly placesByName = new Map<string, Place<any>>();\n\n /** Sets the token count for a place. */\n tokens(place: Place<any>, count: number): this {\n if (count < 0) throw new Error(`Token count cannot be negative: ${count}`);\n if (count > 0) {\n this.tokenCounts.set(place.name, count);\n this.placesByName.set(place.name, place);\n } else {\n this.tokenCounts.delete(place.name);\n this.placesByName.delete(place.name);\n }\n return this;\n }\n\n /** Adds tokens to a place. */\n addTokens(place: Place<any>, count: number): this {\n if (count < 0) throw new Error(`Token count cannot be negative: ${count}`);\n if (count > 0) {\n const current = this.tokenCounts.get(place.name) ?? 0;\n this.tokenCounts.set(place.name, current + count);\n this.placesByName.set(place.name, place);\n }\n return this;\n }\n\n /** Removes tokens from a place. Throws if insufficient. */\n removeTokens(place: Place<any>, count: number): this {\n const current = this.tokenCounts.get(place.name) ?? 0;\n const newCount = current - count;\n if (newCount < 0) {\n throw new Error(\n `Cannot remove ${count} tokens from ${place.name} (has ${current})`,\n );\n }\n if (newCount === 0) {\n this.tokenCounts.delete(place.name);\n this.placesByName.delete(place.name);\n } else {\n this.tokenCounts.set(place.name, newCount);\n }\n return this;\n }\n\n /** Copies all token counts from another marking state. */\n copyFrom(other: MarkingState): this {\n for (const p of other.placesWithTokens()) {\n this.tokenCounts.set(p.name, other.tokens(p));\n this.placesByName.set(p.name, p);\n }\n return this;\n }\n\n build(): MarkingState {\n return new MarkingState(MARKING_STATE_KEY, new Map(this.tokenCounts), new Map(this.placesByName));\n }\n}\n","import type { Place } from '../core/place.js';\n\n/**\n * Safety properties that can be verified via IC3/PDR.\n *\n * Each property is encoded as an error condition: if a reachable state\n * violates the property, Spacer finds a counterexample. If no violation\n * is reachable, the property is proven.\n */\nexport type SmtProperty =\n | DeadlockFree\n | MutualExclusion\n | PlaceBound\n | Unreachable\n | BranchPlaceBound\n | JoinedOrDeadLettered;\n\n/** Deadlock-freedom: no reachable marking has all transitions disabled. */\nexport interface DeadlockFree {\n readonly type: 'deadlock-free';\n}\n\n/** Mutual exclusion: two places never have tokens simultaneously. */\nexport interface MutualExclusion {\n readonly type: 'mutual-exclusion';\n readonly p1: Place<any>;\n readonly p2: Place<any>;\n}\n\n/** Place bound: a place never exceeds a given token count. */\nexport interface PlaceBound {\n readonly type: 'place-bound';\n readonly place: Place<any>;\n readonly bound: number;\n}\n\n/** Unreachability: the given places never all have tokens simultaneously. */\nexport interface Unreachable {\n readonly type: 'unreachable';\n readonly places: ReadonlySet<Place<any>>;\n}\n\n/**\n * Branch / budget place bound: a ν-net budget or fork-branch place never\n * exceeds `bound` tokens — the bounded-budget decidability lever (NU-040).\n *\n * Encodes identically to {@link PlaceBound} (a linear-integer count bound), but\n * names the ν-net intent: the live correlation pool is bounded, keeping the\n * well-structured transition system finite. The matched-transition\n * over-approximation is sound for this safety bound — a `proven` verdict holds\n * for the real net, which fires strictly fewer joins than the over-approximation.\n */\nexport interface BranchPlaceBound {\n readonly type: 'branch-place-bound';\n readonly place: Place<any>;\n readonly bound: number;\n}\n\n/**\n * Joined-or-dead-lettered: every forked name is eventually joined or\n * dead-lettered, so no reachable *quiescent* (deadlocked) marking still holds a\n * token in `pending` (NU-040). Violated when a reachable marking is both\n * quiescent and has `pending >= 1` — a stranded correlation group.\n */\nexport interface JoinedOrDeadLettered {\n readonly type: 'joined-or-dead-lettered';\n readonly pending: Place<any>;\n}\n\n// Factory functions\n\nexport function deadlockFree(): DeadlockFree {\n return { type: 'deadlock-free' };\n}\n\nexport function mutualExclusion(p1: Place<any>, p2: Place<any>): MutualExclusion {\n return { type: 'mutual-exclusion', p1, p2 };\n}\n\nexport function placeBound(place: Place<any>, bound: number): PlaceBound {\n return { type: 'place-bound', place, bound };\n}\n\nexport function unreachable(places: ReadonlySet<Place<any>>): Unreachable {\n return { type: 'unreachable', places: new Set(places) };\n}\n\n/** Branch / budget place bound (NU-040). See {@link BranchPlaceBound}. */\nexport function branchPlaceBound(place: Place<any>, bound: number): BranchPlaceBound {\n return { type: 'branch-place-bound', place, bound };\n}\n\n/** Joined-or-dead-lettered at quiescence (NU-040). See {@link JoinedOrDeadLettered}. */\nexport function joinedOrDeadLettered(pending: Place<any>): JoinedOrDeadLettered {\n return { type: 'joined-or-dead-lettered', pending };\n}\n\n/** Human-readable description of a property. */\nexport function propertyDescription(prop: SmtProperty): string {\n switch (prop.type) {\n case 'deadlock-free':\n return 'Deadlock-freedom';\n case 'mutual-exclusion':\n return `Mutual exclusion of ${prop.p1.name} and ${prop.p2.name}`;\n case 'place-bound':\n return `Place ${prop.place.name} bounded by ${prop.bound}`;\n case 'unreachable':\n return `Unreachability of marking with tokens in {${[...prop.places].map(p => p.name).join(', ')}}`;\n case 'branch-place-bound':\n return `Branch place bound (ν-budget): ${prop.place.name} <= ${prop.bound}`;\n case 'joined-or-dead-lettered':\n return `Joined-or-dead-lettered: ${prop.pending.name} = 0 at quiescence`;\n }\n}\n","import type { Transition } from '../../core/transition.js';\n\n/**\n * A flattened transition with pre/post vectors for SMT encoding.\n *\n * Each Transition with XOR outputs is expanded into multiple FlatTransitions\n * (one per branch). Non-XOR transitions map 1:1.\n */\nexport interface FlatTransition {\n /** Display name (e.g. \"Search_b0\", \"Search_b1\"). */\n readonly name: string;\n /** The original transition. */\n readonly source: Transition;\n /** Which XOR branch (-1 if no XOR). */\n readonly branchIndex: number;\n /** Tokens consumed per place (indexed by place index). */\n readonly preVector: readonly number[];\n /** Tokens produced per place (indexed by place index). */\n readonly postVector: readonly number[];\n /** Place indices where inhibitor arcs block firing. */\n readonly inhibitorPlaces: readonly number[];\n /** Place indices requiring a token without consuming. */\n readonly readPlaces: readonly number[];\n /** Place indices set to 0 on firing. */\n readonly resetPlaces: readonly number[];\n /** True at index i means place i uses All/AtLeast semantics. */\n readonly consumeAll: readonly boolean[];\n}\n\nexport function flatTransition(\n name: string,\n source: Transition,\n branchIndex: number,\n preVector: number[],\n postVector: number[],\n inhibitorPlaces: number[],\n readPlaces: number[],\n resetPlaces: number[],\n consumeAll: boolean[],\n): FlatTransition {\n return {\n name,\n source,\n branchIndex,\n preVector,\n postVector,\n inhibitorPlaces,\n readPlaces,\n resetPlaces,\n consumeAll,\n };\n}\n","/**\n * Analysis mode for environment places in state class graph construction.\n */\nexport type EnvironmentAnalysisMode =\n | { readonly type: 'always-available' }\n | { readonly type: 'bounded'; readonly maxTokens: number }\n | { readonly type: 'ignore' };\n\n/** Assumes environment places always have sufficient tokens. */\nexport function alwaysAvailable(): EnvironmentAnalysisMode {\n return { type: 'always-available' };\n}\n\n/** Analyzes with a bounded number of tokens in environment places. */\nexport function bounded(maxTokens: number): EnvironmentAnalysisMode {\n if (maxTokens < 0) throw new Error('maxTokens must be non-negative');\n return { type: 'bounded', maxTokens };\n}\n\n/** Treats environment places as regular places (default). */\nexport function ignore(): EnvironmentAnalysisMode {\n return { type: 'ignore' };\n}\n","/**\n * @module net-flattener\n *\n * Flattens a PetriNet into integer-indexed pre/post vectors for SMT encoding.\n *\n * **XOR expansion**: Transitions with XOR output specs are expanded into multiple\n * flat transitions — one per deterministic branch. Each branch produces tokens to\n * exactly one XOR child's places. This converts non-deterministic output routing\n * into separate transitions that the SMT solver can reason about independently.\n *\n * **Vector construction**: For each flat transition, builds:\n * - `preVector[p]`: tokens consumed from place p (input cardinality)\n * - `postVector[p]`: tokens produced to place p (from the selected branch)\n * - `consumeAll[p]`: true for `all`/`at-least` inputs (consume everything)\n * - Index arrays for inhibitor, read, and reset arcs\n *\n * Places are sorted by name for stable, deterministic indexing across runs.\n */\nimport type { PetriNet } from '../../core/petri-net.js';\nimport type { Place, EnvironmentPlace } from '../../core/place.js';\nimport type { Out } from '../../core/out.js';\nimport type { FlatNet } from './flat-net.js';\nimport { flatTransition } from './flat-transition.js';\nimport { enumerateBranches, allPlaces as outAllPlaces } from '../../core/out.js';\nimport { type EnvironmentAnalysisMode, alwaysAvailable } from '../analysis/environment-analysis-mode.js';\n\n// The SMT path shares the single 3-mode EnvironmentAnalysisMode with the state\n// class graph (VER-006): AlwaysAvailable / Bounded(k) / Ignore. Re-exported here\n// for the encoding barrel so existing `libpetri/verification` consumers resolve it.\nexport { type EnvironmentAnalysisMode, alwaysAvailable, bounded, ignore } from '../analysis/environment-analysis-mode.js';\n\n/**\n * Flattens a PetriNet into a FlatNet suitable for SMT encoding.\n *\n * Flattening involves:\n * 1. Assigning each place a stable integer index (sorted by name)\n * 2. Expanding XOR outputs into separate flat transitions (one per branch)\n * 3. Building pre/post vectors from input/output specs\n * 4. Recording inhibitor, read, and reset arcs\n * 5. Setting environment bounds for bounded analysis mode\n */\nexport function flatten(\n net: PetriNet,\n environmentPlaces: Set<EnvironmentPlace<any>> = new Set(),\n environmentMode: EnvironmentAnalysisMode = alwaysAvailable(),\n): FlatNet {\n // 1. Collect ALL places\n const allPlacesSet = new Map<string, Place<any>>();\n for (const p of net.places) {\n allPlacesSet.set(p.name, p);\n }\n for (const t of net.transitions) {\n for (const inSpec of t.inputSpecs) {\n allPlacesSet.set(inSpec.place.name, inSpec.place);\n }\n if (t.outputSpec !== null) {\n for (const p of outAllPlaces(t.outputSpec)) {\n allPlacesSet.set(p.name, p);\n }\n }\n for (const arc of t.inhibitors) allPlacesSet.set(arc.place.name, arc.place);\n for (const arc of t.reads) allPlacesSet.set(arc.place.name, arc.place);\n for (const arc of t.resets) allPlacesSet.set(arc.place.name, arc.place);\n }\n\n // Sort by name for stable indexing. Unicode code-point order (not the\n // locale-sensitive `localeCompare`), so the index agrees with the Rust and Java\n // flatteners on every name and the emitted scripts stay byte-identical (VER-013).\n const places = [...allPlacesSet.values()].sort((a, b) => compareCodePoints(a.name, b.name));\n\n const placeIndex = new Map<string, number>();\n for (let i = 0; i < places.length; i++) {\n placeIndex.set(places[i]!.name, i);\n }\n\n // 2. Compute environment bounds (legacy post-cap) and the injection map.\n // The injection map drives the encoder's env-injection rule and the\n // incidence-matrix injector columns; bounds remain a harmless extra cap.\n const environmentBounds = new Map<string, number>();\n const environmentInjection = new Map<string, number | null>();\n switch (environmentMode.type) {\n case 'always-available':\n for (const ep of environmentPlaces) {\n environmentInjection.set(ep.place.name, null);\n }\n break;\n case 'bounded':\n for (const ep of environmentPlaces) {\n environmentBounds.set(ep.place.name, environmentMode.maxTokens);\n environmentInjection.set(ep.place.name, environmentMode.maxTokens);\n }\n break;\n case 'ignore':\n // Not modeled: env places stay ordinary (frozen at their initial count).\n break;\n }\n\n // 3. Expand transitions\n const n = places.length;\n const flatTransitions = [];\n\n for (const transition of net.transitions) {\n const branches = enumerateOutputBranches(transition);\n\n for (let branchIdx = 0; branchIdx < branches.length; branchIdx++) {\n const branchPlaces = branches[branchIdx]!;\n const name = branches.length > 1\n ? `${transition.name}_b${branchIdx}`\n : transition.name;\n\n // Build pre-vector and consumeAll flags\n const preVector = new Array<number>(n).fill(0);\n const consumeAll = new Array<boolean>(n).fill(false);\n\n for (const inSpec of transition.inputSpecs) {\n const idx = placeIndex.get(inSpec.place.name);\n if (idx === undefined) continue;\n\n switch (inSpec.type) {\n case 'one':\n preVector[idx] = 1;\n break;\n case 'exactly':\n preVector[idx] = inSpec.count;\n break;\n case 'all':\n preVector[idx] = 1;\n consumeAll[idx] = true;\n break;\n case 'at-least':\n preVector[idx] = inSpec.minimum;\n consumeAll[idx] = true;\n break;\n }\n }\n\n // Build post-vector from branch output places\n const postVector = new Array<number>(n).fill(0);\n for (const p of branchPlaces) {\n const idx = placeIndex.get(p.name);\n if (idx !== undefined) {\n postVector[idx] = 1;\n }\n }\n\n // Inhibitor places\n const inhibitorPlaces = transition.inhibitors\n .map(arc => placeIndex.get(arc.place.name))\n .filter((idx): idx is number => idx !== undefined);\n\n // Read places\n const readPlaces = transition.reads\n .map(arc => placeIndex.get(arc.place.name))\n .filter((idx): idx is number => idx !== undefined);\n\n // Reset places\n const resetPlaces = transition.resets\n .map(arc => placeIndex.get(arc.place.name))\n .filter((idx): idx is number => idx !== undefined);\n\n flatTransitions.push(flatTransition(\n name,\n transition,\n branches.length > 1 ? branchIdx : -1,\n preVector,\n postVector,\n inhibitorPlaces,\n readPlaces,\n resetPlaces,\n consumeAll,\n ));\n }\n }\n\n return {\n places,\n placeIndex,\n transitions: flatTransitions,\n environmentBounds,\n environmentInjection,\n };\n}\n\nfunction enumerateOutputBranches(t: { outputSpec: Out | null }): ReadonlySet<Place<any>>[] {\n if (t.outputSpec !== null) {\n return enumerateBranches(t.outputSpec) as ReadonlySet<Place<any>>[];\n }\n // No outputs (sink transition)\n return [new Set()];\n}\n\n/** Lexicographic order on Unicode code points (what Rust's `String` order is). */\nexport function compareCodePoints(a: string, b: string): number {\n const ia = a[Symbol.iterator]();\n const ib = b[Symbol.iterator]();\n for (;;) {\n const na = ia.next();\n const nb = ib.next();\n if (na.done && nb.done) return 0;\n if (na.done) return -1;\n if (nb.done) return 1;\n const ca = na.value.codePointAt(0)!;\n const cb = nb.value.codePointAt(0)!;\n if (ca !== cb) return ca - cb;\n }\n}\n","import type { FlatNet } from './flat-net.js';\n\n/**\n * Incidence matrix for a flattened Petri net.\n *\n * The incidence matrix C is defined as C[t][p] = post[t][p] - pre[t][p].\n * It captures the net effect of each transition on each place.\n *\n * P-invariants are solutions to y^T * C = 0, found via null space\n * computation on C^T.\n */\nexport class IncidenceMatrix {\n private readonly _pre: readonly (readonly number[])[];\n private readonly _post: readonly (readonly number[])[];\n private readonly _incidence: readonly (readonly number[])[];\n private readonly _numTransitions: number;\n private readonly _numPlaces: number;\n\n private constructor(\n pre: number[][],\n post: number[][],\n incidence: number[][],\n numTransitions: number,\n numPlaces: number,\n ) {\n this._pre = pre;\n this._post = post;\n this._incidence = incidence;\n this._numTransitions = numTransitions;\n this._numPlaces = numPlaces;\n }\n\n /**\n * Computes the incidence matrix from a FlatNet.\n *\n * Environment-injected places (VER-006) each contribute one extra **injector\n * column** (a virtual transition that produces one token into that place and\n * consumes nothing). This makes P-invariant computation env-aware: a valid\n * invariant `y` must satisfy `y^T·C = 0` for the injector column too, forcing\n * `y[envPlace] = 0` and thereby discarding closed-net conservation laws (e.g.\n * `IN + OUT = const`) that would otherwise vacuously bound an injectable place.\n */\n static from(flatNet: FlatNet): IncidenceMatrix {\n const T = flatNet.transitions.length;\n const P = flatNet.places.length;\n\n const pre: number[][] = [];\n const post: number[][] = [];\n const incidence: number[][] = [];\n\n for (let t = 0; t < T; t++) {\n const ft = flatNet.transitions[t]!;\n const preRow = new Array<number>(P);\n const postRow = new Array<number>(P);\n const incRow = new Array<number>(P);\n\n for (let p = 0; p < P; p++) {\n preRow[p] = ft.preVector[p]!;\n postRow[p] = ft.postVector[p]!;\n incRow[p] = postRow[p]! - preRow[p]!;\n }\n\n pre.push(preRow);\n post.push(postRow);\n incidence.push(incRow);\n }\n\n // Injector columns (one per injected environment place): pre = 0, post = e_p.\n let injectorCount = 0;\n for (const name of flatNet.environmentInjection.keys()) {\n const idx = flatNet.placeIndex.get(name);\n if (idx == null) continue;\n const preRow = new Array<number>(P).fill(0);\n const postRow = new Array<number>(P).fill(0);\n const incRow = new Array<number>(P).fill(0);\n postRow[idx] = 1;\n incRow[idx] = 1;\n pre.push(preRow);\n post.push(postRow);\n incidence.push(incRow);\n injectorCount++;\n }\n\n return new IncidenceMatrix(pre, post, incidence, T + injectorCount, P);\n }\n\n /**\n * Returns C^T (transpose of incidence matrix), dimensions [P][T].\n * Used for P-invariant computation: null space of C^T gives P-invariants.\n */\n transposedIncidence(): number[][] {\n const ct: number[][] = [];\n for (let p = 0; p < this._numPlaces; p++) {\n const row = new Array<number>(this._numTransitions);\n for (let t = 0; t < this._numTransitions; t++) {\n row[t] = this._incidence[t]![p]!;\n }\n ct.push(row);\n }\n return ct;\n }\n\n /** Returns the pre-matrix (tokens consumed). T×P. */\n pre(): readonly (readonly number[])[] { return this._pre; }\n\n /** Returns the post-matrix (tokens produced). T×P. */\n post(): readonly (readonly number[])[] { return this._post; }\n\n /** Returns the incidence matrix C[t][p] = post - pre. T×P. */\n incidence(): readonly (readonly number[])[] { return this._incidence; }\n\n numTransitions(): number { return this._numTransitions; }\n numPlaces(): number { return this._numPlaces; }\n}\n","/**\n * A P-invariant (place invariant) of a Petri net.\n *\n * A P-invariant is a vector y such that y^T * C = 0, where C is the\n * incidence matrix. This means that for any reachable marking M:\n * sum(y_i * M_i) = constant, where constant = sum(y_i * M0_i).\n *\n * P-invariants provide structural bounds on places and are used as\n * strengthening lemmas for the IC3/PDR engine.\n */\nexport interface PInvariant {\n /** Weight vector (one entry per place index). */\n readonly weights: readonly number[];\n /** The invariant value sum(y_i * M0_i). */\n readonly constant: number;\n /** Set of place indices where weight != 0. */\n readonly support: ReadonlySet<number>;\n}\n\nexport function pInvariant(weights: number[], constant: number, support: Set<number>): PInvariant {\n return { weights, constant, support };\n}\n\nexport function pInvariantToString(inv: PInvariant): string {\n const parts: string[] = [];\n for (const i of inv.support) {\n if (inv.weights[i] !== 1) {\n parts.push(`${inv.weights[i]}*p${i}`);\n } else {\n parts.push(`p${i}`);\n }\n }\n return `PInvariant[${parts.join(' + ')} = ${inv.constant}]`;\n}\n","/**\n * @module p-invariant-computer\n *\n * Computes P-invariants of a Petri net via integer Gaussian elimination (Farkas' algorithm).\n *\n * **Algorithm**: A P-invariant is a non-negative integer vector y such that y^T · C = 0\n * (where C is the incidence matrix). This expresses a conservation law: the weighted\n * token sum Σ(y_i · M[i]) is constant across all reachable markings.\n *\n * **Farkas variant**: Constructs the augmented matrix [C^T | I_P] and row-reduces\n * the C^T portion to zero using integer elimination (no floating point). Rows where\n * the C^T part becomes all-zero yield invariant vectors from the identity part.\n * Row normalization by GCD keeps values small during elimination.\n *\n * **Integer Gaussian elimination**: Each elimination step multiplies rows by pivot\n * coefficients (a·row - b·pivotRow) to avoid fractions. This preserves integer\n * arithmetic throughout, critical for exact invariant computation.\n *\n * Invariants are used to strengthen SMT queries (added as constraints on M').\n */\nimport type { FlatNet } from '../encoding/flat-net.js';\nimport type { IncidenceMatrix } from '../encoding/incidence-matrix.js';\nimport type { MarkingState } from '../marking-state.js';\nimport type { PInvariant } from './p-invariant.js';\nimport { pInvariant } from './p-invariant.js';\n\n/**\n * Computes P-invariants of a Petri net via integer Gaussian elimination.\n *\n * P-invariants are non-negative integer vectors y where y^T * C = 0.\n * They express conservation laws: the weighted token sum is constant\n * across all reachable markings.\n *\n * Algorithm: compute the null space of C^T using integer row reduction\n * with an augmented identity matrix (Farkas' algorithm variant).\n */\nexport function computePInvariants(\n matrix: IncidenceMatrix,\n flatNet: FlatNet,\n initialMarking: MarkingState,\n): PInvariant[] {\n const P = matrix.numPlaces();\n const T = matrix.numTransitions();\n\n if (P === 0 || T === 0) return [];\n\n // We want to find y such that y^T * C = 0, i.e., C^T * y = 0\n // Start with augmented matrix [C^T | I_P]\n // Row-reduce C^T part to zero; the I_P part gives the invariant vectors.\n const ct = matrix.transposedIncidence(); // P × T\n\n // Augmented matrix: P rows, T + P columns\n // Use regular numbers (safe for nets with < ~50 places/transitions)\n const cols = T + P;\n const augmented: number[][] = [];\n for (let i = 0; i < P; i++) {\n const row = new Array<number>(cols).fill(0);\n for (let j = 0; j < T; j++) {\n row[j] = ct[i]![j]!;\n }\n row[T + i] = 1; // identity part\n augmented.push(row);\n }\n\n // Integer Gaussian elimination on the C^T part (columns 0..T-1)\n let pivotRow = 0;\n for (let col = 0; col < T && pivotRow < P; col++) {\n // Find pivot (non-zero entry in this column)\n let pivot = -1;\n for (let row = pivotRow; row < P; row++) {\n if (augmented[row]![col] !== 0) {\n pivot = row;\n break;\n }\n }\n if (pivot === -1) continue; // free variable\n\n // Swap pivot row\n if (pivot !== pivotRow) {\n const tmp = augmented[pivotRow]!;\n augmented[pivotRow] = augmented[pivot]!;\n augmented[pivot] = tmp;\n }\n\n // Eliminate this column in all other rows\n for (let row = 0; row < P; row++) {\n if (row === pivotRow || augmented[row]![col] === 0) continue;\n\n const a = augmented[pivotRow]![col]!;\n const b = augmented[row]![col]!;\n\n // row = a*row - b*pivotRow (keeps integers, eliminates col)\n for (let c = 0; c < cols; c++) {\n augmented[row]![c] = a * augmented[row]![c]! - b * augmented[pivotRow]![c]!;\n }\n\n // Normalize by GCD to keep values small\n normalizeRow(augmented[row]!, cols);\n }\n\n pivotRow++;\n }\n\n // Extract invariants: rows where C^T part is all zeros\n const invariants: PInvariant[] = [];\n for (let row = 0; row < P; row++) {\n let isZero = true;\n for (let col = 0; col < T; col++) {\n if (augmented[row]![col] !== 0) {\n isZero = false;\n break;\n }\n }\n if (!isZero) continue;\n\n // Extract the weight vector from the identity part. The elimination above\n // runs in f64 `number`, so a row whose identity part left the safe-integer\n // range carries ROUNDED weights, not exact ones. Emit such a row raw — no\n // sign normalisation, no GCD reduction, which would otherwise launder e.g.\n // (2^54, 2^54) into a plausible-looking (1, 1) — and let\n // validateInvariantsExact drop it by name with the overflow reason.\n if (!rowIsExact(augmented[row]!, T, P)) {\n invariants.push(rawInvariant(augmented[row]!, T, P, flatNet, initialMarking));\n continue;\n }\n\n // A signed null-space basis, exactly as the Rust reference computes it\n // (VER-013 script parity): a mixed-sign row is a conservation law like any\n // other and passes the same exact gate; a semi-negative row is the same law\n // negated. Non-negativity is only required of the P-semiflows that bound the\n // colour slots (computePSemiflows), never of the strengthening laws. Rows were\n // GCD-normalised during the elimination, so no renormalisation here.\n const weights = new Array<number>(P);\n let hasPositive = false;\n let hasNegative = false;\n for (let i = 0; i < P; i++) {\n weights[i] = augmented[row]![T + i]!;\n if (weights[i]! > 0) hasPositive = true;\n if (weights[i]! < 0) hasNegative = true;\n }\n if (!hasPositive && !hasNegative) continue;\n if (!hasPositive) {\n for (let i = 0; i < P; i++) weights[i] = -weights[i]!;\n }\n\n // Compute support and constant\n const support = new Set<number>();\n let constant = 0;\n for (let i = 0; i < P; i++) {\n if (weights[i] !== 0) {\n support.add(i);\n const place = flatNet.places[i]!;\n constant += weights[i]! * initialMarking.tokens(place);\n }\n }\n\n invariants.push(pInvariant(weights, constant, support));\n }\n\n return invariants;\n}\n\n/** True when every weight in the identity part of `row` is an exact integer. */\nfunction rowIsExact(row: readonly number[], T: number, P: number): boolean {\n for (let i = 0; i < P; i++) {\n if (!Number.isSafeInteger(row[T + i]!)) return false;\n }\n return true;\n}\n\n/** The identity part of `row` verbatim, so the exact re-check sees what f64 produced. */\nfunction rawInvariant(\n row: readonly number[],\n T: number,\n P: number,\n flatNet: FlatNet,\n initialMarking: MarkingState,\n): PInvariant {\n const weights = new Array<number>(P);\n const support = new Set<number>();\n let constant = 0;\n for (let i = 0; i < P; i++) {\n weights[i] = row[T + i]!;\n if (weights[i] !== 0) {\n support.add(i);\n constant += weights[i]! * initialMarking.tokens(flatNet.places[i]!);\n }\n }\n return pInvariant(weights, constant, support);\n}\n\n/** An invariant rejected by {@link validateInvariantsExact}, with the reason it failed. */\nexport interface DroppedInvariant {\n readonly invariant: PInvariant;\n readonly reason: string;\n}\n\n/** Result of {@link validateInvariantsExact}: exact-verified invariants plus the rejects. */\nexport interface InvariantValidationResult {\n readonly valid: readonly PInvariant[];\n readonly dropped: readonly DroppedInvariant[];\n}\n\n/**\n * Re-verifies each computed P-invariant **exactly** (BigInt) and drops any that fails.\n *\n * {@link computePInvariants} runs its integer Gaussian elimination in f64 `number`\n * with no overflow guard, and the encoder conjoins each invariant into the CHC\n * transition-rule *body*: a numerically wrong invariant therefore removes reachable\n * successors and can certify a false `Proven`. This pass must run between\n * computation and use, so nothing imprecise ever reaches the encoder — mirroring\n * the defensive style of {@link computePSemiflows}, which drops rows rather than\n * keep imprecise ones.\n *\n * Checks per invariant `y`:\n * - every weight and the constant is a safe integer (`Number.isSafeInteger`),\n * - **H1 linearity**: `y` is zero on every place with non-linear consumption —\n * see below,\n * - `y·C = 0` exactly, per transition column of the incidence matrix (BigInt),\n * - the stored constant equals the exactly recomputed `y·M0`.\n *\n * `flatNet` and `initialMarking` are REQUIRED: they were once optional, and\n * omitting them silently disabled the H1 guard and the constant re-check —\n * i.e. the call had a configuration in which it certified unsound invariants.\n *\n * **H1 linearity guard** (`lean/Libpetri/Strengthening.lean`,\n * `consume_all_hypothesis_is_necessary`): the incidence matrix *linearizes*\n * consumption — its column is `post − pre` with `pre = requiredCount`, so it says\n * nothing about consume-all or reset semantics, where the encoder's fire relation\n * sets `m'_i = post[i]` and erases however many tokens the place actually held.\n * `y·C = 0` is therefore necessary but NOT sufficient: an invariant weighting such\n * a place can pass the exact gate yet be false on the real net, and conjoined into\n * the CHC rule bodies it prunes genuine successors (false PROVEN). Per the Lean\n * theorem's H1 hypothesis, any invariant with a nonzero weight on a place that is,\n * for any flat transition, a consume-all input place (`all` **and** `at-least` —\n * `atLeast(n)` waits for n but then consumes ALL available, see\n * `consumptionCount` in `core/in.ts`; the linear cardinalities are\n * `one`/`exactly(n)`) or a reset place is dropped here. Env-injectable places need\n * no guard of their own: their injector columns ({@link IncidenceMatrix.from})\n * already force `y = 0` there through the `y·C = 0` check — Strengthening.lean's\n * H3′ sufficiency result (`invariant_strengthening_sound_inj`).\n *\n * Dropping a *valid* conservation law only weakens the encoder's strengthening\n * lemmas (sound); keeping an invalid one is what must never happen.\n */\nexport function validateInvariantsExact(\n matrix: IncidenceMatrix,\n invariants: readonly PInvariant[],\n flatNet: FlatNet,\n initialMarking: MarkingState,\n): InvariantValidationResult {\n const nonlinear = nonlinearPlaces(flatNet);\n const valid: PInvariant[] = [];\n const dropped: DroppedInvariant[] = [];\n for (const inv of invariants) {\n const reason = exactCheckFailure(matrix, inv, nonlinear, flatNet, initialMarking);\n if (reason === null) {\n valid.push(inv);\n } else {\n dropped.push({ invariant: inv, reason });\n }\n }\n return { valid, dropped };\n}\n\n/**\n * Place indices with non-linear consumption on some flat transition — the\n * reset/consume-all arms of H1. The matrix may carry extra injector columns beyond\n * `flatNet.transitions`; injections are linear (`+e_p`) and need no entry here.\n */\nfunction nonlinearPlaces(flatNet: FlatNet): ReadonlySet<number> {\n const nonlinear = new Set<number>();\n for (const ft of flatNet.transitions) {\n for (let p = 0; p < ft.consumeAll.length; p++) {\n if (ft.consumeAll[p]) nonlinear.add(p);\n }\n for (const p of ft.resetPlaces) nonlinear.add(p);\n }\n return nonlinear;\n}\n\n/** Returns why `inv` fails the exact re-check, or null when it passes. */\nfunction exactCheckFailure(\n matrix: IncidenceMatrix,\n inv: PInvariant,\n nonlinear: ReadonlySet<number>,\n flatNet: FlatNet,\n initialMarking: MarkingState,\n): string | null {\n const P = matrix.numPlaces();\n const T = matrix.numTransitions();\n\n if (inv.weights.length !== P) {\n return `weight vector has ${inv.weights.length} entries, expected ${P}`;\n }\n for (let p = 0; p < P; p++) {\n if (!Number.isSafeInteger(inv.weights[p]!)) {\n return (\n `weight overflow at place '${placeName(flatNet, p)}' ` +\n `(exact value outside this implementation's integer extraction range)`\n );\n }\n }\n if (!Number.isSafeInteger(inv.constant)) {\n return `constant ${inv.constant} is outside the safe-integer range`;\n }\n\n // H1 linearity guard (see the {@link validateInvariantsExact} doc): a nonzero\n // weight on a consume-all or reset place makes the linearized column a lie about\n // the real firing, so the y·C = 0 check below would not certify conservation.\n for (let p = 0; p < inv.weights.length; p++) {\n if (inv.weights[p] !== 0 && nonlinear.has(p)) {\n return (\n `support intersects consume-all/reset place '${placeName(flatNet, p)}' ` +\n `(non-linear consumption; see Strengthening.lean H1)`\n );\n }\n }\n\n // y·C = 0, re-derived in BigInt from the incidence matrix (immune to f64 rounding).\n const y: bigint[] = inv.weights.map((w) => BigInt(w));\n const incidence = matrix.incidence(); // [t][p]\n for (let t = 0; t < T; t++) {\n const row = incidence[t]!;\n let dot = 0n;\n for (let p = 0; p < P; p++) {\n if (y[p] === 0n) continue;\n if (!Number.isSafeInteger(row[p]!)) {\n return `incidence entry ${row[p]} at [t=${t}][p=${p}] is outside the safe-integer range`;\n }\n dot += y[p]! * BigInt(row[p]!);\n }\n if (dot !== 0n) {\n return `y*C is ${dot} (not 0) at ${columnName(flatNet, t)}`;\n }\n }\n\n // Constant = y·M0, recomputed exactly.\n let exact = 0n;\n for (let p = 0; p < P; p++) {\n if (y[p] === 0n) continue;\n const tokens = initialMarking.tokens(flatNet.places[p]!);\n if (!Number.isSafeInteger(tokens)) {\n return `initial marking of place ${p} (${tokens}) is outside the safe-integer range`;\n }\n exact += y[p]! * BigInt(tokens);\n }\n if (exact !== BigInt(inv.constant)) {\n return `constant ${inv.constant} does not match exact y*M0 = ${exact}`;\n }\n\n return null;\n}\n\n/** Place name for a flat place index (falls back to `#idx` off the end). */\nfunction placeName(flatNet: FlatNet, p: number): string {\n return flatNet.places[p]?.name ?? `#${p}`;\n}\n\n/**\n * Name of incidence column `t`. Columns past `flatNet.transitions` are the\n * per-env-place injector columns {@link IncidenceMatrix.from} appends.\n */\nfunction columnName(flatNet: FlatNet, t: number): string {\n const ft = flatNet.transitions[t];\n return ft != null\n ? `transition '${ft.name}'`\n : `env-injector column ${t - flatNet.transitions.length}`;\n}\n\n/**\n * A P-semiflow generator row during Colom–Silva elimination: the running\n * transition signature `y·C` plus the non-negative place weight `y` that produced\n * it. A row survives an elimination step only when the current column of `y·C` is\n * zero, so after every transition is eliminated the surviving rows have `y·C = 0`.\n */\ninterface SemiflowRow {\n readonly sig: number[];\n readonly weight: number[];\n}\n\n/**\n * Computes minimal **P-semiflows** — non-negative place weightings `y` with\n * `y·C = 0` — via the Colom–Silva / Farkas method. Unlike {@link computePInvariants}\n * (a signed null-space basis), every returned `PInvariant.weights` is non-negative:\n * a genuine P-semiflow, with `constant = y·M0`. A non-negative conservation law\n * soundly **bounds** the token sum over its support: `Σ_{support} M(p) ≤ y·M0`. Used\n * to bound the number of simultaneously-live colours in the name-coloured encoder\n * (see `colourSlotBound`).\n *\n * Mirrors the Rust reference `compute_p_semiflows`.\n */\n/** Same conservation law: identical weight vector and constant. */\nfunction sameInvariant(a: PInvariant, b: PInvariant): boolean {\n if (a.constant !== b.constant || a.weights.length !== b.weights.length) return false;\n for (let i = 0; i < a.weights.length; i++) {\n if (a.weights[i] !== b.weights[i]) return false;\n }\n return true;\n}\n\n/**\n * VER-007 — the semiflow union. Appends every gate-validated P-semiflow that is not\n * already a basis row (same weights, same constant) to `invariants`, returning the\n * strengthened list and how many rows were added.\n *\n * The null-space basis is one basis of many: elimination hands back mixed-sign rows\n * and rows that fold a reset place into a chain whose other combinations avoid it,\n * both lost to the exact gate — on a reset-heavy net every law of the chains those\n * arcs touch, leaving IC3 to rediscover conservation it cannot within any practical\n * budget. The Farkas rows ({@link computePSemiflows}) are the minimal laws of the\n * net. Conjoining them alongside the basis is pure strengthening (`Semiflow.lean`,\n * `semiflow_union_sound`) **provided both lists passed the same exact gate**\n * (`semiflow_gate_is_necessary`) — the caller's obligation; this only merges.\n */\nexport function strengthenWithSemiflows(\n invariants: readonly PInvariant[],\n semiflows: readonly PInvariant[],\n): { readonly invariants: readonly PInvariant[]; readonly added: number } {\n const strengthened = [...invariants];\n let added = 0;\n for (const sf of semiflows) {\n if (!strengthened.some((inv) => sameInvariant(inv, sf))) {\n strengthened.push(sf);\n added++;\n }\n }\n return { invariants: strengthened, added };\n}\n\nexport function computePSemiflows(\n matrix: IncidenceMatrix,\n flatNet: FlatNet,\n initialMarking: MarkingState,\n): PInvariant[] {\n const np = matrix.numPlaces();\n const nt = matrix.numTransitions();\n if (np === 0) return [];\n\n const incidence = matrix.incidence(); // [t][p]\n\n // One generator row per place: signature = the place's column of C (over\n // transitions), weight = e_p. Eliminate one transition column at a time using only\n // non-negative combinations, so accumulated weights stay non-negative.\n let rows: SemiflowRow[] = [];\n for (let p = 0; p < np; p++) {\n const sig = new Array<number>(nt);\n for (let t = 0; t < nt; t++) sig[t] = incidence[t]![p]!;\n const weight = new Array<number>(np).fill(0);\n weight[p] = 1;\n rows.push({ sig, weight });\n }\n\n for (let t = 0; t < nt; t++) {\n const next: SemiflowRow[] = rows.filter((r) => r.sig[t] === 0);\n const pos = rows.filter((r) => r.sig[t]! > 0);\n const neg = rows.filter((r) => r.sig[t]! < 0);\n for (const rp of pos) {\n for (const rn of neg) {\n const cp = -rn.sig[t]!; // > 0\n const cn = rp.sig[t]!; // > 0\n // Checked combination: `number` is f64 and loses integer precision above 2^53,\n // so DROP this generator if any coefficient leaves the safe-integer range rather\n // than keep an imprecise (invalid) row. colourSlotBound then falls back to the\n // sound over-approximation — never an under-approximation.\n const sig = combineRow(cp, rp.sig, cn, rn.sig);\n const weight = combineRow(cp, rp.weight, cn, rn.weight);\n if (sig === null || weight === null) continue;\n reduceGcd(sig, weight);\n next.push({ sig, weight });\n }\n }\n rows = keepSupportMinimal(next);\n if (rows.length > 8192) rows.length = 8192; // safety backstop against blow-up\n }\n\n const semiflows: PInvariant[] = [];\n for (const { weight } of rows) {\n if (!weight.some((x) => x !== 0)) continue;\n const support = new Set<number>();\n let constant = 0;\n for (let p = 0; p < np; p++) {\n if (weight[p] !== 0) {\n support.add(p);\n constant += weight[p]! * initialMarking.tokens(flatNet.places[p]!);\n }\n }\n // Drop a semiflow whose `Σ weight·M0` left the safe-integer range — fewer covering\n // semiflows just means colourSlotBound falls back soundly.\n if (!Number.isSafeInteger(constant)) continue;\n semiflows.push(pInvariant(weight, constant, support));\n }\n return semiflows;\n}\n\n/**\n * `cp*a + cn*b` componentwise, or null if any result leaves the safe-integer range\n * (`number` is f64 and loses integer precision above 2^53) — the caller then drops the\n * generator and the colour bound falls back soundly rather than using imprecise values.\n */\nfunction combineRow(\n cp: number,\n a: readonly number[],\n cn: number,\n b: readonly number[],\n): number[] | null {\n const out = new Array<number>(a.length);\n for (let i = 0; i < a.length; i++) {\n const v = cp * a[i]! + cn * b[i]!;\n if (!Number.isSafeInteger(v)) return null;\n out[i] = v;\n }\n return out;\n}\n\n/**\n * Divides a generator row's signature and weight by the GCD of all their absolute\n * values (keeps the P-semiflow minimal and the integers small). Mutates in place.\n */\nfunction reduceGcd(sig: number[], weight: number[]): void {\n let g = 0;\n for (const v of sig) g = gcd(g, Math.abs(v));\n for (const v of weight) g = gcd(g, Math.abs(v));\n if (g > 1) {\n for (let i = 0; i < sig.length; i++) sig[i] = sig[i]! / g;\n for (let i = 0; i < weight.length; i++) weight[i] = weight[i]! / g;\n }\n}\n\n/**\n * Drops any row whose weight-support is a strict superset of another's — a\n * non-minimal combination only inflates the set (and can cause combinatorial\n * blow-up). Mirrors the Rust reference `keep_support_minimal`.\n */\nfunction keepSupportMinimal(rows: SemiflowRow[]): SemiflowRow[] {\n const supports: number[][] = rows.map((r) => {\n const s: number[] = [];\n for (let i = 0; i < r.weight.length; i++) if (r.weight[i] !== 0) s.push(i);\n return s;\n });\n const keep = new Array<boolean>(rows.length).fill(true);\n for (let i = 0; i < rows.length; i++) {\n if (!keep[i]) continue;\n for (let j = 0; j < rows.length; j++) {\n if (i === j || !keep[j]) continue;\n if (supports[j]!.length < supports[i]!.length && supports[j]!.every((p) => supports[i]!.includes(p))) {\n keep[i] = false;\n break;\n }\n }\n }\n return rows.filter((_, i) => keep[i]);\n}\n\n/**\n * Checks if every place is covered by at least one P-invariant.\n * If true, the net is structurally bounded.\n */\nexport function isCoveredByInvariants(invariants: readonly PInvariant[], numPlaces: number): boolean {\n const covered = new Array<boolean>(numPlaces).fill(false);\n for (const inv of invariants) {\n // Only a non-negative law bounds its support; a mixed-sign law (which the signed\n // null-space basis now carries) says nothing about boundedness.\n if (inv.weights.some((w) => w < 0)) continue;\n for (const idx of inv.support) {\n if (idx < numPlaces) covered[idx] = true;\n }\n }\n return covered.every(c => c);\n}\n\nfunction normalizeRow(row: number[], cols: number): void {\n let g = 0;\n for (let c = 0; c < cols; c++) {\n if (row[c] !== 0) {\n g = gcd(g, Math.abs(row[c]!));\n }\n }\n if (g > 1) {\n for (let c = 0; c < cols; c++) {\n row[c] = row[c]! / g;\n }\n }\n}\n\nfunction gcd(a: number, b: number): number {\n while (b !== 0) {\n const t = b;\n b = a % b;\n a = t;\n }\n return a;\n}\n\n/**\n * The invariants in canonical order (VER-013): by ascending support, then weights,\n * then constant, each compared lexicographically. The same order the Rust and Java\n * verifiers apply, so the strengthened scripts are byte-identical.\n */\nexport function canonicalInvariantOrder(invariants: readonly PInvariant[]): PInvariant[] {\n const lex = (a: readonly number[], b: readonly number[]): number => {\n const n = Math.min(a.length, b.length);\n for (let i = 0; i < n; i++) {\n if (a[i]! !== b[i]!) return a[i]! - b[i]!;\n }\n return a.length - b.length;\n };\n const support = (inv: PInvariant): number[] => [...inv.support].sort((x, y) => x - y);\n return [...invariants].sort(\n (a, b) => lex(support(a), support(b)) || lex(a.weights, b.weights) || a.constant - b.constant,\n );\n}\n","/**\n * @module structural-check\n *\n * Structural deadlock pre-check using siphon/trap analysis (Commoner's theorem).\n *\n * **Commoner's theorem**: A Petri net is deadlock-free if every siphon contains\n * an initially marked trap.\n *\n * **Siphon**: A set of places S where every transition that outputs to S also\n * inputs from S. Key property: once all places in a siphon become empty,\n * they can never be re-marked. An empty siphon can cause deadlock.\n *\n * **Trap**: A set of places S where every transition that inputs from S also\n * outputs to S. Key property: once any place in a trap is marked,\n * the trap remains marked forever.\n *\n * **Algorithm**: For each place, compute the minimal siphon containing it via\n * fixed-point expansion. For each siphon, find the maximal trap within it\n * (fixed-point contraction). If every siphon contains an initially-marked\n * trap, deadlock-freedom is proven structurally — no SMT query needed.\n *\n * Limited to nets with ≤50 places to bound enumeration cost.\n */\nimport type { FlatNet } from '../encoding/flat-net.js';\nimport type { MarkingState } from '../marking-state.js';\n\nconst MAX_PLACES_FOR_SIPHON_ANALYSIS = 50;\n\n/**\n * Result of structural deadlock check using siphon/trap analysis.\n */\nexport type StructuralCheckResult =\n | { readonly type: 'no-potential-deadlock' }\n | { readonly type: 'potential-deadlock'; readonly siphon: ReadonlySet<number> }\n | { readonly type: 'inconclusive'; readonly reason: string };\n\n/**\n * Structural deadlock pre-check using siphon/trap analysis.\n *\n * Commoner's theorem: a Petri net is deadlock-free if every siphon\n * contains a marked trap.\n *\n * A siphon is a set of places S such that every transition with\n * an output in S also has an input in S. Once empty, a siphon stays empty.\n *\n * A trap is a set of places S such that every transition with\n * an input in S also has an output in S. Once marked, a trap stays marked.\n */\nexport function structuralCheck(flatNet: FlatNet, initialMarking: MarkingState): StructuralCheckResult {\n const P = flatNet.places.length;\n\n if (P === 0) {\n return { type: 'no-potential-deadlock' };\n }\n\n if (P > MAX_PLACES_FOR_SIPHON_ANALYSIS) {\n return { type: 'inconclusive', reason: `Net has ${P} places, siphon enumeration skipped` };\n }\n\n const siphons = findMinimalSiphons(flatNet);\n\n if (siphons.length === 0) {\n return { type: 'no-potential-deadlock' };\n }\n\n for (const siphon of siphons) {\n const trap = findMaximalTrapIn(flatNet, siphon);\n\n if (trap.size === 0 || !isMarked(trap, flatNet, initialMarking)) {\n return { type: 'potential-deadlock', siphon };\n }\n }\n\n return { type: 'no-potential-deadlock' };\n}\n\n/**\n * Finds minimal siphons by checking all non-empty subsets of deadlock-enabling places.\n * Uses a fixed-point approach: start from each place and grow the siphon.\n */\nexport function findMinimalSiphons(flatNet: FlatNet): ReadonlySet<number>[] {\n const P = flatNet.places.length;\n const siphons: Set<number>[] = [];\n\n // Pre-compute: for each place, which transitions have it as output?\n const placeAsOutput: number[][] = [];\n for (let p = 0; p < P; p++) {\n placeAsOutput.push([]);\n }\n\n for (let t = 0; t < flatNet.transitions.length; t++) {\n const ft = flatNet.transitions[t]!;\n for (let p = 0; p < P; p++) {\n if (ft.postVector[p]! > 0) {\n placeAsOutput[p]!.push(t);\n }\n }\n }\n\n for (let startPlace = 0; startPlace < P; startPlace++) {\n const siphon = computeSiphonContaining(startPlace, flatNet, placeAsOutput);\n if (siphon !== null && siphon.size > 0) {\n let isMinimal = true;\n const toRemove: number[] = [];\n for (let i = 0; i < siphons.length; i++) {\n const existing = siphons[i]!;\n if (setsEqual(existing, siphon)) {\n isMinimal = false;\n break;\n }\n if (isSubsetOf(existing, siphon)) {\n isMinimal = false;\n break;\n }\n if (isSubsetOf(siphon, existing)) {\n toRemove.push(i);\n }\n }\n for (let i = toRemove.length - 1; i >= 0; i--) {\n siphons.splice(toRemove[i]!, 1);\n }\n if (isMinimal) {\n siphons.push(siphon);\n }\n }\n }\n\n return siphons;\n}\n\nfunction computeSiphonContaining(\n startPlace: number,\n flatNet: FlatNet,\n placeAsOutput: number[][],\n): Set<number> | null {\n const siphon = new Set<number>();\n siphon.add(startPlace);\n\n let changed = true;\n while (changed) {\n changed = false;\n const snapshot = [...siphon];\n\n for (const p of snapshot) {\n for (const t of placeAsOutput[p]!) {\n const ft = flatNet.transitions[t]!;\n\n let hasInputInSiphon = false;\n for (let q = 0; q < flatNet.places.length; q++) {\n if (ft.preVector[q]! > 0 && siphon.has(q)) {\n hasInputInSiphon = true;\n break;\n }\n }\n\n if (!hasInputInSiphon) {\n let added = false;\n for (let q = 0; q < flatNet.places.length; q++) {\n if (ft.preVector[q]! > 0) {\n if (!siphon.has(q)) {\n siphon.add(q);\n changed = true;\n }\n added = true;\n break;\n }\n }\n if (!added) {\n return null;\n }\n }\n }\n }\n }\n\n return siphon;\n}\n\n/**\n * Finds the maximal trap within a given set of places.\n * Uses fixed-point: start with the full set and remove places that violate the trap condition.\n */\nexport function findMaximalTrapIn(flatNet: FlatNet, places: ReadonlySet<number>): ReadonlySet<number> {\n const trap = new Set(places);\n\n let changed = true;\n while (changed) {\n changed = false;\n const toRemove: number[] = [];\n\n for (const p of trap) {\n let satisfies = true;\n for (let t = 0; t < flatNet.transitions.length; t++) {\n const ft = flatNet.transitions[t]!;\n if (ft.preVector[p]! > 0) {\n let outputsToTrap = false;\n for (const q of trap) {\n if (ft.postVector[q]! > 0) {\n outputsToTrap = true;\n break;\n }\n }\n if (!outputsToTrap) {\n satisfies = false;\n break;\n }\n }\n }\n if (!satisfies) {\n toRemove.push(p);\n }\n }\n\n if (toRemove.length > 0) {\n for (const p of toRemove) trap.delete(p);\n changed = true;\n }\n }\n\n return trap;\n}\n\nfunction isMarked(placeIndices: ReadonlySet<number>, flatNet: FlatNet, marking: MarkingState): boolean {\n for (const idx of placeIndices) {\n const place = flatNet.places[idx]!;\n if (marking.tokens(place) > 0) return true;\n }\n return false;\n}\n\nfunction setsEqual(a: ReadonlySet<number>, b: ReadonlySet<number>): boolean {\n if (a.size !== b.size) return false;\n for (const v of a) {\n if (!b.has(v)) return false;\n }\n return true;\n}\n\nfunction isSubsetOf(sub: ReadonlySet<number>, sup: ReadonlySet<number>): boolean {\n if (sub.size > sup.size) return false;\n for (const v of sub) {\n if (!sup.has(v)) return false;\n }\n return true;\n}\n","/**\n * @module z3-process\n *\n * The z3 process transport (VER-013).\n *\n * Every SMT query is one `z3` process: the SMT-LIB2 script goes to its stdin in a\n * single write, stdin is closed so the solver sees end-of-file, and both output\n * streams are collected while a wall-clock watchdog waits. The child is killed on\n * every exit path, so a wedged solver can never outlive the query that started it,\n * and no solver state survives between queries, so concurrent verifiers in one\n * process are independent. The solve runs in another process, so the event loop\n * stays free while it works.\n *\n * The executable is `z3` on `PATH` unless {@link Z3_ENV} names another one. It is\n * probed once per verification with `--version` and refused below\n * {@link MIN_Z3_VERSION}; a missing or too-old binary surfaces as an `unknown`\n * verdict whose reason names the command and the environment variable, never as a\n * rejection out of `verify()`. Setting {@link DUMP_ENV} to a directory writes every\n * script and reply there (`NNN-<phase>.smt2`, `.out`, and `.err` when stderr is not\n * empty), which is how a solver reply is reproduced outside the pipeline.\n *\n * Timeouts are per invocation: `-t:<ms>` asks z3 to answer `unknown` after the soft\n * budget, `-T:<s>` (the budget plus {@link GRACE_MS}, rounded up) makes z3 print\n * `timeout` and exit on its own, and the watchdog at the budget plus twice the grace\n * kills whatever ignored both. The Java, TypeScript and Rust transports pass\n * byte-identical argument lists and classify replies identically.\n */\nimport { spawn, spawnSync } from 'node:child_process';\nimport { existsSync, mkdirSync, statSync, writeFileSync } from 'node:fs';\nimport * as path from 'node:path';\nimport { errorLine, timeoutLine } from './smt-text.js';\n\n/** Environment variable naming the z3 executable (default: `z3` on `PATH`). */\nexport const Z3_ENV = 'LIBPETRI_Z3';\n/** Environment variable naming a directory that receives every script and reply. */\nexport const DUMP_ENV = 'LIBPETRI_SMT_DUMP';\n/** Slack between the soft budget and the hard backstops, in milliseconds. */\nexport const GRACE_MS = 1_000;\n/** How long the `--version` probe may take before it counts as unavailable. */\nconst VERSION_PROBE_MS = 5_000;\n\n/** A z3 release version, ordered numerically. */\nexport interface Z3Version {\n readonly major: number;\n readonly minor: number;\n readonly patch: number;\n}\n\n/**\n * Oldest z3 the transport accepts: `-t`/`-T`, Spacer as `fp.engine`, and the\n * `(get-model)` / `(get-proof)` printers the decoders read are stable from here.\n */\nexport const MIN_Z3_VERSION: Z3Version = { major: 4, minor: 8, patch: 0 };\n\n/** Parses the version out of a `z3 --version` reply (`Z3 version 4.16.0 - 64 bit`). */\nexport function parseZ3Version(text: string): Z3Version | null {\n const m = /Z3 version (\\d+)\\.(\\d+)(?:\\.(\\d+))?/.exec(text);\n if (m == null) return null;\n return { major: Number(m[1]), minor: Number(m[2]), patch: m[3] == null ? 0 : Number(m[3]) };\n}\n\nexport function formatZ3Version(v: Z3Version): string {\n return `${v.major}.${v.minor}.${v.patch}`;\n}\n\nexport function compareZ3Version(a: Z3Version, b: Z3Version): number {\n return a.major - b.major || a.minor - b.minor || a.patch - b.patch;\n}\n\n/** A resolved z3 executable: where it is and which version answered the probe. */\nexport interface Z3Solver {\n /** The executable as resolved (a path, or a bare name on `PATH`). */\n readonly program: string;\n /** The version the probe reported. */\n readonly version: Z3Version;\n /** Where scripts and replies are written, or `null` for no dump. */\n readonly dumpDir: string | null;\n}\n\n/** No usable z3 resolved; the message is the `unknown` reason the verifier reports. */\nexport class Z3Unavailable extends Error {\n constructor(message: string) {\n super(message);\n this.name = 'Z3Unavailable';\n }\n}\n\n/** The process could not be started; the message is the `unknown` reason. */\nexport class Z3ProcessError extends Error {\n constructor(message: string) {\n super(message);\n this.name = 'Z3ProcessError';\n }\n}\n\n/** How a z3 process ended. */\nexport type Z3Exit =\n | { readonly kind: 'exited'; readonly code: number | null }\n | { readonly kind: 'killed' };\n\n/** The raw reply of one z3 run. */\nexport interface Z3Reply {\n readonly stdout: string;\n readonly stderr: string;\n readonly exit: Z3Exit;\n}\n\n/** True when the process exited with status 0. */\nexport function replySucceeded(reply: Z3Reply): boolean {\n return reply.exit.kind === 'exited' && reply.exit.code === 0;\n}\n\n/** The standard argument list: `-smt2 -in -t:<ms> -T:<s>`. */\nexport function argsFor(timeoutMs: number): string[] {\n return ['-smt2', '-in', `-t:${timeoutMs}`, `-T:${hardTimeoutSecs(timeoutMs)}`];\n}\n\n/** The `-T:` backstop in whole seconds: the soft budget plus the grace, rounded up. */\nexport function hardTimeoutSecs(timeoutMs: number): number {\n return Math.max(1, Math.ceil((timeoutMs + GRACE_MS) / 1000));\n}\n\n/** When the watchdog kills the process: the soft budget plus twice the grace. */\nexport function watchdogMs(timeoutMs: number): number {\n return timeoutMs + 2 * GRACE_MS;\n}\n\n/** The soft budget in milliseconds: at least one, so `-t:0` never means \"forever\". */\nexport function timeoutBudget(timeoutMs: number): number {\n return Math.max(1, Math.floor(Number.isFinite(timeoutMs) ? timeoutMs : 1));\n}\n\n/**\n * Why a reply carries no `(check-sat)` answer, in the order the transport contract\n * fixes: the `-T` backstop, the watchdog, an `(error …)` on either stream, anything\n * on stderr, and finally the unexpected stdout itself.\n */\nexport function failureReason(reply: Z3Reply, timeoutMs: number): string {\n if (timeoutLine(reply.stdout)) {\n return `z3 hard timeout after ${hardTimeoutSecs(timeoutMs)}s`;\n }\n if (reply.exit.kind === 'killed') {\n return `z3 did not exit within ${watchdogMs(timeoutMs)} ms and was killed`;\n }\n const err = errorLine(reply.stdout) ?? errorLine(reply.stderr);\n if (err != null) return `Z3 error: ${err}`;\n const stderr = reply.stderr.trim();\n if (stderr !== '') return `Z3 error: ${stderr}`;\n return `Unexpected Z3 output: ${reply.stdout.trim()}`;\n}\n\n/**\n * Where `program` resolves to: the path itself when it names a file, else the first\n * executable of that name on `PATH` (`.exe` tried on Windows); `null` when nothing\n * resolves.\n */\nexport function locateZ3(program: string, env: NodeJS.ProcessEnv = process.env): string | null {\n const isFile = (p: string): boolean => {\n try {\n return existsSync(p) && statSync(p).isFile();\n } catch {\n return false;\n }\n };\n if (program.includes('/') || program.includes(path.sep) || path.isAbsolute(program)) {\n return isFile(program) ? program : null;\n }\n const searchPath = env['PATH'] ?? '';\n const windows = process.platform === 'win32';\n for (const dir of searchPath.split(path.delimiter)) {\n if (dir === '') continue;\n const candidate = path.join(dir, program);\n if (isFile(candidate)) return candidate;\n if (windows && isFile(candidate + '.exe')) return candidate + '.exe';\n }\n return null;\n}\n\n/** Resolves a specific executable (tests point this at a stub). No dump directory. */\nexport function z3SolverAt(program: string, env: NodeJS.ProcessEnv = process.env): Z3Solver {\n const located = locateZ3(program, env);\n if (located == null) {\n throw new Z3Unavailable(\n `z3 binary not found: ${program}; install z3 >= ${formatZ3Version(MIN_Z3_VERSION)} or set ${Z3_ENV}`,\n );\n }\n const probe = spawnSync(located, ['--version'], {\n encoding: 'utf8',\n timeout: VERSION_PROBE_MS,\n stdio: ['ignore', 'pipe', 'pipe'],\n });\n if (probe.error != null) {\n if ((probe.error as NodeJS.ErrnoException).code === 'ETIMEDOUT') {\n throw new Z3Unavailable(`${program} --version did not answer within ${VERSION_PROBE_MS} ms`);\n }\n throw new Z3Unavailable(`failed to spawn ${program}: ${probe.error.message}`);\n }\n const version = parseZ3Version(probe.stdout ?? '');\n if (version == null) {\n const line = `${probe.stdout ?? ''}\\n${probe.stderr ?? ''}`\n .split('\\n')\n .map((l) => l.trim())\n .find((l) => l !== '') ?? '';\n throw new Z3Unavailable(`z3 --version did not report a version: ${line}`);\n }\n if (compareZ3Version(version, MIN_Z3_VERSION) < 0) {\n throw new Z3Unavailable(\n `z3 ${formatZ3Version(version)} is older than the minimum ${formatZ3Version(MIN_Z3_VERSION)}`,\n );\n }\n return { program: located, version, dumpDir: null };\n}\n\n/**\n * Resolves the executable named by {@link Z3_ENV}, or `z3` on `PATH`, probes its\n * version, and reads {@link DUMP_ENV}. Throws {@link Z3Unavailable}.\n */\nexport function resolveZ3(env: NodeJS.ProcessEnv = process.env): Z3Solver {\n const configured = env[Z3_ENV];\n const program = configured == null || configured.trim() === '' ? 'z3' : configured;\n const dump = env[DUMP_ENV];\n const solver = z3SolverAt(program, env);\n return { ...solver, dumpDir: dump == null || dump.trim() === '' ? null : dump };\n}\n\n/**\n * True if a usable `z3` executable resolves: `LIBPETRI_Z3` if set, else `z3` on\n * `PATH`, at or above {@link MIN_Z3_VERSION}. Without one every SMT path returns\n * `unknown`; the test suites use this to skip loudly rather than fail.\n */\nexport function z3Available(env: NodeJS.ProcessEnv = process.env): boolean {\n try {\n resolveZ3(env);\n return true;\n } catch {\n return false;\n }\n}\n\n/** Process-wide counter for dump file names (not solver state). */\nlet dumpCounter = 0;\n\nfunction dumpSlot(solver: Z3Solver, phase: string, script: string): string | null {\n if (solver.dumpDir == null) return null;\n dumpCounter += 1;\n try {\n mkdirSync(solver.dumpDir, { recursive: true });\n const base = path.join(solver.dumpDir, `${String(dumpCounter).padStart(3, '0')}-${phase}`);\n writeFileSync(`${base}.smt2`, script);\n return base;\n } catch {\n return null;\n }\n}\n\nfunction dumpWrite(file: string, text: string): void {\n try {\n writeFileSync(file, text);\n } catch {\n // Dump failures are ignored: the dump is a diagnostic, never the pipeline.\n }\n}\n\n/**\n * Runs one script through one z3 process and resolves with the raw reply. `phase`\n * names the dump files; `extraArgs` follow the standard argument list. The only\n * rejection is a failed spawn: a solver that printed nothing, errored, timed out or\n * was killed still comes back as a reply for the caller to classify\n * ({@link failureReason}).\n */\nexport function runZ3Text(\n solver: Z3Solver,\n script: string,\n phase: string,\n timeoutMs: number,\n extraArgs: readonly string[] = [],\n): Promise<Z3Reply> {\n const budget = timeoutBudget(timeoutMs);\n const base = dumpSlot(solver, phase, script);\n return new Promise<Z3Reply>((resolve, reject) => {\n const child = spawn(solver.program, [...argsFor(budget), ...extraArgs], {\n stdio: ['pipe', 'pipe', 'pipe'],\n });\n const out: Buffer[] = [];\n const err: Buffer[] = [];\n let killed = false;\n let settled = false;\n child.stdout!.on('data', (chunk: Buffer) => out.push(chunk));\n child.stderr!.on('data', (chunk: Buffer) => err.push(chunk));\n // A solver that exited early (parse error, `-T` expiry) closes the pipe under\n // us; that is not a failure of the transport, the reply says what happened.\n child.stdin!.on('error', () => {});\n const watchdog = setTimeout(() => {\n killed = true;\n child.kill('SIGKILL');\n }, watchdogMs(budget));\n child.on('error', (e) => {\n if (settled) return;\n settled = true;\n clearTimeout(watchdog);\n reject(new Z3ProcessError(`failed to spawn ${solver.program}: ${e.message}`));\n });\n child.on('close', (code) => {\n if (settled) return;\n settled = true;\n clearTimeout(watchdog);\n const reply: Z3Reply = {\n stdout: Buffer.concat(out).toString('utf8'),\n stderr: Buffer.concat(err).toString('utf8'),\n exit: killed ? { kind: 'killed' } : { kind: 'exited', code },\n };\n if (base != null) {\n dumpWrite(`${base}.out`, reply.stdout);\n if (reply.stderr.trim() !== '') dumpWrite(`${base}.err`, reply.stderr);\n }\n resolve(reply);\n });\n // The whole script in one write, then EOF.\n child.stdin!.end(script);\n });\n}\n","/**\n * @module smt-text\n *\n * Text-level helpers shared by the transport, the Spacer runner, the certificate\n * check and the counterexample decoder (VER-013). Byte-for-byte mirrors of the Rust\n * `z3_process` / `smt_verifier` helpers and the Java `SmtText` class.\n */\n\n/**\n * The first trimmed stdout line that is a `(check-sat)` answer, or `null`. The answer\n * is a LINE anywhere in the reply, not the first bytes: a build is free to print a\n * warning first, and a HORN script that asks for both a proof and a model always gets\n * one `(error …)` line back.\n */\nexport function classifyFirstLine(stdout: string): 'sat' | 'unsat' | 'unknown' | null {\n for (const raw of stdout.split('\\n')) {\n const line = raw.trim();\n if (line === 'sat' || line === 'unsat' || line === 'unknown') return line;\n }\n return null;\n}\n\n/** True when z3's `-T` backstop fired: it prints the single line `timeout`. */\nexport function timeoutLine(stdout: string): boolean {\n return stdout.split('\\n').some((l) => l.trim() === 'timeout');\n}\n\n/** The first `(error …)` line in a z3 stream, trimmed; `null` if none. */\nexport function errorLine(text: string): string | null {\n for (const raw of text.split('\\n')) {\n const line = raw.trim();\n if (line.startsWith('(error')) return line;\n }\n return null;\n}\n\n/**\n * Returns the index one past the `)` matching the `(` at `start`, or `-1` when the\n * expression is unbalanced. Paren counting skips string literals (`\"…\"`, with `\"\"`\n * escapes) and quoted symbols (`|…|`).\n */\nexport function sexprEnd(s: string, start: number): number {\n let depth = 0;\n let inString = false;\n let inSymbol = false;\n for (let i = start; i < s.length; i++) {\n const c = s[i]!;\n if (inString) {\n if (c === '\"') inString = false;\n } else if (inSymbol) {\n if (c === '|') inSymbol = false;\n } else if (c === '\"') {\n inString = true;\n } else if (c === '|') {\n inSymbol = true;\n } else if (c === '(') {\n depth++;\n } else if (c === ')') {\n depth--;\n if (depth === 0) return i + 1;\n }\n }\n return -1;\n}\n\n/**\n * Every complete `(define-fun …)` s-expression in `output`, in order. A truncated\n * (unbalanced) definition is dropped rather than half-captured.\n */\nexport function extractDefineFuns(output: string): string[] {\n const defs: string[] = [];\n let from = 0;\n for (;;) {\n const pos = output.indexOf('(define-fun', from);\n if (pos < 0) break;\n const end = sexprEnd(output, pos);\n if (end < 0) break;\n defs.push(output.slice(pos, end));\n from = end;\n }\n return defs;\n}\n\n/**\n * The inductive invariant of a `sat` reply: every `(define-fun …)` of the\n * `(get-model)` block joined with newlines, or `null` when no model was printed.\n */\nexport function extractInvariant(output: string): string | null {\n const defs = extractDefineFuns(output);\n return defs.length === 0 ? null : defs.join('\\n');\n}\n","/**\n * @module spacer-runner\n *\n * Runs Z3 Spacer on a HORN script through one `z3` process (VER-013) and\n * classifies the reply in verdict terms.\n *\n * HORN/Spacer convention (shared with the Rust and Java verifiers and corroborated\n * by the certificate check): with the query `(assert (not Error))`, z3 prints `sat`\n * when the property is PROVEN (an inductive invariant excluding every violating\n * state exists) and `unsat` when it is VIOLATED (no such invariant; the refutation\n * proof carries the counterexample states).\n */\nimport { failureReason, runZ3Text, timeoutBudget, type Z3Solver } from './z3-process.js';\nimport { classifyFirstLine, extractInvariant } from './smt-text.js';\n\n/** Result of a Spacer query. */\nexport type QueryResult = QueryProven | QueryViolated | QueryUnknown;\n\n/** Property proven (z3 `sat`). */\nexport interface QueryProven {\n readonly type: 'proven';\n /**\n * The `(define-fun …)` block of the model, verbatim (the certificate the\n * certificate checker re-validates), or `null` when no model printed.\n */\n readonly invariantFormula: string | null;\n}\n\n/** Property violated (z3 `unsat`). */\nexport interface QueryViolated {\n readonly type: 'violated';\n /** The raw solver reply; the refutation proof in it is decoded by the counterexample decoder. */\n readonly answer: string;\n}\n\n/** Solver could not determine (timeout, resource limit, transport failure). */\nexport interface QueryUnknown {\n readonly type: 'unknown';\n readonly reason: string;\n}\n\n/**\n * Runs `smt2` with `fp.engine=spacer`. `phase` names the dump files (`horn` or\n * `horn-coloured`).\n */\nexport async function runZ3Spacer(\n solver: Z3Solver,\n timeoutMs: number,\n smt2: string,\n phase: string,\n): Promise<QueryResult> {\n let reply;\n try {\n reply = await runZ3Text(solver, smt2, phase, timeoutMs, ['fp.engine=spacer']);\n } catch (e: any) {\n return { type: 'unknown', reason: String(e?.message ?? e) };\n }\n const stdout = reply.stdout.trim();\n\n // The verdict is a LINE anywhere in the reply, never its first bytes: the script\n // asks for both (get-proof) and (get-model), one of which answers `(error …)` on\n // either branch, and a build is free to print a warning first.\n switch (classifyFirstLine(stdout)) {\n // unsat => no inductive invariant excludes the bad state => VIOLATED.\n case 'unsat':\n return { type: 'violated', answer: stdout };\n // sat => an inductive invariant exists => PROVEN.\n case 'sat':\n return { type: 'proven', invariantFormula: extractInvariant(stdout) };\n case 'unknown':\n return { type: 'unknown', reason: 'Z3 answered unknown' };\n default:\n // No verdict at all: the `-T` backstop, the watchdog, an `(error …)` on\n // either stream, in that order (VER-013).\n return { type: 'unknown', reason: failureReason(reply, timeoutBudget(timeoutMs)) };\n }\n}\n","/**\n * @module smt-encoder\n *\n * Encodes a flattened Petri net as Constrained Horn Clauses (CHC) in SMT-LIB2 text\n * for Z3's Spacer engine (VER-013).\n *\n * The net's state space is modeled as integer vectors (one variable per place = token\n * count). Three rule types:\n *\n * 1. **Init**: `(assert (Reachable M0))` — the initial marking is reachable\n * 2. **Transition**: `Reachable(M') :- Reachable(M) ∧ enabled(M,t) ∧ fire(M,M',t) ∧\n * M' ≥ 0 ∧ invariants(M') ∧ env-bounds(M')` — one rule per flat transition, plus\n * one env-injection rule per injected environment place (VER-006)\n * 3. **Error**: `Error :- Reachable(M) ∧ violation(M)`; `(assert (not Error))`, so\n * `sat` is PROVEN and `unsat` is VIOLATED\n *\n * The emitted script is byte-identical to the Rust reference (`smt_encoder.rs`) and\n * the Java port for the same input: places in code-point order of their names, the\n * property's places, sinks, env bounds and injections in place-index order,\n * invariants in the order the verifier canonicalised.\n */\nimport type { FlatNet } from '../encoding/flat-net.js';\nimport type { FlatTransition } from '../encoding/flat-transition.js';\nimport type { MarkingState } from '../marking-state.js';\nimport type { SmtProperty } from '../smt-property.js';\nimport type { PInvariant } from '../invariant/p-invariant.js';\nimport type { Place } from '../../core/place.js';\n\n/** An encoded SMT-LIB2 script. */\nexport interface SmtEncoding {\n /** The script text. */\n readonly smt2: string;\n /** The number of flat places (the arity of `Reachable` in the flat encoding). */\n readonly placeCount: number;\n}\n\n/** An injected environment place: its flat index and its cap (`null` = unbounded). */\nexport interface Injection {\n readonly pid: number;\n readonly bound: number | null;\n}\n\n/**\n * Encodes the net and property as a HORN script.\n *\n * @param produceProofs emit `:produce-proofs` and `(get-proof)` so an `unsat` reply\n * carries the refutation the replay decodes\n */\nexport function encode(\n flatNet: FlatNet,\n initialMarking: MarkingState,\n property: SmtProperty,\n invariants: readonly PInvariant[],\n sinkPlaces: ReadonlySet<Place<any>> = new Set(),\n produceProofs = false,\n): SmtEncoding {\n const P = flatNet.places.length;\n const lines: string[] = [];\n const envInject = resolveEnvInjection(flatNet);\n\n if (produceProofs) lines.push('(set-option :produce-proofs true)');\n lines.push('(set-logic HORN)');\n lines.push('');\n\n lines.push(`(declare-fun Reachable (${ints(P).join(' ')}) Bool)`);\n lines.push('(declare-fun Error () Bool)');\n lines.push('');\n\n const mVars = vars(P, '');\n const mpVars = vars(P, 'p');\n\n const m0: string[] = [];\n for (let i = 0; i < P; i++) m0.push(String(initialMarking.tokens(flatNet.places[i]!)));\n lines.push(`(assert (Reachable ${m0.join(' ')}))`);\n lines.push('');\n\n for (const ft of flatNet.transitions) {\n lines.push(encodeTransitionRule(flatNet, ft, mVars, mpVars, invariants));\n }\n // Environment-injection rules (VER-006): NOT flat transitions, so the deadlock\n // encoding never sees them; no P-invariant strengthening, injection breaks\n // conservation on purpose.\n for (const inj of envInject) {\n lines.push(encodeInjectionRule(P, inj.pid, inj.bound, mVars, mpVars));\n }\n lines.push('');\n\n lines.push(encodeErrorRule(flatNet, property, mVars, sinkPlaces, envInject));\n lines.push('');\n\n // Under HORN/Spacer this is SAT when an inductive invariant excludes every\n // violating state (PROVEN) and UNSAT when none exists (VIOLATED).\n lines.push('(assert (not Error))');\n lines.push('(check-sat)');\n if (produceProofs) lines.push('(get-proof)');\n lines.push('(get-model)');\n\n return { smt2: lines.join('\\n'), placeCount: P };\n}\n\n/** The injected environment places in place-index order. */\nexport function resolveEnvInjection(flatNet: FlatNet): Injection[] {\n const out: Injection[] = [];\n for (const [name, bound] of flatNet.environmentInjection) {\n const pid = flatNet.placeIndex.get(name);\n if (pid != null) out.push({ pid, bound });\n }\n out.sort((a, b) => a.pid - b.pid);\n return out;\n}\n\n/** The bounded environment places (legacy post-cap) in place-index order. */\nfunction envBounds(flatNet: FlatNet): Array<[number, number]> {\n const out: Array<[number, number]> = [];\n for (const [name, max] of flatNet.environmentBounds) {\n const pid = flatNet.placeIndex.get(name);\n if (pid != null) out.push([pid, max]);\n }\n out.sort((a, b) => a[0] - b[0]);\n return out;\n}\n\nfunction ints(n: number): string[] {\n return new Array<string>(n).fill('Int');\n}\n\nfunction vars(P: number, suffix: string): string[] {\n const out: string[] = [];\n for (let i = 0; i < P; i++) out.push(`m${i}${suffix}`);\n return out;\n}\n\nfunction quantified(names: readonly string[]): string {\n return names.map((v) => `(${v} Int)`).join(' ');\n}\n\n// === Shared condition emitters ===\n//\n// Emitted by BOTH the CHC rule encoding and the plain-SMT step relation\n// (encodeStepRelationSmt2) the certificate check uses, so the two cannot drift.\n\n/**\n * Enablement + firing + non-negativity conjuncts for one flat transition:\n * `enabled(M, t)`, `fire(M, M', t)`, `M' >= 0`. Excludes the `Reachable` body atom,\n * the P-invariant strengthening and the env bounds.\n */\nfunction firingConditions(\n flatNet: FlatNet,\n ft: FlatTransition,\n mVars: readonly string[],\n mpVars: readonly string[],\n): string[] {\n const P = flatNet.places.length;\n const conditions: string[] = [];\n for (let i = 0; i < P; i++) {\n if (ft.preVector[i]! > 0) conditions.push(`(>= ${mVars[i]} ${ft.preVector[i]})`);\n }\n for (const inh of ft.inhibitorPlaces) conditions.push(`(= ${mVars[inh]} 0)`);\n for (const rd of ft.readPlaces) conditions.push(`(>= ${mVars[rd]} 1)`);\n for (let i = 0; i < P; i++) {\n if (ft.resetPlaces.includes(i) || ft.consumeAll[i]) {\n // Reset / consume-all: clear then add post.\n conditions.push(`(= ${mpVars[i]} ${ft.postVector[i]})`);\n } else {\n const delta = ft.postVector[i]! - ft.preVector[i]!;\n if (delta > 0) conditions.push(`(= ${mpVars[i]} (+ ${mVars[i]} ${delta}))`);\n else if (delta < 0) conditions.push(`(= ${mpVars[i]} (- ${mVars[i]} ${-delta}))`);\n else conditions.push(`(= ${mpVars[i]} ${mVars[i]})`);\n }\n }\n for (let i = 0; i < P; i++) conditions.push(`(>= ${mpVars[i]} 0)`);\n return conditions;\n}\n\n/**\n * P-invariant conjuncts over the given marking variables. The step relation never\n * emits these: the certificate check keeps its relation UNSTRENGTHENED and conjoins\n * them into the candidate instead, where the VCs re-prove them.\n */\nexport function invariantConditions(invariants: readonly PInvariant[], names: readonly string[]): string[] {\n const conditions: string[] = [];\n for (const inv of invariants) {\n const terms = [...inv.support].sort((a, b) => a - b).map((i) => `(* ${inv.weights[i]} ${names[i]})`);\n if (terms.length === 0) continue;\n const sum = terms.length === 1 ? terms[0]! : `(+ ${terms.join(' ')})`;\n conditions.push(`(= ${sum} ${inv.constant})`);\n }\n return conditions;\n}\n\n/** Environment post-cap conjuncts on the next marking (legacy Bounded mode). */\nfunction envBoundConditions(flatNet: FlatNet, mpVars: readonly string[]): string[] {\n return envBounds(flatNet).map(([pid, max]) => `(<= ${mpVars[pid]} ${max})`);\n}\n\n/**\n * Guard + column-update conjuncts for one env-injection step (VER-006):\n * `[m_pid < bound]`, `m'_pid = m_pid + 1`, all other columns copied.\n */\nfunction injectionConditions(\n P: number,\n pid: number,\n bound: number | null,\n mVars: readonly string[],\n mpVars: readonly string[],\n): string[] {\n const conditions: string[] = [];\n if (bound != null) conditions.push(`(< ${mVars[pid]} ${bound})`);\n for (let i = 0; i < P; i++) {\n if (i === pid) conditions.push(`(= ${mpVars[i]} (+ ${mVars[i]} 1))`);\n else conditions.push(`(= ${mpVars[i]} ${mVars[i]})`);\n }\n return conditions;\n}\n\nfunction encodeTransitionRule(\n flatNet: FlatNet,\n ft: FlatTransition,\n mVars: readonly string[],\n mpVars: readonly string[],\n invariants: readonly PInvariant[],\n): string {\n const conditions = [`(Reachable ${mVars.join(' ')})`];\n conditions.push(...firingConditions(flatNet, ft, mVars, mpVars));\n conditions.push(...invariantConditions(invariants, mpVars));\n conditions.push(...envBoundConditions(flatNet, mpVars));\n const body = `(and ${conditions.join('\\n ')})`;\n return `(assert (forall (${quantified([...mVars, ...mpVars])})\\n (=> ${body}\\n (Reachable ${mpVars.join(' ')}))))`;\n}\n\nfunction encodeInjectionRule(\n P: number,\n pid: number,\n bound: number | null,\n mVars: readonly string[],\n mpVars: readonly string[],\n): string {\n const conditions = [`(Reachable ${mVars.join(' ')})`];\n conditions.push(...injectionConditions(P, pid, bound, mVars, mpVars));\n const body = `(and ${conditions.join('\\n ')})`;\n return `(assert (forall (${quantified([...mVars, ...mpVars])})\\n (=> ${body}\\n (Reachable ${mpVars.join(' ')}))))`;\n}\n\n/**\n * Joins conjuncts into one formula (`true` when empty, the bare conjunct when\n * singleton, since SMT-LIB `and` wants at least two arguments).\n */\nexport function conjoin(conditions: readonly string[]): string {\n if (conditions.length === 0) return 'true';\n if (conditions.length === 1) return conditions[0]!;\n return `(and ${conditions.join(' ')})`;\n}\n\n/**\n * The net's one-step relation `T(M, M')` as one plain SMT-LIB2 formula over the free\n * variables `m0..` / `m0p..`: the disjunction of every flat transition firing and\n * every env-injection step (VER-006). This is the UNSTRENGTHENED relation the\n * certificate check validates against: it shares the condition emitters with the CHC\n * path but omits the P-invariant conjuncts, so a certificate poisoned by a wrong\n * invariant cannot re-certify itself.\n */\nexport function encodeStepRelationSmt2(flatNet: FlatNet): string {\n const P = flatNet.places.length;\n const mVars = vars(P, '');\n const mpVars = vars(P, 'p');\n const disjuncts: string[] = [];\n for (const ft of flatNet.transitions) {\n const conditions = firingConditions(flatNet, ft, mVars, mpVars);\n conditions.push(...envBoundConditions(flatNet, mpVars));\n disjuncts.push(conjoin(conditions));\n }\n for (const inj of resolveEnvInjection(flatNet)) {\n disjuncts.push(conjoin(injectionConditions(P, inj.pid, inj.bound, mVars, mpVars)));\n }\n if (disjuncts.length === 0) return 'false';\n if (disjuncts.length === 1) return disjuncts[0]!;\n return `(or ${disjuncts.join('\\n ')})`;\n}\n\nfunction encodeErrorRule(\n flatNet: FlatNet,\n property: SmtProperty,\n mVars: readonly string[],\n sinkPlaces: ReadonlySet<Place<any>>,\n envInject: readonly Injection[],\n): string {\n const violation = encodePropertyViolation(flatNet, property, mVars, sinkPlaces, envInject);\n return `(assert (forall (${quantified(mVars)})\\n (=> (and (Reachable ${mVars.join(' ')}) ${violation})\\n Error)))`;\n}\n\n/** The flat indices of the given places that resolve, ascending and deduplicated. */\nexport function indexOrdered(flatNet: FlatNet, places: Iterable<Place<any>>): number[] {\n const idx = new Set<number>();\n for (const place of places) {\n const i = flatNet.placeIndex.get(place.name);\n if (i != null) idx.add(i);\n }\n return [...idx].sort((a, b) => a - b);\n}\n\n/**\n * The property-violation condition `Bad(M)` over `mVars`. Also used by the\n * certificate check's safety VC, which must test against exactly the violation the\n * error rule encodes. A place the net does not declare contributes nothing; the\n * verifier refuses such a property before encoding.\n */\nexport function encodePropertyViolation(\n flatNet: FlatNet,\n property: SmtProperty,\n mVars: readonly string[],\n sinkPlaces: ReadonlySet<Place<any>>,\n envInject: readonly Injection[],\n): string {\n switch (property.type) {\n case 'deadlock-free':\n return encodeDeadlock(flatNet, mVars, sinkPlaces, envInject);\n case 'mutual-exclusion': {\n const conditions = indexOrdered(flatNet, [property.p1, property.p2]).map((i) => `(>= ${mVars[i]} 1)`);\n return conditions.length === 0 ? 'false' : `(and ${conditions.join(' ')})`;\n }\n case 'place-bound':\n case 'branch-place-bound': {\n // BranchPlaceBound is the ν-net budget lever (NU-040): a count bound, encoded\n // like PlaceBound.\n const pid = flatNet.placeIndex.get(property.place.name);\n return pid == null ? 'false' : `(> ${mVars[pid]} ${property.bound})`;\n }\n case 'unreachable': {\n const conditions = indexOrdered(flatNet, property.places).map((i) => `(>= ${mVars[i]} 1)`);\n return conditions.length === 0 ? 'false' : `(and ${conditions.join(' ')})`;\n }\n case 'joined-or-dead-lettered': {\n // NU-040: a quiescent marking still holding a `pending` token.\n const deadlock = encodeDeadlock(flatNet, mVars, sinkPlaces, envInject);\n const pid = flatNet.placeIndex.get(property.pending.name);\n return pid == null ? 'false' : `(and ${deadlock} (>= ${mVars[pid]} 1))`;\n }\n }\n}\n\n/**\n * Deadlock: every transition is disabled. Environment inputs are treated as\n * injectable (VER-006): an input/read on an injectable env place is NOT a reason the\n * transition is disabled (AlwaysAvailable always satisfies it, Bounded(k) iff the\n * demand is at most k), so a reactive net merely waiting for input is not a deadlock;\n * only a genuinely stuck marking is. Declared sinks (VER-002) each contribute\n * `M[sink] = 0`.\n */\nfunction encodeDeadlock(\n flatNet: FlatNet,\n mVars: readonly string[],\n sinkPlaces: ReadonlySet<Place<any>>,\n envInject: readonly Injection[],\n): string {\n const envBound = new Map<number, number | null>();\n for (const inj of envInject) envBound.set(inj.pid, inj.bound);\n const disabledConditions: string[] = [];\n for (const ft of flatNet.transitions) {\n const disableReasons: string[] = [];\n let permanentlyDisabled = false;\n for (let i = 0; i < flatNet.places.length; i++) {\n if (ft.preVector[i]! > 0) {\n if (envBound.has(i)) {\n const k = envBound.get(i)!;\n if (k != null && ft.preVector[i]! > k) permanentlyDisabled = true;\n continue;\n }\n disableReasons.push(`(< ${mVars[i]} ${ft.preVector[i]})`);\n }\n }\n for (const inh of ft.inhibitorPlaces) disableReasons.push(`(> ${mVars[inh]} 0)`);\n for (const rd of ft.readPlaces) {\n if (envBound.has(rd)) {\n const k = envBound.get(rd)!;\n if (k != null && k < 1) permanentlyDisabled = true;\n continue;\n }\n disableReasons.push(`(< ${mVars[rd]} 1)`);\n }\n if (permanentlyDisabled) {\n disabledConditions.push('true');\n continue;\n }\n if (disableReasons.length === 0) return 'false';\n disabledConditions.push(`(or ${disableReasons.join(' ')})`);\n }\n for (const pid of indexOrdered(flatNet, sinkPlaces)) {\n disabledConditions.push(`(= ${mVars[pid]} 0)`);\n }\n return disabledConditions.length === 0 ? 'true' : `(and ${disabledConditions.join('\\n ')})`;\n}\n\n/** Env-injectable bound map, index to cap (`null` = unbounded), for the coloured encoder. */\nexport function injectionMap(flatNet: FlatNet): Map<number, number | null> {\n const out = new Map<number, number | null>();\n for (const inj of resolveEnvInjection(flatNet)) out.set(inj.pid, inj.bound);\n return out;\n}\n","/**\n * @module certificate-checker\n *\n * Independent certificate check for IC3/PDR proofs.\n *\n * When Z3 Spacer answers `sat` on the CHC encoding ({@link module:smt-encoder}), the\n * model it prints interprets `Reachable` as an inductive invariant, the proof\n * certificate. This module re-verifies that certificate with plain (non-HORN) SMT\n * queries in a SECOND z3 run, so a `proven` verdict no longer rests on the empirical\n * HORN sat ⇒ proven mapping alone, nor on the correctness of the P-invariant\n * strengthening: the three verification conditions below are discharged against the\n * UNSTRENGTHENED step relation ({@link encodeStepRelationSmt2}).\n *\n * The candidate invariant is `R' := R ∧ Inv`, where `R` is the pasted `Reachable`\n * interpretation and `Inv` the validated P-invariant equalities the CHC encoding\n * strengthened its rule bodies with: a Spacer model is only guaranteed inductive\n * *relative to* that strengthening, so the conjuncts ride along in the candidate, but\n * the RELATION stays unstrengthened, which means VC1/VC2 re-prove each conjunct's\n * initiation and inductiveness from scratch. A wrong P-invariant cannot weaken this\n * check: it fails init or consecution instead.\n *\n * 1. **VC1 (init)**: `¬R'(M₀)` is UNSAT.\n * 2. **VC2 (consecution)**: `M ≥ 0 ∧ R'(M) ∧ T(M,M') ∧ ¬R'(M')` is UNSAT.\n * 3. **VC3 (safety)**: `M ≥ 0 ∧ R'(M) ∧ Bad(M)` is UNSAT.\n *\n * The `M ≥ 0` conjunct is the state domain: markings are token counts, so the VCs\n * range over ℕ^P; without it a certificate inductive over ℕ^P is refuted by a negative\n * predecessor in ℤ^P.\n *\n * The certificate is the `(define-fun …)` block of the `(get-model)` reply, pasted\n * verbatim: auxiliary definitions stay alongside `Reachable`, so every name resolves\n * in the fresh script. The three VCs run under `(push)`/`(pop)` in ONE script; the\n * emitted text is byte-identical to the Rust reference (`certificate_check.rs`) and\n * the Java port.\n *\n * Outcomes are split the way the caller must treat them: `failed` names the first VC\n * that was not UNSAT (with the solver status and, for SAT, a witness marking),\n * `unavailable` means the check could not run at all (missing or malformed\n * certificate, solver spawn failure, errored assert). Both withhold PROVEN; neither\n * throws.\n */\nimport type { FlatNet } from '../encoding/flat-net.js';\nimport type { MarkingState } from '../marking-state.js';\nimport type { SmtProperty } from '../smt-property.js';\nimport type { PInvariant } from '../invariant/p-invariant.js';\nimport type { Place } from '../../core/place.js';\nimport {\n conjoin, encodePropertyViolation, encodeStepRelationSmt2, invariantConditions, resolveEnvInjection,\n} from './smt-encoder.js';\nimport { errorLine, sexprEnd, timeoutLine } from './smt-text.js';\nimport {\n hardTimeoutSecs, replySucceeded, runZ3Text, timeoutBudget, watchdogMs, type Z3Solver,\n} from './z3-process.js';\n\n/** Label of a validity condition, as it appears in the downgrade reason. */\nexport type CertificateVc = 'initiation (VC1)' | 'consecution (VC2)' | 'safety (VC3)';\n\nconst VC_LABELS: readonly CertificateVc[] = ['initiation (VC1)', 'consecution (VC2)', 'safety (VC3)'];\n\n/**\n * Outcome of the certificate check.\n *\n * `passed` — all three validity conditions are UNSAT; the proven verdict is certified\n * independently of the Fixedpoint engine.\n * `failed` — a validity condition was not UNSAT; `detail` carries the solver status\n * and, when the solver produced a model, a witness marking.\n * `unavailable` — the check could not run (missing/malformed certificate, solver\n * failure), so no VC is implicated.\n *\n * The caller must withhold PROVEN on `failed` and `unavailable` alike.\n */\nexport type CertificateCheckOutcome =\n | { readonly type: 'passed'; readonly invariant: string }\n | {\n readonly type: 'failed';\n readonly vc: CertificateVc;\n readonly detail: string;\n readonly invariant: string;\n }\n | { readonly type: 'unavailable'; readonly reason: string; readonly invariant: string | null };\n\n/**\n * Re-verifies an extracted proof certificate against the unstrengthened step relation.\n *\n * @param certificate the `(define-fun …)` block extracted verbatim from the Spacer\n * model (`null` when the solver printed none)\n * @param flatNet the flat net the CHC query was encoded from\n * @param initialMarking the verified initial marking (VC1)\n * @param property the verified property (VC3)\n * @param invariants the exactly-validated P-invariants the CHC bodies were\n * strengthened with; conjoined into the CANDIDATE certificate and re-proven by the\n * three VCs (never conjoined into the step relation)\n * @param sinkPlaces declared sink places (deadlock-freedom VC3)\n * @param solver the resolved z3 executable\n * @param timeoutMs per-invocation solver budget in milliseconds\n */\nexport async function checkCertificate(\n certificate: string | null,\n flatNet: FlatNet,\n initialMarking: MarkingState,\n property: SmtProperty,\n invariants: readonly PInvariant[],\n sinkPlaces: ReadonlySet<Place<any>>,\n solver: Z3Solver,\n timeoutMs: number,\n): Promise<CertificateCheckOutcome> {\n if (certificate == null) {\n return {\n type: 'unavailable',\n reason: 'no inductive invariant (define-fun block) could be extracted from the z3 model',\n invariant: null,\n };\n }\n const shape = shapeFailure(flatNet, invariants);\n if (shape != null) return { type: 'unavailable', reason: shape, invariant: certificate };\n if (!certificate.includes('(define-fun Reachable ') && !certificate.includes('(define-fun |Reachable| ')) {\n return { type: 'unavailable', reason: 'certificate does not define Reachable', invariant: certificate };\n }\n\n const vcs = buildVerificationConditions(certificate, flatNet, initialMarking, property, sinkPlaces, invariants);\n let results: string[];\n try {\n results = await runVcScript(script(vcs), timeoutMs, solver);\n } catch (e: any) {\n return { type: 'unavailable', reason: String(e?.message ?? e), invariant: certificate };\n }\n for (let i = 0; i < results.length; i++) {\n if (results[i] !== 'unsat') {\n const detail = await detailFor(vcs, i, results[i]!, flatNet, timeoutMs, solver);\n return { type: 'failed', vc: VC_LABELS[i]!, detail, invariant: certificate };\n }\n }\n return { type: 'passed', invariant: certificate };\n}\n\n/**\n * The certificate-check script for the given inputs, exactly as\n * {@link checkCertificate} would send it (VER-013 script parity): what the\n * cross-language golden tests diff.\n */\nexport function vcScript(\n certificate: string,\n flatNet: FlatNet,\n initialMarking: MarkingState,\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n invariants: readonly PInvariant[],\n): string {\n return script(buildVerificationConditions(certificate, flatNet, initialMarking, property, sinkPlaces, invariants));\n}\n\n/** Why the net and invariants cannot be indexed safely, or `null`. */\nfunction shapeFailure(flatNet: FlatNet, invariants: readonly PInvariant[]): string | null {\n const P = flatNet.places.length;\n for (const inv of invariants) {\n if (inv.weights.length !== P) {\n return `P-invariant has ${inv.weights.length} weights for a ${P}-place net`;\n }\n for (const pid of inv.support) {\n if (pid >= P || pid < 0) return `P-invariant support names place index ${pid} in a ${P}-place net`;\n }\n }\n return null;\n}\n\n/** A VC run that could not be trusted; the message is the reason. */\nclass VcFailure extends Error {}\n\n/**\n * Runs one plain-SMT script and returns the three positional `(check-sat)` answers.\n * Both output channels are inspected: an `(error …)` on EITHER stream means an assert\n * was dropped, which would silently make a VC vacuous; a `timeout` line, a watchdog\n * kill and a non-success exit mean the run did not complete. Only a clean\n * three-answer stdout counts.\n */\nasync function runVcScript(text: string, timeoutMs: number, solver: Z3Solver): Promise<string[]> {\n const reply = await runZ3Text(solver, text, 'certificate', timeoutMs, []);\n const budget = timeoutBudget(timeoutMs);\n const err = errorLine(reply.stderr);\n if (err != null) throw new VcFailure(`z3 reported an error on stderr: ${err}`);\n if (timeoutLine(reply.stdout)) {\n throw new VcFailure(`z3 hard timeout after ${hardTimeoutSecs(budget)}s while checking the certificate`);\n }\n if (reply.exit.kind === 'killed') {\n throw new VcFailure(`z3 did not exit within ${watchdogMs(budget)} ms while checking the certificate and was killed`);\n }\n const results = parseVcResults(reply.stdout);\n if (!replySucceeded(reply)) {\n const status = reply.exit.kind === 'exited' ? `exit status: ${reply.exit.code}` : 'the watchdog kill';\n throw new VcFailure(`z3 exited with ${status} after answering [${results.join(', ')}]`);\n }\n return results;\n}\n\n/**\n * Parses the three positional `(check-sat)` answers. Any `(error …)` line fails the\n * check outright (an errored assert silently vanishes from the query, which could\n * leave a VC vacuous); a `timeout` line is z3's `-T` backstop, not a fourth answer.\n */\nexport function parseVcResults(stdout: string): string[] {\n const err = errorLine(stdout);\n if (err != null) throw new VcFailure(`z3 error while checking the certificate: ${err}`);\n if (timeoutLine(stdout)) throw new VcFailure('z3 hard timeout while checking the certificate');\n const results = stdout\n .split('\\n')\n .map((l) => l.trim())\n .filter((l) => l === 'sat' || l === 'unsat' || l === 'unknown');\n if (results.length !== 3) {\n throw new VcFailure(`expected 3 VC answers from z3, got ${results.length}: [${results.join(', ')}]`);\n }\n return results;\n}\n\n/** The assembled VC script, kept in parts so one VC can be re-run alone. */\ninterface VerificationConditions {\n readonly prelude: readonly string[];\n /** The asserts of each VC, in `VC_LABELS` order. */\n readonly asserts: readonly (readonly string[])[];\n}\n\nfunction buildVerificationConditions(\n certificate: string,\n flatNet: FlatNet,\n initialMarking: MarkingState,\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n invariants: readonly PInvariant[],\n): VerificationConditions {\n const P = flatNet.places.length;\n const mVars: string[] = [];\n const mpVars: string[] = [];\n for (let i = 0; i < P; i++) {\n mVars.push(`m${i}`);\n mpVars.push(`m${i}p`);\n }\n\n const prelude: string[] = [\n '; IC3/PDR certificate check (plain SMT-LIB2, not HORN):',\n '; each VC below must be unsat for the certificate to stand.',\n certificate,\n '',\n ];\n for (const v of mVars) prelude.push(`(declare-const ${v} Int)`);\n for (const v of mpVars) prelude.push(`(declare-const ${v} Int)`);\n\n // VC1 (init): the initial marking satisfies the candidate invariant.\n const m0: string[] = [];\n for (let i = 0; i < P; i++) m0.push(String(initialMarking.tokens(flatNet.places[i]!)));\n const vc1 = [`(assert (not ${candidate(m0, invariants)}))`];\n\n // The system lives in N^P, not Z^P.\n const nonNegative = mVars.map((v) => `(assert (>= ${v} 0))`);\n\n // VC2 (consecution): closed under the unstrengthened step relation.\n const step = encodeStepRelationSmt2(flatNet);\n const vc2 = [\n ...nonNegative,\n `(assert ${candidate(mVars, invariants)})`,\n `(assert ${step})`,\n `(assert (not ${candidate(mpVars, invariants)}))`,\n ];\n\n // VC3 (safety): excludes every property-violating state, exactly the violation\n // the CHC error rule encodes.\n const bad = encodePropertyViolation(flatNet, property, mVars, sinkPlaces, resolveEnvInjection(flatNet));\n const vc3 = [...nonNegative, `(assert ${candidate(mVars, invariants)})`, `(assert ${bad})`];\n\n return { prelude, asserts: [vc1, vc2, vc3] };\n}\n\n/** The full script: the prelude, then the three VCs under push/pop. */\nfunction script(vcs: VerificationConditions): string {\n const lines = [...vcs.prelude];\n for (let i = 0; i < vcs.asserts.length; i++) {\n lines.push('');\n lines.push(`; VC${i + 1} ${VC_LABELS[i]}`);\n lines.push('(push)');\n lines.push(...vcs.asserts[i]!);\n lines.push('(check-sat)');\n lines.push('(pop)');\n }\n return lines.join('\\n');\n}\n\n/**\n * Describes VC `i`'s non-`unsat` answer for the downgrade reason, by re-running that\n * VC alone with model/reason extraction enabled. Best effort: without it the answer is\n * still named.\n */\nasync function detailFor(\n vcs: VerificationConditions,\n i: number,\n answer: string,\n flatNet: FlatNet,\n timeoutMs: number,\n solver: Z3Solver,\n): Promise<string> {\n const lines = ['(set-option :produce-models true)', ...vcs.prelude, ...vcs.asserts[i]!, '(check-sat)'];\n lines.push(answer === 'sat' ? '(get-model)' : '(get-info :reason-unknown)');\n let reply = '';\n try {\n reply = (await runZ3Text(solver, lines.join('\\n'), 'certificate-detail', timeoutMs, [])).stdout;\n } catch {\n reply = '';\n }\n if (answer === 'sat') {\n const w = witness(reply, flatNet);\n return w == null ? 'solver returned SATISFIABLE' : `solver returned SATISFIABLE (witness: ${w})`;\n }\n const r = reasonUnknown(reply);\n return r == null ? 'solver returned UNKNOWN' : `solver returned UNKNOWN (${r})`;\n}\n\n/**\n * Reads the current-marking assignment out of a `(get-model)` reply as `p0=2, p1=1`\n * (place names, index order); `null` when no `m_i` was defined.\n */\nexport function witness(model: string, flatNet: FlatNet): string | null {\n const parts: string[] = [];\n for (let i = 0; i < flatNet.places.length; i++) {\n const needle = `(define-fun m${i} () Int`;\n const at = model.indexOf(needle);\n if (at < 0) continue;\n const rest = model.slice(at + needle.length).trimStart();\n let value: string;\n if (rest.startsWith('(')) {\n const end = sexprEnd(rest, 0);\n if (end < 0) continue;\n // A negative literal prints as `(- 1)`; flatten it back to `-1`.\n value = rest.slice(1, end - 1).trim().split(/\\s+/).join('');\n } else {\n let end = 0;\n while (end < rest.length && !/\\s/.test(rest[end]!) && rest[end] !== ')') end++;\n if (end === 0) continue;\n value = rest.slice(0, end);\n }\n parts.push(`${flatNet.places[i]!.name}=${value}`);\n }\n return parts.length === 0 ? null : parts.join(', ');\n}\n\n/** Reads z3's `(get-info :reason-unknown)` reply, e.g. `timeout`. */\nexport function reasonUnknown(reply: string): string | null {\n const at = reply.indexOf(':reason-unknown');\n if (at < 0) return null;\n const rest = reply.slice(at + ':reason-unknown'.length).trimStart();\n const end = rest.indexOf(')');\n if (end < 0) return null;\n let reason = rest.slice(0, end).trim();\n if (reason.startsWith('\"') && reason.endsWith('\"') && reason.length >= 2) reason = reason.slice(1, -1);\n reason = reason.trim();\n return reason === '' ? null : reason;\n}\n\n/**\n * The candidate invariant applied to a variable (or literal) vector:\n * `R'(vars) = (Reachable vars) ∧ Inv(vars)`.\n */\nfunction candidate(names: readonly string[], invariants: readonly PInvariant[]): string {\n return conjoin([`(Reachable ${names.join(' ')})`, ...invariantConditions(invariants, names)]);\n}\n","const EPSILON = 1e-9;\n\n/**\n * Difference Bound Matrix (DBM) for Time Petri Net state class analysis.\n *\n * Implements the Berthomieu-Diaz (1991) algorithm for computing firing domains\n * and their successors. Matrix bounds[i][j] = upper bound on (xi - xj).\n * Index 0 is the reference clock; index i+1 is the clock for transition i.\n */\nexport class DBM {\n private readonly bounds: Float64Array;\n private readonly dim: number;\n readonly clockNames: readonly string[];\n private readonly _empty: boolean;\n\n private constructor(bounds: Float64Array, dim: number, clockNames: readonly string[], empty: boolean) {\n this.bounds = bounds;\n this.dim = dim;\n this.clockNames = clockNames;\n this._empty = empty;\n }\n\n /** Creates an initial firing domain for enabled transitions. */\n static create(clockNames: readonly string[], lowerBounds: number[], upperBounds: number[]): DBM {\n const n = clockNames.length;\n const dim = n + 1;\n const bounds = makeMatrix(dim, Infinity);\n\n for (let i = 0; i < n; i++) {\n bounds[(0) * dim + (i + 1)] = -lowerBounds[i]!;\n bounds[(i + 1) * dim + (0)] = upperBounds[i]!;\n }\n\n return new DBM(bounds, dim, clockNames, false).canonicalize();\n }\n\n /** Creates an empty (unsatisfiable) zone. */\n static empty(clockNames: readonly string[]): DBM {\n const b = new Float64Array(1);\n b[0] = 0;\n return new DBM(b, 1, clockNames, true);\n }\n\n isEmpty(): boolean {\n return this._empty;\n }\n\n clockCount(): number {\n return this.clockNames.length;\n }\n\n private get(i: number, j: number): number {\n return this.bounds[i * this.dim + j]!;\n }\n\n /** Gets the lower bound (earliest firing time) for clock i. */\n getLowerBound(clockIndex: number): number {\n if (this._empty || clockIndex < 0 || clockIndex >= this.clockNames.length) return 0;\n const val = -this.get(0, clockIndex + 1);\n return val === 0 ? 0 : val; // normalize -0 to 0\n }\n\n /** Gets the upper bound (latest firing time / deadline) for clock i. */\n getUpperBound(clockIndex: number): number {\n if (this._empty || clockIndex < 0 || clockIndex >= this.clockNames.length) return Infinity;\n return this.get(clockIndex + 1, 0);\n }\n\n /** Checks if transition can fire (lower bound <= 0 after time passage). */\n canFire(clockIndex: number): boolean {\n return !this._empty && this.getLowerBound(clockIndex) <= EPSILON;\n }\n\n /**\n * Computes the successor firing domain after firing transition t_f.\n * Implements the 5-step Berthomieu-Diaz successor formula.\n */\n fireTransition(\n firedClock: number,\n newClockNames: readonly string[],\n newLowerBounds: number[],\n newUpperBounds: number[],\n persistentClocks: number[],\n ): DBM {\n if (this._empty) return this;\n\n const n = this.clockNames.length;\n if (firedClock < 0 || firedClock >= n) {\n throw new Error(`Invalid fired clock index: ${firedClock}`);\n }\n\n // Step 1: Intersect with \"t_f fires first\" constraint\n const constrained = new Float64Array(this.bounds);\n const dim = this.dim;\n const f = firedClock + 1;\n\n for (let i = 0; i < n; i++) {\n if (i !== firedClock) {\n const idx = i + 1;\n const pos = f * dim + idx;\n constrained[pos] = Math.min(constrained[pos]!, 0);\n }\n }\n\n // Step 2: Canonicalize\n if (!canonicalizeInPlace(constrained, dim)) {\n return DBM.empty([]);\n }\n\n // Steps 3 & 4: Substitution and Elimination\n const newN = persistentClocks.length + newClockNames.length;\n const newDim = newN + 1;\n const newBounds = makeMatrix(newDim, Infinity);\n\n // Copy persistent clocks with transformed bounds\n for (let pi = 0; pi < persistentClocks.length; pi++) {\n const oldIdx = persistentClocks[pi]! + 1;\n const newIdx = pi + 1;\n\n const upper = constrained[oldIdx * dim + f]!;\n const lower = Math.max(0, -constrained[f * dim + oldIdx]!);\n\n newBounds[0 * newDim + newIdx] = -lower;\n newBounds[newIdx * newDim + 0] = upper;\n\n // Inter-clock constraints between persistent transitions (preserved)\n for (let pj = 0; pj < persistentClocks.length; pj++) {\n const oldJ = persistentClocks[pj]! + 1;\n const newJ = pj + 1;\n newBounds[newIdx * newDim + newJ] = constrained[oldIdx * dim + oldJ]!;\n }\n }\n\n // Step 5: Add fresh intervals for newly enabled transitions\n const offset = persistentClocks.length;\n for (let k = 0; k < newClockNames.length; k++) {\n const idx = offset + k + 1;\n newBounds[0 * newDim + idx] = -newLowerBounds[k]!;\n newBounds[idx * newDim + 0] = newUpperBounds[k]!;\n }\n\n // Build new clock names\n const allNames: string[] = [];\n for (const idx of persistentClocks) {\n allNames.push(this.clockNames[idx]!);\n }\n allNames.push(...newClockNames);\n\n // Step 6: Final canonicalization\n return new DBM(newBounds, newDim, allNames, false).canonicalize();\n }\n\n /** Lets time pass: set all lower bounds to 0. */\n letTimePass(): DBM {\n if (this._empty) return this;\n\n const newBounds = new Float64Array(this.bounds);\n for (let i = 1; i < this.dim; i++) {\n newBounds[0 * this.dim + i] = 0;\n }\n\n return new DBM(newBounds, this.dim, this.clockNames, false).canonicalize();\n }\n\n private canonicalize(): DBM {\n if (this._empty) return this;\n\n const canon = new Float64Array(this.bounds);\n if (!canonicalizeInPlace(canon, this.dim)) {\n return DBM.empty(this.clockNames);\n }\n return new DBM(canon, this.dim, this.clockNames, false);\n }\n\n equals(other: DBM): boolean {\n if (this === other) return true;\n if (this._empty && other._empty) return true;\n if (this._empty || other._empty) return false;\n if (this.clockNames.length !== other.clockNames.length) return false;\n for (let i = 0; i < this.clockNames.length; i++) {\n if (this.clockNames[i] !== other.clockNames[i]) return false;\n }\n if (this.bounds.length !== other.bounds.length) return false;\n for (let i = 0; i < this.bounds.length; i++) {\n if (Math.abs(this.bounds[i]! - other.bounds[i]!) > EPSILON) return false;\n }\n return true;\n }\n\n toString(): string {\n if (this._empty) return 'DBM[empty]';\n const parts: string[] = [];\n for (let i = 0; i < this.clockNames.length; i++) {\n const lo = formatBound(this.getLowerBound(i));\n const hi = formatBound(this.getUpperBound(i));\n parts.push(`${this.clockNames[i]}:[${lo},${hi}]`);\n }\n return `DBM{${parts.join(', ')}}`;\n }\n}\n\nfunction makeMatrix(dim: number, fill: number): Float64Array {\n const m = new Float64Array(dim * dim).fill(fill);\n for (let i = 0; i < dim; i++) {\n m[i * dim + i] = 0;\n }\n return m;\n}\n\nfunction canonicalizeInPlace(dbm: Float64Array, dim: number): boolean {\n for (let k = 0; k < dim; k++) {\n for (let i = 0; i < dim; i++) {\n for (let j = 0; j < dim; j++) {\n const ik = dbm[i * dim + k]!;\n const kj = dbm[k * dim + j]!;\n if (ik < Infinity && kj < Infinity) {\n const via = ik + kj;\n if (via < dbm[i * dim + j]!) {\n dbm[i * dim + j] = via;\n }\n }\n }\n }\n }\n for (let i = 0; i < dim; i++) {\n if (dbm[i * dim + i]! < -EPSILON) return false;\n }\n return true;\n}\n\nfunction formatBound(b: number): string {\n if (b >= Infinity / 2) return '\\u221e';\n if (b === Math.trunc(b)) return String(b);\n return b.toFixed(3);\n}\n","import type { Transition } from '../../core/transition.js';\nimport type { MarkingState } from '../marking-state.js';\nimport type { DBM } from './dbm.js';\n\n/**\n * A State Class in Time Petri Net analysis.\n *\n * A state class is a pair (M, D) where M is a marking and D is a firing domain (DBM).\n * State classes provide a finite abstraction of the infinite state space of Time Petri Nets.\n */\nexport class StateClass {\n readonly marking: MarkingState;\n readonly firingDomain: DBM;\n readonly enabledTransitions: readonly Transition[];\n /**\n * Class-relative earliest-ready time (seconds) of each enabled transition,\n * parallel to `enabledTransitions`. Captured from the firing-domain DBM\n * (`getLowerBound(k)`) *before* `letTimePass()` zeroes the lower bounds, i.e.\n * the minimum time from class entry at which clock `k` may fire.\n *\n * Purely additive: base timed-reachability (marking + DBM zone, `equals`,\n * `classKey`) ignores it. Read only by the ν conflict-priority prune (NU-052,\n * `priorityDominated`), where comparing `readyEarliest[H] <= readyEarliest[L]`\n * decides whether the strictly higher-priority `H` becomes ready no later than\n * `L` and so pre-empts it.\n */\n readonly readyEarliest: readonly number[];\n\n constructor(\n marking: MarkingState,\n firingDomain: DBM,\n enabledTransitions: readonly Transition[],\n readyEarliest: readonly number[],\n ) {\n this.marking = marking;\n this.firingDomain = firingDomain;\n this.enabledTransitions = [...enabledTransitions];\n this.readyEarliest = [...readyEarliest];\n }\n\n isEmpty(): boolean {\n return this.firingDomain.isEmpty();\n }\n\n canFire(transition: Transition): boolean {\n const idx = this.enabledTransitions.indexOf(transition);\n if (idx < 0) return false;\n return this.firingDomain.getUpperBound(idx) >= 0;\n }\n\n transitionIndex(transition: Transition): number {\n return this.enabledTransitions.indexOf(transition);\n }\n\n equals(other: StateClass): boolean {\n if (this === other) return true;\n return this.marking.toString() === other.marking.toString()\n && this.firingDomain.equals(other.firingDomain);\n }\n\n toString(): string {\n return `StateClass{${this.marking}, ${this.firingDomain}}`;\n }\n}\n","import type { PetriNet } from '../petri-net.js';\nimport { isPassthrough } from '../transition-action.js';\n\n/**\n * CORE-043: a transition that declares an output spec must not carry the built-in\n * `passthrough()`. It produces no tokens, so output validation (IO-015) rejects every\n * firing and the declared output never arrives. Enforced when a net is compiled for\n * execution and when one is handed to verification, so verification cannot green-light a net that will not compile.\n */\nexport function requireOutputProducingActions(net: PetriNet): void {\n for (const t of net.transitions) {\n if (t.outputSpec !== null && isPassthrough(t.action)) {\n throw new Error(\n `Transition '${t.name}' declares an output spec but carries passthrough(), which ` +\n `produces no tokens. Every firing would fail output validation (IO-015) and ` +\n `the declared output would never arrive. Bind an action that produces it — ` +\n `fork() moves the input token across — or drop the output spec if the ` +\n `transition is meant to be a sink.`,\n );\n }\n }\n}\n","import type { Place } from '../../core/place.js';\nimport type { EnvironmentPlace } from '../../core/place.js';\nimport type { In } from '../../core/in.js';\nimport { consumptionCount } from '../../core/in.js';\nimport type { Transition } from '../../core/transition.js';\nimport type { PetriNet } from '../../core/petri-net.js';\nimport { earliest, latest } from '../../core/timing.js';\nimport { enumerateBranches } from '../../core/out.js';\nimport { MarkingState } from '../marking-state.js';\nimport { DBM } from './dbm.js';\nimport { StateClass } from './state-class.js';\nimport type { EnvironmentAnalysisMode } from './environment-analysis-mode.js';\nimport { ignore } from './environment-analysis-mode.js';\nimport { requireOutputProducingActions } from '../../core/internal/output-action-check.js';\n\n/** Edge that tracks which XOR branch was taken. */\nexport interface BranchEdge {\n readonly branchIndex: number;\n readonly target: StateClass;\n}\n\nexport interface VirtualTransition {\n readonly transition: Transition;\n readonly branchIndex: number;\n readonly outputPlaces: ReadonlySet<Place<any>>;\n}\n\n/**\n * State Class Graph for Time Petri Net analysis.\n *\n * Implements the Berthomieu-Diaz (1991) algorithm for computing the state class\n * graph of a bounded Time Petri Net.\n */\nexport class StateClassGraph {\n readonly net: PetriNet;\n readonly initialClass: StateClass;\n private readonly _stateClasses: StateClass[];\n private readonly _transitions: Map<StateClass, Map<Transition, BranchEdge[]>>;\n private readonly _successors: Map<StateClass, Set<StateClass>>;\n private readonly _predecessors: Map<StateClass, Set<StateClass>>;\n private readonly _complete: boolean;\n\n private constructor(\n net: PetriNet,\n initialClass: StateClass,\n stateClasses: StateClass[],\n transitions: Map<StateClass, Map<Transition, BranchEdge[]>>,\n complete: boolean,\n ) {\n this.net = net;\n this.initialClass = initialClass;\n this._stateClasses = stateClasses;\n this._transitions = transitions;\n this._complete = complete;\n\n // Build successor/predecessor maps\n this._successors = new Map();\n this._predecessors = new Map();\n for (const sc of stateClasses) {\n this._successors.set(sc, new Set());\n this._predecessors.set(sc, new Set());\n }\n for (const [from, tMap] of transitions) {\n for (const edges of tMap.values()) {\n for (const edge of edges) {\n this._successors.get(from)!.add(edge.target);\n this._predecessors.get(edge.target)!.add(from);\n }\n }\n }\n }\n\n /**\n * Builds the state class graph for a Time Petri Net.\n *\n * @throws Error if the net violates CORE-043 — analysis rejects the same nets execution rejects.\n */\n static build(\n net: PetriNet,\n initialMarking: MarkingState,\n maxClasses: number,\n environmentPlaces?: Set<EnvironmentPlace<any>>,\n environmentMode?: EnvironmentAnalysisMode,\n ): StateClassGraph {\n requireOutputProducingActions(net);\n\n const envMode = environmentMode ?? ignore();\n const envPlaces = new Set<Place<any>>();\n if (environmentPlaces) {\n for (const ep of environmentPlaces) {\n envPlaces.add(ep.place);\n }\n }\n\n const initialClass = initialStateClass(net, initialMarking, envPlaces, envMode);\n\n // BFS exploration\n const stateClasses: StateClass[] = [initialClass];\n const stateClassSet = new Set<string>([classKey(initialClass)]);\n const classMap = new Map<string, StateClass>([[classKey(initialClass), initialClass]]);\n const transitionMap = new Map<StateClass, Map<Transition, BranchEdge[]>>();\n transitionMap.set(initialClass, new Map());\n const queue: StateClass[] = [initialClass];\n let complete = true;\n\n while (queue.length > 0) {\n if (stateClasses.length >= maxClasses) {\n complete = false;\n break;\n }\n\n const current = queue.shift()!;\n\n for (const transition of current.enabledTransitions) {\n const virtualTransitions = expandTransition(transition);\n\n for (const vt of virtualTransitions) {\n const successor = computeSuccessor(net, current, vt, envPlaces, envMode);\n if (successor === null || successor.isEmpty()) continue;\n\n // Add edge with branch index\n const tEdges = transitionMap.get(current)!;\n if (!tEdges.has(transition)) tEdges.set(transition, []);\n tEdges.get(transition)!.push({ branchIndex: vt.branchIndex, target: successor });\n\n // Dedup state classes by key\n const key = classKey(successor);\n if (!stateClassSet.has(key)) {\n stateClassSet.add(key);\n classMap.set(key, successor);\n stateClasses.push(successor);\n transitionMap.set(successor, new Map());\n queue.push(successor);\n } else {\n // Rewrite edge target to existing canonical instance\n const canonical = classMap.get(key)!;\n if (canonical !== successor) {\n const edges = tEdges.get(transition)!;\n edges[edges.length - 1] = { branchIndex: vt.branchIndex, target: canonical };\n }\n }\n }\n }\n }\n\n return new StateClassGraph(net, initialClass, stateClasses, transitionMap, complete);\n }\n\n stateClasses(): readonly StateClass[] {\n return this._stateClasses;\n }\n\n size(): number {\n return this._stateClasses.length;\n }\n\n isComplete(): boolean {\n return this._complete;\n }\n\n successors(sc: StateClass): Set<StateClass> {\n return this._successors.get(sc) ?? new Set();\n }\n\n predecessors(sc: StateClass): Set<StateClass> {\n return this._predecessors.get(sc) ?? new Set();\n }\n\n /** Returns all outgoing transitions with their branch edges. */\n outgoingBranchEdges(sc: StateClass): Map<Transition, BranchEdge[]> {\n return this._transitions.get(sc) ?? new Map();\n }\n\n /** Returns the branch edges for a specific transition from a state class. */\n branchEdges(sc: StateClass, transition: Transition): BranchEdge[] {\n const map = this._transitions.get(sc);\n if (!map) return [];\n return map.get(transition) ?? [];\n }\n\n /** Returns all transitions that are enabled from a state class. */\n enabledTransitions(sc: StateClass): Set<Transition> {\n const map = this._transitions.get(sc);\n if (!map) return new Set();\n return new Set(map.keys());\n }\n\n /** Finds all state classes with a given marking. */\n classesWithMarking(marking: MarkingState): StateClass[] {\n const key = marking.toString();\n return this._stateClasses.filter(sc => sc.marking.toString() === key);\n }\n\n /** Checks if a marking is reachable. */\n isReachable(marking: MarkingState): boolean {\n const key = marking.toString();\n return this._stateClasses.some(sc => sc.marking.toString() === key);\n }\n\n /** Gets all reachable markings. */\n reachableMarkings(): Set<string> {\n const markings = new Set<string>();\n for (const sc of this._stateClasses) {\n markings.add(sc.marking.toString());\n }\n return markings;\n }\n\n /** Counts edges in the graph (each branch edge counts separately). */\n edgeCount(): number {\n let count = 0;\n for (const map of this._transitions.values()) {\n for (const edges of map.values()) {\n count += edges.length;\n }\n }\n return count;\n }\n\n toString(): string {\n return `StateClassGraph[classes=${this.size()}, edges=${this.edgeCount()}, complete=${this._complete}]`;\n }\n}\n\nfunction classKey(sc: StateClass): string {\n return `${sc.marking.toString()}|${sc.firingDomain.toString()}`;\n}\n\n/**\n * Builds the initial state class (enabled set + firing-domain DBM after letting\n * time pass). Shared by the plain SCG and the name-aware ν-partition SCG\n * (NU-050, Route B).\n */\nexport function initialStateClass(\n net: PetriNet,\n initialMarking: MarkingState,\n envPlaces: Set<Place<any>>,\n envMode: EnvironmentAnalysisMode,\n): StateClass {\n const enabledTransitions = findEnabledTransitions(net, initialMarking, envPlaces, envMode);\n const clockNames = enabledTransitions.map(t => t.name);\n const lowerBounds = enabledTransitions.map(t => earliest(t.timing) / 1000);\n const upperBounds = enabledTransitions.map(t => latest(t.timing) / 1000);\n const baseDBM = DBM.create(clockNames, lowerBounds, upperBounds);\n // Class-relative earliest-ready time of each enabled clock, captured BEFORE\n // letTimePass() zeroes the DBM lower bounds (NU-052 residual-earliest).\n const readyEarliest = enabledTransitions.map((_, k) => baseDBM.getLowerBound(k));\n const initialDBM = baseDBM.letTimePass();\n return new StateClass(initialMarking, initialDBM, enabledTransitions, readyEarliest);\n}\n\nexport function expandTransition(t: Transition): VirtualTransition[] {\n let branches: ReadonlyArray<ReadonlySet<Place<any>>>;\n\n if (t.outputSpec !== null) {\n branches = enumerateBranches(t.outputSpec);\n } else {\n branches = [new Set()];\n }\n\n return branches.map((outputPlaces, i) => ({\n transition: t,\n branchIndex: i,\n outputPlaces: outputPlaces as ReadonlySet<Place<any>>,\n }));\n}\n\nexport function computeSuccessor(\n net: PetriNet,\n current: StateClass,\n fired: VirtualTransition,\n environmentPlaces: Set<Place<any>>,\n environmentMode: EnvironmentAnalysisMode,\n): StateClass | null {\n const transition = fired.transition;\n\n // 1. Compute new marking\n const newMarking = fireTransition(current.marking, transition, fired.outputPlaces, environmentPlaces, environmentMode);\n\n // 2. Determine persistent and newly enabled transitions\n const newEnabledAll = findEnabledTransitions(net, newMarking, environmentPlaces, environmentMode);\n\n const persistent: Transition[] = [];\n const persistentIndices: number[] = [];\n for (let i = 0; i < current.enabledTransitions.length; i++) {\n const t = current.enabledTransitions[i]!;\n if (t !== transition && newEnabledAll.includes(t)) {\n persistent.push(t);\n persistentIndices.push(i);\n }\n }\n\n const newlyEnabled: Transition[] = [];\n for (const t of newEnabledAll) {\n if (!persistent.includes(t)) {\n newlyEnabled.push(t);\n }\n }\n\n // 3. Compute successor DBM\n const firedIdx = current.transitionIndex(transition);\n const newClockNames = newlyEnabled.map(t => t.name);\n const newLowerBounds = newlyEnabled.map(t => earliest(t.timing) / 1000);\n const newUpperBounds = newlyEnabled.map(t => latest(t.timing) / 1000);\n\n const firedDBM = current.firingDomain.fireTransition(\n firedIdx,\n newClockNames,\n newLowerBounds,\n newUpperBounds,\n persistentIndices,\n );\n\n // allEnabled order matches firedDBM's clock order (persistent-then-newly-enabled).\n // Capture the class-relative earliest-ready time of each clock BEFORE\n // letTimePass() zeroes the DBM lower bounds (NU-052 residual-earliest).\n const allEnabled = [...persistent, ...newlyEnabled];\n const readyEarliest = allEnabled.map((_, k) => firedDBM.getLowerBound(k));\n\n const newDBM = firedDBM.letTimePass();\n\n return new StateClass(newMarking, newDBM, allEnabled, readyEarliest);\n}\n\nfunction findEnabledTransitions(\n net: PetriNet,\n marking: MarkingState,\n environmentPlaces: Set<Place<any>>,\n environmentMode: EnvironmentAnalysisMode,\n): Transition[] {\n const enabled: Transition[] = [];\n for (const transition of net.transitions) {\n if (isEnabled(transition, marking, environmentPlaces, environmentMode)) {\n enabled.push(transition);\n }\n }\n return enabled;\n}\n\nfunction isEnabled(\n transition: Transition,\n marking: MarkingState,\n environmentPlaces: Set<Place<any>>,\n environmentMode: EnvironmentAnalysisMode,\n): boolean {\n for (const spec of transition.inputSpecs) {\n const required = inputRequiredCount(spec);\n if (!checkPlaceEnabled(spec.place, required, marking, environmentPlaces, environmentMode)) {\n return false;\n }\n }\n\n for (const arc of transition.reads) {\n if (!checkPlaceEnabled(arc.place, 1, marking, environmentPlaces, environmentMode)) {\n return false;\n }\n }\n\n for (const arc of transition.inhibitors) {\n if (marking.hasTokens(arc.place)) {\n return false;\n }\n }\n\n return true;\n}\n\nfunction inputRequiredCount(spec: In): number {\n switch (spec.type) {\n case 'one': return 1;\n case 'exactly': return spec.count;\n case 'all': return 1;\n case 'at-least': return spec.minimum;\n }\n}\n\n/**\n * Number of tokens this transition removes from `spec.place` when it fires,\n * given the `available` count currently in that place.\n *\n * Delegates to {@link consumptionCount} — the canonical IO-007 definition in\n * `core/in.ts`. The executors do not call it: `BitmapNetExecutor` fuses the\n * same rule into its consume loop (`bitmap-net-executor.ts:745`) and\n * `PrecompiledNetExecutor` compiles it to a CONSUME_ALL / CONSUME_ATLEAST\n * opcode resolved at run time (`precompiled-net.ts:423`). Three encodings of\n * one rule, which must stay in agreement.\n *\n * The analysis MUST NOT add a fourth: a divergent local definition here is\n * exactly what produced a verifier soundness bug (`all` was modelled as\n * consuming 1).\n *\n * `all` and `at-least` are **draining** arcs. The executor removes *every*\n * available token, not merely the minimum needed to enable. Do not\n * \"simplify\" this back to a constant. Modelling a minimum leaves residual\n * tokens the real net never holds; those phantom tokens keep inhibitor arcs\n * on the drained place unsatisfied, so successor state classes are never\n * generated and a genuinely reachable marking is reported unreachable. Since\n * `nu-scg-verifier` derives a `proven` verdict from this graph, that is a\n * false `Proven` — an unsound result, not merely an imprecise one.\n *\n * Note the deliberate asymmetry with {@link inputRequiredCount}\n * (`all` => 1, `at-least` => minimum): *enablement* tests the minimum,\n * *consumption* takes everything. Both are correct, for different questions.\n */\nfunction inputConsumeCount(spec: In, available: number): number {\n return consumptionCount(spec, available);\n}\n\nfunction checkPlaceEnabled(\n place: Place<any>,\n required: number,\n marking: MarkingState,\n environmentPlaces: Set<Place<any>>,\n environmentMode: EnvironmentAnalysisMode,\n): boolean {\n if (!environmentPlaces.has(place)) {\n return marking.tokens(place) >= required;\n }\n\n switch (environmentMode.type) {\n case 'always-available': return true;\n case 'bounded': return required <= environmentMode.maxTokens;\n case 'ignore': return marking.tokens(place) >= required;\n }\n}\n\nfunction fireTransition(\n marking: MarkingState,\n transition: Transition,\n outputPlaces: ReadonlySet<Place<any>>,\n environmentPlaces: Set<Place<any>>,\n environmentMode: EnvironmentAnalysisMode,\n): MarkingState {\n const builder = MarkingState.builder().copyFrom(marking);\n\n // Consume from inputs. `all`/`at-least` drain the place, so the consumed\n // amount depends on what is actually there — read the current marking.\n for (const spec of transition.inputSpecs) {\n const available = marking.tokens(spec.place);\n if (available < inputRequiredCount(spec)) {\n // Only reachable for environment places under the always-available /\n // bounded modes, where enablement deliberately ignores the concrete\n // marking. consumeFromPlace is a no-op for those, so nothing to remove.\n continue;\n }\n const toConsume = inputConsumeCount(spec, available);\n consumeFromPlace(builder, spec.place, toConsume, environmentPlaces, environmentMode);\n }\n\n // Reset places\n for (const arc of transition.resets) {\n const current = marking.tokens(arc.place);\n if (current > 0) {\n builder.removeTokens(arc.place, current);\n }\n }\n\n // Produce to outputs\n for (const place of outputPlaces) {\n builder.addTokens(place, 1);\n }\n\n return builder.build();\n}\n\nfunction consumeFromPlace(\n builder: ReturnType<typeof MarkingState.builder>,\n place: Place<any>,\n count: number,\n environmentPlaces: Set<Place<any>>,\n environmentMode: EnvironmentAnalysisMode,\n): void {\n if (!environmentPlaces.has(place)) {\n builder.removeTokens(place, count);\n return;\n }\n if (environmentMode.type === 'ignore') {\n builder.removeTokens(place, count);\n }\n}\n","/**\n * @module counterexample-decoder\n *\n * Decodes z3's refutation output into replayable counterexample material.\n *\n * There is exactly one decoder: {@link decodeStateSet}, which collects the ground\n * `Reachable` facts of a `:produce-proofs` refutation into a SET. The ordered trace\n * a caller sees is reconstructed from that set by the abstract replayer; the proof\n * printer's traversal order is not a firing order and was never safe to read as one.\n *\n * Applications with non-ground arguments (rule bodies quantify `Reachable` over\n * variables) or the wrong arity are skipped; a malformed proof simply yields a\n * smaller (possibly empty) set, never a throw. Byte-for-byte mirror of the Rust\n * `counterexample::decode_state_set`.\n */\nimport { MarkingState } from '../marking-state.js';\nimport type { FlatNet } from '../encoding/flat-net.js';\nimport { sexprEnd } from './smt-text.js';\n\n/** Result of counterexample decoding. */\nexport interface DecodedTrace {\n /**\n * The ground `Reachable` markings of the proof as an order-free set (text order\n * preserved for display), what the abstract replayer chains into a firing order.\n */\n readonly states: ReadonlySet<MarkingState>;\n /** Why nothing was decoded; `null` when `states` is non-empty. */\n readonly note: string | null;\n}\n\n/** Decodes the states of a z3 reply; a note says so when none were found. */\nexport function decode(answer: string, flatNet: FlatNet): DecodedTrace {\n const states = decodeStateSet(answer, flatNet);\n return { states, note: states.size === 0 ? 'no ground Reachable states in the z3 proof' : null };\n}\n\n/**\n * Collects the ground `Reachable(...)` applications from a z3 refutation proof into\n * a state set, in text order.\n */\nexport function decodeStateSet(answer: string, flatNet: FlatNet): ReadonlySet<MarkingState> {\n const byKey = new Map<string, MarkingState>();\n const P = flatNet.places.length;\n for (const head of ['(Reachable', '(|Reachable|']) {\n let from = 0;\n for (;;) {\n const start = answer.indexOf(head, from);\n if (start < 0) break;\n from = start + head.length;\n // Word boundary: \"(Reachable\" must not match \"(ReachableFoo …\".\n if (head === '(Reachable') {\n const next = answer[from];\n if (next == null || !(/\\s/.test(next) || next === ')')) continue;\n }\n const end = sexprEnd(answer, start);\n if (end < 0) break;\n const inner = answer.slice(start + head.length, end - 1);\n const args = parseGroundIntArgs(inner);\n if (args != null && args.length === P) {\n const marking = toMarking(args, flatNet);\n const key = marking.toString();\n if (!byKey.has(key)) byKey.set(key, marking);\n }\n }\n }\n return new Set(byKey.values());\n}\n\nfunction toMarking(args: readonly number[], flatNet: FlatNet): MarkingState {\n const builder = MarkingState.builder();\n for (let i = 0; i < args.length; i++) {\n if (args[i]! > 0) builder.tokens(flatNet.places[i]!, args[i]!);\n }\n return builder.build();\n}\n\n/**\n * Parses an application's argument text into integers, accepting only GROUND\n * arguments: bare integer literals (`3`, `-1`) and the SMT-LIB negation form\n * `(- 3)`. Any other token (a bound variable, a nested expression) makes the\n * application non-ground: returns `null`.\n */\nexport function parseGroundIntArgs(inner: string): number[] | null {\n const args: number[] = [];\n let rest = inner.trimStart();\n while (rest !== '') {\n if (rest.startsWith('(')) {\n const stripped = rest.slice(1);\n const close = stripped.indexOf(')');\n if (close < 0) return null;\n const body = stripped.slice(0, close);\n if (body.includes('(')) return null;\n const trimmed = body.trim();\n if (!trimmed.startsWith('-')) return null;\n const n = parseInt64(trimmed.slice(1).trim());\n if (n == null) return null;\n args.push(-n);\n rest = stripped.slice(close + 1).trimStart();\n } else {\n let tokenEnd = rest.length;\n for (let i = 0; i < rest.length; i++) {\n const c = rest[i]!;\n if (/\\s/.test(c) || c === '(' || c === ')') {\n tokenEnd = i;\n break;\n }\n }\n const n = parseInt64(rest.slice(0, tokenEnd));\n if (n == null) return null;\n args.push(n);\n rest = rest.slice(tokenEnd).trimStart();\n }\n }\n return args;\n}\n\nfunction parseInt64(token: string): number | null {\n return /^-?\\d+$/.test(token) ? Number(token) : null;\n}\n","import type { Place } from '../../core/place.js';\nimport type { FlatTransition } from './flat-transition.js';\n\n/**\n * A flattened Petri net with indexed places and XOR-expanded transitions.\n *\n * Intermediate representation between the high-level PetriNet and Z3 CHC encoding.\n */\nexport interface FlatNet {\n /** Ordered list of places (index = position). */\n readonly places: readonly Place<any>[];\n /** Reverse lookup: place name -> index. */\n readonly placeIndex: ReadonlyMap<string, number>;\n /** XOR-expanded flat transitions. */\n readonly transitions: readonly FlatTransition[];\n /** For bounded environment places: place name -> max tokens. */\n readonly environmentBounds: ReadonlyMap<string, number>;\n /**\n * Environment places whose tokens the analysis MODELS as externally injected\n * (VER-006). Maps env place name -> injection bound: a number caps injection\n * (`Bounded(k)`), `null` means unbounded (`AlwaysAvailable`). Absent entries\n * (incl. `Ignore` mode) are not injected. The encoder emits one injection CHC\n * rule per entry and the incidence matrix gains one injector column per entry\n * so closed-net P-invariants over these places are correctly discarded.\n */\n readonly environmentInjection: ReadonlyMap<string, number | null>;\n}\n\nexport function flatNetPlaceCount(net: FlatNet): number {\n return net.places.length;\n}\n\nexport function flatNetTransitionCount(net: FlatNet): number {\n return net.transitions.length;\n}\n\nexport function flatNetIndexOf(net: FlatNet, place: Place<any>): number {\n return net.placeIndex.get(place.name) ?? -1;\n}\n","/**\n * @module abstract-replayer\n *\n * Pure TS-side replayer for Spacer counterexamples over the ABSTRACT\n * (untimed, value-blind) count-vector semantics — the exact semantics the CHC\n * encoder emits and the Lean development verifies:\n *\n * - {@link enabledA} mirrors `lean/Libpetri/Basic.lean` `enabledA` and the\n * encoder's `encodeEnabled` arm (smt-encoder.ts): every input place holds at\n * least `pre[p]` tokens, every inhibited place is empty, every read place is\n * non-empty.\n * - {@link fireA} mirrors `Basic.lean` `fireA` and the encoder's `encodeFire`\n * arm: a reset or consume-all (`All`/`AtLeast`) place jumps to `post[p]`;\n * every other place moves by `M[p] - pre[p] + post[p]`.\n * - {@link successors} mirrors one disjunct of `encodeStepRelation`: a firing\n * is a successor only when its `M'` also respects `environmentBounds` (the\n * `envBounds(M')` conjunct every transition disjunct carries), and one\n * injection per modeled environment place whose guard admits it.\n * - {@link injectA} mirrors `encodeInjectionFire`/`encodeInjectionGuard`\n * (VER-006): one environment injection adds one token to the env place,\n * gated by `M[p] < k` for `Bounded(k)` and unguarded for `AlwaysAvailable`.\n * - {@link satisfiesBad} mirrors `encodePropertyViolation` — including the\n * relax-env deadlock enablement and the declared-sink exemption — as a\n * direct TS evaluator, so confirming a counterexample never needs a Z3 call.\n *\n * Because the abstraction over-approximates the concrete timed/valued net\n * (VER-004), a decoded counterexample can be spurious. This module therefore\n * only ever REPORTS an outcome ({@link ReplayOutcome}) — nothing here is\n * allowed to certify by crashing, and only the `no-chain` outcome (a fully\n * explored search that found no chain) is strong enough to withdraw a verdict.\n */\nimport type { FlatNet } from '../encoding/flat-net.js';\nimport type { FlatTransition } from '../encoding/flat-transition.js';\nimport type { SmtProperty } from '../smt-property.js';\nimport type { Place } from '../../core/place.js';\nimport { MarkingState } from '../marking-state.js';\nimport { flatNetIndexOf } from '../encoding/flat-net.js';\n\n/** An abstract marking: token count per flat place index. */\nexport type AbstractState = readonly number[];\n\n/** One abstract step in a replayed chain. */\nexport type ReplayStep =\n | { readonly kind: 'fire'; readonly transition: string }\n | { readonly kind: 'inject'; readonly place: string };\n\n/** Display name for a step: the flat transition name, or `inject(<place>)`. */\nexport function stepName(step: ReplayStep): string {\n return step.kind === 'fire' ? step.transition : `inject(${step.place})`;\n}\n\n/** Canonical key for an abstract state (place counts joined by comma). */\nexport function stateKey(state: AbstractState): string {\n return state.join(',');\n}\n\n/** Projects a MarkingState onto the flat place indexing as a count vector. */\nexport function vectorize(marking: MarkingState, flatNet: FlatNet): number[] {\n return flatNet.places.map(p => marking.tokens(p));\n}\n\n/** Rebuilds a MarkingState from a count vector (inverse of {@link vectorize}). */\nexport function toMarkingState(state: AbstractState, flatNet: FlatNet): MarkingState {\n const builder = MarkingState.builder();\n for (let i = 0; i < flatNet.places.length; i++) {\n if (state[i]! > 0) builder.tokens(flatNet.places[i]!, state[i]!);\n }\n return builder.build();\n}\n\n/**\n * Abstract enablement (`Basic.lean` `enabledA`; encoder `encodeEnabled` with\n * `relaxEnv = false`): `M[p] >= pre[p]` per input, `M[p] = 0` per inhibitor,\n * `M[p] >= 1` per read. The encoder's non-negativity conjunct is invariant\n * here (states start in ℕ^P and every step preserves it), so it is not\n * re-checked.\n */\nexport function enabledA(state: AbstractState, ft: FlatTransition): boolean {\n const P = state.length;\n for (let p = 0; p < P; p++) {\n if (ft.preVector[p]! > 0 && state[p]! < ft.preVector[p]!) return false;\n }\n for (const p of ft.readPlaces) {\n if (state[p]! < 1) return false;\n }\n for (const p of ft.inhibitorPlaces) {\n if (state[p]! !== 0) return false;\n }\n return true;\n}\n\n/**\n * The abstract fire relation (`Basic.lean` `fireA`; encoder `encodeFire`):\n *\n * - reset place → `M'[p] = post[p]`\n * - consume-all place → `M'[p] = post[p]` (All/AtLeast drain the place)\n * - otherwise → `M'[p] = M[p] - pre[p] + post[p]`\n */\nexport function fireA(state: AbstractState, ft: FlatTransition): number[] {\n return fireIndexed(state, ft, new Set(ft.resetPlaces));\n}\n\n/** {@link fireA} with the transition's reset places already indexed. */\nfunction fireIndexed(\n state: AbstractState,\n ft: FlatTransition,\n resets: ReadonlySet<number>,\n): number[] {\n const P = state.length;\n const next = new Array<number>(P);\n for (let p = 0; p < P; p++) {\n if (resets.has(p) || ft.consumeAll[p]) {\n next[p] = ft.postVector[p]!;\n } else {\n next[p] = state[p]! - ft.preVector[p]! + ft.postVector[p]!;\n }\n }\n return next;\n}\n\n/**\n * One environment injection (encoder `encodeInjectionFire`): adds one token at\n * `idx`, all other places unchanged. Callers gate on the bound (VER-006).\n */\nexport function injectA(state: AbstractState, idx: number): number[] {\n const next = [...state];\n next[idx] = next[idx]! + 1;\n return next;\n}\n\n/** A successor state together with the step that produced it. */\nexport interface Successor {\n readonly state: number[];\n readonly step: ReplayStep;\n}\n\n/**\n * Per-replay indexes over a flat net, built once and reused by every expansion:\n * reset places per transition, the injection map, and the environment post-caps\n * every transition disjunct of the step relation carries.\n */\ninterface ReplayIndex {\n readonly flatNet: FlatNet;\n /** `resetSets[t]` — reset place indices of `flatNet.transitions[t]`. */\n readonly resetSets: readonly ReadonlySet<number>[];\n /** Injected env place index -> injection bound (`null` = unbounded). */\n readonly envInj: ReadonlyMap<number, number | null>;\n /** `environmentBounds` as `[place index, cap]` pairs: `M'[idx] <= cap`. */\n readonly envCaps: readonly (readonly [number, number])[];\n}\n\nfunction buildIndex(flatNet: FlatNet): ReplayIndex {\n const resetSets = flatNet.transitions.map(ft => new Set(ft.resetPlaces));\n const envInj = new Map<number, number | null>();\n for (const [name, bound] of flatNet.environmentInjection) {\n const idx = flatNet.placeIndex.get(name);\n if (idx != null) envInj.set(idx, bound);\n }\n const envCaps: [number, number][] = [];\n for (const [name, cap] of flatNet.environmentBounds) {\n const idx = flatNet.placeIndex.get(name);\n if (idx != null) envCaps.push([idx, cap]);\n }\n return { flatNet, resetSets, envInj, envCaps };\n}\n\n/** The `envBounds(M')` conjunct of every transition disjunct (smt-encoder.ts). */\nfunction withinEnvBounds(index: ReplayIndex, state: AbstractState): boolean {\n for (const [idx, cap] of index.envCaps) {\n if (state[idx]! > cap) return false;\n }\n return true;\n}\n\n/**\n * All abstract successors of a state under the UNSTRENGTHENED step relation:\n * every enabled flat transition whose successor also respects the environment\n * post-caps, plus one injection per modeled environment place whose guard\n * admits it (`M[p] < k` for `Bounded(k)`, always for `AlwaysAvailable`).\n */\nexport function successors(state: AbstractState, flatNet: FlatNet): Successor[] {\n return successorsIndexed(buildIndex(flatNet), state);\n}\n\nfunction successorsIndexed(index: ReplayIndex, state: AbstractState): Successor[] {\n const out: Successor[] = [];\n const transitions = index.flatNet.transitions;\n for (let t = 0; t < transitions.length; t++) {\n const ft = transitions[t]!;\n if (!enabledA(state, ft)) continue;\n const next = fireIndexed(state, ft, index.resetSets[t]!);\n // The encoder conjoins envBounds(M') into every transition disjunct: a\n // firing that would push an environment place over its cap is NOT a step of\n // the encoded system, and chaining through one would confirm a trace the\n // CHC system cannot produce.\n if (!withinEnvBounds(index, next)) continue;\n out.push({ state: next, step: { kind: 'fire', transition: ft.name } });\n }\n for (const [name, bound] of index.flatNet.environmentInjection) {\n const idx = index.flatNet.placeIndex.get(name);\n if (idx == null) continue;\n if (bound === null || state[idx]! < bound) {\n out.push({ state: injectA(state, idx), step: { kind: 'inject', place: name } });\n }\n }\n return out;\n}\n\n/**\n * Relax-env enablement (encoder `encodeEnabled` with `relaxEnv = true`), used\n * only inside the deadlock predicate: input/read requirements on injectable\n * environment places are satisfiable by external injection — `AlwaysAvailable`\n * always, `Bounded(k)` iff the required cardinality is ≤ k.\n */\nfunction enabledRelaxEnv(\n state: AbstractState,\n ft: FlatTransition,\n envInj: ReadonlyMap<number, number | null>,\n): boolean {\n const P = state.length;\n for (let p = 0; p < P; p++) {\n const pre = ft.preVector[p]!;\n if (pre <= 0) continue;\n if (envInj.has(p)) {\n const bound = envInj.get(p)!;\n if (bound !== null && pre > bound) return false; // never enableable\n continue; // satisfiable by injection\n }\n if (state[p]! < pre) return false;\n }\n for (const p of ft.readPlaces) {\n if (envInj.has(p)) {\n const bound = envInj.get(p)!;\n if (bound !== null && bound < 1) return false;\n continue;\n }\n if (state[p]! < 1) return false;\n }\n for (const p of ft.inhibitorPlaces) {\n if (state[p]! !== 0) return false;\n }\n return true;\n}\n\n/**\n * Deadlock predicate (encoder `encodeDeadlock`): no flat transition is enabled\n * under relax-env semantics — a marking an external injection could re-enable\n * is NOT a deadlock (VER-006).\n */\nfunction isDeadlockA(index: ReplayIndex, state: AbstractState): boolean {\n for (const ft of index.flatNet.transitions) {\n if (enabledRelaxEnv(state, ft, index.envInj)) return false;\n }\n return true;\n}\n\n/**\n * TS evaluator of the property-violation predicate `Bad(M)` — the direct\n * mirror of the encoder's `encodePropertyViolation`, including the declared\n * sink exemption for deadlock-freedom and the \"unresolved place\" edge cases\n * (unknown pending → never violated; unresolved unreachable places are\n * skipped, exactly as the encoder skips them).\n */\nexport function satisfiesBad(\n state: AbstractState,\n flatNet: FlatNet,\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n): boolean {\n return satisfiesBadIndexed(buildIndex(flatNet), state, property, sinkPlaces);\n}\n\nfunction satisfiesBadIndexed(\n index: ReplayIndex,\n state: AbstractState,\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n): boolean {\n const flatNet = index.flatNet;\n switch (property.type) {\n case 'deadlock-free': {\n if (!isDeadlockA(index, state)) return false;\n for (const sink of sinkPlaces) {\n const idx = flatNetIndexOf(flatNet, sink);\n if (idx >= 0 && state[idx]! > 0) return false; // quiescent at a declared sink\n }\n return true;\n }\n case 'mutual-exclusion': {\n const idx1 = flatNetIndexOf(flatNet, property.p1);\n const idx2 = flatNetIndexOf(flatNet, property.p2);\n if (idx1 < 0 || idx2 < 0) return false; // encoder would have thrown before replay\n return state[idx1]! >= 1 && state[idx2]! >= 1;\n }\n case 'place-bound':\n case 'branch-place-bound': {\n const idx = flatNetIndexOf(flatNet, property.place);\n if (idx < 0) return false; // encoder would have thrown before replay\n return state[idx]! > property.bound;\n }\n case 'joined-or-dead-lettered': {\n const idx = flatNetIndexOf(flatNet, property.pending);\n if (idx < 0) return false; // mirror: unknown pending place is never a violation\n return isDeadlockA(index, state) && state[idx]! >= 1;\n }\n case 'unreachable': {\n let resolved = 0;\n for (const p of property.places) {\n const idx = flatNetIndexOf(flatNet, p);\n if (idx < 0) continue; // unresolved places skipped (encoder parity)\n resolved++;\n if (state[idx]! < 1) return false;\n }\n // With nothing resolved the conjunction would be vacuously true and EVERY\n // marking would violate — replay would then \"confirm\" at M0.\n return resolved > 0;\n }\n }\n}\n\n/** Options for {@link replayCounterexample}. */\nexport interface ReplayOptions {\n /** Max abstract steps searched between decoded anchors (default 3). */\n readonly segmentBudget?: number;\n /**\n * Max search nodes ADMITTED to the whole search (default 10_000).\n *\n * A node is admitted when it survives the segment budget and the domination\n * check; dominated successors are never admitted and never counted. The root\n * (`M₀`) counts as the first admitted node, and the search stops as soon as\n * `nodeBudget` nodes have been admitted and another one is due — the same\n * `>=`-before-admission rule the Rust and Java replayers apply, so the same\n * nominal budget means the same effective search depth in all of them.\n */\n readonly nodeBudget?: number;\n}\n\n/**\n * Outcome of an abstract replay attempt.\n *\n * `confirmed` — a genuine abstract chain `M₀ → … → Bad` was found.\n * `no-chain` — the search ran to completion without truncation and no chain\n * exists: the counterexample is spurious or the decoder mis-read the\n * derivation, and ONLY this outcome may withdraw a `violated` verdict.\n * `exhausted` — the search was cut short (node or segment budget, or `M₀` was\n * not among the decoded states), so nothing was proved either way.\n */\nexport type ReplayOutcome =\n | {\n readonly kind: 'confirmed';\n /** The replayed chain in FIRING order, `M₀ … M_bad` inclusive. */\n readonly states: readonly AbstractState[];\n /** One step per consecutive pair of {@link states}. */\n readonly steps: readonly ReplayStep[];\n readonly nodesExplored: number;\n }\n | { readonly kind: 'no-chain'; readonly nodesExplored: number }\n | { readonly kind: 'exhausted'; readonly reason: string; readonly nodesExplored: number };\n\n/** One BFS node; the chain is recovered by walking `parent` back to the root. */\ninterface SearchNode {\n readonly state: AbstractState;\n /** The step that produced {@link state}; null at the root (`M₀`). */\n readonly step: ReplayStep | null;\n /** Index of the predecessor node, or -1 at the root. */\n readonly parent: number;\n /** Steps taken since the last decoded anchor (0 at an anchor). */\n readonly segment: number;\n}\n\n/**\n * Attempts to re-execute a decoded (order-free) counterexample state set in\n * the abstract semantics.\n *\n * The decoder collects Spacer's `Reachable` applications in derivation\n * TRAVERSAL order, which is not firing order; this search recovers a firing\n * order or reports that none exists. It is a single global breadth-first\n * search from `initial` over {@link successors}, where each node carries the\n * number of steps taken since the last decoded state (`segment`, reset to 0\n * whenever a decoded state is reached) and a node is expanded only while that\n * counter is below `segmentBudget`. A state is re-entered only when reached\n * with a strictly smaller segment counter (domination by `(state, segment)`),\n * and the whole search shares one `nodeBudget` counting nodes ADMITTED to the\n * search — non-dominated states only, the root included (see\n * {@link ReplayOptions.nodeBudget}).\n */\nexport function replayCounterexample(\n flatNet: FlatNet,\n initial: AbstractState,\n decodedStates: readonly AbstractState[],\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n options: ReplayOptions = {},\n): ReplayOutcome {\n const segmentBudget = options.segmentBudget ?? 3;\n const nodeBudget = options.nodeBudget ?? 10_000;\n\n const anchors = new Set<string>();\n for (const s of decodedStates) anchors.add(stateKey(s));\n\n if (anchors.size === 0) {\n return { kind: 'exhausted', reason: 'no decoded states to replay', nodesExplored: 0 };\n }\n\n const initKey = stateKey(initial);\n if (!anchors.has(initKey)) {\n // Not evidence against the counterexample — the decoder simply did not\n // recover the init fact, so there is no anchored search to run.\n return {\n kind: 'exhausted',\n reason: 'the initial marking is not among the decoded states',\n nodesExplored: 0,\n };\n }\n\n const index = buildIndex(flatNet);\n if (satisfiesBadIndexed(index, initial, property, sinkPlaces)) {\n return { kind: 'confirmed', states: [initial], steps: [], nodesExplored: 1 };\n }\n\n const nodes: SearchNode[] = [{ state: initial, step: null, parent: -1, segment: 0 }];\n const bestSegment = new Map<string, number>([[initKey, 0]]);\n const queue: number[] = [0];\n let truncated = false;\n\n for (let head = 0; head < queue.length; head++) {\n const idx = queue[head]!;\n const node = nodes[idx]!;\n if (node.segment >= segmentBudget) {\n truncated = true; // the segment budget, not the state space, stopped us here\n continue;\n }\n for (const succ of successorsIndexed(index, node.state)) {\n const key = stateKey(succ.state);\n const segment = anchors.has(key) ? 0 : node.segment + 1;\n const prior = bestSegment.get(key);\n if (prior !== undefined && prior <= segment) continue; // dominated\n bestSegment.set(key, segment);\n\n // Checked BEFORE admission and with `>=`, so at most `nodeBudget` nodes\n // ever enter the search (the root among them) — same rule, same effective\n // depth, as the Rust and Java replayers.\n if (nodes.length >= nodeBudget) {\n return {\n kind: 'exhausted',\n reason: `search budget exhausted (${nodeBudget} nodes) before reaching a violating state`,\n nodesExplored: nodes.length,\n };\n }\n nodes.push({ state: succ.state, step: succ.step, parent: idx, segment });\n const childIdx = nodes.length - 1;\n if (satisfiesBadIndexed(index, succ.state, property, sinkPlaces)) {\n const chain = reconstruct(nodes, childIdx);\n return { kind: 'confirmed', ...chain, nodesExplored: nodes.length };\n }\n queue.push(childIdx);\n }\n }\n\n if (truncated) {\n return {\n kind: 'exhausted',\n reason:\n `no violating state within ${segmentBudget} abstract step(s) of a decoded state ` +\n `(${bestSegment.size} state(s) explored)`,\n nodesExplored: nodes.length,\n };\n }\n return { kind: 'no-chain', nodesExplored: nodes.length };\n}\n\n/** Walks `parent` links back to the root, yielding the chain in firing order. */\nfunction reconstruct(\n nodes: readonly SearchNode[],\n last: number,\n): { states: readonly AbstractState[]; steps: readonly ReplayStep[] } {\n const states: AbstractState[] = [];\n const steps: ReplayStep[] = [];\n for (let i = last; i >= 0; i = nodes[i]!.parent) {\n const node = nodes[i]!;\n states.push(node.state);\n if (node.step != null) steps.push(node.step);\n }\n states.reverse();\n steps.reverse();\n return { states, steps };\n}\n","/**\n * @module name-coloured-encoder\n *\n * Bounded **name-coloured** CHC encoding for ν-net join correlation\n * ([NU-050] #1, Route A — the EUF-style carve-out).\n *\n * The flat {@link module:smt-encoder} is a pure *counting* abstraction: a place\n * is one integer, and a matched (ν-join) transition is encoded name-blind — it\n * fires whenever the input *counts* allow, regardless of whether the consumed\n * tokens actually share a correlation name. That over-approximation is sound for\n * `proven` on reachability-safety bounds but can report a **spurious** `violated`\n * whose counterexample silently equates two *distinct* names.\n *\n * This encoder removes that imprecision for the bounded fragment. The\n * decidability lever ([NU-040]) is a bounded live-name count: a budget place gates\n * minting, and a non-negative **P-semiflow** weighting every coloured place bounds\n * the simultaneously-live names to a finite `k` (`Σ_{coloured} M ≤ y·M0`; see\n * {@link buildColouredPlan} / `colourSlotBound`). So names are modelled as a\n * **finite set of `k` colours**. Each coloured\n * place becomes `k` per-colour integer counts; a mint introduces a *globally\n * fresh* colour (one currently empty everywhere); a matched join consumes the\n * **same colour** from every correlated input. Within the budget bound the\n * encoding is *exact* — sound and complete — so no different-name counterexample\n * survives.\n *\n * **Supported fragment**: {@link buildColouredPlan} returns `null` (and the\n * verifier falls back to the sound over-approximation) unless the net is in the\n * budget-bounded coloured fragment:\n * - coloured places = the correlated inputs of every matched transition, plus (in\n * EXTENDED mode, [NU-051]) the declared carrier places;\n * - each coloured place is *produced only by* minting forks (count 1, no coloured\n * input, costs ≥1 budget token) or EXTENDED relays, and *consumed only by*\n * matched joins or EXTENDED coloured consumers — a relay threads one colour on, a\n * drain drops it, each consuming exactly one coloured input at count 1;\n * - the coloured place set is structurally token-bounded: some non-negative\n * P-semiflow weights every coloured place, so the simultaneously-live colour count\n * is bounded by that semiflow's initial value `k` (`Σ_{coloured} M ≤ y·M0`). A net\n * with no covering non-negative semiflow (an unbounded colour leak) falls back;\n * - coloured places start empty; no inhibitor/read/reset/consume-all arc touches a\n * coloured place.\n *\n * XOR output branches are supported ([NU-053], Part 3): each branch is a separate\n * flat row classified by its own incidence, with `matchSpec` read from its source.\n *\n * **Properties**: reachability-safety properties compare aggregate coloured place\n * counts. Quiescence properties (`deadlock-free`, `joined-or-dead-lettered`) use a\n * colour-aware deadlock predicate ([NU-053], Part 2): every transition is disabled\n * for every colour (a mint has no globally-fresh colour, a join no shared colour, a\n * consumer no resident colour) and the marking is not a sink state — mirroring the\n * flat {@link module:smt-encoder} deadlock with the same env-injection relaxation.\n *\n * Mirrors the Rust reference `name_coloured_encoder.rs` exactly and emits the same\n * SMT-LIB2 text byte for byte (VER-013).\n */\nimport type { PetriNet } from '../../core/petri-net.js';\nimport type { Place } from '../../core/place.js';\nimport type { FlatNet } from '../encoding/flat-net.js';\nimport type { FlatTransition } from '../encoding/flat-transition.js';\nimport type { MarkingState } from '../marking-state.js';\nimport type { SmtProperty } from '../smt-property.js';\nimport type { PInvariant } from '../invariant/p-invariant.js';\nimport type { FragmentMode } from '../analysis/name-fragment.js';\nimport { indexOrdered, injectionMap, type SmtEncoding } from './smt-encoder.js';\n\n/** How a transition relates to the coloured (correlation-carrying) places. */\ntype Klass =\n | { readonly kind: 'mint'; readonly colouredOut: readonly number[] }\n | { readonly kind: 'join'; readonly colouredIn: readonly number[] }\n /**\n * EXTENDED coloured consumer ([NU-051]): a non-match transition that consumes\n * one same-coloured token from `inputCol` (count 1) and threads it into each\n * `colouredOut` (relay) or into none (drain — `colouredOut` empty).\n */\n | { readonly kind: 'consume'; readonly inputCol: number; readonly colouredOut: readonly number[] }\n | { readonly kind: 'untouched' };\n\n/** A validated plan for the name-coloured encoding of a budget-bounded ν-net. */\nexport interface ColouredPlan {\n /** Flat indices of the coloured places (ascending). */\n readonly coloured: readonly number[];\n /** Per flat place: whether it is coloured. */\n readonly isColoured: readonly boolean[];\n /** Colour bound — the number of simultaneously-live names (the P-semiflow slot bound). */\n readonly k: number;\n /** Classification, one entry per flat transition (XOR branches included). */\n readonly classes: readonly Klass[];\n}\n\n/**\n * Sound colour-slot bound `k`: a colour is live iff some coloured place holds it, so\n * `#live colours ≤ Σ_{coloured} M(p) ≤ y·M0` for any non-negative P-semiflow `y`\n * (`y·C = 0`, `y ≥ 0`) that weights every coloured place `≥ 1`. Returns the tightest\n * such `y·M0` (each `PInvariant.constant` is `y·M0`), or `null` when no covering\n * non-negative semiflow exists — the coloured set is then not structurally\n * token-bounded (a genuine unbounded colour leak) and the caller must fall back.\n *\n * `0` is a bound like any other (NU-053 AC6): with the covering law's initial sum at\n * zero no coloured token can ever exist, every mint / join / consumer is dead on the\n * reachable set, and the zero-slot plan is exact (`Semiflow.lean`,\n * `vacuous_colour_layer`). A validated semi-positive law's `y·M0` is never negative.\n *\n * Mirrors the Rust reference `colour_slot_bound`.\n */\nfunction colourSlotBound(coloured: readonly number[], semiflows: readonly PInvariant[]): number | null {\n const w = (inv: PInvariant, pid: number): number => inv.weights[pid] ?? 0;\n const isSemiflow = (inv: PInvariant): boolean => inv.weights.every((x) => x >= 0);\n\n // Tightest bound: a single non-negative P-semiflow weighting every coloured place.\n let single: number | null = null;\n for (const inv of semiflows) {\n if (isSemiflow(inv) && coloured.every((pid) => w(inv, pid) >= 1)) {\n if (single === null || inv.constant < single) single = inv.constant;\n }\n }\n if (single !== null) return single;\n\n // Otherwise sum non-negative semiflows that touch a coloured place — the sum is\n // itself a valid non-negative P-semiflow, so `Σ y·M0` over any covering set is a\n // sound (looser) bound. Zero-constant semiflows cover their places for free, so they\n // go in first; a semiflow with a positive constant is added only if it touches a\n // coloured place the free ones left uncovered (decided against that snapshot, so the\n // result does not depend on enumeration order). If some coloured place stays at\n // weight 0 across all of them, no non-negative semiflow covers it, so the coloured\n // set is not structurally token-bounded → null (sound over-approximation).\n const covered = new Array<boolean>(coloured.length).fill(false);\n for (const inv of semiflows) {\n if (!isSemiflow(inv) || inv.constant !== 0) continue;\n for (let i = 0; i < coloured.length; i++) {\n if (w(inv, coloured[i]!) >= 1) covered[i] = true;\n }\n }\n const free = [...covered];\n let sumConst = 0;\n for (const inv of semiflows) {\n if (!isSemiflow(inv) || inv.constant === 0) continue;\n if (!coloured.some((pid, i) => !free[i] && w(inv, pid) >= 1)) continue;\n for (let i = 0; i < coloured.length; i++) {\n if (w(inv, coloured[i]!) >= 1) covered[i] = true;\n }\n sumConst += inv.constant;\n }\n if (covered.every((c) => c)) return sumConst;\n return null;\n}\n\n/**\n * Detects whether `net` is in the supported budget-bounded coloured fragment\n * (mint→matched-join, plus the EXTENDED coloured consumers and carrier places of\n * [NU-051], with XOR-expanded output branches) and, if so, returns the plan for\n * {@link encodeColoured}. Returns `null` otherwise — the verifier then uses the\n * sound over-approximation.\n *\n * Each flat row carries a back-reference to its source transition\n * ({@link FlatTransition.source}); an XOR transition expands to one flat row per\n * output branch (no 1:1 net↔flat assumption), so we read `matchSpec` from the\n * source while classifying by the flat row's own incidence.\n *\n * `semiflows` are the net's non-negative P-semiflows ({@link computePSemiflows}); a\n * covering one sets the colour-slot bound `k` (see {@link colourSlotBound}).\n */\nexport function buildColouredPlan(\n net: PetriNet,\n flat: FlatNet,\n initial: MarkingState,\n budgetNames: ReadonlySet<string>,\n fragmentMode: FragmentMode,\n carrierPlaces: ReadonlySet<string>,\n semiflows: readonly PInvariant[],\n): ColouredPlan | null {\n const P = flat.places.length;\n\n // 1. Coloured places = every matched transition's correlated inputs, plus (in\n // EXTENDED mode) the declared carrier places that thread a fork-minted name\n // through intermediate places to a ν-join input ([NU-051]).\n const isColoured: boolean[] = new Array<boolean>(P).fill(false);\n for (const t of net.transitions) {\n const ms = t.matchSpec;\n if (ms) {\n for (const key of ms.keys) {\n const pid = flat.placeIndex.get(key.place.name);\n if (pid == null) return null;\n isColoured[pid] = true;\n }\n }\n }\n if (fragmentMode === 'extended') {\n for (const c of carrierPlaces) {\n const pid = flat.placeIndex.get(c);\n if (pid != null) isColoured[pid] = true;\n }\n }\n const coloured: number[] = [];\n for (let i = 0; i < P; i++) if (isColoured[i]) coloured.push(i);\n if (coloured.length === 0) return null;\n\n // Coloured places must start empty — no initial colour assignment is modelled.\n for (const pid of coloured) {\n if (initial.tokens(flat.places[pid]!) !== 0) return null;\n }\n\n // Colour-slot bound k: a colour is live iff some coloured place holds it, so\n // `#live colours ≤ Σ_{coloured} M(p) ≤ y·M0` for any non-negative P-semiflow `y`\n // weighting every coloured place `≥ 1`. `k` is the tightest such `y·M0`; any\n // `k ≥ #live` is sound — a larger k only costs O(k) columns, never\n // under-approximates, since a mint may take any free slot behind the freshness\n // guard. If no covering non-negative semiflow exists the coloured set is not\n // structurally token-bounded (a genuine unbounded colour leak), so fall back to the\n // sound over-approximation. This replaces the old budget-count `k` and both\n // structural discipline checks (atomic-rejoin + budget-Φ) below.\n const k = colourSlotBound(coloured, semiflows);\n if (k === null) return null;\n // NU-053 AC6: `k = 0` is an exact plan — no coloured token can ever exist, so every\n // mint / join / consumer is dead and the zero-slot encoding emits no rule for them\n // (`Semiflow.lean`, `vacuous_colour_layer`). The one shape it cannot encode is a net\n // with no uncoloured place at all (`Reachable` would be nullary and every rule's\n // `ForAll` binder list empty); such a net holds no token at M0, so fall back.\n if (k === 0 && coloured.length === P) return null;\n\n // Budget places gate minting: a mint must consume ≥1 budget token — that is what\n // makes it a fresh-name fork rather than an arbitrary coloured producer.\n const budgetIdx = new Set<number>();\n for (const n of budgetNames) {\n const i = flat.placeIndex.get(n);\n if (i != null) budgetIdx.add(i);\n }\n\n // No inhibitor/read/reset/consume-all arc may touch a coloured place.\n for (const ft of flat.transitions) {\n const touches =\n ft.inhibitorPlaces.some((i) => isColoured[i]) ||\n ft.readPlaces.some((i) => isColoured[i]) ||\n ft.resetPlaces.some((i) => isColoured[i]) ||\n ft.consumeAll.some((ca, i) => ca && isColoured[i]!);\n if (touches) return null;\n }\n\n // 2. Classify each flat row from its own incidence (matchSpec from its source).\n const classes: Klass[] = [];\n for (const ft of flat.transitions) {\n const colouredIn = coloured.filter((pid) => ft.preVector[pid]! > 0);\n const colouredOut = coloured.filter((pid) => ft.postVector[pid]! > 0);\n const ms = ft.source.matchSpec;\n\n if (ms) {\n // Matched join: consumes coloured inputs (count 1), produces none.\n if (colouredOut.length !== 0 || colouredIn.length === 0) return null;\n if (colouredIn.some((pid) => ft.preVector[pid]! !== 1)) return null;\n classes.push({ kind: 'join', colouredIn });\n } else if (colouredIn.length !== 0) {\n // EXTENDED coloured consumer (relay/drain, [NU-051]): a non-match transition\n // consuming a coloured place. Admitted only in EXTENDED mode, and only when it\n // consumes EXACTLY ONE coloured input at count EXACTLY ONE (higher counts would\n // over-count the name layer against the base marking's single token per place).\n // It relays the name into its coloured outputs (each at count 1) or drains it.\n if (fragmentMode !== 'extended') return null;\n if (colouredIn.length !== 1 || ft.preVector[colouredIn[0]!]! !== 1) return null;\n if (colouredOut.some((o) => ft.postVector[o]! !== 1)) return null;\n classes.push({ kind: 'consume', inputCol: colouredIn[0]!, colouredOut });\n } else if (colouredOut.length !== 0) {\n // Minting fork: produces coloured (count 1), consumes none, and must consume\n // ≥1 budget token — that is what makes it a fresh-name fork rather than an\n // arbitrary coloured producer. (Boundedness is decided by the colour-slot bound\n // above, not here.)\n if (colouredOut.some((o) => ft.postVector[o]! !== 1)) return null;\n let budgetConsumed = 0;\n for (const b of budgetIdx) budgetConsumed += ft.preVector[b]!;\n if (budgetConsumed < 1) return null;\n classes.push({ kind: 'mint', colouredOut });\n } else {\n // Touches no coloured place at all.\n classes.push({ kind: 'untouched' });\n }\n }\n\n return { coloured, isColoured, k, classes };\n}\n\n/**\n * Column layout over the coloured state vector: uncoloured place → one var,\n * coloured place → `k` per-colour vars, named exactly as the Rust reference names\n * them (`m{i}` / `m{i}_{c}`, next marking with a `p` suffix).\n */\ninterface Layout {\n /** Column index of each uncoloured place (`-1` if coloured). */\n readonly colUnc: number[];\n /** Per coloured place: its `k` column indices (empty if uncoloured). */\n readonly colCol: number[][];\n /** Current-marking variable names, one per column. */\n readonly cur: string[];\n /** Next-marking variable names, one per column. */\n readonly nxt: string[];\n}\n\nfunction buildLayout(plan: ColouredPlan, P: number): Layout {\n const colUnc: number[] = new Array<number>(P).fill(-1);\n const colCol: number[][] = Array.from({ length: P }, () => []);\n const cur: string[] = [];\n const nxt: string[] = [];\n for (let i = 0; i < P; i++) {\n if (plan.isColoured[i]) {\n const idxs: number[] = [];\n for (let c = 0; c < plan.k; c++) {\n idxs.push(cur.length);\n cur.push(`m${i}_${c}`);\n nxt.push(`m${i}_${c}p`);\n }\n colCol[i] = idxs;\n } else {\n colUnc[i] = cur.length;\n cur.push(`m${i}`);\n nxt.push(`m${i}p`);\n }\n }\n return { colUnc, colCol, cur, nxt };\n}\n\nfunction quantified(names: readonly string[]): string {\n return names.map((v) => `(${v} Int)`).join(' ');\n}\n\n/** A changed column and its update expression. */\ninterface Update {\n readonly col: number;\n readonly expr: string;\n}\n\n/** Contributes the enablement guards and the changed-column updates of a rule. */\ntype Fill = (enab: string[], upd: Update[]) => void;\n\n/**\n * Encodes the supported ν-net as bounded name-coloured CHC for Z3 Spacer, as SMT-LIB2\n * text byte-identical to the Rust reference (`encode_coloured`). With the query\n * `(not Error)`, `sat` ⇒ PROVEN, `unsat` ⇒ VIOLATED (the Spacer convention shared with\n * the flat encoder).\n *\n * Returns `null` when the property names a place that does not resolve in the net\n * (see {@link encodeViolation}); the verifier reports Unknown rather than certify a\n * vacuous PROVEN.\n */\nexport function encodeColoured(\n plan: ColouredPlan,\n flat: FlatNet,\n initial: MarkingState,\n property: SmtProperty,\n invariants: readonly PInvariant[],\n sinkPlaces: ReadonlySet<Place<any>>,\n): SmtEncoding | null {\n const P = flat.places.length;\n const k = plan.k;\n const lay = buildLayout(plan, P);\n const nCols = lay.cur.length;\n\n const lines: string[] = [];\n lines.push('(set-logic HORN)');\n lines.push('');\n lines.push(`(declare-fun Reachable (${new Array<string>(nCols).fill('Int').join(' ')}) Bool)`);\n lines.push('(declare-fun Error () Bool)');\n lines.push('');\n\n // Init: uncoloured places carry their initial count; coloured start empty.\n const init: string[] = [];\n for (let i = 0; i < P; i++) {\n if (plan.isColoured[i]) {\n for (let c = 0; c < k; c++) init.push('0');\n } else {\n init.push(String(initial.tokens(flat.places[i]!)));\n }\n }\n lines.push(`(assert (Reachable ${init.join(' ')}))`);\n lines.push('');\n\n // Transition rules.\n for (let ti = 0; ti < plan.classes.length; ti++) {\n const cls = plan.classes[ti]!;\n const ft = flat.transitions[ti]!;\n switch (cls.kind) {\n case 'untouched':\n lines.push(encodeRule(plan, lay, invariants, (enab, upd) => uncolouredIncidence(lay, plan, ft, enab, upd)));\n break;\n case 'mint':\n for (let c = 0; c < k; c++) {\n lines.push(encodeRule(plan, lay, invariants, (enab, upd) => {\n uncolouredIncidence(lay, plan, ft, enab, upd);\n // Globally fresh colour: c must be empty in every coloured place.\n for (const q of plan.coloured) enab.push(`(= ${lay.cur[lay.colCol[q]![c]!]} 0)`);\n for (const o of cls.colouredOut) {\n const col = lay.colCol[o]![c]!;\n upd.push({ col, expr: `(+ ${lay.cur[col]} 1)` });\n }\n }));\n }\n break;\n case 'join':\n for (let c = 0; c < k; c++) {\n lines.push(encodeRule(plan, lay, invariants, (enab, upd) => {\n uncolouredIncidence(lay, plan, ft, enab, upd);\n // Same colour c present in every correlated input.\n for (const ip of cls.colouredIn) {\n const col = lay.colCol[ip]![c]!;\n enab.push(`(>= ${lay.cur[col]} 1)`);\n upd.push({ col, expr: `(- ${lay.cur[col]} 1)` });\n }\n }));\n }\n break;\n case 'consume':\n // One rule per colour: consume colour c from the single coloured input and\n // thread it into each coloured output (relay), or into none (drain).\n for (let c = 0; c < k; c++) {\n lines.push(encodeRule(plan, lay, invariants, (enab, upd) => {\n uncolouredIncidence(lay, plan, ft, enab, upd);\n const icol = lay.colCol[cls.inputCol]![c]!;\n enab.push(`(>= ${lay.cur[icol]} 1)`);\n upd.push({ col: icol, expr: `(- ${lay.cur[icol]} 1)` });\n for (const o of cls.colouredOut) {\n const ocol = lay.colCol[o]![c]!;\n upd.push({ col: ocol, expr: `(+ ${lay.cur[ocol]} 1)` });\n }\n }));\n }\n break;\n }\n }\n lines.push('');\n\n // Error rule. `null` ⇒ the property names an unresolved place; refuse to build a\n // vacuously-provable encoding and let the verifier report Unknown.\n const error = encodeError(plan, lay, flat, property, sinkPlaces, injectionMap(flat));\n if (error == null) return null;\n lines.push(error);\n lines.push('');\n lines.push('(assert (not Error))');\n lines.push('(check-sat)');\n\n return { smt2: lines.join('\\n'), placeCount: P };\n}\n\n/**\n * Builds one transition CHC rule. `fill` contributes the enablement guards and the\n * changed-column updates; every other column is copied unchanged, changed columns get\n * a non-negativity guard, and the (lifted) P-invariants constrain the successor.\n */\nfunction encodeRule(plan: ColouredPlan, lay: Layout, invariants: readonly PInvariant[], fill: Fill): string {\n const enab: string[] = [];\n const upd: Update[] = [];\n fill(enab, upd);\n\n const conditions: string[] = [`(Reachable ${lay.cur.join(' ')})`, ...enab];\n\n // A changed column gets its update + non-negativity guard; every other column is\n // copied unchanged. A later update of the same column wins.\n const changed: (string | null)[] = new Array<string | null>(lay.cur.length).fill(null);\n for (const u of upd) changed[u.col] = u.expr;\n for (let col = 0; col < lay.cur.length; col++) {\n const expr = changed[col];\n if (expr != null) {\n conditions.push(`(= ${lay.nxt[col]} ${expr})`);\n conditions.push(`(>= ${lay.nxt[col]} 0)`);\n } else {\n conditions.push(`(= ${lay.nxt[col]} ${lay.cur[col]})`);\n }\n }\n\n for (const inv of invariants) {\n const eq = liftedInvariant(inv, plan, lay, lay.nxt);\n if (eq != null) conditions.push(eq);\n }\n\n const body = `(and ${conditions.join('\\n ')})`;\n return `(assert (forall (${quantified([...lay.cur, ...lay.nxt])})\\n (=> ${body}\\n (Reachable ${lay.nxt.join(' ')}))))`;\n}\n\n/**\n * Pushes the enablement guards and column updates contributed by a transition's\n * **uncoloured** incidence (consume/produce on non-coloured places). Coloured columns\n * are handled by the caller (mint produces, join/consumer consume).\n */\nfunction uncolouredIncidence(lay: Layout, plan: ColouredPlan, ft: FlatTransition, enab: string[], upd: Update[]): void {\n const P = ft.preVector.length;\n for (let i = 0; i < P; i++) {\n if (plan.isColoured[i]) continue;\n const col = lay.colUnc[i]!;\n const pre = ft.preVector[i]!;\n if (pre > 0) enab.push(`(>= ${lay.cur[col]} ${pre})`);\n if (ft.resetPlaces.includes(i) || ft.consumeAll[i]) {\n upd.push({ col, expr: String(ft.postVector[i]) });\n } else {\n const delta = ft.postVector[i]! - ft.preVector[i]!;\n if (delta > 0) upd.push({ col, expr: `(+ ${lay.cur[col]} ${delta})` });\n else if (delta < 0) upd.push({ col, expr: `(- ${lay.cur[col]} ${-delta})` });\n }\n }\n // Inhibitor / read arcs (all on uncoloured places — checked in buildColouredPlan).\n for (const pid of ft.inhibitorPlaces) enab.push(`(= ${lay.cur[lay.colUnc[pid]!]} 0)`);\n for (const pid of ft.readPlaces) enab.push(`(>= ${lay.cur[lay.colUnc[pid]!]} 1)`);\n}\n\n/**\n * Aggregate token-count expression for a place over the given var-set (`cur` or\n * `nxt`): the single uncoloured var, or the sum of its colours.\n */\nfunction aggregate(plan: ColouredPlan, lay: Layout, place: number, names: readonly string[]): string {\n if (plan.isColoured[place]) {\n const cols = lay.colCol[place]!;\n // k = 0: a coloured place has no slot and never holds a token.\n if (cols.length === 0) return '0';\n if (cols.length === 1) return names[cols[0]!]!;\n return `(+ ${cols.map((c) => names[c]!).join(' ')})`;\n }\n return names[lay.colUnc[place]!]!;\n}\n\n/**\n * Lifts a flat P-invariant to the coloured layout: a coloured place's variable\n * becomes the sum of its colours (= its aggregate count). Returns `null` when the\n * invariant support is empty.\n */\nfunction liftedInvariant(inv: PInvariant, plan: ColouredPlan, lay: Layout, names: readonly string[]): string | null {\n const terms: string[] = [];\n for (const i of [...inv.support].sort((a, b) => a - b)) {\n const agg = aggregate(plan, lay, i, names);\n const w = inv.weights[i]!;\n terms.push(w === 1 ? agg : `(* ${w} ${agg})`);\n }\n if (terms.length === 0) return null;\n const sum = terms.length === 1 ? terms[0]! : `(+ ${terms.join(' ')})`;\n return `(= ${sum} ${inv.constant})`;\n}\n\n/**\n * Encodes the error rule: a reachable marking that violates the property, or `null`\n * when the property names an unresolved place ({@link encodeViolation}).\n */\nfunction encodeError(\n plan: ColouredPlan,\n lay: Layout,\n flat: FlatNet,\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n envInj: ReadonlyMap<number, number | null>,\n): string | null {\n const violation = encodeViolation(plan, lay, flat, property, sinkPlaces, envInj);\n if (violation == null) return null;\n return `(assert (forall (${quantified(lay.cur)})\\n (=> (and (Reachable ${lay.cur.join(' ')}) ${violation})\\n Error)))`;\n}\n\n/**\n * Encodes the property-violation condition over the coloured current marking.\n * Reachability-safety properties compare aggregate place counts; quiescence\n * properties (NU-053) use the colour-aware deadlock predicate.\n *\n * Returns `null` when the property names a place that does not resolve in the net\n * (e.g. a typo'd bound/pending place). A `false` violation term there would make the\n * Error rule unsatisfiable and yield a **vacuous** PROVEN, silently certifying a\n * mis-named place; `null` propagates up so the verifier reports Unknown instead.\n */\nfunction encodeViolation(\n plan: ColouredPlan,\n lay: Layout,\n flat: FlatNet,\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n envInj: ReadonlyMap<number, number | null>,\n): string | null {\n const anyPlacePresent = (places: Iterable<Place<any>>): string => {\n const conds = indexOrdered(flat, places).map((pid) => `(>= ${aggregate(plan, lay, pid, lay.cur)} 1)`);\n return conds.length === 0 ? 'false' : `(and ${conds.join(' ')})`;\n };\n switch (property.type) {\n case 'place-bound':\n case 'branch-place-bound': {\n const pid = flat.placeIndex.get(property.place.name);\n // Unresolved bound place: a false violation term would vacuously PROVE the\n // bound. Return null so the verifier reports Unknown instead of certifying.\n if (pid == null) return null;\n return `(> ${aggregate(plan, lay, pid, lay.cur)} ${property.bound})`;\n }\n case 'mutual-exclusion':\n return anyPlacePresent([property.p1, property.p2]);\n case 'unreachable':\n return anyPlacePresent(property.places);\n case 'deadlock-free':\n return encodeColouredDeadlock(plan, lay, flat, sinkPlaces, envInj);\n case 'joined-or-dead-lettered': {\n const pid = flat.placeIndex.get(property.pending.name);\n if (pid == null) return null;\n const deadlock = encodeColouredDeadlock(plan, lay, flat, sinkPlaces, envInj);\n return `(and ${deadlock} (>= ${aggregate(plan, lay, pid, lay.cur)} 1))`;\n }\n }\n}\n\n/**\n * The uncoloured disable reasons for a flat row: marking-dependent clauses (any one\n * true ⇒ the transition's uncoloured part is unmet), collected into `reasons`;\n * returns `true` when the transition is permanently disabled (an env cap below the\n * demand means it can never fire). Coloured places are excluded — their enablement is\n * the per-class colour term.\n */\nfunction uncolouredDisable(\n ft: FlatTransition,\n lay: Layout,\n plan: ColouredPlan,\n envInj: ReadonlyMap<number, number | null>,\n reasons: string[],\n): boolean {\n let permanentlyDisabled = false;\n const P = ft.preVector.length;\n for (let i = 0; i < P; i++) {\n if (plan.isColoured[i] || ft.preVector[i] === 0) continue;\n if (envInj.has(i)) {\n const bound = envInj.get(i)!;\n if (bound != null && ft.preVector[i]! > bound) permanentlyDisabled = true;\n continue;\n }\n reasons.push(`(< ${lay.cur[lay.colUnc[i]!]} ${ft.preVector[i]})`);\n }\n for (const inh of ft.inhibitorPlaces) reasons.push(`(> ${lay.cur[lay.colUnc[inh]!]} 0)`);\n for (const rd of ft.readPlaces) {\n if (envInj.has(rd)) {\n const bound = envInj.get(rd)!;\n if (bound != null && bound < 1) permanentlyDisabled = true;\n continue;\n }\n reasons.push(`(< ${lay.cur[lay.colUnc[rd]!]} 1)`);\n }\n return permanentlyDisabled;\n}\n\n/**\n * The colour-specific \"disabled for every colour\" term for a class (`null` if the\n * class imposes no coloured enablement constraint). Combined by the caller with the\n * uncoloured disable reasons: the transition is disabled if EITHER holds.\n */\nfunction colouredDisabledTerm(cls: Klass, plan: ColouredPlan, lay: Layout): string | null {\n const k = plan.k;\n if (k === 0) {\n // k = 0 (NU-053 AC6): no colour can ever be present, so every coloured class is\n // disabled outright; the empty conjunctions below would render as `(and )`.\n return cls.kind === 'untouched' ? null : 'true';\n }\n switch (cls.kind) {\n case 'untouched':\n return null;\n case 'mint': {\n // No globally-fresh colour: for every colour c, some coloured place holds c.\n const perColour: string[] = [];\n for (let c = 0; c < k; c++) {\n const present = plan.coloured.map((q) => `(>= ${lay.cur[lay.colCol[q]![c]!]} 1)`);\n perColour.push(`(or ${present.join(' ')})`);\n }\n return `(and ${perColour.join(' ')})`;\n }\n case 'join': {\n // No colour is shared by all correlated inputs: for every colour c, some input\n // lacks c.\n const perColour: string[] = [];\n for (let c = 0; c < k; c++) {\n const missing = cls.colouredIn.map((i) => `(= ${lay.cur[lay.colCol[i]![c]!]} 0)`);\n perColour.push(`(or ${missing.join(' ')})`);\n }\n return `(and ${perColour.join(' ')})`;\n }\n case 'consume': {\n // No colour present at the single coloured input.\n const perColour: string[] = [];\n for (let c = 0; c < k; c++) perColour.push(`(= ${lay.cur[lay.colCol[cls.inputCol]![c]!]} 0)`);\n return `(and ${perColour.join(' ')})`;\n }\n }\n}\n\n/**\n * Colour-aware deadlock predicate (NU-053): every transition is disabled (no colour\n * enables it) and no declared sink place holds a token (VER-002). Mirrors the flat\n * deadlock with the same env-injection relaxation (VER-006), lifted to the coloured\n * layout.\n */\nfunction encodeColouredDeadlock(\n plan: ColouredPlan,\n lay: Layout,\n flat: FlatNet,\n sinkPlaces: ReadonlySet<Place<any>>,\n envInj: ReadonlyMap<number, number | null>,\n): string {\n const disabledConditions: string[] = [];\n for (let ti = 0; ti < plan.classes.length; ti++) {\n const cls = plan.classes[ti]!;\n const ft = flat.transitions[ti]!;\n const reasons: string[] = [];\n const permanentlyDisabled = uncolouredDisable(ft, lay, plan, envInj, reasons);\n if (permanentlyDisabled) {\n // The transition can never fire — it is always \"disabled\".\n disabledConditions.push('true');\n continue;\n }\n const term = colouredDisabledTerm(cls, plan, lay);\n if (term != null) reasons.push(term);\n // Always enabled (possibly via injection) — no marking is a deadlock.\n if (reasons.length === 0) return 'false';\n disabledConditions.push(reasons.length === 1 ? reasons[0]! : `(or ${reasons.join(' ')})`);\n }\n\n // Declared sinks (VER-002): quiescence is a violation only when NO declared sink\n // holds a token, so each declared sink contributes `aggregate(sink) = 0` over its\n // colour slots. Same predicate as the flat deadlock.\n for (const pid of indexOrdered(flat, sinkPlaces)) {\n disabledConditions.push(`(= ${aggregate(plan, lay, pid, lay.cur)} 0)`);\n }\n\n return disabledConditions.length === 0 ? 'true' : `(and ${disabledConditions.join(' ')})`;\n}\n","/**\n * Name-correlation fragment classifier for the ν-aware state class graph\n * (NU-050, Route B). See the Rust/Java equivalents for the full contract.\n *\n * Identifies the coloured places (the correlated inputs of ν-joins) and the role\n * of each transition in the supported fragment. Returns `null` when the net is\n * not a ν-net or falls outside the admitted fragment (the caller falls back to\n * the SMT / Route A path).\n *\n * {@link FragmentMode.base} (default) admits the shipped mint → matched-join\n * fragment only: a non-match transition consuming a coloured place, or a join\n * re-minting into one, rejects the net. {@link FragmentMode.extended} (opt-in,\n * NU-051) additionally admits the coloured-consumer role ({@link Role} `consume`,\n * drain/relay) and unions user-declared *carrier* places into the coloured set\n * (fork-threaded co-mint). The one deliberate tightening shared by both modes is\n * the reset/read/inhibitor-on-coloured guard below.\n */\nimport type { PetriNet } from '../../core/petri-net.js';\nimport type { Transition } from '../../core/transition.js';\nimport { enumerateBranches } from '../../core/out.js';\n\n/**\n * Selects which coloured-place fragment {@link classify} admits. `base` (default)\n * reproduces the shipped mint → matched-join fragment exactly; `extended`\n * additionally admits the coloured-consumer (drain/relay) role and carrier\n * places (NU-051).\n */\nexport type FragmentMode = 'base' | 'extended';\n\nexport type Role =\n | { readonly type: 'ordinary' }\n | { readonly type: 'mint' }\n | { readonly type: 'join'; readonly colouredIn: ReadonlyArray<readonly [string, number]> }\n /**\n * Coloured consumer (drain/relay), EXTENDED only (NU-051). A non-match\n * transition that consumes **exactly one** coloured place at count **exactly\n * one**. It *relays* the consumed name-symbol into each coloured output of the\n * fired branch (threading `s`), or *drains* it (dead-letters `s`) when the\n * branch produces no coloured output. Because the consumed count is fixed at\n * one, the role carries only the input place name — no count, no list.\n *\n * Documented precondition (NU-051): the action MUST thread the consumed symbol\n * (relay) or drop it (drain); it MUST NOT mint a *fresh* name into a coloured\n * output while consuming a coloured token (a consume-and-remint transition is\n * out of contract — the name layer would thread `s` where the runtime mints\n * afresh).\n */\n | { readonly type: 'consume'; readonly colouredInput: string };\n\nexport interface NameFragment {\n readonly colouredOrder: readonly string[];\n isColoured(place: string): boolean;\n role(transition: string): Role;\n}\n\n/**\n * Classifies `net` under `mode`. Under {@link FragmentMode.extended} the declared\n * `carrierPlaces` (intermediate places carrying a fresh name from the minting\n * fork onward to a ν-join input) are unioned into the coloured set *before* role\n * assignment, so the existing mint co-mints one fresh name into all of them, and\n * non-match transitions may take the drain/relay `consume` role. Under\n * {@link FragmentMode.base} the `carrierPlaces` are ignored and any non-match\n * transition consuming a coloured place rejects the net (NU-051).\n *\n * Both modes reject a net where any coloured place carries a reset, read, or\n * inhibitor arc: those arcs would be silently misclassified ordinary and the\n * name layer would drift from the base marking (a soundness guard; rejection\n * just falls back to the sound over-approximation).\n */\nexport function classify(\n net: PetriNet,\n mode: FragmentMode,\n carrierPlaces: ReadonlySet<string>,\n): NameFragment | null {\n // 1. Coloured places = union of every match transition's correlated inputs,\n // plus (EXTENDED only) the declared carrier places.\n const coloured = new Set<string>();\n let anyMatch = false;\n for (const t of net.transitions) {\n if (t.matchSpec !== null) {\n anyMatch = true;\n for (const key of t.matchSpec.keys) coloured.add(key.place.name);\n }\n }\n if (!anyMatch || coloured.size === 0) return null;\n if (mode === 'extended') {\n for (const c of carrierPlaces) coloured.add(c);\n }\n\n // 1b. Soundness guard (BOTH modes): no coloured place may carry a reset, read,\n // or inhibitor arc on any transition. Checked after the coloured set is\n // finalized (a carrier could carry such an arc).\n for (const t of net.transitions) {\n if (\n t.resets.some(r => coloured.has(r.place.name)) ||\n t.reads.some(r => coloured.has(r.place.name)) ||\n t.inhibitors.some(i => coloured.has(i.place.name))\n ) {\n return null;\n }\n }\n\n const roles = new Map<string, Role>();\n for (const t of net.transitions) {\n const colouredInputs = t.inputSpecs.filter(s => coloured.has(s.place.name));\n const consumesColoured = colouredInputs.length > 0;\n let producesColoured = false;\n if (t.outputSpec !== null) {\n for (const branch of enumerateBranches(t.outputSpec)) {\n for (const p of branch) {\n if (coloured.has(p.name)) producesColoured = true;\n }\n }\n }\n\n let role: Role;\n if (t.matchSpec !== null) {\n if (producesColoured) return null; // re-mint onto a coloured place — out of fragment\n const colouredIn: Array<readonly [string, number]> = [];\n for (const key of t.matchSpec.keys) {\n const place = key.place.name;\n // One/Exactly consume a fixed count of the matched name (faithfully\n // modelled). All/AtLeast consume ALL matching tokens at runtime — the\n // fixed-count SCG step would under-consume — so drop to the over-approx.\n const required = fixedRequiredCount(t, place);\n if (required === null) return null;\n colouredIn.push([place, required] as const);\n }\n colouredIn.sort((a, b) => (a[0] < b[0] ? -1 : a[0] > b[0] ? 1 : 0));\n role = { type: 'join', colouredIn };\n } else if (consumesColoured) {\n // A non-match transition consuming a coloured token.\n if (mode === 'base') return null; // BASE: unsupported — the name would be ambiguous.\n // EXTENDED: admitted as a drain/relay ONLY when it consumes exactly ONE\n // coloured place at count EXACTLY ONE (one or exactly{count:1}). More than\n // one coloured input, or any higher / all / at-least count, would over-count\n // the name layer relative to the base marking (which adds exactly one token\n // per output place) — reject to the sound over-approximation.\n if (colouredInputs.length !== 1) return null;\n const spec = colouredInputs[0]!;\n const countOne = spec.type === 'one' || (spec.type === 'exactly' && spec.count === 1);\n if (!countOne) return null;\n role = { type: 'consume', colouredInput: spec.place.name };\n } else if (producesColoured) {\n role = { type: 'mint' };\n } else {\n role = { type: 'ordinary' };\n }\n roles.set(t.name, role);\n }\n\n const colouredOrder = [...coloured].sort();\n return {\n colouredOrder,\n isColoured: (p) => coloured.has(p),\n role: (tn) => roles.get(tn) ?? { type: 'ordinary' },\n };\n}\n\n/**\n * The fixed per-firing consumption of the matched name for `t`'s input on\n * `placeName`, or `null` when the cardinality consumes ALL matching tokens\n * (all/at-least) or no such input exists — neither of which the fixed-count SCG\n * step can model faithfully.\n */\nfunction fixedRequiredCount(t: Transition, placeName: string): number | null {\n for (const spec of t.inputSpecs) {\n if (spec.place.name === placeName) {\n switch (spec.type) {\n case 'one': return 1;\n case 'exactly': return spec.count;\n case 'all': return null;\n case 'at-least': return null;\n }\n }\n }\n return null;\n}\n","/**\n * The abstract **name-partition** layer for the ν-aware state class graph\n * (NU-050, Route B).\n *\n * The plain {@link StateClassGraph} is name-blind: a marking is a per-place token\n * count, so a ν-join fires whenever the counts allow, ignoring whether the\n * consumed tokens share a correlation name. This carries, beside the count\n * marking, an abstract partition of the correlation tokens into name-symbols. A\n * `Sym` is an opaque identity only (NU-001) — the analyzer never evaluates the\n * runtime name projection. {@link NameMarking.canonicalKey} quotients markings\n * that differ only by a permutation of symbols (the raw ids never appear in a\n * key), keeping the graph finite when the live-name count is structurally\n * bounded. The key string format matches the Rust and Java implementations.\n */\n\nexport type Sym = number;\n\nexport class NameMarking {\n // place name -> (symbol -> count). Only coloured places appear; a place's\n // total here equals its count in the base MarkingState.\n private readonly perPlace: Map<string, Map<Sym, number>>;\n\n constructor(perPlace?: Map<string, Map<Sym, number>>) {\n this.perPlace = perPlace ?? new Map();\n }\n\n copy(): NameMarking {\n const p = new Map<string, Map<Sym, number>>();\n for (const [place, syms] of this.perPlace) {\n p.set(place, new Map(syms));\n }\n return new NameMarking(p);\n }\n\n add(place: string, sym: Sym, count: number): void {\n if (count === 0) return;\n let syms = this.perPlace.get(place);\n if (!syms) {\n syms = new Map();\n this.perPlace.set(place, syms);\n }\n syms.set(sym, (syms.get(sym) ?? 0) + count);\n }\n\n /** Removes `count` of `sym` from `place`; returns false (unchanged) if fewer present. */\n remove(place: string, sym: Sym, count: number): boolean {\n const syms = this.perPlace.get(place);\n if (!syms) return false;\n const have = syms.get(sym);\n if (have === undefined || have < count) return false;\n const left = have - count;\n if (left === 0) {\n syms.delete(sym);\n if (syms.size === 0) this.perPlace.delete(place);\n } else {\n syms.set(sym, left);\n }\n return true;\n }\n\n countOf(place: string, sym: Sym): number {\n return this.perPlace.get(place)?.get(sym) ?? 0;\n }\n\n symbolsIn(place: string): Sym[] {\n const syms = this.perPlace.get(place);\n return syms ? [...syms.keys()] : [];\n }\n\n private liveSymbols(): Sym[] {\n const all = new Set<Sym>();\n for (const syms of this.perPlace.values()) {\n for (const s of syms.keys()) all.add(s);\n }\n return [...all];\n }\n\n /**\n * Symmetry-canonical key over `colouredOrder` (the finiteness mechanism). Two\n * markings differing only by a permutation of symbols produce an identical key\n * (NU-001). Each symbol's signature is its count vector over `colouredOrder`;\n * symbols are ranked by (signature, raw id) and emitted per place as a\n * rank-multiset — a complete invariant of the symbol-permutation orbit.\n */\n canonicalKey(colouredOrder: readonly string[]): string {\n const signature = (s: Sym): number[] => colouredOrder.map(p => this.countOf(p, s));\n const ranked = this.liveSymbols().map(s => ({ sig: signature(s), sym: s }));\n ranked.sort((a, b) => {\n const c = compareNumberArrays(a.sig, b.sig);\n return c !== 0 ? c : a.sym - b.sym;\n });\n const rankOf = new Map<Sym, number>();\n ranked.forEach((r, i) => rankOf.set(r.sym, i));\n\n const parts = colouredOrder.map(p => {\n const syms = this.perPlace.get(p);\n const entries: Array<[number, number]> = [];\n if (syms) {\n for (const [s, c] of syms) entries.push([rankOf.get(s)!, c]);\n }\n entries.sort((a, b) => (a[0] !== b[0] ? a[0] - b[0] : a[1] - b[1]));\n const inner = entries.map(([r, c]) => `${r}x${c}`).join(',');\n return `${p}:{${inner}}`;\n });\n return parts.join('#');\n }\n}\n\nfunction compareNumberArrays(a: readonly number[], b: readonly number[]): number {\n const n = Math.min(a.length, b.length);\n for (let i = 0; i < n; i++) {\n if (a[i]! !== b[i]!) return a[i]! - b[i]!;\n }\n return a.length - b.length;\n}\n","import type { StateClass } from './state-class.js';\nimport type { NameMarking } from './name-marking.js';\n\n/**\n * A name-aware state class (NU-050, Route B): the base count + DBM\n * {@link StateClass} plus the abstract {@link NameMarking} partition layer. The\n * base class is reused verbatim, so the timing/zone dimension is untouched —\n * name×time composition is automatic.\n *\n * Both layers are interned by {@link NameStateClassGraph.build} (VER-012): a class\n * shares its base with every class at the same marking, zone and earliest-ready\n * times, and its name layer with every class whose partition has the same\n * canonical key — a renaming of it, which every consumer of the layer is\n * invariant under (`Interning.lean`, `interned_keys_eq`).\n */\nexport class NameStateClass {\n readonly base: StateClass;\n readonly names: NameMarking;\n /** The symmetry-canonical name-partition key (the name layer's intern key). */\n readonly nameKey: string;\n\n constructor(base: StateClass, names: NameMarking, colouredOrder: readonly string[], nameKey?: string) {\n this.base = base;\n this.names = names;\n this.nameKey = nameKey ?? names.canonicalKey(colouredOrder);\n }\n\n /** Full dedup key: the base key (marking + DBM zone) joined with the name key. */\n get key(): string {\n return `${baseKeyOf(this.base)}||${this.nameKey}`;\n }\n}\n\n/** The base layer's identity for dedup: marking + DBM zone (what `StateClass.equals` compares). */\nexport function baseKeyOf(base: StateClass): string {\n return `${base.marking.toString()}|${base.firingDomain.toString()}`;\n}\n","/**\n * The ν-aware (name-partition quotient) State Class Graph (NU-050, Route B).\n *\n * Mirrors {@link StateClassGraph} — same Berthomieu-Diaz BFS, same count + DBM\n * successor step (reused verbatim via {@link computeSuccessor}) — but each class\n * additionally carries the abstract {@link NameMarking} partition. A ν-join is\n * enabled only when one shared name is present at the required multiplicity in\n * every correlated input; a mint introduces a globally-fresh name-symbol; dedup\n * is by the symmetry-canonical key so states differing only by a permutation of\n * names collapse. If BFS closes within `maxClasses` the graph is the complete\n * reachable quotient (exact); otherwise it truncates and the verifier reports\n * `unknown` (ν-PN reachability is undecidable).\n */\nimport type { PetriNet } from '../../core/petri-net.js';\nimport type { Place } from '../../core/place.js';\nimport type { EnvironmentPlace } from '../../core/place.js';\nimport type { In } from '../../core/in.js';\nimport type { Transition } from '../../core/transition.js';\nimport type { MarkingState } from '../marking-state.js';\nimport type { EnvironmentAnalysisMode } from './environment-analysis-mode.js';\nimport { ignore } from './environment-analysis-mode.js';\nimport { initialStateClass, expandTransition, computeSuccessor } from './state-class-graph.js';\nimport { NameMarking, type Sym } from './name-marking.js';\nimport { NameStateClass, baseKeyOf } from './name-state-class.js';\nimport type { StateClass } from './state-class.js';\nimport type { NameFragment, Role } from './name-fragment.js';\nimport type { PrioritySemantics } from './priority-semantics.js';\n\nexport interface NameEdge {\n readonly from: number;\n readonly to: number;\n readonly transitionName: string;\n}\n\nexport class NameStateClassGraph {\n readonly classes: NameStateClass[] = [];\n readonly edges: NameEdge[] = [];\n private readonly _successors: number[][] = [];\n private _complete = true;\n\n isComplete(): boolean {\n return this._complete;\n }\n\n classCount(): number {\n return this.classes.length;\n }\n\n successorsOf(idx: number): readonly number[] {\n return this._successors[idx]!;\n }\n\n /** The base count-marking of class `idx` (for property queries). */\n markingOf(idx: number): MarkingState {\n return this.classes[idx]!.base.marking;\n }\n\n static build(\n net: PetriNet,\n initialMarking: MarkingState,\n fragment: NameFragment,\n maxClasses: number,\n environmentPlaces?: Set<EnvironmentPlace<any>>,\n environmentMode?: EnvironmentAnalysisMode,\n prioritySemantics: PrioritySemantics = 'none',\n ): NameStateClassGraph {\n const envMode = environmentMode ?? ignore();\n const envPlaces = new Set<Place<any>>();\n if (environmentPlaces) {\n for (const ep of environmentPlaces) envPlaces.add(ep.place);\n }\n\n const graph = new NameStateClassGraph();\n const base0 = initialStateClass(net, initialMarking, envPlaces, envMode);\n // Hash-consing (memory only, no semantic effect — VER-012, `Interning.lean`):\n // the base layer is shared between classes at the same (marking, zone,\n // earliest-ready times) and the name layer between classes with the same\n // canonical key; a class is identified by the pair of intern ids, so no\n // per-class key string is retained.\n const baseIntern = new Map<string, InternedBase>();\n const nameIntern = new Map<string, InternedNames>();\n const indexOf = new Map<string, number>();\n // Coloured places start empty in the supported fragment (the verifier guards\n // this), so the initial name partition is empty.\n const b0 = internBase(baseIntern, base0);\n const n0 = internNames(nameIntern, new NameMarking(), fragment.colouredOrder);\n graph.pushClass(\n new NameStateClass(b0.base, n0.names, fragment.colouredOrder, n0.nameKey),\n classId(b0.id, n0.id),\n indexOf,\n );\n\n const sym = { next: 0 as Sym };\n const queue: number[] = [0];\n\n while (queue.length > 0) {\n if (graph.classes.length >= maxClasses) {\n graph._complete = false;\n break;\n }\n const curIdx = queue.shift()!;\n const current = graph.classes[curIdx]!;\n\n // The enabled transitions of this class as objects — used by the\n // conflict-only priority prune below (NU-052).\n const enabled = current.base.enabledTransitions;\n for (let idxL = 0; idxL < enabled.length; idxL++) {\n const transition = enabled[idxL]!;\n // NU-052: under CONFLICT semantics, skip a firing the eager,\n // priority-ordered executor would never produce — a conflicting,\n // no-later-ready, strictly-higher-priority transition that actually fires\n // takes the contested token first. `idxL` is L's index in the enabled set\n // (parallel to `readyEarliest`).\n if (\n prioritySemantics === 'conflict' &&\n priorityDominated(\n transition,\n idxL,\n enabled,\n current.base.readyEarliest,\n current.base.marking,\n current.names,\n fragment,\n )\n ) {\n continue;\n }\n const role = fragment.role(transition.name);\n for (const vt of expandTransition(transition)) {\n const baseSucc = computeSuccessor(net, current.base, vt, envPlaces, envMode);\n if (baseSucc === null || baseSucc.isEmpty()) continue;\n const nameSuccs = nameSuccessors(role, current.names, vt.outputPlaces, fragment, sym);\n const shared = internBase(baseIntern, baseSucc);\n for (const nm of nameSuccs) {\n const sharedNames = internNames(nameIntern, nm, fragment.colouredOrder);\n const id = classId(shared.id, sharedNames.id);\n let toIdx = indexOf.get(id);\n if (toIdx === undefined) {\n toIdx = graph.classes.length;\n graph.pushClass(\n new NameStateClass(shared.base, sharedNames.names, fragment.colouredOrder, sharedNames.nameKey),\n id,\n indexOf,\n );\n queue.push(toIdx);\n }\n graph.addEdge(curIdx, toIdx, transition.name);\n }\n }\n }\n }\n return graph;\n }\n\n private pushClass(c: NameStateClass, id: string, indexOf: Map<string, number>): void {\n const idx = this.classes.length;\n this.classes.push(c);\n this._successors.push([]);\n indexOf.set(id, idx);\n }\n\n private addEdge(from: number, to: number, name: string): void {\n this.edges.push({ from, to, transitionName: name });\n this._successors[from]!.push(to);\n }\n}\n\ninterface InternedBase {\n readonly id: number;\n readonly base: StateClass;\n}\n\ninterface InternedNames {\n readonly id: number;\n readonly names: NameMarking;\n readonly nameKey: string;\n}\n\n/** A class's identity: the pair of intern ids of its two layers. */\nfunction classId(baseId: number, nameId: number): string {\n return `${baseId}:${nameId}`;\n}\n\n/**\n * Interns the base layer: one {@link StateClass} per distinct (marking, zone,\n * earliest-ready times). `StateClass.equals` is marking + zone, which is all base\n * timed-reachability needs — but the NU-052 prune ({@link priorityDominated}) also\n * reads `readyEarliest`, the class-relative lower bounds captured before\n * `letTimePass`, and two arrivals at one zone can disagree on those (a transition\n * freshly enabled here versus one persistent through an unbounded delay). Sharing a\n * base across name layers is semantics-free only if the shared object carries\n * everything the successor step reads (`Interning.lean`, `equivariance_is_necessary`\n * is the witness), so the key is all three.\n */\nfunction internBase(intern: Map<string, InternedBase>, base: StateClass): InternedBase {\n const key = `${baseKeyOf(base)}#${base.readyEarliest.join(',')}`;\n let entry = intern.get(key);\n if (entry === undefined) {\n entry = { id: intern.size, base };\n intern.set(key, entry);\n }\n return entry;\n}\n\n/**\n * Interns the name layer: one {@link NameMarking} per canonical key. Two layers with\n * the same key are the same partition up to a renaming of symbols, and every\n * consumer of the layer — {@link nameSuccessors}, {@link willFire}, the key itself —\n * is invariant under renaming; freshness stays sound because the mint counter never\n * revisits an id (`Interning.lean`, `interned_keys_eq`).\n */\nfunction internNames(\n intern: Map<string, InternedNames>,\n names: NameMarking,\n colouredOrder: readonly string[],\n): InternedNames {\n const nameKey = names.canonicalKey(colouredOrder);\n let entry = intern.get(nameKey);\n if (entry === undefined) {\n entry = { id: intern.size, names, nameKey };\n intern.set(nameKey, entry);\n }\n return entry;\n}\n\n/** Float slack for the class-relative earliest-ready comparison (matches the DBM's own EPSILON). */\nconst READY_EPS = 1e-9;\n\n/**\n * True if a firing of `l` is pre-empted by conflict-only priority (NU-052): some\n * other enabled transition `h` has strictly higher priority, shares a consumed\n * input place with `l` **under real competition**, becomes ready no later than\n * `l`, and actually fires in this class (produces a name-successor). The executor\n * fires ready transitions in descending priority order within a pass, so `h` takes\n * the contested token and `l` cannot fire — the pruned firing is not\n * runtime-reachable.\n *\n * **Readiness (DBM residual-earliest).** The name-SCG carries a DBM, so a static\n * `earliest(h) <= earliest(l)` does NOT entail \"H ready no later than L\": their\n * class-relative enabling epochs can put H's clock behind L's. We compare the\n * class-relative earliest-ready times captured on the base class\n * (`StateClass.readyEarliest`, the DBM lower bounds before `letTimePass`): H\n * pre-empts L only when `readyEarliest[H] <= readyEarliest[L] + EPS`. This is\n * fully precise on the zone off-diagonal and subsumes the previously-shipped\n * `earliest 0` case (an immediate H has `readyEarliest[H] === 0 <=\n * readyEarliest[L]`), so no capability is lost.\n *\n * **Real competition (multiplicity).** Sharing a consumed place is not enough: if\n * the place holds enough tokens for H and L at once they do not compete, and\n * pruning L would be unsound — see {@link sharesConsumedInput}.\n *\n * The `willFire` guard is essential on a ν-net: a match (join) transition can be\n * base-enabled yet **name-disabled** (its inputs carry no shared name). Such a\n * join never consumes the contested token, so it must not pre-empt a conflicting\n * drain — otherwise a genuine straggler would strand.\n */\nfunction priorityDominated(\n l: Transition,\n idxL: number,\n enabled: readonly Transition[],\n readyEarliest: readonly number[],\n marking: MarkingState,\n names: NameMarking,\n fragment: NameFragment,\n): boolean {\n return enabled.some(\n (h, idxH) =>\n h !== l &&\n h.priority > l.priority &&\n readyEarliest[idxH]! <= readyEarliest[idxL]! + READY_EPS &&\n willFire(h, names, fragment) &&\n sharesConsumedInput(h, l, marking),\n );\n}\n\n/**\n * True if base-enabled `h` actually produces a name-successor from this class — a\n * join finds a shared enabling name and a consumer finds a resident symbol.\n * Ordinary and Mint always fire; only a name-disabled join (or an empty-input\n * consumer) does not, and such a transition must not pre-empt a conflicting firing.\n */\nfunction willFire(h: Transition, names: NameMarking, fragment: NameFragment): boolean {\n const role = fragment.role(h.name);\n switch (role.type) {\n case 'join':\n return enablingSymbols(names, role.colouredIn).length > 0;\n case 'consume':\n return names.symbolsIn(role.colouredInput).length > 0;\n case 'ordinary':\n case 'mint':\n return true;\n default: {\n // Exhaustiveness guard: a future Role member is a compile error here,\n // rather than silently defaulting to will-fire=true.\n const _exhaustive: never = role;\n return _exhaustive;\n }\n }\n}\n\n/**\n * True if `h` and `l` genuinely compete for a consumed token — they share a\n * consumed input place `p` whose token count in `marking` cannot satisfy both\n * demands at once (`count(p) < demand_h(p) + demand_l(p)`). Read and inhibitor\n * arcs are excluded ({@link Transition.inputPlaces} is consumed inputs only),\n * since they do not remove a token another transition competes for. Compared by\n * place name (name-based Place equality, MOD-024).\n *\n * The multiplicity clause is a soundness guard for the NU-052 prune: if the shared\n * place holds enough tokens for both, `h` does NOT rob `l`, so pruning `l` would\n * drop a runtime-reachable firing.\n */\nfunction sharesConsumedInput(h: Transition, l: Transition, marking: MarkingState): boolean {\n const lIns = new Set<string>();\n for (const p of l.inputPlaces()) lIns.add(p.name);\n for (const p of h.inputPlaces()) {\n if (lIns.has(p.name) && marking.tokens(p) < consumedDemand(h, p.name) + consumedDemand(l, p.name)) {\n return true;\n }\n }\n return false;\n}\n\n/**\n * Tokens `t` consumes from the named place on one firing (summed across its input\n * specs referencing that place — normally a single spec). Uses the enablement\n * required-count so `all`/`at-least` demand their minimum, matching the base SCG's\n * consumption model.\n */\nfunction consumedDemand(t: Transition, placeName: string): number {\n let demand = 0;\n for (const spec of t.inputSpecs) {\n if (spec.place.name === placeName) demand += inputRequiredCount(spec);\n }\n return demand;\n}\n\nfunction inputRequiredCount(spec: In): number {\n switch (spec.type) {\n case 'one': return 1;\n case 'exactly': return spec.count;\n case 'all': return 1;\n case 'at-least': return spec.minimum;\n }\n}\n\n/**\n * The coloured output place names of the fired branch (used by Mint to stamp a\n * fresh symbol, and by Consume to relay the consumed symbol).\n */\nfunction colouredOutputs(outputPlaces: ReadonlySet<Place<any>>, fragment: NameFragment): string[] {\n return [...outputPlaces].filter(p => fragment.isColoured(p.name)).map(p => p.name);\n}\n\n/**\n * Name-layer successors of one firing. Ordinary passes the layer through; Mint\n * stamps one globally-fresh symbol into the coloured outputs of this branch (one\n * symbol into several = same-mint siblings); Join yields one successor per\n * enabling symbol (none ⇒ the join is name-disabled); Consume (EXTENDED, NU-051)\n * yields one successor per resident symbol of the single coloured input (count 1,\n * so NONE is dropped), threading that symbol into every coloured output (relay)\n * or dropping it (drain, no coloured output).\n *\n * Exported for the interning test only: this step's equivariance under symbol\n * renaming is the hypothesis `Interning.lean` rests on.\n */\nexport function nameSuccessors(\n role: Role,\n names: NameMarking,\n outputPlaces: ReadonlySet<Place<any>>,\n fragment: NameFragment,\n sym: { next: Sym },\n): NameMarking[] {\n switch (role.type) {\n case 'ordinary':\n return [names.copy()];\n case 'mint': {\n const colouredOut = colouredOutputs(outputPlaces, fragment);\n const nm = names.copy();\n if (colouredOut.length > 0) {\n const fresh = sym.next++;\n for (const p of colouredOut) nm.add(p, fresh, 1);\n }\n return [nm];\n }\n case 'join': {\n const result: NameMarking[] = [];\n for (const s of enablingSymbols(names, role.colouredIn)) {\n const nm = names.copy();\n for (const [p, req] of role.colouredIn) nm.remove(p, s, req);\n result.push(nm);\n }\n return result;\n }\n case 'consume': {\n // Count is fixed at one, so every resident symbol satisfies the required\n // count — NO base-enabled firing is dropped. Emit EXACTLY ONE symbol per\n // coloured output (relay), keeping the name-layer total == base count.\n const colouredOut = colouredOutputs(outputPlaces, fragment);\n const result: NameMarking[] = [];\n for (const s of names.symbolsIn(role.colouredInput)) {\n const nm = names.copy();\n nm.remove(role.colouredInput, s, 1);\n for (const p of colouredOut) nm.add(p, s, 1);\n result.push(nm);\n }\n return result;\n }\n }\n}\n\n/**\n * Symbols that enable a join: present at the required multiplicity in EVERY\n * correlated input — the exactness core of NU-050 (a count-only check would\n * wrongly fire on two distinct names).\n */\nfunction enablingSymbols(names: NameMarking, colouredIn: ReadonlyArray<readonly [string, number]>): Sym[] {\n if (colouredIn.length === 0) return [];\n const [firstPlace, firstReq] = colouredIn[0]!;\n const result: Sym[] = [];\n for (const s of names.symbolsIn(firstPlace)) {\n if (names.countOf(firstPlace, s) < firstReq) continue;\n let ok = true;\n for (let i = 1; i < colouredIn.length; i++) {\n const [p, req] = colouredIn[i]!;\n if (names.countOf(p, s) < req) {\n ok = false;\n break;\n }\n }\n if (ok) result.push(s);\n }\n return result;\n}\n","/**\n * ν-net exact verification via the name-aware state-class-graph name-partition\n * quotient (NU-050, Route B). Bridges {@link NameStateClassGraph} to the\n * {@link SmtVerificationResult} verdict types.\n *\n * {@link verifyViaNameScg} returns `null` when the net is outside the supported\n * mint→matched-join fragment (the caller falls back to the SMT / Route A path);\n * otherwise an exact verdict when the symbolic graph closes, or `unknown` when it\n * truncates (the live correlation pool is unbounded).\n */\nimport type { PetriNet } from '../core/petri-net.js';\nimport type { Place } from '../core/place.js';\nimport type { EnvironmentPlace } from '../core/place.js';\nimport type { MarkingState } from './marking-state.js';\nimport type { EnvironmentAnalysisMode } from './analysis/environment-analysis-mode.js';\nimport { classify, type FragmentMode } from './analysis/name-fragment.js';\nimport type { PrioritySemantics } from './analysis/priority-semantics.js';\nimport { NameStateClassGraph } from './analysis/name-state-class-graph.js';\nimport type { SmtProperty } from './smt-property.js';\nimport type { Verdict } from './smt-verification-result.js';\n\nconst NOTE_EXACT =\n '\\nNote: ν-join correlation decided exactly via the state-class-graph name-partition ' +\n 'quotient — the symbolic graph closed, so the verdict is sound AND complete (no spurious ' +\n 'different-name counterexample; quiescence is name-aware), beyond the bounded-budget ' +\n 'fragment (NU-050, Route B).\\n';\n\nexport interface NuScgOutcome {\n readonly verdict: Verdict;\n readonly trace: MarkingState[];\n readonly transitions: string[];\n readonly note: string;\n readonly classCount: number;\n}\n\nexport function verifyViaNameScg(\n net: PetriNet,\n initial: MarkingState,\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n environmentPlaces: Set<EnvironmentPlace<any>>,\n environmentMode: EnvironmentAnalysisMode,\n maxClasses: number,\n fragmentMode: FragmentMode,\n carrierPlaces: ReadonlySet<string>,\n prioritySemantics: PrioritySemantics,\n): NuScgOutcome | null {\n const fragment = classify(net, fragmentMode, carrierPlaces);\n if (fragment === null) return null;\n // We model no initial colour assignment, so coloured places must start empty.\n for (const p of initial.placesWithTokens()) {\n if (fragment.isColoured(p.name)) return null;\n }\n\n const scg = NameStateClassGraph.build(\n net, initial, fragment, maxClasses, environmentPlaces, environmentMode, prioritySemantics,\n );\n\n if (!scg.isComplete()) {\n return {\n verdict: {\n type: 'unknown',\n reason:\n `ν name-aware state-class graph truncated at ${maxClasses} classes — the live ` +\n 'correlation pool is not structurally bounded; reachability over unbounded fresh ' +\n 'names is undecidable (NU-050, Route B). Declare a budget place to bound the live ' +\n 'pool, or raise nuMaxClasses.',\n },\n trace: [],\n transitions: [],\n note: '',\n classCount: scg.classCount(),\n };\n }\n\n const violating = decide(scg, property, sinkPlaces);\n if (violating >= 0) {\n const [trace, transitions] = counterexamplePath(scg, violating);\n return { verdict: { type: 'violated' }, trace, transitions, note: NOTE_EXACT, classCount: scg.classCount() };\n }\n return {\n verdict: { type: 'proven', method: 'ν name-partition SCG (NU-050, Route B)', inductiveInvariant: null },\n trace: [],\n transitions: [],\n note: NOTE_EXACT,\n classCount: scg.classCount(),\n };\n}\n\n/** Returns a witnessing class index for a violation, or -1 if the property holds. */\nfunction decide(scg: NameStateClassGraph, property: SmtProperty, sinkPlaces: ReadonlySet<Place<any>>): number {\n const firstWhere = (pred: (i: number) => boolean): number => {\n for (let i = 0; i < scg.classCount(); i++) {\n if (pred(i)) return i;\n }\n return -1;\n };\n\n switch (property.type) {\n case 'place-bound':\n case 'branch-place-bound':\n return firstWhere(i => scg.markingOf(i).tokens(property.place) > property.bound);\n case 'unreachable':\n return firstWhere(i => {\n const m = scg.markingOf(i);\n for (const p of property.places) {\n if (!m.hasTokens(p)) return false;\n }\n return true;\n });\n case 'mutual-exclusion':\n return firstWhere(i => {\n const m = scg.markingOf(i);\n return m.hasTokens(property.p1) && m.hasTokens(property.p2);\n });\n case 'deadlock-free':\n return firstWhere(i => scg.successorsOf(i).length === 0 && !allTokensInSinks(scg.markingOf(i), sinkPlaces));\n case 'joined-or-dead-lettered':\n return firstWhere(i => scg.successorsOf(i).length === 0 && scg.markingOf(i).hasTokens(property.pending));\n }\n}\n\nfunction allTokensInSinks(m: MarkingState, sinks: ReadonlySet<Place<any>>): boolean {\n const sinkNames = new Set<string>();\n for (const s of sinks) sinkNames.add(s.name);\n for (const p of m.placesWithTokens()) {\n if (!sinkNames.has(p.name)) return false;\n }\n return true;\n}\n\n/** Shortest firing sequence from the initial class (0) to `target`. */\nfunction counterexamplePath(scg: NameStateClassGraph, target: number): [MarkingState[], string[]] {\n const n = scg.classCount();\n const parent = new Array<number>(n).fill(-1);\n const via = new Array<string>(n).fill('');\n const visited = new Array<boolean>(n).fill(false);\n visited[0] = true;\n const queue: number[] = [0];\n while (queue.length > 0) {\n const u = queue.shift()!;\n if (u === target) break;\n for (const e of scg.edges) {\n if (e.from === u && !visited[e.to]) {\n visited[e.to] = true;\n parent[e.to] = u;\n via[e.to] = e.transitionName;\n queue.push(e.to);\n }\n }\n }\n const chain: number[] = [];\n for (let cur = target; cur !== -1; cur = parent[cur]!) {\n chain.push(cur);\n }\n chain.reverse();\n const markings = chain.map(i => scg.markingOf(i));\n const transitions = chain.slice(1).map(i => via[i]!);\n return [markings, transitions];\n}\n","import type { PetriNet } from '../core/petri-net.js';\nimport type { EnvironmentPlace, Place } from '../core/place.js';\nimport { MarkingState, MarkingStateBuilder } from './marking-state.js';\nimport type { SmtProperty } from './smt-property.js';\nimport { deadlockFree, propertyDescription } from './smt-property.js';\nimport type { SmtVerificationResult, SmtStatistics, Verdict } from './smt-verification-result.js';\nimport type { PInvariant } from './invariant/p-invariant.js';\nimport type { FlatNet } from './encoding/flat-net.js';\nimport { flatten } from './encoding/net-flattener.js';\nimport { type EnvironmentAnalysisMode, alwaysAvailable } from './analysis/environment-analysis-mode.js';\nimport { IncidenceMatrix } from './encoding/incidence-matrix.js';\nimport { canonicalInvariantOrder, computePInvariants, computePSemiflows, isCoveredByInvariants, strengthenWithSemiflows, validateInvariantsExact } from './invariant/p-invariant-computer.js';\nimport { structuralCheck } from './invariant/structural-check.js';\nimport { runZ3Spacer } from './z3/spacer-runner.js';\nimport { checkCertificate, vcScript, type CertificateCheckOutcome } from './z3/certificate-checker.js';\nimport { encode, type SmtEncoding } from './z3/smt-encoder.js';\nimport { formatZ3Version, resolveZ3, Z3Unavailable, type Z3Solver } from './z3/z3-process.js';\nimport { buildColouredPlan, encodeColoured, type ColouredPlan } from './z3/name-coloured-encoder.js';\nimport { verifyViaNameScg } from './nu-scg-verifier.js';\nimport type { FragmentMode } from './analysis/name-fragment.js';\nimport type { PrioritySemantics } from './analysis/priority-semantics.js';\nimport { decode } from './z3/counterexample-decoder.js';\nimport {\n replayCounterexample, vectorize, toMarkingState, stepName, type ReplayOutcome,\n} from './z3/abstract-replayer.js';\nimport { requireOutputProducingActions } from '../core/internal/output-action-check.js';\n\n/**\n * IC3/PDR-based safety verifier for Petri nets using Z3's Spacer engine.\n *\n * Proves safety properties (especially deadlock-freedom) without\n * enumerating all reachable states. IC3 constructs inductive invariants\n * incrementally, which works well for bounded nets.\n *\n * Key design decisions:\n * - Operates on the marking projection (integer vectors) — no timing\n * - An untimed deadlock-freedom proof is stronger than needed\n * (timing can only restrict behavior)\n * - Input specifications are purely structural (IO-006) — there is no per-arc\n * predicate for the encoder to be blind to\n * - If a counterexample is found, it may be spurious in timed semantics —\n * the report notes this\n *\n * Verification Pipeline:\n * 1. Flatten — expand XOR, index places, build pre/post vectors\n * 2. Structural pre-check — siphon/trap analysis (may prove early)\n * 3. P-invariants — compute conservation laws for strengthening\n * 4. SMT encode + query — IC3/PDR via Z3 Spacer\n * 5. Decode result — proof or counterexample trace\n */\nexport class SmtVerifier {\n private _initialMarking: MarkingState = MarkingState.empty();\n private _property: SmtProperty = deadlockFree();\n private readonly _environmentPlaces = new Set<EnvironmentPlace<any>>();\n private readonly _sinkPlaces = new Set<Place<any>>();\n private readonly _budgetPlaces = new Set<string>();\n private _environmentMode: EnvironmentAnalysisMode = alwaysAvailable();\n private _timeoutMs: number = 60_000;\n private _certificateCheck: boolean = true;\n private _counterexampleReplay: boolean = true;\n private _semiflowInvariants: boolean = false;\n private _nuMaxClasses: number = 100_000;\n private _fragmentMode: FragmentMode = 'base';\n private readonly _carrierPlaces = new Set<string>();\n private _prioritySemantics: PrioritySemantics = 'none';\n\n private constructor(private readonly net: PetriNet) {}\n\n static forNet(net: PetriNet): SmtVerifier {\n return new SmtVerifier(net);\n }\n\n initialMarking(marking: MarkingState): this;\n initialMarking(configurator: (builder: MarkingStateBuilder) => void): this;\n initialMarking(arg: MarkingState | ((builder: MarkingStateBuilder) => void)): this {\n if (arg instanceof MarkingState) {\n this._initialMarking = arg;\n } else {\n const builder = MarkingState.builder();\n arg(builder);\n this._initialMarking = builder.build();\n }\n return this;\n }\n\n property(property: SmtProperty): this {\n this._property = property;\n return this;\n }\n\n environmentPlaces(...places: EnvironmentPlace<any>[]): this {\n for (const p of places) this._environmentPlaces.add(p);\n return this;\n }\n\n environmentMode(mode: EnvironmentAnalysisMode): this {\n this._environmentMode = mode;\n return this;\n }\n\n /**\n * Declares expected sink (terminal) places for deadlock-freedom analysis.\n * Markings where any sink place has a token are not considered deadlocks.\n */\n sinkPlaces(...places: Place<any>[]): this {\n for (const p of places) this._sinkPlaces.add(p);\n return this;\n }\n\n /**\n * Declares ν-net budget places (NU-040): places whose token count bounds the\n * live correlation pool (they gate fresh-name minting). Declaring at least one\n * places the net in the decidable bounded fragment, so reachability-safety\n * properties over its ν-joins are verified (the matched transitions are\n * over-approximated). Without any budget place, a net that mints fresh names\n * is treated as unbounded and the verifier returns `unknown` (NU-050).\n */\n budgetPlaces(...places: Place<any>[]): this {\n for (const p of places) this._budgetPlaces.add(p.name);\n return this;\n }\n\n timeout(ms: number): this {\n this._timeoutMs = ms;\n return this;\n }\n\n /**\n * Enables/disables the independent IC3 certificate check (default: enabled).\n *\n * When a proven verdict comes from the IC3/Spacer path on the flat count\n * encoding, the synthesized inductive invariant is re-validated with a plain\n * solver against the UNSTRENGTHENED step relation — VC1 (init), VC2\n * (consecution), VC3 (safety) — so a Spacer or encoder defect cannot certify\n * a false PROVEN. A certificate that fails validation downgrades the verdict\n * to unknown. Structural proofs and the coloured ν-encoding are unaffected.\n */\n certificateCheck(enabled: boolean): this {\n this._certificateCheck = enabled;\n return this;\n }\n\n /**\n * Enables/disables abstract counterexample replay (default: enabled).\n *\n * When a violated verdict comes from the flat count encoding, the decoded\n * counterexample states (an order-free set — the derivation tree is walked in\n * traversal order, not firing order) are re-executed TS-side against the\n * abstract semantics the encoder emits (Lean's `fireA`, Basic.lean), searching\n * for a firing order from M₀ to a property-violating marking. See\n * `SmtVerificationResult.counterexampleConfirmed` for how each outcome lands.\n */\n counterexampleReplay(enabled: boolean): this {\n this._counterexampleReplay = enabled;\n return this;\n }\n\n /**\n * Also hands the validated **P-semiflows** to the encoders as invariants\n * (VER-007; default: disabled — the encoders then see only the null-space basis).\n *\n * Every validated semiflow is a conservation law in its own right (`y >= 0`,\n * `y·C = 0`, `y·M0` exact, zero weight on every reset / consume-all place), and\n * the Farkas enumeration returns the *minimal* laws of the net. The null-space\n * basis the encoders get by default is one basis of many: elimination hands back\n * mixed-sign rows (discarded as not semi-positive) or rows that fold a reset place\n * into a chain whose other combinations avoid it (dropped by the H1 guard). On a\n * net with a few reset arcs that can lose every law of the chains those arcs\n * touch, and without them IC3 has to rediscover the conservation of each chain —\n * on a ~100-place net it does not within any practical budget. With the semiflows\n * in, the same reachability-safety queries close in about a second.\n *\n * Soundness is unchanged: the semiflows pass the same exact re-validation as the\n * basis rows, the union is pure strengthening (`Semiflow.lean`,\n * `semiflow_union_sound`), and the certificate check re-proves the strengthened\n * invariant. Off by default so reports stay byte-equal.\n */\n semiflowInvariants(enabled: boolean): this {\n this._semiflowInvariants = enabled;\n return this;\n }\n\n /**\n * Sets the class-count cap for the ν-aware state-class-graph analysis (NU-050,\n * Route B). When the symbolic name-aware graph would exceed this, the analysis\n * truncates and the verdict is `unknown` (the live correlation pool is not\n * structurally bounded). Default 100_000.\n */\n nuMaxClasses(max: number): this {\n this._nuMaxClasses = max;\n return this;\n }\n\n /**\n * Selects the ν-net coloured-place fragment for Route B (NU-051). `base`\n * (default) admits the shipped mint → matched-join fragment only; `extended`\n * additionally admits the opt-in coloured-consumer (drain/relay) role and the\n * declared {@link carrierPlaces}. When `extended` is requested but the net\n * falls outside the coloured-consumer fragment, Route B declines and a short\n * note is appended to the report before falling back to the sound\n * over-approximation.\n */\n fragmentMode(mode: FragmentMode): this {\n this._fragmentMode = mode;\n return this;\n }\n\n /**\n * Declares ν-net *carrier* places (NU-051, EXTENDED only): intermediate places\n * that carry a fresh name from the minting fork onward to a ν-join input. Under\n * {@link fragmentMode} `extended` they are unioned into the coloured set so the\n * existing mint co-mints one fresh name into all of them; under `base` they are\n * ignored. Accumulating. Throws if a declared place is not in the net — a\n * mistyped carrier name would let two fork branches mint independent names, so\n * the join never becomes name-enabled and the verifier would otherwise report a\n * confident false deadlock; it must surface, never silently proceed.\n */\n carrierPlaces(...places: Place<any>[]): this {\n for (const p of places) {\n if (![...this.net.places].some(np => np.name === p.name)) {\n throw new Error(`declared carrier place '${p.name}' not in the net`);\n }\n this._carrierPlaces.add(p.name);\n }\n return this;\n }\n\n /**\n * Selects how the Route-B name-aware analyzer treats transition priority\n * (NU-052). Defaults to `'none'` (the priority-blind over-approximation).\n * `'conflict'` models the executor's conflict-only priority resolution, so a\n * lower-priority transition pre-empted by a conflicting, no-later-ready,\n * strictly-higher-priority one is not explored — removing spurious\n * dead-letter-drain stalls the eager, priority-ordered executor never produces.\n */\n prioritySemantics(semantics: PrioritySemantics): this {\n this._prioritySemantics = semantics;\n return this;\n }\n\n /**\n * The SMT-LIB2 scripts {@link verify} would send to z3 for this configuration,\n * without running a solver (VER-013 AC1): the HORN query (flat, or name-coloured\n * when a declared budget puts the net on Route A's exact encoding) and, for the\n * flat encoding, the certificate-check script built around\n * {@link placeholderCertificate}. This is what the cross-language golden tests diff\n * byte for byte. Route B, the structural pre-check and the unresolved-place\n * refusal are bypassed: it is what Route A encodes.\n */\n encodeScripts(): EncodedScripts {\n requireOutputProducingActions(this.net);\n const hasMatch = [...this.net.transitions].some(t => t.matchSpec !== null);\n const nuBounded = this._budgetPlaces.size > 0;\n const flatNet = flatten(this.net, this._environmentPlaces, this._environmentMode);\n const matrix = IncidenceMatrix.from(flatNet);\n const { valid: basis } = validateInvariantsExact(\n matrix, computePInvariants(matrix, flatNet, this._initialMarking), flatNet, this._initialMarking,\n );\n const { valid: semiflows } = validateInvariantsExact(\n matrix, computePSemiflows(matrix, flatNet, this._initialMarking), flatNet, this._initialMarking,\n );\n let invariants: readonly PInvariant[] = basis;\n if (this._semiflowInvariants) invariants = strengthenWithSemiflows(basis, semiflows).invariants;\n invariants = canonicalInvariantOrder(invariants);\n if (hasMatch && nuBounded) {\n const plan = buildColouredPlan(\n this.net, flatNet, this._initialMarking, this._budgetPlaces,\n this._fragmentMode, this._carrierPlaces, semiflows,\n );\n if (plan != null) {\n const coloured = encodeColoured(plan, flatNet, this._initialMarking, this._property, invariants, this._sinkPlaces);\n if (coloured != null) return { horn: coloured.smt2, certificate: null, coloured: true };\n }\n }\n const horn = encode(flatNet, this._initialMarking, this._property, invariants, this._sinkPlaces, this._counterexampleReplay).smt2;\n const certificate = vcScript(\n placeholderCertificate(flatNet.places.length), flatNet, this._initialMarking,\n this._property, this._sinkPlaces, invariants,\n );\n return { horn, certificate, coloured: false };\n }\n\n /**\n * Runs the verification pipeline.\n *\n * @throws Error if the net violates CORE-043 — verification rejects the same nets execution rejects.\n */\n async verify(): Promise<SmtVerificationResult> {\n requireOutputProducingActions(this.net);\n const start = performance.now();\n const report: string[] = [];\n report.push('=== IC3/PDR SAFETY VERIFICATION ===\\n');\n report.push(`Net: ${this.net.name}`);\n const propDesc = this._sinkPlaces.size === 0\n ? propertyDescription(this._property)\n : `${propertyDescription(this._property)} (sinks: ${[...this._sinkPlaces].map(p => p.name).join(', ')})`;\n report.push(`Property: ${propDesc}`);\n report.push(`Timeout: ${(this._timeoutMs / 1000).toFixed(0)}s\\n`);\n\n // ν-net awareness (NU-040, NU-050). A transition with a match spec joins by\n // name equality; the untimed encoder over-approximates that (name equality\n // assumed satisfiable). Sound for reachability-safety bounds (proven holds —\n // the real net fires strictly fewer joins) but NOT for quiescence-based\n // properties, which name-blind firing distorts. `applyNuGuard` turns those\n // cases into unknown.\n const hasMatch = [...this.net.transitions].some(t => t.matchSpec !== null);\n const nuBounded = this._budgetPlaces.size > 0;\n\n // ν-net Route B (NU-050): the name-aware state-class-graph name-partition\n // quotient decides ν-join correlation EXACTLY — including name×time and\n // quiescence — without a budget. It \"fills the gaps\" the SMT / Route A path\n // cannot answer exactly: quiescence properties on a ν-net, and unbudgeted\n // reachability-safety. Budgeted, untimed reachability-safety in Route A's\n // fragment stays on Route A below (this trigger is false there). If the net is\n // outside the supported fragment, verifyViaNameScg returns null and we fall\n // through to the existing pipeline (which applies the sound unknown downgrade).\n if (hasMatch && (!isReachabilitySafety(this._property) || !nuBounded)) {\n const outcome = verifyViaNameScg(\n this.net, this._initialMarking, this._property, this._sinkPlaces,\n this._environmentPlaces, this._environmentMode, this._nuMaxClasses,\n this._fragmentMode, this._carrierPlaces, this._prioritySemantics,\n );\n // Route B truncating to unknown on a bounded quiescence ν-net is not the\n // final word: defer to the scalable Route A coloured IC3/PDR encoder\n // (NU-053) below instead of returning unknown here.\n const deferToRouteA =\n outcome !== null &&\n outcome.verdict.type === 'unknown' &&\n !isReachabilitySafety(this._property) &&\n nuBounded;\n if (outcome !== null && !deferToRouteA) {\n report.push('=== ν-net Route B: name-aware state-class graph (NU-050) ===');\n report.push(` Name-partition state classes: ${outcome.classCount}`);\n report.push(outcome.note);\n if (outcome.transitions.length > 0) {\n report.push(` Counterexample trace: ${outcome.trace.length} states, ${outcome.transitions.length} transitions`);\n }\n return buildResult(\n outcome.verdict, report.join('\\n'), [], [], outcome.trace, outcome.transitions,\n performance.now() - start,\n {\n places: [...this.net.places].length,\n transitions: [...this.net.transitions].length,\n invariantsFound: 0,\n structuralResult: 'n/a (ν name-partition SCG)',\n },\n );\n } else if (deferToRouteA) {\n report.push(\n 'ν-net Route B inconclusive (name-partition truncated); deferring to ' +\n 'Route A coloured IC3/PDR (NU-053).',\n );\n }\n // EXTENDED was requested but the net is outside the coloured-consumer\n // fragment (classify declined). Surface a short note instead of a silent\n // cliff, then verify via the sound over-approximation below (NU-051, §5\n // diagnosability).\n if (this._fragmentMode === 'extended' && !deferToRouteA) {\n report.push(\n 'ν-net Route B (EXTENDED) declined: net outside coloured-consumer fragment ' +\n '(a coloured place consumed count != 1 or by multiple inputs, carries a ' +\n 'reset/read/inhibitor arc, or a join re-mints a coloured place); verified via ' +\n 'sound over-approximation instead.',\n );\n }\n }\n\n // Phase 1: Flatten\n report.push('Phase 1: Flattening net...');\n const flatNet = flatten(this.net, this._environmentPlaces, this._environmentMode);\n report.push(` Places: ${flatNet.places.length}`);\n report.push(` Transitions (expanded): ${flatNet.transitions.length}`);\n if (flatNet.environmentBounds.size > 0) {\n report.push(` Environment bounds: ${flatNet.environmentBounds.size} places`);\n }\n report.push('');\n\n // Phase 2: Structural pre-check\n report.push('Phase 2: Structural pre-check (siphon/trap)...');\n const structResult = structuralCheck(flatNet, this._initialMarking);\n let structResultStr: string;\n switch (structResult.type) {\n case 'no-potential-deadlock':\n structResultStr = 'no potential deadlock';\n break;\n case 'potential-deadlock':\n structResultStr = `potential deadlock (siphon: {${[...structResult.siphon].join(',')}})`;\n break;\n case 'inconclusive':\n structResultStr = `inconclusive (${structResult.reason})`;\n break;\n }\n report.push(` Result: ${structResultStr}\\n`);\n\n // If structural check proves deadlock-freedom for DeadlockFree property\n // (only valid when no sink places — structural check doesn't account for sinks).\n // Skipped when environment places are registered: the siphon/trap analysis runs\n // on the closed net and is blind to env injection (VER-006), so its early proof\n // could be unsound — fall through to the (injection-aware) SMT encoding instead.\n if (\n this._property.type === 'deadlock-free' &&\n !hasMatch &&\n this._sinkPlaces.size === 0 &&\n structResult.type === 'no-potential-deadlock' &&\n this._environmentPlaces.size === 0\n ) {\n report.push('=== RESULT ===\\n');\n report.push('PROVEN (structural): Deadlock-freedom verified by Commoner\\'s theorem.');\n report.push(' All siphons contain initially marked traps.');\n report.push(' Certificate check: not applicable (structural proof)');\n return buildResult(\n { type: 'proven', method: 'structural', inductiveInvariant: null },\n report.join('\\n'), [], [], [], [],\n performance.now() - start,\n { places: flatNet.places.length, transitions: flatNet.transitions.length, invariantsFound: 0, structuralResult: structResultStr },\n );\n }\n\n // Phase 3: P-invariants\n report.push('Phase 3: Computing P-invariants...');\n const matrix = IncidenceMatrix.from(flatNet);\n // Exact re-check (BigInt) before invariants reach the encoder: the Gaussian\n // elimination runs in f64 `number`, and a numerically wrong invariant conjoined\n // into the CHC transition bodies removes reachable successors — i.e. it could\n // certify a false PROVEN. Drop anything the exact re-verification rejects.\n const { valid: basisInvariants, dropped: droppedInvariants } = validateInvariantsExact(\n matrix,\n computePInvariants(matrix, flatNet, this._initialMarking),\n flatNet,\n this._initialMarking,\n );\n // P-semiflows (non-negative conservation laws) bound the simultaneously-live\n // colour count that sets the name-coloured encoder's slot count `k` (see\n // buildColouredPlan / colourSlotBound) — validated the same way (incl. the H1\n // linearity guard) before they can set that bound, mirroring the Rust verifier.\n const { valid: semiflows, dropped: droppedSemiflows } = validateInvariantsExact(\n matrix,\n computePSemiflows(matrix, flatNet, this._initialMarking),\n flatNet,\n this._initialMarking,\n );\n report.push(` Found: ${basisInvariants.length} P-invariant(s)`);\n // VER-007: the minimal conservation laws, as extra invariants for the encoders.\n // The report line is emitted only when enabled so default reports stay\n // byte-identical (AC2/AC3).\n let invariants: readonly PInvariant[] = basisInvariants;\n if (this._semiflowInvariants) {\n const { invariants: strengthened, added } = strengthenWithSemiflows(basisInvariants, semiflows);\n invariants = strengthened;\n report.push(` Semiflows encoded as invariants: ${added}`);\n }\n // VER-013: canonical invariant order (support, weights, constant), so the\n // strengthened rule bodies and the certificate candidate read the same in every\n // implementation whatever order the elimination produced them in.\n invariants = canonicalInvariantOrder(invariants);\n const structurallyBounded = isCoveredByInvariants(invariants, flatNet.places.length);\n report.push(` Structurally bounded: ${structurallyBounded ? 'YES' : 'NO'}`);\n for (const inv of invariants) {\n report.push(` ${formatInvariant(inv, flatNet)}`);\n }\n // Canonical cross-language wording: \" Dropped <kind>: <desc> - <reason>\",\n // ASCII hyphen-minus as the clause separator so the four implementations'\n // reports diff byte-for-byte. The structured {invariant, reason} pairs stay\n // on the result for callers that want more than the rendered line.\n for (const { invariant, reason } of droppedInvariants) {\n report.push(` Dropped invariant: ${formatInvariant(invariant, flatNet)} - ${reason}`);\n }\n if (droppedInvariants.length > 0) {\n report.push(` Dropped: ${droppedInvariants.length} invariant(s) failed the exact re-check`);\n }\n for (const { invariant, reason } of droppedSemiflows) {\n report.push(` Dropped semiflow: ${formatInvariant(invariant, flatNet)} - ${reason}`);\n }\n if (droppedSemiflows.length > 0) {\n report.push(` Dropped: ${droppedSemiflows.length} semiflow(s) failed the exact re-check`);\n }\n report.push('');\n\n // Phase 4: SMT encode + query via Spacer\n report.push('Phase 4: IC3/PDR verification via Z3 Spacer...');\n\n // ν-net exact refinement (NU-050 #1, Route A). For a budget-bounded ν-net in\n // the supported fragment, encode names as a finite colour set (k = the declared\n // budget) with exact same-colour join matching, instead of the name-blind\n // over-approximation — this rules out spurious counterexamples that would equate\n // two distinct names. Reachability-safety AND quiescence (NU-053) properties are\n // both routed here; a net outside the fragment keeps the flat encoding.\n const colouredPlan: ColouredPlan | null =\n hasMatch && nuBounded\n ? buildColouredPlan(\n this.net, flatNet, this._initialMarking, this._budgetPlaces,\n this._fragmentMode, this._carrierPlaces, semiflows,\n )\n : null;\n\n // VER-013: one z3 process per query. Resolve the executable before any encoding\n // work so a missing or too-old solver is reported as such.\n const stats: SmtStatistics = {\n places: flatNet.places.length,\n transitions: flatNet.transitions.length,\n invariantsFound: invariants.length,\n structuralResult: structResultStr,\n };\n let solver: Z3Solver;\n try {\n solver = resolveZ3();\n } catch (e: any) {\n const reason = e instanceof Z3Unavailable ? e.message : String(e?.message ?? e);\n report.push(` Solver: z3 unavailable (${reason})`);\n report.push(` Status: UNKNOWN (${reason})\\n`);\n report.push('=== RESULT ===\\n');\n report.push(`UNKNOWN: Could not determine ${propDesc}`);\n report.push(` Reason: ${reason}`);\n return buildResult({ type: 'unknown', reason }, report.join('\\n'), invariants, [], [], [], performance.now() - start, stats);\n }\n report.push(` Solver: z3 ${formatZ3Version(solver.version)}`);\n\n let encoding: SmtEncoding;\n if (colouredPlan != null) {\n report.push(\n ` ν-encoding: name-coloured (exact within budget k=${colouredPlan.k}; ` +\n `${colouredPlan.coloured.length} coloured place(s))`,\n );\n const coloured = encodeColoured(colouredPlan, flatNet, this._initialMarking, this._property, invariants, this._sinkPlaces);\n if (coloured == null) {\n // The property names a place that does not resolve in the net (e.g. a\n // typo'd bound/pending place). Emitting the encoding anyway would certify\n // a vacuous PROVEN; refuse and report Unknown so a mis-named place never\n // silently certifies.\n const reason =\n 'property names a place that does not resolve in the net; refusing to certify ' +\n '(the encoding would be vacuously proven)';\n report.push(' Status: UNKNOWN (unresolved property place)\\n');\n report.push('=== RESULT ===\\n');\n report.push(`UNKNOWN: ${reason}`);\n return buildResult({ type: 'unknown', reason }, report.join('\\n'), invariants, [], [], [], performance.now() - start, stats);\n }\n encoding = coloured;\n } else {\n // A property naming a place outside the net would encode to a vacuous\n // violation predicate (`false` proves anything). Refuse, as the coloured path\n // does, so a mis-named place never silently certifies.\n const unresolved = unresolvedPropertyPlace(flatNet, this._property);\n if (unresolved != null) {\n const reason =\n `property names a place that does not resolve in the net ('${unresolved}'); ` +\n 'refusing to certify (the encoding would be vacuously proven)';\n report.push(' Status: UNKNOWN (unresolved property place)\\n');\n report.push('=== RESULT ===\\n');\n report.push(`UNKNOWN: ${reason}`);\n return buildResult({ type: 'unknown', reason }, report.join('\\n'), invariants, [], [], [], performance.now() - start, stats);\n }\n // C3: request the refutation proof the replay decoder reads.\n encoding = encode(flatNet, this._initialMarking, this._property, invariants, this._sinkPlaces, this._counterexampleReplay);\n }\n const queryResult = await runZ3Spacer(\n solver, this._timeoutMs, encoding.smt2, colouredPlan != null ? 'horn-coloured' : 'horn',\n );\n\n switch (queryResult.type) {\n case 'proven': {\n // Guard against silent vacuous proofs (VER-006): in `ignore` mode the\n // encoding does not model env injection, so env-gated transitions never\n // fire and ANY safety bound is trivially \"proven\". Refuse to certify —\n // downgrade to UNKNOWN with actionable guidance.\n if (this._environmentPlaces.size > 0 && this._environmentMode.type === 'ignore') {\n const reason =\n 'environment places present but not modeled (mode=ignore); a proof would be ' +\n 'vacuous — use alwaysAvailable() or bounded(k) to model external injection';\n report.push(` Status: UNSAT, but vacuous under ignore mode\\n`);\n report.push('=== RESULT ===\\n');\n report.push(`UNKNOWN: ${reason}`);\n return buildResult({ type: 'unknown', reason }, report.join('\\n'), invariants, [], [], [], performance.now() - start, stats);\n }\n\n report.push(' Status: UNSAT (property holds)');\n\n // Independent certificate check (flat count encoding only): re-validate\n // the IC3 certificate in a second z3 run against the UNSTRENGTHENED step\n // relation, so neither a Spacer/encoder defect nor a wrong-but-\n // validated-looking invariant strengthening can certify a false PROVEN.\n // The coloured ν-encoding has its own state shape and is out of scope;\n // structural proofs return before this point.\n if (colouredPlan != null) {\n report.push(' Certificate check: not applicable (name-coloured encoding)');\n } else if (!this._certificateCheck) {\n report.push(' Certificate check: not applicable (disabled)');\n } else {\n const certificate = await checkCertificate(\n queryResult.invariantFormula, flatNet, this._initialMarking,\n this._property, invariants, this._sinkPlaces, solver, this._timeoutMs,\n );\n const reason = certificateDowngradeReason(certificate);\n if (reason != null) {\n report.push(' Certificate check: FAILED');\n if (certificate.type !== 'passed' && certificate.invariant != null) {\n report.push(' Uncertified invariant:');\n for (const line of certificate.invariant.split('\\n')) report.push(` ${line}`);\n }\n report.push('');\n report.push('=== RESULT ===\\n');\n report.push(`UNKNOWN: ${reason}`);\n return buildResult({ type: 'unknown', reason }, report.join('\\n'), invariants, [], [], [], performance.now() - start, stats);\n }\n report.push(' Certificate check: PASSED (init, consecution, safety)');\n }\n report.push('');\n\n // The inductive invariant is the (define-fun …) block of the model,\n // verbatim (the certificate the check above re-validated).\n const formula = queryResult.invariantFormula;\n const discoveredInvariants: string[] = formula != null ? [formula] : [];\n\n // Phase 5: Inductive invariant\n if (formula != null) {\n report.push('Phase 5: Inductive invariant (discovered by IC3)');\n report.push(' Spacer synthesized:');\n for (const line of formula.split('\\n')) report.push(` ${line}`);\n report.push(' This formula is INDUCTIVE: preserved by all transitions.');\n report.push('');\n }\n\n report.push('=== RESULT ===\\n');\n report.push(`PROVEN (IC3/PDR): ${propDesc}`);\n report.push(' Z3 Spacer proved no reachable state violates the property.');\n report.push(' NOTE: Verification ignores timing constraints.');\n report.push(' An untimed proof is STRONGER than a timed one (timing only restricts behavior).');\n\n return this.applyNuGuard(buildResult(\n { type: 'proven', method: 'IC3/PDR', inductiveInvariant: formula },\n report.join('\\n'), invariants, discoveredInvariants, [], [],\n performance.now() - start,\n stats,\n ), hasMatch, nuBounded, colouredPlan != null);\n }\n\n case 'violated': {\n report.push(' Status: SAT (counterexample found)\\n');\n\n const decoded = decode(queryResult.answer, flatNet);\n if (decoded.note != null) report.push(` Counterexample decoding: ${decoded.note}`);\n\n // C3/C4: abstract counterexample replay (flat count encoding only — the\n // coloured ν-encoding's state shape is outside the replayer's scope). The\n // decoder collects the ground Reachable states of the refutation proof as\n // an order-free set; the replay recovers a genuine firing order.\n let confirmed: boolean | null = null;\n let trace: readonly MarkingState[] = [...decoded.states];\n let transitions: readonly string[] = [];\n let replayed = false;\n if (colouredPlan == null && this._counterexampleReplay) {\n const assessment = assessCounterexample(\n flatNet, this._initialMarking, decoded.states, this._property, this._sinkPlaces,\n );\n if (assessment.kind === 'confirmed') {\n confirmed = true;\n replayed = true;\n trace = assessment.trace;\n transitions = assessment.firings;\n report.push(' Counterexample replay: CONFIRMED (abstract chain M0 -> bad re-executed)');\n } else if (assessment.kind === 'unconfirmed') {\n // The replay could not run to completion (nothing decoded, or the\n // search hit a budget). Spacer's answer stands on its own — only a\n // completed search that found no chain may withdraw it.\n confirmed = false;\n report.push(` Counterexample replay: UNCONFIRMED (${assessment.note})`);\n report.push(\" The verdict rests on Spacer's answer.\");\n } else {\n // The search completed and no abstract chain reaches a violating\n // marking: a spurious counterexample of the untimed+value-blind\n // over-approximation, or a decoder mismatch. Never keep an\n // unreplayable VIOLATED — downgrade, with raw + decoded evidence.\n report.push(' Counterexample replay: FAILED');\n report.push(` Decoded states (order-free set, ${decoded.states.size}):`);\n for (const m of decoded.states) report.push(` ${m}`);\n report.push(` Raw Z3 answer: ${truncate(queryResult.answer, 2000)}`);\n report.push('');\n report.push('=== RESULT ===\\n');\n report.push(`UNKNOWN: ${assessment.reason}`);\n // The replay APPLIED and refuted the trace, so `false` — not `null`,\n // which is reserved for \"the replay did not apply\".\n return buildResult(\n { type: 'unknown', reason: assessment.reason },\n report.join('\\n'), invariants, [], [], [],\n performance.now() - start,\n stats,\n false,\n );\n }\n }\n\n report.push('=== RESULT ===\\n');\n report.push(`VIOLATED: ${propDesc}`);\n if (trace.length > 0) {\n report.push(` Counterexample trace (${replayed ? 'replay order, ' : 'proof order, '}${trace.length} states):`);\n for (let i = 0; i < trace.length; i++) report.push(` ${i}: ${trace[i]}`);\n }\n if (transitions.length > 0) report.push(` Firing sequence: ${transitions.join(' -> ')}`);\n report.push('\\n WARNING: This counterexample is in UNTIMED semantics.');\n report.push(' It may be spurious if timing constraints prevent this sequence.');\n\n return this.applyNuGuard(buildResult(\n { type: 'violated' },\n report.join('\\n'), invariants, [], trace as MarkingState[], transitions as string[],\n performance.now() - start,\n stats,\n confirmed,\n ), hasMatch, nuBounded, colouredPlan != null);\n }\n\n case 'unknown': {\n report.push(` Status: UNKNOWN (${queryResult.reason})\\n`);\n report.push('=== RESULT ===\\n');\n report.push(`UNKNOWN: Could not determine ${propDesc}`);\n report.push(` Reason: ${queryResult.reason}`);\n return buildResult(\n { type: 'unknown', reason: queryResult.reason },\n report.join('\\n'), invariants, [], [], [],\n performance.now() - start,\n stats,\n );\n }\n }\n }\n\n /**\n * ν-net soundness guard (NU-040, NU-050). Applied only when the net contains\n * match (ν-join) transitions, and only to a proven/violated verdict (an\n * existing unknown is left as-is).\n *\n * - Quiescence-based properties (deadlock / joined-or-dead-lettered): the\n * name-blind over-approximation over-fires joins, so it sees fewer quiescent\n * states and may miss a real stranded marking — downgraded to unknown\n * (exact quiescence reasoning is deferred to the SCG name-partition quotient).\n * - Reachability-safety with unbounded fresh names (no budget declared):\n * reachability over unbounded fresh names is undecidable — unknown.\n * - Bounded reachability-safety in the name-coloured fragment (`exact`): name\n * equality is encoded exactly via bounded name-colouring, so the verdict is\n * sound *and* complete within the budget — no spurious different-name\n * counterexample. The verdict is kept and the exact-path note is appended.\n * - Bounded reachability-safety outside that fragment: `proven` is sound; a\n * `violated` may be spurious — the verdict is kept and the over-approximation\n * caveat is appended to the report.\n */\n private applyNuGuard(\n result: SmtVerificationResult,\n hasMatch: boolean,\n nuBounded: boolean,\n exact: boolean,\n ): SmtVerificationResult {\n if (!hasMatch || result.verdict.type === 'unknown') return result;\n // Exact path FIRST (NU-050 #1 / NU-053, Route A): name equality is encoded\n // exactly via bounded name-colouring, so the verdict is sound AND complete\n // within the budget bound — no spurious different-name counterexample. This\n // holds for reachability-safety AND quiescence (deadlock / joined-or-dead-\n // lettered), so an exact coloured plan keeps its verdict for quiescence too;\n // the colour-aware deadlock encoding does not over-fire joins.\n if (exact) {\n const note =\n '\\nNote: ν-join name equality is encoded exactly via bounded name-colouring ' +\n '(k = budget); the verdict is sound and complete within the budget bound — no spurious ' +\n 'different-name counterexample (NU-050 #1 / NU-053).\\n';\n return { ...result, report: result.report + note };\n }\n if (!isReachabilitySafety(this._property)) {\n return downgradeToUnknown(\n result,\n 'ν-matching transitions present and the property depends on quiescence ' +\n '(deadlock / joined-or-dead-lettered); the name-blind over-approximation cannot ' +\n 'decide it soundly — deferred to the exact ν-analysis (NU-050)',\n );\n }\n if (!nuBounded) {\n return downgradeToUnknown(\n result,\n 'ν-matching transitions present with unbounded fresh names (no budget place declared ' +\n 'via budgetPlaces(...)); reachability over unbounded fresh names is undecidable ' +\n '(NU-040) — declare the budget place(s) that gate minting to verify within the ' +\n 'bounded fragment',\n );\n }\n // Bounded reachability-safety outside the name-coloured fragment: the matched\n // transitions are over-approximated, so a violated may be spurious.\n const note =\n \"\\nNote: matched (ν-join) transitions are over-approximated (name equality assumed \" +\n \"satisfiable). 'proven' is sound; a 'violated' counterexample may be spurious pending \" +\n 'the exact ν-analysis (NU-050).\\n';\n return { ...result, report: result.report + note };\n }\n}\n\n/**\n * Whether a property is a reachability-safety property — one whose violation is\n * a reachable bad marking. For these the matched-transition over-approximation\n * is sound for `proven`. Quiescence-based properties (deadlock,\n * joined-or-dead-lettered) are not: their violation involves the absence of\n * enabled transitions, which the name-blind over-approximation distorts (NU-050).\n */\nfunction isReachabilitySafety(property: SmtProperty): boolean {\n switch (property.type) {\n case 'place-bound':\n case 'branch-place-bound':\n case 'mutual-exclusion':\n case 'unreachable':\n return true;\n case 'deadlock-free':\n case 'joined-or-dead-lettered':\n return false;\n }\n}\n\n/**\n * Assessment of a decoded counterexample by abstract replay (C4). Pure and free\n * of Z3 types, so the verdict mapping is unit-testable without booting the WASM\n * solver — the mirror of {@link certificateDowngradeReason}.\n */\nexport type ReplayAssessment =\n /** The decoded states chain into an abstract run reaching the violation. */\n | {\n readonly kind: 'confirmed';\n readonly trace: readonly MarkingState[];\n readonly firings: readonly string[];\n }\n /** The replay could not complete; the VIOLATED verdict stands, unconfirmed. */\n | { readonly kind: 'unconfirmed'; readonly note: string }\n /** No firing chain exists at all; the verdict must not be trusted. */\n | { readonly kind: 'downgraded'; readonly reason: string };\n\n/**\n * Maps a decoded counterexample to its replay assessment. Only a completed\n * search that found no chain (`no-chain`) downgrades: nothing decoded, a\n * truncated search (node/segment budget, `M₀` absent from the decoded set) and\n * a replayer crash all leave the verdict `violated` but unconfirmed, because\n * none of them is evidence that the counterexample is spurious.\n */\nexport function assessCounterexample(\n flatNet: FlatNet,\n initialMarking: MarkingState,\n decodedStates: ReadonlySet<MarkingState>,\n property: SmtProperty,\n sinkPlaces: ReadonlySet<Place<any>>,\n): ReplayAssessment {\n if (decodedStates.size === 0) {\n return {\n kind: 'unconfirmed',\n note: 'no counterexample states could be decoded from the Spacer answer, ' +\n 'so the abstract replay could not run',\n };\n }\n\n let outcome: ReplayOutcome;\n try {\n outcome = replayCounterexample(\n flatNet,\n vectorize(initialMarking, flatNet),\n [...decodedStates].map(m => vectorize(m, flatNet)),\n property,\n sinkPlaces,\n );\n } catch (e: any) {\n // A replayer bug must degrade like a truncated search — never crash the\n // verifier, and never withdraw a verdict on its own.\n outcome = { kind: 'exhausted', reason: `replay threw: ${e?.message ?? e}`, nodesExplored: 0 };\n }\n\n switch (outcome.kind) {\n case 'confirmed':\n return {\n kind: 'confirmed',\n trace: outcome.states.map(s => toMarkingState(s, flatNet)),\n firings: outcome.steps.map(stepName),\n };\n case 'exhausted':\n return { kind: 'unconfirmed', note: `abstract replay did not complete: ${outcome.reason}` };\n case 'no-chain':\n return {\n kind: 'downgraded',\n reason: 'counterexample replay found no firing chain to the violation under ' +\n 'the abstract semantics, so VIOLATED is withheld',\n };\n }\n}\n\n/**\n * Maps a certificate-check outcome to the UNKNOWN downgrade reason, or null\n * when the PROVEN verdict stands. Pure (no Z3 involvement) so the verdict\n * plumbing is unit-testable without booting the WASM solver.\n */\nexport function certificateDowngradeReason(outcome: CertificateCheckOutcome): string | null {\n switch (outcome.type) {\n case 'passed':\n return null;\n case 'failed':\n return `certificate check failed: ${outcome.vc} was not UNSAT - ${outcome.detail}; ` +\n 'the IC3 certificate could not be independently re-validated against the ' +\n 'unstrengthened step relation, so PROVEN is withheld';\n case 'unavailable':\n return `certificate check could not run: ${outcome.reason}; ` +\n 'PROVEN is withheld without an independently validated certificate';\n }\n}\n\n/** The scripts {@link SmtVerifier.encodeScripts} reports. */\nexport interface EncodedScripts {\n /** The HORN query, flat or name-coloured. */\n readonly horn: string;\n /** The certificate-check script around {@link placeholderCertificate}; `null` for the name-coloured encoding. */\n readonly certificate: string | null;\n /** Whether `horn` is the name-coloured encoding. */\n readonly coloured: boolean;\n}\n\n/**\n * `(define-fun Reachable ((x!0 Int) …) Bool true)`: the certificate stand-in the\n * golden certificate scripts are built around (a real certificate is solver output\n * and never part of a golden).\n */\nexport function placeholderCertificate(placeCount: number): string {\n const params: string[] = [];\n for (let i = 0; i < placeCount; i++) params.push(`(x!${i} Int)`);\n return `(define-fun Reachable (${params.join(' ')}) Bool\\n true)`;\n}\n\nfunction downgradeToUnknown(result: SmtVerificationResult, reason: string): SmtVerificationResult {\n return {\n ...result,\n verdict: { type: 'unknown', reason },\n report: result.report + `\\nDowngraded to UNKNOWN: ${reason}\\n`,\n discoveredInvariants: [],\n counterexampleTrace: [],\n counterexampleTransitions: [],\n counterexampleConfirmed: null,\n };\n}\n\n/** Truncates long raw solver output for the report. */\nfunction truncate(s: string, max: number): string {\n return s.length <= max ? s : `${s.slice(0, max)}… (${s.length - max} chars truncated)`;\n}\n\n/** The name of the first place the property names that is not in the flat net, or `null`. */\nfunction unresolvedPropertyPlace(flatNet: FlatNet, property: SmtProperty): string | null {\n const named: Place<any>[] = (() => {\n switch (property.type) {\n case 'deadlock-free': return [];\n case 'mutual-exclusion': return [property.p1, property.p2];\n case 'place-bound': return [property.place];\n case 'branch-place-bound': return [property.place];\n case 'unreachable': return [...property.places];\n case 'joined-or-dead-lettered': return [property.pending];\n }\n })();\n for (const place of named) {\n if (!flatNet.placeIndex.has(place.name)) return place.name;\n }\n return null;\n}\n\nfunction formatInvariant(inv: PInvariant, flatNet: FlatNet): string {\n const parts: string[] = [];\n for (const idx of inv.support) {\n if (inv.weights[idx] !== 1) {\n parts.push(`${inv.weights[idx]}*${flatNet.places[idx]!.name}`);\n } else {\n parts.push(flatNet.places[idx]!.name);\n }\n }\n // Empty support renders as `0 = c`, matching Java and Rust — the line is byte-diffed.\n return `${parts.length === 0 ? '0' : parts.join(' + ')} = ${inv.constant}`;\n}\n\nfunction buildResult(\n verdict: Verdict,\n report: string,\n invariants: readonly PInvariant[],\n discoveredInvariants: readonly string[],\n trace: readonly MarkingState[],\n transitions: readonly string[],\n elapsedMs: number,\n statistics: SmtStatistics,\n counterexampleConfirmed: boolean | null = null,\n): SmtVerificationResult {\n return { verdict, report, invariants, discoveredInvariants, counterexampleTrace: trace, counterexampleTransitions: transitions, counterexampleConfirmed, elapsedMs, statistics };\n}\n","import type { MarkingState } from './marking-state.js';\nimport type { PInvariant } from './invariant/p-invariant.js';\n\n/**\n * Verification verdict.\n */\nexport type Verdict = Proven | Violated | Unknown;\n\n/** Property proven safe. No reachable state violates it. */\nexport interface Proven {\n readonly type: 'proven';\n readonly method: string;\n readonly inductiveInvariant: string | null;\n}\n\n/** Property violated. A counterexample trace is available. */\nexport interface Violated {\n readonly type: 'violated';\n}\n\n/** Could not determine. */\nexport interface Unknown {\n readonly type: 'unknown';\n readonly reason: string;\n}\n\n/**\n * Solver statistics.\n */\nexport interface SmtStatistics {\n readonly places: number;\n readonly transitions: number;\n readonly invariantsFound: number;\n readonly structuralResult: string;\n}\n\n/**\n * Result of SMT-based verification.\n */\nexport interface SmtVerificationResult {\n readonly verdict: Verdict;\n readonly report: string;\n readonly invariants: readonly PInvariant[];\n readonly discoveredInvariants: readonly string[];\n readonly counterexampleTrace: readonly MarkingState[];\n readonly counterexampleTransitions: readonly string[];\n /**\n * Outcome of the abstract counterexample replay, as a TRI-STATE. `null` means\n * \"the replay did not apply\"; the two booleans both mean it ran.\n *\n * - `true` — an abstract firing chain from M₀ to a property-violating state\n * was re-executed TS-side; `counterexampleTrace` is that chain in FIRING\n * (replay) order and the verdict is `violated`.\n * - `false` — the replay ran without confirming the trace. Either it could not\n * settle the question (nothing decoded from the Z3 derivation, M₀ absent\n * from the decoded set, or a node/segment budget hit), in which case the\n * `violated` verdict rests on Spacer's SAT answer alone; or the search\n * completed and found NO chain, in which case the verdict was downgraded to\n * `unknown`. The report distinguishes the two (\"UNCONFIRMED\" vs \"FAILED\").\n * - `null` — replay did not apply: non-violated verdict, replay disabled via\n * `counterexampleReplay(false)`, the coloured ν-encoding / Route B (whose\n * state shapes are outside the flat replayer's scope), or a structural\n * proof.\n */\n readonly counterexampleConfirmed: boolean | null;\n readonly elapsedMs: number;\n readonly statistics: SmtStatistics;\n}\n\nexport function isProven(result: SmtVerificationResult): boolean {\n return result.verdict.type === 'proven';\n}\n\nexport function isViolated(result: SmtVerificationResult): boolean {\n return result.verdict.type === 'violated';\n}\n"],"mappings":"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","names":["timeoutPlace","candidate","script","quantified","placeName","all","placeName","inputRequiredCount","note"]}