@fraczak/k 6.0.3 → 6.1.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.
- package/AGENTS.md +2 -2
- package/CHANGELOG.md +22 -5
- package/CLAUDE.md +4 -4
- package/DOCS/BIG_PICTURE.md +5 -5
- package/DOCS/BINARY_CODEC_STATUS_AND_TODO.md +3 -3
- package/DOCS/KIR_SPECIALIZATION_DESIGN.md +458 -0
- package/DOCS/OBJECT_FILE_AND_PATTERN.md +135 -49
- package/DOCS/PATTERNS.md +6 -5
- package/DOCS/REPL.md +8 -6
- package/DOCS/book/06-values-in-memory.md +1 -1
- package/DOCS/book.md +20 -24
- package/README.md +200 -268
- package/codecs/README.md +21 -2
- package/codecs/example-pipeline.mjs +14 -0
- package/codecs/ieee.mjs +13 -3
- package/codecs/int.mjs +13 -3
- package/codecs/json.mjs +13 -3
- package/codecs/k-parse.mjs +5 -0
- package/codecs/k-print.mjs +16 -1
- package/codecs/show.mjs +15 -1
- package/codecs/unit.mjs +13 -3
- package/codecs/utf16.mjs +13 -3
- package/codecs/utf8.mjs +13 -3
- package/core.json +1 -0
- package/core.klib +0 -0
- package/export.mjs +1 -1
- package/ieee.klib +0 -0
- package/index.mjs +1 -1
- package/k-vscode/README.md +3 -2
- package/k.mjs +9 -1
- package/object.mjs +303 -62
- package/objects/README.md +29 -9
- package/objects/compile-lib.mjs +3 -2
- package/objects/compile.mjs +1 -0
- package/objects/decompile.mjs +1 -1
- package/objects/extract-aliases.mjs +1 -1
- package/p.json +5475 -0
- package/package.json +13 -7
- package/{repl2.mjs → repl.mjs} +45 -11
- package/run.mjs +172 -2
- package/test-k-object.mjs +58 -7
- package/{test-repl2.mjs → test-repl.mjs} +4 -4
package/AGENTS.md
CHANGED
|
@@ -11,8 +11,8 @@
|
|
|
11
11
|
- `npm install` installs dev dependencies and runs `prepare` to generate parsers.
|
|
12
12
|
- `npm run prepare` regenerates `parser.mjs` and `valueParser.mjs` from `.jison` grammars.
|
|
13
13
|
- `npm test` runs the full suite (`test.mjs`, `Code-derivation-tests/*.mjs`, `test-fingerprint.mjs`, `tests.sh`).
|
|
14
|
-
- `node
|
|
15
|
-
- `./k.mjs <file.k>` executes a k script on binary pattern+value stream input from stdin or a file; use `k-parse` and `k-print` at the boundaries.
|
|
14
|
+
- `node repl.mjs` (or `k-repl`) starts the interactive REPL.
|
|
15
|
+
- `./k.mjs -k <file.k>` executes a k script on binary pattern+value stream input from stdin or a file; use `k-parse` and `k-print` at the boundaries.
|
|
16
16
|
|
|
17
17
|
## Coding Style & Naming Conventions
|
|
18
18
|
- JavaScript uses ES modules (`.mjs`) with 2-space indentation and semicolons.
|
package/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,22 @@ This project uses [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
|
7
7
|
|
|
8
8
|
---
|
|
9
9
|
|
|
10
|
+
## [6.1.0] — 2026-05-20 — CLI aliases and help
|
|
11
|
+
|
|
12
|
+
### Toolchain
|
|
13
|
+
|
|
14
|
+
- Renamed the REPL entry point to `repl.mjs` and the installed binary to `k-repl`.
|
|
15
|
+
- Unified installed command names around the `k-` prefix and source basenames.
|
|
16
|
+
- Added `-h` / `--help` support across executable CLI scripts.
|
|
17
|
+
- Added public aliases in `Examples/ieee.k` for `add`, `sub`, `mul`, `div`, comparisons, and `neg`.
|
|
18
|
+
|
|
19
|
+
### Documentation
|
|
20
|
+
|
|
21
|
+
- Reworked the README around typed data transformations, contributor entry points, and the IEEE example.
|
|
22
|
+
- Updated CLI references across documentation to the current installed command names.
|
|
23
|
+
|
|
24
|
+
---
|
|
25
|
+
|
|
10
26
|
## [6.0.0] — 2026-05-12 — First public release
|
|
11
27
|
|
|
12
28
|
### Language & Runtime
|
|
@@ -22,18 +38,18 @@ This project uses [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
|
22
38
|
- Finite tree automaton type representation (`codes.mjs`).
|
|
23
39
|
- Graph-based constraint propagation via `TypePatternGraph`.
|
|
24
40
|
- SCC-aware convergence with configurable strategy (`auto` / `single_pass` / `fixed_point`).
|
|
25
|
-
- `compileStats` API for inspecting convergence
|
|
41
|
+
- `compileStats` API for inspecting convergence behavior per SCC.
|
|
26
42
|
|
|
27
43
|
### Toolchain
|
|
28
44
|
|
|
29
45
|
- `k` — CLI executor: reads binary pattern+value stream, applies a k script, writes result.
|
|
30
|
-
- `k-repl`
|
|
31
|
-
- `k-
|
|
32
|
-
- `k-compile-
|
|
46
|
+
- `k-repl` — interactive interpreter with tab-completion.
|
|
47
|
+
- `k-compile` / `k-decompile` — object file compilation and decompilation.
|
|
48
|
+
- `k-compile-lib` / `k-extract-aliases` — library compilation and alias extraction.
|
|
33
49
|
|
|
34
50
|
### Codec Pipeline
|
|
35
51
|
|
|
36
|
-
- Binary format:
|
|
52
|
+
- Binary format: serialized pattern graph followed by value encoded under that pattern.
|
|
37
53
|
- JSON codec, UTF-8/UTF-16 string codec, IEEE 754 codec.
|
|
38
54
|
- Polymorphic codec streams: pattern carried in-memory through projections and constructors.
|
|
39
55
|
|
|
@@ -45,4 +61,5 @@ This project uses [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
|
45
61
|
|
|
46
62
|
---
|
|
47
63
|
|
|
64
|
+
[6.1.0]: https://github.com/fraczak/k/releases/tag/v6.1.0
|
|
48
65
|
[6.0.0]: https://github.com/fraczak/k/releases/tag/v6.0.0
|
package/CLAUDE.md
CHANGED
|
@@ -4,7 +4,7 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co
|
|
|
4
4
|
|
|
5
5
|
## Project Overview
|
|
6
6
|
|
|
7
|
-
k
|
|
7
|
+
k is an experimental language for describing algebraic data shapes and composing typed transformations over them. Data descriptions and transformations share one syntax; the native k-like notation is canonical, and a JSON-like notation is available as a convenience for textual values.
|
|
8
8
|
|
|
9
9
|
## Essential Commands
|
|
10
10
|
|
|
@@ -20,8 +20,8 @@ npm test # Run comprehensive test suite (unit tests, derivation tests, shell te
|
|
|
20
20
|
|
|
21
21
|
**Running k programs:**
|
|
22
22
|
```bash
|
|
23
|
-
./k.mjs <file.k>
|
|
24
|
-
./
|
|
23
|
+
./k.mjs -k <file.k> # Execute k script
|
|
24
|
+
./repl.mjs # Start interactive REPL (or: k-repl)
|
|
25
25
|
```
|
|
26
26
|
|
|
27
27
|
## Architecture
|
|
@@ -61,4 +61,4 @@ npm test # Run comprehensive test suite (unit tests, derivation tests, shell te
|
|
|
61
61
|
- No external runtime dependencies (only jiwson for parser generation)
|
|
62
62
|
- Uses ES6 modules (.mjs files) throughout
|
|
63
63
|
- Extensive test suite in `Code-derivation-tests/` for type system validation
|
|
64
|
-
- REPL supports commands like
|
|
64
|
+
- REPL supports commands like `:C name` (show canonical type), `:t name` (show relation type), and `:d name` (show relation definition)
|
package/DOCS/BIG_PICTURE.md
CHANGED
|
@@ -82,7 +82,7 @@ filter_label_list ::= /* empty */ | '...'
|
|
|
82
82
|
|
|
83
83
|
Examples:
|
|
84
84
|
|
|
85
|
-
```
|
|
85
|
+
```text
|
|
86
86
|
X -- any type
|
|
87
87
|
( ... ) -- any type
|
|
88
88
|
{ ... } -- any product type
|
|
@@ -178,7 +178,7 @@ The normalization steps are:
|
|
|
178
178
|
|
|
179
179
|
#### Example 1
|
|
180
180
|
|
|
181
|
-
```
|
|
181
|
+
```text
|
|
182
182
|
$ bit = < {} o, {} i >;
|
|
183
183
|
bit0 = | o $bit;
|
|
184
184
|
bit1 = | i $bit;
|
|
@@ -242,7 +242,7 @@ Such a pattern is called _singleton pattern_, as only one type fits the pattern.
|
|
|
242
242
|
|
|
243
243
|
Polymorphic list functions:
|
|
244
244
|
|
|
245
|
-
```
|
|
245
|
+
```text
|
|
246
246
|
list? = ?< {} nil, {X car, Y cdr} cons > = Y;
|
|
247
247
|
nil = {} |nil list?;
|
|
248
248
|
singleton = {() car, nil cdr} |cons list?;
|
|
@@ -254,7 +254,7 @@ cdr = list? /cons .cdr;
|
|
|
254
254
|
|
|
255
255
|
For example, the filter annotation for `car` is:
|
|
256
256
|
|
|
257
|
-
```
|
|
257
|
+
```text
|
|
258
258
|
> :t car
|
|
259
259
|
car : ?<{X1 car, X0 cdr} cons, $KL nil>=X0 --> ?X1 (@...)
|
|
260
260
|
> :C KL
|
|
@@ -301,7 +301,7 @@ A type can be translated into a Rust data structure, and a function can be trans
|
|
|
301
301
|
|
|
302
302
|
Extending `@string` into `@bits`.
|
|
303
303
|
|
|
304
|
-
```
|
|
304
|
+
```text
|
|
305
305
|
$ bits = < {} _, bits 0, bits 1 >;
|
|
306
306
|
```
|
|
307
307
|
|
|
@@ -51,9 +51,9 @@ value-payload DAG compression.
|
|
|
51
51
|
|
|
52
52
|
```bash
|
|
53
53
|
echo '["zebara", "ela", "kupa", ala, owca]' | \
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
54
|
+
k-parse | \
|
|
55
|
+
k '{.1 0,.3 1}' | \
|
|
56
|
+
k-print
|
|
57
57
|
```
|
|
58
58
|
|
|
59
59
|
Expected output:
|
|
@@ -0,0 +1,458 @@
|
|
|
1
|
+
# KIR: k Intermediate Representation, Retyping, and Conformance
|
|
2
|
+
|
|
3
|
+
The document defines an object IR and conformance platform for LLVM and
|
|
4
|
+
WebAssembly backends.
|
|
5
|
+
|
|
6
|
+
## Goals
|
|
7
|
+
|
|
8
|
+
- Define a portable polymorphic object IR.
|
|
9
|
+
- Define retyping for concrete input envelope patterns.
|
|
10
|
+
- Define conformance fixtures for interpreter, object execution,
|
|
11
|
+
retyped execution, and future backends.
|
|
12
|
+
- Keep `.ko` and `.klib` inspectable.
|
|
13
|
+
- Record type-derivation convergence per relation.
|
|
14
|
+
|
|
15
|
+
## Out of Scope
|
|
16
|
+
|
|
17
|
+
- LLVM backend design.
|
|
18
|
+
- WebAssembly backend design.
|
|
19
|
+
- New language syntax.
|
|
20
|
+
- Replacing the current JavaScript evaluator.
|
|
21
|
+
|
|
22
|
+
## Execution Layers
|
|
23
|
+
|
|
24
|
+
### KIR-P: Polymorphic IR
|
|
25
|
+
|
|
26
|
+
KIR-P is the portable representation of a k relation. It keeps the current
|
|
27
|
+
pattern-carrying execution model.
|
|
28
|
+
|
|
29
|
+
KIR-P must:
|
|
30
|
+
|
|
31
|
+
- run any valid k program;
|
|
32
|
+
- preserve filters and pattern operations;
|
|
33
|
+
- store relation input and output patterns;
|
|
34
|
+
- be the canonical `.ko` / `.klib` relation format;
|
|
35
|
+
- be the reference for retyping and backend tests.
|
|
36
|
+
|
|
37
|
+
Alternative:
|
|
38
|
+
|
|
39
|
+
- Store source and re-run type derivation on load. This gives smaller objects,
|
|
40
|
+
but makes object behavior depend on the compiler version. Do not use this for
|
|
41
|
+
KIR.
|
|
42
|
+
|
|
43
|
+
### KIR-R: Retyped IR
|
|
44
|
+
|
|
45
|
+
KIR-R is produced from `KIR-P + input envelope pattern`.
|
|
46
|
+
|
|
47
|
+
KIR-R must:
|
|
48
|
+
|
|
49
|
+
- be equivalent to typing the entry expression `?P __main__`;
|
|
50
|
+
- derive the output pattern for that invocation;
|
|
51
|
+
- validate filters and pattern constraints before value execution;
|
|
52
|
+
- preserve the same value-level partial function semantics;
|
|
53
|
+
- support multiple pattern contexts for the same helper relation;
|
|
54
|
+
- be cacheable by relation hash and input pattern hash.
|
|
55
|
+
|
|
56
|
+
Alternative:
|
|
57
|
+
|
|
58
|
+
- Re-run full source compilation for each input pattern. This is acceptable for
|
|
59
|
+
the first prototype, but the public API should still be
|
|
60
|
+
`retype(rel, inputPattern)`.
|
|
61
|
+
|
|
62
|
+
### KIR-M: Backend IR
|
|
63
|
+
|
|
64
|
+
KIR-M is produced from KIR-R after call-site pattern contexts, layout, and ABI
|
|
65
|
+
decisions are fixed.
|
|
66
|
+
|
|
67
|
+
KIR-M should:
|
|
68
|
+
|
|
69
|
+
- use static product field offsets;
|
|
70
|
+
- use static union tag dispatch;
|
|
71
|
+
- represent partial failure explicitly;
|
|
72
|
+
- avoid envelope propagation only where call-site pattern contexts prove it safe;
|
|
73
|
+
- require converged type derivation for every compiled relation;
|
|
74
|
+
- target LLVM, Wasm, C, or another backend.
|
|
75
|
+
|
|
76
|
+
Alternative:
|
|
77
|
+
|
|
78
|
+
- Compile KIR-P directly. This is useful for a correctness experiment, but it
|
|
79
|
+
recreates the polymorphic interpreter and is not the final performance path.
|
|
80
|
+
|
|
81
|
+
## Object IR
|
|
82
|
+
|
|
83
|
+
### Step 1: Define KIR-P
|
|
84
|
+
|
|
85
|
+
Add `DOCS/KIR_V1.md`.
|
|
86
|
+
|
|
87
|
+
Define:
|
|
88
|
+
|
|
89
|
+
- top-level object fields: `format`, `codes`, `rels`, `relAlias`,
|
|
90
|
+
`compileStats`, `meta`, and `main`;
|
|
91
|
+
- canonical code table;
|
|
92
|
+
- polymorphic relation table;
|
|
93
|
+
- relation aliases;
|
|
94
|
+
- metadata;
|
|
95
|
+
- per-relation type-derivation status;
|
|
96
|
+
- optional origin source range;
|
|
97
|
+
- `.ko` main relation;
|
|
98
|
+
- `.klib` null main.
|
|
99
|
+
|
|
100
|
+
Current storage rules to preserve:
|
|
101
|
+
|
|
102
|
+
- `.klib` is plain UTF-8 JSON with no binary header;
|
|
103
|
+
- `.ko` is a `KOBJ\n` binary container around the JSON payload;
|
|
104
|
+
- no payload version field is stored;
|
|
105
|
+
- relation `typeDerivation` stores only `status`;
|
|
106
|
+
- code entries do not carry `typeDerivation`;
|
|
107
|
+
- relation bodies do not store generated input/output boundary filters;
|
|
108
|
+
- source ranges live only in metadata origin entries;
|
|
109
|
+
- origin entries do not have `kind`; the metadata entry has `type`.
|
|
110
|
+
|
|
111
|
+
Implementation:
|
|
112
|
+
|
|
113
|
+
- Add `kir.mjs`.
|
|
114
|
+
- Add a converter from current object payloads to KIR-P.
|
|
115
|
+
- Keep current object storage until KIR-P is validated.
|
|
116
|
+
|
|
117
|
+
Alternative:
|
|
118
|
+
|
|
119
|
+
- Change the stored object JSON immediately. This is less code, but risks
|
|
120
|
+
mixing backend contracts with current JS evaluator internals.
|
|
121
|
+
|
|
122
|
+
### Step 1a: Record Type-Derivation Status
|
|
123
|
+
|
|
124
|
+
Each relation definition should carry:
|
|
125
|
+
|
|
126
|
+
```json
|
|
127
|
+
{
|
|
128
|
+
"typeDerivation": {
|
|
129
|
+
"status": "converged"
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
```
|
|
133
|
+
|
|
134
|
+
Rules:
|
|
135
|
+
|
|
136
|
+
- valid statuses are `converged`, `not-converged`, and `unknown`;
|
|
137
|
+
- LLVM and Wasm compilation require `converged`;
|
|
138
|
+
- codes/types do not carry type-derivation status;
|
|
139
|
+
- `.ko` and `.klib` may still store non-converged relations;
|
|
140
|
+
- object execution may still use the JS evaluator for non-converged relations.
|
|
141
|
+
|
|
142
|
+
Alternative:
|
|
143
|
+
|
|
144
|
+
- Store one object-level `backendEligible` flag. This hides which relation
|
|
145
|
+
blocks backend compilation and is not enough for libraries.
|
|
146
|
+
|
|
147
|
+
### Step 2: Normalize Opcodes
|
|
148
|
+
|
|
149
|
+
KIR-P should use a closed opcode set:
|
|
150
|
+
|
|
151
|
+
```json
|
|
152
|
+
{ "op": "identity" }
|
|
153
|
+
{ "op": "empty" }
|
|
154
|
+
{ "op": "dot", "label": "x" }
|
|
155
|
+
{ "op": "div", "tag": "some" }
|
|
156
|
+
{ "op": "vid", "tag": "some" }
|
|
157
|
+
{ "op": "code", "code": "@..." }
|
|
158
|
+
{ "op": "filter", "filter": {} }
|
|
159
|
+
{ "op": "ref", "ref": "@..." }
|
|
160
|
+
{ "op": "comp", "items": [] }
|
|
161
|
+
{ "op": "union", "items": [] }
|
|
162
|
+
{ "op": "product", "fields": [{ "label": "x", "expr": {} }] }
|
|
163
|
+
```
|
|
164
|
+
|
|
165
|
+
Alternative:
|
|
166
|
+
|
|
167
|
+
- Keep current AST field names. This is faster now, but backend code should not
|
|
168
|
+
depend on parser-shaped fields.
|
|
169
|
+
|
|
170
|
+
### Step 3: Normalize Codes
|
|
171
|
+
|
|
172
|
+
Represent codes as canonical product or union nodes:
|
|
173
|
+
|
|
174
|
+
```json
|
|
175
|
+
{
|
|
176
|
+
"@hash": {
|
|
177
|
+
"kind": "product",
|
|
178
|
+
"fields": [{ "label": "x", "code": "@..." }],
|
|
179
|
+
"canonical": "$C0={...};"
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
```
|
|
183
|
+
|
|
184
|
+
Rules:
|
|
185
|
+
|
|
186
|
+
- Sort labels and tags canonically.
|
|
187
|
+
- Store references as canonical hashes.
|
|
188
|
+
- Validate that each hash matches its canonical form.
|
|
189
|
+
|
|
190
|
+
Alternative:
|
|
191
|
+
|
|
192
|
+
- Omit `canonical` and recompute it. This reduces payload size. Keeping it helps
|
|
193
|
+
debugging and validation during the POC.
|
|
194
|
+
|
|
195
|
+
### Step 4: Normalize Pattern Graphs
|
|
196
|
+
|
|
197
|
+
Do not expose `TypePatternGraph` internals as the backend contract.
|
|
198
|
+
|
|
199
|
+
Use:
|
|
200
|
+
|
|
201
|
+
```json
|
|
202
|
+
{
|
|
203
|
+
"root": 0,
|
|
204
|
+
"nodes": [
|
|
205
|
+
{
|
|
206
|
+
"id": 0,
|
|
207
|
+
"kind": "open-product",
|
|
208
|
+
"edges": [{ "label": "x", "target": 1 }]
|
|
209
|
+
}
|
|
210
|
+
]
|
|
211
|
+
}
|
|
212
|
+
```
|
|
213
|
+
|
|
214
|
+
Rules:
|
|
215
|
+
|
|
216
|
+
- Valid kinds: `any`, `open-product`, `closed-product`, `open-union`,
|
|
217
|
+
`closed-union`, `type`.
|
|
218
|
+
- Type nodes carry a code hash.
|
|
219
|
+
- Edge targets must exist.
|
|
220
|
+
- Edge order must be canonical.
|
|
221
|
+
|
|
222
|
+
Alternative:
|
|
223
|
+
|
|
224
|
+
- Store union-find state as debug metadata. Do not use it as backend input.
|
|
225
|
+
|
|
226
|
+
## Retyping
|
|
227
|
+
|
|
228
|
+
### Step 5: Add `retype(rel, inputPattern)`
|
|
229
|
+
|
|
230
|
+
Input:
|
|
231
|
+
|
|
232
|
+
- KIR-P relation;
|
|
233
|
+
- concrete canonical input pattern;
|
|
234
|
+
- code table;
|
|
235
|
+
- relation table.
|
|
236
|
+
|
|
237
|
+
Output:
|
|
238
|
+
|
|
239
|
+
- KIR-R relation;
|
|
240
|
+
- output pattern;
|
|
241
|
+
- call-site pattern summary.
|
|
242
|
+
|
|
243
|
+
Algorithm:
|
|
244
|
+
|
|
245
|
+
1. Type the entry as if the program were `?inputPattern __main__`.
|
|
246
|
+
2. Re-run pattern derivation over the reachable relation graph.
|
|
247
|
+
3. Preserve value-level partial operations.
|
|
248
|
+
4. Record the derived output pattern.
|
|
249
|
+
5. Record call-site pattern contexts for helper calls.
|
|
250
|
+
|
|
251
|
+
Alternative:
|
|
252
|
+
|
|
253
|
+
- Implement this inside `run.mjs` first. This may be useful for bootstrapping,
|
|
254
|
+
but the final API should be separate from the evaluator.
|
|
255
|
+
|
|
256
|
+
### Step 6: Execution After Retyping
|
|
257
|
+
|
|
258
|
+
Safe baseline:
|
|
259
|
+
|
|
260
|
+
- keep current envelope-carrying execution;
|
|
261
|
+
- use KIR-R only to derive the top-level output pattern;
|
|
262
|
+
- treat filters as already validated by retyping.
|
|
263
|
+
|
|
264
|
+
Optimized mode:
|
|
265
|
+
|
|
266
|
+
- remove envelope propagation only when every call site has a known stable
|
|
267
|
+
pattern context;
|
|
268
|
+
- keep value-level partiality for `.field`, `/tag`, merge, and composition;
|
|
269
|
+
- attach the derived output pattern after execution.
|
|
270
|
+
|
|
271
|
+
Alternative:
|
|
272
|
+
|
|
273
|
+
- Never remove envelopes in the JS evaluator. This is simplest and remains the
|
|
274
|
+
reference path. Envelope-free execution can be left to KIR-M.
|
|
275
|
+
|
|
276
|
+
### Step 7: Call-Site Retyping
|
|
277
|
+
|
|
278
|
+
One relation may be called under multiple patterns:
|
|
279
|
+
|
|
280
|
+
```text
|
|
281
|
+
f@P1
|
|
282
|
+
f@P2
|
|
283
|
+
```
|
|
284
|
+
|
|
285
|
+
KIR-R should model these as separate instances:
|
|
286
|
+
|
|
287
|
+
```text
|
|
288
|
+
relation hash + input pattern hash
|
|
289
|
+
```
|
|
290
|
+
|
|
291
|
+
Recursive definitions require fixed-point iteration over these instances.
|
|
292
|
+
|
|
293
|
+
Alternative:
|
|
294
|
+
|
|
295
|
+
- Use one annotation per relation. This is easier, but too coarse for precise
|
|
296
|
+
output patterns and unsafe for envelope-free execution.
|
|
297
|
+
|
|
298
|
+
### Step 8: Cache Retyping Results
|
|
299
|
+
|
|
300
|
+
Cache key:
|
|
301
|
+
|
|
302
|
+
```text
|
|
303
|
+
relation-hash + input-pattern-hash
|
|
304
|
+
```
|
|
305
|
+
|
|
306
|
+
Cache value:
|
|
307
|
+
|
|
308
|
+
- KIR-R relation;
|
|
309
|
+
- output pattern;
|
|
310
|
+
- call-site pattern summary;
|
|
311
|
+
- optional backend artifact.
|
|
312
|
+
|
|
313
|
+
Alternative:
|
|
314
|
+
|
|
315
|
+
- Cache by pattern JSON first. Replace with pattern hashes once pattern hashing
|
|
316
|
+
is stable.
|
|
317
|
+
|
|
318
|
+
## Conformance
|
|
319
|
+
|
|
320
|
+
### Step 9: Fixture Format
|
|
321
|
+
|
|
322
|
+
Use one directory per case:
|
|
323
|
+
|
|
324
|
+
```text
|
|
325
|
+
conformance/projection-field/
|
|
326
|
+
case.json
|
|
327
|
+
program.k
|
|
328
|
+
input.kv
|
|
329
|
+
expected.kv
|
|
330
|
+
```
|
|
331
|
+
|
|
332
|
+
Example:
|
|
333
|
+
|
|
334
|
+
```json
|
|
335
|
+
{
|
|
336
|
+
"name": "project field",
|
|
337
|
+
"program": "program.k",
|
|
338
|
+
"input": "input.kv",
|
|
339
|
+
"expected": "expected.kv",
|
|
340
|
+
"modes": ["source", "object", "retyped"],
|
|
341
|
+
"tags": ["runtime", "projection"]
|
|
342
|
+
}
|
|
343
|
+
```
|
|
344
|
+
|
|
345
|
+
Alternative:
|
|
346
|
+
|
|
347
|
+
- Store all fixtures in one JSON file. This is compact but harder to debug.
|
|
348
|
+
|
|
349
|
+
### Step 10: Runner
|
|
350
|
+
|
|
351
|
+
Add `conformance/run.mjs`.
|
|
352
|
+
|
|
353
|
+
Modes:
|
|
354
|
+
|
|
355
|
+
- `source`: compile source and run the JS evaluator;
|
|
356
|
+
- `object`: compile `.ko`, load it, and run object evaluation;
|
|
357
|
+
- `retyped`: retype using the input wire pattern and run the retyped evaluator;
|
|
358
|
+
- future `wasm` / `llvm`: run backend artifacts.
|
|
359
|
+
|
|
360
|
+
Comparison:
|
|
361
|
+
|
|
362
|
+
- Parse `input.kv` through `k-parse`.
|
|
363
|
+
- Run one mode.
|
|
364
|
+
- Print through `k-print`.
|
|
365
|
+
- Compare normalized textual output.
|
|
366
|
+
|
|
367
|
+
Alternative:
|
|
368
|
+
|
|
369
|
+
- Compare JS values directly. This is faster, but fixtures should not depend on
|
|
370
|
+
JS object representation.
|
|
371
|
+
|
|
372
|
+
### Step 11: Initial Fixtures
|
|
373
|
+
|
|
374
|
+
Runtime:
|
|
375
|
+
|
|
376
|
+
- identity;
|
|
377
|
+
- product projection;
|
|
378
|
+
- union projection;
|
|
379
|
+
- variant construction;
|
|
380
|
+
- composition;
|
|
381
|
+
- merge fallback;
|
|
382
|
+
- product construction.
|
|
383
|
+
|
|
384
|
+
Typing and patterns:
|
|
385
|
+
|
|
386
|
+
- `$type` filter;
|
|
387
|
+
- open product filter;
|
|
388
|
+
- open union filter;
|
|
389
|
+
- recursive list/tree filter;
|
|
390
|
+
- incompatible filter error.
|
|
391
|
+
|
|
392
|
+
Objects and libraries:
|
|
393
|
+
|
|
394
|
+
- compile `.klib`;
|
|
395
|
+
- compile `.ko` with `--lib`;
|
|
396
|
+
- load aliases from metadata;
|
|
397
|
+
- `:load --no-alias`;
|
|
398
|
+
- reload `extract-aliases` output.
|
|
399
|
+
|
|
400
|
+
Codecs:
|
|
401
|
+
|
|
402
|
+
- unit;
|
|
403
|
+
- nested product;
|
|
404
|
+
- nested variant;
|
|
405
|
+
- Unicode labels;
|
|
406
|
+
- explicit pattern vs derived witness pattern.
|
|
407
|
+
|
|
408
|
+
Retyping:
|
|
409
|
+
|
|
410
|
+
- output pattern derived from `?P __main__`;
|
|
411
|
+
- helper called under two different patterns;
|
|
412
|
+
- recursive helper retyping convergence;
|
|
413
|
+
- retyping cache reuse.
|
|
414
|
+
|
|
415
|
+
Backend eligibility:
|
|
416
|
+
|
|
417
|
+
- converged relation compiles to KIR-M;
|
|
418
|
+
- non-converged relation is rejected by LLVM/Wasm compiler;
|
|
419
|
+
- `.klib` with mixed relations reports the exact rejected aliases.
|
|
420
|
+
|
|
421
|
+
Alternative:
|
|
422
|
+
|
|
423
|
+
- Start with fuzzing. Do this later. First fixtures should be deterministic and
|
|
424
|
+
readable.
|
|
425
|
+
|
|
426
|
+
## Tooling Ideas
|
|
427
|
+
|
|
428
|
+
- `k-inspect-object`: print object sections, KIR-P, aliases, metadata, and
|
|
429
|
+
pattern summaries.
|
|
430
|
+
- `k-validate-object`: validate `.ko` and `.klib` schemas and references.
|
|
431
|
+
- `k-retype-object`: precompute KIR-R for one relation and input pattern.
|
|
432
|
+
- Retyping heat counters in the JS runtime.
|
|
433
|
+
- Pattern-hash backend artifact cache.
|
|
434
|
+
- Optional binary executable object payload after KIR stabilizes.
|
|
435
|
+
- Minimal C backend before LLVM.
|
|
436
|
+
- Wasm KIR-R interpreter before native LLVM.
|
|
437
|
+
|
|
438
|
+
## Implementation Order
|
|
439
|
+
|
|
440
|
+
1. Write `DOCS/KIR_V1.md`.
|
|
441
|
+
2. Treat current `.ko` / `.klib` storage as the initial KIR-P input format.
|
|
442
|
+
3. Add `kir.mjs` to export KIR-P from current objects.
|
|
443
|
+
4. Add `objects/inspect.mjs --kir`.
|
|
444
|
+
5. Add `objects/validate.mjs`.
|
|
445
|
+
6. Add conformance fixture format and runner.
|
|
446
|
+
7. Add entry retyping for `?P __main__`.
|
|
447
|
+
8. Add a KIR-R JS evaluator or retyped execution wrapper.
|
|
448
|
+
9. Compare KIR-R execution against `run.mjs`.
|
|
449
|
+
10. Add call-site retyping for helper relations.
|
|
450
|
+
11. Add retyping cache.
|
|
451
|
+
12. Reject non-converged relations in LLVM/Wasm compilation.
|
|
452
|
+
13. Prototype a small C or Wasm backend for KIR-R.
|
|
453
|
+
|
|
454
|
+
Rule:
|
|
455
|
+
|
|
456
|
+
- KIR-P is the portable semantic contract.
|
|
457
|
+
- KIR-R is the retyping contract.
|
|
458
|
+
- KIR-M is backend material.
|