parseman 0.28.1 → 0.29.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/dist/compiler/codegen.d.ts +23 -0
- package/dist/compiler/codegen.d.ts.map +1 -1
- package/dist/compiler/linker.d.ts +10 -0
- package/dist/compiler/linker.d.ts.map +1 -1
- package/dist/index.cjs +109 -2
- package/dist/index.cjs.map +3 -3
- package/dist/index.js +109 -2
- package/dist/index.js.map +3 -3
- package/dist/language-service/index.cjs.map +2 -2
- package/dist/language-service/index.js.map +2 -2
- package/dist/plugin/index.cjs +110 -3
- package/dist/plugin/index.cjs.map +3 -3
- package/dist/plugin/index.d.ts.map +1 -1
- package/dist/plugin/index.js +110 -3
- package/dist/plugin/index.js.map +3 -3
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -4140,6 +4140,61 @@ function tryInlineDestructureTransform(src, valueVars) {
|
|
|
4140
4140
|
}
|
|
4141
4141
|
|
|
4142
4142
|
// src/compiler/codegen.ts
|
|
4143
|
+
function leadingFirstSetRecipe(p, seen = /* @__PURE__ */ new Set()) {
|
|
4144
|
+
if (seen.has(p)) return { concrete: empty(), refs: [] };
|
|
4145
|
+
seen.add(p);
|
|
4146
|
+
const d = p._def;
|
|
4147
|
+
const rec = (c) => leadingFirstSetRecipe(c, seen);
|
|
4148
|
+
const merge2 = (a, b) => ({ concrete: union(a.concrete, b.concrete), refs: [...a.refs, ...b.refs] });
|
|
4149
|
+
switch (d.tag) {
|
|
4150
|
+
case "lazy": {
|
|
4151
|
+
const name = p._ruleName;
|
|
4152
|
+
if (name !== void 0) return { concrete: empty(), refs: [name] };
|
|
4153
|
+
try {
|
|
4154
|
+
return rec(d.thunk());
|
|
4155
|
+
} catch {
|
|
4156
|
+
return { concrete: any(), refs: [] };
|
|
4157
|
+
}
|
|
4158
|
+
}
|
|
4159
|
+
case "literal":
|
|
4160
|
+
case "regex":
|
|
4161
|
+
case "keywords":
|
|
4162
|
+
return { concrete: p._meta.firstSet, refs: [] };
|
|
4163
|
+
case "choice": {
|
|
4164
|
+
let out = { concrete: empty(), refs: [] };
|
|
4165
|
+
for (const arm of d.parsers) out = merge2(out, rec(arm));
|
|
4166
|
+
return out;
|
|
4167
|
+
}
|
|
4168
|
+
case "sequence": {
|
|
4169
|
+
let out = { concrete: empty(), refs: [] };
|
|
4170
|
+
for (const term of d.parsers) {
|
|
4171
|
+
out = merge2(out, rec(term));
|
|
4172
|
+
if (!matchesEmpty(term)) return out;
|
|
4173
|
+
}
|
|
4174
|
+
return out;
|
|
4175
|
+
}
|
|
4176
|
+
case "oneOrMore":
|
|
4177
|
+
case "many":
|
|
4178
|
+
case "optional":
|
|
4179
|
+
case "transform":
|
|
4180
|
+
case "label":
|
|
4181
|
+
case "field":
|
|
4182
|
+
case "trivia":
|
|
4183
|
+
case "token":
|
|
4184
|
+
case "leaf":
|
|
4185
|
+
case "node":
|
|
4186
|
+
case "grammar":
|
|
4187
|
+
case "expect":
|
|
4188
|
+
return rec(d.parser);
|
|
4189
|
+
case "sepBy":
|
|
4190
|
+
return rec(d.parser);
|
|
4191
|
+
case "skip":
|
|
4192
|
+
return rec(d.main);
|
|
4193
|
+
// not / scanTo / guard / withCtx / recover / unknown → shallow set (safe).
|
|
4194
|
+
default:
|
|
4195
|
+
return { concrete: p._meta.firstSet, refs: [] };
|
|
4196
|
+
}
|
|
4197
|
+
}
|
|
4143
4198
|
var HOST_READS_DECL = "const _hostReads = (b, n) => { if (b === undefined) return false; let s; try { s = Function.prototype.toString.call(b) } catch (e) { return true } if (/\\barguments\\b/.test(s)) return true; const m = /^[^(]*\\(([\\s\\S]*?)\\)/.exec(s); if (m && /\\.\\.\\.|=/.test(m[1])) return true; return b.length > n }";
|
|
4144
4199
|
var _loweringSink = null;
|
|
4145
4200
|
function v(ctx, prefix = "_v") {
|
|
@@ -5186,6 +5241,13 @@ function emitMany(def, ctx, pos) {
|
|
|
5186
5241
|
itemPos = npV;
|
|
5187
5242
|
}
|
|
5188
5243
|
}
|
|
5244
|
+
if (!ctx.recovery && !ctx.coverage && !failsAtStart(def.parser) && needsFirstSetGuard(def.parser)) {
|
|
5245
|
+
const lcV = v(ctx, "_lc");
|
|
5246
|
+
stmts.push(
|
|
5247
|
+
`${ind(ctx)}const ${lcV} = ${itemPos} < input.length ? (input.codePointAt(${itemPos}) ?? -1) : -1`,
|
|
5248
|
+
`${ind(ctx)}if (!(${firstSetCond(lcV, def.parser._meta.firstSet)})) { ${rollback}break }`
|
|
5249
|
+
);
|
|
5250
|
+
}
|
|
5189
5251
|
const { stmts: iterStmts, okVar: iterOk, valVar: iterVal, endVar: iterEnd } = emitFallible(def.parser, ctx, itemPos, true);
|
|
5190
5252
|
stmts.push(...iterStmts);
|
|
5191
5253
|
if (ctx.recovery) {
|
|
@@ -5236,8 +5298,19 @@ function emitAttempt(p, def, ctx, pos) {
|
|
|
5236
5298
|
const rollback = `if (_ctx._cstLeaves) _ctx._cstLeaves.length = ${leaves}; if (_ctx._cstRawChildren) _ctx._cstRawChildren.length = ${raw}; if (_ctx._cstTriviaLog) _ctx._cstTriviaLog.length = ${trivia2}; if (_ctx._triviaLog) _ctx._triviaLog.length = ${log}; if (_ctx._fields) _ctx._fields.length = ${fields}; if (_ctx._errors) _ctx._errors.length = ${errors}`;
|
|
5237
5299
|
const traceId = ctx.coverage?.plan.attempts.get(p);
|
|
5238
5300
|
const traceRollback = traceId === void 0 ? "" : ` _ctx._grammarTrace?.write({ id: ${JSON.stringify(traceId)}, phase: 'rollback', offset: ${pos} });`;
|
|
5301
|
+
const preGuard = [];
|
|
5302
|
+
if (!ctx.recovery && !ctx.coverage && needsFirstSetGuard(def.parser)) {
|
|
5303
|
+
const gcV = v(ctx, "_agc");
|
|
5304
|
+
const gExp = armStaticExpected(ctx, def.parser);
|
|
5305
|
+
const gFail = ctx.failLabel ? `{ _ctx._fe = ${pos};${ctx.recordFail ? ` _ctx._fx = ${gExp};` : ""} break ${ctx.failLabel} }` : `{ _ctx._fe = ${pos}; ${failReturnArr(gExp, pos)} }`;
|
|
5306
|
+
preGuard.push(
|
|
5307
|
+
`${ind(ctx)}const ${gcV} = ${pos} < input.length ? (input.codePointAt(${pos}) ?? -1) : -1`,
|
|
5308
|
+
`${ind(ctx)}if (!(${firstSetCond(gcV, def.parser._meta.firstSet)})) ${gFail}`
|
|
5309
|
+
);
|
|
5310
|
+
}
|
|
5239
5311
|
return {
|
|
5240
5312
|
stmts: [
|
|
5313
|
+
...preGuard,
|
|
5241
5314
|
`${ind(ctx)}const ${leaves} = _ctx._cstLeaves?.length ?? 0, ${raw} = _ctx._cstRawChildren?.length ?? 0, ${trivia2} = _ctx._cstTriviaLog?.length ?? 0, ${log} = _ctx._triviaLog?.length ?? 0, ${fields} = _ctx._fields?.length ?? 0, ${errors} = _ctx._errors?.length ?? 0`,
|
|
5242
5315
|
...inner.stmts,
|
|
5243
5316
|
...emitIfFail(ctx, `!${inner.okVar}`, `{ ${rollback};${traceRollback} _ctx._fe = ${pos}; ${propagateFailBody(ctx)} }`)
|
|
@@ -5617,7 +5690,18 @@ ${i}const ${chV} = ${profileRecognizer} ? undefined : [], ${rawV} = ${profileRec
|
|
|
5617
5690
|
const saveTrivia = needsTriviaFrame ? `, ${st} = _ctx.captureTrivia, ${stl} = _ctx._cstTriviaLog${smk ? `, ${smk} = _ctx._triviaCaptureMask` : ""}` : "";
|
|
5618
5691
|
const installTrivia = needsTriviaFrame ? `; _ctx.captureTrivia = ${capTLv ?? "false"}; _ctx._cstTriviaLog = ${innerTl}${smk ? `; _ctx._triviaCaptureMask = ${capTLv} && _ctx.build !== undefined && _ctx.build._parsemanTriviaKinds !== undefined ? _ctx.build._parsemanTriviaKinds(${JSON.stringify(def.type)}) : ${smk}` : ""}` : "";
|
|
5619
5692
|
const restoreTrivia = needsTriviaFrame ? `; _ctx.captureTrivia = ${st}; _ctx._cstTriviaLog = ${stl}${smk ? `; _ctx._triviaCaptureMask = ${smk}` : ""}` : "";
|
|
5693
|
+
const preGuard = [];
|
|
5694
|
+
if (!ctx.recovery && !ctx.coverage && (capturesChildren || structural) && needsFirstSetGuard(def.parser)) {
|
|
5695
|
+
const gcV = v(ctx, "_ngc");
|
|
5696
|
+
const gExp = armStaticExpected(ctx, def.parser);
|
|
5697
|
+
const gFail = ctx.failLabel ? ctx.recordFail ? `{ _ctx._fe = ${pos}; _ctx._fx = ${gExp}; break ${ctx.failLabel} }` : `break ${ctx.failLabel}` : failReturnArr(gExp, pos);
|
|
5698
|
+
preGuard.push(
|
|
5699
|
+
`${i}const ${gcV} = ${pos} < input.length ? (input.codePointAt(${pos}) ?? -1) : -1`,
|
|
5700
|
+
`${i}if (!(${firstSetCond(gcV, def.parser._meta.firstSet)})) ${gFail}`
|
|
5701
|
+
);
|
|
5702
|
+
}
|
|
5620
5703
|
const stmts = [
|
|
5704
|
+
...preGuard,
|
|
5621
5705
|
profHoist,
|
|
5622
5706
|
allocStmt,
|
|
5623
5707
|
`${i}const ${sc} = _ctx._cstChildren, ${sl} = _ctx._cstLeaves, ${sr} = _ctx._cstRawChildren${saveTrivia}${sf ? `, ${sf} = _ctx._fields` : ""}`,
|
|
@@ -6534,6 +6618,7 @@ function compileLinkable(ruleMapArg, ns, opts) {
|
|
|
6534
6618
|
].join("\n")));
|
|
6535
6619
|
}
|
|
6536
6620
|
const firstSets = /* @__PURE__ */ new Map();
|
|
6621
|
+
const firstSetRecipes = /* @__PURE__ */ new Map();
|
|
6537
6622
|
for (const [key, rule] of ruleMap) {
|
|
6538
6623
|
let resolved = rule;
|
|
6539
6624
|
const d = rule._def;
|
|
@@ -6545,6 +6630,7 @@ function compileLinkable(ruleMapArg, ns, opts) {
|
|
|
6545
6630
|
}
|
|
6546
6631
|
}
|
|
6547
6632
|
firstSets.set(key, canMatchEmptyAtStart(resolved) ? { kind: "any" } : resolved._meta.firstSet);
|
|
6633
|
+
firstSetRecipes.set(key, canMatchEmptyAtStart(resolved) ? { concrete: any(), refs: [] } : leadingFirstSetRecipe(resolved));
|
|
6548
6634
|
}
|
|
6549
6635
|
return {
|
|
6550
6636
|
ns,
|
|
@@ -6553,6 +6639,7 @@ function compileLinkable(ruleMapArg, ns, opts) {
|
|
|
6553
6639
|
ruleFns,
|
|
6554
6640
|
wrappers,
|
|
6555
6641
|
firstSets,
|
|
6642
|
+
firstSetRecipes,
|
|
6556
6643
|
deps: ruleDependencies(ruleMap),
|
|
6557
6644
|
needsEmptyTl: !!ctx.needsEmptyTl,
|
|
6558
6645
|
needsHostReads: !!ctx.needsHostReads,
|
|
@@ -7188,10 +7275,30 @@ function fusedBody(pieces) {
|
|
|
7188
7275
|
];
|
|
7189
7276
|
const wrapperEntries = [...winner].map(([k, p]) => `${JSON.stringify(k)}: ${p.wrappers.get(k)}`);
|
|
7190
7277
|
const rawBody = [...lines, "return {", wrapperEntries.join(",\n"), "}"].join("\n");
|
|
7191
|
-
const
|
|
7278
|
+
const ANY2 = { kind: "any" };
|
|
7279
|
+
const recipes = /* @__PURE__ */ new Map();
|
|
7280
|
+
const shallow = /* @__PURE__ */ new Map();
|
|
7192
7281
|
for (const [k, p] of winner) {
|
|
7282
|
+
const r = p.firstSetRecipes?.get(k);
|
|
7283
|
+
if (r) recipes.set(k, r);
|
|
7193
7284
|
const fs = p.firstSets?.get(k);
|
|
7194
|
-
if (fs)
|
|
7285
|
+
if (fs) shallow.set(k, fs);
|
|
7286
|
+
}
|
|
7287
|
+
const finalFS = /* @__PURE__ */ new Map();
|
|
7288
|
+
for (const [k] of winner) finalFS.set(k, recipes.get(k)?.concrete ?? shallow.get(k) ?? ANY2);
|
|
7289
|
+
for (let iter = 0; iter <= recipes.size; iter++) {
|
|
7290
|
+
let changed = false;
|
|
7291
|
+
for (const [k, r] of recipes) {
|
|
7292
|
+
let fs = r.concrete;
|
|
7293
|
+
for (const ref2 of r.refs) {
|
|
7294
|
+
fs = union(fs, recipes.has(ref2) || shallow.has(ref2) ? finalFS.get(ref2) ?? ANY2 : ANY2);
|
|
7295
|
+
}
|
|
7296
|
+
if (JSON.stringify(finalFS.get(k)) !== JSON.stringify(fs)) {
|
|
7297
|
+
finalFS.set(k, fs);
|
|
7298
|
+
changed = true;
|
|
7299
|
+
}
|
|
7300
|
+
}
|
|
7301
|
+
if (!changed) break;
|
|
7195
7302
|
}
|
|
7196
7303
|
const body = rawBody.replace(
|
|
7197
7304
|
// Rule name + code-point var are both JS identifiers (rule names are validated
|