@thomasfosterau/effect-parse 0.1.0 → 0.2.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/README.md +247 -230
- package/dist/Ascii.d.ts +32 -53
- package/dist/Ascii.d.ts.map +1 -1
- package/dist/Ascii.js +576 -571
- package/dist/Ascii.js.map +1 -1
- package/dist/Binary.d.ts +6 -29
- package/dist/Binary.d.ts.map +1 -1
- package/dist/Binary.js +129 -116
- package/dist/Binary.js.map +1 -1
- package/dist/Bits.d.ts +4 -2
- package/dist/Bits.d.ts.map +1 -1
- package/dist/Bits.js +121 -123
- package/dist/Bits.js.map +1 -1
- package/dist/Compiler.d.ts +39 -0
- package/dist/Compiler.d.ts.map +1 -0
- package/dist/Compiler.js +48 -0
- package/dist/Compiler.js.map +1 -0
- package/dist/Encoding.d.ts +29 -46
- package/dist/Encoding.d.ts.map +1 -1
- package/dist/Encoding.js +76 -75
- package/dist/Encoding.js.map +1 -1
- package/dist/Expression.d.ts +15 -49
- package/dist/Expression.d.ts.map +1 -1
- package/dist/Expression.js +143 -131
- package/dist/Expression.js.map +1 -1
- package/dist/Input.d.ts +206 -177
- package/dist/Input.d.ts.map +1 -1
- package/dist/Input.js +317 -299
- package/dist/Input.js.map +1 -1
- package/dist/Nom.d.ts +44 -84
- package/dist/Nom.d.ts.map +1 -1
- package/dist/Nom.js +423 -453
- package/dist/Nom.js.map +1 -1
- package/dist/ParseError.d.ts +54 -49
- package/dist/ParseError.d.ts.map +1 -1
- package/dist/ParseError.js +233 -275
- package/dist/ParseError.js.map +1 -1
- package/dist/Parser.d.ts +345 -313
- package/dist/Parser.d.ts.map +1 -1
- package/dist/Parser.js +2010 -1802
- package/dist/Parser.js.map +1 -1
- package/dist/ParserSchema.d.ts +8 -7
- package/dist/ParserSchema.d.ts.map +1 -1
- package/dist/ParserSchema.js +49 -49
- package/dist/ParserSchema.js.map +1 -1
- package/dist/ParserStream.d.ts +26 -20
- package/dist/ParserStream.d.ts.map +1 -1
- package/dist/ParserStream.js +267 -255
- package/dist/ParserStream.js.map +1 -1
- package/dist/Syntax.d.ts +401 -0
- package/dist/Syntax.d.ts.map +1 -0
- package/dist/Syntax.js +717 -0
- package/dist/Syntax.js.map +1 -0
- package/dist/Text.d.ts +98 -134
- package/dist/Text.d.ts.map +1 -1
- package/dist/Text.js +534 -496
- package/dist/Text.js.map +1 -1
- package/dist/Token.d.ts +60 -42
- package/dist/Token.d.ts.map +1 -1
- package/dist/Token.js +331 -265
- package/dist/Token.js.map +1 -1
- package/dist/index.d.ts +16 -17
- package/dist/index.js +16 -17
- package/dist/internal/compiler/closure.d.ts +14 -16
- package/dist/internal/compiler/closure.d.ts.map +1 -1
- package/dist/internal/compiler/closure.js +1458 -1637
- package/dist/internal/compiler/closure.js.map +1 -1
- package/dist/internal/compiler/entries.d.ts +11 -11
- package/dist/internal/compiler/entries.d.ts.map +1 -1
- package/dist/internal/compiler/entries.js +36 -26
- package/dist/internal/compiler/entries.js.map +1 -1
- package/dist/internal/compiler/first.d.ts +19 -19
- package/dist/internal/compiler/first.d.ts.map +1 -1
- package/dist/internal/compiler/first.js +251 -227
- package/dist/internal/compiler/first.js.map +1 -1
- package/dist/internal/compiler/jit.d.ts +6 -17
- package/dist/internal/compiler/jit.d.ts.map +1 -1
- package/dist/internal/compiler/jit.js +860 -988
- package/dist/internal/compiler/jit.js.map +1 -1
- package/dist/internal/compiler/registry.d.ts +20 -21
- package/dist/internal/compiler/registry.d.ts.map +1 -1
- package/dist/internal/compiler/registry.js +21 -41
- package/dist/internal/compiler/registry.js.map +1 -1
- package/dist/internal/compiler/sets.d.ts +9 -13
- package/dist/internal/compiler/sets.d.ts.map +1 -1
- package/dist/internal/compiler/sets.js +76 -73
- package/dist/internal/compiler/sets.js.map +1 -1
- package/dist/internal/entries.d.ts +3 -3
- package/dist/internal/entries.d.ts.map +1 -1
- package/dist/internal/entries.js +38 -30
- package/dist/internal/entries.js.map +1 -1
- package/dist/internal/node.d.ts +177 -173
- package/dist/internal/node.d.ts.map +1 -1
- package/dist/internal/node.js +77 -66
- package/dist/internal/node.js.map +1 -1
- package/dist/internal/numbers.d.ts +7 -8
- package/dist/internal/numbers.d.ts.map +1 -1
- package/dist/internal/numbers.js +246 -276
- package/dist/internal/numbers.js.map +1 -1
- package/dist/internal/resume.d.ts +6 -24
- package/dist/internal/resume.d.ts.map +1 -1
- package/dist/internal/resume.js +30 -29
- package/dist/internal/resume.js.map +1 -1
- package/dist/internal/run.d.ts +15 -0
- package/dist/internal/run.d.ts.map +1 -0
- package/dist/internal/run.js +36 -0
- package/dist/internal/run.js.map +1 -0
- package/dist/internal/stack.d.ts +16 -0
- package/dist/internal/stack.d.ts.map +1 -0
- package/dist/internal/stack.js +26 -0
- package/dist/internal/stack.js.map +1 -0
- package/dist/internal/syntax.d.ts +146 -0
- package/dist/internal/syntax.d.ts.map +1 -0
- package/dist/internal/syntax.js +305 -0
- package/dist/internal/syntax.js.map +1 -0
- package/dist/internal/text.d.ts +10 -2
- package/dist/internal/text.d.ts.map +1 -1
- package/dist/internal/text.js +295 -345
- package/dist/internal/text.js.map +1 -1
- package/dist/internal/tokens.d.ts +25 -30
- package/dist/internal/tokens.d.ts.map +1 -1
- package/dist/internal/tokens.js +369 -363
- package/dist/internal/tokens.js.map +1 -1
- package/package.json +42 -28
- package/src/Ascii.ts +278 -187
- package/src/Binary.ts +150 -44
- package/src/Bits.ts +6 -3
- package/src/Compiler.ts +98 -0
- package/src/Expression.ts +10 -5
- package/src/Input.ts +106 -28
- package/src/Nom.ts +4 -3
- package/src/ParseError.ts +48 -51
- package/src/Parser.ts +1163 -795
- package/src/ParserStream.ts +104 -80
- package/src/Syntax.ts +900 -0
- package/src/Text.ts +272 -187
- package/src/Token.ts +180 -87
- package/src/index.ts +2 -0
- package/src/internal/compiler/closure.ts +121 -88
- package/src/internal/compiler/entries.ts +21 -8
- package/src/internal/compiler/first.ts +17 -15
- package/src/internal/compiler/jit.ts +360 -157
- package/src/internal/compiler/registry.ts +12 -33
- package/src/internal/compiler/sets.ts +17 -11
- package/src/internal/entries.ts +4 -2
- package/src/internal/node.ts +51 -37
- package/src/internal/numbers.ts +22 -20
- package/src/internal/resume.ts +8 -4
- package/src/internal/run.ts +41 -0
- package/src/internal/stack.ts +36 -0
- package/src/internal/syntax.ts +421 -0
- package/src/internal/text.ts +32 -25
- package/src/internal/tokens.ts +96 -51
- package/dist/index.d.ts.map +0 -1
- package/dist/index.js.map +0 -1
package/dist/internal/tokens.js
CHANGED
|
@@ -1,400 +1,406 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
1
|
+
import * as Predicate from "effect/Predicate";
|
|
2
|
+
import { charOf, firstCodePoint } from "./text.js";
|
|
3
|
+
//#region src/internal/tokens.ts
|
|
4
|
+
const isRange = (u) => Predicate.isObjectOrArray(u) && u._tag === "TokenRange";
|
|
5
|
+
const toCode = (u) => Predicate.isNumber(u) ? u : firstCodePoint(u);
|
|
3
6
|
/** @internal */
|
|
4
|
-
|
|
7
|
+
const describeChar = (s) => JSON.stringify(s);
|
|
5
8
|
const describeSet = (u) => {
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
return u.name ? u.name : "a matching token";
|
|
14
|
-
if (u instanceof Uint8Array)
|
|
15
|
-
return `one of ${describeBytes(u)}`;
|
|
16
|
-
if (isRange(u))
|
|
17
|
-
return `${describeSet(u.from)}..=${describeSet(u.to)}`;
|
|
18
|
-
if (Array.isArray(u))
|
|
19
|
-
return u.map(describeSet).join(" or ");
|
|
20
|
-
return JSON.stringify(u);
|
|
9
|
+
if (Predicate.isString(u)) return Array.from(u).length === 1 ? describeChar(u) : `one of ${JSON.stringify(u)}`;
|
|
10
|
+
if (Predicate.isNumber(u)) return `0x${u.toString(16).padStart(2, "0")}`;
|
|
11
|
+
if (Predicate.isFunction(u)) return u.name ? u.name : "a matching token";
|
|
12
|
+
if (u instanceof Uint8Array) return `one of ${describeBytes(u)}`;
|
|
13
|
+
if (isRange(u)) return `${describeSet(u.from)}..=${describeSet(u.to)}`;
|
|
14
|
+
if (Array.isArray(u)) return u.map(describeSet).join(" or ");
|
|
15
|
+
return JSON.stringify(u);
|
|
21
16
|
};
|
|
22
17
|
/** Renders bytes as a Rust-style byte string literal: b"GET\r\n". */
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
out += "\\r";
|
|
34
|
-
else if (b === 0x09)
|
|
35
|
-
out += "\\t";
|
|
36
|
-
else if (b >= 0x20 && b < 0x7f)
|
|
37
|
-
out += String.fromCharCode(b);
|
|
38
|
-
else
|
|
39
|
-
out += `\\x${b.toString(16).padStart(2, "0")}`;
|
|
40
|
-
}
|
|
41
|
-
return out + "\"";
|
|
18
|
+
const describeBytes = (bytes) => {
|
|
19
|
+
let out = "b\"";
|
|
20
|
+
for (const b of bytes) if (b === 34) out += "\\\"";
|
|
21
|
+
else if (b === 92) out += "\\\\";
|
|
22
|
+
else if (b === 10) out += "\\n";
|
|
23
|
+
else if (b === 13) out += "\\r";
|
|
24
|
+
else if (b === 9) out += "\\t";
|
|
25
|
+
else if (b >= 32 && b < 127) out += String.fromCharCode(b);
|
|
26
|
+
else out += `\\x${b.toString(16).padStart(2, "0")}`;
|
|
27
|
+
return out + "\"";
|
|
42
28
|
};
|
|
43
29
|
const compileCode = (u) => {
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
if (tests[i](x))
|
|
70
|
-
return true;
|
|
71
|
-
return false;
|
|
72
|
-
};
|
|
73
|
-
}
|
|
74
|
-
throw new TypeError(`invalid token set: ${String(u)}`);
|
|
30
|
+
if (Predicate.isString(u)) {
|
|
31
|
+
const codes = Array.from(u, firstCodePoint);
|
|
32
|
+
if (codes.length === 1) {
|
|
33
|
+
const c = codes[0];
|
|
34
|
+
return (x) => x === c;
|
|
35
|
+
}
|
|
36
|
+
return bitmap(codes);
|
|
37
|
+
}
|
|
38
|
+
if (Predicate.isNumber(u)) return (x) => x === u;
|
|
39
|
+
if (Predicate.isFunction(u)) return u;
|
|
40
|
+
if (u instanceof Uint8Array) return bitmap(Array.from(u));
|
|
41
|
+
if (isRange(u)) {
|
|
42
|
+
const from = toCode(u.from);
|
|
43
|
+
const to = toCode(u.to);
|
|
44
|
+
return (x) => x >= from && x <= to;
|
|
45
|
+
}
|
|
46
|
+
if (Array.isArray(u)) {
|
|
47
|
+
const tests = u.map(compileCode);
|
|
48
|
+
if (tests.length === 1) return tests[0];
|
|
49
|
+
return (x) => {
|
|
50
|
+
for (let i = 0; i < tests.length; i++) if (tests[i](x)) return true;
|
|
51
|
+
return false;
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
throw new TypeError(`invalid token set: ${String(u)}`);
|
|
75
55
|
};
|
|
76
56
|
const bitmap = (codes) => {
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
}
|
|
85
|
-
if (other === undefined)
|
|
86
|
-
return (x) => x < 256 && ascii[x] === 1;
|
|
87
|
-
const set = other;
|
|
88
|
-
return (x) => x < 256 ? ascii[x] === 1 : set.has(x);
|
|
57
|
+
const ascii = /* @__PURE__ */ new Uint8Array(256);
|
|
58
|
+
let other;
|
|
59
|
+
for (const c of codes) if (c < 256) ascii[c] = 1;
|
|
60
|
+
else (other ??= /* @__PURE__ */ new Set()).add(c);
|
|
61
|
+
if (other === void 0) return (x) => x < 256 && ascii[x] === 1;
|
|
62
|
+
const set = other;
|
|
63
|
+
return (x) => x < 256 ? ascii[x] === 1 : set.has(x);
|
|
89
64
|
};
|
|
90
65
|
const compileToken = (u) => {
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
return (t) => t === u;
|
|
66
|
+
if (Predicate.isFunction(u)) return u;
|
|
67
|
+
if (Array.isArray(u)) {
|
|
68
|
+
const set = new Set(u);
|
|
69
|
+
return (t) => set.has(t);
|
|
70
|
+
}
|
|
71
|
+
return (t) => t === u;
|
|
98
72
|
};
|
|
99
73
|
/**
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
74
|
+
* Marks a predicate over characters that also accepts a code point (a
|
|
75
|
+
* number), so string inputs can call it without allocating a string per
|
|
76
|
+
* character.
|
|
77
|
+
*/
|
|
78
|
+
const CodePointPredicate = /*#__PURE__*/ Symbol.for("effect-parse/CodePointPredicate");
|
|
105
79
|
/**
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
80
|
+
* The code points accepted by a predicate, as sorted, disjoint, inclusive
|
|
81
|
+
* ranges, when they are known. The compiler turns such predicates into
|
|
82
|
+
* comparisons or tables.
|
|
83
|
+
*/
|
|
84
|
+
const PredicateRanges = /*#__PURE__*/ Symbol.for("effect-parse/PredicateRanges");
|
|
111
85
|
/**
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
return f;
|
|
86
|
+
* Marks `f` as a {@link CodePointPredicate} named `name` (used in error
|
|
87
|
+
* messages), optionally recording the code point ranges it accepts.
|
|
88
|
+
*/
|
|
89
|
+
const codePointPredicate = (name, f, ranges) => {
|
|
90
|
+
Object.defineProperty(f, "name", { value: name });
|
|
91
|
+
f[CodePointPredicate] = true;
|
|
92
|
+
if (ranges !== void 0) f[PredicateRanges] = ranges;
|
|
93
|
+
return f;
|
|
121
94
|
};
|
|
122
95
|
/**
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
96
|
+
* Compiles a token set. Predicates for string inputs receive the token as a
|
|
97
|
+
* string, so they are wrapped here; `charOf` avoids `String.fromCodePoint`,
|
|
98
|
+
* which is several times slower, for the Basic Multilingual Plane.
|
|
99
|
+
*/
|
|
100
|
+
const compile = (set, kind = "code") => {
|
|
101
|
+
const description = describeSet(set);
|
|
102
|
+
let code;
|
|
103
|
+
if (Predicate.isFunction(set) && kind === "string" && !(CodePointPredicate in set)) {
|
|
104
|
+
const pred = set;
|
|
105
|
+
code = (x) => pred(charOf(x));
|
|
106
|
+
} else code = compileCodeSafe(set, kind);
|
|
107
|
+
return {
|
|
108
|
+
code,
|
|
109
|
+
token: compileToken(set),
|
|
110
|
+
description
|
|
111
|
+
};
|
|
137
112
|
};
|
|
138
113
|
const compileCodeSafe = (set, kind) => {
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
}
|
|
152
|
-
catch {
|
|
153
|
-
return () => false;
|
|
154
|
-
}
|
|
114
|
+
if (Array.isArray(set) && kind === "string") {
|
|
115
|
+
const tests = set.map((s) => compile(s, kind).code);
|
|
116
|
+
return (x) => {
|
|
117
|
+
for (let i = 0; i < tests.length; i++) if (tests[i](x)) return true;
|
|
118
|
+
return false;
|
|
119
|
+
};
|
|
120
|
+
}
|
|
121
|
+
try {
|
|
122
|
+
return compileCode(set);
|
|
123
|
+
} catch {
|
|
124
|
+
return () => false;
|
|
125
|
+
}
|
|
155
126
|
};
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
127
|
+
/**
|
|
128
|
+
* A small cache keyed by value, for the parts of a parser that are costly to
|
|
129
|
+
* build and depend only on a string (compiled sets, descriptions). Parsers
|
|
130
|
+
* built inside `Parser.gen` bodies are rebuilt on every run, usually from the
|
|
131
|
+
* same few strings. Dynamic strings could grow it without bound, so it is
|
|
132
|
+
* cleared when full.
|
|
133
|
+
*/
|
|
134
|
+
const cached = (cache, key, build) => {
|
|
135
|
+
let a = cache.get(key);
|
|
136
|
+
if (a === void 0) {
|
|
137
|
+
if (cache.size >= 1024) cache.clear();
|
|
138
|
+
a = build(key);
|
|
139
|
+
cache.set(key, a);
|
|
140
|
+
}
|
|
141
|
+
return a;
|
|
142
|
+
};
|
|
143
|
+
const literalDescriptions = /*#__PURE__*/ new Map();
|
|
144
|
+
/** Describes a literal for error messages: `"abc"`, `b"abc"` or `["a", 1]`. */
|
|
145
|
+
const describeLiteral = (lit) => Predicate.isString(lit) ? cached(literalDescriptions, lit, describeChar) : lit instanceof Uint8Array ? describeBytes(lit) : `[${lit.map((t) => JSON.stringify(t)).join(", ")}]`;
|
|
146
|
+
const stringMatchers = /*#__PURE__*/ new Map();
|
|
147
|
+
const compileAny = (set) => Predicate.isString(set) ? cached(stringMatchers, set, compileAnyImpl) : compileAnyImpl(set);
|
|
148
|
+
const compileAnyImpl = (set) => {
|
|
149
|
+
const forCode = compile(set, "code");
|
|
150
|
+
return {
|
|
151
|
+
forString: Predicate.isFunction(set) || Array.isArray(set) ? compile(set, "string") : forCode,
|
|
152
|
+
forCode,
|
|
153
|
+
description: forCode.description
|
|
154
|
+
};
|
|
164
155
|
};
|
|
165
156
|
/**
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
return c >= 0xd800 && c <= 0xdbff;
|
|
157
|
+
* Whether the string token at `i` is a high surrogate at the very end of a
|
|
158
|
+
* partial input, i.e. the first half of a code point whose second half has
|
|
159
|
+
* not arrived yet.
|
|
160
|
+
*/
|
|
161
|
+
const splitSurrogate = (state, i) => {
|
|
162
|
+
if (!state.partial || i !== state.end - 1) return false;
|
|
163
|
+
const c = state.input.charCodeAt(i);
|
|
164
|
+
return c >= 55296 && c <= 56319;
|
|
175
165
|
};
|
|
176
166
|
/** Reads the code point at `i` of a string. */
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
return c;
|
|
167
|
+
const codePointAt = (s, i) => {
|
|
168
|
+
const c = s.charCodeAt(i);
|
|
169
|
+
if (c >= 55296 && c <= 56319 && i + 1 < s.length) {
|
|
170
|
+
const d = s.charCodeAt(i + 1);
|
|
171
|
+
if (d >= 56320 && d <= 57343) return (c - 55296 << 10) + (d - 56320) + 65536;
|
|
172
|
+
}
|
|
173
|
+
return c;
|
|
185
174
|
};
|
|
186
175
|
/**
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
return NoMatch;
|
|
219
|
-
state.pos = pos + 1;
|
|
220
|
-
return t;
|
|
221
|
-
}
|
|
222
|
-
}
|
|
176
|
+
* Tests the token at the current position. Returns the token (as the input's
|
|
177
|
+
* token type) and advances, or returns `NoMatch`/`End`.
|
|
178
|
+
*/
|
|
179
|
+
const NoMatch = /*#__PURE__*/ Symbol("NoMatch");
|
|
180
|
+
const End = /*#__PURE__*/ Symbol("End");
|
|
181
|
+
const nextIf = (state, m, negate) => {
|
|
182
|
+
const pos = state.pos;
|
|
183
|
+
if (pos >= state.end) return End;
|
|
184
|
+
switch (state.inputKind) {
|
|
185
|
+
case 0: {
|
|
186
|
+
const s = state.input;
|
|
187
|
+
if (splitSurrogate(state, pos)) return End;
|
|
188
|
+
const cp = codePointAt(s, pos);
|
|
189
|
+
if (m.forString.code(cp) === negate) return NoMatch;
|
|
190
|
+
const len = cp > 65535 ? 2 : 1;
|
|
191
|
+
state.pos = pos + len;
|
|
192
|
+
return len === 1 ? s[pos] : s.slice(pos, pos + 2);
|
|
193
|
+
}
|
|
194
|
+
case 1: {
|
|
195
|
+
const b = state.input[pos];
|
|
196
|
+
if (m.forCode.code(b) === negate) return NoMatch;
|
|
197
|
+
state.pos = pos + 1;
|
|
198
|
+
return b;
|
|
199
|
+
}
|
|
200
|
+
default: {
|
|
201
|
+
const t = state.input[pos];
|
|
202
|
+
if (m.forCode.token(t) === negate) return NoMatch;
|
|
203
|
+
state.pos = pos + 1;
|
|
204
|
+
return t;
|
|
205
|
+
}
|
|
206
|
+
}
|
|
223
207
|
};
|
|
224
208
|
/**
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
209
|
+
* Scans forward while tokens satisfy the matcher (xor `negate`), up to `max`
|
|
210
|
+
* tokens. Returns the offset reached, the number of tokens matched, and
|
|
211
|
+
* whether the end of input was hit before `max` tokens.
|
|
212
|
+
*/
|
|
213
|
+
const scan = (state, m, negate, max) => {
|
|
214
|
+
let i = state.pos;
|
|
215
|
+
const end = state.end;
|
|
216
|
+
let count = 0;
|
|
217
|
+
switch (state.inputKind) {
|
|
218
|
+
case 0: {
|
|
219
|
+
const s = state.input;
|
|
220
|
+
const test = m.forString.code;
|
|
221
|
+
while (count < max) {
|
|
222
|
+
if (i >= end) return {
|
|
223
|
+
offset: i,
|
|
224
|
+
count,
|
|
225
|
+
hitEnd: true
|
|
226
|
+
};
|
|
227
|
+
const c = s.charCodeAt(i);
|
|
228
|
+
if (c < 55296 || c > 56319) {
|
|
229
|
+
if (test(c) === negate) break;
|
|
230
|
+
i++;
|
|
231
|
+
} else {
|
|
232
|
+
if (splitSurrogate(state, i)) return {
|
|
233
|
+
offset: i,
|
|
234
|
+
count,
|
|
235
|
+
hitEnd: true
|
|
236
|
+
};
|
|
237
|
+
const cp = codePointAt(s, i);
|
|
238
|
+
if (test(cp) === negate) break;
|
|
239
|
+
i += cp > 65535 ? 2 : 1;
|
|
240
|
+
}
|
|
241
|
+
count++;
|
|
242
|
+
}
|
|
243
|
+
return {
|
|
244
|
+
offset: i,
|
|
245
|
+
count,
|
|
246
|
+
hitEnd: false
|
|
247
|
+
};
|
|
248
|
+
}
|
|
249
|
+
case 1: {
|
|
250
|
+
const bytes = state.input;
|
|
251
|
+
const test = m.forCode.code;
|
|
252
|
+
while (count < max) {
|
|
253
|
+
if (i >= end) return {
|
|
254
|
+
offset: i,
|
|
255
|
+
count,
|
|
256
|
+
hitEnd: true
|
|
257
|
+
};
|
|
258
|
+
if (test(bytes[i]) === negate) break;
|
|
259
|
+
i++;
|
|
260
|
+
count++;
|
|
261
|
+
}
|
|
262
|
+
return {
|
|
263
|
+
offset: i,
|
|
264
|
+
count,
|
|
265
|
+
hitEnd: false
|
|
266
|
+
};
|
|
267
|
+
}
|
|
268
|
+
default: {
|
|
269
|
+
const arr = state.input;
|
|
270
|
+
const test = m.forCode.token;
|
|
271
|
+
while (count < max) {
|
|
272
|
+
if (i >= end) return {
|
|
273
|
+
offset: i,
|
|
274
|
+
count,
|
|
275
|
+
hitEnd: true
|
|
276
|
+
};
|
|
277
|
+
if (test(arr[i]) === negate) break;
|
|
278
|
+
i++;
|
|
279
|
+
count++;
|
|
280
|
+
}
|
|
281
|
+
return {
|
|
282
|
+
offset: i,
|
|
283
|
+
count,
|
|
284
|
+
hitEnd: false
|
|
285
|
+
};
|
|
286
|
+
}
|
|
287
|
+
}
|
|
285
288
|
};
|
|
286
289
|
/** Advances `n` tokens from `start`, returning the offset reached and the count. */
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
290
|
+
const advance = (state, start, n) => {
|
|
291
|
+
if (state.inputKind !== 0) {
|
|
292
|
+
const offset = Math.min(state.end, start + n);
|
|
293
|
+
return {
|
|
294
|
+
offset,
|
|
295
|
+
count: offset - start
|
|
296
|
+
};
|
|
297
|
+
}
|
|
298
|
+
const s = state.input;
|
|
299
|
+
let i = start;
|
|
300
|
+
let count = 0;
|
|
301
|
+
while (count < n && i < state.end) {
|
|
302
|
+
if (splitSurrogate(state, i)) break;
|
|
303
|
+
const c = s.charCodeAt(i);
|
|
304
|
+
i += c >= 55296 && c <= 56319 && i + 1 < s.length && (s.charCodeAt(i + 1) & 64512) === 56320 ? 2 : 1;
|
|
305
|
+
count++;
|
|
306
|
+
}
|
|
307
|
+
return {
|
|
308
|
+
offset: i,
|
|
309
|
+
count
|
|
310
|
+
};
|
|
303
311
|
};
|
|
304
312
|
/** Counts tokens between two offsets. */
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
}
|
|
316
|
-
return count;
|
|
313
|
+
const countTokens = (state, start, end) => {
|
|
314
|
+
if (state.inputKind !== 0) return end - start;
|
|
315
|
+
const s = state.input;
|
|
316
|
+
let count = 0;
|
|
317
|
+
for (let i = start; i < end; i++) {
|
|
318
|
+
const c = s.charCodeAt(i);
|
|
319
|
+
if (c >= 55296 && c <= 56319 && i + 1 < end && (s.charCodeAt(i + 1) & 64512) === 56320) i++;
|
|
320
|
+
count++;
|
|
321
|
+
}
|
|
322
|
+
return count;
|
|
317
323
|
};
|
|
318
|
-
/** Finds `needle`
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
}
|
|
324
|
+
/** Finds `needle` within `[from, state.end)`; returns -1 if absent. */
|
|
325
|
+
const indexOf = (state, needle, from) => {
|
|
326
|
+
const last = state.end - needle.length;
|
|
327
|
+
if (from > last) return -1;
|
|
328
|
+
switch (state.inputKind) {
|
|
329
|
+
case 0: {
|
|
330
|
+
const i = state.input.indexOf(needle, from);
|
|
331
|
+
return i <= last ? i : -1;
|
|
332
|
+
}
|
|
333
|
+
case 1: {
|
|
334
|
+
const hay = state.input;
|
|
335
|
+
const n = needle;
|
|
336
|
+
if (n.length === 0) return from;
|
|
337
|
+
const first = n[0];
|
|
338
|
+
let i = hay.indexOf(first, from);
|
|
339
|
+
while (i !== -1 && i <= last) {
|
|
340
|
+
let j = 1;
|
|
341
|
+
while (j < n.length && hay[i + j] === n[j]) j++;
|
|
342
|
+
if (j === n.length) return i;
|
|
343
|
+
i = hay.indexOf(first, i + 1);
|
|
344
|
+
}
|
|
345
|
+
return -1;
|
|
346
|
+
}
|
|
347
|
+
default: {
|
|
348
|
+
const hay = state.input;
|
|
349
|
+
const n = needle;
|
|
350
|
+
outer: for (let i = from; i <= last; i++) {
|
|
351
|
+
for (let j = 0; j < n.length; j++) if (hay[i + j] !== n[j]) continue outer;
|
|
352
|
+
return i;
|
|
353
|
+
}
|
|
354
|
+
return -1;
|
|
355
|
+
}
|
|
356
|
+
}
|
|
352
357
|
};
|
|
353
358
|
/**
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
}
|
|
397
|
-
}
|
|
359
|
+
* Compares the input at the current position with a literal. Returns the
|
|
360
|
+
* number of matching units if the literal matches completely (its length),
|
|
361
|
+
* -1 on mismatch, or -2 when the input ends while matching a prefix.
|
|
362
|
+
*/
|
|
363
|
+
const matchLiteral = (state, lit, caseless) => {
|
|
364
|
+
const r = match(state, lit, caseless);
|
|
365
|
+
if (r < 0 && state.syntax !== void 0) state.syntax.read(state.pos + Math.min(lit.length, state.end - state.pos));
|
|
366
|
+
return r;
|
|
367
|
+
};
|
|
368
|
+
const match = (state, lit, caseless) => {
|
|
369
|
+
const pos = state.pos;
|
|
370
|
+
const len = lit.length;
|
|
371
|
+
const avail = state.end - pos;
|
|
372
|
+
const n = Math.min(len, avail);
|
|
373
|
+
switch (state.inputKind) {
|
|
374
|
+
case 0: {
|
|
375
|
+
const s = state.input;
|
|
376
|
+
const l = lit;
|
|
377
|
+
if (!caseless) {
|
|
378
|
+
if (avail >= len) return s.startsWith(l, pos) ? len : -1;
|
|
379
|
+
return l.startsWith(s.slice(pos)) ? -2 : -1;
|
|
380
|
+
}
|
|
381
|
+
for (let i = 0; i < n; i++) if (lowerAscii(s.charCodeAt(pos + i)) !== lowerAscii(l.charCodeAt(i))) return -1;
|
|
382
|
+
return n === len ? len : -2;
|
|
383
|
+
}
|
|
384
|
+
case 1: {
|
|
385
|
+
const b = state.input;
|
|
386
|
+
const l = lit;
|
|
387
|
+
for (let i = 0; i < n; i++) {
|
|
388
|
+
const x = b[pos + i];
|
|
389
|
+
const y = l[i];
|
|
390
|
+
if (caseless ? lowerAscii(x) !== lowerAscii(y) : x !== y) return -1;
|
|
391
|
+
}
|
|
392
|
+
return n === len ? len : -2;
|
|
393
|
+
}
|
|
394
|
+
default: {
|
|
395
|
+
const a = state.input;
|
|
396
|
+
const l = lit;
|
|
397
|
+
for (let i = 0; i < n; i++) if (a[pos + i] !== l[i]) return -1;
|
|
398
|
+
return n === len ? len : -2;
|
|
399
|
+
}
|
|
400
|
+
}
|
|
398
401
|
};
|
|
399
402
|
const lowerAscii = (c) => c >= 65 && c <= 90 ? c + 32 : c;
|
|
403
|
+
//#endregion
|
|
404
|
+
export { End, NoMatch, PredicateRanges, advance, codePointPredicate, compile, compileAny, countTokens, describeChar, describeLiteral, indexOf, matchLiteral, nextIf, scan, splitSurrogate };
|
|
405
|
+
|
|
400
406
|
//# sourceMappingURL=tokens.js.map
|