Skip to content

Commit b6d80bc

Browse files
cukasKERN-Agon
andauthored
Feat/kern 5 r1 kir v1 parity (#514)
* feat(runtime): add internal transactional envelope ⚔️ Forged by [Agon](https://github.com/KERNlang/agon) Co-Authored-By: agon (KERN) <292465531+KERN-Agon@users.noreply.github.com> * feat(runtime): add typed internal handler entry ⚔️ Forged by [Agon](https://github.com/KERNlang/agon) Co-Authored-By: agon (KERN) <292465531+KERN-Agon@users.noreply.github.com> * feat(runtime): link internal source handlers ⚔️ Forged by [Agon](https://github.com/KERNlang/agon) Co-Authored-By: agon (KERN) <292465531+KERN-Agon@users.noreply.github.com> --------- Co-authored-by: agon (KERN) <292465531+KERN-Agon@users.noreply.github.com>
1 parent 5bb0f47 commit b6d80bc

18 files changed

Lines changed: 1911 additions & 1 deletion

File tree

Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
# KERN 5 R2/M3.2 Internal Typed Handler Entry
2+
3+
## Status
4+
5+
Implementation contract for the second M3 slice. The entry is internal,
6+
default-off, and does not promote the public runtime/handler ABI. **DECIDED**
7+
8+
## Baseline and Decision
9+
10+
- M3.1 is remotely verified at `30c733aa`. **VERIFIED**
11+
- M3.1 supplies a closed transactional envelope but accepts prebuilt IR and an
12+
already-populated semantic environment. **VERIFIED**
13+
- Agon tribunal `tribunal-1783872910960-gb74q8-kern5-m3-2-next-slice`
14+
selected typed internal handler entry before scheduler or runner-contract
15+
promotion. **VERIFIED**
16+
- The current ReferenceRunner executable argument domain is narrower than the
17+
envelope value domain: Decimal values and recursively nested records are not
18+
general runner-portable values. **VERIFIED**
19+
20+
## Entry Contract
21+
22+
An entry contains an ordered, duplicate-free parameter-name list and IR handler
23+
body. A request supplies an exact-arity ordered argument list. Names must be
24+
portable KERN bindings. Argument count is bounded by `maxCollectionLength`.
25+
**DECIDED**
26+
27+
Arguments normalize completely before environment construction or runner
28+
registration. The admitted M3.2 domain is null, boolean, text, safe integer,
29+
nested lists of admitted non-record values, and flat records whose fields are
30+
admitted scalars or lists. Decimal values and nested records reject before
31+
execution until the ReferenceRunner owns those handler semantics. **GUARD**
32+
33+
The entry constructs a fresh root binding map containing only normalized
34+
arguments. Host capabilities and deterministic seed/time may be inherited from
35+
the supplied host environment. Host bindings, function registries, class
36+
registries, and call-frame state never cross the entry boundary. **GUARD**
37+
38+
## Failure and Containment
39+
40+
Invalid names, arity, hostile arrays/values (including Proxy containers),
41+
unsupported admitted-shape combinations, and resource overflow yield a transactional
42+
`invalid-handler-arguments` failure envelope. No handler node, capability,
43+
event, or result executes first. M3.1 execution failures retain their existing
44+
stable identities. **DECIDED**
45+
46+
Proxy reflection traps are host-language admission effects and may run while
47+
the boundary proves that a raw JavaScript container is invalid. They are not
48+
KERN handler or capability effects and are outside this transactional guarantee.
49+
Callers that require side-effect-free hostile-byte admission must decode and
50+
materialize trusted plain data before invoking this internal entry. **GUARD**
51+
52+
Sync and async entrypoints feed the same validated arguments into the existing
53+
M3.1 execution lanes and must encode byte-identically for immediately-resolved
54+
behavior. Existing public source executors and package exports remain
55+
unchanged. **GUARD**
56+
57+
## Acceptance
58+
59+
- [x] Default-off, exact arity, portable names, duplicates, and fresh bindings
60+
are enforced.
61+
- [x] Null, boolean, text, safe integer, list, flat record, and void/result
62+
paths round-trip through sync and async entries.
63+
- [x] Decimal, nested record, accessor, symbol, cycle/shared-reference, unsafe
64+
numeric, and overflow arguments reject before execution.
65+
- [x] Invalid arguments cannot invoke a capability or expose events/result.
66+
- [x] Public containment and the planned `runtime-handler-abi` gate remain.
67+
- [x] Full KERN 5 fitness wall remains green.
68+
- [x] Final Agon review with `claude,codex,agy` has zero verified findings.
69+
70+
## Deferred
71+
72+
Source-level handler identity and linking, Decimal and nested-record handler
73+
arguments, effect scheduling, cancellation, true host-effect rollback, stable
74+
public ABI, KIR v1 freeze, and all 16 runner-contract promotions. **DEFERRED**
75+
76+
## Kill Switches
77+
78+
- Any invalid argument reaches runner registration or capability execution.
79+
- Any host binding becomes visible to the handler.
80+
- Any failed request contains events or a result.
81+
- Any unsupported value is coerced, stringified, or silently dropped.
82+
- Any public executor, barrel, or package export adopts the internal entry.
Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
# KERN 5 R2/M3.1 Internal Transactional Runtime Envelope
2+
3+
## Status
4+
5+
Implementation contract for the first M3 slice. The envelope is internal,
6+
default-off, and does not freeze the runtime, handler, trace, or capability
7+
ABI. **DECIDED**
8+
9+
## Baseline and Decision
10+
11+
- Alpha KIR/evidence/receipt is remotely verified at `7099c95d`. **VERIFIED**
12+
- Sixteen runner constructs plus trace, handler, and capability ABIs remain
13+
explicitly deferred to M3. **VERIFIED**
14+
- Public `executeKernSource*` wrappers return stdout strings; sync and async
15+
execution still use separate evaluators. **VERIFIED**
16+
- Agon tribunal `tribunal-1783864102213-mjaw2b-kern5-m3-first-slice`
17+
completed 3/3 and selected transactional envelope normalization before typed
18+
arguments or scheduler unification. **VERIFIED**
19+
20+
## Envelope Contract
21+
22+
Format is `kern.runtime.internal.r0`. The exact envelope contains `format`,
23+
`outcome`, `completion`, `result`, `events`, and `diagnostics`. All fields are
24+
always present and canonical JSON encoding ends in one LF. **DECIDED**
25+
26+
- Success completion is `normal | return`; `result` is an explicit slot so
27+
absent/void and explicit null cannot collapse.
28+
- Failure completion is `error`, result is absent, and events are empty.
29+
- Diagnostics contain stable `category`, `code`, and `phase` only. Host error
30+
messages are not identity and do not enter envelope bytes.
31+
- Observable events are only `stdout`, `stderr`, and `capability`. Assignment,
32+
call, iteration, enter, and exit events remain internal trace mechanics.
33+
**GUARD**
34+
35+
## Portable Value Contract
36+
37+
Values are closed tagged forms: null, boolean, text, safe integer text,
38+
canonical decimal text, list, and code-point-sorted record entries. Undefined
39+
is represented only by an absent slot. Functions, symbols, bigint, negative
40+
zero, NaN/infinity, unsafe integers, exponent-form numbers, RegExp, Date, Map,
41+
Set, class instances, sparse arrays, forbidden record keys, cycles, malformed
42+
Unicode, and configured resource overflow reject. **GUARD**
43+
44+
Limits are required caller configuration: maximum depth, collection length,
45+
string UTF-8 bytes, events, diagnostics, and encoded bytes. **DECIDED**
46+
47+
## Execution and Containment
48+
49+
Sync and async internal entrypoints require `enabled: true`; omission or false
50+
rejects before execution. Both run the current semantic lanes and then pass
51+
through the same normalizer. Existing source executors and public exports are
52+
unchanged. The module is unreachable from runtime/browser/public barrels and
53+
package exports. **GUARD**
54+
55+
Transactional means the new envelope exposes no partial result, diagnostic,
56+
or event after execution failure. It does not claim rollback of a host
57+
capability effect that already occurred inside the current evaluators; that
58+
requires the unified effect scheduler slice. **DECIDED**
59+
60+
## Acceptance
61+
62+
- [x] Success, explicit null, void, stdout, and capability events normalize.
63+
- [x] Sync and immediately-resolved async execution encode byte-identically.
64+
- [x] Failure after stdout or attempted return yields empty events and absent
65+
result with stable diagnostic identity.
66+
- [x] Hostile values and every configured resource overflow reject or become a
67+
transactional `non-portable-value` failure without partial output.
68+
- [x] Default-off and internal containment kill public/runtime adoption.
69+
- [x] Existing R1 gates and full KERN 5 fitness wall remain green.
70+
- [x] Final Agon review with exactly `claude,codex,agy` has zero verified
71+
findings.
72+
73+
## Deferred
74+
75+
Typed handler arguments/results at the source entry boundary, unified effect
76+
scheduler, cancellation, actual effect rollback, stable public ABI, all 16
77+
runner-contract promotions, KIR v1 freeze, and runtime cutover. **DEFERRED**
78+
79+
## Kill Switches
80+
81+
- Any existing public executor changes behavior or return type.
82+
- Any failed envelope contains result or events.
83+
- Any host message becomes diagnostic identity.
84+
- Any unknown/non-portable value falls back or stringifies.
85+
- Any internal envelope becomes publicly exported or default-on.
Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
# KERN 5 R2/M3.3 Internal Source Handler Link
2+
3+
## Status
4+
5+
Implementation contract for the third M3 slice. Source identity and linking
6+
remain internal and default-off; no public runner, handler, or capability ABI is
7+
promoted. **DECIDED**
8+
9+
## Baseline and Decision
10+
11+
- M3.2 is remotely verified at `9911ae31`. **VERIFIED**
12+
- M3.2 executes a supplied typed handler entry but does not establish which
13+
source declaration owns that entry. **VERIFIED**
14+
- Agon tribunal `tribunal-1783882531919-g0x67v-kern5-m3-3-next-slice`
15+
selected bounded source handler identity/linking before an effect scheduler or
16+
runner-contract promotion. **VERIFIED**
17+
- Current capability dispatch has no internal pre-call interception seam; a
18+
scheduler now would modify the production runner path and overclaim this
19+
contained slice. **VERIFIED**
20+
21+
## Identity and Link Contract
22+
23+
An identity is exactly one canonical `sourcePath` and one portable
24+
`handlerName`. The supplied source is one bounded KERN document. Resolution
25+
selects exactly one top-level `fn` whose `name` equals `handlerName`, exactly one
26+
direct child `handler lang="kern"`, and the current runner-portable exact-name
27+
parameter subset. **DECIDED**
28+
29+
The resolver accepts either legacy `params=` syntax or direct `param` children,
30+
never both. Default, optional, variadic, destructured, duplicate, non-portable,
31+
or otherwise unsupported parameter forms reject. Async and stream functions,
32+
foreign/empty/multiple KERN handlers, parse errors, and schema-invalid source
33+
reject before handler execution. **GUARD**
34+
35+
Source and identity strings are bounded by the existing runtime envelope limits.
36+
Default-off validation happens before source parsing. The resolved body and
37+
ordered parameter names feed only the existing M3.2 sync/async typed entry.
38+
**GUARD**
39+
40+
## Failure and Containment
41+
42+
Link failures use closed internal diagnostics with phase `link`:
43+
`handler-entry-not-found`, `handler-entry-ambiguous`,
44+
`handler-entry-unsupported`, and `handler-link-error`. Every link failure has an
45+
error completion, no events, no result, and invokes no handler or capability.
46+
**DECIDED**
47+
48+
The public source executors, package exports, runner capability dispatch, module
49+
loader, and KIR reader remain unchanged. **GUARD**
50+
51+
## Acceptance
52+
53+
- [x] Default-off and bounded source/identity validation happen before parsing.
54+
- [x] One valid source handler links ordered parameters and executes through
55+
both M3.2 lanes with byte-identical immediately-resolved behavior.
56+
- [x] Missing, duplicate, foreign, multiple-handler, async/stream, malformed,
57+
schema-invalid, and unsupported-parameter sources fail with stable link
58+
diagnostics.
59+
- [x] Link failure cannot invoke a capability or expose events/result.
60+
- [x] Public containment and the planned `runtime-handler-abi` gate remain.
61+
- [ ] Full KERN 5 fitness wall remains green.
62+
- [ ] Final Agon review with `claude,codex,agy` has zero verified findings.
63+
64+
## Deferred
65+
66+
Module loading, import/export and re-export resolution, helper/class registry
67+
linking, overloads, Decimal and nested-record arguments, effect scheduling,
68+
cancellation, host-effect rollback, stable public ABI, KIR v1 freeze, and all 16
69+
runner-contract promotions. **DEFERRED**
70+
71+
## Kill Switches
72+
73+
- Any disabled request parses source.
74+
- Any ambiguous or invalid source executes a handler or capability.
75+
- Any link failure contains events or a result.
76+
- Any module, import, export, helper, or class is linked implicitly.
77+
- Any public executor, barrel, package export, or capability dispatcher adopts
78+
the internal source link.

docs/kern-5-release-train.md

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -200,6 +200,22 @@ trusted-publishing/provenance configuration is inspected.
200200
gate: policy-bound hashes/oracles/exclusions, dirty-tree and symlink kill
201201
tests, full fitness wall, and final 3/3 Agon review passed on 2026-07-12.
202202
The SHA-named ignored receipt is generated only after commit.
203+
- [ ] R2 M3 runtime and handler ownership.
204+
- [x] M3.1 internal transactional runtime envelope: default-off sync/async
205+
normalization with closed portable values, structural diagnostics, failure
206+
suppression, and containment from every public export. This deliberately
207+
leaves the public runtime/handler ABI and effect scheduler unpromoted. The
208+
full fitness wall and final 3/3 Agon review passed on 2026-07-12.
209+
- [x] M3.2 internal typed handler entry: exact-arity portable parameters feed
210+
fresh sync/async runtime environments, with invalid or currently
211+
non-executable argument shapes rejected before handler execution. Decimal,
212+
nested-record, source-linking, scheduler, and public-ABI work remain
213+
explicitly deferred. The full fitness wall and terminal 3/3 Agon review
214+
passed with zero verified findings on 2026-07-12.
215+
- [ ] M3.3 internal source handler identity/link: one bounded source document
216+
resolves a canonical source path and exact top-level KERN handler into the
217+
M3.2 typed entry. Modules, helper/class linking, scheduler, runner-contract,
218+
and public-ABI work remain explicitly deferred.
203219

204220
1. Correct the support matrix and make `fitness:kern-5` the planned aggregate,
205221
without pretending missing commands already exist.

docs/kern-5-support-matrix.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@ before partial output, result, diagnostic, or implicit host effect escapes.
4242
| kir-coverage-closure | Structural KIR coverage witness closure | current | `pnpm test:kern-kir-coverage-closure` |
4343
| kir-evidence | Diagnostic and UTF-8 location evidence | current | `pnpm test:kern-kir-evidence` |
4444
| kir-alpha-receipt | Clean-HEAD immutable Alpha receipt | current | `pnpm test:kern-alpha-receipt` |
45+
| internal-runtime-envelope | Internal runtime envelope, handler entry, and source link | current | `pnpm test:kern-runtime-envelope` |
4546
| diff-hygiene | Git diff hygiene | current | `git diff --check` |
4647
| kir-v1 | Versioned canonical KIR | planned | `pnpm test:kern-ir` |
4748
| runtime-handler-abi | Runtime and handler ABI | planned | `pnpm test:runtime-abi` |
@@ -79,6 +80,9 @@ wall and must remain absent until promoted.
7980
| kir-coverage-closure | Structural KIR coverage witness closure | internal-oracle | `pnpm test:kern-kir-coverage-closure` |
8081
| kir-evidence | Diagnostic and UTF-8 location evidence | internal-oracle | `pnpm test:kern-kir-evidence` |
8182
| kir-alpha-receipt | Clean-HEAD immutable Alpha receipt | internal-oracle | `pnpm test:kern-alpha-receipt` |
83+
| internal-runtime-envelope | Default-off transactional runtime envelope | internal-oracle | `pnpm test:kern-runtime-envelope` |
84+
| internal-runtime-handler-entry | Typed current-domain handler entry | internal-oracle | `pnpm test:kern-runtime-envelope` |
85+
| internal-runtime-source-handler-link | Bounded source handler identity and link | internal-oracle | `pnpm test:kern-runtime-envelope` |
8286
| versioned-kir-v1 | Versioned canonical KIR v1 | not-shipped | R1 planned |
8387
| typed-runtime-handler-abi | Typed runtime and handler ABI | not-shipped | R2 M3 planned |
8488
| kern-formatter | KERN formatter or canonicalizer | not-shipped | R2 planned |

package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,8 +49,9 @@
4949
"test:kern-kir-coverage-closure": "pnpm --filter @kernlang/core build && node --test scripts/kir-v1/coverage-ledger.test.mjs && node ./scripts/check-kir-coverage-closure.mjs",
5050
"test:kern-kir-evidence": "pnpm --filter @kernlang/core test --testPathPatterns=kir-evidence && node ./scripts/check-kir-evidence.mjs",
5151
"test:kern-alpha-receipt": "node --test scripts/kir-v1/alpha-receipt.test.mjs",
52+
"test:kern-runtime-envelope": "pnpm --filter @kernlang/core test --testPathPatterns=runtime-envelope && node ./scripts/check-runtime-envelope.mjs",
5253
"build:kern-alpha-receipt": "node ./scripts/kir-v1/alpha-receipt.mjs",
53-
"test:infra": "pnpm test:prepush && pnpm test:release-policy && pnpm test:kern-5-fitness && pnpm test:kern-semantic-ownership && pnpm test:kern-ir-eligibility && pnpm test:kern-canonical-value && pnpm test:kern-kir-structural-constitution && pnpm test:kern-kir-structural-codec && pnpm test:kern-kir-module-graph && pnpm test:kern-kir-coverage-closure && pnpm test:kern-kir-evidence && pnpm test:kern-alpha-receipt",
54+
"test:infra": "pnpm test:prepush && pnpm test:release-policy && pnpm test:kern-5-fitness && pnpm test:kern-semantic-ownership && pnpm test:kern-ir-eligibility && pnpm test:kern-canonical-value && pnpm test:kern-kir-structural-constitution && pnpm test:kern-kir-structural-codec && pnpm test:kern-kir-module-graph && pnpm test:kern-kir-coverage-closure && pnpm test:kern-kir-evidence && pnpm test:kern-alpha-receipt && pnpm test:kern-runtime-envelope",
5455
"fitness": "pnpm fitness:kern-5",
5556
"fitness:kern-5": "node ./scripts/kern-5-fitness.mjs",
5657
"check:kern-5-contract": "node ./scripts/kern-5-fitness.mjs --check",
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
import { type AsyncReferenceRunnerOptions, asyncReferenceRunSequence } from '../ir/semantics/async-reference-runner.js';
2+
import type { SemanticEnv } from '../ir/semantics/index.js';
3+
import { referenceRunSequence } from '../ir/semantics/reference-runner.js';
4+
import { registerAllContracts } from '../ir/semantics/register-all.js';
5+
import type { IRNode } from '../types.js';
6+
import { normalizeInternalRuntimeFailure, normalizeInternalRuntimeTrace } from './normalize.js';
7+
import {
8+
type InternalRuntimeEnvelope,
9+
InternalRuntimeEnvelopeError,
10+
type InternalRuntimeEnvelopeOptions,
11+
} from './types.js';
12+
import { validateInternalRuntimeLimits } from './value.js';
13+
14+
function enabled(options: InternalRuntimeEnvelopeOptions | undefined): InternalRuntimeEnvelopeOptions {
15+
if (options?.enabled !== true) {
16+
throw new InternalRuntimeEnvelopeError('disabled', 'internal runtime envelope is default-off');
17+
}
18+
validateInternalRuntimeLimits(options.limits);
19+
return options;
20+
}
21+
22+
export function executeInternalRuntimeEnvelopeSync(
23+
nodes: readonly IRNode[],
24+
env: SemanticEnv,
25+
options?: InternalRuntimeEnvelopeOptions,
26+
): InternalRuntimeEnvelope {
27+
const accepted = enabled(options);
28+
try {
29+
registerAllContracts();
30+
return normalizeInternalRuntimeTrace(referenceRunSequence(nodes, env), accepted.limits);
31+
} catch (error) {
32+
return normalizeInternalRuntimeFailure(error);
33+
}
34+
}
35+
36+
export async function executeInternalRuntimeEnvelopeAsync(
37+
nodes: readonly IRNode[],
38+
env: SemanticEnv,
39+
options: InternalRuntimeEnvelopeOptions | undefined,
40+
asyncOptions: AsyncReferenceRunnerOptions = {},
41+
): Promise<InternalRuntimeEnvelope> {
42+
const accepted = enabled(options);
43+
try {
44+
registerAllContracts();
45+
return normalizeInternalRuntimeTrace(await asyncReferenceRunSequence(nodes, env, asyncOptions), accepted.limits);
46+
} catch (error) {
47+
return normalizeInternalRuntimeFailure(error);
48+
}
49+
}

0 commit comments

Comments
 (0)