@fraczak/k 6.10.5 → 7.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.
- package/CHANGELOG.md +70 -0
- package/CLAUDE.md +1 -1
- package/DOCS/BIG_PICTURE.md +156 -172
- package/DOCS/BINARY_CODEC_STATUS_AND_TODO.md +3 -3
- package/DOCS/CODEC_ARCHITECTURE.md +2 -2
- package/DOCS/DICTIONARY.md +243 -250
- package/DOCS/DIVERGENCE_DETECTION.md +0 -1
- package/DOCS/FILE_FORMATS.md +5 -5
- package/DOCS/KIR_SPECIALIZATION_DESIGN.md +1 -1
- package/DOCS/OBJECT_FILE_AND_PATTERN.md +12 -12
- package/DOCS/PATTERNS.md +17 -17
- package/DOCS/PATTERNS_AND_TYPED_VALUES.md +1 -1
- package/DOCS/REPL.md +9 -19
- package/DOCS/TYPE_DERIVATION.md +2 -8
- package/DOCS/WEB_REPL_REQUIREMENTS.md +8 -8
- package/DOCS/book/01-introduction.md +8 -11
- package/DOCS/book/02-syntax-and-values.md +19 -20
- package/DOCS/book/03-types-as-finite-automata.md +42 -43
- package/DOCS/book/04-partial-functions-and-composition.md +2 -3
- package/DOCS/book/05-typing-filters-and-normalization.md +44 -46
- package/DOCS/book/06-values-in-memory.md +10 -10
- package/DOCS/book/08-operational-semantics-and-execution.md +21 -26
- package/DOCS/book/09-compiler-architecture.md +11 -11
- package/DOCS/book/10-from-ast-to-intermediate-representation.md +6 -7
- package/DOCS/book/14-canonical-serialization.md +2 -2
- package/DOCS/book/appendix-b-incorporating-external-predefined-types-and-functions.md +17 -17
- package/DOCS/book.md +5 -5
- package/Examples/arithmetics.k +49 -153
- package/Examples/bnat.k +13 -13
- package/Examples/byte.k +2 -50
- package/Examples/ieee.k +408 -423
- package/Examples/karatsuba-mult.k +30 -34
- package/Examples/nat.k +5 -6
- package/README.md +54 -49
- package/TODO.md +13 -18
- package/browser/repl-browser.mjs +40 -22
- package/browser/shims/fs.mjs +7 -10
- package/browser/vfs-data.mjs +12 -12
- package/codecs/BINARY_FORMAT.md +4 -4
- package/codecs/POLYMORPHIC_BINARY_FORMAT.md +4 -4
- package/codecs/README.md +6 -6
- package/codecs/ieee.mjs +15 -11
- package/codecs/int.mjs +9 -5
- package/codecs/string-codec.mjs +46 -47
- package/core.k +124 -175
- package/object.mjs +0 -7
- package/package.json +5 -2
- package/parser.jison +2 -41
- package/parser.mjs +55 -95
- package/pretty.mjs +11 -4
- package/repl.mjs +8 -63
- package/scripts/build-repl-html.mjs +18 -49
- package/tests/code-derivation/blowup.mjs +2 -4
- package/tests/code-derivation/bnat.mjs +2 -3
- package/tests/code-derivation/dot.mjs +5 -11
- package/tests/code-derivation/nat.mjs +2 -2
- package/tests/code-derivation/not-not.mjs +6 -6
- package/tests/code-derivation/pattern-envelope.mjs +4 -6
- package/tests/code-derivation/product.mjs +3 -6
- package/tests/code-derivation/rlz.mjs +4 -5
- package/tests/test-codecs.mjs +1 -1
- package/tests/test-fingerprint.mjs +36 -41
- package/tests/test-hash-normalization.mjs +4 -6
- package/tests/test-ieee-arithmetic.mjs +6 -7
- package/tests/test-k-object.mjs +11 -15
- package/tests/test-kir.mjs +0 -1
- package/tests/test-kvm-polymorphic.mjs +1 -2
- package/tests/test-kvm.mjs +8 -11
- package/tests/test-repl-html.mjs +86 -9
- package/tests/test-repl.mjs +38 -53
- package/tests/test.mjs +2 -3
|
@@ -2,23 +2,22 @@
|
|
|
2
2
|
-- Self-contained and minimal implementation
|
|
3
3
|
-- for arbitrary-precision integers
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
no = {} | no $yes_no;
|
|
5
|
+
yes = {} | yes;
|
|
6
|
+
no = {} | no;
|
|
8
7
|
|
|
9
|
-
|
|
8
|
+
bits = ?< {} _, bits 0, bits 1 > = bits;
|
|
10
9
|
0b = {} | _;
|
|
11
10
|
0 = 0b |0;
|
|
12
11
|
1 = 0b |1;
|
|
13
12
|
|
|
14
|
-
|
|
15
|
-
0u = {} | _
|
|
13
|
+
unat = ?< {} _, unat 1 > = unat;
|
|
14
|
+
0u = {} | _;
|
|
16
15
|
|
|
17
|
-
empty =
|
|
16
|
+
empty = < /_ yes, no >;
|
|
18
17
|
empty? = {empty /yes if, () then} .then;
|
|
19
18
|
|
|
20
19
|
inv = {()x, 0b r} _inv;
|
|
21
|
-
_inv =
|
|
20
|
+
_inv = ?{ <X 0, X 1, {} _>=X x, ... }
|
|
22
21
|
<
|
|
23
22
|
{.x empty? if, .r then} .then,
|
|
24
23
|
<
|
|
@@ -27,8 +26,8 @@ _inv = ${bits x, bits r}
|
|
|
27
26
|
> _inv
|
|
28
27
|
>;
|
|
29
28
|
|
|
30
|
-
concat =
|
|
31
|
-
concat_ =
|
|
29
|
+
concat = {.x inv x, .y y} concat_;
|
|
30
|
+
concat_ = ?{ <X 0, X 1, {} _>=X x, ... }
|
|
32
31
|
<
|
|
33
32
|
{.x empty? if, .y then} .then,
|
|
34
33
|
<
|
|
@@ -40,21 +39,18 @@ concat_ = ${bits x, bits y}
|
|
|
40
39
|
remove_leading_zeros = < /0 remove_leading_zeros, () >;
|
|
41
40
|
nat = remove_leading_zeros <empty? 0, ()>;
|
|
42
41
|
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
abs = $int </'+', /'-'>;
|
|
42
|
+
int = nat | '+';
|
|
43
|
+
abs = </'+', /'-'>;
|
|
46
44
|
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
sign_minus = {} | '-' $sign;
|
|
45
|
+
sign_plus = {} | '+';
|
|
46
|
+
sign_minus = {} | '-';
|
|
50
47
|
swap_sign = < /'+' | '-', /'-' | '+' >;
|
|
51
48
|
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
c1 = {} | 1 $carry;
|
|
49
|
+
c0 = {} | 0;
|
|
50
|
+
c1 = {} | 1;
|
|
55
51
|
|
|
56
52
|
_plus = {.x x, .y y, .c c, 0b r} _plus_;
|
|
57
|
-
_plus_ =
|
|
53
|
+
_plus_ = ?{ <X 0, X 1, {} _>=X x, ... }
|
|
58
54
|
<
|
|
59
55
|
{.x empty? if, .y empty? and, .c/0 c, .r inv then} .then,
|
|
60
56
|
{.x empty? if, .y empty? and, {.r x, 1 r} _inv then} .then,
|
|
@@ -74,7 +70,7 @@ _plus_ = ${bits x, bits y, carry c, bits r}
|
|
|
74
70
|
>;
|
|
75
71
|
|
|
76
72
|
_minus = {.x x, .y y, .c c, 0b r} _minus_;
|
|
77
|
-
_minus_ =
|
|
73
|
+
_minus_ = ?{ <X 0, X 1, {} _>=X x, ... }
|
|
78
74
|
<
|
|
79
75
|
{.y empty? if, .c/0 and, {.r x, .x r} _inv then} .then,
|
|
80
76
|
<
|
|
@@ -91,10 +87,10 @@ _minus_ = ${bits x, bits y, carry c, bits r}
|
|
|
91
87
|
> _minus_
|
|
92
88
|
>;
|
|
93
89
|
|
|
94
|
-
plus_bits =
|
|
95
|
-
minus_bits =
|
|
90
|
+
plus_bits = {.x inv x, .y inv y, c0 c} _plus inv nat;
|
|
91
|
+
minus_bits = {.x inv x, .y inv y, c0 c} _minus inv nat;
|
|
96
92
|
|
|
97
|
-
_times =
|
|
93
|
+
_times = ?{ <Y 0, Y 1, {} _>=Y y, ... }
|
|
98
94
|
<
|
|
99
95
|
{.y empty? if, .result then} .then,
|
|
100
96
|
<
|
|
@@ -102,21 +98,21 @@ _times = ${bits result, bits _x, bits y}
|
|
|
102
98
|
{{._x x, .result |0 y, c0 c} _plus result, ._x _x, .y /1 y}
|
|
103
99
|
> _times
|
|
104
100
|
>;
|
|
105
|
-
times_bits =
|
|
101
|
+
times_bits = {0 result, .x inv _x, .y y} _times inv nat;
|
|
106
102
|
|
|
107
|
-
unat_to_zeros =
|
|
108
|
-
unat_to_double_zeros =
|
|
109
|
-
< /_ 0b, /1 unat_to_double_zeros |0 |0 >
|
|
103
|
+
unat_to_zeros = ?< {} _, X 1 >=X < /_ 0b, /1 unat_to_zeros |0 > ?< {} _, Z 0, Z 1 >=Z;
|
|
104
|
+
unat_to_double_zeros = ?< {} _, X 1 >=X
|
|
105
|
+
< /_ 0b, /1 unat_to_double_zeros |0 |0 > ?< {} _, Z 0, Z 1 >=Z;
|
|
110
106
|
|
|
111
107
|
_peel2 = < </0,/1> </0,/1>, </0,/1>, () >;
|
|
112
|
-
_half_unat =
|
|
108
|
+
_half_unat = ?{ <X 0, X 1, {} _>=X x, ... }
|
|
113
109
|
<
|
|
114
110
|
{.x empty? if, .y empty? and, .m then} .then,
|
|
115
111
|
{.x _peel2 x, .y _peel2 y, .m |1 m} _half_unat
|
|
116
112
|
>;
|
|
117
113
|
half_unat = {.x x, .y y, 0u m} _half_unat;
|
|
118
114
|
|
|
119
|
-
_split_rev_u =
|
|
115
|
+
_split_rev_u = ?{ <X 0, X 1, {} _>=X x_rev, <M 1, {} _>=M m, ... }
|
|
120
116
|
<
|
|
121
117
|
{.m /_ if, {.low nat low, .x_rev inv nat high} then} .then,
|
|
122
118
|
{.x_rev empty? if, {.low nat low, 0 high} then} .then,
|
|
@@ -147,19 +143,19 @@ at_least_256_u? = <
|
|
|
147
143
|
yes, no
|
|
148
144
|
>;
|
|
149
145
|
|
|
150
|
-
shift_bits_u =
|
|
146
|
+
shift_bits_u =
|
|
151
147
|
<
|
|
152
148
|
{.val empty? if, 0b then} .then,
|
|
153
149
|
{.val x, .m unat_to_zeros y} concat
|
|
154
150
|
>;
|
|
155
151
|
|
|
156
|
-
shift2_bits_u =
|
|
152
|
+
shift2_bits_u =
|
|
157
153
|
<
|
|
158
154
|
{.val empty? if, 0b then} .then,
|
|
159
155
|
{.val x, .m unat_to_double_zeros y} concat
|
|
160
156
|
>;
|
|
161
157
|
|
|
162
|
-
_karatsuba =
|
|
158
|
+
_karatsuba = ?{ <X 0, X 1, {} _>=X x, <Y 0, Y 1, {} _>=Y y }
|
|
163
159
|
<
|
|
164
160
|
-- Base case: if m < 256 (< 512 bits), fall back to times_bits
|
|
165
161
|
{{.x x, .y y} half_unat m, .x x, .y y}
|
|
@@ -198,7 +194,7 @@ _karatsuba = ${bits x, bits y}
|
|
|
198
194
|
>
|
|
199
195
|
>;
|
|
200
196
|
|
|
201
|
-
karatsuba =
|
|
197
|
+
karatsuba =
|
|
202
198
|
{
|
|
203
199
|
<
|
|
204
200
|
{.x/'+' if, .y /'+' and} sign_plus,
|
package/Examples/nat.k
CHANGED
|
@@ -1,10 +1,9 @@
|
|
|
1
|
-
$ nat = < {} 0, nat +1 >;
|
|
2
1
|
0 = {} | 0 ;
|
|
3
|
-
0? =
|
|
4
|
-
succ = | +1
|
|
5
|
-
pred =
|
|
6
|
-
add = ?{
|
|
7
|
-
mult = <
|
|
2
|
+
0? = { / 0 if, () then} .then;
|
|
3
|
+
succ = | +1 ;
|
|
4
|
+
pred = / +1 ;
|
|
5
|
+
add = ?{ < {} 0, N +1 > = N x, ... } = X <{.x pred x, .y succ y} ?X add, .y> ;
|
|
6
|
+
mult = ?{ < {} 0, M +1 > = M x, ... } <
|
|
8
7
|
{{.x pred x, .y y} mult x, .y y} add,
|
|
9
8
|
0
|
|
10
9
|
> ;
|
package/README.md
CHANGED
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
# k
|
|
2
2
|
|
|
3
|
-
**k is a small language for
|
|
3
|
+
**k is a small language for content-addressable schemas and data transformations.**
|
|
4
4
|
|
|
5
|
-
It describes data as algebraic
|
|
6
|
-
|
|
7
|
-
that can be parsed, transformed, printed, compiled, and inspected.
|
|
5
|
+
It describes data as algebraic schemas, programs as first-order partial
|
|
6
|
+
relations, and runtime values as a self-describing binary `schema + payload`
|
|
7
|
+
stream that can be parsed, transformed, printed, compiled, and inspected.
|
|
8
8
|
|
|
9
|
-
|
|
10
|
-
define both
|
|
9
|
+
Schema definitions and transformations share one syntax, so a k file can
|
|
10
|
+
define both data schemas and the relations that transform between them.
|
|
11
11
|
|
|
12
|
-
k is experimental, but it already has a working parser,
|
|
12
|
+
k is experimental, but it already has a working parser, contract-derivation
|
|
13
13
|
engine, REPL, binary codec pipeline, object/library format, Node.js API,
|
|
14
14
|
and test suite.
|
|
15
15
|
|
|
@@ -17,23 +17,23 @@ and test suite.
|
|
|
17
17
|
|
|
18
18
|
Many systems need to answer the same questions:
|
|
19
19
|
|
|
20
|
-
- What
|
|
21
|
-
- Which transformations are valid for that
|
|
22
|
-
- What does a program accept, produce, or
|
|
23
|
-
- Can this transformation be serialized, tested, reused, or
|
|
20
|
+
- What schema does this data have?
|
|
21
|
+
- Which transformations are valid for that schema?
|
|
22
|
+
- What does a program accept, produce, or preserve?
|
|
23
|
+
- Can this transformation be serialized, tested, reused, or verified?
|
|
24
24
|
|
|
25
|
-
k explores a compact answer: define algebraic
|
|
26
|
-
partial
|
|
27
|
-
automatically, and move values across process boundaries with a canonical
|
|
28
|
-
binary representation.
|
|
25
|
+
k explores a compact answer: define algebraic schemas, compose
|
|
26
|
+
partial relations over them, derive input/output contracts
|
|
27
|
+
automatically, and move values across process boundaries with a canonical,
|
|
28
|
+
content-addressable binary representation.
|
|
29
29
|
|
|
30
30
|
That makes k interesting as a foundation for:
|
|
31
31
|
|
|
32
|
-
- schema
|
|
32
|
+
- content-addressable schema registries and schema-to-schema pipelines
|
|
33
33
|
- binary codecs and canonical serialization
|
|
34
34
|
- protocol, hardware, or test-vector transformation pipelines
|
|
35
|
-
- teaching algebraic data types and compositional programming
|
|
36
|
-
- research into partial
|
|
35
|
+
- teaching algebraic data types and compositional relational programming
|
|
36
|
+
- research into partial relations, finite tree automata, and typed IRs
|
|
37
37
|
|
|
38
38
|
## A Small Example
|
|
39
39
|
|
|
@@ -41,11 +41,10 @@ k can define recursive data and transformations in the same file. Peano
|
|
|
41
41
|
natural numbers are either `0` or one more than another natural number:
|
|
42
42
|
|
|
43
43
|
```k
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
add = $ { nat x, nat y } <
|
|
44
|
+
0 = {} | 0;
|
|
45
|
+
inc = | +1;
|
|
46
|
+
dec = / +1; # undefined for '0'
|
|
47
|
+
add = ?{ < {} 0, N +1 > = N x, ... } <
|
|
49
48
|
{ . x dec x, . y inc y } add, # defined if 'x > 0'
|
|
50
49
|
. y # else, return 'y'
|
|
51
50
|
>;
|
|
@@ -53,7 +52,8 @@ add = $ { nat x, nat y } <
|
|
|
53
52
|
|
|
54
53
|
`add` takes a product `{ x, y }`. If `x` has a `+1`, it moves that
|
|
55
54
|
successor from `x` to `y` and recurses. When that no longer applies, it
|
|
56
|
-
returns `y`.
|
|
55
|
+
returns `y`. The inductive filter `?{ < {} 0, N +1 > = N x, ... }`
|
|
56
|
+
explicitly witnesses that recursive calls shrink `x`.
|
|
57
57
|
|
|
58
58
|
In the REPL:
|
|
59
59
|
|
|
@@ -118,12 +118,13 @@ Every installed command supports `-h` and `--help`.
|
|
|
118
118
|
|
|
119
119
|
**Algebraic data shapes**
|
|
120
120
|
|
|
121
|
-
|
|
121
|
+
All data structures in k are built from products and tagged unions (variants).
|
|
122
|
+
Relations and pattern filters describe their domains:
|
|
122
123
|
|
|
123
124
|
```k
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
125
|
+
bit = ?< {} 0, {} 1 >;
|
|
126
|
+
byte = ?{ Bit 0, Bit 1, Bit 2, Bit 3, Bit 4, Bit 5, Bit 6, Bit 7 };
|
|
127
|
+
bits = ?< {} _, bits 0, bits 1 > = bits;
|
|
127
128
|
```
|
|
128
129
|
|
|
129
130
|
There are no built-in primitive values. The empty product `{}` is the
|
|
@@ -137,34 +138,38 @@ Core expressions are deliberately small:
|
|
|
137
138
|
| --- | --- |
|
|
138
139
|
| `.field` | project a product field |
|
|
139
140
|
| `/tag` | project a tagged-union branch |
|
|
140
|
-
| `\|tag` | introduce a tagged
|
|
141
|
+
| `\|tag` | introduce a variant (tagged union) |
|
|
141
142
|
| `(f g)` | compose transformations |
|
|
142
143
|
| `<f, g>` | try `f`, then `g` if `f` is undefined |
|
|
143
144
|
| `{f a, g b}` | build a product from parallel transformations |
|
|
145
|
+
| `?filter` | schema filter / inductive termination witness |
|
|
144
146
|
| `()` | identity |
|
|
145
147
|
| `<>` | always undefined |
|
|
146
148
|
| `{}` | constant empty product |
|
|
147
149
|
|
|
148
|
-
**Derived
|
|
150
|
+
**Derived relational contracts**
|
|
149
151
|
|
|
150
|
-
k derives structural
|
|
151
|
-
|
|
152
|
-
|
|
152
|
+
k derives structural contracts for relations. A contract is a connected
|
|
153
|
+
$(input, output)$ schema graph that specifies accepted input schemas,
|
|
154
|
+
guaranteed output schemas, and preserved data structures ($=X$). Those
|
|
155
|
+
contracts guide diagnostics, REPL output, binary serialization, and
|
|
156
|
+
optimizations.
|
|
153
157
|
|
|
154
|
-
**
|
|
158
|
+
**Self-describing binary streams**
|
|
155
159
|
|
|
156
160
|
The command-line pipeline uses a self-describing binary stream:
|
|
157
161
|
|
|
158
162
|
```text
|
|
159
|
-
encoded
|
|
163
|
+
encoded schema, followed by payload encoded under that schema
|
|
160
164
|
```
|
|
161
165
|
|
|
162
166
|
The boundary tools are:
|
|
163
167
|
|
|
164
168
|
```bash
|
|
165
|
-
k-parse # textual k value -> binary
|
|
169
|
+
k-parse # textual k value -> binary schema+payload stream
|
|
166
170
|
k # apply a k expression or .k/.ko program to the stream
|
|
167
|
-
k-print # binary
|
|
171
|
+
k-print # binary schema+payload stream -> textual value
|
|
172
|
+
k-show # inspect decoded schema and payload value
|
|
168
173
|
```
|
|
169
174
|
|
|
170
175
|
**Inspectable objects and libraries**
|
|
@@ -172,21 +177,21 @@ k-print # binary pattern+value stream -> textual value
|
|
|
172
177
|
`k` programs can be authored, compiled, and linked across four main
|
|
173
178
|
file formats:
|
|
174
179
|
|
|
175
|
-
- `.k`: human-readable source code defining algebraic
|
|
176
|
-
- `.klib`: ahead-of-time (AOT)
|
|
177
|
-
|
|
178
|
-
- `.ko`: ahead-of-time (AOT)
|
|
179
|
-
|
|
180
|
-
|
|
180
|
+
- `.k`: human-readable source code defining algebraic schemas and relations.
|
|
181
|
+
- `.klib`: ahead-of-time (AOT) library objects (`main: null`) storing
|
|
182
|
+
canonical relation definitions, schemas, and local aliases.
|
|
183
|
+
- `.ko`: ahead-of-time (AOT) executable containers (`KOBJ\n` magic header)
|
|
184
|
+
with entrypoint `main: "__main__"`, skipping parsing and contract
|
|
185
|
+
derivation at runtime.
|
|
181
186
|
- `.kvm`: polymorphic register-IR template artifacts (`layer: "KVM-P"`)
|
|
182
|
-
carrying principal
|
|
187
|
+
carrying principal schema contracts for instant runtime specialization
|
|
183
188
|
(`specializeKVM`).
|
|
184
189
|
|
|
185
|
-
In `k`, all relations and
|
|
190
|
+
In `k`, all relations and derived schemas are identified canonically by immutable
|
|
186
191
|
content-addressed hashes (`@hash`). There is no global symbol namespace;
|
|
187
192
|
friendly names (such as `plus`, `int`, or `5`) are local aliases stored
|
|
188
193
|
in metadata. Similarly, there are no primitive numbers: numerical
|
|
189
|
-
identifiers like `5` or `10` are nullary relations mapping
|
|
194
|
+
identifiers like `5` or `10` are nullary relations mapping `{}` to `bits`.
|
|
190
195
|
|
|
191
196
|
For a detailed guide to all four formats, commands, and workflows, see
|
|
192
197
|
[DOCS/FILE_FORMATS.md](DOCS/FILE_FORMATS.md).
|
|
@@ -204,9 +209,9 @@ For a detailed guide to all four formats, commands, and workflows, see
|
|
|
204
209
|
|
|
205
210
|
| Command | Purpose |
|
|
206
211
|
| --- | --- |
|
|
207
|
-
| `k-parse` | Convert textual k values to binary
|
|
208
|
-
| `k-print` | Convert binary
|
|
209
|
-
| `k-show` | Pass a stream through while showing the decoded
|
|
212
|
+
| `k-parse` | Convert textual k values to binary schema+payload streams |
|
|
213
|
+
| `k-print` | Convert binary schema+payload streams back to textual values |
|
|
214
|
+
| `k-show` | Pass a stream through while showing the decoded payload and schema |
|
|
210
215
|
|
|
211
216
|
**Built-in codecs**
|
|
212
217
|
|
package/TODO.md
CHANGED
|
@@ -17,37 +17,32 @@ This document details the issues, conceptual improvements, and completed enhance
|
|
|
17
17
|
## 2. Help Modal (`? Help` / `:help`) Overhaul
|
|
18
18
|
|
|
19
19
|
### Language Overview & Grammar Categorization
|
|
20
|
-
- [x] **Language Overview**: Short, positive, accessible description: `k` is a concise language of
|
|
21
|
-
- [x] **Content-Addressed Identity**:
|
|
22
|
-
- [x] **
|
|
20
|
+
- [x] **Language Overview**: Short, positive, accessible description: `k` is a concise language of relations (functions) over tree-like (JSON-like) documents.
|
|
21
|
+
- [x] **Content-Addressed Identity**: Relations are identified by their canonical content hash (`@...`) derived directly from their structure; local names are just temporary aliases used for recursion and readability.
|
|
22
|
+
- [x] **Grammar Categories**:
|
|
23
23
|
1. **Definitions (Local Aliases)**:
|
|
24
24
|
- `name = relExpr;` — Relation alias (e.g. `swap = { . y x, . x y };`).
|
|
25
|
-
|
|
26
|
-
2. **Type Expressions (`typeExpr`)**: Schemas describing tree-like documents:
|
|
27
|
-
- `{ Type_1 label_1, ..., Type_k label_k }` — Product type of arity $k$ (labeled records, e.g. `{float64 x, string n}`; special case: `{}` is the 0-ary product).
|
|
28
|
-
- `< Type_1 tag_1, ..., Type_k tag_k >` — Union type of arity $k$ (tagged sum of variants, e.g. `<int ok, string err>`).
|
|
29
|
-
- `name` / `@hash` — Type reference.
|
|
30
|
-
3. **Relation Expressions (`relExpr`)**: Functions transforming an input document to an output document:
|
|
25
|
+
2. **Relation Expressions (`relExpr`)**: Functions transforming an input document to an output document:
|
|
31
26
|
- `{ rel_1 label_1, ..., rel_k label_k }` — Product of arity $k$ (evaluates relations into record fields; special case: `{}` evaluates 0 relations, producing empty record `{}`).
|
|
32
27
|
- `< rel_1, ..., rel_k >` — Union / ordered choice of arity $k$ (evaluates relations in order until one succeeds).
|
|
33
28
|
- `( rel_1 ... rel_k )` — Composition of arity $k$ (sequentially composes relations; special case: `()` is the 0-ary composition denoting identity; parentheses can be omitted when non-empty: `f g`).
|
|
34
29
|
- `. label` — Field projection (extracts field `label`).
|
|
35
30
|
- `/ tag` — Variant branch projection (extracts payload of variant `tag`).
|
|
36
31
|
- `| tag` — Variant constructor (wraps document into variant `tag`).
|
|
37
|
-
-
|
|
32
|
+
- `? filterExpr` — Pattern filter (asserts input matches pattern; serves as inductive termination witness).
|
|
38
33
|
- `name` / `@hash` — Relation reference.
|
|
39
34
|
- [x] **Simplified Intro**:
|
|
40
35
|
- Made arbitrary arity explicit across products `{...}`, unions `<...>`, and compositions `(...)`; explained `{}` and `()` as the natural 0-ary special cases; omitted the pattern/filter expressions table from the introductory reference.
|
|
41
36
|
- [x] **Replaced Misleading Expressions & Snippets**:
|
|
42
37
|
- Removed phantom concepts (`10` as literal, "bit-path", `{10 int x, 5 int y} plus` in default state).
|
|
43
|
-
- Added self-contained snippets (`{} | ok`, `not = < / true | false, / false | true >;`,
|
|
38
|
+
- Added self-contained snippets (`{} | ok`, `not = < / true | false, / false | true >;`, `bool = ?< {} true, {} false >;`, `not = bool ?X < / true | false, {} | true > ?X;`, `swap = { . y x, . x y };`).
|
|
44
39
|
- [x] **Command Reference Table**:
|
|
45
40
|
- Added `:time <expr>`.
|
|
46
41
|
- Removed obsolete commands: `:rel <name> = expr`, `:val`, `:timing [on|off]`, `:codec define n t b`.
|
|
47
|
-
-
|
|
42
|
+
- Removed obsolete commands: `:type`, `:types`, `:code`, `:codes`.
|
|
48
43
|
- Timing is now always enabled by default across all evaluations.
|
|
49
44
|
- Updated `:input` documentation to note the interactive browser dialog.
|
|
50
|
-
- Clarified `:
|
|
45
|
+
- Clarified `:rels` (relation aliases).
|
|
51
46
|
|
|
52
47
|
---
|
|
53
48
|
|
|
@@ -56,15 +51,15 @@ This document details the issues, conceptual improvements, and completed enhance
|
|
|
56
51
|
### Concept Correction: External Format Adapters
|
|
57
52
|
- [x] Reframed codecs as format adapters translating external text to/from $k$ values defined as pairs `(filter, tree)`.
|
|
58
53
|
- [x] **Type-Specific Codecs**:
|
|
59
|
-
- `int`: Converts decimal integers to/from
|
|
60
|
-
- `ieee`: Converts decimal floats to/from
|
|
61
|
-
- `utf8`: Converts text to/from
|
|
54
|
+
- `int`: Converts decimal integers to/from `int = ?< bits '+', bits '-' >`.
|
|
55
|
+
- `ieee`: Converts decimal floats to/from `float64` records (`sign`, `exponent`, `fraction`).
|
|
56
|
+
- `utf8`: Converts text to/from `string` (aliased to `utf8`), a list of Unicode scalar values (`unicode`) partitioned by Unicode planes.
|
|
62
57
|
- `unit`: Converts to/from `{}`.
|
|
63
58
|
- [x] **Parameterized Codecs**:
|
|
64
59
|
- `json`: JSON text is untyped; deserializing JSON requires a target $k$ type schema parameter (e.g. `:input {float64 x, string n} json`).
|
|
65
60
|
- [x] **Custom Codec Studio**:
|
|
66
61
|
- Updated explanation to emphasize pairs `(filter, tree)`.
|
|
67
|
-
- Fixed `yn` preset to provide self-contained
|
|
62
|
+
- Fixed `yn` preset to provide self-contained relation definition `bool = ?< {} true, {} false >;`.
|
|
68
63
|
- Fixed `blank` preset with proper Value payload formatting.
|
|
69
64
|
|
|
70
65
|
---
|
|
@@ -105,7 +100,7 @@ This document details the issues, conceptual improvements, and completed enhance
|
|
|
105
100
|
- Verified via headless Chromium CDP automated tests that `#btn-help` is completely visible and interactable at narrow viewport widths (e.g. 600px).
|
|
106
101
|
- [x] **Removed Obsolete Commands**:
|
|
107
102
|
- Removed `:rel <name> = expr` and `:def` (relations are defined using native syntax `name = expr;`).
|
|
108
|
-
- Removed `:type
|
|
103
|
+
- Removed `:type`, `:types`, `:code`, `:codes` commands completely on `no-codes`.
|
|
109
104
|
- Removed `:val` completely.
|
|
110
105
|
- Removed `:timing [on|off]` (timing reporting is now permanently enabled by default for all evaluations; `:time <expr>` remains for explicit timing).
|
|
111
106
|
- Removed `:codec define n t b` (custom codecs are created using the browser Custom Codec Studio UI or loaded from modules via `:codec load`).
|
package/browser/repl-browser.mjs
CHANGED
|
@@ -477,7 +477,7 @@ function showVfsFilePreview(filename) {
|
|
|
477
477
|
function loadPreviewedFile() {
|
|
478
478
|
if (!currentPreviewFile) return;
|
|
479
479
|
closeVfsModal();
|
|
480
|
-
if (currentPreviewFile.endsWith(".mjs") || currentPreviewFile.startsWith("codecs/")) {
|
|
480
|
+
if (currentPreviewFile.endsWith(".mjs") || currentPreviewFile.endsWith(".js") || currentPreviewFile.startsWith("codecs/")) {
|
|
481
481
|
executeCommand(`:codec load ${currentPreviewFile}`);
|
|
482
482
|
} else {
|
|
483
483
|
executeCommand(`:load ${currentPreviewFile}`);
|
|
@@ -498,32 +498,49 @@ function downloadPreviewedFile() {
|
|
|
498
498
|
URL.revokeObjectURL(url);
|
|
499
499
|
}
|
|
500
500
|
|
|
501
|
-
// File Upload Handler
|
|
501
|
+
// File Upload Handler (adds file to VFS without auto-loading)
|
|
502
502
|
function handleFileUpload(file) {
|
|
503
|
-
|
|
504
|
-
|
|
503
|
+
return new Promise((resolve, reject) => {
|
|
504
|
+
const reader = new FileReader();
|
|
505
|
+
const isBinary = file.name.endsWith(".klib") ||
|
|
506
|
+
file.name.endsWith(".ko") ||
|
|
507
|
+
file.name.endsWith(".wasm");
|
|
508
|
+
|
|
509
|
+
reader.onload = (e) => {
|
|
510
|
+
let data;
|
|
511
|
+
if (isBinary) {
|
|
512
|
+
data = new Uint8Array(e.target.result);
|
|
513
|
+
} else {
|
|
514
|
+
data = e.target.result;
|
|
515
|
+
}
|
|
516
|
+
setVfsFile(file.name, data);
|
|
517
|
+
appendSystemMessage(
|
|
518
|
+
`📁 Uploaded <b>${escapeHtml(file.name)}</b> into VFS (` +
|
|
519
|
+
`${(data.length / 1024).toFixed(1)} KB).`,
|
|
520
|
+
false,
|
|
521
|
+
true
|
|
522
|
+
);
|
|
523
|
+
if (vfsModal && vfsModal.classList.contains("open")) {
|
|
524
|
+
renderVfsFileList();
|
|
525
|
+
showVfsFilePreview(file.name);
|
|
526
|
+
}
|
|
527
|
+
resolve();
|
|
528
|
+
};
|
|
529
|
+
|
|
530
|
+
reader.onerror = () => {
|
|
531
|
+
appendSystemMessage(
|
|
532
|
+
`❌ Error reading file: ${file.name}`,
|
|
533
|
+
true
|
|
534
|
+
);
|
|
535
|
+
reject(reader.error || new Error("Failed to read file"));
|
|
536
|
+
};
|
|
505
537
|
|
|
506
|
-
reader.onload = (e) => {
|
|
507
|
-
let data;
|
|
508
538
|
if (isBinary) {
|
|
509
|
-
|
|
539
|
+
reader.readAsArrayBuffer(file);
|
|
510
540
|
} else {
|
|
511
|
-
|
|
541
|
+
reader.readAsText(file);
|
|
512
542
|
}
|
|
513
|
-
|
|
514
|
-
appendSystemMessage(`📁 Uploaded <b>${escapeHtml(file.name)}</b> into VFS (${(data.length / 1024).toFixed(1)} KB).`);
|
|
515
|
-
if (file.name.endsWith("-codec.mjs") || file.name.endsWith("-codec.js") || file.name.includes("codec")) {
|
|
516
|
-
executeCommand(`:codec load ${file.name}`);
|
|
517
|
-
} else {
|
|
518
|
-
executeCommand(`:load ${file.name}`);
|
|
519
|
-
}
|
|
520
|
-
};
|
|
521
|
-
|
|
522
|
-
if (isBinary) {
|
|
523
|
-
reader.readAsArrayBuffer(file);
|
|
524
|
-
} else {
|
|
525
|
-
reader.readAsText(file);
|
|
526
|
-
}
|
|
543
|
+
});
|
|
527
544
|
}
|
|
528
545
|
|
|
529
546
|
// Export State as .klib
|
|
@@ -993,6 +1010,7 @@ if (typeof window !== "undefined") {
|
|
|
993
1010
|
getVfsFile,
|
|
994
1011
|
setVfsFile,
|
|
995
1012
|
getAllVfsFiles,
|
|
1013
|
+
handleFileUpload,
|
|
996
1014
|
openCodecsModal,
|
|
997
1015
|
registerCodec,
|
|
998
1016
|
unregisterCodec
|
package/browser/shims/fs.mjs
CHANGED
|
@@ -25,10 +25,7 @@ function cleanPath(p) {
|
|
|
25
25
|
}
|
|
26
26
|
|
|
27
27
|
export function setVfsFile(path, content) {
|
|
28
|
-
|
|
29
|
-
if (cleaned.endsWith(".mjs") && !cleaned.startsWith("codecs/")) {
|
|
30
|
-
cleaned = `codecs/${cleaned}`;
|
|
31
|
-
}
|
|
28
|
+
const cleaned = cleanPath(path);
|
|
32
29
|
vfs.set(cleaned, content);
|
|
33
30
|
}
|
|
34
31
|
|
|
@@ -58,11 +55,11 @@ const CURATED_VFS_FILES = [
|
|
|
58
55
|
"ieee.k",
|
|
59
56
|
"poly.k",
|
|
60
57
|
"karatsuba-mult.k",
|
|
61
|
-
"
|
|
62
|
-
"
|
|
63
|
-
"
|
|
64
|
-
"
|
|
65
|
-
"
|
|
58
|
+
"json.mjs",
|
|
59
|
+
"utf8.mjs",
|
|
60
|
+
"int.mjs",
|
|
61
|
+
"unit.mjs",
|
|
62
|
+
"ieee.mjs"
|
|
66
63
|
];
|
|
67
64
|
|
|
68
65
|
export function getAllVfsFiles() {
|
|
@@ -74,7 +71,7 @@ export function getAllVfsFiles() {
|
|
|
74
71
|
}
|
|
75
72
|
for (const key of vfs.keys()) {
|
|
76
73
|
if (key.endsWith("runtime.wat") || key.startsWith("backends/")) continue;
|
|
77
|
-
if (key.startsWith("Examples/")) continue;
|
|
74
|
+
if (key.startsWith("Examples/") || key.startsWith("codecs/")) continue;
|
|
78
75
|
result.add(key);
|
|
79
76
|
}
|
|
80
77
|
return Array.from(result);
|