@cbortech/cbor 0.27.0 → 0.27.1

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.
Files changed (48) hide show
  1. package/README.ja.md +73 -0
  2. package/README.md +75 -0
  3. package/dist/ast/CborAppSeqResult.d.ts +37 -4
  4. package/dist/ast/CborArray.d.ts +2 -2
  5. package/dist/ast/CborByteString.d.ts +2 -2
  6. package/dist/ast/CborEmbeddedCBOR.d.ts +1 -1
  7. package/dist/ast/CborFloat.d.ts +1 -1
  8. package/dist/ast/CborIndefiniteByteString.d.ts +1 -1
  9. package/dist/ast/CborIndefiniteTextString.d.ts +1 -1
  10. package/dist/ast/CborItem.d.ts +297 -7
  11. package/dist/ast/CborMap.d.ts +2 -2
  12. package/dist/ast/CborNint.d.ts +1 -1
  13. package/dist/ast/CborTag.d.ts +4 -4
  14. package/dist/ast/CborTextString.d.ts +2 -2
  15. package/dist/ast/CborUint.d.ts +1 -1
  16. package/dist/ast/index.cjs +1 -1
  17. package/dist/ast/index.js +1 -1
  18. package/dist/cddl/index.cjs +1 -1
  19. package/dist/cddl/index.js +1 -1
  20. package/dist/cdn/index.cjs +1 -1
  21. package/dist/cdn/index.js +1 -1
  22. package/dist/cdn/serialize-utils.d.ts +30 -2
  23. package/dist/extensions/cri.d.ts +2 -2
  24. package/dist/extensions/dt.d.ts +4 -4
  25. package/dist/extensions/ip.d.ts +3 -3
  26. package/dist/extensions/types.d.ts +40 -1
  27. package/dist/index.cjs +1 -1
  28. package/dist/index.d.ts +1 -1
  29. package/dist/index.js +3 -3
  30. package/dist/{mapEntries-CvLdiN0h.js → mapEntries-CCLaJSaJ.js} +1114 -933
  31. package/dist/mapEntries-CCLaJSaJ.js.map +1 -0
  32. package/dist/mapEntries-CZZJScaj.cjs +13 -0
  33. package/dist/mapEntries-CZZJScaj.cjs.map +1 -0
  34. package/dist/{schema-CNfrVRYp.js → schema-DN9inJny.js} +3 -3
  35. package/dist/{schema-CNfrVRYp.js.map → schema-DN9inJny.js.map} +1 -1
  36. package/dist/{schema-iXpYtKQl.cjs → schema-zsg5yCPK.cjs} +2 -2
  37. package/dist/{schema-iXpYtKQl.cjs.map → schema-zsg5yCPK.cjs.map} +1 -1
  38. package/dist/{serialize-utils-CjTqQivB.cjs → serialize-utils-DhlW61ZX.cjs} +6 -6
  39. package/dist/serialize-utils-DhlW61ZX.cjs.map +1 -0
  40. package/dist/{serialize-utils-BuIZPaUc.js → serialize-utils-h-CVB9rg.js} +57 -47
  41. package/dist/{serialize-utils-BuIZPaUc.js.map → serialize-utils-h-CVB9rg.js.map} +1 -1
  42. package/dist/types.d.ts +273 -0
  43. package/dist/utils/hexfloat.d.ts +10 -2
  44. package/package.json +7 -8
  45. package/dist/mapEntries-C1f7G0AM.cjs +0 -13
  46. package/dist/mapEntries-C1f7G0AM.cjs.map +0 -1
  47. package/dist/mapEntries-CvLdiN0h.js.map +0 -1
  48. package/dist/serialize-utils-CjTqQivB.cjs.map +0 -1
@@ -1 +1 @@
1
- {"version":3,"file":"schema-iXpYtKQl.cjs","names":[],"sources":["../src/cddl/errors.ts","../src/cddl/tokenizer.ts","../src/cddl/parser.ts","../src/cddl/prelude.ts","../src/cddl/writer.ts","../src/cddl/equal.ts","../src/cddl/controls.ts","../src/cddl/validator.ts","../src/cddl/schema.ts"],"sourcesContent":["/**\n * Structured errors thrown by the CDDL tokenizer, parser, and compiler.\n *\n * Both carry source positions so tooling (editors, linters, playgrounds) can\n * point at the offending range without parsing the message.\n */\n\n/** A semantic problem found while compiling a syntactically valid CDDL file. */\nexport interface CddlWarning {\n /** Stable machine-readable identifier, e.g. 'undefined-name'. */\n code:\n | 'no-rules'\n | 'duplicate-rule'\n | 'undefined-name'\n | 'generic-arity'\n | 'invalid-major'\n | 'invalid-root';\n message: string;\n /** Character offset of the start of the offending range in the source input. */\n start?: number;\n /** Character offset just past the end of the offending range. */\n end?: number;\n}\n\n/**\n * A single validation failure. When a data item does not match the schema,\n * the reported error is the one recorded at the deepest point the matcher\n * reached (failures discarded by backtracking are noise and are not kept).\n */\nexport interface CddlValidationError {\n message: string;\n /** Location inside the instance, e.g. '/claims/2/name' ('' = root). */\n path: string;\n /** Instance-side source offsets (byte offsets for CBOR input, character\n * offsets for CDN input), when the input carried them. */\n start?: number;\n end?: number;\n /** The CDDL rule being matched when the failure was recorded. */\n ruleName?: string;\n /** Schema-side source offsets of the CDDL construct that failed to match. */\n schemaStart?: number;\n schemaEnd?: number;\n}\n\n/** A non-fatal observation made while validating (e.g. unsupported control\n * operators, whose targets are then matched without the constraint). */\nexport interface CddlValidationWarning {\n message: string;\n schemaStart?: number;\n schemaEnd?: number;\n}\n\n/** Result of {@link CddlSchema.validate}. */\nexport interface ValidationResult {\n valid: boolean;\n /** Empty when valid; otherwise the deepest-reach failure(s). */\n errors: CddlValidationError[];\n /** Present when the validator had to approximate or skip constraints. */\n warnings?: CddlValidationWarning[];\n}\n\n/** Syntax error thrown by the CDDL tokenizer and parser. */\nexport class CddlSyntaxError extends SyntaxError {\n /** Character offset of the start of the offending range in the source input. */\n readonly offset?: number;\n /** 1-based line number of the offending range. */\n readonly line?: number;\n /** 1-based column number of the offending range. */\n readonly column?: number;\n /** Character offset just past the end of the offending range. */\n readonly endOffset?: number;\n\n constructor(\n message: string,\n position?: {\n offset?: number;\n line?: number;\n column?: number;\n endOffset?: number;\n }\n ) {\n const loc =\n position?.line !== undefined\n ? ` at line ${position.line}, column ${position.column}`\n : '';\n super(`CDDL parse error${loc}: ${message}`);\n this.name = 'CddlSyntaxError';\n this.offset = position?.offset;\n this.line = position?.line;\n this.column = position?.column;\n this.endOffset = position?.endOffset;\n }\n}\n\n/**\n * Error thrown when a data item does not match a CDDL schema supplied via\n * the `cddl` option of a throwing entry point (`CBOR.parse`, `CBOR.decode`,\n * `CBOR.fromCDN`, `CBOR.encode`, …). Non-throwing checks (`CBOR.validate`,\n * `CddlSchema.validate`) report the same failures in their result instead.\n */\nexport class CddlMismatchError extends Error {\n /** The deepest-reach validation failure(s). */\n readonly errors: CddlValidationError[];\n /** Non-fatal validator observations (approximated/skipped constraints). */\n readonly warnings: CddlValidationWarning[];\n\n constructor(\n errors: CddlValidationError[],\n warnings: CddlValidationWarning[] = []\n ) {\n const head = errors[0];\n const loc = head?.path ? ` at ${head.path}` : '';\n const rest = errors.length > 1 ? ` (and ${errors.length - 1} more)` : '';\n super(`CDDL validation failed${loc}: ${head?.message ?? 'unknown'}${rest}`);\n this.name = 'CddlMismatchError';\n this.errors = errors;\n this.warnings = warnings;\n }\n}\n\n/**\n * Semantic error thrown by `CDDL.compile` in strict mode (the default) when\n * a syntactically valid file has semantic problems: undefined names,\n * duplicate rule definitions, generic arity mismatches, and the like.\n * With `strict: false` the same problems are collected into\n * `CddlSchema.warnings` instead.\n */\nexport class CddlSemanticError extends Error {\n readonly warnings: CddlWarning[];\n\n constructor(warnings: CddlWarning[]) {\n const head = warnings[0];\n const rest =\n warnings.length > 1 ? ` (and ${warnings.length - 1} more)` : '';\n super(`CDDL semantic error: ${head?.message ?? 'unknown'}${rest}`);\n this.name = 'CddlSemanticError';\n this.warnings = warnings;\n }\n}\n","/**\n * CDDL lexer (internal).\n *\n * Implements the token-level grammar of RFC 8610 as updated by RFC 9682\n * (Appendix A collected ABNF). Used by parser.ts and exposed through the\n * `tokenize()` / `tokenizeLenient()` helpers in index.ts so tooling such as\n * syntax highlighters stays in exact agreement with parsing behavior.\n */\n\nimport { CddlSyntaxError } from './errors';\nimport { hexToBytes } from '../utils/hex';\nimport { base64ToBytes } from '../utils/base64';\n\nexport type CddlTokenType =\n | 'ID'\n | 'INT' // raw text in `value`, incl. optional '-' and 0x/0b forms\n | 'FLOAT' // raw text in `value`, decimal or hexfloat\n | 'TSTR' // decoded content in `value`\n | 'BYTES' // raw content in `value`, decoded bytes in `bytes`\n | 'HASH' // '#' with optional major/head-number (see hashMajor/hashAI)\n | 'ASSIGN' // =\n | 'SLASH_EQ' // /=\n | 'DSLASH_EQ' // //=\n | 'SLASH' // /\n | 'DSLASH' // //\n | 'COMMA'\n | 'LPAREN'\n | 'RPAREN'\n | 'LBRACE'\n | 'RBRACE'\n | 'LBRACKET'\n | 'RBRACKET'\n | 'LT'\n | 'GT'\n | 'TILDE'\n | 'AMP'\n | 'RANGE_INCL' // ..\n | 'RANGE_EXCL' // ...\n | 'CTLOP' // .id — operator name (without the dot) in `value`\n | 'STAR'\n | 'PLUS'\n | 'QUEST'\n | 'ARROW' // =>\n | 'COLON'\n | 'CARET'\n | 'EOF'\n /** Synthetic token emitted by tokenizeLenient() for the unscannable tail. */\n | 'ERROR';\n\nexport interface CddlToken {\n type: CddlTokenType;\n /** Processed value: decoded string content, raw numeric text, id text, etc. */\n value: string;\n /** Original source text for this token. */\n raw: string;\n line: number;\n col: number;\n /** Character offset of the first character of this token in the source input. */\n offset: number;\n /** Character offset just past the last character of this token in the source input. */\n endOffset: number;\n /** Only set when type === 'BYTES': the qualifier ('' | 'h' | 'b64'). */\n qualifier?: '' | 'h' | 'b64';\n /** Only set when type === 'BYTES': the decoded byte content. */\n bytes?: Uint8Array;\n /** Only set when type === 'HASH': the major digit (0–9), absent for bare '#'. */\n hashMajor?: number;\n /** Only set when type === 'HASH': the literal head-number after the dot. */\n hashAI?: bigint;\n /**\n * Only set when type === 'HASH': the head-number is a `<type>` expression\n * (RFC 9682 §3.2); the tokens for `<` type `>` follow this token.\n */\n hashAIExpr?: boolean;\n}\n\n/** A `;` line comment collected while scanning. */\nexport interface CddlComment {\n /** Comment text after the ';' marker, without the trailing newline. */\n text: string;\n start: number;\n end: number;\n line: number;\n col: number;\n}\n\n// Shared codec instance — constructing TextEncoder per token is measurably\n// expensive in hot parsing paths (same pattern as cdn/parser.ts).\nconst textEncoder = new TextEncoder();\n\nconst isDigit = (c: string): boolean => c >= '0' && c <= '9';\nconst isHexDigit = (c: string): boolean =>\n isDigit(c) || (c >= 'a' && c <= 'f') || (c >= 'A' && c <= 'F');\nconst isEAlpha = (c: string): boolean =>\n (c >= 'a' && c <= 'z') ||\n (c >= 'A' && c <= 'Z') ||\n c === '@' ||\n c === '_' ||\n c === '$';\n\n/** NONASCII = %xA0-D7FF / %xE000-10FFFD (RFC 9682) */\nconst isNonAscii = (cp: number): boolean =>\n (cp >= 0xa0 && cp <= 0xd7ff) || (cp >= 0xe000 && cp <= 0x10fffd);\n\nexport class CddlTokenizer {\n private readonly input: string;\n private pos = 0;\n private line = 1;\n private col = 1;\n\n /** Comments encountered while scanning, in source order. */\n readonly comments: CddlComment[] = [];\n\n /** Character offset just past the last successfully scanned token. */\n lastEndOffset = 0;\n\n constructor(input: string) {\n this.input = input;\n }\n\n // ─── Low-level helpers ──────────────────────────────────────────────────────\n\n private _eof(): boolean {\n return this.pos >= this.input.length;\n }\n\n private _ch(): string {\n return this.input[this.pos] ?? '';\n }\n\n private _advance(): string {\n const ch = this.input[this.pos] ?? '';\n this.pos++;\n if (ch === '\\n') {\n this.line++;\n this.col = 1;\n } else {\n this.col++;\n }\n return ch;\n }\n\n private _fail(message: string, line?: number, col?: number): never {\n throw new CddlSyntaxError(message, {\n offset: this.pos,\n line: line ?? this.line,\n column: col ?? this.col,\n });\n }\n\n // ─── Whitespace and comments ────────────────────────────────────────────────\n\n /**\n * Skip S = *(SP / NL) where NL = COMMENT / CRLF.\n *\n * Per the ABNF only SP (0x20), LF, and CRLF are whitespace; horizontal tab\n * is not valid CDDL whitespace and is rejected with a targeted message.\n * Deliberate leniency: a bare CR (not part of CRLF) is also accepted as\n * whitespace, as source-level line-ending normalization.\n */\n private _skipWs(): void {\n for (;;) {\n const ch = this._ch();\n if (ch === ' ' || ch === '\\n' || ch === '\\r') {\n this._advance();\n continue;\n }\n if (ch === '\\t')\n this._fail(\n 'horizontal tab is not valid whitespace in CDDL (RFC 8610 ABNF allows only space and newline)'\n );\n if (ch === ';') {\n this._scanComment();\n continue;\n }\n return;\n }\n }\n\n /**\n * COMMENT = \";\" *PCHAR CRLF — collected into `this.comments`.\n *\n * Deliberate leniency: content characters are not PCHAR-validated, and a\n * comment terminated by end-of-input (no trailing newline) is accepted.\n */\n private _scanComment(): void {\n const start = this.pos;\n const line = this.line;\n const col = this.col;\n this._advance(); // ';'\n let p = this.pos;\n while (p < this.input.length) {\n const c = this.input[p]!;\n if (c === '\\n' || c === '\\r') break;\n p++;\n }\n const text = this.input.slice(this.pos, p);\n this.col += p - this.pos;\n this.pos = p;\n this.comments.push({ text, start, end: p, line, col });\n }\n\n // ─── Token production ───────────────────────────────────────────────────────\n\n private _make(\n type: CddlTokenType,\n value: string,\n startOffset: number,\n line: number,\n col: number,\n extra?: Partial<CddlToken>\n ): CddlToken {\n const token: CddlToken = {\n type,\n value,\n raw: this.input.slice(startOffset, this.pos),\n line,\n col,\n offset: startOffset,\n endOffset: this.pos,\n ...extra,\n };\n this.lastEndOffset = this.pos;\n return token;\n }\n\n /** Scan and return the next token (skipping whitespace and comments). */\n consume(): CddlToken {\n this._skipWs();\n const start = this.pos;\n const line = this.line;\n const col = this.col;\n\n if (this._eof()) return this._make('EOF', '', start, line, col);\n\n const ch = this._ch();\n\n if (isEAlpha(ch)) {\n const id = this._scanIdText();\n // bsqual: h'...' / b64'...'\n if ((id === 'h' || id === 'b64') && this._ch() === \"'\")\n return this._scanBytes(id, start, line, col);\n return this._make('ID', id, start, line, col);\n }\n\n if (isDigit(ch) || ch === '-') return this._scanNumber(start, line, col);\n\n if (ch === '\"') return this._scanText(start, line, col);\n if (ch === \"'\") return this._scanBytes('', start, line, col);\n if (ch === '#') return this._scanHash(start, line, col);\n\n switch (ch) {\n case '=':\n this._advance();\n if (this._ch() === '>') {\n this._advance();\n return this._make('ARROW', '=>', start, line, col);\n }\n return this._make('ASSIGN', '=', start, line, col);\n case '/':\n this._advance();\n if (this._ch() === '/') {\n this._advance();\n if (this._ch() === '=') {\n this._advance();\n return this._make('DSLASH_EQ', '//=', start, line, col);\n }\n return this._make('DSLASH', '//', start, line, col);\n }\n if (this._ch() === '=') {\n this._advance();\n return this._make('SLASH_EQ', '/=', start, line, col);\n }\n return this._make('SLASH', '/', start, line, col);\n case '.': {\n // '...' / '..' / '.id' (control operator)\n this._advance();\n if (this._ch() === '.') {\n this._advance();\n if (this._ch() === '.') {\n this._advance();\n return this._make('RANGE_EXCL', '...', start, line, col);\n }\n return this._make('RANGE_INCL', '..', start, line, col);\n }\n if (!isEAlpha(this._ch()))\n this._fail(\n `expected a control operator name after '.' (e.g. .size), got ${this._eof() ? 'end of input' : JSON.stringify(this._ch())}`,\n line,\n col\n );\n const op = this._scanIdText();\n return this._make('CTLOP', op, start, line, col);\n }\n case ',':\n this._advance();\n return this._make('COMMA', ',', start, line, col);\n case '(':\n this._advance();\n return this._make('LPAREN', '(', start, line, col);\n case ')':\n this._advance();\n return this._make('RPAREN', ')', start, line, col);\n case '{':\n this._advance();\n return this._make('LBRACE', '{', start, line, col);\n case '}':\n this._advance();\n return this._make('RBRACE', '}', start, line, col);\n case '[':\n this._advance();\n return this._make('LBRACKET', '[', start, line, col);\n case ']':\n this._advance();\n return this._make('RBRACKET', ']', start, line, col);\n case '<':\n this._advance();\n return this._make('LT', '<', start, line, col);\n case '>':\n this._advance();\n return this._make('GT', '>', start, line, col);\n case '~':\n this._advance();\n return this._make('TILDE', '~', start, line, col);\n case '&':\n this._advance();\n return this._make('AMP', '&', start, line, col);\n case '*':\n this._advance();\n return this._make('STAR', '*', start, line, col);\n case '+':\n this._advance();\n return this._make('PLUS', '+', start, line, col);\n case '?':\n this._advance();\n return this._make('QUEST', '?', start, line, col);\n case ':':\n this._advance();\n return this._make('COLON', ':', start, line, col);\n case '^':\n this._advance();\n return this._make('CARET', '^', start, line, col);\n default:\n this._fail(`unexpected character ${JSON.stringify(ch)}`);\n }\n }\n\n // ─── Identifiers ────────────────────────────────────────────────────────────\n\n /**\n * id = EALPHA *(*(\"-\" / \".\") (EALPHA / DIGIT))\n *\n * Interior '-' and '.' runs are allowed when followed by an EALPHA/DIGIT,\n * so `a.b`, `a-b`, and even `tstr.size` are single ids (the ABNF note\n * \"space may be needed before the operator if type2 ends in a name\" exists\n * for exactly this reason). This includes `..`: RFC 8610 §2.2.2.1 says\n * `min..max` \"is not a range expression but a single name\" — a range with\n * a name on the left-hand side must be written `min .. max`.\n */\n private _scanIdText(): string {\n const start = this.pos;\n this._advance(); // leading EALPHA, verified by caller\n for (;;) {\n const c = this._ch();\n if (isEAlpha(c) || isDigit(c)) {\n this._advance();\n continue;\n }\n if (c === '-' || c === '.') {\n // Look ahead across the separator run without consuming: the run is\n // part of the id only when an EALPHA/DIGIT follows it.\n let q = this.pos;\n while (this.input[q] === '-' || this.input[q] === '.') q++;\n const after = this.input[q] ?? '';\n if (!(isEAlpha(after) || isDigit(after))) break;\n while (this.pos <= q) this._advance(); // separators + first id char\n continue;\n }\n break;\n }\n return this.input.slice(start, this.pos);\n }\n\n // ─── Numbers ────────────────────────────────────────────────────────────────\n\n /**\n * number = hexfloat / (int [\".\" fraction] [\"e\" exponent])\n * hexfloat = [\"-\"] \"0x\" 1*HEXDIG [\".\" 1*HEXDIG] \"p\" exponent\n * uint = DIGIT1 *DIGIT / \"0x\" 1*HEXDIG / \"0b\" 1*BINDIG / \"0\"\n *\n * The token `value` is the raw numeric text; the parser converts it.\n * A '.' followed by another '.' is never consumed (range operator).\n */\n private _scanNumber(start: number, line: number, col: number): CddlToken {\n if (this._ch() === '-') this._advance();\n if (!isDigit(this._ch()))\n this._fail(`expected a digit after '-'`, line, col);\n\n let isFloat = false;\n\n if (this._ch() === '0' && /[xX]/.test(this.input[this.pos + 1] ?? '')) {\n this._advance(); // 0\n this._advance(); // x\n if (!isHexDigit(this._ch()))\n this._fail('expected hex digits after 0x', line, col);\n while (isHexDigit(this._ch())) this._advance();\n // hexfloat fraction/exponent\n if (\n this._ch() === '.' &&\n isHexDigit(this.input[this.pos + 1] ?? '') &&\n this.input[this.pos + 1] !== undefined\n ) {\n // Only a hexfloat may follow; a plain hex int never has a fraction.\n this._advance(); // .\n while (isHexDigit(this._ch())) this._advance();\n if (!/[pP]/.test(this._ch()))\n this._fail(\n \"hexadecimal fraction requires a 'p' exponent (hexfloat)\",\n line,\n col\n );\n }\n if (/[pP]/.test(this._ch())) {\n this._advance(); // p\n if (this._ch() === '+' || this._ch() === '-') this._advance();\n if (!isDigit(this._ch()))\n this._fail(\"expected exponent digits after 'p'\", line, col);\n while (isDigit(this._ch())) this._advance();\n isFloat = true;\n }\n } else if (\n this._ch() === '0' &&\n /[bB]/.test(this.input[this.pos + 1] ?? '')\n ) {\n this._advance(); // 0\n this._advance(); // b\n if (!/[01]/.test(this._ch()))\n this._fail('expected binary digits after 0b', line, col);\n while (/[01]/.test(this._ch())) this._advance();\n } else {\n if (this._ch() === '0' && isDigit(this.input[this.pos + 1] ?? ''))\n this._fail('leading zeros are not allowed in CDDL numbers', line, col);\n while (isDigit(this._ch())) this._advance();\n // fraction — but never consume '..' (range operator)\n if (this._ch() === '.' && isDigit(this.input[this.pos + 1] ?? '')) {\n this._advance(); // .\n while (isDigit(this._ch())) this._advance();\n isFloat = true;\n }\n if (/[eE]/.test(this._ch())) {\n this._advance(); // e\n if (this._ch() === '+' || this._ch() === '-') this._advance();\n if (!isDigit(this._ch()))\n this._fail(\"expected exponent digits after 'e'\", line, col);\n while (isDigit(this._ch())) this._advance();\n isFloat = true;\n }\n }\n\n const raw = this.input.slice(start, this.pos);\n return this._make(isFloat ? 'FLOAT' : 'INT', raw, start, line, col);\n }\n\n /** Scan a uint (decimal / 0x / 0b) for a '#' head-number; returns raw text. */\n private _scanUintRaw(): string {\n const start = this.pos;\n if (!isDigit(this._ch()))\n this._fail('expected an unsigned integer head-number');\n if (this._ch() === '0' && /[xX]/.test(this.input[this.pos + 1] ?? '')) {\n this._advance();\n this._advance();\n if (!isHexDigit(this._ch())) this._fail('expected hex digits after 0x');\n while (isHexDigit(this._ch())) this._advance();\n } else if (\n this._ch() === '0' &&\n /[bB]/.test(this.input[this.pos + 1] ?? '')\n ) {\n this._advance();\n this._advance();\n if (!/[01]/.test(this._ch()))\n this._fail('expected binary digits after 0b');\n while (/[01]/.test(this._ch())) this._advance();\n } else {\n if (this._ch() === '0' && isDigit(this.input[this.pos + 1] ?? ''))\n this._fail('leading zeros are not allowed in CDDL numbers');\n while (isDigit(this._ch())) this._advance();\n }\n return this.input.slice(start, this.pos);\n }\n\n // ─── '#' types ──────────────────────────────────────────────────────────────\n\n /**\n * \"#\" — any\n * \"#\" DIGIT [\".\" head-number] — major type (and tag/simple shorthands)\n * head-number = uint / \"<\" type \">\" (RFC 9682 §3.2)\n *\n * The '#', major digit, and a literal head-number are fused into a single\n * HASH token (they must be adjacent in the source; `# 6` is a bare '#'\n * followed by the value 6). For the `<type>` form, hashAIExpr is set and\n * the `<` type `>` tokens follow.\n */\n private _scanHash(start: number, line: number, col: number): CddlToken {\n this._advance(); // '#'\n const extra: Partial<CddlToken> = {};\n if (isDigit(this._ch())) {\n extra.hashMajor = this._advance().charCodeAt(0) - 0x30;\n if (this._ch() === '.') {\n if (this.input[this.pos + 1] === '<') {\n this._advance(); // '.' — the '<' type '>' tokens follow\n extra.hashAIExpr = true;\n } else {\n this._advance(); // '.'\n extra.hashAI = BigInt(this._scanUintRaw());\n }\n }\n }\n return this._make(\n 'HASH',\n this.input.slice(start, this.pos),\n start,\n line,\n col,\n extra\n );\n }\n\n // ─── Strings ────────────────────────────────────────────────────────────────\n\n /** text = %x22 *SCHAR %x22 — single-line, strict SCHAR/SESC per RFC 9682. */\n private _scanText(start: number, line: number, col: number): CddlToken {\n const value = this._readStringBody('\"');\n return this._make('TSTR', value, start, line, col);\n }\n\n /**\n * bytes = [bsqual] %x27 *BCHAR %x27\n *\n * Unqualified: content is UTF-8-encoded like a text string ('\\'' must be\n * escaped). Qualified h''/b64'': whitespace and ';' line comments inside\n * the literal are ignored, then the rest is hex / base64 decoded\n * (RFC 8610 §3.1).\n */\n private _scanBytes(\n qualifier: '' | 'h' | 'b64',\n start: number,\n line: number,\n col: number\n ): CddlToken {\n const content = this._readStringBody(\"'\");\n let bytes: Uint8Array;\n if (qualifier === '') {\n bytes = textEncoder.encode(content);\n } else {\n const data = stripWsAndComments(content);\n try {\n bytes = qualifier === 'h' ? hexToBytes(data) : base64ToBytes(data);\n } catch (e) {\n if (!(e instanceof SyntaxError) || e instanceof CddlSyntaxError)\n throw e;\n throw new CddlSyntaxError(e.message, {\n offset: start,\n line,\n column: col,\n endOffset: this.pos,\n });\n }\n }\n return this._make('BYTES', content, start, line, col, {\n qualifier,\n bytes,\n });\n }\n\n /**\n * Read the body of a '\"' text string or \"'\" byte string, decoding escapes.\n *\n * SCHAR = %x20-21 / %x23-5B / %x5D-7E / NONASCII / SESC\n * BCHAR = %x20-26 / %x28-5B / %x5D-7E / NONASCII / SESC / \"\\'\" / CRLF\n * SESC = \"\\\" ( %x22 / \"/\" / \"\\\" / b / f / n / r / t / (%x75 hexchar) )\n */\n private _readStringBody(quote: '\"' | \"'\"): string {\n const isBytes = quote === \"'\";\n this._advance(); // opening quote\n let out = '';\n for (;;) {\n if (this._eof())\n this._fail(`unterminated ${isBytes ? 'byte' : 'text'} string literal`);\n const ch = this._ch();\n if (ch === quote) {\n this._advance();\n return out;\n }\n if (ch === '\\\\') {\n const eLine = this.line;\n const eCol = this.col;\n this._advance();\n const e = this._advance();\n switch (e) {\n case '\"':\n out += '\"';\n break;\n case '/':\n out += '/';\n break;\n case '\\\\':\n out += '\\\\';\n break;\n case 'b':\n out += '\\b';\n break;\n case 'f':\n out += '\\f';\n break;\n case 'n':\n out += '\\n';\n break;\n case 'r':\n out += '\\r';\n break;\n case 't':\n out += '\\t';\n break;\n case 'u':\n out += this._readUnicodeEscape(eLine, eCol);\n break;\n case \"'\":\n if (!isBytes)\n this._fail(\n `\\\\' is only valid in byte string literals; text strings do not need it`,\n eLine,\n eCol\n );\n out += \"'\";\n break;\n default:\n this._fail(`invalid escape sequence \\\\${e}`, eLine, eCol);\n }\n continue;\n }\n // CRLF / LF is content in byte strings only.\n if (ch === '\\n' || ch === '\\r') {\n if (!isBytes)\n this._fail(\n 'text string literals cannot span lines (escape the newline as \\\\n)'\n );\n if (ch === '\\r') {\n this._advance();\n if (this._ch() !== '\\n')\n this._fail('bare CR is not allowed in byte string literals');\n this._advance();\n out += '\\r\\n';\n } else {\n this._advance();\n out += '\\n';\n }\n continue;\n }\n // Read the full code point (an astral char spans two UTF-16 units).\n const cp = this.input.codePointAt(this.pos)!;\n if (cp < 0x20 || (cp >= 0x7f && cp <= 0x9f))\n this._fail(\n `unescaped control character U+${cp.toString(16).padStart(4, '0').toUpperCase()} is not allowed in string literals`\n );\n if (cp > 0x7e && !isNonAscii(cp))\n this._fail(\n `code point U+${cp.toString(16).toUpperCase()} is not allowed in CDDL source`\n );\n this._advance();\n if (cp > 0xffff) this._advance(); // astral: second UTF-16 code unit\n out += String.fromCodePoint(cp);\n }\n }\n\n /**\n * hexchar (RFC 9682): after `\\u`, either `{...}` with a scalar value\n * (leading zeros allowed, surrogates rejected) or 4 hex digits, where a\n * high surrogate must be immediately followed by `\\uXXXX` low surrogate.\n */\n private _readUnicodeEscape(eLine: number, eCol: number): string {\n if (this._ch() === '{') {\n this._advance();\n let hex = '';\n while (isHexDigit(this._ch())) hex += this._advance();\n if (hex.length === 0)\n this._fail('\\\\u{} escape requires at least one hex digit', eLine, eCol);\n if (this._ch() !== '}')\n this._fail(\"expected '}' to close \\\\u{...} escape\", eLine, eCol);\n this._advance();\n const cp = parseInt(hex, 16);\n if (cp > 0x10ffff)\n this._fail(\n `\\\\u{${hex}} is above the Unicode code point maximum U+10FFFF`,\n eLine,\n eCol\n );\n if (cp >= 0xd800 && cp <= 0xdfff)\n this._fail(\n `\\\\u{${hex}} is a surrogate code point, not a Unicode scalar value`,\n eLine,\n eCol\n );\n return String.fromCodePoint(cp);\n }\n const readHex4 = (): number => {\n let hex = '';\n for (let i = 0; i < 4; i++) {\n if (!isHexDigit(this._ch()))\n this._fail('\\\\u escape requires four hex digits', eLine, eCol);\n hex += this._advance();\n }\n return parseInt(hex, 16);\n };\n const cp = readHex4();\n if (cp >= 0xd800 && cp <= 0xdbff) {\n // High surrogate: a low surrogate escape must follow immediately.\n if (this._ch() !== '\\\\' || this.input[this.pos + 1] !== 'u')\n this._fail(\n 'high surrogate \\\\u escape must be followed by a low surrogate \\\\u escape',\n eLine,\n eCol\n );\n this._advance();\n this._advance();\n const lo = readHex4();\n if (lo < 0xdc00 || lo > 0xdfff)\n this._fail(\n 'high surrogate \\\\u escape must be followed by a low surrogate \\\\u escape',\n eLine,\n eCol\n );\n return String.fromCodePoint(\n 0x10000 + ((cp - 0xd800) << 10) + (lo - 0xdc00)\n );\n }\n if (cp >= 0xdc00 && cp <= 0xdfff)\n this._fail('lone low surrogate \\\\u escape', eLine, eCol);\n return String.fromCodePoint(cp);\n }\n}\n\n/**\n * Remove whitespace and ';' line comments from the (escape-processed) content\n * of a prefixed h''/b64'' byte string — RFC 8610 §3.1: \"any whitespace\n * present within the string (including comments) is ignored in the prefixed\n * case\".\n */\nfunction stripWsAndComments(content: string): string {\n let out = '';\n let i = 0;\n while (i < content.length) {\n const c = content[i]!;\n if (c === ' ' || c === '\\n' || c === '\\r') {\n i++;\n continue;\n }\n if (c === ';') {\n while (i < content.length && content[i] !== '\\n') i++;\n continue;\n }\n out += c;\n i++;\n }\n return out;\n}\n","/**\n * CDDL recursive-descent parser (internal).\n *\n * Implements the grammar of RFC 8610 as updated by RFC 9682 Appendix A.\n * Produces the plain AST defined in ast.ts; all semantic processing\n * (prelude merging, name resolution, /= and //= extension) happens in\n * schema.ts.\n */\n\nimport { CddlTokenizer, type CddlComment, type CddlToken } from './tokenizer';\nimport { CddlSyntaxError } from './errors';\nimport { parseHexFloat } from '../utils/hexfloat';\nimport type {\n CddlEntryValue,\n CddlGroup,\n CddlGroupEntry,\n CddlMemberKey,\n CddlOccur,\n CddlRef,\n CddlRule,\n CddlType,\n CddlType1,\n CddlType2,\n CddlValue,\n} from './ast';\n\nexport interface ParseCddlResult {\n /** Rules in source order (unmerged; `/=` and `//=` appear as-is). */\n rules: CddlRule[];\n /** `;` comments encountered while scanning, in source order. */\n comments: CddlComment[];\n}\n\n/**\n * Parse CDDL text into rule ASTs.\n * Throws {@link CddlSyntaxError} on invalid input.\n */\nexport function parseCDDL(text: string): ParseCddlResult {\n const tokenizer = new CddlTokenizer(text);\n const parser = new CddlParser(tokenizer);\n const rules = parser.parse();\n return { rules, comments: tokenizer.comments };\n}\n\n/** Token types that continue a type1/type/memberkey after a closing paren. */\nconst TYPE_CONTINUATION: ReadonlySet<string> = new Set([\n 'SLASH',\n 'RANGE_INCL',\n 'RANGE_EXCL',\n 'CTLOP',\n 'ARROW',\n 'CARET',\n]);\n\nclass CddlParser {\n private readonly t: CddlTokenizer;\n private readonly buf: CddlToken[] = [];\n\n constructor(tokenizer: CddlTokenizer) {\n this.t = tokenizer;\n }\n\n // ─── Token plumbing ─────────────────────────────────────────────────────────\n\n private peek(i = 0): CddlToken {\n while (this.buf.length <= i) this.buf.push(this.t.consume());\n return this.buf[i]!;\n }\n\n private consume(): CddlToken {\n return this.buf.shift() ?? this.t.consume();\n }\n\n private expect(type: CddlToken['type'], what: string): CddlToken {\n const tok = this.peek();\n if (tok.type !== type) this._fail(`expected ${what}`, tok);\n return this.consume();\n }\n\n private _fail(message: string, tok: CddlToken): never {\n const got =\n tok.type === 'EOF' ? 'end of input' : `${JSON.stringify(tok.raw)}`;\n throw new CddlSyntaxError(`${message}, got ${got}`, {\n offset: tok.offset,\n endOffset: tok.endOffset,\n line: tok.line,\n column: tok.col,\n });\n }\n\n // ─── cddl = S *(rule S) ─────────────────────────────────────────────────────\n\n parse(): CddlRule[] {\n const rules: CddlRule[] = [];\n while (this.peek().type !== 'EOF') rules.push(this.parseRule());\n return rules;\n }\n\n /**\n * rule = typename [genericparm] S assignt S type\n * / groupname [genericparm] S assigng S grpent\n *\n * For '=' (shared by assignt and assigng) the body is parsed as a group\n * entry, which subsumes a plain type. '/=' is assignt only, so its\n * right-hand side must be a plain type; '//=' (assigng) takes a grpent.\n */\n private parseRule(): CddlRule {\n const nameTok = this.expect('ID', 'a rule name');\n let generics: string[] | undefined;\n if (this.peek().type === 'LT') {\n this.consume();\n generics = [this.expect('ID', 'a generic parameter name').value];\n while (this.peek().type === 'COMMA') {\n this.consume();\n generics.push(this.expect('ID', 'a generic parameter name').value);\n }\n this.expect('GT', `'>' after generic parameters`);\n }\n const assignTok = this.peek();\n let assign: CddlRule['assign'];\n if (assignTok.type === 'ASSIGN') assign = '=';\n else if (assignTok.type === 'SLASH_EQ') assign = '/=';\n else if (assignTok.type === 'DSLASH_EQ') assign = '//=';\n else this._fail(`expected '=', '/=' or '//=' after rule name`, assignTok);\n this.consume();\n const body =\n assign === '/=' ? this.parseTypeAsEntry() : this.parseGroupEntry();\n return {\n kind: 'rule',\n name: nameTok.value,\n ...(generics ? { generics } : {}),\n assign,\n body,\n start: nameTok.offset,\n end: body.end,\n };\n }\n\n /** A plain type in rule-body position, wrapped as an entry AST node. */\n private parseTypeAsEntry(): CddlEntryValue {\n const value = this.parseType();\n return {\n kind: 'entry',\n value,\n start: value.start,\n end: value.end,\n };\n }\n\n // ─── Groups ─────────────────────────────────────────────────────────────────\n\n /** group = grpchoice *(S \"//\" S grpchoice), up to (not including) `closer`. */\n private parseGroup(closer: CddlToken['type']): CddlGroup {\n const start = this.peek().offset;\n const choices: CddlGroupEntry[][] = [[]];\n let lastWasComma = false;\n for (;;) {\n const tok = this.peek();\n if (tok.type === closer) break;\n if (tok.type === 'EOF')\n this._fail(\n `unterminated group; expected ${JSON.stringify(closer)}`,\n tok\n );\n if (tok.type === 'DSLASH') {\n this.consume();\n choices.push([]);\n lastWasComma = false;\n continue;\n }\n choices[choices.length - 1]!.push(this.parseGroupEntry());\n // optcom = S [\",\" S] — the comma after an entry is optional.\n lastWasComma = this.peek().type === 'COMMA';\n if (lastWasComma) this.consume();\n }\n const endTok = this.peek(); // the closer, consumed by the caller\n return {\n kind: 'group',\n choices,\n ...(lastWasComma ? { trailingComma: true } : {}),\n start,\n end: endTok.offset,\n };\n }\n\n /**\n * grpent = [occur S] [memberkey S] type\n * / [occur S] groupname [genericarg] ; covered by the type branch\n * / [occur S] \"(\" S group S \")\"\n */\n private parseGroupEntry(): CddlGroupEntry {\n const start = this.peek().offset;\n const occur = this.tryParseOccur();\n\n // Inline parenthesized group — unless what follows the ')' pulls the\n // parenthesized expression back into type position (e.g. `(\"a\"/\"b\") .size 1`\n // is a paren *type* with a control operator, not a group entry).\n if (this.peek().type === 'LPAREN') {\n const lparen = this.consume();\n const group = this.parseGroup('RPAREN');\n const rparen = this.consume();\n if (TYPE_CONTINUATION.has(this.peek().type)) {\n const paren = this.groupAsParenType(group, lparen, rparen);\n const type1 = this.continueType1(paren);\n return this.finishEntryFromType1(start, occur, type1);\n }\n return {\n kind: 'entry-group',\n ...(occur ? { occur } : {}),\n group,\n start,\n end: rparen.endOffset,\n };\n }\n\n // memberkey shortcuts: bareword \":\" and value \":\"\n const t0 = this.peek(0);\n const t1 = this.peek(1);\n if (t1.type === 'COLON' && (t0.type === 'ID' || this.isValueToken(t0))) {\n let memberKey: CddlMemberKey;\n if (t0.type === 'ID') {\n this.consume();\n const colon = this.consume();\n memberKey = {\n kind: 'bareword',\n key: t0.value,\n cut: true,\n start: t0.offset,\n end: colon.endOffset,\n };\n } else {\n const key = this.parseValue();\n const colon = this.consume();\n memberKey = {\n kind: 'value',\n key,\n cut: true,\n start: key.start,\n end: colon.endOffset,\n };\n }\n const value = this.parseType();\n return {\n kind: 'entry',\n ...(occur ? { occur } : {}),\n memberKey,\n value,\n start,\n end: value.end,\n };\n }\n\n // General case: parse a type1, then decide whether it was a member key.\n const type1 = this.parseType1();\n return this.finishEntryFromType1(start, occur, type1);\n }\n\n /**\n * After parsing an initial type1 in entry position: `^`/`=>` make it a\n * member key (memberkey = type1 S [\"^\" S] \"=>\"); otherwise it starts the\n * entry's type and further `/` alternatives may follow.\n */\n private finishEntryFromType1(\n start: number,\n occur: CddlOccur | undefined,\n type1: CddlType1\n ): CddlEntryValue {\n let memberKey: CddlMemberKey | undefined;\n if (this.peek().type === 'CARET' || this.peek().type === 'ARROW') {\n let cut = false;\n if (this.peek().type === 'CARET') {\n this.consume();\n cut = true;\n }\n const arrow = this.expect('ARROW', `'=>' after member key`);\n memberKey = {\n kind: 'type1',\n key: type1,\n cut,\n start: type1.start,\n end: arrow.endOffset,\n };\n }\n const value = memberKey\n ? this.parseType()\n : this.continueTypeAlternatives(type1);\n return {\n kind: 'entry',\n ...(occur ? { occur } : {}),\n ...(memberKey ? { memberKey } : {}),\n value,\n start,\n end: value.end,\n };\n }\n\n /** occur = [uint] \"*\" [uint] / \"+\" / \"?\" — components must be adjacent. */\n private tryParseOccur(): CddlOccur | undefined {\n const t0 = this.peek(0);\n if (t0.type === 'QUEST') {\n this.consume();\n return {\n kind: 'occur',\n marker: '?',\n start: t0.offset,\n end: t0.endOffset,\n };\n }\n if (t0.type === 'PLUS') {\n this.consume();\n return {\n kind: 'occur',\n marker: '+',\n start: t0.offset,\n end: t0.endOffset,\n };\n }\n if (t0.type === 'STAR') {\n this.consume();\n let max: number | undefined;\n let end = t0.endOffset;\n const next = this.peek();\n if (next.type === 'INT' && next.offset === t0.endOffset) {\n max = this.occurBound(this.consume());\n end = next.endOffset;\n }\n return {\n kind: 'occur',\n marker: '*',\n ...(max !== undefined ? { max } : {}),\n start: t0.offset,\n end,\n };\n }\n // `n*` / `n*m` — only when INT and '*' are adjacent (per the ABNF, occur\n // has no interior whitespace; adjacency is what distinguishes the\n // occurrence `1*2` from the value 1 followed by the occurrence `*2`).\n if (\n t0.type === 'INT' &&\n !t0.value.startsWith('-') &&\n this.peek(1).type === 'STAR' &&\n this.peek(1).offset === t0.endOffset\n ) {\n const min = this.occurBound(this.consume());\n const star = this.consume();\n let max: number | undefined;\n let end = star.endOffset;\n const next = this.peek();\n if (next.type === 'INT' && next.offset === star.endOffset) {\n max = this.occurBound(this.consume());\n end = next.endOffset;\n }\n return { kind: 'occur', marker: '*', min, max, start: t0.offset, end };\n }\n return undefined;\n }\n\n private occurBound(tok: CddlToken): number {\n if (tok.value.startsWith('-'))\n this._fail('occurrence bounds must be unsigned integers', tok);\n const n = Number(tok.value);\n if (!Number.isSafeInteger(n))\n this._fail('occurrence bound is too large', tok);\n return n;\n }\n\n // ─── Types ──────────────────────────────────────────────────────────────────\n\n /** type = type1 *(S \"/\" S type1) */\n private parseType(): CddlType {\n return this.continueTypeAlternatives(this.parseType1());\n }\n\n private continueTypeAlternatives(first: CddlType1): CddlType {\n const alternatives = [first];\n while (this.peek().type === 'SLASH') {\n this.consume();\n alternatives.push(this.parseType1());\n }\n return {\n kind: 'type',\n alternatives,\n start: first.start,\n end: alternatives[alternatives.length - 1]!.end,\n };\n }\n\n /** type1 = type2 [S (rangeop / ctlop) S type2] */\n private parseType1(): CddlType1 {\n return this.continueType1(this.parseType2());\n }\n\n private continueType1(target: CddlType2): CddlType1 {\n const opTok = this.peek();\n let op: CddlType1['op'];\n if (opTok.type === 'RANGE_INCL' || opTok.type === 'RANGE_EXCL')\n op = { kind: 'range', inclusive: opTok.type === 'RANGE_INCL' };\n else if (opTok.type === 'CTLOP') op = { kind: 'ctl', name: opTok.value };\n if (!op)\n return { kind: 'type1', target, start: target.start, end: target.end };\n this.consume();\n const controller = this.parseType2();\n return {\n kind: 'type1',\n target,\n op,\n controller,\n start: target.start,\n end: controller.end,\n };\n }\n\n private parseType2(): CddlType2 {\n const tok = this.peek();\n switch (tok.type) {\n case 'INT':\n case 'FLOAT':\n case 'TSTR':\n case 'BYTES':\n return this.parseValue();\n\n case 'ID': {\n this.consume();\n return this.parseRefTail(tok);\n }\n\n case 'LPAREN': {\n const lparen = this.consume();\n const type = this.parseType();\n const rparen = this.expect(\n 'RPAREN',\n `')' to close the parenthesized type`\n );\n return {\n kind: 'paren',\n type,\n start: lparen.offset,\n end: rparen.endOffset,\n };\n }\n\n case 'LBRACE': {\n const open = this.consume();\n const group = this.parseGroup('RBRACE');\n const close = this.consume();\n return {\n kind: 'map',\n group,\n start: open.offset,\n end: close.endOffset,\n };\n }\n\n case 'LBRACKET': {\n const open = this.consume();\n const group = this.parseGroup('RBRACKET');\n const close = this.consume();\n return {\n kind: 'array',\n group,\n start: open.offset,\n end: close.endOffset,\n };\n }\n\n case 'TILDE': {\n const tilde = this.consume();\n const nameTok = this.expect('ID', `a type name after '~'`);\n const ref = this.parseRefTail(nameTok);\n return { kind: 'unwrap', ref, start: tilde.offset, end: ref.end };\n }\n\n case 'AMP': {\n const amp = this.consume();\n if (this.peek().type === 'LPAREN') {\n this.consume();\n const group = this.parseGroup('RPAREN');\n const rparen = this.consume();\n return {\n kind: 'enum',\n group,\n start: amp.offset,\n end: rparen.endOffset,\n };\n }\n const nameTok = this.expect('ID', `a group name or '(' after '&'`);\n const ref = this.parseRefTail(nameTok);\n return { kind: 'enum', group: ref, start: amp.offset, end: ref.end };\n }\n\n case 'HASH':\n return this.parseHashType(this.consume());\n\n default:\n this._fail('expected a type', tok);\n }\n }\n\n /** Generic arguments after a just-consumed ID token: [genericarg]. */\n private parseRefTail(nameTok: CddlToken): CddlRef {\n if (this.peek().type !== 'LT')\n return {\n kind: 'ref',\n name: nameTok.value,\n start: nameTok.offset,\n end: nameTok.endOffset,\n };\n this.consume();\n const genericArgs = [this.parseType1()];\n while (this.peek().type === 'COMMA') {\n this.consume();\n genericArgs.push(this.parseType1());\n }\n const gt = this.expect('GT', `'>' after generic arguments`);\n return {\n kind: 'ref',\n name: nameTok.value,\n genericArgs,\n start: nameTok.offset,\n end: gt.endOffset,\n };\n }\n\n /**\n * '#' family, from a HASH token produced by the tokenizer:\n * \"#\" → any\n * \"#\" \"6\" [\".\" head-number] \"(\" type \")\" → tagged\n * \"#\" \"7\" [\".\" head-number] → major 7 (simple/float)\n * \"#\" DIGIT [\".\" uint] → major/ai\n * head-number = uint / \"<\" type \">\" (RFC 9682 §3.2)\n */\n private parseHashType(tok: CddlToken): CddlType2 {\n if (tok.hashMajor === undefined) {\n if (tok.hashAIExpr || tok.hashAI !== undefined)\n this._fail(`'#' without a major type cannot take a head-number`, tok);\n return { kind: 'any', start: tok.offset, end: tok.endOffset };\n }\n const major = tok.hashMajor;\n\n let head: bigint | CddlType | undefined = tok.hashAI;\n let headEnd = tok.endOffset;\n if (tok.hashAIExpr) {\n if (major !== 6 && major !== 7)\n this._fail(\n `a <type> head-number is only allowed for #6 and #7 (RFC 9682 §3.2)`,\n tok\n );\n this.expect('LT', `'<' for the head-number expression`);\n head = this.parseType();\n const gt = this.expect('GT', `'>' after the head-number expression`);\n headEnd = gt.endOffset;\n }\n\n // For a literal (or absent) head-number, keep the '#…' source text so the\n // formatter can preserve the number base (e.g. '#6.0x10').\n const raw = tok.hashAIExpr ? undefined : tok.raw;\n\n if (major === 6 && this.peek().type === 'LPAREN') {\n this.consume();\n const item = this.parseType();\n const rparen = this.expect('RPAREN', `')' to close the tagged type`);\n return {\n kind: 'tagged',\n ...(head !== undefined ? { tag: head } : {}),\n item,\n ...(raw !== undefined ? { raw } : {}),\n start: tok.offset,\n end: rparen.endOffset,\n };\n }\n if (tok.hashAIExpr && major === 6)\n this._fail(`#6.<…> must be followed by '(' type ')'`, this.peek());\n\n return {\n kind: 'major',\n major,\n ...(head !== undefined ? { ai: head } : {}),\n ...(raw !== undefined ? { raw } : {}),\n start: tok.offset,\n end: headEnd,\n };\n }\n\n // ─── Values ─────────────────────────────────────────────────────────────────\n\n private isValueToken(tok: CddlToken): boolean {\n return (\n tok.type === 'INT' ||\n tok.type === 'FLOAT' ||\n tok.type === 'TSTR' ||\n tok.type === 'BYTES'\n );\n }\n\n private parseValue(): CddlValue {\n const tok = this.consume();\n const base = { start: tok.offset, end: tok.endOffset, raw: tok.raw };\n switch (tok.type) {\n case 'INT': {\n // BigInt() rejects a sign on 0x/0b literals — apply it separately.\n const big = tok.value.startsWith('-')\n ? -BigInt(tok.value.slice(1))\n : BigInt(tok.value);\n const value =\n big >= BigInt(Number.MIN_SAFE_INTEGER) &&\n big <= BigInt(Number.MAX_SAFE_INTEGER)\n ? Number(big)\n : big;\n return { kind: 'value', type: 'int', value, ...base };\n }\n case 'FLOAT': {\n const value = /^-?0[xX]/.test(tok.value)\n ? parseHexFloat(tok.value)\n : parseFloat(tok.value);\n return { kind: 'value', type: 'float', value, ...base };\n }\n case 'TSTR':\n return { kind: 'value', type: 'text', value: tok.value, ...base };\n case 'BYTES':\n return {\n kind: 'value',\n type: 'bytes',\n value: tok.bytes!,\n qualifier: tok.qualifier!,\n ...base,\n };\n default:\n this._fail('expected a literal value', tok);\n }\n }\n\n /**\n * Reinterpret a parsed parenthesized group as a parenthesized *type* —\n * needed when a range/control operator, '/', or '=>' follows the ')'.\n * Only a group of exactly one plain entry (no occurrence, no member key,\n * no trailing comma, single choice) is a valid type.\n */\n private groupAsParenType(\n group: CddlGroup,\n lparen: CddlToken,\n rparen: CddlToken\n ): CddlType2 {\n const only =\n group.choices.length === 1 && group.choices[0]!.length === 1\n ? group.choices[0]![0]!\n : undefined;\n if (\n !only ||\n only.kind !== 'entry' ||\n only.occur ||\n only.memberKey ||\n group.trailingComma\n )\n this._fail(\n 'this parenthesized group is used as a type (an operator follows), but it contains group syntax',\n this.peek()\n );\n return {\n kind: 'paren',\n type: only.value,\n start: lparen.offset,\n end: rparen.endOffset,\n };\n }\n}\n","/**\n * The CDDL standard prelude (RFC 8610 Appendix D, normative).\n *\n * The prelude is automatically added to each CDDL file. It is technically a\n * postlude: it never disturbs the selection of the first user rule as the\n * root of the definition, and user rules shadow prelude names.\n */\n\nimport { parseCDDL } from './parser';\nimport type { CddlRule } from './ast';\n\n/** Verbatim text of the RFC 8610 Appendix D standard prelude. */\nexport const PRELUDE_CDDL = `any = #\n\nuint = #0\nnint = #1\nint = uint / nint\n\nbstr = #2\nbytes = bstr\ntstr = #3\ntext = tstr\n\ntdate = #6.0(tstr)\ntime = #6.1(number)\nnumber = int / float\nbiguint = #6.2(bstr)\nbignint = #6.3(bstr)\nbigint = biguint / bignint\ninteger = int / bigint\nunsigned = uint / biguint\ndecfrac = #6.4([e10: int, m: integer])\nbigfloat = #6.5([e2: int, m: integer])\neb64url = #6.21(any)\neb64legacy = #6.22(any)\neb16 = #6.23(any)\nencoded-cbor = #6.24(bstr)\nuri = #6.32(tstr)\nb64url = #6.33(tstr)\nb64legacy = #6.34(tstr)\nregexp = #6.35(tstr)\nmime-message = #6.36(tstr)\ncbor-any = #6.55799(any)\n\nfloat16 = #7.25\nfloat32 = #7.26\nfloat64 = #7.27\nfloat16-32 = float16 / float32\nfloat32-64 = float32 / float64\nfloat = float16-32 / float64\n\nfalse = #7.20\ntrue = #7.21\nbool = false / true\nnil = #7.22\nnull = nil\nundefined = #7.23\n`;\n\nlet cached: Map<string, CddlRule> | undefined;\n\n/** The parsed prelude rules by name, parsed once and cached. */\nexport function getPreludeRules(): Map<string, CddlRule> {\n if (!cached) {\n cached = new Map();\n for (const rule of parseCDDL(PRELUDE_CDDL).rules)\n cached.set(rule.name, rule);\n }\n return cached;\n}\n","/**\n * CDDL formatter: serialize rule ASTs back to CDDL text.\n *\n * Two layouts:\n * - Compact (default): one rule per line with single-space separators.\n * - Pretty (`indent` set): groups with more than one entry (or group\n * choices) put each entry on its own indented line; multi-line rules are\n * separated by blank lines.\n *\n * Literal values are emitted verbatim from their source text (`raw`), so\n * number bases, string escapes, and byte-string qualifiers survive a round\n * trip. With `preserveComments`, `;` comments are re-attached by position\n * and none is dropped: rule leading/trailing, before a rule body (after\n * `=`), on group entries, before a group's closing delimiter, and — for\n * comments inside inline-only positions such as type choices — on the\n * enclosing rule's line end. The compact layout cannot hold an interior\n * line comment (`;` runs to the end of the line), so it hoists body\n * comments above the rule and keeps only rule-level placements.\n */\n\nimport type { CddlComment } from './tokenizer';\nimport type {\n CddlGroup,\n CddlGroupEntry,\n CddlMemberKey,\n CddlOccur,\n CddlRef,\n CddlRule,\n CddlType,\n CddlType1,\n CddlType2,\n} from './ast';\n\nexport interface CddlFormatOptions {\n /**\n * Pretty-print groups with one entry per line, indented by this many\n * spaces (or by the given string). Omit for compact single-line rules.\n */\n indent?: number | string;\n /**\n * Re-emit `;` comments. Rule-level comments are kept in both layouts;\n * comments attached to group entries require `indent` (the pretty\n * layout). Only effective when the formatter has the comment stream and\n * source text — i.e. when called through `CddlSchema.format()`.\n */\n preserveComments?: boolean;\n}\n\n/** @internal Extras supplied by CddlSchema.format(). */\nexport interface CddlFormatContext {\n source?: string;\n comments?: readonly CddlComment[];\n}\n\ninterface Notes {\n leading: string[];\n trailing: string[];\n}\n\ninterface Ctx {\n /** Indent unit; null = compact layout. */\n unit: string | null;\n notes: Map<object, Notes> | null;\n /** Comments emitted before a group's closing delimiter. */\n endNotes: Map<CddlGroup, string[]> | null;\n /** Comments after the last rule (emitted at the end). */\n tail: string[];\n}\n\nconst EMPTY_NOTES: Notes = { leading: [], trailing: [] };\n\n/** Format rules (in the given order) as CDDL text with a trailing newline. */\nexport function formatCddl(\n rules: readonly CddlRule[],\n options?: CddlFormatOptions & CddlFormatContext\n): string {\n const unit =\n options?.indent === undefined\n ? null\n : typeof options.indent === 'string'\n ? options.indent\n : ' '.repeat(options.indent);\n const ctx: Ctx = { unit, notes: null, endNotes: null, tail: [] };\n if (\n options?.preserveComments &&\n options.comments !== undefined &&\n options.comments.length > 0 &&\n options.source !== undefined\n ) {\n const built = buildNotes(rules, options.comments, options.source);\n ctx.notes = built.notes;\n ctx.endNotes = built.endNotes;\n ctx.tail = built.tail;\n }\n\n const parts: string[] = [];\n let prevMultiline = false;\n rules.forEach((rule, i) => {\n const { text, multiline } = formatRule(rule, ctx);\n // Blank line around rules with multi-line bodies in the pretty layout\n // (leading comments alone do not count).\n if (i > 0 && ctx.unit !== null && (multiline || prevMultiline))\n parts.push('');\n parts.push(text);\n prevMultiline = multiline;\n });\n for (const text of ctx.tail) parts.push(`;${text}`);\n if (parts.length === 0) return '';\n return parts.join('\\n') + '\\n';\n}\n\n// ─── Comment attachment ──────────────────────────────────────────────────────\n\ninterface Anchor {\n node: object;\n start: number;\n end: number;\n isRule: boolean;\n}\n\n/**\n * Associate each comment with the position it will be emitted at, so that\n * `preserveComments` never drops one:\n * - trailing on the rule/entry ending on the comment's line;\n * - else leading on the next rule/entry — but only when that target stays\n * inside every group/rule enclosing the comment;\n * - else, for a comment inside a group with nothing after it (including\n * empty groups), on the group's end position (before the closer);\n * - else, for a comment inside a rule's type expression (e.g. between type\n * choices, which format inline), trailing on the rule;\n * - comments after everything go to `tail`.\n */\nfunction buildNotes(\n rules: readonly CddlRule[],\n comments: readonly CddlComment[],\n source: string\n): {\n notes: Map<object, Notes>;\n endNotes: Map<CddlGroup, string[]>;\n tail: string[];\n} {\n // Line-start offsets for offset→line lookups (comments carry their line).\n const lineStarts = [0];\n for (let i = 0; i < source.length; i++)\n if (source.charCodeAt(i) === 0x0a) lineStarts.push(i + 1);\n const lineOf = (offset: number): number => {\n let lo = 0;\n let hi = lineStarts.length - 1;\n while (lo < hi) {\n const mid = (lo + hi + 1) >> 1;\n if (lineStarts[mid]! <= offset) lo = mid;\n else hi = mid - 1;\n }\n return lo + 1; // 1-based, matching CddlComment.line\n };\n\n const anchors: Anchor[] = [];\n // Group containment uses the span of the *construct* holding the group\n // (including its delimiters) — an empty group's own span is zero-width.\n const groups: { group: CddlGroup; start: number; end: number }[] = [];\n const addGroup = (group: CddlGroup, start: number, end: number): void => {\n groups.push({ group, start, end });\n for (const choice of group.choices) choice.forEach(addEntry);\n };\n const addEntry = (entry: CddlGroupEntry): void => {\n anchors.push({\n node: entry,\n start: entry.start,\n end: entry.end,\n isRule: false,\n });\n if (entry.kind === 'entry-group') {\n addGroup(entry.group, entry.start, entry.end);\n return;\n }\n for (const t1 of entry.value.alternatives) addType1(t1);\n };\n const addType1 = (t1: CddlType1): void => {\n addType2(t1.target);\n if (t1.controller) addType2(t1.controller);\n };\n const addType2 = (t2: CddlType2): void => {\n switch (t2.kind) {\n case 'map':\n case 'array':\n addGroup(t2.group, t2.start, t2.end);\n return;\n case 'paren':\n for (const t1 of t2.type.alternatives) addType1(t1);\n return;\n case 'enum':\n if (t2.group.kind === 'group') addGroup(t2.group, t2.start, t2.end);\n return;\n case 'tagged':\n if (typeof t2.tag === 'object')\n for (const t1 of t2.tag.alternatives) addType1(t1);\n for (const t1 of t2.item.alternatives) addType1(t1);\n return;\n default:\n return;\n }\n };\n for (const rule of rules) {\n anchors.push({\n node: rule,\n start: rule.start,\n end: rule.end,\n isRule: true,\n });\n addEntry(rule.body);\n }\n\n // Trailing lookup: maximal end ≤ comment start; rules win end-ties so a\n // comment after `a = int` lands on the rule, not on its body entry.\n const byEnd = [...anchors].sort(\n (a, b) => a.end - b.end || Number(a.isRule) - Number(b.isRule)\n );\n // Leading lookup: minimal start ≥ comment end; rules win start-ties.\n const byStart = [...anchors].sort(\n (a, b) => a.start - b.start || Number(b.isRule) - Number(a.isRule)\n );\n\n const notes = new Map<object, Notes>();\n const endNotes = new Map<CddlGroup, string[]>();\n const tail: string[] = [];\n const notesFor = (node: object): Notes => {\n let n = notes.get(node);\n if (!n) {\n n = { leading: [], trailing: [] };\n notes.set(node, n);\n }\n return n;\n };\n\n for (const c of comments) {\n // Trailing: the anchor ending last at or before the comment, same line.\n let trailingTo: Anchor | undefined;\n for (let i = byEnd.length - 1; i >= 0; i--) {\n const a = byEnd[i]!;\n if (a.end > c.start) continue;\n if (lineOf(Math.max(a.start, a.end - 1)) === c.line) trailingTo = a;\n break;\n }\n if (trailingTo) {\n notesFor(trailingTo.node).trailing.push(c.text);\n continue;\n }\n\n // Innermost group / rule whose span encloses the comment.\n let containerGroup:\n { group: CddlGroup; start: number; end: number } | undefined;\n for (const g of groups)\n if (\n g.start <= c.start &&\n c.end <= g.end &&\n (!containerGroup || g.start >= containerGroup.start)\n )\n containerGroup = g;\n const containerRule = rules.find(\n (r) => r.start <= c.start && c.end <= r.end\n );\n\n // Leading on the next rule/entry — only when that target does not\n // escape an enclosing construct (which would move the comment outside).\n const leadingTo = byStart.find((a) => a.start >= c.end);\n const escapesGroup =\n containerGroup !== undefined &&\n (leadingTo === undefined || leadingTo.start > containerGroup.end);\n const escapesRule =\n containerRule !== undefined &&\n (leadingTo === undefined || leadingTo.start > containerRule.end);\n if (leadingTo && !escapesGroup && !escapesRule) {\n notesFor(leadingTo.node).leading.push(c.text);\n } else if (escapesGroup) {\n // Nothing follows inside the group (or it is empty): emit the\n // comment just before the group's closing delimiter.\n const list = endNotes.get(containerGroup!.group) ?? [];\n list.push(c.text);\n endNotes.set(containerGroup!.group, list);\n } else if (escapesRule) {\n // Inside the rule's type expression (choices format inline): keep it\n // on the rule line as a trailing comment.\n notesFor(containerRule!).trailing.push(c.text);\n } else if (leadingTo) {\n notesFor(leadingTo.node).leading.push(c.text);\n } else {\n tail.push(c.text);\n }\n }\n return { notes, endNotes, tail };\n}\n\n// ─── Emission ─────────────────────────────────────────────────────────────────\n\nconst notesOf = (ctx: Ctx, node: object): Notes =>\n ctx.notes?.get(node) ?? EMPTY_NOTES;\n\nconst trailingText = (notes: Notes): string =>\n notes.trailing.length === 0\n ? ''\n : ' ' + notes.trailing.map((t) => `;${t}`).join(' ');\n\nfunction formatRule(\n rule: CddlRule,\n ctx: Ctx\n): { text: string; multiline: boolean } {\n const notes = notesOf(ctx, rule);\n const bodyNotes = notesOf(ctx, rule.body);\n const generics = rule.generics ? `<${rule.generics.join(', ')}>` : '';\n const head = `${rule.name}${generics} ${rule.assign}`;\n const trailing = trailingText({\n leading: [],\n trailing: [...bodyNotes.trailing, ...notes.trailing],\n });\n\n let main: string;\n let leading = notes.leading;\n if (bodyNotes.leading.length > 0 && ctx.unit !== null) {\n // Comments between `=` and the body get their own indented lines:\n // a =\n // ; important\n // int\n const pad = ctx.unit;\n main = [\n head,\n ...bodyNotes.leading.map((t) => `${pad};${t}`),\n `${pad}${formatEntry(rule.body, ctx, 1)}${trailing}`,\n ].join('\\n');\n } else {\n // Compact layout cannot hold a mid-line comment: hoist body-leading\n // comments above the rule so they are never dropped.\n if (bodyNotes.leading.length > 0)\n leading = [...leading, ...bodyNotes.leading];\n main = `${head} ${formatEntry(rule.body, ctx, 0)}${trailing}`;\n }\n\n const multiline = main.includes('\\n');\n if (leading.length === 0) return { text: main, multiline };\n return {\n text: [...leading.map((t) => `;${t}`), main].join('\\n'),\n multiline,\n };\n}\n\nfunction formatEntry(entry: CddlGroupEntry, ctx: Ctx, depth: number): string {\n const occur = entry.occur ? `${formatOccur(entry.occur)} ` : '';\n if (entry.kind === 'entry-group')\n return `${occur}${formatGroupBody(entry.group, ctx, depth, '(', ')')}`;\n const key = entry.memberKey\n ? `${formatMemberKey(entry.memberKey, ctx, depth)} `\n : '';\n return `${occur}${key}${formatType(entry.value, ctx, depth)}`;\n}\n\nfunction formatOccur(occur: CddlOccur): string {\n if (occur.marker !== '*') return occur.marker;\n return `${occur.min ?? ''}*${occur.max ?? ''}`;\n}\n\nfunction formatMemberKey(key: CddlMemberKey, ctx: Ctx, depth: number): string {\n switch (key.kind) {\n case 'bareword':\n return `${key.key}:`;\n case 'value':\n return `${key.key.raw}:`;\n case 'type1':\n return `${formatType1(key.key, ctx, depth)} ${key.cut ? '^ ' : ''}=>`;\n }\n}\n\n/**\n * A group between `open`/`close` delimiters. In the pretty layout, groups\n * with more than one entry (or more than one choice) are laid out one entry\n * per line; group choices are separated by a `//` line.\n */\nfunction formatGroupBody(\n group: CddlGroup,\n ctx: Ctx,\n depth: number,\n open: string,\n close: string\n): string {\n const entryCount = group.choices.reduce((n, c) => n + c.length, 0);\n const endComments = ctx.endNotes?.get(group) ?? [];\n // Any comment inside the group forces the multi-line layout — an inline\n // group cannot hold a `;` comment (it runs to the end of the line).\n const hasNotes =\n endComments.length > 0 ||\n (ctx.notes !== null &&\n group.choices.some((c) => c.some((e) => ctx.notes!.has(e))));\n const multiline =\n ctx.unit !== null &&\n (entryCount > 1 || group.choices.length > 1 || hasNotes);\n\n if (!multiline) {\n const body =\n group.choices\n .map((entries) =>\n entries.map((e) => formatEntry(e, ctx, depth)).join(', ')\n )\n .join(' // ') + (group.trailingComma ? ',' : '');\n return `${open}${body}${close}`;\n }\n\n const unit = ctx.unit!;\n const pad = unit.repeat(depth + 1);\n const lines: string[] = [open];\n group.choices.forEach((entries, ci) => {\n if (ci > 0) lines.push(`${pad}//`);\n entries.forEach((entry, ei) => {\n const notes = notesOf(ctx, entry);\n for (const t of notes.leading) lines.push(`${pad};${t}`);\n const isLast =\n ci === group.choices.length - 1 && ei === entries.length - 1;\n const comma = !isLast || group.trailingComma ? ',' : '';\n lines.push(\n `${pad}${formatEntry(entry, ctx, depth + 1)}${comma}${trailingText(notes)}`\n );\n });\n });\n // Comments with nothing after them inside the group (including comments\n // in empty groups) sit just before the closing delimiter.\n for (const t of endComments) lines.push(`${pad};${t}`);\n lines.push(`${unit.repeat(depth)}${close}`);\n return lines.join('\\n');\n}\n\nfunction formatType(type: CddlType, ctx: Ctx, depth: number): string {\n return type.alternatives.map((t1) => formatType1(t1, ctx, depth)).join(' / ');\n}\n\nfunction formatType1(type1: CddlType1, ctx: Ctx, depth: number): string {\n const target = formatType2(type1.target, ctx, depth);\n if (!type1.op || !type1.controller) return target;\n const controller = formatType2(type1.controller, ctx, depth);\n if (type1.op.kind === 'range')\n return `${target}${type1.op.inclusive ? '..' : '...'}${controller}`;\n return `${target} .${type1.op.name} ${controller}`;\n}\n\nfunction formatRef(ref: CddlRef, ctx: Ctx, depth: number): string {\n const args = ref.genericArgs\n ? `<${ref.genericArgs.map((a) => formatType1(a, ctx, depth)).join(', ')}>`\n : '';\n return `${ref.name}${args}`;\n}\n\nfunction formatType2(type2: CddlType2, ctx: Ctx, depth: number): string {\n switch (type2.kind) {\n case 'value':\n return type2.raw;\n case 'ref':\n return formatRef(type2, ctx, depth);\n case 'paren':\n return `(${formatType(type2.type, ctx, depth)})`;\n case 'map':\n return formatGroupBody(type2.group, ctx, depth, '{', '}');\n case 'array':\n return formatGroupBody(type2.group, ctx, depth, '[', ']');\n case 'unwrap':\n return `~${formatRef(type2.ref, ctx, depth)}`;\n case 'enum':\n return type2.group.kind === 'ref'\n ? `&${formatRef(type2.group, ctx, depth)}`\n : `&${formatGroupBody(type2.group, ctx, depth, '(', ')')}`;\n case 'tagged': {\n const head =\n type2.raw ??\n (typeof type2.tag === 'object'\n ? `#6.<${formatType(type2.tag, ctx, depth)}>`\n : `#6${type2.tag === undefined ? '' : `.${type2.tag}`}`);\n return `${head}(${formatType(type2.item, ctx, depth)})`;\n }\n case 'major': {\n if (type2.raw !== undefined) return type2.raw;\n return typeof type2.ai === 'object'\n ? `#${type2.major}.<${formatType(type2.ai, ctx, depth)}>`\n : `#${type2.major}${type2.ai === undefined ? '' : `.${type2.ai}`}`;\n }\n case 'any':\n return '#';\n }\n}\n","/**\n * Structural equality and value-access helpers over CBOR AST nodes,\n * used by the CDDL validator for literal matching, map-key comparison,\n * enumerations, and the .eq/.ne control operators.\n *\n * Equality is CDDL value equality, not byte equality: encoding widths and\n * definite/indefinite length are ignored (an indefinite-length \"a\", \"b\"\n * equals the definite \"ab\"), but CBOR type classes stay distinct — an\n * integer never equals a float, and a bignum (tag 2/3) never equals a\n * plain integer.\n */\n\nimport { CborItem } from '../ast/CborItem';\nimport { CborUint } from '../ast/CborUint';\nimport { CborNint } from '../ast/CborNint';\nimport { CborFloat } from '../ast/CborFloat';\nimport { CborSimple } from '../ast/CborSimple';\nimport { CborTextString } from '../ast/CborTextString';\nimport { CborIndefiniteTextString } from '../ast/CborIndefiniteTextString';\nimport { CborByteString } from '../ast/CborByteString';\nimport { CborIndefiniteByteString } from '../ast/CborIndefiniteByteString';\nimport { CborEmbeddedCBOR } from '../ast/CborEmbeddedCBOR';\nimport { CborArray } from '../ast/CborArray';\nimport { CborMap } from '../ast/CborMap';\nimport { CborTag } from '../ast/CborTag';\nimport { CborBigUint, CborBigNint } from '../ast/CborBignum';\n\n/**\n * The integer value of a node, including bignums (tags 2/3): CDDL *values*\n * are abstract numbers, so literals, ranges, and comparison operators must\n * see 2^64 the same way whether it arrived as a basic int or as a bignum.\n * (Type matching stays structural: a bignum is a tagged item, not #0/#1.)\n */\nexport function intValueOf(item: CborItem): bigint | undefined {\n if (item instanceof CborUint || item instanceof CborNint) return item.value;\n if (item instanceof CborBigUint || item instanceof CborBigNint)\n return item.bigValue;\n return undefined;\n}\n\n/** The text value of a (possibly indefinite-length) text string node. */\nexport function textValue(item: CborItem): string | undefined {\n if (item instanceof CborTextString) return item.value;\n if (item instanceof CborIndefiniteTextString)\n return item.chunks.map((c) => c.value).join('');\n return undefined;\n}\n\n/**\n * The byte content of a byte-string-like node: a (possibly\n * indefinite-length) byte string, or an `<<…>>` embedded-CBOR literal\n * (whose value is the encoding of its items).\n */\nexport function byteValue(item: CborItem): Uint8Array | undefined {\n if (item instanceof CborByteString) return item.value;\n if (item instanceof CborIndefiniteByteString) {\n const parts = item.chunks.map((c) => c.value);\n const total = parts.reduce((n, p) => n + p.length, 0);\n const out = new Uint8Array(total);\n let off = 0;\n for (const p of parts) {\n out.set(p, off);\n off += p.length;\n }\n return out;\n }\n if (item instanceof CborEmbeddedCBOR) {\n const parts = item.items.map((i) => i.toCBOR());\n const total = parts.reduce((n, p) => n + p.length, 0);\n const out = new Uint8Array(total);\n let off = 0;\n for (const p of parts) {\n out.set(p, off);\n off += p.length;\n }\n return out;\n }\n return undefined;\n}\n\nexport function bytesEqual(a: Uint8Array, b: Uint8Array): boolean {\n if (a.length !== b.length) return false;\n for (let i = 0; i < a.length; i++) if (a[i] !== b[i]) return false;\n return true;\n}\n\n/** CDDL value equality of two CBOR AST nodes (see module doc). */\nexport function equalItems(a: CborItem, b: CborItem): boolean {\n if (a === b) return true;\n\n if (a instanceof CborUint)\n return b instanceof CborUint && a.value === b.value;\n if (a instanceof CborNint)\n return b instanceof CborNint && a.value === b.value;\n if (a instanceof CborFloat)\n return (\n b instanceof CborFloat &&\n (a.value === b.value || (Number.isNaN(a.value) && Number.isNaN(b.value)))\n );\n if (a instanceof CborSimple)\n return b instanceof CborSimple && a.value === b.value;\n\n const aText = textValue(a);\n if (aText !== undefined) {\n const bText = textValue(b);\n return bText !== undefined && aText === bText;\n }\n const aBytes = byteValue(a);\n if (aBytes !== undefined) {\n const bBytes = byteValue(b);\n return bBytes !== undefined && bytesEqual(aBytes, bBytes);\n }\n\n if (a instanceof CborArray)\n return (\n b instanceof CborArray &&\n a.items.length === b.items.length &&\n a.items.every((item, i) => equalItems(item, b.items[i]!))\n );\n\n if (a instanceof CborMap) {\n if (!(b instanceof CborMap) || a.entries.length !== b.entries.length)\n return false;\n // Order-insensitive with one-to-one consumption.\n const used = new Array<boolean>(b.entries.length).fill(false);\n for (const [ak, av] of a.entries) {\n let found = false;\n for (let i = 0; i < b.entries.length; i++) {\n if (used[i]) continue;\n const [bk, bv] = b.entries[i]!;\n if (equalItems(ak, bk) && equalItems(av, bv)) {\n used[i] = true;\n found = true;\n break;\n }\n }\n if (!found) return false;\n }\n return true;\n }\n\n // Tags last: bignums, embedded app extensions, etc. are CborTag subclasses.\n if (a instanceof CborTag)\n return (\n b instanceof CborTag &&\n a.tag === b.tag &&\n equalItems(a.content, b.content)\n );\n\n return false;\n}\n","/**\n * Control operator implementations (RFC 8610 §3.8 plus RFC 9165 .plus /\n * .cat / .feature), table-driven and injected with the validator's matching\n * primitives to avoid an import cycle.\n *\n * Operators that are not in the table (.det, .abnf, .abnfb, the RFC 9741\n * text-conversion set, and anything unknown) are reported as a warning by\n * the validator, which then matches the target without the constraint.\n */\n\nimport type { CborItem } from '../ast/CborItem';\nimport { CborUint } from '../ast/CborUint';\nimport { CborFloat } from '../ast/CborFloat';\nimport { decodeCBOR } from '../cbor/decoder';\nimport { textValue, byteValue, intValueOf } from './equal';\nimport type { CddlNodeBase, CddlType2, CddlValue } from './ast';\n\ntype Path = readonly (string | number)[];\n\n/** Matching primitives provided by the validator (closed over env/ctx). */\nexport interface ControlDeps {\n matchType2(item: CborItem, t2: CddlType2, path: Path): boolean;\n /** Like matchType2, but suppresses instance offsets in recorded errors —\n * the item was decoded out of an embedded byte string, so its offsets\n * are relative to the embedded bytes, not the outer document. */\n matchEmbedded(item: CborItem, t2: CddlType2, path: Path): boolean;\n resolveValue(t2: CddlType2): CddlValue | undefined;\n /** Whether some integer ≥ min matches the type; undefined = unanalyzable. */\n existsIntGE(t2: CddlType2, min: bigint): boolean | undefined;\n matchesLiteral(item: CborItem, v: CddlValue): boolean;\n fail(\n path: Path,\n item: CborItem | undefined,\n node: CddlNodeBase | undefined,\n message: string\n ): false;\n warnOnce(message: string, node?: CddlNodeBase): void;\n features: ReadonlySet<string>;\n uint(n: number | bigint): CborItem;\n}\n\nexport type ControlHandler = (\n deps: ControlDeps,\n item: CborItem,\n target: CddlType2,\n controller: CddlType2,\n path: Path,\n node: CddlNodeBase\n) => boolean;\n\nconst textEncoder = new TextEncoder();\nconst utf8Strict = new TextDecoder('utf-8', { fatal: true });\n\n/** Synthesize a literal value for computed operators (.plus, .cat). */\nconst synthValue = (\n v:\n | { type: 'int'; value: number | bigint }\n | { type: 'float'; value: number }\n | { type: 'text'; value: string }\n | { type: 'bytes'; value: Uint8Array; qualifier: '' | 'h' | 'b64' }\n): CddlValue =>\n ({ kind: 'value', raw: '', start: 0, end: 0, ...v }) as CddlValue;\n\nconst numericOf = (item: CborItem): bigint | number | undefined => {\n // Includes bignums (tags 2/3): CDDL values are abstract numbers.\n const int = intValueOf(item);\n if (int !== undefined) return int;\n if (item instanceof CborFloat) return item.value;\n return undefined;\n};\n\nconst valueNumeric = (v: CddlValue): bigint | number | undefined =>\n v.type === 'int' || v.type === 'float' ? v.value : undefined;\n\n/** Compare possibly-mixed bigint/number numerics: -1, 0, 1 (NaN → NaN). */\nconst cmp = (a: bigint | number, b: bigint | number): number => {\n if (typeof a === 'bigint' && typeof b === 'bigint')\n return a < b ? -1 : a > b ? 1 : 0;\n const an = Number(a);\n const bn = Number(b);\n return an < bn ? -1 : an > bn ? 1 : an === bn ? 0 : NaN;\n};\n\n// ─── RFC 8610 §3.8 ────────────────────────────────────────────────────────────\n\nconst size: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const checkSize = (n: number | bigint): boolean =>\n deps.matchType2(deps.uint(n), controller, path)\n ? true\n : deps.fail(\n path,\n item,\n node,\n `size ${n} does not match the .size constraint`\n );\n const text = textValue(item);\n if (text !== undefined) return checkSize(textEncoder.encode(text).length);\n const bytes = byteValue(item);\n if (bytes !== undefined) return checkSize(bytes.length);\n if (item instanceof CborUint) {\n // uint .size N means 0 ≤ value < 256^N (no upper limit on N): the value\n // fits iff the controller's integer set intersects [minBytes, ∞).\n let minBytes = 0;\n for (let v = item.value; v > 0n; v >>= 8n) minBytes++;\n const exists = deps.existsIntGE(controller, BigInt(minBytes));\n if (exists !== undefined)\n return exists\n ? true\n : deps.fail(\n path,\n item,\n node,\n `${item.value} does not fit the .size constraint`\n );\n // The controller could not be analyzed structurally (e.g. it uses a\n // control operator); fall back to a bounded search and say so.\n deps.warnOnce(\n '.size controller could not be analyzed; searching a bounded window of byte counts',\n node\n );\n for (let n = minBytes; n <= minBytes + 64; n++)\n if (deps.matchType2(deps.uint(n), controller, path)) return true;\n return deps.fail(\n path,\n item,\n node,\n `${item.value} does not fit the .size constraint`\n );\n }\n return deps.fail(\n path,\n item,\n node,\n '.size applies to strings and unsigned integers'\n );\n};\n\nconst bits: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const positions: number[] = [];\n const bytes = byteValue(item);\n if (bytes !== undefined) {\n // Bit n of the string means (str[n >> 3] & (1 << (n & 7))) != 0 (§3.8.2).\n for (let i = 0; i < bytes.length; i++)\n for (let j = 0; j < 8; j++)\n if (bytes[i]! & (1 << j)) positions.push(i * 8 + j);\n } else if (item instanceof CborUint) {\n let v = item.value;\n for (let n = 0; v > 0n; n++, v >>= 1n) if (v & 1n) positions.push(n);\n } else {\n return deps.fail(\n path,\n item,\n node,\n '.bits applies to byte strings and unsigned integers'\n );\n }\n for (const n of positions)\n if (!deps.matchType2(deps.uint(n), controller, path))\n return deps.fail(\n path,\n item,\n node,\n `bit ${n} is set but not allowed by .bits`\n );\n return true;\n};\n\nconst regexpCache = new Map<string, RegExp | null>();\n\nconst regexp: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const text = textValue(item);\n if (text === undefined)\n return deps.fail(path, item, node, '.regexp applies to text strings');\n const c = deps.resolveValue(controller);\n if (!c || c.type !== 'text') {\n deps.warnOnce(\n '.regexp controller does not resolve to a text string; not checked',\n node\n );\n return true;\n }\n // Approximation: the spec prescribes XSD regular expressions; we compile\n // the pattern as an anchored JavaScript RegExp with the 'u' flag, which\n // covers common patterns but differs in some character-class details.\n let re = regexpCache.get(c.value);\n if (re === undefined) {\n try {\n re = new RegExp(`^(?:${c.value})$`, 'u');\n } catch {\n re = null;\n }\n regexpCache.set(c.value, re);\n }\n if (re === null) {\n deps.warnOnce(\n `.regexp pattern is not a valid regular expression here: ${c.value}`,\n node\n );\n return true;\n }\n return re.test(text)\n ? true\n : deps.fail(\n path,\n item,\n node,\n `text does not match .regexp ${JSON.stringify(c.value)}`\n );\n};\n\nconst makeCborControl =\n (seq: boolean): ControlHandler =>\n (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const bytes = byteValue(item);\n if (bytes === undefined)\n return deps.fail(\n path,\n item,\n node,\n `.cbor${seq ? 'seq' : ''} applies to byte strings`\n );\n let decoded: CborItem;\n try {\n if (seq) {\n // §3.8.4: wrap the sequence between 0x9f/0xff and decode as an\n // indefinite-length array.\n const wrapped = new Uint8Array(bytes.length + 2);\n wrapped[0] = 0x9f;\n wrapped.set(bytes, 1);\n wrapped[wrapped.length - 1] = 0xff;\n decoded = decodeCBOR(wrapped);\n } else {\n decoded = decodeCBOR(bytes);\n }\n } catch (e) {\n return deps.fail(\n path,\n item,\n node,\n `byte string does not contain valid CBOR: ${e instanceof Error ? e.message : String(e)}`\n );\n }\n return deps.matchEmbedded(decoded, controller, path)\n ? true\n : deps.fail(\n path,\n item,\n node,\n `embedded CBOR does not match the .cbor${seq ? 'seq' : ''} type`\n );\n };\n\nconst within: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n return deps.matchType2(item, controller, path)\n ? true\n : deps.fail(\n path,\n item,\n node,\n 'value does not match the .within/.and constraint'\n );\n};\n\nconst makeCompare =\n (op: 'lt' | 'le' | 'gt' | 'ge'): ControlHandler =>\n (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const c = deps.resolveValue(controller);\n const bound = c && valueNumeric(c);\n if (bound === undefined) {\n deps.warnOnce(\n `.${op} controller does not resolve to a number; not checked`,\n node\n );\n return true;\n }\n const v = numericOf(item);\n if (v === undefined)\n return deps.fail(path, item, node, `.${op} applies to numbers`);\n const d = cmp(v, bound);\n const ok =\n op === 'lt' ? d < 0 : op === 'le' ? d <= 0 : op === 'gt' ? d > 0 : d >= 0;\n return ok\n ? true\n : deps.fail(path, item, node, `${v} does not satisfy .${op} ${bound}`);\n };\n\nconst eq: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const c = deps.resolveValue(controller);\n if (!c) {\n deps.warnOnce(\n '.eq controller does not resolve to a literal value; not checked',\n node\n );\n return true;\n }\n return deps.matchesLiteral(item, c)\n ? true\n : deps.fail(\n path,\n item,\n node,\n `value does not equal ${c.raw || '.eq controller'}`\n );\n};\n\nconst ne: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const c = deps.resolveValue(controller);\n if (!c) {\n deps.warnOnce(\n '.ne controller does not resolve to a literal value; not checked',\n node\n );\n return true;\n }\n return deps.matchesLiteral(item, c)\n ? deps.fail(\n path,\n item,\n node,\n `value must not equal ${c.raw || '.ne controller'}`\n )\n : true;\n};\n\nconst dflt: ControlHandler = (deps, item, target, controller, path, node) => {\n // .default is a variant of .ne: \"the implied .ne control is there to\n // prevent this value from being sent over the wire\" (RFC 8610 §3.8.6),\n // so the default value itself does not validate.\n if (!deps.matchType2(item, target, path)) return false;\n const c = deps.resolveValue(controller);\n if (!c) {\n deps.warnOnce(\n '.default controller does not resolve to a literal value; the implied .ne is not checked',\n node\n );\n return true;\n }\n return deps.matchesLiteral(item, c)\n ? deps.fail(\n path,\n item,\n node,\n `value equals the default ${c.raw || 'value'} (implied .ne, RFC 8610 §3.8.6)`\n )\n : true;\n};\n\n// ─── RFC 9165 ─────────────────────────────────────────────────────────────────\n\nconst plus: ControlHandler = (deps, item, target, controller, path, node) => {\n const t = deps.resolveValue(target);\n const c = deps.resolveValue(controller);\n const tv = t && valueNumeric(t);\n const cv = c && valueNumeric(c);\n if (t === undefined || tv === undefined || cv === undefined) {\n deps.warnOnce(\n '.plus operands do not resolve to numbers; not checked',\n node\n );\n return deps.fail(path, item, node, '.plus could not be computed');\n }\n // The sum is converted to the type of the target; float→int rounds\n // towards negative infinity (RFC 9165 §2.1).\n if (t!.type === 'float') {\n const sum = Number(tv) + Number(cv);\n return deps.matchesLiteral(item, synthValue({ type: 'float', value: sum }))\n ? true\n : deps.fail(path, item, node, `expected ${sum} (.plus)`);\n }\n // Integer target: compute in bigint so values beyond 2^53 stay exact.\n // An integer CddlValue is only a `number` when within the safe range, so\n // BigInt(tv) is lossless; for a float controller, floor(int + x) equals\n // int + floor(x), keeping the big integer part untouched.\n if (typeof cv === 'number' && !Number.isFinite(cv))\n return deps.fail(path, item, node, '.plus controller is not finite');\n const sum =\n (typeof tv === 'bigint' ? tv : BigInt(tv)) +\n (typeof cv === 'bigint' ? cv : BigInt(Math.floor(cv)));\n return deps.matchesLiteral(item, synthValue({ type: 'int', value: sum }))\n ? true\n : deps.fail(path, item, node, `expected ${sum} (.plus)`);\n};\n\nconst cat: ControlHandler = (deps, item, target, controller, path, node) => {\n const t = deps.resolveValue(target);\n const c = deps.resolveValue(controller);\n const toBytes = (v: CddlValue): Uint8Array | undefined =>\n v.type === 'text'\n ? textEncoder.encode(v.value)\n : v.type === 'bytes'\n ? v.value\n : undefined;\n const tb = t && toBytes(t);\n const cb = c && toBytes(c);\n if (!t || tb === undefined || cb === undefined) {\n deps.warnOnce('.cat operands do not resolve to strings; not checked', node);\n return deps.fail(path, item, node, '.cat could not be computed');\n }\n const joined = new Uint8Array(tb.length + cb.length);\n joined.set(tb, 0);\n joined.set(cb, tb.length);\n // The result has the type of the target (RFC 9165 §2.2).\n if (t.type === 'text') {\n let text: string;\n try {\n text = utf8Strict.decode(joined);\n } catch {\n return deps.fail(path, item, node, '.cat result is not valid UTF-8');\n }\n return deps.matchesLiteral(item, synthValue({ type: 'text', value: text }))\n ? true\n : deps.fail(path, item, node, `expected ${JSON.stringify(text)} (.cat)`);\n }\n return deps.matchesLiteral(\n item,\n synthValue({ type: 'bytes', value: joined, qualifier: 'h' })\n )\n ? true\n : deps.fail(path, item, node, 'byte string does not equal the .cat result');\n};\n\n/** Peel `( … )` layers off a type2 (single plain alternative only). */\nconst stripParens = (t2: CddlType2): CddlType2 => {\n while (\n t2.kind === 'paren' &&\n t2.type.alternatives.length === 1 &&\n !t2.type.alternatives[0]!.op\n )\n t2 = t2.type.alternatives[0]!.target;\n return t2;\n};\n\n/**\n * The .feature controller is a feature name, or an array whose first\n * element is the feature name and whose rest is detail (RFC 9165 §5) —\n * either form may be parenthesized, e.g. `.feature ([\"x\", \"detail\"])`.\n */\nexport const featureName = (\n deps: ControlDeps,\n controller: CddlType2\n): string | undefined => {\n let t2 = stripParens(controller);\n if (t2.kind === 'array') {\n const first = t2.group.choices[0]?.[0];\n if (\n !first ||\n first.kind !== 'entry' ||\n first.value.alternatives.length !== 1 ||\n first.value.alternatives[0]!.op\n )\n return undefined;\n t2 = first.value.alternatives[0]!.target;\n }\n const c = deps.resolveValue(t2);\n return c?.type === 'text' ? c.value : undefined;\n};\n\nconst feature: ControlHandler = (\n deps,\n item,\n target,\n controller,\n path,\n node\n) => {\n const name = featureName(deps, controller);\n if (name === undefined) {\n deps.warnOnce(\n '.feature controller does not resolve to a feature name',\n node\n );\n return deps.fail(path, item, node, 'unresolvable .feature');\n }\n if (!deps.features.has(name)) {\n deps.warnOnce(\n `feature \"${name}\" is not enabled (pass it in options.features to accept it)`,\n node\n );\n return deps.fail(path, item, node, `feature \"${name}\" is not enabled`);\n }\n return deps.matchType2(item, target, path);\n};\n\n// ─── Table ────────────────────────────────────────────────────────────────────\n\nconst CONTROLS: Record<string, ControlHandler> = {\n size,\n bits,\n regexp,\n cbor: makeCborControl(false),\n cborseq: makeCborControl(true),\n within,\n and: within,\n lt: makeCompare('lt'),\n le: makeCompare('le'),\n gt: makeCompare('gt'),\n ge: makeCompare('ge'),\n eq,\n ne,\n default: dflt,\n plus,\n cat,\n feature,\n};\n\nexport function getControl(name: string): ControlHandler | undefined {\n return Object.prototype.hasOwnProperty.call(CONTROLS, name)\n ? CONTROLS[name]\n : undefined;\n}\n","/**\n * CDDL validation engine: matches a CBOR AST (CborItem) against a compiled\n * CDDL schema (CddlSchema).\n *\n * Design notes:\n * - Arrays are matched by backtracking over the group's occurrence\n * indicators (regex-style over the item sequence), enumerating the\n * possible end positions of each sub-group.\n * - Maps are matched by consuming entries: group entries are processed in\n * definition order and greedily consume matching map entries; member keys\n * with cut semantics (`:` and `^ =>`, RFC 8610 §3.5.4) commit to an entry\n * once its key matches, failing the whole map when the value mismatches.\n * - Failures discarded by backtracking are noise; only the failure that\n * reached furthest into the instance source is reported.\n * - `maxSteps` / `maxDepth` bound pathological backtracking and unbounded\n * recursion; exceeding them aborts validation with an explanatory error.\n * - A CDN elision (`...`, CborEllipsis) matches any single item or map\n * entry; container lengths and required counts still apply.\n */\n\nimport type { CddlSchema } from './schema';\nimport { getPreludeRules } from './prelude';\nimport { CborItem } from '../ast/CborItem';\nimport { CborUint } from '../ast/CborUint';\nimport { CborNint } from '../ast/CborNint';\nimport { CborFloat } from '../ast/CborFloat';\nimport { CborSimple } from '../ast/CborSimple';\nimport { CborArray } from '../ast/CborArray';\nimport { CborMap } from '../ast/CborMap';\nimport { CborTag } from '../ast/CborTag';\nimport { CborEllipsis } from '../ast/CborEllipsis';\nimport { CborAppSeqResult } from '../ast/CborAppSeqResult';\nimport { autoSelectFloatPrecision } from '../cbor/encode';\nimport { textValue, byteValue, bytesEqual, intValueOf } from './equal';\nimport type {\n CddlValidationError,\n CddlValidationWarning,\n ValidationResult,\n} from './errors';\nimport type {\n CddlGroup,\n CddlGroupEntry,\n CddlMemberKey,\n CddlNodeBase,\n CddlRef,\n CddlRule,\n CddlType,\n CddlType1,\n CddlType2,\n CddlValue,\n} from './ast';\nimport { featureName, getControl, type ControlDeps } from './controls';\n\nexport interface ValidateOptions {\n /** Recursion guard for rule references and nested groups (default 256). */\n maxDepth?: number;\n /** Total backtracking step budget (default 1e6). */\n maxSteps?: number;\n /** Feature names accepted by the `.feature` control operator. */\n features?: string[];\n /**\n * Name of the rule to validate against, in place of the schema's root\n * (the first rule in source order — RFC 8610 §3.1 defines only one root\n * per model). Any non-generic rule usable as a type can be selected,\n * defined in the schema or its prelude — e.g. a variant used only as a\n * component elsewhere.\n *\n * An unknown name fails validation (`errors[0].message` is `'<name>' is\n * not defined`) rather than throwing, matching how an unresolved `$ref`\n * inside the schema is reported. A generic rule (`g<T> = ...`) also fails\n * validation rather than throwing: there is no `genericArgs` site to bind\n * its parameters from here, so it cannot be selected directly. Likewise a\n * group-only rule fails with `group rule '<name>' cannot be used as a\n * type`, exactly as when such a rule is referenced in type position.\n */\n rule?: string;\n}\n\n// ─── Context ──────────────────────────────────────────────────────────────────\n\ntype PathSeg = string | number;\n\n/** Generic parameter bindings; each binding closes over its defining env. */\ntype Env = Map<string, { type1: CddlType1; env: Env }> | undefined;\n\nclass LimitExceeded extends Error {}\n\nclass Ctx {\n steps = 0;\n ruleName: string | undefined;\n /** >0 while matching content decoded out of a .cbor/.cborseq byte string,\n * whose node offsets are relative to the embedded bytes — meaningless in\n * the outer document, so they are suppressed. */\n embeddedDepth = 0;\n /** >0 while matching inside a prelude rule, whose node offsets point into\n * the prelude text; errors are anchored to the referencing user node. */\n preludeDepth = 0;\n preludeRef: CddlNodeBase | undefined;\n readonly warnings: CddlValidationWarning[] = [];\n private readonly warned = new Set<string>();\n best: (CddlValidationError & { depth: number; startKey: number }) | undefined;\n\n constructor(\n readonly schema: CddlSchema,\n readonly maxDepth: number,\n readonly maxSteps: number,\n readonly features: Set<string>\n ) {}\n\n step(): void {\n if (++this.steps > this.maxSteps)\n throw new LimitExceeded(\n `validation aborted: step budget of ${this.maxSteps} exceeded (pathological backtracking?)`\n );\n }\n\n checkDepth(depth: number): void {\n if (depth > this.maxDepth)\n throw new LimitExceeded(\n `validation aborted: recursion depth ${this.maxDepth} exceeded (cyclic rules without progress?)`\n );\n }\n\n warnOnce(message: string, node?: CddlNodeBase): void {\n const key = `${message}@${node?.start ?? -1}`;\n if (this.warned.has(key)) return;\n this.warned.add(key);\n this.warnings.push({\n message,\n ...(node ? { schemaStart: node.start, schemaEnd: node.end } : {}),\n });\n }\n\n /**\n * Record a failure candidate. The failure furthest into the instance\n * source wins (the standard furthest-progress heuristic — sub-failures\n * of ultimately-successful alternatives, e.g. the uint branch of `int`\n * rejecting a negative number, are left behind by later progress);\n * offset ties are broken by the deeper instance path, then recency.\n */\n fail(\n path: readonly PathSeg[],\n item: CborItem | undefined,\n node: CddlNodeBase | undefined,\n message: string\n ): false {\n const suppressed = this.embeddedDepth > 0;\n const startKey = suppressed ? -1 : (item?.start ?? -1);\n if (\n !this.best ||\n startKey > this.best.startKey ||\n (startKey === this.best.startKey && path.length >= this.best.depth)\n ) {\n const schemaNode = this.preludeDepth > 0 ? this.preludeRef : node;\n this.best = {\n depth: path.length,\n startKey,\n message,\n path: path.length === 0 ? '/' : '/' + path.join('/'),\n ...(!suppressed && item?.start !== undefined\n ? { start: item.start, end: item.end }\n : {}),\n ...(this.ruleName !== undefined ? { ruleName: this.ruleName } : {}),\n ...(schemaNode\n ? { schemaStart: schemaNode.start, schemaEnd: schemaNode.end }\n : {}),\n };\n }\n return false;\n }\n}\n\n// ─── Entry point ──────────────────────────────────────────────────────────────\n\nexport function validateItem(\n schema: CddlSchema,\n item: CborItem,\n options?: ValidateOptions\n): ValidationResult {\n const ruleName = options?.rule ?? schema.root?.name;\n if (ruleName === undefined)\n return {\n valid: false,\n errors: [\n {\n message: 'schema has no rules (no root to validate against)',\n path: '/',\n },\n ],\n };\n const ctx = new Ctx(\n schema,\n options?.maxDepth ?? 256,\n options?.maxSteps ?? 1_000_000,\n new Set(options?.features ?? [])\n );\n // A generic rule's parameters are only ever bound from a referencing\n // site's `genericArgs` (see `bindGenericsForDef`); neither the schema\n // root nor `{ rule }` has one to supply, so selecting a generic rule here\n // would either leave its parameter names unresolved (reported as\n // undefined names, misleadingly) or silently ignore them if unused.\n // Reject it explicitly instead.\n const defs = ruleDefs(ctx, ruleName);\n const genericCount = defs?.[0]?.generics?.length ?? 0;\n if (genericCount > 0)\n return {\n valid: false,\n errors: [\n {\n message: `rule '${ruleName}' takes ${genericCount} generic argument${genericCount === 1 ? '' : 's'} and cannot be used as a validation target directly; reference it with concrete arguments from another rule instead`,\n path: '/',\n },\n ],\n };\n let valid: boolean;\n try {\n valid = matchRuleName(item, ruleName, undefined, [], ctx, 0);\n } catch (e) {\n if (!(e instanceof LimitExceeded)) throw e;\n return {\n valid: false,\n errors: [{ message: e.message, path: '/' }],\n ...(ctx.warnings.length ? { warnings: ctx.warnings } : {}),\n };\n }\n if (valid)\n return {\n valid: true,\n errors: [],\n ...(ctx.warnings.length ? { warnings: ctx.warnings } : {}),\n };\n const errors: CddlValidationError[] = ctx.best\n ? [(({ depth: _d, startKey: _s, ...rest }) => rest)(ctx.best)]\n : [\n {\n message: `value does not match rule '${ruleName}'`,\n path: '/',\n ...(item.start !== undefined\n ? { start: item.start, end: item.end }\n : {}),\n },\n ];\n return {\n valid: false,\n errors,\n ...(ctx.warnings.length ? { warnings: ctx.warnings } : {}),\n };\n}\n\n// ─── Rule resolution ──────────────────────────────────────────────────────────\n\nfunction ruleDefs(ctx: Ctx, name: string): readonly CddlRule[] | undefined {\n const defs = ctx.schema.rules.get(name);\n if (defs) return defs;\n const preludeRule = getPreludeRules().get(name);\n return preludeRule ? [preludeRule] : undefined;\n}\n\nfunction isPlainTypeEntry(\n entry: CddlGroupEntry\n): entry is Extract<CddlGroupEntry, { kind: 'entry' }> {\n return entry.kind === 'entry' && !entry.occur && !entry.memberKey;\n}\n\n/** The group choices contributed by one rule definition body. */\nfunction choicesOfBody(entry: CddlGroupEntry): CddlGroupEntry[][] {\n if (entry.kind === 'entry-group' && !entry.occur) return entry.group.choices;\n return [[entry]];\n}\n\n/** Whether a set of rule definitions can only be used as a group. */\nfunction isGroupLike(defs: readonly CddlRule[]): boolean {\n return defs.some((d) => !isPlainTypeEntry(d.body));\n}\n\n/**\n * Bind one definition's own generic parameter names to the reference's\n * arguments. Each `/=` / `//=` extension may name its parameters\n * differently, so binding is per definition, never from `defs[0]` alone.\n */\nfunction bindGenericsForDef(\n def: CddlRule,\n genericArgs: readonly CddlType1[] | undefined,\n callerEnv: Env\n): Env {\n const params = def.generics;\n if (!params || !genericArgs) return undefined;\n const bound = new Map<string, { type1: CddlType1; env: Env }>();\n for (let i = 0; i < params.length && i < genericArgs.length; i++)\n bound.set(params[i]!, { type1: genericArgs[i]!, env: callerEnv });\n return bound;\n}\n\nfunction matchRuleName(\n item: CborItem,\n name: string,\n callerEnv: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number,\n refNode?: CddlNodeBase,\n genericArgs?: readonly CddlType1[]\n): boolean {\n const defs = ruleDefs(ctx, name);\n if (!defs)\n return ctx.fail(\n path,\n item,\n refNode,\n name.startsWith('$')\n ? `socket '${name}' has no definitions, so nothing matches it`\n : `'${name}' is not defined`\n );\n ctx.checkDepth(depth);\n const prevRule = ctx.ruleName;\n ctx.ruleName = name;\n const fromPrelude = !ctx.schema.rules.has(name);\n if (fromPrelude && ++ctx.preludeDepth === 1) ctx.preludeRef = refNode;\n try {\n for (const def of defs) {\n const env = bindGenericsForDef(def, genericArgs, callerEnv);\n if (isPlainTypeEntry(def.body)) {\n if (matchType(item, def.body.value, env, path, ctx, depth + 1))\n return true;\n continue;\n }\n // A group-bodied definition in type position: usable only when every\n // choice reduces to a single plain entry (a choice-of-types group).\n const choices = choicesOfBody(def.body);\n let usable = true;\n for (const choice of choices) {\n if (choice.length === 1 && isPlainTypeEntry(choice[0]!)) continue;\n usable = false;\n break;\n }\n if (!usable) {\n ctx.fail(\n path,\n item,\n def.body,\n `group rule '${name}' cannot be used as a type`\n );\n continue;\n }\n for (const choice of choices) {\n const only = choice[0]! as Extract<CddlGroupEntry, { kind: 'entry' }>;\n if (matchType(item, only.value, env, path, ctx, depth + 1)) return true;\n }\n }\n return false;\n } finally {\n ctx.ruleName = prevRule;\n if (fromPrelude && --ctx.preludeDepth === 0) ctx.preludeRef = undefined;\n }\n}\n\n// ─── Type matching ────────────────────────────────────────────────────────────\n\n/**\n * See through transparent app-string sequence wrappers (`t1<<…>>`,\n * `b1<<…>>`, `ilbs`/`ilts`, `same<<…>>`): the wrapper only preserves the\n * CDN source spelling for re-serialization; the data-model item is its\n * `inner` result, which is what CDDL types describe.\n */\nfunction unwrapAppSeq(item: CborItem): CborItem {\n while (item instanceof CborAppSeqResult) item = item.inner;\n return item;\n}\n\nfunction matchType(\n item: CborItem,\n type: CddlType,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n for (const alt of type.alternatives)\n if (matchType1(item, alt, env, path, ctx, depth)) return true;\n return false;\n}\n\nfunction matchType1(\n item: CborItem,\n t1: CddlType1,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n ctx.step();\n // Unwrapped here (before control handlers see the item) and again in\n // matchType2, which is also entered directly from control plumbing.\n item = unwrapAppSeq(item);\n if (!t1.op || !t1.controller)\n return matchType2(item, t1.target, env, path, ctx, depth);\n if (t1.op.kind === 'range')\n return matchRange(item, t1, env, path, ctx, depth);\n const handler = getControl(t1.op.name);\n const deps = makeControlDeps(env, ctx, depth);\n if (!handler) {\n ctx.warnOnce(\n `control operator .${t1.op.name} is not supported; matching the target only`,\n t1\n );\n return matchType2(item, t1.target, env, path, ctx, depth);\n }\n return handler(deps, item, t1.target, t1.controller, path, t1);\n}\n\nfunction matchType2(\n item: CborItem,\n t2: CddlType2,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n item = unwrapAppSeq(item);\n // A CDN elision stands for content that was deliberately left out.\n if (item instanceof CborEllipsis) return true;\n\n switch (t2.kind) {\n case 'any':\n return true;\n\n case 'value':\n return matchesLiteral(item, t2)\n ? true\n : ctx.fail(path, item, t2, `expected the value ${t2.raw}`);\n\n case 'ref': {\n const binding = env?.get(t2.name);\n if (binding && !t2.genericArgs)\n return matchType1(\n item,\n binding.type1,\n binding.env,\n path,\n ctx,\n depth + 1\n );\n return matchRuleName(\n item,\n t2.name,\n env,\n path,\n ctx,\n depth + 1,\n t2,\n t2.genericArgs\n );\n }\n\n case 'paren':\n return matchType(item, t2.type, env, path, ctx, depth);\n\n case 'map':\n if (!(item instanceof CborMap))\n return ctx.fail(path, item, t2, 'expected a map');\n return matchMapGroup(item, t2.group, env, path, ctx, depth + 1);\n\n case 'array':\n if (!(item instanceof CborArray))\n return ctx.fail(path, item, t2, 'expected an array');\n return matchArrayGroup(item, t2.group, env, path, ctx, depth + 1);\n\n case 'tagged': {\n // #6.n(type) denotes a *tagged data item* (RFC 8610 §3.6): an untagged\n // integer never matches #6.2/#6.3. (Value-level bignum equivalence\n // lives in literals/ranges/comparisons via intValueOf instead.)\n if (!(item instanceof CborTag))\n return ctx.fail(path, item, t2, 'expected a tagged item');\n if (typeof t2.tag === 'bigint') {\n if (item.tag !== t2.tag)\n return ctx.fail(\n path,\n item,\n t2,\n `expected tag ${t2.tag}, got ${item.tag}`\n );\n } else if (t2.tag !== undefined) {\n if (\n !matchType(new CborUint(item.tag), t2.tag, env, path, ctx, depth + 1)\n )\n return ctx.fail(\n path,\n item,\n t2,\n `tag number ${item.tag} does not match the head type`\n );\n }\n return matchType(item.content, t2.item, env, path, ctx, depth + 1);\n }\n\n case 'major':\n return matchMajor(item, t2, env, path, ctx, depth);\n\n case 'unwrap': {\n // Unwrapping a tag rule exposes the tagged content's type\n // (RFC 8610 §3.7, e.g. `my-uri = ~uri` is a tstr).\n const inner = resolveUnwrapTagType(t2.ref, env, ctx, 0);\n if (inner)\n return matchType(item, inner.type, inner.env, path, ctx, depth + 1);\n // Unwrapping an array/map splices a group into the enclosing\n // array/map; group matching resolves that before type matching, so\n // reaching this point means it was used where only a type can appear.\n ctx.warnOnce(\n `~${t2.ref.name} is used outside of an array/map group context`,\n t2\n );\n return ctx.fail(path, item, t2, `~${t2.ref.name} cannot match here`);\n }\n\n case 'enum': {\n const choices =\n t2.group.kind === 'ref'\n ? resolveGroupRef(t2.group, env, ctx)\n : plainChoices(t2.group, env);\n if (!choices)\n return ctx.fail(\n path,\n item,\n t2,\n `'&' target does not resolve to a group`\n );\n ctx.checkDepth(depth);\n if (matchEnum(item, choices, path, ctx, depth + 1)) return true;\n return ctx.fail(path, item, t2, 'no enumeration value matches');\n }\n }\n}\n\n/** Match an item against the set of entry values of an enum group. */\nfunction matchEnum(\n item: CborItem,\n choices: readonly GroupChoice[],\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n for (const { entries, env } of choices) {\n for (const entry of entries) {\n ctx.step();\n if (entry.kind === 'entry-group') {\n if (\n matchEnum(item, plainChoices(entry.group, env), path, ctx, depth + 1)\n )\n return true;\n continue;\n }\n // Nested group reference inside the enum.\n const groupRef = asBareGroupRef(entry, env, ctx);\n if (groupRef) {\n ctx.checkDepth(depth);\n if (matchEnum(item, groupRef, path, ctx, depth + 1)) return true;\n continue;\n }\n if (matchType(item, entry.value, env, path, ctx, depth + 1)) return true;\n }\n }\n return false;\n}\n\n// ─── Literal and numeric matching ─────────────────────────────────────────────\n\nexport function matchesLiteral(item: CborItem, v: CddlValue): boolean {\n switch (v.type) {\n case 'int':\n // Value comparison is numeric, including bignums: the only wire form\n // of an integer beyond ±(2^64) is its tag-2/3 representation.\n return intValueOf(item) === BigInt(v.value);\n case 'float':\n return (\n item instanceof CborFloat &&\n (item.value === v.value ||\n (Number.isNaN(item.value) && Number.isNaN(v.value)))\n );\n case 'text':\n return textValue(item) === v.value;\n case 'bytes': {\n const bytes = byteValue(item);\n return bytes !== undefined && bytesEqual(bytes, v.value);\n }\n }\n}\n\n/**\n * Resolve a type2 to a literal value, following parentheses, generic\n * bindings, and references to single-alternative value rules. Used for\n * range endpoints and computing control operators (.plus, .cat, …).\n */\nfunction resolveValue(\n t2: CddlType2,\n env: Env,\n ctx: Ctx,\n depth = 0\n): CddlValue | undefined {\n if (depth > 32) return undefined;\n if (t2.kind === 'value') return t2;\n if (t2.kind === 'paren') {\n const only =\n t2.type.alternatives.length === 1 ? t2.type.alternatives[0] : undefined;\n if (!only || only.op) return undefined;\n return resolveValue(only.target, env, ctx, depth + 1);\n }\n if (t2.kind !== 'ref') return undefined;\n const binding = env?.get(t2.name);\n if (binding && !t2.genericArgs) {\n if (binding.type1.op) return undefined;\n return resolveValue(binding.type1.target, binding.env, ctx, depth + 1);\n }\n const defs = ruleDefs(ctx, t2.name);\n if (!defs || defs.length !== 1) return undefined;\n const body = defs[0]!.body;\n if (!isPlainTypeEntry(body) || body.value.alternatives.length !== 1)\n return undefined;\n const only = body.value.alternatives[0]!;\n if (only.op) return undefined;\n const newEnv = bindGenericsForDef(defs[0]!, t2.genericArgs, env);\n return resolveValue(only.target, newEnv, ctx, depth + 1);\n}\n\n/**\n * Whether some integer ≥ `min` matches the type — i.e. whether the type's\n * integer set intersects [min, ∞). Used by `uint .size N` (which accepts\n * any byte count N ≥ the value's minimal length, with no upper limit on N).\n *\n * Tri-state: `undefined` means the type could not be analyzed structurally\n * (control operators, non-integer constructs, …) and the caller must fall\n * back to another strategy.\n */\nfunction existsIntGE(\n t2: CddlType2,\n min: bigint,\n env: Env,\n ctx: Ctx,\n depth = 0\n): boolean | undefined {\n return existsIntInRange(t2, min, undefined, env, ctx, depth);\n}\n\n/** Whether an integer in the inclusive interval [min, max] matches t2. */\nfunction existsIntInRange(\n t2: CddlType2,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth = 0\n): boolean | undefined {\n const found = findIntInRange(t2, min, max, env, ctx, depth);\n return found === undefined ? undefined : found !== null;\n}\n\n/**\n * The first integer in [min, max] matching t2. `null` means the analyzed\n * type has no such integer; `undefined` means it cannot be analyzed.\n */\nfunction findIntInRange(\n t2: CddlType2,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth = 0\n): bigint | null | undefined {\n if (max !== undefined && min > max) return null;\n if (depth > 32) return undefined;\n switch (t2.kind) {\n case 'value': {\n if (t2.type === 'int') {\n const value = BigInt(t2.value);\n return value >= min && (max === undefined || value <= max)\n ? value\n : null;\n }\n return null;\n }\n case 'any': {\n const candidate = min > 0n ? min : 0n;\n return max === undefined || candidate <= max ? candidate : null;\n }\n case 'major': {\n if (t2.ai !== undefined) return undefined;\n if (t2.major === 0) {\n const candidate = min > 0n ? min : 0n;\n return candidate <= 0xffff_ffff_ffff_ffffn &&\n (max === undefined || candidate <= max)\n ? candidate\n : null;\n }\n if (t2.major === 1) {\n const candidate =\n min > -0x1_0000_0000_0000_0000n ? min : -0x1_0000_0000_0000_0000n;\n return candidate <= -1n && (max === undefined || candidate <= max)\n ? candidate\n : null;\n }\n return null;\n }\n case 'paren':\n return findIntInRangeType(t2.type, min, max, env, ctx, depth + 1);\n case 'ref': {\n const binding = env?.get(t2.name);\n if (binding && !t2.genericArgs)\n return findIntInRangeType1(\n binding.type1,\n min,\n max,\n binding.env,\n ctx,\n depth + 1\n );\n const defs = ruleDefs(ctx, t2.name);\n if (!defs) return undefined;\n let sawUnknown = false;\n let best: bigint | null = null;\n for (const def of defs) {\n if (!isPlainTypeEntry(def.body)) {\n sawUnknown = true;\n continue;\n }\n const defEnv = bindGenericsForDef(def, t2.genericArgs, env);\n const r = findIntInRangeType(\n def.body.value,\n min,\n max,\n defEnv,\n ctx,\n depth + 1\n );\n if (typeof r === 'bigint' && (best === null || r < best)) best = r;\n if (r === undefined) sawUnknown = true;\n }\n return best ?? (sawUnknown ? undefined : null);\n }\n case 'enum': {\n const choices =\n t2.group.kind === 'ref'\n ? resolveGroupRef(t2.group, env, ctx)\n : plainChoices(t2.group, env);\n if (!choices) return undefined;\n let sawUnknown = false;\n let best: bigint | null = null;\n for (const { entries, env: choiceEnv } of choices) {\n for (const entry of entries) {\n if (entry.kind !== 'entry') {\n sawUnknown = true;\n continue;\n }\n const r = findIntInRangeType(\n entry.value,\n min,\n max,\n choiceEnv,\n ctx,\n depth + 1\n );\n if (typeof r === 'bigint' && (best === null || r < best)) best = r;\n if (r === undefined) sawUnknown = true;\n }\n }\n return best ?? (sawUnknown ? undefined : null);\n }\n default:\n return undefined;\n }\n}\n\nfunction findIntInRangeType(\n type: CddlType,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth: number\n): bigint | null | undefined {\n let sawUnknown = false;\n let best: bigint | null = null;\n for (const alt of type.alternatives) {\n const r = findIntInRangeType1(alt, min, max, env, ctx, depth);\n if (typeof r === 'bigint' && (best === null || r < best)) best = r;\n if (r === undefined) sawUnknown = true;\n }\n return best ?? (sawUnknown ? undefined : null);\n}\n\nfunction findIntInRangeType1(\n t1: CddlType1,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth: number\n): bigint | null | undefined {\n if (!t1.op) return findIntInRange(t1.target, min, max, env, ctx, depth);\n if (t1.op.kind === 'ctl') {\n if (t1.op.name === 'bits')\n return findBitsIntersection(\n t1.target,\n t1.controller!,\n min,\n max,\n env,\n ctx,\n depth + 1\n );\n if (t1.op.name === 'size') {\n const candidate = findIntInRange(\n t1.target,\n min > 0n ? min : 0n,\n max,\n env,\n ctx,\n depth + 1\n );\n if (candidate === undefined || candidate === null) return candidate;\n const fits = existsIntGE(\n t1.controller!,\n BigInt(uintByteLength(candidate)),\n env,\n ctx,\n depth + 1\n );\n return fits === undefined ? undefined : fits ? candidate : null;\n }\n if (t1.op.name === 'feature') {\n const name = featureName(\n makeControlDeps(env, ctx, depth),\n t1.controller!\n );\n if (name === undefined) return undefined;\n if (!ctx.features.has(name)) {\n ctx.warnOnce(\n `feature \"${name}\" is not enabled (pass it in options.features to accept it)`,\n t1\n );\n return null;\n }\n return findIntInRange(t1.target, min, max, env, ctx, depth + 1);\n }\n if (t1.op.name === 'and' || t1.op.name === 'within')\n return findIntIntersection(\n t1.target,\n t1.controller!,\n min,\n max,\n env,\n ctx,\n depth + 1\n );\n if (t1.op.name === 'plus') {\n const left = resolveValue(t1.target, env, ctx);\n const right = resolveValue(t1.controller!, env, ctx);\n if (\n !left ||\n !right ||\n left.type === 'text' ||\n left.type === 'bytes' ||\n right.type === 'text' ||\n right.type === 'bytes'\n )\n return undefined;\n // .plus converts the result to the target's numeric type. A float\n // target therefore cannot produce the integer byte count sought here;\n // an integer target floors a mixed float sum (RFC 9165 §2.1).\n if (left.type === 'float') return null;\n const sum =\n right.type === 'int'\n ? BigInt(left.value) + BigInt(right.value)\n : BigInt(Math.floor(Number(left.value) + right.value));\n return sum >= min && (max === undefined || sum <= max) ? sum : null;\n }\n const bound = resolveValue(t1.controller!, env, ctx);\n if (!bound || bound.type !== 'int') return undefined;\n const value = BigInt(bound.value);\n switch (t1.op.name) {\n case 'eq':\n return findIntInRange(\n t1.target,\n value > min ? value : min,\n max === undefined || value < max ? value : max,\n env,\n ctx,\n depth + 1\n );\n case 'ne':\n case 'default': {\n const below = findIntInRange(\n t1.target,\n min,\n max === undefined || value - 1n < max ? value - 1n : max,\n env,\n ctx,\n depth + 1\n );\n if (typeof below === 'bigint') return below;\n const above = findIntInRange(\n t1.target,\n value + 1n > min ? value + 1n : min,\n max,\n env,\n ctx,\n depth + 1\n );\n if (typeof above === 'bigint') return above;\n return below === undefined || above === undefined ? undefined : null;\n }\n case 'lt':\n case 'le': {\n const upper = value - (t1.op.name === 'lt' ? 1n : 0n);\n return findIntInRange(\n t1.target,\n min,\n max === undefined || upper < max ? upper : max,\n env,\n ctx,\n depth + 1\n );\n }\n case 'gt':\n case 'ge': {\n const lower = value + (t1.op.name === 'gt' ? 1n : 0n);\n return findIntInRange(\n t1.target,\n lower > min ? lower : min,\n max,\n env,\n ctx,\n depth + 1\n );\n }\n default:\n return undefined;\n }\n }\n const lo = resolveValue(t1.target, env, ctx);\n const hi = resolveValue(t1.controller!, env, ctx);\n if (!lo || !hi || lo.type !== 'int' || hi.type !== 'int') return undefined;\n const loV = BigInt(lo.value);\n const hiV = BigInt(hi.value) - (t1.op.inclusive ? 0n : 1n);\n const lower = loV > min ? loV : min;\n const upper = max === undefined || hiV < max ? hiV : max;\n return lower <= upper ? lower : null;\n}\n\n/** First integer in the intersection of two analyzable integer types. */\nfunction findIntIntersection(\n left: CddlType2,\n right: CddlType2,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth: number\n): bigint | null | undefined {\n let cursor = min;\n // Each iteration advances to a boundary returned by one side. The guard\n // only protects malformed/cyclic analyses; ordinary finite unions\n // converge in at most their combined number of alternatives.\n for (let i = 0; i < 256; i++) {\n const a = findIntInRange(left, cursor, max, env, ctx, depth + 1);\n const b = findIntInRange(right, cursor, max, env, ctx, depth + 1);\n if (a === null || b === null) return null;\n if (a === undefined || b === undefined) return undefined;\n if (a === b) return a;\n cursor = a > b ? a : b;\n }\n return undefined;\n}\n\n/** First uint in the target whose set bits are all admitted by controller. */\nfunction findBitsIntersection(\n target: CddlType2,\n controller: CddlType2,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth: number\n): bigint | null | undefined {\n let allowedMask = 0n;\n for (let bit = 0; bit < 64; bit++) {\n const allowed = findIntInRange(\n controller,\n BigInt(bit),\n BigInt(bit),\n env,\n ctx,\n depth + 1\n );\n if (allowed === undefined) return undefined;\n if (allowed !== null) allowedMask |= 1n << BigInt(bit);\n }\n\n let cursor = min > 0n ? min : 0n;\n const upper =\n max === undefined || max > 0xffff_ffff_ffff_ffffn\n ? 0xffff_ffff_ffff_ffffn\n : max;\n for (let i = 0; i < 256; i++) {\n const fromTarget = findIntInRange(\n target,\n cursor,\n upper,\n env,\n ctx,\n depth + 1\n );\n const fromBits = nextAllowedBitValue(cursor, upper, allowedMask);\n if (fromTarget === undefined) return undefined;\n if (fromTarget === null || fromBits === null) return null;\n if (fromTarget === fromBits) return fromTarget;\n cursor = fromTarget > fromBits ? fromTarget : fromBits;\n }\n return undefined;\n}\n\n/** Smallest value >= min, <= max whose one-bits are a subset of mask. */\nfunction nextAllowedBitValue(\n min: bigint,\n max: bigint,\n mask: bigint\n): bigint | null {\n if (min < 0n) min = 0n;\n if (min > max) return null;\n\n const visit = (\n bit: number,\n greater: boolean,\n value: bigint\n ): bigint | null => {\n if (bit < 0) return value <= max ? value : null;\n const minBit = Number((min >> BigInt(bit)) & 1n);\n for (let chosen = 0; chosen <= 1; chosen++) {\n if (chosen === 1 && (mask & (1n << BigInt(bit))) === 0n) continue;\n if (!greater && chosen < minBit) continue;\n const found = visit(\n bit - 1,\n greater || chosen > minBit,\n chosen === 1 ? value | (1n << BigInt(bit)) : value\n );\n if (found !== null) return found;\n }\n return null;\n };\n return visit(63, false, 0n);\n}\n\nfunction uintByteLength(value: bigint): number {\n let bytes = 0;\n for (let v = value; v > 0n; v >>= 8n) bytes++;\n return bytes;\n}\n\nfunction matchRange(\n item: CborItem,\n t1: CddlType1,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n void depth;\n const op = t1.op as { kind: 'range'; inclusive: boolean };\n const lo = resolveValue(t1.target, env, ctx);\n const hi = resolveValue(t1.controller!, env, ctx);\n if (!lo || !hi) {\n ctx.warnOnce('range endpoints do not resolve to literal values', t1);\n return ctx.fail(path, item, t1, 'unresolvable range');\n }\n if (lo.type === 'int' && hi.type === 'int') {\n // Numeric comparison, including bignums (tags 2/3).\n const v = intValueOf(item);\n if (v === undefined)\n return ctx.fail(\n path,\n item,\n t1,\n `expected an integer in ${rangeText(t1)}`\n );\n const min = BigInt(lo.value);\n const max = BigInt(hi.value);\n if (v >= min && (op.inclusive ? v <= max : v < max)) return true;\n return ctx.fail(path, item, t1, `${v} is outside ${rangeText(t1)}`);\n }\n if (lo.type === 'float' && hi.type === 'float') {\n if (!(item instanceof CborFloat))\n return ctx.fail(path, item, t1, `expected a float in ${rangeText(t1)}`);\n const v = item.value;\n if (v >= lo.value && (op.inclusive ? v <= hi.value : v < hi.value))\n return true;\n return ctx.fail(path, item, t1, `${v} is outside ${rangeText(t1)}`);\n }\n ctx.warnOnce('range endpoints mix integer and float types', t1);\n return ctx.fail(path, item, t1, 'invalid range');\n}\n\nfunction rangeText(t1: CddlType1): string {\n const op = t1.op as { kind: 'range'; inclusive: boolean };\n return `${sourceText(t1.target)}${op.inclusive ? '..' : '...'}${sourceText(t1.controller!)}`;\n}\n\nfunction sourceText(t2: CddlType2): string {\n if (t2.kind === 'value') return t2.raw;\n if (t2.kind === 'ref') return t2.name;\n return '…';\n}\n\n// ─── Major types (#N[.ai]) ────────────────────────────────────────────────────\n\nconst FLOAT_AI: Record<string, bigint> = {\n half: 25n,\n single: 26n,\n double: 27n,\n};\n\nfunction matchMajor(\n item: CborItem,\n t2: Extract<CddlType2, { kind: 'major' }>,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n const matchHead = (n: bigint): boolean => {\n if (t2.ai === undefined) return true;\n if (typeof t2.ai === 'bigint') return t2.ai === n;\n return matchType(new CborUint(n), t2.ai, env, path, ctx, depth + 1);\n };\n const failKind = (what: string): false =>\n ctx.fail(path, item, t2, `expected ${what} (#${t2.major})`);\n\n switch (t2.major) {\n case 0:\n if (!(item instanceof CborUint)) return failKind('an unsigned integer');\n break;\n case 1:\n if (!(item instanceof CborNint)) return failKind('a negative integer');\n break;\n case 2:\n if (byteValue(item) === undefined) return failKind('a byte string');\n break;\n case 3:\n if (textValue(item) === undefined) return failKind('a text string');\n break;\n case 4:\n if (!(item instanceof CborArray)) return failKind('an array');\n break;\n case 5:\n if (!(item instanceof CborMap)) return failKind('a map');\n break;\n case 6: {\n if (!(item instanceof CborTag)) return failKind('a tagged item');\n if (!matchHead(item.tag))\n return ctx.fail(\n path,\n item,\n t2,\n `tag ${item.tag} does not match ${sourceMajor(t2)}`\n );\n return true;\n }\n case 7: {\n if (item instanceof CborSimple) {\n if (matchHead(BigInt(item.value))) return true;\n return ctx.fail(\n path,\n item,\n t2,\n `simple(${item.value}) does not match ${sourceMajor(t2)}`\n );\n }\n if (item instanceof CborFloat) {\n if (t2.ai === undefined) return true;\n // When no width was recorded (e.g. CDN input without an encoding\n // suffix), use the smallest width that represents the value\n // losslessly — its preferred serialization.\n const precision =\n item.precision ?? autoSelectFloatPrecision(item.value);\n if (matchHead(FLOAT_AI[precision]!)) return true;\n return ctx.fail(\n path,\n item,\n t2,\n `float does not match ${sourceMajor(t2)}`\n );\n }\n return failKind('a simple value or float');\n }\n default:\n return ctx.fail(path, item, t2, `#${t2.major} is not a valid major type`);\n }\n // Majors 0–5: an additional-information constraint is about encoding,\n // which Phase 2 does not check.\n if (t2.ai !== undefined && t2.major <= 5)\n ctx.warnOnce(\n `the additional-information constraint ${sourceMajor(t2)} is not checked (encoding-level)`,\n t2\n );\n return true;\n}\n\nfunction sourceMajor(t2: Extract<CddlType2, { kind: 'major' }>): string {\n return t2.raw ?? `#${t2.major}`;\n}\n\n// ─── Group matching: shared expansion ─────────────────────────────────────────\n\ninterface Occ {\n min: number;\n max: number;\n}\n\n/**\n * One group choice with the environment its entries are evaluated in.\n * The env is per choice because `//=` extensions of a generic rule may\n * name their parameters differently per definition.\n */\ninterface GroupChoice {\n entries: readonly CddlGroupEntry[];\n env: Env;\n}\n\nconst plainChoices = (group: CddlGroup, env: Env): GroupChoice[] =>\n group.choices.map((entries) => ({ entries, env }));\n\ntype SeqMatcher =\n | {\n kind: 'type';\n occur: Occ;\n memberKey?: CddlMemberKey;\n type: CddlType;\n env: Env;\n node: CddlNodeBase;\n }\n | {\n kind: 'group';\n occur: Occ;\n choices: readonly GroupChoice[];\n node: CddlNodeBase;\n };\n\nconst ONE: Occ = { min: 1, max: 1 };\n\nfunction occOf(entry: CddlGroupEntry): Occ {\n const o = entry.occur;\n if (!o) return ONE;\n if (o.marker === '?') return { min: 0, max: 1 };\n if (o.marker === '+') return { min: 1, max: Infinity };\n return { min: o.min ?? 0, max: o.max ?? Infinity };\n}\n\n/** Resolve a bare reference to a group-like rule (for splicing). */\nfunction resolveGroupRef(\n ref: CddlRef,\n env: Env,\n ctx: Ctx\n): GroupChoice[] | undefined {\n const defs = ruleDefs(ctx, ref.name);\n if (!defs) return undefined;\n if (!isGroupLike(defs)) return undefined;\n const choices: GroupChoice[] = [];\n for (const def of defs) {\n const defEnv = bindGenericsForDef(def, ref.genericArgs, env);\n for (const entries of choicesOfBody(def.body))\n choices.push({ entries, env: defEnv });\n }\n return choices;\n}\n\n/**\n * When an entry is a bare single reference, return the group it stands for\n * (group rule or unwrap) — the caller splices it into the sequence.\n */\nfunction asBareGroupRef(\n entry: CddlGroupEntry,\n env: Env,\n ctx: Ctx\n): GroupChoice[] | undefined {\n if (entry.kind !== 'entry' || entry.memberKey) return undefined;\n if (entry.value.alternatives.length !== 1) return undefined;\n const t1 = entry.value.alternatives[0]!;\n if (t1.op) return undefined;\n const target = t1.target;\n if (target.kind === 'ref') {\n if (env?.has(target.name) && !target.genericArgs) return undefined;\n const resolved = resolveGroupRef(target, env, ctx);\n if (resolved) return resolved;\n // An unplugged group socket is a choice with zero alternatives: it\n // matches nothing (which is why sockets are used as `* $$name`).\n if (target.name.startsWith('$$') && !ruleDefs(ctx, target.name)) return [];\n return undefined;\n }\n if (target.kind === 'unwrap')\n return resolveUnwrapGroup(target.ref, env, ctx, 0);\n return undefined;\n}\n\n/** ~ref: follow references to a map/array type and return its group. */\nfunction resolveUnwrapGroup(\n ref: CddlRef,\n env: Env,\n ctx: Ctx,\n depth: number\n): GroupChoice[] | undefined {\n if (depth > 32) return undefined;\n const defs = ruleDefs(ctx, ref.name);\n if (!defs || defs.length !== 1) return undefined;\n const body = defs[0]!.body;\n const newEnv = bindGenericsForDef(defs[0]!, ref.genericArgs, env);\n if (!isPlainTypeEntry(body)) {\n // Unwrapping a group rule: the group itself.\n return choicesOfBody(body).map((entries) => ({ entries, env: newEnv }));\n }\n if (body.value.alternatives.length !== 1) return undefined;\n const t1 = body.value.alternatives[0]!;\n if (t1.op) return undefined;\n if (t1.target.kind === 'map' || t1.target.kind === 'array')\n return plainChoices(t1.target.group, newEnv);\n if (t1.target.kind === 'ref')\n return resolveUnwrapGroup(t1.target, newEnv, ctx, depth + 1);\n return undefined;\n}\n\n/**\n * ~ref where the target is a tag rule: unwrapping removes the tag, exposing\n * the content type (RFC 8610 §3.7, e.g. `my-uri = ~uri` is a tstr).\n */\nfunction resolveUnwrapTagType(\n ref: CddlRef,\n env: Env,\n ctx: Ctx,\n depth: number\n): { type: CddlType; env: Env } | undefined {\n if (depth > 32) return undefined;\n const defs = ruleDefs(ctx, ref.name);\n if (!defs || defs.length !== 1) return undefined;\n const body = defs[0]!.body;\n if (!isPlainTypeEntry(body) || body.value.alternatives.length !== 1)\n return undefined;\n const t1 = body.value.alternatives[0]!;\n if (t1.op) return undefined;\n const newEnv = bindGenericsForDef(defs[0]!, ref.genericArgs, env);\n if (t1.target.kind === 'tagged') return { type: t1.target.item, env: newEnv };\n if (t1.target.kind === 'ref')\n return resolveUnwrapTagType(t1.target, newEnv, ctx, depth + 1);\n return undefined;\n}\n\nfunction expandEntry(entry: CddlGroupEntry, env: Env, ctx: Ctx): SeqMatcher {\n const occur = occOf(entry);\n if (entry.kind === 'entry-group')\n return {\n kind: 'group',\n occur,\n choices: plainChoices(entry.group, env),\n node: entry,\n };\n const groupRef = asBareGroupRef(entry, env, ctx);\n if (groupRef)\n return {\n kind: 'group',\n occur,\n choices: groupRef,\n node: entry,\n };\n return {\n kind: 'type',\n occur,\n ...(entry.memberKey ? { memberKey: entry.memberKey } : {}),\n type: entry.value,\n env,\n node: entry,\n };\n}\n\n// ─── Group matching: arrays (sequences) ───────────────────────────────────────\n\nfunction matchArrayGroup(\n arr: CborArray,\n group: CddlGroup,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n ctx.checkDepth(depth);\n const ends = seqEnds(\n arr.items,\n 0,\n plainChoices(group, env),\n path,\n ctx,\n depth\n );\n if (ends.has(arr.items.length)) return true;\n return ctx.fail(\n path,\n arr,\n group,\n `array of ${arr.items.length} item(s) does not match the group`\n );\n}\n\n/** All end positions reachable by matching the group's choices at `idx`. */\nfunction seqEnds(\n items: readonly CborItem[],\n idx: number,\n choices: readonly GroupChoice[],\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): Set<number> {\n const out = new Set<number>();\n for (const choice of choices) {\n const matchers = choice.entries.map((e) => expandEntry(e, choice.env, ctx));\n seqStep(items, idx, matchers, 0, path, ctx, depth, out);\n }\n return out;\n}\n\nfunction seqStep(\n items: readonly CborItem[],\n idx: number,\n ms: readonly SeqMatcher[],\n k: number,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number,\n out: Set<number>\n): void {\n if (k === ms.length) {\n out.add(idx);\n return;\n }\n const m = ms[k]!;\n\n const tryCount = (count: number, at: number): void => {\n ctx.step();\n if (count >= m.occur.min)\n seqStep(items, at, ms, k + 1, path, ctx, depth, out);\n if (count >= m.occur.max || at >= items.length) return;\n for (const end of matchOnceEnds(items, at, m, path, ctx, depth)) {\n // An empty match makes no progress; recursing on it would loop.\n if (end === at) continue;\n tryCount(count + 1, end);\n }\n };\n tryCount(0, idx);\n}\n\n/** End positions from matching a single occurrence of `m` at `at`. */\nfunction matchOnceEnds(\n items: readonly CborItem[],\n at: number,\n m: SeqMatcher,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): number[] {\n if (m.kind === 'type') {\n // Member keys inside arrays are documentation only (RFC 8610 §3.4).\n return matchType(items[at]!, m.type, m.env, [...path, at], ctx, depth)\n ? [at + 1]\n : [];\n }\n ctx.checkDepth(depth);\n const ends = seqEnds(items, at, m.choices, path, ctx, depth + 1);\n // Descending order: prefer greedy consumption first.\n return [...ends].sort((a, b) => b - a);\n}\n\n// ─── Group matching: maps ─────────────────────────────────────────────────────\n\nfunction matchMapGroup(\n map: CborMap,\n group: CddlGroup,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n ctx.checkDepth(depth);\n const consumed = new Array<boolean>(map.entries.length).fill(false);\n for (const choice of plainChoices(group, env)) {\n consumed.fill(false);\n if (\n mapSeq(\n map,\n choice.entries,\n 0,\n consumed,\n choice.env,\n path,\n ctx,\n depth,\n () => mapFullyConsumed(map, consumed, path, ctx, group)\n )\n )\n return true;\n }\n return false;\n}\n\nfunction mapFullyConsumed(\n map: CborMap,\n consumed: boolean[],\n path: readonly PathSeg[],\n ctx: Ctx,\n node: CddlNodeBase\n): boolean {\n for (let i = 0; i < consumed.length; i++) {\n if (consumed[i]) continue;\n const [k, v] = map.entries[i]!;\n // Leftover elided entries are what \"...\" stands for — ignore them.\n if (k instanceof CborEllipsis) continue;\n ctx.fail(\n [...path, keySeg(k, i)],\n v,\n node,\n `entry ${describeItem(k)} is not allowed by the group`\n );\n return false;\n }\n return true;\n}\n\n/**\n * Match the entries of one group choice against the map, in continuation\n * style so that sub-group choices and occurrence counts can backtrack when\n * downstream matchers (or the final completeness check) fail.\n *\n * Entry-to-member assignment itself is greedy in definition order and is\n * not backtracked (a deliberate heuristic — put wildcard members last).\n */\nfunction mapSeq(\n map: CborMap,\n entries: readonly CddlGroupEntry[],\n k: number,\n consumed: boolean[],\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number,\n cont: () => boolean\n): boolean {\n if (k === entries.length) return cont();\n const m = expandEntry(entries[k]!, env, ctx);\n\n if (m.kind === 'type') {\n if (!m.memberKey) {\n // A bare type as a map entry can only be `any` standing for a whole\n // entry — not expressible; report instead of silently ignoring.\n return ctx.fail(\n path,\n map,\n m.node,\n 'group entry without a member key cannot match a map entry'\n );\n }\n let count = 0;\n for (let i = 0; i < map.entries.length && count < m.occur.max; i++) {\n if (consumed[i]) continue;\n const [key, value] = map.entries[i]!;\n if (!keyMatches(m.memberKey, key, m.env, path, ctx, depth)) continue;\n const valuePath = [...path, keySeg(key, i)];\n if (matchType(value, m.type, m.env, valuePath, ctx, depth + 1)) {\n consumed[i] = true;\n count++;\n continue;\n }\n if (m.memberKey.cut) {\n // Cut: the key committed this entry to this member; a value\n // mismatch fails the whole map (§3.5.4).\n return ctx.fail(\n valuePath,\n value,\n m.node,\n `value for ${describeKey(m.memberKey)} does not match`\n );\n }\n }\n if (count < m.occur.min)\n return ctx.fail(\n path,\n map,\n m.node,\n `missing required entry ${describeKey(m.memberKey)}`\n );\n return mapSeq(map, entries, k + 1, consumed, env, path, ctx, depth, cont);\n }\n\n // Sub-group with an occurrence: backtrack over stop-vs-repeat and over\n // the sub-group's choices.\n ctx.checkDepth(depth);\n const consumedCount = (): number => {\n let n = 0;\n for (const c of consumed) if (c) n++;\n return n;\n };\n const tryIter = (iter: number): boolean => {\n ctx.step();\n if (\n iter >= m.occur.min &&\n mapSeq(map, entries, k + 1, consumed, env, path, ctx, depth, cont)\n )\n return true;\n if (iter >= m.occur.max) return false;\n const snapshot = consumed.slice();\n const before = consumedCount();\n for (const sub of m.choices) {\n if (\n mapSeq(\n map,\n sub.entries,\n 0,\n consumed,\n sub.env,\n path,\n ctx,\n depth + 1,\n () => {\n if (consumedCount() === before)\n // An empty iteration makes no progress; repeating it cannot\n // help, so treat the occurrence as satisfied and move on.\n return mapSeq(\n map,\n entries,\n k + 1,\n consumed,\n env,\n path,\n ctx,\n depth,\n cont\n );\n return tryIter(iter + 1);\n }\n )\n )\n return true;\n for (let i = 0; i < consumed.length; i++) consumed[i] = snapshot[i]!;\n }\n return false;\n };\n return tryIter(0);\n}\n\nfunction keyMatches(\n mk: CddlMemberKey,\n key: CborItem,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n key = unwrapAppSeq(key);\n if (key instanceof CborEllipsis) return true;\n switch (mk.kind) {\n case 'bareword':\n return textValue(key) === mk.key;\n case 'value':\n return matchesLiteral(key, mk.key);\n case 'type1':\n return matchType1(key, mk.key, env, path, ctx, depth + 1);\n }\n}\n\nfunction describeKey(mk: CddlMemberKey): string {\n switch (mk.kind) {\n case 'bareword':\n return `'${mk.key}'`;\n case 'value':\n return mk.key.raw;\n case 'type1':\n return sourceText(mk.key.target);\n }\n}\n\nfunction keySeg(key: CborItem, index: number): PathSeg {\n const text = textValue(key);\n if (text !== undefined) return text;\n if (key instanceof CborUint || key instanceof CborNint) {\n const v = key.value;\n if (\n v >= BigInt(Number.MIN_SAFE_INTEGER) &&\n v <= BigInt(Number.MAX_SAFE_INTEGER)\n )\n return Number(v);\n }\n return index;\n}\n\nfunction describeItem(item: CborItem): string {\n const text = textValue(item);\n if (text !== undefined) return JSON.stringify(text);\n if (item instanceof CborUint || item instanceof CborNint)\n return item.value.toString();\n return item.constructor.name.replace(/^Cbor/, '').toLowerCase();\n}\n\n// ─── Control operator plumbing ────────────────────────────────────────────────\n\nfunction makeControlDeps(env: Env, ctx: Ctx, depth: number): ControlDeps {\n return {\n matchType2: (item, t2, path) =>\n matchType2(item, t2, env, path, ctx, depth + 1),\n matchEmbedded: (item, t2, path) => {\n ctx.embeddedDepth++;\n try {\n return matchType2(item, t2, env, path, ctx, depth + 1);\n } finally {\n ctx.embeddedDepth--;\n }\n },\n resolveValue: (t2) => resolveValue(t2, env, ctx),\n existsIntGE: (t2, min) => existsIntGE(t2, min, env, ctx),\n matchesLiteral,\n fail: (path, item, node, message) => ctx.fail(path, item, node, message),\n warnOnce: (message, node) => ctx.warnOnce(message, node),\n features: ctx.features,\n uint: (n) => new CborUint(n),\n };\n}\n","/**\n * CDDL compilation: rule table construction and static checks.\n *\n * `compile()` parses CDDL text and performs the semantic checks that do not\n * require a data item: duplicate rule detection, name resolution against the\n * user rules and the standard prelude, and generic arity checks. Validation\n * of CBOR data against a schema is a later phase.\n */\n\nimport { parseCDDL } from './parser';\nimport { getPreludeRules } from './prelude';\nimport { formatCddl, type CddlFormatOptions } from './writer';\nimport type { CddlComment } from './tokenizer';\nimport { validateItem, type ValidateOptions } from './validator';\nimport { CborItem } from '../ast/CborItem';\nimport { decodeCBOR } from '../cbor/decoder';\nimport { parseCDN } from '../cdn/parser';\nimport {\n CddlSemanticError,\n type CddlWarning,\n type ValidationResult,\n} from './errors';\nimport type {\n CddlGroup,\n CddlGroupEntry,\n CddlRef,\n CddlRule,\n CddlType,\n CddlType1,\n CddlType2,\n} from './ast';\n\nexport interface CompileOptions {\n /**\n * When true (the default), semantic problems (undefined names, duplicate\n * rules, generic arity mismatches) throw a {@link CddlSemanticError}.\n * When false, they are collected into {@link CddlSchema.warnings}.\n */\n strict?: boolean;\n}\n\n/**\n * A compiled CDDL data model.\n *\n * `rules` maps each rule name to its definitions in source order: the base\n * definition plus any `/=` / `//=` choice extensions. User rules shadow\n * prelude names; the prelude itself is available via `getPreludeRules()`.\n */\nexport class CddlSchema {\n /**\n * The CDDL source text this schema was compiled from. AST node offsets\n * (and validation errors' `schemaStart`/`schemaEnd`) index into it, so\n * tooling can render positions without carrying the text separately.\n */\n readonly source: string;\n /** `;` comments collected while parsing, in source order. */\n readonly comments: readonly CddlComment[];\n /** All rules in source order, as parsed (extensions unmerged). */\n readonly ast: readonly CddlRule[];\n /** Rule definitions by name (base definition first, then extensions). */\n readonly rules: ReadonlyMap<string, readonly CddlRule[]>;\n /**\n * The root of the data model: the first rule in the source (RFC 8610 §3.1).\n * Unset only for an empty model compiled with `strict: false`.\n */\n readonly root?: CddlRule;\n /** Semantic problems collected with `strict: false`; unset when clean. */\n readonly warnings?: CddlWarning[];\n\n /** @internal — use `CDDL.compile()`. */\n constructor(\n source: string,\n comments: readonly CddlComment[],\n ast: CddlRule[],\n rules: Map<string, CddlRule[]>,\n root: CddlRule | undefined,\n warnings: CddlWarning[]\n ) {\n this.source = source;\n this.comments = comments;\n this.ast = ast;\n this.rules = rules;\n if (root) this.root = root;\n if (warnings.length > 0) this.warnings = warnings;\n }\n\n /**\n * Serialize the data model back to CDDL text.\n *\n * Compact one-rule-per-line output by default; pass `indent` for a\n * pretty layout (one group entry per line) and `preserveComments` to\n * re-emit `;` comments.\n *\n * @example\n * CDDL.compile(text).format({ indent: 2, preserveComments: true });\n */\n format(options?: CddlFormatOptions): string {\n return formatCddl(this.ast, {\n ...options,\n source: this.source,\n comments: this.comments,\n });\n }\n\n /**\n * Validate a data item against this schema's root rule — the first rule\n * in source order (RFC 8610 §3.1). Pass `{ rule: 'otherName' }` to\n * validate against a different rule instead: any non-generic rule usable\n * as a type, defined in the schema or its prelude (e.g. `'uint'`).\n * Generic rules (`g<T> = ...`) and group-only rules are reported as\n * validation failures, as is an unknown name (see\n * {@link ValidateOptions.rule}).\n *\n * Accepts a CborItem, CBOR bytes (decoded with `decodeCBOR`), or CDN text\n * (parsed with `parseCDN`). Validation failures are reported in the\n * result, not thrown; decode/parse failures of the input throw as usual.\n *\n * @example\n * const schema = CDDL.compile('person = { name: tstr, ? age: uint }');\n * const result = schema.validate('{\"name\": \"kudo\", \"age\": 42}');\n * result.valid; // true\n *\n * @example\n * // Validate against a rule other than the root.\n * const schema = CDDL.compile(`\n * p1 = { name: tstr, ? addr: tstr }\n * p2 = { name: tstr, ? age: uint }\n * `);\n * schema.validate('{\"name\": \"kudo\", \"age\": 42}', { rule: 'p2' }).valid; // true\n */\n validate(\n input: CborItem | Uint8Array | string,\n options?: ValidateOptions\n ): ValidationResult {\n const item =\n input instanceof CborItem\n ? input\n : typeof input === 'string'\n ? parseCDN(input)\n : decodeCBOR(input);\n return validateItem(this, item, options);\n }\n}\n\n/**\n * Parse and compile CDDL text.\n *\n * Throws `CddlSyntaxError` on grammar errors. Semantic problems throw a\n * {@link CddlSemanticError} by default; pass `strict: false` to collect them\n * into `schema.warnings` instead.\n */\nexport function compile(text: string, options?: CompileOptions): CddlSchema {\n const { rules, comments } = parseCDDL(text);\n const warnings: CddlWarning[] = [];\n const prelude = getPreludeRules();\n\n if (rules.length === 0)\n warnings.push({\n code: 'no-rules',\n message:\n 'a CDDL data model needs at least one rule to provide the root of the definition',\n });\n\n // Rule table: base definition plus /= and //= extensions, in source order.\n const table = new Map<string, CddlRule[]>();\n for (const rule of rules) {\n const existing = table.get(rule.name);\n if (!existing) {\n table.set(rule.name, [rule]);\n continue;\n }\n if (rule.assign === '=')\n warnings.push({\n code: 'duplicate-rule',\n message: `rule '${rule.name}' is already defined; use /= or //= to extend it`,\n start: rule.start,\n end: rule.end,\n });\n existing.push(rule);\n }\n\n // Name resolution and generic arity, per rule (generic parameters are in\n // scope only within their own rule definition's body).\n const declaredArity = (name: string): number | undefined => {\n const defs = table.get(name);\n if (defs) return defs[0]!.generics?.length ?? 0;\n const preludeRule = prelude.get(name);\n if (preludeRule) return preludeRule.generics?.length ?? 0;\n return undefined;\n };\n\n for (const rule of rules) {\n const generics = rule.generics;\n walkEntry(rule.body, {\n onRef(ref: CddlRef): void {\n if (generics?.includes(ref.name)) return;\n // Type and group sockets ($name / $$name) may be referenced and\n // extended without ever being defined.\n if (ref.name.startsWith('$')) return;\n const arity = declaredArity(ref.name);\n if (arity === undefined) {\n warnings.push({\n code: 'undefined-name',\n message: `'${ref.name}' is not defined (and is not a prelude name)`,\n start: ref.start,\n end: ref.end,\n });\n return;\n }\n const given = ref.genericArgs?.length ?? 0;\n if (arity !== given)\n warnings.push({\n code: 'generic-arity',\n message: `'${ref.name}' takes ${arity} generic argument${arity === 1 ? '' : 's'} but is used with ${given}`,\n start: ref.start,\n end: ref.end,\n });\n },\n onMajor(major: number, start: number, end: number): void {\n if (major > 7)\n warnings.push({\n code: 'invalid-major',\n message: `#${major} is not a CBOR major type (0–7)`,\n start,\n end,\n });\n },\n });\n }\n\n // The first rule is the root of the data model, and \"there is no way to\n // use a group as a root -- it must be a type\" (RFC 8610 §2.2.4).\n const root = rules[0];\n if (root && !isTypeBody(root.body))\n warnings.push({\n code: 'invalid-root',\n message: `the first rule '${root.name}' is the root of the data model and must define a type, not a group (RFC 8610 §2.2.4)`,\n start: root.start,\n end: root.end,\n });\n\n if ((options?.strict ?? true) && warnings.length > 0)\n throw new CddlSemanticError(warnings);\n\n // An empty model has no root; `no-rules` was already reported above.\n return new CddlSchema(text, comments, rules, table, root, warnings);\n}\n\n/**\n * Whether a rule body is usable as a type: a plain entry (no occurrence, no\n * member key), or a parenthesized group that reduces to one such entry.\n * A trailing comma makes a parenthesized expression a group — `(int,)` is\n * never a parenthesized type.\n */\nfunction isTypeBody(entry: CddlGroupEntry): boolean {\n if (entry.kind === 'entry') return !entry.occur && !entry.memberKey;\n if (entry.occur || entry.group.trailingComma) return false;\n const { choices } = entry.group;\n return (\n choices.length === 1 &&\n choices[0]!.length === 1 &&\n isTypeBody(choices[0]![0]!)\n );\n}\n\n// ─── AST walk ─────────────────────────────────────────────────────────────────\n\ninterface WalkHooks {\n onRef(ref: CddlRef): void;\n onMajor(major: number, start: number, end: number): void;\n}\n\nfunction walkEntry(entry: CddlGroupEntry, hooks: WalkHooks): void {\n if (entry.kind === 'entry-group') {\n walkGroup(entry.group, hooks);\n return;\n }\n if (entry.memberKey?.kind === 'type1') walkType1(entry.memberKey.key, hooks);\n walkType(entry.value, hooks);\n}\n\nfunction walkGroup(group: CddlGroup, hooks: WalkHooks): void {\n for (const choice of group.choices)\n for (const entry of choice) walkEntry(entry, hooks);\n}\n\nfunction walkType(type: CddlType, hooks: WalkHooks): void {\n for (const alt of type.alternatives) walkType1(alt, hooks);\n}\n\nfunction walkType1(type1: CddlType1, hooks: WalkHooks): void {\n walkType2(type1.target, hooks);\n if (type1.controller) walkType2(type1.controller, hooks);\n}\n\nfunction walkType2(type2: CddlType2, hooks: WalkHooks): void {\n switch (type2.kind) {\n case 'value':\n case 'any':\n return;\n case 'ref':\n hooks.onRef(type2);\n for (const arg of type2.genericArgs ?? []) walkType1(arg, hooks);\n return;\n case 'paren':\n walkType(type2.type, hooks);\n return;\n case 'map':\n case 'array':\n walkGroup(type2.group, hooks);\n return;\n case 'unwrap':\n hooks.onRef(type2.ref);\n for (const arg of type2.ref.genericArgs ?? []) walkType1(arg, hooks);\n return;\n case 'enum':\n if (type2.group.kind === 'ref') {\n hooks.onRef(type2.group);\n for (const arg of type2.group.genericArgs ?? []) walkType1(arg, hooks);\n } else walkGroup(type2.group, hooks);\n return;\n case 'tagged':\n if (typeof type2.tag === 'object') walkType(type2.tag, hooks);\n walkType(type2.item, hooks);\n return;\n case 'major':\n hooks.onMajor(type2.major, type2.start, type2.end);\n if (typeof type2.ai === 'object') walkType(type2.ai, hooks);\n return;\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"schema-zsg5yCPK.cjs","names":[],"sources":["../src/cddl/errors.ts","../src/cddl/tokenizer.ts","../src/cddl/parser.ts","../src/cddl/prelude.ts","../src/cddl/writer.ts","../src/cddl/equal.ts","../src/cddl/controls.ts","../src/cddl/validator.ts","../src/cddl/schema.ts"],"sourcesContent":["/**\n * Structured errors thrown by the CDDL tokenizer, parser, and compiler.\n *\n * Both carry source positions so tooling (editors, linters, playgrounds) can\n * point at the offending range without parsing the message.\n */\n\n/** A semantic problem found while compiling a syntactically valid CDDL file. */\nexport interface CddlWarning {\n /** Stable machine-readable identifier, e.g. 'undefined-name'. */\n code:\n | 'no-rules'\n | 'duplicate-rule'\n | 'undefined-name'\n | 'generic-arity'\n | 'invalid-major'\n | 'invalid-root';\n message: string;\n /** Character offset of the start of the offending range in the source input. */\n start?: number;\n /** Character offset just past the end of the offending range. */\n end?: number;\n}\n\n/**\n * A single validation failure. When a data item does not match the schema,\n * the reported error is the one recorded at the deepest point the matcher\n * reached (failures discarded by backtracking are noise and are not kept).\n */\nexport interface CddlValidationError {\n message: string;\n /** Location inside the instance, e.g. '/claims/2/name' ('' = root). */\n path: string;\n /** Instance-side source offsets (byte offsets for CBOR input, character\n * offsets for CDN input), when the input carried them. */\n start?: number;\n end?: number;\n /** The CDDL rule being matched when the failure was recorded. */\n ruleName?: string;\n /** Schema-side source offsets of the CDDL construct that failed to match. */\n schemaStart?: number;\n schemaEnd?: number;\n}\n\n/** A non-fatal observation made while validating (e.g. unsupported control\n * operators, whose targets are then matched without the constraint). */\nexport interface CddlValidationWarning {\n message: string;\n schemaStart?: number;\n schemaEnd?: number;\n}\n\n/** Result of {@link CddlSchema.validate}. */\nexport interface ValidationResult {\n valid: boolean;\n /** Empty when valid; otherwise the deepest-reach failure(s). */\n errors: CddlValidationError[];\n /** Present when the validator had to approximate or skip constraints. */\n warnings?: CddlValidationWarning[];\n}\n\n/** Syntax error thrown by the CDDL tokenizer and parser. */\nexport class CddlSyntaxError extends SyntaxError {\n /** Character offset of the start of the offending range in the source input. */\n readonly offset?: number;\n /** 1-based line number of the offending range. */\n readonly line?: number;\n /** 1-based column number of the offending range. */\n readonly column?: number;\n /** Character offset just past the end of the offending range. */\n readonly endOffset?: number;\n\n constructor(\n message: string,\n position?: {\n offset?: number;\n line?: number;\n column?: number;\n endOffset?: number;\n }\n ) {\n const loc =\n position?.line !== undefined\n ? ` at line ${position.line}, column ${position.column}`\n : '';\n super(`CDDL parse error${loc}: ${message}`);\n this.name = 'CddlSyntaxError';\n this.offset = position?.offset;\n this.line = position?.line;\n this.column = position?.column;\n this.endOffset = position?.endOffset;\n }\n}\n\n/**\n * Error thrown when a data item does not match a CDDL schema supplied via\n * the `cddl` option of a throwing entry point (`CBOR.parse`, `CBOR.decode`,\n * `CBOR.fromCDN`, `CBOR.encode`, …). Non-throwing checks (`CBOR.validate`,\n * `CddlSchema.validate`) report the same failures in their result instead.\n */\nexport class CddlMismatchError extends Error {\n /** The deepest-reach validation failure(s). */\n readonly errors: CddlValidationError[];\n /** Non-fatal validator observations (approximated/skipped constraints). */\n readonly warnings: CddlValidationWarning[];\n\n constructor(\n errors: CddlValidationError[],\n warnings: CddlValidationWarning[] = []\n ) {\n const head = errors[0];\n const loc = head?.path ? ` at ${head.path}` : '';\n const rest = errors.length > 1 ? ` (and ${errors.length - 1} more)` : '';\n super(`CDDL validation failed${loc}: ${head?.message ?? 'unknown'}${rest}`);\n this.name = 'CddlMismatchError';\n this.errors = errors;\n this.warnings = warnings;\n }\n}\n\n/**\n * Semantic error thrown by `CDDL.compile` in strict mode (the default) when\n * a syntactically valid file has semantic problems: undefined names,\n * duplicate rule definitions, generic arity mismatches, and the like.\n * With `strict: false` the same problems are collected into\n * `CddlSchema.warnings` instead.\n */\nexport class CddlSemanticError extends Error {\n readonly warnings: CddlWarning[];\n\n constructor(warnings: CddlWarning[]) {\n const head = warnings[0];\n const rest =\n warnings.length > 1 ? ` (and ${warnings.length - 1} more)` : '';\n super(`CDDL semantic error: ${head?.message ?? 'unknown'}${rest}`);\n this.name = 'CddlSemanticError';\n this.warnings = warnings;\n }\n}\n","/**\n * CDDL lexer (internal).\n *\n * Implements the token-level grammar of RFC 8610 as updated by RFC 9682\n * (Appendix A collected ABNF). Used by parser.ts and exposed through the\n * `tokenize()` / `tokenizeLenient()` helpers in index.ts so tooling such as\n * syntax highlighters stays in exact agreement with parsing behavior.\n */\n\nimport { CddlSyntaxError } from './errors';\nimport { hexToBytes } from '../utils/hex';\nimport { base64ToBytes } from '../utils/base64';\n\nexport type CddlTokenType =\n | 'ID'\n | 'INT' // raw text in `value`, incl. optional '-' and 0x/0b forms\n | 'FLOAT' // raw text in `value`, decimal or hexfloat\n | 'TSTR' // decoded content in `value`\n | 'BYTES' // raw content in `value`, decoded bytes in `bytes`\n | 'HASH' // '#' with optional major/head-number (see hashMajor/hashAI)\n | 'ASSIGN' // =\n | 'SLASH_EQ' // /=\n | 'DSLASH_EQ' // //=\n | 'SLASH' // /\n | 'DSLASH' // //\n | 'COMMA'\n | 'LPAREN'\n | 'RPAREN'\n | 'LBRACE'\n | 'RBRACE'\n | 'LBRACKET'\n | 'RBRACKET'\n | 'LT'\n | 'GT'\n | 'TILDE'\n | 'AMP'\n | 'RANGE_INCL' // ..\n | 'RANGE_EXCL' // ...\n | 'CTLOP' // .id — operator name (without the dot) in `value`\n | 'STAR'\n | 'PLUS'\n | 'QUEST'\n | 'ARROW' // =>\n | 'COLON'\n | 'CARET'\n | 'EOF'\n /** Synthetic token emitted by tokenizeLenient() for the unscannable tail. */\n | 'ERROR';\n\nexport interface CddlToken {\n type: CddlTokenType;\n /** Processed value: decoded string content, raw numeric text, id text, etc. */\n value: string;\n /** Original source text for this token. */\n raw: string;\n line: number;\n col: number;\n /** Character offset of the first character of this token in the source input. */\n offset: number;\n /** Character offset just past the last character of this token in the source input. */\n endOffset: number;\n /** Only set when type === 'BYTES': the qualifier ('' | 'h' | 'b64'). */\n qualifier?: '' | 'h' | 'b64';\n /** Only set when type === 'BYTES': the decoded byte content. */\n bytes?: Uint8Array;\n /** Only set when type === 'HASH': the major digit (0–9), absent for bare '#'. */\n hashMajor?: number;\n /** Only set when type === 'HASH': the literal head-number after the dot. */\n hashAI?: bigint;\n /**\n * Only set when type === 'HASH': the head-number is a `<type>` expression\n * (RFC 9682 §3.2); the tokens for `<` type `>` follow this token.\n */\n hashAIExpr?: boolean;\n}\n\n/** A `;` line comment collected while scanning. */\nexport interface CddlComment {\n /** Comment text after the ';' marker, without the trailing newline. */\n text: string;\n start: number;\n end: number;\n line: number;\n col: number;\n}\n\n// Shared codec instance — constructing TextEncoder per token is measurably\n// expensive in hot parsing paths (same pattern as cdn/parser.ts).\nconst textEncoder = new TextEncoder();\n\nconst isDigit = (c: string): boolean => c >= '0' && c <= '9';\nconst isHexDigit = (c: string): boolean =>\n isDigit(c) || (c >= 'a' && c <= 'f') || (c >= 'A' && c <= 'F');\nconst isEAlpha = (c: string): boolean =>\n (c >= 'a' && c <= 'z') ||\n (c >= 'A' && c <= 'Z') ||\n c === '@' ||\n c === '_' ||\n c === '$';\n\n/** NONASCII = %xA0-D7FF / %xE000-10FFFD (RFC 9682) */\nconst isNonAscii = (cp: number): boolean =>\n (cp >= 0xa0 && cp <= 0xd7ff) || (cp >= 0xe000 && cp <= 0x10fffd);\n\nexport class CddlTokenizer {\n private readonly input: string;\n private pos = 0;\n private line = 1;\n private col = 1;\n\n /** Comments encountered while scanning, in source order. */\n readonly comments: CddlComment[] = [];\n\n /** Character offset just past the last successfully scanned token. */\n lastEndOffset = 0;\n\n constructor(input: string) {\n this.input = input;\n }\n\n // ─── Low-level helpers ──────────────────────────────────────────────────────\n\n private _eof(): boolean {\n return this.pos >= this.input.length;\n }\n\n private _ch(): string {\n return this.input[this.pos] ?? '';\n }\n\n private _advance(): string {\n const ch = this.input[this.pos] ?? '';\n this.pos++;\n if (ch === '\\n') {\n this.line++;\n this.col = 1;\n } else {\n this.col++;\n }\n return ch;\n }\n\n private _fail(message: string, line?: number, col?: number): never {\n throw new CddlSyntaxError(message, {\n offset: this.pos,\n line: line ?? this.line,\n column: col ?? this.col,\n });\n }\n\n // ─── Whitespace and comments ────────────────────────────────────────────────\n\n /**\n * Skip S = *(SP / NL) where NL = COMMENT / CRLF.\n *\n * Per the ABNF only SP (0x20), LF, and CRLF are whitespace; horizontal tab\n * is not valid CDDL whitespace and is rejected with a targeted message.\n * Deliberate leniency: a bare CR (not part of CRLF) is also accepted as\n * whitespace, as source-level line-ending normalization.\n */\n private _skipWs(): void {\n for (;;) {\n const ch = this._ch();\n if (ch === ' ' || ch === '\\n' || ch === '\\r') {\n this._advance();\n continue;\n }\n if (ch === '\\t')\n this._fail(\n 'horizontal tab is not valid whitespace in CDDL (RFC 8610 ABNF allows only space and newline)'\n );\n if (ch === ';') {\n this._scanComment();\n continue;\n }\n return;\n }\n }\n\n /**\n * COMMENT = \";\" *PCHAR CRLF — collected into `this.comments`.\n *\n * Deliberate leniency: content characters are not PCHAR-validated, and a\n * comment terminated by end-of-input (no trailing newline) is accepted.\n */\n private _scanComment(): void {\n const start = this.pos;\n const line = this.line;\n const col = this.col;\n this._advance(); // ';'\n let p = this.pos;\n while (p < this.input.length) {\n const c = this.input[p]!;\n if (c === '\\n' || c === '\\r') break;\n p++;\n }\n const text = this.input.slice(this.pos, p);\n this.col += p - this.pos;\n this.pos = p;\n this.comments.push({ text, start, end: p, line, col });\n }\n\n // ─── Token production ───────────────────────────────────────────────────────\n\n private _make(\n type: CddlTokenType,\n value: string,\n startOffset: number,\n line: number,\n col: number,\n extra?: Partial<CddlToken>\n ): CddlToken {\n const token: CddlToken = {\n type,\n value,\n raw: this.input.slice(startOffset, this.pos),\n line,\n col,\n offset: startOffset,\n endOffset: this.pos,\n ...extra,\n };\n this.lastEndOffset = this.pos;\n return token;\n }\n\n /** Scan and return the next token (skipping whitespace and comments). */\n consume(): CddlToken {\n this._skipWs();\n const start = this.pos;\n const line = this.line;\n const col = this.col;\n\n if (this._eof()) return this._make('EOF', '', start, line, col);\n\n const ch = this._ch();\n\n if (isEAlpha(ch)) {\n const id = this._scanIdText();\n // bsqual: h'...' / b64'...'\n if ((id === 'h' || id === 'b64') && this._ch() === \"'\")\n return this._scanBytes(id, start, line, col);\n return this._make('ID', id, start, line, col);\n }\n\n if (isDigit(ch) || ch === '-') return this._scanNumber(start, line, col);\n\n if (ch === '\"') return this._scanText(start, line, col);\n if (ch === \"'\") return this._scanBytes('', start, line, col);\n if (ch === '#') return this._scanHash(start, line, col);\n\n switch (ch) {\n case '=':\n this._advance();\n if (this._ch() === '>') {\n this._advance();\n return this._make('ARROW', '=>', start, line, col);\n }\n return this._make('ASSIGN', '=', start, line, col);\n case '/':\n this._advance();\n if (this._ch() === '/') {\n this._advance();\n if (this._ch() === '=') {\n this._advance();\n return this._make('DSLASH_EQ', '//=', start, line, col);\n }\n return this._make('DSLASH', '//', start, line, col);\n }\n if (this._ch() === '=') {\n this._advance();\n return this._make('SLASH_EQ', '/=', start, line, col);\n }\n return this._make('SLASH', '/', start, line, col);\n case '.': {\n // '...' / '..' / '.id' (control operator)\n this._advance();\n if (this._ch() === '.') {\n this._advance();\n if (this._ch() === '.') {\n this._advance();\n return this._make('RANGE_EXCL', '...', start, line, col);\n }\n return this._make('RANGE_INCL', '..', start, line, col);\n }\n if (!isEAlpha(this._ch()))\n this._fail(\n `expected a control operator name after '.' (e.g. .size), got ${this._eof() ? 'end of input' : JSON.stringify(this._ch())}`,\n line,\n col\n );\n const op = this._scanIdText();\n return this._make('CTLOP', op, start, line, col);\n }\n case ',':\n this._advance();\n return this._make('COMMA', ',', start, line, col);\n case '(':\n this._advance();\n return this._make('LPAREN', '(', start, line, col);\n case ')':\n this._advance();\n return this._make('RPAREN', ')', start, line, col);\n case '{':\n this._advance();\n return this._make('LBRACE', '{', start, line, col);\n case '}':\n this._advance();\n return this._make('RBRACE', '}', start, line, col);\n case '[':\n this._advance();\n return this._make('LBRACKET', '[', start, line, col);\n case ']':\n this._advance();\n return this._make('RBRACKET', ']', start, line, col);\n case '<':\n this._advance();\n return this._make('LT', '<', start, line, col);\n case '>':\n this._advance();\n return this._make('GT', '>', start, line, col);\n case '~':\n this._advance();\n return this._make('TILDE', '~', start, line, col);\n case '&':\n this._advance();\n return this._make('AMP', '&', start, line, col);\n case '*':\n this._advance();\n return this._make('STAR', '*', start, line, col);\n case '+':\n this._advance();\n return this._make('PLUS', '+', start, line, col);\n case '?':\n this._advance();\n return this._make('QUEST', '?', start, line, col);\n case ':':\n this._advance();\n return this._make('COLON', ':', start, line, col);\n case '^':\n this._advance();\n return this._make('CARET', '^', start, line, col);\n default:\n this._fail(`unexpected character ${JSON.stringify(ch)}`);\n }\n }\n\n // ─── Identifiers ────────────────────────────────────────────────────────────\n\n /**\n * id = EALPHA *(*(\"-\" / \".\") (EALPHA / DIGIT))\n *\n * Interior '-' and '.' runs are allowed when followed by an EALPHA/DIGIT,\n * so `a.b`, `a-b`, and even `tstr.size` are single ids (the ABNF note\n * \"space may be needed before the operator if type2 ends in a name\" exists\n * for exactly this reason). This includes `..`: RFC 8610 §2.2.2.1 says\n * `min..max` \"is not a range expression but a single name\" — a range with\n * a name on the left-hand side must be written `min .. max`.\n */\n private _scanIdText(): string {\n const start = this.pos;\n this._advance(); // leading EALPHA, verified by caller\n for (;;) {\n const c = this._ch();\n if (isEAlpha(c) || isDigit(c)) {\n this._advance();\n continue;\n }\n if (c === '-' || c === '.') {\n // Look ahead across the separator run without consuming: the run is\n // part of the id only when an EALPHA/DIGIT follows it.\n let q = this.pos;\n while (this.input[q] === '-' || this.input[q] === '.') q++;\n const after = this.input[q] ?? '';\n if (!(isEAlpha(after) || isDigit(after))) break;\n while (this.pos <= q) this._advance(); // separators + first id char\n continue;\n }\n break;\n }\n return this.input.slice(start, this.pos);\n }\n\n // ─── Numbers ────────────────────────────────────────────────────────────────\n\n /**\n * number = hexfloat / (int [\".\" fraction] [\"e\" exponent])\n * hexfloat = [\"-\"] \"0x\" 1*HEXDIG [\".\" 1*HEXDIG] \"p\" exponent\n * uint = DIGIT1 *DIGIT / \"0x\" 1*HEXDIG / \"0b\" 1*BINDIG / \"0\"\n *\n * The token `value` is the raw numeric text; the parser converts it.\n * A '.' followed by another '.' is never consumed (range operator).\n */\n private _scanNumber(start: number, line: number, col: number): CddlToken {\n if (this._ch() === '-') this._advance();\n if (!isDigit(this._ch()))\n this._fail(`expected a digit after '-'`, line, col);\n\n let isFloat = false;\n\n if (this._ch() === '0' && /[xX]/.test(this.input[this.pos + 1] ?? '')) {\n this._advance(); // 0\n this._advance(); // x\n if (!isHexDigit(this._ch()))\n this._fail('expected hex digits after 0x', line, col);\n while (isHexDigit(this._ch())) this._advance();\n // hexfloat fraction/exponent\n if (\n this._ch() === '.' &&\n isHexDigit(this.input[this.pos + 1] ?? '') &&\n this.input[this.pos + 1] !== undefined\n ) {\n // Only a hexfloat may follow; a plain hex int never has a fraction.\n this._advance(); // .\n while (isHexDigit(this._ch())) this._advance();\n if (!/[pP]/.test(this._ch()))\n this._fail(\n \"hexadecimal fraction requires a 'p' exponent (hexfloat)\",\n line,\n col\n );\n }\n if (/[pP]/.test(this._ch())) {\n this._advance(); // p\n if (this._ch() === '+' || this._ch() === '-') this._advance();\n if (!isDigit(this._ch()))\n this._fail(\"expected exponent digits after 'p'\", line, col);\n while (isDigit(this._ch())) this._advance();\n isFloat = true;\n }\n } else if (\n this._ch() === '0' &&\n /[bB]/.test(this.input[this.pos + 1] ?? '')\n ) {\n this._advance(); // 0\n this._advance(); // b\n if (!/[01]/.test(this._ch()))\n this._fail('expected binary digits after 0b', line, col);\n while (/[01]/.test(this._ch())) this._advance();\n } else {\n if (this._ch() === '0' && isDigit(this.input[this.pos + 1] ?? ''))\n this._fail('leading zeros are not allowed in CDDL numbers', line, col);\n while (isDigit(this._ch())) this._advance();\n // fraction — but never consume '..' (range operator)\n if (this._ch() === '.' && isDigit(this.input[this.pos + 1] ?? '')) {\n this._advance(); // .\n while (isDigit(this._ch())) this._advance();\n isFloat = true;\n }\n if (/[eE]/.test(this._ch())) {\n this._advance(); // e\n if (this._ch() === '+' || this._ch() === '-') this._advance();\n if (!isDigit(this._ch()))\n this._fail(\"expected exponent digits after 'e'\", line, col);\n while (isDigit(this._ch())) this._advance();\n isFloat = true;\n }\n }\n\n const raw = this.input.slice(start, this.pos);\n return this._make(isFloat ? 'FLOAT' : 'INT', raw, start, line, col);\n }\n\n /** Scan a uint (decimal / 0x / 0b) for a '#' head-number; returns raw text. */\n private _scanUintRaw(): string {\n const start = this.pos;\n if (!isDigit(this._ch()))\n this._fail('expected an unsigned integer head-number');\n if (this._ch() === '0' && /[xX]/.test(this.input[this.pos + 1] ?? '')) {\n this._advance();\n this._advance();\n if (!isHexDigit(this._ch())) this._fail('expected hex digits after 0x');\n while (isHexDigit(this._ch())) this._advance();\n } else if (\n this._ch() === '0' &&\n /[bB]/.test(this.input[this.pos + 1] ?? '')\n ) {\n this._advance();\n this._advance();\n if (!/[01]/.test(this._ch()))\n this._fail('expected binary digits after 0b');\n while (/[01]/.test(this._ch())) this._advance();\n } else {\n if (this._ch() === '0' && isDigit(this.input[this.pos + 1] ?? ''))\n this._fail('leading zeros are not allowed in CDDL numbers');\n while (isDigit(this._ch())) this._advance();\n }\n return this.input.slice(start, this.pos);\n }\n\n // ─── '#' types ──────────────────────────────────────────────────────────────\n\n /**\n * \"#\" — any\n * \"#\" DIGIT [\".\" head-number] — major type (and tag/simple shorthands)\n * head-number = uint / \"<\" type \">\" (RFC 9682 §3.2)\n *\n * The '#', major digit, and a literal head-number are fused into a single\n * HASH token (they must be adjacent in the source; `# 6` is a bare '#'\n * followed by the value 6). For the `<type>` form, hashAIExpr is set and\n * the `<` type `>` tokens follow.\n */\n private _scanHash(start: number, line: number, col: number): CddlToken {\n this._advance(); // '#'\n const extra: Partial<CddlToken> = {};\n if (isDigit(this._ch())) {\n extra.hashMajor = this._advance().charCodeAt(0) - 0x30;\n if (this._ch() === '.') {\n if (this.input[this.pos + 1] === '<') {\n this._advance(); // '.' — the '<' type '>' tokens follow\n extra.hashAIExpr = true;\n } else {\n this._advance(); // '.'\n extra.hashAI = BigInt(this._scanUintRaw());\n }\n }\n }\n return this._make(\n 'HASH',\n this.input.slice(start, this.pos),\n start,\n line,\n col,\n extra\n );\n }\n\n // ─── Strings ────────────────────────────────────────────────────────────────\n\n /** text = %x22 *SCHAR %x22 — single-line, strict SCHAR/SESC per RFC 9682. */\n private _scanText(start: number, line: number, col: number): CddlToken {\n const value = this._readStringBody('\"');\n return this._make('TSTR', value, start, line, col);\n }\n\n /**\n * bytes = [bsqual] %x27 *BCHAR %x27\n *\n * Unqualified: content is UTF-8-encoded like a text string ('\\'' must be\n * escaped). Qualified h''/b64'': whitespace and ';' line comments inside\n * the literal are ignored, then the rest is hex / base64 decoded\n * (RFC 8610 §3.1).\n */\n private _scanBytes(\n qualifier: '' | 'h' | 'b64',\n start: number,\n line: number,\n col: number\n ): CddlToken {\n const content = this._readStringBody(\"'\");\n let bytes: Uint8Array;\n if (qualifier === '') {\n bytes = textEncoder.encode(content);\n } else {\n const data = stripWsAndComments(content);\n try {\n bytes = qualifier === 'h' ? hexToBytes(data) : base64ToBytes(data);\n } catch (e) {\n if (!(e instanceof SyntaxError) || e instanceof CddlSyntaxError)\n throw e;\n throw new CddlSyntaxError(e.message, {\n offset: start,\n line,\n column: col,\n endOffset: this.pos,\n });\n }\n }\n return this._make('BYTES', content, start, line, col, {\n qualifier,\n bytes,\n });\n }\n\n /**\n * Read the body of a '\"' text string or \"'\" byte string, decoding escapes.\n *\n * SCHAR = %x20-21 / %x23-5B / %x5D-7E / NONASCII / SESC\n * BCHAR = %x20-26 / %x28-5B / %x5D-7E / NONASCII / SESC / \"\\'\" / CRLF\n * SESC = \"\\\" ( %x22 / \"/\" / \"\\\" / b / f / n / r / t / (%x75 hexchar) )\n */\n private _readStringBody(quote: '\"' | \"'\"): string {\n const isBytes = quote === \"'\";\n this._advance(); // opening quote\n let out = '';\n for (;;) {\n if (this._eof())\n this._fail(`unterminated ${isBytes ? 'byte' : 'text'} string literal`);\n const ch = this._ch();\n if (ch === quote) {\n this._advance();\n return out;\n }\n if (ch === '\\\\') {\n const eLine = this.line;\n const eCol = this.col;\n this._advance();\n const e = this._advance();\n switch (e) {\n case '\"':\n out += '\"';\n break;\n case '/':\n out += '/';\n break;\n case '\\\\':\n out += '\\\\';\n break;\n case 'b':\n out += '\\b';\n break;\n case 'f':\n out += '\\f';\n break;\n case 'n':\n out += '\\n';\n break;\n case 'r':\n out += '\\r';\n break;\n case 't':\n out += '\\t';\n break;\n case 'u':\n out += this._readUnicodeEscape(eLine, eCol);\n break;\n case \"'\":\n if (!isBytes)\n this._fail(\n `\\\\' is only valid in byte string literals; text strings do not need it`,\n eLine,\n eCol\n );\n out += \"'\";\n break;\n default:\n this._fail(`invalid escape sequence \\\\${e}`, eLine, eCol);\n }\n continue;\n }\n // CRLF / LF is content in byte strings only.\n if (ch === '\\n' || ch === '\\r') {\n if (!isBytes)\n this._fail(\n 'text string literals cannot span lines (escape the newline as \\\\n)'\n );\n if (ch === '\\r') {\n this._advance();\n if (this._ch() !== '\\n')\n this._fail('bare CR is not allowed in byte string literals');\n this._advance();\n out += '\\r\\n';\n } else {\n this._advance();\n out += '\\n';\n }\n continue;\n }\n // Read the full code point (an astral char spans two UTF-16 units).\n const cp = this.input.codePointAt(this.pos)!;\n if (cp < 0x20 || (cp >= 0x7f && cp <= 0x9f))\n this._fail(\n `unescaped control character U+${cp.toString(16).padStart(4, '0').toUpperCase()} is not allowed in string literals`\n );\n if (cp > 0x7e && !isNonAscii(cp))\n this._fail(\n `code point U+${cp.toString(16).toUpperCase()} is not allowed in CDDL source`\n );\n this._advance();\n if (cp > 0xffff) this._advance(); // astral: second UTF-16 code unit\n out += String.fromCodePoint(cp);\n }\n }\n\n /**\n * hexchar (RFC 9682): after `\\u`, either `{...}` with a scalar value\n * (leading zeros allowed, surrogates rejected) or 4 hex digits, where a\n * high surrogate must be immediately followed by `\\uXXXX` low surrogate.\n */\n private _readUnicodeEscape(eLine: number, eCol: number): string {\n if (this._ch() === '{') {\n this._advance();\n let hex = '';\n while (isHexDigit(this._ch())) hex += this._advance();\n if (hex.length === 0)\n this._fail('\\\\u{} escape requires at least one hex digit', eLine, eCol);\n if (this._ch() !== '}')\n this._fail(\"expected '}' to close \\\\u{...} escape\", eLine, eCol);\n this._advance();\n const cp = parseInt(hex, 16);\n if (cp > 0x10ffff)\n this._fail(\n `\\\\u{${hex}} is above the Unicode code point maximum U+10FFFF`,\n eLine,\n eCol\n );\n if (cp >= 0xd800 && cp <= 0xdfff)\n this._fail(\n `\\\\u{${hex}} is a surrogate code point, not a Unicode scalar value`,\n eLine,\n eCol\n );\n return String.fromCodePoint(cp);\n }\n const readHex4 = (): number => {\n let hex = '';\n for (let i = 0; i < 4; i++) {\n if (!isHexDigit(this._ch()))\n this._fail('\\\\u escape requires four hex digits', eLine, eCol);\n hex += this._advance();\n }\n return parseInt(hex, 16);\n };\n const cp = readHex4();\n if (cp >= 0xd800 && cp <= 0xdbff) {\n // High surrogate: a low surrogate escape must follow immediately.\n if (this._ch() !== '\\\\' || this.input[this.pos + 1] !== 'u')\n this._fail(\n 'high surrogate \\\\u escape must be followed by a low surrogate \\\\u escape',\n eLine,\n eCol\n );\n this._advance();\n this._advance();\n const lo = readHex4();\n if (lo < 0xdc00 || lo > 0xdfff)\n this._fail(\n 'high surrogate \\\\u escape must be followed by a low surrogate \\\\u escape',\n eLine,\n eCol\n );\n return String.fromCodePoint(\n 0x10000 + ((cp - 0xd800) << 10) + (lo - 0xdc00)\n );\n }\n if (cp >= 0xdc00 && cp <= 0xdfff)\n this._fail('lone low surrogate \\\\u escape', eLine, eCol);\n return String.fromCodePoint(cp);\n }\n}\n\n/**\n * Remove whitespace and ';' line comments from the (escape-processed) content\n * of a prefixed h''/b64'' byte string — RFC 8610 §3.1: \"any whitespace\n * present within the string (including comments) is ignored in the prefixed\n * case\".\n */\nfunction stripWsAndComments(content: string): string {\n let out = '';\n let i = 0;\n while (i < content.length) {\n const c = content[i]!;\n if (c === ' ' || c === '\\n' || c === '\\r') {\n i++;\n continue;\n }\n if (c === ';') {\n while (i < content.length && content[i] !== '\\n') i++;\n continue;\n }\n out += c;\n i++;\n }\n return out;\n}\n","/**\n * CDDL recursive-descent parser (internal).\n *\n * Implements the grammar of RFC 8610 as updated by RFC 9682 Appendix A.\n * Produces the plain AST defined in ast.ts; all semantic processing\n * (prelude merging, name resolution, /= and //= extension) happens in\n * schema.ts.\n */\n\nimport { CddlTokenizer, type CddlComment, type CddlToken } from './tokenizer';\nimport { CddlSyntaxError } from './errors';\nimport { parseHexFloat } from '../utils/hexfloat';\nimport type {\n CddlEntryValue,\n CddlGroup,\n CddlGroupEntry,\n CddlMemberKey,\n CddlOccur,\n CddlRef,\n CddlRule,\n CddlType,\n CddlType1,\n CddlType2,\n CddlValue,\n} from './ast';\n\nexport interface ParseCddlResult {\n /** Rules in source order (unmerged; `/=` and `//=` appear as-is). */\n rules: CddlRule[];\n /** `;` comments encountered while scanning, in source order. */\n comments: CddlComment[];\n}\n\n/**\n * Parse CDDL text into rule ASTs.\n * Throws {@link CddlSyntaxError} on invalid input.\n */\nexport function parseCDDL(text: string): ParseCddlResult {\n const tokenizer = new CddlTokenizer(text);\n const parser = new CddlParser(tokenizer);\n const rules = parser.parse();\n return { rules, comments: tokenizer.comments };\n}\n\n/** Token types that continue a type1/type/memberkey after a closing paren. */\nconst TYPE_CONTINUATION: ReadonlySet<string> = new Set([\n 'SLASH',\n 'RANGE_INCL',\n 'RANGE_EXCL',\n 'CTLOP',\n 'ARROW',\n 'CARET',\n]);\n\nclass CddlParser {\n private readonly t: CddlTokenizer;\n private readonly buf: CddlToken[] = [];\n\n constructor(tokenizer: CddlTokenizer) {\n this.t = tokenizer;\n }\n\n // ─── Token plumbing ─────────────────────────────────────────────────────────\n\n private peek(i = 0): CddlToken {\n while (this.buf.length <= i) this.buf.push(this.t.consume());\n return this.buf[i]!;\n }\n\n private consume(): CddlToken {\n return this.buf.shift() ?? this.t.consume();\n }\n\n private expect(type: CddlToken['type'], what: string): CddlToken {\n const tok = this.peek();\n if (tok.type !== type) this._fail(`expected ${what}`, tok);\n return this.consume();\n }\n\n private _fail(message: string, tok: CddlToken): never {\n const got =\n tok.type === 'EOF' ? 'end of input' : `${JSON.stringify(tok.raw)}`;\n throw new CddlSyntaxError(`${message}, got ${got}`, {\n offset: tok.offset,\n endOffset: tok.endOffset,\n line: tok.line,\n column: tok.col,\n });\n }\n\n // ─── cddl = S *(rule S) ─────────────────────────────────────────────────────\n\n parse(): CddlRule[] {\n const rules: CddlRule[] = [];\n while (this.peek().type !== 'EOF') rules.push(this.parseRule());\n return rules;\n }\n\n /**\n * rule = typename [genericparm] S assignt S type\n * / groupname [genericparm] S assigng S grpent\n *\n * For '=' (shared by assignt and assigng) the body is parsed as a group\n * entry, which subsumes a plain type. '/=' is assignt only, so its\n * right-hand side must be a plain type; '//=' (assigng) takes a grpent.\n */\n private parseRule(): CddlRule {\n const nameTok = this.expect('ID', 'a rule name');\n let generics: string[] | undefined;\n if (this.peek().type === 'LT') {\n this.consume();\n generics = [this.expect('ID', 'a generic parameter name').value];\n while (this.peek().type === 'COMMA') {\n this.consume();\n generics.push(this.expect('ID', 'a generic parameter name').value);\n }\n this.expect('GT', `'>' after generic parameters`);\n }\n const assignTok = this.peek();\n let assign: CddlRule['assign'];\n if (assignTok.type === 'ASSIGN') assign = '=';\n else if (assignTok.type === 'SLASH_EQ') assign = '/=';\n else if (assignTok.type === 'DSLASH_EQ') assign = '//=';\n else this._fail(`expected '=', '/=' or '//=' after rule name`, assignTok);\n this.consume();\n const body =\n assign === '/=' ? this.parseTypeAsEntry() : this.parseGroupEntry();\n return {\n kind: 'rule',\n name: nameTok.value,\n ...(generics ? { generics } : {}),\n assign,\n body,\n start: nameTok.offset,\n end: body.end,\n };\n }\n\n /** A plain type in rule-body position, wrapped as an entry AST node. */\n private parseTypeAsEntry(): CddlEntryValue {\n const value = this.parseType();\n return {\n kind: 'entry',\n value,\n start: value.start,\n end: value.end,\n };\n }\n\n // ─── Groups ─────────────────────────────────────────────────────────────────\n\n /** group = grpchoice *(S \"//\" S grpchoice), up to (not including) `closer`. */\n private parseGroup(closer: CddlToken['type']): CddlGroup {\n const start = this.peek().offset;\n const choices: CddlGroupEntry[][] = [[]];\n let lastWasComma = false;\n for (;;) {\n const tok = this.peek();\n if (tok.type === closer) break;\n if (tok.type === 'EOF')\n this._fail(\n `unterminated group; expected ${JSON.stringify(closer)}`,\n tok\n );\n if (tok.type === 'DSLASH') {\n this.consume();\n choices.push([]);\n lastWasComma = false;\n continue;\n }\n choices[choices.length - 1]!.push(this.parseGroupEntry());\n // optcom = S [\",\" S] — the comma after an entry is optional.\n lastWasComma = this.peek().type === 'COMMA';\n if (lastWasComma) this.consume();\n }\n const endTok = this.peek(); // the closer, consumed by the caller\n return {\n kind: 'group',\n choices,\n ...(lastWasComma ? { trailingComma: true } : {}),\n start,\n end: endTok.offset,\n };\n }\n\n /**\n * grpent = [occur S] [memberkey S] type\n * / [occur S] groupname [genericarg] ; covered by the type branch\n * / [occur S] \"(\" S group S \")\"\n */\n private parseGroupEntry(): CddlGroupEntry {\n const start = this.peek().offset;\n const occur = this.tryParseOccur();\n\n // Inline parenthesized group — unless what follows the ')' pulls the\n // parenthesized expression back into type position (e.g. `(\"a\"/\"b\") .size 1`\n // is a paren *type* with a control operator, not a group entry).\n if (this.peek().type === 'LPAREN') {\n const lparen = this.consume();\n const group = this.parseGroup('RPAREN');\n const rparen = this.consume();\n if (TYPE_CONTINUATION.has(this.peek().type)) {\n const paren = this.groupAsParenType(group, lparen, rparen);\n const type1 = this.continueType1(paren);\n return this.finishEntryFromType1(start, occur, type1);\n }\n return {\n kind: 'entry-group',\n ...(occur ? { occur } : {}),\n group,\n start,\n end: rparen.endOffset,\n };\n }\n\n // memberkey shortcuts: bareword \":\" and value \":\"\n const t0 = this.peek(0);\n const t1 = this.peek(1);\n if (t1.type === 'COLON' && (t0.type === 'ID' || this.isValueToken(t0))) {\n let memberKey: CddlMemberKey;\n if (t0.type === 'ID') {\n this.consume();\n const colon = this.consume();\n memberKey = {\n kind: 'bareword',\n key: t0.value,\n cut: true,\n start: t0.offset,\n end: colon.endOffset,\n };\n } else {\n const key = this.parseValue();\n const colon = this.consume();\n memberKey = {\n kind: 'value',\n key,\n cut: true,\n start: key.start,\n end: colon.endOffset,\n };\n }\n const value = this.parseType();\n return {\n kind: 'entry',\n ...(occur ? { occur } : {}),\n memberKey,\n value,\n start,\n end: value.end,\n };\n }\n\n // General case: parse a type1, then decide whether it was a member key.\n const type1 = this.parseType1();\n return this.finishEntryFromType1(start, occur, type1);\n }\n\n /**\n * After parsing an initial type1 in entry position: `^`/`=>` make it a\n * member key (memberkey = type1 S [\"^\" S] \"=>\"); otherwise it starts the\n * entry's type and further `/` alternatives may follow.\n */\n private finishEntryFromType1(\n start: number,\n occur: CddlOccur | undefined,\n type1: CddlType1\n ): CddlEntryValue {\n let memberKey: CddlMemberKey | undefined;\n if (this.peek().type === 'CARET' || this.peek().type === 'ARROW') {\n let cut = false;\n if (this.peek().type === 'CARET') {\n this.consume();\n cut = true;\n }\n const arrow = this.expect('ARROW', `'=>' after member key`);\n memberKey = {\n kind: 'type1',\n key: type1,\n cut,\n start: type1.start,\n end: arrow.endOffset,\n };\n }\n const value = memberKey\n ? this.parseType()\n : this.continueTypeAlternatives(type1);\n return {\n kind: 'entry',\n ...(occur ? { occur } : {}),\n ...(memberKey ? { memberKey } : {}),\n value,\n start,\n end: value.end,\n };\n }\n\n /** occur = [uint] \"*\" [uint] / \"+\" / \"?\" — components must be adjacent. */\n private tryParseOccur(): CddlOccur | undefined {\n const t0 = this.peek(0);\n if (t0.type === 'QUEST') {\n this.consume();\n return {\n kind: 'occur',\n marker: '?',\n start: t0.offset,\n end: t0.endOffset,\n };\n }\n if (t0.type === 'PLUS') {\n this.consume();\n return {\n kind: 'occur',\n marker: '+',\n start: t0.offset,\n end: t0.endOffset,\n };\n }\n if (t0.type === 'STAR') {\n this.consume();\n let max: number | undefined;\n let end = t0.endOffset;\n const next = this.peek();\n if (next.type === 'INT' && next.offset === t0.endOffset) {\n max = this.occurBound(this.consume());\n end = next.endOffset;\n }\n return {\n kind: 'occur',\n marker: '*',\n ...(max !== undefined ? { max } : {}),\n start: t0.offset,\n end,\n };\n }\n // `n*` / `n*m` — only when INT and '*' are adjacent (per the ABNF, occur\n // has no interior whitespace; adjacency is what distinguishes the\n // occurrence `1*2` from the value 1 followed by the occurrence `*2`).\n if (\n t0.type === 'INT' &&\n !t0.value.startsWith('-') &&\n this.peek(1).type === 'STAR' &&\n this.peek(1).offset === t0.endOffset\n ) {\n const min = this.occurBound(this.consume());\n const star = this.consume();\n let max: number | undefined;\n let end = star.endOffset;\n const next = this.peek();\n if (next.type === 'INT' && next.offset === star.endOffset) {\n max = this.occurBound(this.consume());\n end = next.endOffset;\n }\n return { kind: 'occur', marker: '*', min, max, start: t0.offset, end };\n }\n return undefined;\n }\n\n private occurBound(tok: CddlToken): number {\n if (tok.value.startsWith('-'))\n this._fail('occurrence bounds must be unsigned integers', tok);\n const n = Number(tok.value);\n if (!Number.isSafeInteger(n))\n this._fail('occurrence bound is too large', tok);\n return n;\n }\n\n // ─── Types ──────────────────────────────────────────────────────────────────\n\n /** type = type1 *(S \"/\" S type1) */\n private parseType(): CddlType {\n return this.continueTypeAlternatives(this.parseType1());\n }\n\n private continueTypeAlternatives(first: CddlType1): CddlType {\n const alternatives = [first];\n while (this.peek().type === 'SLASH') {\n this.consume();\n alternatives.push(this.parseType1());\n }\n return {\n kind: 'type',\n alternatives,\n start: first.start,\n end: alternatives[alternatives.length - 1]!.end,\n };\n }\n\n /** type1 = type2 [S (rangeop / ctlop) S type2] */\n private parseType1(): CddlType1 {\n return this.continueType1(this.parseType2());\n }\n\n private continueType1(target: CddlType2): CddlType1 {\n const opTok = this.peek();\n let op: CddlType1['op'];\n if (opTok.type === 'RANGE_INCL' || opTok.type === 'RANGE_EXCL')\n op = { kind: 'range', inclusive: opTok.type === 'RANGE_INCL' };\n else if (opTok.type === 'CTLOP') op = { kind: 'ctl', name: opTok.value };\n if (!op)\n return { kind: 'type1', target, start: target.start, end: target.end };\n this.consume();\n const controller = this.parseType2();\n return {\n kind: 'type1',\n target,\n op,\n controller,\n start: target.start,\n end: controller.end,\n };\n }\n\n private parseType2(): CddlType2 {\n const tok = this.peek();\n switch (tok.type) {\n case 'INT':\n case 'FLOAT':\n case 'TSTR':\n case 'BYTES':\n return this.parseValue();\n\n case 'ID': {\n this.consume();\n return this.parseRefTail(tok);\n }\n\n case 'LPAREN': {\n const lparen = this.consume();\n const type = this.parseType();\n const rparen = this.expect(\n 'RPAREN',\n `')' to close the parenthesized type`\n );\n return {\n kind: 'paren',\n type,\n start: lparen.offset,\n end: rparen.endOffset,\n };\n }\n\n case 'LBRACE': {\n const open = this.consume();\n const group = this.parseGroup('RBRACE');\n const close = this.consume();\n return {\n kind: 'map',\n group,\n start: open.offset,\n end: close.endOffset,\n };\n }\n\n case 'LBRACKET': {\n const open = this.consume();\n const group = this.parseGroup('RBRACKET');\n const close = this.consume();\n return {\n kind: 'array',\n group,\n start: open.offset,\n end: close.endOffset,\n };\n }\n\n case 'TILDE': {\n const tilde = this.consume();\n const nameTok = this.expect('ID', `a type name after '~'`);\n const ref = this.parseRefTail(nameTok);\n return { kind: 'unwrap', ref, start: tilde.offset, end: ref.end };\n }\n\n case 'AMP': {\n const amp = this.consume();\n if (this.peek().type === 'LPAREN') {\n this.consume();\n const group = this.parseGroup('RPAREN');\n const rparen = this.consume();\n return {\n kind: 'enum',\n group,\n start: amp.offset,\n end: rparen.endOffset,\n };\n }\n const nameTok = this.expect('ID', `a group name or '(' after '&'`);\n const ref = this.parseRefTail(nameTok);\n return { kind: 'enum', group: ref, start: amp.offset, end: ref.end };\n }\n\n case 'HASH':\n return this.parseHashType(this.consume());\n\n default:\n this._fail('expected a type', tok);\n }\n }\n\n /** Generic arguments after a just-consumed ID token: [genericarg]. */\n private parseRefTail(nameTok: CddlToken): CddlRef {\n if (this.peek().type !== 'LT')\n return {\n kind: 'ref',\n name: nameTok.value,\n start: nameTok.offset,\n end: nameTok.endOffset,\n };\n this.consume();\n const genericArgs = [this.parseType1()];\n while (this.peek().type === 'COMMA') {\n this.consume();\n genericArgs.push(this.parseType1());\n }\n const gt = this.expect('GT', `'>' after generic arguments`);\n return {\n kind: 'ref',\n name: nameTok.value,\n genericArgs,\n start: nameTok.offset,\n end: gt.endOffset,\n };\n }\n\n /**\n * '#' family, from a HASH token produced by the tokenizer:\n * \"#\" → any\n * \"#\" \"6\" [\".\" head-number] \"(\" type \")\" → tagged\n * \"#\" \"7\" [\".\" head-number] → major 7 (simple/float)\n * \"#\" DIGIT [\".\" uint] → major/ai\n * head-number = uint / \"<\" type \">\" (RFC 9682 §3.2)\n */\n private parseHashType(tok: CddlToken): CddlType2 {\n if (tok.hashMajor === undefined) {\n if (tok.hashAIExpr || tok.hashAI !== undefined)\n this._fail(`'#' without a major type cannot take a head-number`, tok);\n return { kind: 'any', start: tok.offset, end: tok.endOffset };\n }\n const major = tok.hashMajor;\n\n let head: bigint | CddlType | undefined = tok.hashAI;\n let headEnd = tok.endOffset;\n if (tok.hashAIExpr) {\n if (major !== 6 && major !== 7)\n this._fail(\n `a <type> head-number is only allowed for #6 and #7 (RFC 9682 §3.2)`,\n tok\n );\n this.expect('LT', `'<' for the head-number expression`);\n head = this.parseType();\n const gt = this.expect('GT', `'>' after the head-number expression`);\n headEnd = gt.endOffset;\n }\n\n // For a literal (or absent) head-number, keep the '#…' source text so the\n // formatter can preserve the number base (e.g. '#6.0x10').\n const raw = tok.hashAIExpr ? undefined : tok.raw;\n\n if (major === 6 && this.peek().type === 'LPAREN') {\n this.consume();\n const item = this.parseType();\n const rparen = this.expect('RPAREN', `')' to close the tagged type`);\n return {\n kind: 'tagged',\n ...(head !== undefined ? { tag: head } : {}),\n item,\n ...(raw !== undefined ? { raw } : {}),\n start: tok.offset,\n end: rparen.endOffset,\n };\n }\n if (tok.hashAIExpr && major === 6)\n this._fail(`#6.<…> must be followed by '(' type ')'`, this.peek());\n\n return {\n kind: 'major',\n major,\n ...(head !== undefined ? { ai: head } : {}),\n ...(raw !== undefined ? { raw } : {}),\n start: tok.offset,\n end: headEnd,\n };\n }\n\n // ─── Values ─────────────────────────────────────────────────────────────────\n\n private isValueToken(tok: CddlToken): boolean {\n return (\n tok.type === 'INT' ||\n tok.type === 'FLOAT' ||\n tok.type === 'TSTR' ||\n tok.type === 'BYTES'\n );\n }\n\n private parseValue(): CddlValue {\n const tok = this.consume();\n const base = { start: tok.offset, end: tok.endOffset, raw: tok.raw };\n switch (tok.type) {\n case 'INT': {\n // BigInt() rejects a sign on 0x/0b literals — apply it separately.\n const big = tok.value.startsWith('-')\n ? -BigInt(tok.value.slice(1))\n : BigInt(tok.value);\n const value =\n big >= BigInt(Number.MIN_SAFE_INTEGER) &&\n big <= BigInt(Number.MAX_SAFE_INTEGER)\n ? Number(big)\n : big;\n return { kind: 'value', type: 'int', value, ...base };\n }\n case 'FLOAT': {\n const value = /^-?0[xX]/.test(tok.value)\n ? parseHexFloat(tok.value)\n : parseFloat(tok.value);\n return { kind: 'value', type: 'float', value, ...base };\n }\n case 'TSTR':\n return { kind: 'value', type: 'text', value: tok.value, ...base };\n case 'BYTES':\n return {\n kind: 'value',\n type: 'bytes',\n value: tok.bytes!,\n qualifier: tok.qualifier!,\n ...base,\n };\n default:\n this._fail('expected a literal value', tok);\n }\n }\n\n /**\n * Reinterpret a parsed parenthesized group as a parenthesized *type* —\n * needed when a range/control operator, '/', or '=>' follows the ')'.\n * Only a group of exactly one plain entry (no occurrence, no member key,\n * no trailing comma, single choice) is a valid type.\n */\n private groupAsParenType(\n group: CddlGroup,\n lparen: CddlToken,\n rparen: CddlToken\n ): CddlType2 {\n const only =\n group.choices.length === 1 && group.choices[0]!.length === 1\n ? group.choices[0]![0]!\n : undefined;\n if (\n !only ||\n only.kind !== 'entry' ||\n only.occur ||\n only.memberKey ||\n group.trailingComma\n )\n this._fail(\n 'this parenthesized group is used as a type (an operator follows), but it contains group syntax',\n this.peek()\n );\n return {\n kind: 'paren',\n type: only.value,\n start: lparen.offset,\n end: rparen.endOffset,\n };\n }\n}\n","/**\n * The CDDL standard prelude (RFC 8610 Appendix D, normative).\n *\n * The prelude is automatically added to each CDDL file. It is technically a\n * postlude: it never disturbs the selection of the first user rule as the\n * root of the definition, and user rules shadow prelude names.\n */\n\nimport { parseCDDL } from './parser';\nimport type { CddlRule } from './ast';\n\n/** Verbatim text of the RFC 8610 Appendix D standard prelude. */\nexport const PRELUDE_CDDL = `any = #\n\nuint = #0\nnint = #1\nint = uint / nint\n\nbstr = #2\nbytes = bstr\ntstr = #3\ntext = tstr\n\ntdate = #6.0(tstr)\ntime = #6.1(number)\nnumber = int / float\nbiguint = #6.2(bstr)\nbignint = #6.3(bstr)\nbigint = biguint / bignint\ninteger = int / bigint\nunsigned = uint / biguint\ndecfrac = #6.4([e10: int, m: integer])\nbigfloat = #6.5([e2: int, m: integer])\neb64url = #6.21(any)\neb64legacy = #6.22(any)\neb16 = #6.23(any)\nencoded-cbor = #6.24(bstr)\nuri = #6.32(tstr)\nb64url = #6.33(tstr)\nb64legacy = #6.34(tstr)\nregexp = #6.35(tstr)\nmime-message = #6.36(tstr)\ncbor-any = #6.55799(any)\n\nfloat16 = #7.25\nfloat32 = #7.26\nfloat64 = #7.27\nfloat16-32 = float16 / float32\nfloat32-64 = float32 / float64\nfloat = float16-32 / float64\n\nfalse = #7.20\ntrue = #7.21\nbool = false / true\nnil = #7.22\nnull = nil\nundefined = #7.23\n`;\n\nlet cached: Map<string, CddlRule> | undefined;\n\n/** The parsed prelude rules by name, parsed once and cached. */\nexport function getPreludeRules(): Map<string, CddlRule> {\n if (!cached) {\n cached = new Map();\n for (const rule of parseCDDL(PRELUDE_CDDL).rules)\n cached.set(rule.name, rule);\n }\n return cached;\n}\n","/**\n * CDDL formatter: serialize rule ASTs back to CDDL text.\n *\n * Two layouts:\n * - Compact (default): one rule per line with single-space separators.\n * - Pretty (`indent` set): groups with more than one entry (or group\n * choices) put each entry on its own indented line; multi-line rules are\n * separated by blank lines.\n *\n * Literal values are emitted verbatim from their source text (`raw`), so\n * number bases, string escapes, and byte-string qualifiers survive a round\n * trip. With `preserveComments`, `;` comments are re-attached by position\n * and none is dropped: rule leading/trailing, before a rule body (after\n * `=`), on group entries, before a group's closing delimiter, and — for\n * comments inside inline-only positions such as type choices — on the\n * enclosing rule's line end. The compact layout cannot hold an interior\n * line comment (`;` runs to the end of the line), so it hoists body\n * comments above the rule and keeps only rule-level placements.\n */\n\nimport type { CddlComment } from './tokenizer';\nimport type {\n CddlGroup,\n CddlGroupEntry,\n CddlMemberKey,\n CddlOccur,\n CddlRef,\n CddlRule,\n CddlType,\n CddlType1,\n CddlType2,\n} from './ast';\n\nexport interface CddlFormatOptions {\n /**\n * Pretty-print groups with one entry per line, indented by this many\n * spaces (or by the given string). Omit for compact single-line rules.\n */\n indent?: number | string;\n /**\n * Re-emit `;` comments. Rule-level comments are kept in both layouts;\n * comments attached to group entries require `indent` (the pretty\n * layout). Only effective when the formatter has the comment stream and\n * source text — i.e. when called through `CddlSchema.format()`.\n */\n preserveComments?: boolean;\n}\n\n/** @internal Extras supplied by CddlSchema.format(). */\nexport interface CddlFormatContext {\n source?: string;\n comments?: readonly CddlComment[];\n}\n\ninterface Notes {\n leading: string[];\n trailing: string[];\n}\n\ninterface Ctx {\n /** Indent unit; null = compact layout. */\n unit: string | null;\n notes: Map<object, Notes> | null;\n /** Comments emitted before a group's closing delimiter. */\n endNotes: Map<CddlGroup, string[]> | null;\n /** Comments after the last rule (emitted at the end). */\n tail: string[];\n}\n\nconst EMPTY_NOTES: Notes = { leading: [], trailing: [] };\n\n/** Format rules (in the given order) as CDDL text with a trailing newline. */\nexport function formatCddl(\n rules: readonly CddlRule[],\n options?: CddlFormatOptions & CddlFormatContext\n): string {\n const unit =\n options?.indent === undefined\n ? null\n : typeof options.indent === 'string'\n ? options.indent\n : ' '.repeat(options.indent);\n const ctx: Ctx = { unit, notes: null, endNotes: null, tail: [] };\n if (\n options?.preserveComments &&\n options.comments !== undefined &&\n options.comments.length > 0 &&\n options.source !== undefined\n ) {\n const built = buildNotes(rules, options.comments, options.source);\n ctx.notes = built.notes;\n ctx.endNotes = built.endNotes;\n ctx.tail = built.tail;\n }\n\n const parts: string[] = [];\n let prevMultiline = false;\n rules.forEach((rule, i) => {\n const { text, multiline } = formatRule(rule, ctx);\n // Blank line around rules with multi-line bodies in the pretty layout\n // (leading comments alone do not count).\n if (i > 0 && ctx.unit !== null && (multiline || prevMultiline))\n parts.push('');\n parts.push(text);\n prevMultiline = multiline;\n });\n for (const text of ctx.tail) parts.push(`;${text}`);\n if (parts.length === 0) return '';\n return parts.join('\\n') + '\\n';\n}\n\n// ─── Comment attachment ──────────────────────────────────────────────────────\n\ninterface Anchor {\n node: object;\n start: number;\n end: number;\n isRule: boolean;\n}\n\n/**\n * Associate each comment with the position it will be emitted at, so that\n * `preserveComments` never drops one:\n * - trailing on the rule/entry ending on the comment's line;\n * - else leading on the next rule/entry — but only when that target stays\n * inside every group/rule enclosing the comment;\n * - else, for a comment inside a group with nothing after it (including\n * empty groups), on the group's end position (before the closer);\n * - else, for a comment inside a rule's type expression (e.g. between type\n * choices, which format inline), trailing on the rule;\n * - comments after everything go to `tail`.\n */\nfunction buildNotes(\n rules: readonly CddlRule[],\n comments: readonly CddlComment[],\n source: string\n): {\n notes: Map<object, Notes>;\n endNotes: Map<CddlGroup, string[]>;\n tail: string[];\n} {\n // Line-start offsets for offset→line lookups (comments carry their line).\n const lineStarts = [0];\n for (let i = 0; i < source.length; i++)\n if (source.charCodeAt(i) === 0x0a) lineStarts.push(i + 1);\n const lineOf = (offset: number): number => {\n let lo = 0;\n let hi = lineStarts.length - 1;\n while (lo < hi) {\n const mid = (lo + hi + 1) >> 1;\n if (lineStarts[mid]! <= offset) lo = mid;\n else hi = mid - 1;\n }\n return lo + 1; // 1-based, matching CddlComment.line\n };\n\n const anchors: Anchor[] = [];\n // Group containment uses the span of the *construct* holding the group\n // (including its delimiters) — an empty group's own span is zero-width.\n const groups: { group: CddlGroup; start: number; end: number }[] = [];\n const addGroup = (group: CddlGroup, start: number, end: number): void => {\n groups.push({ group, start, end });\n for (const choice of group.choices) choice.forEach(addEntry);\n };\n const addEntry = (entry: CddlGroupEntry): void => {\n anchors.push({\n node: entry,\n start: entry.start,\n end: entry.end,\n isRule: false,\n });\n if (entry.kind === 'entry-group') {\n addGroup(entry.group, entry.start, entry.end);\n return;\n }\n for (const t1 of entry.value.alternatives) addType1(t1);\n };\n const addType1 = (t1: CddlType1): void => {\n addType2(t1.target);\n if (t1.controller) addType2(t1.controller);\n };\n const addType2 = (t2: CddlType2): void => {\n switch (t2.kind) {\n case 'map':\n case 'array':\n addGroup(t2.group, t2.start, t2.end);\n return;\n case 'paren':\n for (const t1 of t2.type.alternatives) addType1(t1);\n return;\n case 'enum':\n if (t2.group.kind === 'group') addGroup(t2.group, t2.start, t2.end);\n return;\n case 'tagged':\n if (typeof t2.tag === 'object')\n for (const t1 of t2.tag.alternatives) addType1(t1);\n for (const t1 of t2.item.alternatives) addType1(t1);\n return;\n default:\n return;\n }\n };\n for (const rule of rules) {\n anchors.push({\n node: rule,\n start: rule.start,\n end: rule.end,\n isRule: true,\n });\n addEntry(rule.body);\n }\n\n // Trailing lookup: maximal end ≤ comment start; rules win end-ties so a\n // comment after `a = int` lands on the rule, not on its body entry.\n const byEnd = [...anchors].sort(\n (a, b) => a.end - b.end || Number(a.isRule) - Number(b.isRule)\n );\n // Leading lookup: minimal start ≥ comment end; rules win start-ties.\n const byStart = [...anchors].sort(\n (a, b) => a.start - b.start || Number(b.isRule) - Number(a.isRule)\n );\n\n const notes = new Map<object, Notes>();\n const endNotes = new Map<CddlGroup, string[]>();\n const tail: string[] = [];\n const notesFor = (node: object): Notes => {\n let n = notes.get(node);\n if (!n) {\n n = { leading: [], trailing: [] };\n notes.set(node, n);\n }\n return n;\n };\n\n for (const c of comments) {\n // Trailing: the anchor ending last at or before the comment, same line.\n let trailingTo: Anchor | undefined;\n for (let i = byEnd.length - 1; i >= 0; i--) {\n const a = byEnd[i]!;\n if (a.end > c.start) continue;\n if (lineOf(Math.max(a.start, a.end - 1)) === c.line) trailingTo = a;\n break;\n }\n if (trailingTo) {\n notesFor(trailingTo.node).trailing.push(c.text);\n continue;\n }\n\n // Innermost group / rule whose span encloses the comment.\n let containerGroup:\n { group: CddlGroup; start: number; end: number } | undefined;\n for (const g of groups)\n if (\n g.start <= c.start &&\n c.end <= g.end &&\n (!containerGroup || g.start >= containerGroup.start)\n )\n containerGroup = g;\n const containerRule = rules.find(\n (r) => r.start <= c.start && c.end <= r.end\n );\n\n // Leading on the next rule/entry — only when that target does not\n // escape an enclosing construct (which would move the comment outside).\n const leadingTo = byStart.find((a) => a.start >= c.end);\n const escapesGroup =\n containerGroup !== undefined &&\n (leadingTo === undefined || leadingTo.start > containerGroup.end);\n const escapesRule =\n containerRule !== undefined &&\n (leadingTo === undefined || leadingTo.start > containerRule.end);\n if (leadingTo && !escapesGroup && !escapesRule) {\n notesFor(leadingTo.node).leading.push(c.text);\n } else if (escapesGroup) {\n // Nothing follows inside the group (or it is empty): emit the\n // comment just before the group's closing delimiter.\n const list = endNotes.get(containerGroup!.group) ?? [];\n list.push(c.text);\n endNotes.set(containerGroup!.group, list);\n } else if (escapesRule) {\n // Inside the rule's type expression (choices format inline): keep it\n // on the rule line as a trailing comment.\n notesFor(containerRule!).trailing.push(c.text);\n } else if (leadingTo) {\n notesFor(leadingTo.node).leading.push(c.text);\n } else {\n tail.push(c.text);\n }\n }\n return { notes, endNotes, tail };\n}\n\n// ─── Emission ─────────────────────────────────────────────────────────────────\n\nconst notesOf = (ctx: Ctx, node: object): Notes =>\n ctx.notes?.get(node) ?? EMPTY_NOTES;\n\nconst trailingText = (notes: Notes): string =>\n notes.trailing.length === 0\n ? ''\n : ' ' + notes.trailing.map((t) => `;${t}`).join(' ');\n\nfunction formatRule(\n rule: CddlRule,\n ctx: Ctx\n): { text: string; multiline: boolean } {\n const notes = notesOf(ctx, rule);\n const bodyNotes = notesOf(ctx, rule.body);\n const generics = rule.generics ? `<${rule.generics.join(', ')}>` : '';\n const head = `${rule.name}${generics} ${rule.assign}`;\n const trailing = trailingText({\n leading: [],\n trailing: [...bodyNotes.trailing, ...notes.trailing],\n });\n\n let main: string;\n let leading = notes.leading;\n if (bodyNotes.leading.length > 0 && ctx.unit !== null) {\n // Comments between `=` and the body get their own indented lines:\n // a =\n // ; important\n // int\n const pad = ctx.unit;\n main = [\n head,\n ...bodyNotes.leading.map((t) => `${pad};${t}`),\n `${pad}${formatEntry(rule.body, ctx, 1)}${trailing}`,\n ].join('\\n');\n } else {\n // Compact layout cannot hold a mid-line comment: hoist body-leading\n // comments above the rule so they are never dropped.\n if (bodyNotes.leading.length > 0)\n leading = [...leading, ...bodyNotes.leading];\n main = `${head} ${formatEntry(rule.body, ctx, 0)}${trailing}`;\n }\n\n const multiline = main.includes('\\n');\n if (leading.length === 0) return { text: main, multiline };\n return {\n text: [...leading.map((t) => `;${t}`), main].join('\\n'),\n multiline,\n };\n}\n\nfunction formatEntry(entry: CddlGroupEntry, ctx: Ctx, depth: number): string {\n const occur = entry.occur ? `${formatOccur(entry.occur)} ` : '';\n if (entry.kind === 'entry-group')\n return `${occur}${formatGroupBody(entry.group, ctx, depth, '(', ')')}`;\n const key = entry.memberKey\n ? `${formatMemberKey(entry.memberKey, ctx, depth)} `\n : '';\n return `${occur}${key}${formatType(entry.value, ctx, depth)}`;\n}\n\nfunction formatOccur(occur: CddlOccur): string {\n if (occur.marker !== '*') return occur.marker;\n return `${occur.min ?? ''}*${occur.max ?? ''}`;\n}\n\nfunction formatMemberKey(key: CddlMemberKey, ctx: Ctx, depth: number): string {\n switch (key.kind) {\n case 'bareword':\n return `${key.key}:`;\n case 'value':\n return `${key.key.raw}:`;\n case 'type1':\n return `${formatType1(key.key, ctx, depth)} ${key.cut ? '^ ' : ''}=>`;\n }\n}\n\n/**\n * A group between `open`/`close` delimiters. In the pretty layout, groups\n * with more than one entry (or more than one choice) are laid out one entry\n * per line; group choices are separated by a `//` line.\n */\nfunction formatGroupBody(\n group: CddlGroup,\n ctx: Ctx,\n depth: number,\n open: string,\n close: string\n): string {\n const entryCount = group.choices.reduce((n, c) => n + c.length, 0);\n const endComments = ctx.endNotes?.get(group) ?? [];\n // Any comment inside the group forces the multi-line layout — an inline\n // group cannot hold a `;` comment (it runs to the end of the line).\n const hasNotes =\n endComments.length > 0 ||\n (ctx.notes !== null &&\n group.choices.some((c) => c.some((e) => ctx.notes!.has(e))));\n const multiline =\n ctx.unit !== null &&\n (entryCount > 1 || group.choices.length > 1 || hasNotes);\n\n if (!multiline) {\n const body =\n group.choices\n .map((entries) =>\n entries.map((e) => formatEntry(e, ctx, depth)).join(', ')\n )\n .join(' // ') + (group.trailingComma ? ',' : '');\n return `${open}${body}${close}`;\n }\n\n const unit = ctx.unit!;\n const pad = unit.repeat(depth + 1);\n const lines: string[] = [open];\n group.choices.forEach((entries, ci) => {\n if (ci > 0) lines.push(`${pad}//`);\n entries.forEach((entry, ei) => {\n const notes = notesOf(ctx, entry);\n for (const t of notes.leading) lines.push(`${pad};${t}`);\n const isLast =\n ci === group.choices.length - 1 && ei === entries.length - 1;\n const comma = !isLast || group.trailingComma ? ',' : '';\n lines.push(\n `${pad}${formatEntry(entry, ctx, depth + 1)}${comma}${trailingText(notes)}`\n );\n });\n });\n // Comments with nothing after them inside the group (including comments\n // in empty groups) sit just before the closing delimiter.\n for (const t of endComments) lines.push(`${pad};${t}`);\n lines.push(`${unit.repeat(depth)}${close}`);\n return lines.join('\\n');\n}\n\nfunction formatType(type: CddlType, ctx: Ctx, depth: number): string {\n return type.alternatives.map((t1) => formatType1(t1, ctx, depth)).join(' / ');\n}\n\nfunction formatType1(type1: CddlType1, ctx: Ctx, depth: number): string {\n const target = formatType2(type1.target, ctx, depth);\n if (!type1.op || !type1.controller) return target;\n const controller = formatType2(type1.controller, ctx, depth);\n if (type1.op.kind === 'range')\n return `${target}${type1.op.inclusive ? '..' : '...'}${controller}`;\n return `${target} .${type1.op.name} ${controller}`;\n}\n\nfunction formatRef(ref: CddlRef, ctx: Ctx, depth: number): string {\n const args = ref.genericArgs\n ? `<${ref.genericArgs.map((a) => formatType1(a, ctx, depth)).join(', ')}>`\n : '';\n return `${ref.name}${args}`;\n}\n\nfunction formatType2(type2: CddlType2, ctx: Ctx, depth: number): string {\n switch (type2.kind) {\n case 'value':\n return type2.raw;\n case 'ref':\n return formatRef(type2, ctx, depth);\n case 'paren':\n return `(${formatType(type2.type, ctx, depth)})`;\n case 'map':\n return formatGroupBody(type2.group, ctx, depth, '{', '}');\n case 'array':\n return formatGroupBody(type2.group, ctx, depth, '[', ']');\n case 'unwrap':\n return `~${formatRef(type2.ref, ctx, depth)}`;\n case 'enum':\n return type2.group.kind === 'ref'\n ? `&${formatRef(type2.group, ctx, depth)}`\n : `&${formatGroupBody(type2.group, ctx, depth, '(', ')')}`;\n case 'tagged': {\n const head =\n type2.raw ??\n (typeof type2.tag === 'object'\n ? `#6.<${formatType(type2.tag, ctx, depth)}>`\n : `#6${type2.tag === undefined ? '' : `.${type2.tag}`}`);\n return `${head}(${formatType(type2.item, ctx, depth)})`;\n }\n case 'major': {\n if (type2.raw !== undefined) return type2.raw;\n return typeof type2.ai === 'object'\n ? `#${type2.major}.<${formatType(type2.ai, ctx, depth)}>`\n : `#${type2.major}${type2.ai === undefined ? '' : `.${type2.ai}`}`;\n }\n case 'any':\n return '#';\n }\n}\n","/**\n * Structural equality and value-access helpers over CBOR AST nodes,\n * used by the CDDL validator for literal matching, map-key comparison,\n * enumerations, and the .eq/.ne control operators.\n *\n * Equality is CDDL value equality, not byte equality: encoding widths and\n * definite/indefinite length are ignored (an indefinite-length \"a\", \"b\"\n * equals the definite \"ab\"), but CBOR type classes stay distinct — an\n * integer never equals a float, and a bignum (tag 2/3) never equals a\n * plain integer.\n */\n\nimport { CborItem } from '../ast/CborItem';\nimport { CborUint } from '../ast/CborUint';\nimport { CborNint } from '../ast/CborNint';\nimport { CborFloat } from '../ast/CborFloat';\nimport { CborSimple } from '../ast/CborSimple';\nimport { CborTextString } from '../ast/CborTextString';\nimport { CborIndefiniteTextString } from '../ast/CborIndefiniteTextString';\nimport { CborByteString } from '../ast/CborByteString';\nimport { CborIndefiniteByteString } from '../ast/CborIndefiniteByteString';\nimport { CborEmbeddedCBOR } from '../ast/CborEmbeddedCBOR';\nimport { CborArray } from '../ast/CborArray';\nimport { CborMap } from '../ast/CborMap';\nimport { CborTag } from '../ast/CborTag';\nimport { CborBigUint, CborBigNint } from '../ast/CborBignum';\n\n/**\n * The integer value of a node, including bignums (tags 2/3): CDDL *values*\n * are abstract numbers, so literals, ranges, and comparison operators must\n * see 2^64 the same way whether it arrived as a basic int or as a bignum.\n * (Type matching stays structural: a bignum is a tagged item, not #0/#1.)\n */\nexport function intValueOf(item: CborItem): bigint | undefined {\n if (item instanceof CborUint || item instanceof CborNint) return item.value;\n if (item instanceof CborBigUint || item instanceof CborBigNint)\n return item.bigValue;\n return undefined;\n}\n\n/** The text value of a (possibly indefinite-length) text string node. */\nexport function textValue(item: CborItem): string | undefined {\n if (item instanceof CborTextString) return item.value;\n if (item instanceof CborIndefiniteTextString)\n return item.chunks.map((c) => c.value).join('');\n return undefined;\n}\n\n/**\n * The byte content of a byte-string-like node: a (possibly\n * indefinite-length) byte string, or an `<<…>>` embedded-CBOR literal\n * (whose value is the encoding of its items).\n */\nexport function byteValue(item: CborItem): Uint8Array | undefined {\n if (item instanceof CborByteString) return item.value;\n if (item instanceof CborIndefiniteByteString) {\n const parts = item.chunks.map((c) => c.value);\n const total = parts.reduce((n, p) => n + p.length, 0);\n const out = new Uint8Array(total);\n let off = 0;\n for (const p of parts) {\n out.set(p, off);\n off += p.length;\n }\n return out;\n }\n if (item instanceof CborEmbeddedCBOR) {\n const parts = item.items.map((i) => i.toCBOR());\n const total = parts.reduce((n, p) => n + p.length, 0);\n const out = new Uint8Array(total);\n let off = 0;\n for (const p of parts) {\n out.set(p, off);\n off += p.length;\n }\n return out;\n }\n return undefined;\n}\n\nexport function bytesEqual(a: Uint8Array, b: Uint8Array): boolean {\n if (a.length !== b.length) return false;\n for (let i = 0; i < a.length; i++) if (a[i] !== b[i]) return false;\n return true;\n}\n\n/** CDDL value equality of two CBOR AST nodes (see module doc). */\nexport function equalItems(a: CborItem, b: CborItem): boolean {\n if (a === b) return true;\n\n if (a instanceof CborUint)\n return b instanceof CborUint && a.value === b.value;\n if (a instanceof CborNint)\n return b instanceof CborNint && a.value === b.value;\n if (a instanceof CborFloat)\n return (\n b instanceof CborFloat &&\n (a.value === b.value || (Number.isNaN(a.value) && Number.isNaN(b.value)))\n );\n if (a instanceof CborSimple)\n return b instanceof CborSimple && a.value === b.value;\n\n const aText = textValue(a);\n if (aText !== undefined) {\n const bText = textValue(b);\n return bText !== undefined && aText === bText;\n }\n const aBytes = byteValue(a);\n if (aBytes !== undefined) {\n const bBytes = byteValue(b);\n return bBytes !== undefined && bytesEqual(aBytes, bBytes);\n }\n\n if (a instanceof CborArray)\n return (\n b instanceof CborArray &&\n a.items.length === b.items.length &&\n a.items.every((item, i) => equalItems(item, b.items[i]!))\n );\n\n if (a instanceof CborMap) {\n if (!(b instanceof CborMap) || a.entries.length !== b.entries.length)\n return false;\n // Order-insensitive with one-to-one consumption.\n const used = new Array<boolean>(b.entries.length).fill(false);\n for (const [ak, av] of a.entries) {\n let found = false;\n for (let i = 0; i < b.entries.length; i++) {\n if (used[i]) continue;\n const [bk, bv] = b.entries[i]!;\n if (equalItems(ak, bk) && equalItems(av, bv)) {\n used[i] = true;\n found = true;\n break;\n }\n }\n if (!found) return false;\n }\n return true;\n }\n\n // Tags last: bignums, embedded app extensions, etc. are CborTag subclasses.\n if (a instanceof CborTag)\n return (\n b instanceof CborTag &&\n a.tag === b.tag &&\n equalItems(a.content, b.content)\n );\n\n return false;\n}\n","/**\n * Control operator implementations (RFC 8610 §3.8 plus RFC 9165 .plus /\n * .cat / .feature), table-driven and injected with the validator's matching\n * primitives to avoid an import cycle.\n *\n * Operators that are not in the table (.det, .abnf, .abnfb, the RFC 9741\n * text-conversion set, and anything unknown) are reported as a warning by\n * the validator, which then matches the target without the constraint.\n */\n\nimport type { CborItem } from '../ast/CborItem';\nimport { CborUint } from '../ast/CborUint';\nimport { CborFloat } from '../ast/CborFloat';\nimport { decodeCBOR } from '../cbor/decoder';\nimport { textValue, byteValue, intValueOf } from './equal';\nimport type { CddlNodeBase, CddlType2, CddlValue } from './ast';\n\ntype Path = readonly (string | number)[];\n\n/** Matching primitives provided by the validator (closed over env/ctx). */\nexport interface ControlDeps {\n matchType2(item: CborItem, t2: CddlType2, path: Path): boolean;\n /** Like matchType2, but suppresses instance offsets in recorded errors —\n * the item was decoded out of an embedded byte string, so its offsets\n * are relative to the embedded bytes, not the outer document. */\n matchEmbedded(item: CborItem, t2: CddlType2, path: Path): boolean;\n resolveValue(t2: CddlType2): CddlValue | undefined;\n /** Whether some integer ≥ min matches the type; undefined = unanalyzable. */\n existsIntGE(t2: CddlType2, min: bigint): boolean | undefined;\n matchesLiteral(item: CborItem, v: CddlValue): boolean;\n fail(\n path: Path,\n item: CborItem | undefined,\n node: CddlNodeBase | undefined,\n message: string\n ): false;\n warnOnce(message: string, node?: CddlNodeBase): void;\n features: ReadonlySet<string>;\n uint(n: number | bigint): CborItem;\n}\n\nexport type ControlHandler = (\n deps: ControlDeps,\n item: CborItem,\n target: CddlType2,\n controller: CddlType2,\n path: Path,\n node: CddlNodeBase\n) => boolean;\n\nconst textEncoder = new TextEncoder();\nconst utf8Strict = new TextDecoder('utf-8', { fatal: true });\n\n/** Synthesize a literal value for computed operators (.plus, .cat). */\nconst synthValue = (\n v:\n | { type: 'int'; value: number | bigint }\n | { type: 'float'; value: number }\n | { type: 'text'; value: string }\n | { type: 'bytes'; value: Uint8Array; qualifier: '' | 'h' | 'b64' }\n): CddlValue =>\n ({ kind: 'value', raw: '', start: 0, end: 0, ...v }) as CddlValue;\n\nconst numericOf = (item: CborItem): bigint | number | undefined => {\n // Includes bignums (tags 2/3): CDDL values are abstract numbers.\n const int = intValueOf(item);\n if (int !== undefined) return int;\n if (item instanceof CborFloat) return item.value;\n return undefined;\n};\n\nconst valueNumeric = (v: CddlValue): bigint | number | undefined =>\n v.type === 'int' || v.type === 'float' ? v.value : undefined;\n\n/** Compare possibly-mixed bigint/number numerics: -1, 0, 1 (NaN → NaN). */\nconst cmp = (a: bigint | number, b: bigint | number): number => {\n if (typeof a === 'bigint' && typeof b === 'bigint')\n return a < b ? -1 : a > b ? 1 : 0;\n const an = Number(a);\n const bn = Number(b);\n return an < bn ? -1 : an > bn ? 1 : an === bn ? 0 : NaN;\n};\n\n// ─── RFC 8610 §3.8 ────────────────────────────────────────────────────────────\n\nconst size: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const checkSize = (n: number | bigint): boolean =>\n deps.matchType2(deps.uint(n), controller, path)\n ? true\n : deps.fail(\n path,\n item,\n node,\n `size ${n} does not match the .size constraint`\n );\n const text = textValue(item);\n if (text !== undefined) return checkSize(textEncoder.encode(text).length);\n const bytes = byteValue(item);\n if (bytes !== undefined) return checkSize(bytes.length);\n if (item instanceof CborUint) {\n // uint .size N means 0 ≤ value < 256^N (no upper limit on N): the value\n // fits iff the controller's integer set intersects [minBytes, ∞).\n let minBytes = 0;\n for (let v = item.value; v > 0n; v >>= 8n) minBytes++;\n const exists = deps.existsIntGE(controller, BigInt(minBytes));\n if (exists !== undefined)\n return exists\n ? true\n : deps.fail(\n path,\n item,\n node,\n `${item.value} does not fit the .size constraint`\n );\n // The controller could not be analyzed structurally (e.g. it uses a\n // control operator); fall back to a bounded search and say so.\n deps.warnOnce(\n '.size controller could not be analyzed; searching a bounded window of byte counts',\n node\n );\n for (let n = minBytes; n <= minBytes + 64; n++)\n if (deps.matchType2(deps.uint(n), controller, path)) return true;\n return deps.fail(\n path,\n item,\n node,\n `${item.value} does not fit the .size constraint`\n );\n }\n return deps.fail(\n path,\n item,\n node,\n '.size applies to strings and unsigned integers'\n );\n};\n\nconst bits: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const positions: number[] = [];\n const bytes = byteValue(item);\n if (bytes !== undefined) {\n // Bit n of the string means (str[n >> 3] & (1 << (n & 7))) != 0 (§3.8.2).\n for (let i = 0; i < bytes.length; i++)\n for (let j = 0; j < 8; j++)\n if (bytes[i]! & (1 << j)) positions.push(i * 8 + j);\n } else if (item instanceof CborUint) {\n let v = item.value;\n for (let n = 0; v > 0n; n++, v >>= 1n) if (v & 1n) positions.push(n);\n } else {\n return deps.fail(\n path,\n item,\n node,\n '.bits applies to byte strings and unsigned integers'\n );\n }\n for (const n of positions)\n if (!deps.matchType2(deps.uint(n), controller, path))\n return deps.fail(\n path,\n item,\n node,\n `bit ${n} is set but not allowed by .bits`\n );\n return true;\n};\n\nconst regexpCache = new Map<string, RegExp | null>();\n\nconst regexp: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const text = textValue(item);\n if (text === undefined)\n return deps.fail(path, item, node, '.regexp applies to text strings');\n const c = deps.resolveValue(controller);\n if (!c || c.type !== 'text') {\n deps.warnOnce(\n '.regexp controller does not resolve to a text string; not checked',\n node\n );\n return true;\n }\n // Approximation: the spec prescribes XSD regular expressions; we compile\n // the pattern as an anchored JavaScript RegExp with the 'u' flag, which\n // covers common patterns but differs in some character-class details.\n let re = regexpCache.get(c.value);\n if (re === undefined) {\n try {\n re = new RegExp(`^(?:${c.value})$`, 'u');\n } catch {\n re = null;\n }\n regexpCache.set(c.value, re);\n }\n if (re === null) {\n deps.warnOnce(\n `.regexp pattern is not a valid regular expression here: ${c.value}`,\n node\n );\n return true;\n }\n return re.test(text)\n ? true\n : deps.fail(\n path,\n item,\n node,\n `text does not match .regexp ${JSON.stringify(c.value)}`\n );\n};\n\nconst makeCborControl =\n (seq: boolean): ControlHandler =>\n (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const bytes = byteValue(item);\n if (bytes === undefined)\n return deps.fail(\n path,\n item,\n node,\n `.cbor${seq ? 'seq' : ''} applies to byte strings`\n );\n let decoded: CborItem;\n try {\n if (seq) {\n // §3.8.4: wrap the sequence between 0x9f/0xff and decode as an\n // indefinite-length array.\n const wrapped = new Uint8Array(bytes.length + 2);\n wrapped[0] = 0x9f;\n wrapped.set(bytes, 1);\n wrapped[wrapped.length - 1] = 0xff;\n decoded = decodeCBOR(wrapped);\n } else {\n decoded = decodeCBOR(bytes);\n }\n } catch (e) {\n return deps.fail(\n path,\n item,\n node,\n `byte string does not contain valid CBOR: ${e instanceof Error ? e.message : String(e)}`\n );\n }\n return deps.matchEmbedded(decoded, controller, path)\n ? true\n : deps.fail(\n path,\n item,\n node,\n `embedded CBOR does not match the .cbor${seq ? 'seq' : ''} type`\n );\n };\n\nconst within: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n return deps.matchType2(item, controller, path)\n ? true\n : deps.fail(\n path,\n item,\n node,\n 'value does not match the .within/.and constraint'\n );\n};\n\nconst makeCompare =\n (op: 'lt' | 'le' | 'gt' | 'ge'): ControlHandler =>\n (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const c = deps.resolveValue(controller);\n const bound = c && valueNumeric(c);\n if (bound === undefined) {\n deps.warnOnce(\n `.${op} controller does not resolve to a number; not checked`,\n node\n );\n return true;\n }\n const v = numericOf(item);\n if (v === undefined)\n return deps.fail(path, item, node, `.${op} applies to numbers`);\n const d = cmp(v, bound);\n const ok =\n op === 'lt' ? d < 0 : op === 'le' ? d <= 0 : op === 'gt' ? d > 0 : d >= 0;\n return ok\n ? true\n : deps.fail(path, item, node, `${v} does not satisfy .${op} ${bound}`);\n };\n\nconst eq: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const c = deps.resolveValue(controller);\n if (!c) {\n deps.warnOnce(\n '.eq controller does not resolve to a literal value; not checked',\n node\n );\n return true;\n }\n return deps.matchesLiteral(item, c)\n ? true\n : deps.fail(\n path,\n item,\n node,\n `value does not equal ${c.raw || '.eq controller'}`\n );\n};\n\nconst ne: ControlHandler = (deps, item, target, controller, path, node) => {\n if (!deps.matchType2(item, target, path)) return false;\n const c = deps.resolveValue(controller);\n if (!c) {\n deps.warnOnce(\n '.ne controller does not resolve to a literal value; not checked',\n node\n );\n return true;\n }\n return deps.matchesLiteral(item, c)\n ? deps.fail(\n path,\n item,\n node,\n `value must not equal ${c.raw || '.ne controller'}`\n )\n : true;\n};\n\nconst dflt: ControlHandler = (deps, item, target, controller, path, node) => {\n // .default is a variant of .ne: \"the implied .ne control is there to\n // prevent this value from being sent over the wire\" (RFC 8610 §3.8.6),\n // so the default value itself does not validate.\n if (!deps.matchType2(item, target, path)) return false;\n const c = deps.resolveValue(controller);\n if (!c) {\n deps.warnOnce(\n '.default controller does not resolve to a literal value; the implied .ne is not checked',\n node\n );\n return true;\n }\n return deps.matchesLiteral(item, c)\n ? deps.fail(\n path,\n item,\n node,\n `value equals the default ${c.raw || 'value'} (implied .ne, RFC 8610 §3.8.6)`\n )\n : true;\n};\n\n// ─── RFC 9165 ─────────────────────────────────────────────────────────────────\n\nconst plus: ControlHandler = (deps, item, target, controller, path, node) => {\n const t = deps.resolveValue(target);\n const c = deps.resolveValue(controller);\n const tv = t && valueNumeric(t);\n const cv = c && valueNumeric(c);\n if (t === undefined || tv === undefined || cv === undefined) {\n deps.warnOnce(\n '.plus operands do not resolve to numbers; not checked',\n node\n );\n return deps.fail(path, item, node, '.plus could not be computed');\n }\n // The sum is converted to the type of the target; float→int rounds\n // towards negative infinity (RFC 9165 §2.1).\n if (t!.type === 'float') {\n const sum = Number(tv) + Number(cv);\n return deps.matchesLiteral(item, synthValue({ type: 'float', value: sum }))\n ? true\n : deps.fail(path, item, node, `expected ${sum} (.plus)`);\n }\n // Integer target: compute in bigint so values beyond 2^53 stay exact.\n // An integer CddlValue is only a `number` when within the safe range, so\n // BigInt(tv) is lossless; for a float controller, floor(int + x) equals\n // int + floor(x), keeping the big integer part untouched.\n if (typeof cv === 'number' && !Number.isFinite(cv))\n return deps.fail(path, item, node, '.plus controller is not finite');\n const sum =\n (typeof tv === 'bigint' ? tv : BigInt(tv)) +\n (typeof cv === 'bigint' ? cv : BigInt(Math.floor(cv)));\n return deps.matchesLiteral(item, synthValue({ type: 'int', value: sum }))\n ? true\n : deps.fail(path, item, node, `expected ${sum} (.plus)`);\n};\n\nconst cat: ControlHandler = (deps, item, target, controller, path, node) => {\n const t = deps.resolveValue(target);\n const c = deps.resolveValue(controller);\n const toBytes = (v: CddlValue): Uint8Array | undefined =>\n v.type === 'text'\n ? textEncoder.encode(v.value)\n : v.type === 'bytes'\n ? v.value\n : undefined;\n const tb = t && toBytes(t);\n const cb = c && toBytes(c);\n if (!t || tb === undefined || cb === undefined) {\n deps.warnOnce('.cat operands do not resolve to strings; not checked', node);\n return deps.fail(path, item, node, '.cat could not be computed');\n }\n const joined = new Uint8Array(tb.length + cb.length);\n joined.set(tb, 0);\n joined.set(cb, tb.length);\n // The result has the type of the target (RFC 9165 §2.2).\n if (t.type === 'text') {\n let text: string;\n try {\n text = utf8Strict.decode(joined);\n } catch {\n return deps.fail(path, item, node, '.cat result is not valid UTF-8');\n }\n return deps.matchesLiteral(item, synthValue({ type: 'text', value: text }))\n ? true\n : deps.fail(path, item, node, `expected ${JSON.stringify(text)} (.cat)`);\n }\n return deps.matchesLiteral(\n item,\n synthValue({ type: 'bytes', value: joined, qualifier: 'h' })\n )\n ? true\n : deps.fail(path, item, node, 'byte string does not equal the .cat result');\n};\n\n/** Peel `( … )` layers off a type2 (single plain alternative only). */\nconst stripParens = (t2: CddlType2): CddlType2 => {\n while (\n t2.kind === 'paren' &&\n t2.type.alternatives.length === 1 &&\n !t2.type.alternatives[0]!.op\n )\n t2 = t2.type.alternatives[0]!.target;\n return t2;\n};\n\n/**\n * The .feature controller is a feature name, or an array whose first\n * element is the feature name and whose rest is detail (RFC 9165 §5) —\n * either form may be parenthesized, e.g. `.feature ([\"x\", \"detail\"])`.\n */\nexport const featureName = (\n deps: ControlDeps,\n controller: CddlType2\n): string | undefined => {\n let t2 = stripParens(controller);\n if (t2.kind === 'array') {\n const first = t2.group.choices[0]?.[0];\n if (\n !first ||\n first.kind !== 'entry' ||\n first.value.alternatives.length !== 1 ||\n first.value.alternatives[0]!.op\n )\n return undefined;\n t2 = first.value.alternatives[0]!.target;\n }\n const c = deps.resolveValue(t2);\n return c?.type === 'text' ? c.value : undefined;\n};\n\nconst feature: ControlHandler = (\n deps,\n item,\n target,\n controller,\n path,\n node\n) => {\n const name = featureName(deps, controller);\n if (name === undefined) {\n deps.warnOnce(\n '.feature controller does not resolve to a feature name',\n node\n );\n return deps.fail(path, item, node, 'unresolvable .feature');\n }\n if (!deps.features.has(name)) {\n deps.warnOnce(\n `feature \"${name}\" is not enabled (pass it in options.features to accept it)`,\n node\n );\n return deps.fail(path, item, node, `feature \"${name}\" is not enabled`);\n }\n return deps.matchType2(item, target, path);\n};\n\n// ─── Table ────────────────────────────────────────────────────────────────────\n\nconst CONTROLS: Record<string, ControlHandler> = {\n size,\n bits,\n regexp,\n cbor: makeCborControl(false),\n cborseq: makeCborControl(true),\n within,\n and: within,\n lt: makeCompare('lt'),\n le: makeCompare('le'),\n gt: makeCompare('gt'),\n ge: makeCompare('ge'),\n eq,\n ne,\n default: dflt,\n plus,\n cat,\n feature,\n};\n\nexport function getControl(name: string): ControlHandler | undefined {\n return Object.prototype.hasOwnProperty.call(CONTROLS, name)\n ? CONTROLS[name]\n : undefined;\n}\n","/**\n * CDDL validation engine: matches a CBOR AST (CborItem) against a compiled\n * CDDL schema (CddlSchema).\n *\n * Design notes:\n * - Arrays are matched by backtracking over the group's occurrence\n * indicators (regex-style over the item sequence), enumerating the\n * possible end positions of each sub-group.\n * - Maps are matched by consuming entries: group entries are processed in\n * definition order and greedily consume matching map entries; member keys\n * with cut semantics (`:` and `^ =>`, RFC 8610 §3.5.4) commit to an entry\n * once its key matches, failing the whole map when the value mismatches.\n * - Failures discarded by backtracking are noise; only the failure that\n * reached furthest into the instance source is reported.\n * - `maxSteps` / `maxDepth` bound pathological backtracking and unbounded\n * recursion; exceeding them aborts validation with an explanatory error.\n * - A CDN elision (`...`, CborEllipsis) matches any single item or map\n * entry; container lengths and required counts still apply.\n */\n\nimport type { CddlSchema } from './schema';\nimport { getPreludeRules } from './prelude';\nimport { CborItem } from '../ast/CborItem';\nimport { CborUint } from '../ast/CborUint';\nimport { CborNint } from '../ast/CborNint';\nimport { CborFloat } from '../ast/CborFloat';\nimport { CborSimple } from '../ast/CborSimple';\nimport { CborArray } from '../ast/CborArray';\nimport { CborMap } from '../ast/CborMap';\nimport { CborTag } from '../ast/CborTag';\nimport { CborEllipsis } from '../ast/CborEllipsis';\nimport { CborAppSeqResult } from '../ast/CborAppSeqResult';\nimport { autoSelectFloatPrecision } from '../cbor/encode';\nimport { textValue, byteValue, bytesEqual, intValueOf } from './equal';\nimport type {\n CddlValidationError,\n CddlValidationWarning,\n ValidationResult,\n} from './errors';\nimport type {\n CddlGroup,\n CddlGroupEntry,\n CddlMemberKey,\n CddlNodeBase,\n CddlRef,\n CddlRule,\n CddlType,\n CddlType1,\n CddlType2,\n CddlValue,\n} from './ast';\nimport { featureName, getControl, type ControlDeps } from './controls';\n\nexport interface ValidateOptions {\n /** Recursion guard for rule references and nested groups (default 256). */\n maxDepth?: number;\n /** Total backtracking step budget (default 1e6). */\n maxSteps?: number;\n /** Feature names accepted by the `.feature` control operator. */\n features?: string[];\n /**\n * Name of the rule to validate against, in place of the schema's root\n * (the first rule in source order — RFC 8610 §3.1 defines only one root\n * per model). Any non-generic rule usable as a type can be selected,\n * defined in the schema or its prelude — e.g. a variant used only as a\n * component elsewhere.\n *\n * An unknown name fails validation (`errors[0].message` is `'<name>' is\n * not defined`) rather than throwing, matching how an unresolved `$ref`\n * inside the schema is reported. A generic rule (`g<T> = ...`) also fails\n * validation rather than throwing: there is no `genericArgs` site to bind\n * its parameters from here, so it cannot be selected directly. Likewise a\n * group-only rule fails with `group rule '<name>' cannot be used as a\n * type`, exactly as when such a rule is referenced in type position.\n */\n rule?: string;\n}\n\n// ─── Context ──────────────────────────────────────────────────────────────────\n\ntype PathSeg = string | number;\n\n/** Generic parameter bindings; each binding closes over its defining env. */\ntype Env = Map<string, { type1: CddlType1; env: Env }> | undefined;\n\nclass LimitExceeded extends Error {}\n\nclass Ctx {\n steps = 0;\n ruleName: string | undefined;\n /** >0 while matching content decoded out of a .cbor/.cborseq byte string,\n * whose node offsets are relative to the embedded bytes — meaningless in\n * the outer document, so they are suppressed. */\n embeddedDepth = 0;\n /** >0 while matching inside a prelude rule, whose node offsets point into\n * the prelude text; errors are anchored to the referencing user node. */\n preludeDepth = 0;\n preludeRef: CddlNodeBase | undefined;\n readonly warnings: CddlValidationWarning[] = [];\n private readonly warned = new Set<string>();\n best: (CddlValidationError & { depth: number; startKey: number }) | undefined;\n\n constructor(\n readonly schema: CddlSchema,\n readonly maxDepth: number,\n readonly maxSteps: number,\n readonly features: Set<string>\n ) {}\n\n step(): void {\n if (++this.steps > this.maxSteps)\n throw new LimitExceeded(\n `validation aborted: step budget of ${this.maxSteps} exceeded (pathological backtracking?)`\n );\n }\n\n checkDepth(depth: number): void {\n if (depth > this.maxDepth)\n throw new LimitExceeded(\n `validation aborted: recursion depth ${this.maxDepth} exceeded (cyclic rules without progress?)`\n );\n }\n\n warnOnce(message: string, node?: CddlNodeBase): void {\n const key = `${message}@${node?.start ?? -1}`;\n if (this.warned.has(key)) return;\n this.warned.add(key);\n this.warnings.push({\n message,\n ...(node ? { schemaStart: node.start, schemaEnd: node.end } : {}),\n });\n }\n\n /**\n * Record a failure candidate. The failure furthest into the instance\n * source wins (the standard furthest-progress heuristic — sub-failures\n * of ultimately-successful alternatives, e.g. the uint branch of `int`\n * rejecting a negative number, are left behind by later progress);\n * offset ties are broken by the deeper instance path, then recency.\n */\n fail(\n path: readonly PathSeg[],\n item: CborItem | undefined,\n node: CddlNodeBase | undefined,\n message: string\n ): false {\n const suppressed = this.embeddedDepth > 0;\n const startKey = suppressed ? -1 : (item?.start ?? -1);\n if (\n !this.best ||\n startKey > this.best.startKey ||\n (startKey === this.best.startKey && path.length >= this.best.depth)\n ) {\n const schemaNode = this.preludeDepth > 0 ? this.preludeRef : node;\n this.best = {\n depth: path.length,\n startKey,\n message,\n path: path.length === 0 ? '/' : '/' + path.join('/'),\n ...(!suppressed && item?.start !== undefined\n ? { start: item.start, end: item.end }\n : {}),\n ...(this.ruleName !== undefined ? { ruleName: this.ruleName } : {}),\n ...(schemaNode\n ? { schemaStart: schemaNode.start, schemaEnd: schemaNode.end }\n : {}),\n };\n }\n return false;\n }\n}\n\n// ─── Entry point ──────────────────────────────────────────────────────────────\n\nexport function validateItem(\n schema: CddlSchema,\n item: CborItem,\n options?: ValidateOptions\n): ValidationResult {\n const ruleName = options?.rule ?? schema.root?.name;\n if (ruleName === undefined)\n return {\n valid: false,\n errors: [\n {\n message: 'schema has no rules (no root to validate against)',\n path: '/',\n },\n ],\n };\n const ctx = new Ctx(\n schema,\n options?.maxDepth ?? 256,\n options?.maxSteps ?? 1_000_000,\n new Set(options?.features ?? [])\n );\n // A generic rule's parameters are only ever bound from a referencing\n // site's `genericArgs` (see `bindGenericsForDef`); neither the schema\n // root nor `{ rule }` has one to supply, so selecting a generic rule here\n // would either leave its parameter names unresolved (reported as\n // undefined names, misleadingly) or silently ignore them if unused.\n // Reject it explicitly instead.\n const defs = ruleDefs(ctx, ruleName);\n const genericCount = defs?.[0]?.generics?.length ?? 0;\n if (genericCount > 0)\n return {\n valid: false,\n errors: [\n {\n message: `rule '${ruleName}' takes ${genericCount} generic argument${genericCount === 1 ? '' : 's'} and cannot be used as a validation target directly; reference it with concrete arguments from another rule instead`,\n path: '/',\n },\n ],\n };\n let valid: boolean;\n try {\n valid = matchRuleName(item, ruleName, undefined, [], ctx, 0);\n } catch (e) {\n if (!(e instanceof LimitExceeded)) throw e;\n return {\n valid: false,\n errors: [{ message: e.message, path: '/' }],\n ...(ctx.warnings.length ? { warnings: ctx.warnings } : {}),\n };\n }\n if (valid)\n return {\n valid: true,\n errors: [],\n ...(ctx.warnings.length ? { warnings: ctx.warnings } : {}),\n };\n const errors: CddlValidationError[] = ctx.best\n ? [(({ depth: _d, startKey: _s, ...rest }) => rest)(ctx.best)]\n : [\n {\n message: `value does not match rule '${ruleName}'`,\n path: '/',\n ...(item.start !== undefined\n ? { start: item.start, end: item.end }\n : {}),\n },\n ];\n return {\n valid: false,\n errors,\n ...(ctx.warnings.length ? { warnings: ctx.warnings } : {}),\n };\n}\n\n// ─── Rule resolution ──────────────────────────────────────────────────────────\n\nfunction ruleDefs(ctx: Ctx, name: string): readonly CddlRule[] | undefined {\n const defs = ctx.schema.rules.get(name);\n if (defs) return defs;\n const preludeRule = getPreludeRules().get(name);\n return preludeRule ? [preludeRule] : undefined;\n}\n\nfunction isPlainTypeEntry(\n entry: CddlGroupEntry\n): entry is Extract<CddlGroupEntry, { kind: 'entry' }> {\n return entry.kind === 'entry' && !entry.occur && !entry.memberKey;\n}\n\n/** The group choices contributed by one rule definition body. */\nfunction choicesOfBody(entry: CddlGroupEntry): CddlGroupEntry[][] {\n if (entry.kind === 'entry-group' && !entry.occur) return entry.group.choices;\n return [[entry]];\n}\n\n/** Whether a set of rule definitions can only be used as a group. */\nfunction isGroupLike(defs: readonly CddlRule[]): boolean {\n return defs.some((d) => !isPlainTypeEntry(d.body));\n}\n\n/**\n * Bind one definition's own generic parameter names to the reference's\n * arguments. Each `/=` / `//=` extension may name its parameters\n * differently, so binding is per definition, never from `defs[0]` alone.\n */\nfunction bindGenericsForDef(\n def: CddlRule,\n genericArgs: readonly CddlType1[] | undefined,\n callerEnv: Env\n): Env {\n const params = def.generics;\n if (!params || !genericArgs) return undefined;\n const bound = new Map<string, { type1: CddlType1; env: Env }>();\n for (let i = 0; i < params.length && i < genericArgs.length; i++)\n bound.set(params[i]!, { type1: genericArgs[i]!, env: callerEnv });\n return bound;\n}\n\nfunction matchRuleName(\n item: CborItem,\n name: string,\n callerEnv: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number,\n refNode?: CddlNodeBase,\n genericArgs?: readonly CddlType1[]\n): boolean {\n const defs = ruleDefs(ctx, name);\n if (!defs)\n return ctx.fail(\n path,\n item,\n refNode,\n name.startsWith('$')\n ? `socket '${name}' has no definitions, so nothing matches it`\n : `'${name}' is not defined`\n );\n ctx.checkDepth(depth);\n const prevRule = ctx.ruleName;\n ctx.ruleName = name;\n const fromPrelude = !ctx.schema.rules.has(name);\n if (fromPrelude && ++ctx.preludeDepth === 1) ctx.preludeRef = refNode;\n try {\n for (const def of defs) {\n const env = bindGenericsForDef(def, genericArgs, callerEnv);\n if (isPlainTypeEntry(def.body)) {\n if (matchType(item, def.body.value, env, path, ctx, depth + 1))\n return true;\n continue;\n }\n // A group-bodied definition in type position: usable only when every\n // choice reduces to a single plain entry (a choice-of-types group).\n const choices = choicesOfBody(def.body);\n let usable = true;\n for (const choice of choices) {\n if (choice.length === 1 && isPlainTypeEntry(choice[0]!)) continue;\n usable = false;\n break;\n }\n if (!usable) {\n ctx.fail(\n path,\n item,\n def.body,\n `group rule '${name}' cannot be used as a type`\n );\n continue;\n }\n for (const choice of choices) {\n const only = choice[0]! as Extract<CddlGroupEntry, { kind: 'entry' }>;\n if (matchType(item, only.value, env, path, ctx, depth + 1)) return true;\n }\n }\n return false;\n } finally {\n ctx.ruleName = prevRule;\n if (fromPrelude && --ctx.preludeDepth === 0) ctx.preludeRef = undefined;\n }\n}\n\n// ─── Type matching ────────────────────────────────────────────────────────────\n\n/**\n * See through transparent app-string sequence wrappers (`t1<<…>>`,\n * `b1<<…>>`, `ilbs`/`ilts`, `same<<…>>`): the wrapper only preserves the\n * CDN source spelling for re-serialization; the data-model item is its\n * `inner` result, which is what CDDL types describe.\n */\nfunction unwrapAppSeq(item: CborItem): CborItem {\n while (item instanceof CborAppSeqResult) item = item.inner;\n return item;\n}\n\nfunction matchType(\n item: CborItem,\n type: CddlType,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n for (const alt of type.alternatives)\n if (matchType1(item, alt, env, path, ctx, depth)) return true;\n return false;\n}\n\nfunction matchType1(\n item: CborItem,\n t1: CddlType1,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n ctx.step();\n // Unwrapped here (before control handlers see the item) and again in\n // matchType2, which is also entered directly from control plumbing.\n item = unwrapAppSeq(item);\n if (!t1.op || !t1.controller)\n return matchType2(item, t1.target, env, path, ctx, depth);\n if (t1.op.kind === 'range')\n return matchRange(item, t1, env, path, ctx, depth);\n const handler = getControl(t1.op.name);\n const deps = makeControlDeps(env, ctx, depth);\n if (!handler) {\n ctx.warnOnce(\n `control operator .${t1.op.name} is not supported; matching the target only`,\n t1\n );\n return matchType2(item, t1.target, env, path, ctx, depth);\n }\n return handler(deps, item, t1.target, t1.controller, path, t1);\n}\n\nfunction matchType2(\n item: CborItem,\n t2: CddlType2,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n item = unwrapAppSeq(item);\n // A CDN elision stands for content that was deliberately left out.\n if (item instanceof CborEllipsis) return true;\n\n switch (t2.kind) {\n case 'any':\n return true;\n\n case 'value':\n return matchesLiteral(item, t2)\n ? true\n : ctx.fail(path, item, t2, `expected the value ${t2.raw}`);\n\n case 'ref': {\n const binding = env?.get(t2.name);\n if (binding && !t2.genericArgs)\n return matchType1(\n item,\n binding.type1,\n binding.env,\n path,\n ctx,\n depth + 1\n );\n return matchRuleName(\n item,\n t2.name,\n env,\n path,\n ctx,\n depth + 1,\n t2,\n t2.genericArgs\n );\n }\n\n case 'paren':\n return matchType(item, t2.type, env, path, ctx, depth);\n\n case 'map':\n if (!(item instanceof CborMap))\n return ctx.fail(path, item, t2, 'expected a map');\n return matchMapGroup(item, t2.group, env, path, ctx, depth + 1);\n\n case 'array':\n if (!(item instanceof CborArray))\n return ctx.fail(path, item, t2, 'expected an array');\n return matchArrayGroup(item, t2.group, env, path, ctx, depth + 1);\n\n case 'tagged': {\n // #6.n(type) denotes a *tagged data item* (RFC 8610 §3.6): an untagged\n // integer never matches #6.2/#6.3. (Value-level bignum equivalence\n // lives in literals/ranges/comparisons via intValueOf instead.)\n if (!(item instanceof CborTag))\n return ctx.fail(path, item, t2, 'expected a tagged item');\n if (typeof t2.tag === 'bigint') {\n if (item.tag !== t2.tag)\n return ctx.fail(\n path,\n item,\n t2,\n `expected tag ${t2.tag}, got ${item.tag}`\n );\n } else if (t2.tag !== undefined) {\n if (\n !matchType(new CborUint(item.tag), t2.tag, env, path, ctx, depth + 1)\n )\n return ctx.fail(\n path,\n item,\n t2,\n `tag number ${item.tag} does not match the head type`\n );\n }\n return matchType(item.content, t2.item, env, path, ctx, depth + 1);\n }\n\n case 'major':\n return matchMajor(item, t2, env, path, ctx, depth);\n\n case 'unwrap': {\n // Unwrapping a tag rule exposes the tagged content's type\n // (RFC 8610 §3.7, e.g. `my-uri = ~uri` is a tstr).\n const inner = resolveUnwrapTagType(t2.ref, env, ctx, 0);\n if (inner)\n return matchType(item, inner.type, inner.env, path, ctx, depth + 1);\n // Unwrapping an array/map splices a group into the enclosing\n // array/map; group matching resolves that before type matching, so\n // reaching this point means it was used where only a type can appear.\n ctx.warnOnce(\n `~${t2.ref.name} is used outside of an array/map group context`,\n t2\n );\n return ctx.fail(path, item, t2, `~${t2.ref.name} cannot match here`);\n }\n\n case 'enum': {\n const choices =\n t2.group.kind === 'ref'\n ? resolveGroupRef(t2.group, env, ctx)\n : plainChoices(t2.group, env);\n if (!choices)\n return ctx.fail(\n path,\n item,\n t2,\n `'&' target does not resolve to a group`\n );\n ctx.checkDepth(depth);\n if (matchEnum(item, choices, path, ctx, depth + 1)) return true;\n return ctx.fail(path, item, t2, 'no enumeration value matches');\n }\n }\n}\n\n/** Match an item against the set of entry values of an enum group. */\nfunction matchEnum(\n item: CborItem,\n choices: readonly GroupChoice[],\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n for (const { entries, env } of choices) {\n for (const entry of entries) {\n ctx.step();\n if (entry.kind === 'entry-group') {\n if (\n matchEnum(item, plainChoices(entry.group, env), path, ctx, depth + 1)\n )\n return true;\n continue;\n }\n // Nested group reference inside the enum.\n const groupRef = asBareGroupRef(entry, env, ctx);\n if (groupRef) {\n ctx.checkDepth(depth);\n if (matchEnum(item, groupRef, path, ctx, depth + 1)) return true;\n continue;\n }\n if (matchType(item, entry.value, env, path, ctx, depth + 1)) return true;\n }\n }\n return false;\n}\n\n// ─── Literal and numeric matching ─────────────────────────────────────────────\n\nexport function matchesLiteral(item: CborItem, v: CddlValue): boolean {\n switch (v.type) {\n case 'int':\n // Value comparison is numeric, including bignums: the only wire form\n // of an integer beyond ±(2^64) is its tag-2/3 representation.\n return intValueOf(item) === BigInt(v.value);\n case 'float':\n return (\n item instanceof CborFloat &&\n (item.value === v.value ||\n (Number.isNaN(item.value) && Number.isNaN(v.value)))\n );\n case 'text':\n return textValue(item) === v.value;\n case 'bytes': {\n const bytes = byteValue(item);\n return bytes !== undefined && bytesEqual(bytes, v.value);\n }\n }\n}\n\n/**\n * Resolve a type2 to a literal value, following parentheses, generic\n * bindings, and references to single-alternative value rules. Used for\n * range endpoints and computing control operators (.plus, .cat, …).\n */\nfunction resolveValue(\n t2: CddlType2,\n env: Env,\n ctx: Ctx,\n depth = 0\n): CddlValue | undefined {\n if (depth > 32) return undefined;\n if (t2.kind === 'value') return t2;\n if (t2.kind === 'paren') {\n const only =\n t2.type.alternatives.length === 1 ? t2.type.alternatives[0] : undefined;\n if (!only || only.op) return undefined;\n return resolveValue(only.target, env, ctx, depth + 1);\n }\n if (t2.kind !== 'ref') return undefined;\n const binding = env?.get(t2.name);\n if (binding && !t2.genericArgs) {\n if (binding.type1.op) return undefined;\n return resolveValue(binding.type1.target, binding.env, ctx, depth + 1);\n }\n const defs = ruleDefs(ctx, t2.name);\n if (!defs || defs.length !== 1) return undefined;\n const body = defs[0]!.body;\n if (!isPlainTypeEntry(body) || body.value.alternatives.length !== 1)\n return undefined;\n const only = body.value.alternatives[0]!;\n if (only.op) return undefined;\n const newEnv = bindGenericsForDef(defs[0]!, t2.genericArgs, env);\n return resolveValue(only.target, newEnv, ctx, depth + 1);\n}\n\n/**\n * Whether some integer ≥ `min` matches the type — i.e. whether the type's\n * integer set intersects [min, ∞). Used by `uint .size N` (which accepts\n * any byte count N ≥ the value's minimal length, with no upper limit on N).\n *\n * Tri-state: `undefined` means the type could not be analyzed structurally\n * (control operators, non-integer constructs, …) and the caller must fall\n * back to another strategy.\n */\nfunction existsIntGE(\n t2: CddlType2,\n min: bigint,\n env: Env,\n ctx: Ctx,\n depth = 0\n): boolean | undefined {\n return existsIntInRange(t2, min, undefined, env, ctx, depth);\n}\n\n/** Whether an integer in the inclusive interval [min, max] matches t2. */\nfunction existsIntInRange(\n t2: CddlType2,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth = 0\n): boolean | undefined {\n const found = findIntInRange(t2, min, max, env, ctx, depth);\n return found === undefined ? undefined : found !== null;\n}\n\n/**\n * The first integer in [min, max] matching t2. `null` means the analyzed\n * type has no such integer; `undefined` means it cannot be analyzed.\n */\nfunction findIntInRange(\n t2: CddlType2,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth = 0\n): bigint | null | undefined {\n if (max !== undefined && min > max) return null;\n if (depth > 32) return undefined;\n switch (t2.kind) {\n case 'value': {\n if (t2.type === 'int') {\n const value = BigInt(t2.value);\n return value >= min && (max === undefined || value <= max)\n ? value\n : null;\n }\n return null;\n }\n case 'any': {\n const candidate = min > 0n ? min : 0n;\n return max === undefined || candidate <= max ? candidate : null;\n }\n case 'major': {\n if (t2.ai !== undefined) return undefined;\n if (t2.major === 0) {\n const candidate = min > 0n ? min : 0n;\n return candidate <= 0xffff_ffff_ffff_ffffn &&\n (max === undefined || candidate <= max)\n ? candidate\n : null;\n }\n if (t2.major === 1) {\n const candidate =\n min > -0x1_0000_0000_0000_0000n ? min : -0x1_0000_0000_0000_0000n;\n return candidate <= -1n && (max === undefined || candidate <= max)\n ? candidate\n : null;\n }\n return null;\n }\n case 'paren':\n return findIntInRangeType(t2.type, min, max, env, ctx, depth + 1);\n case 'ref': {\n const binding = env?.get(t2.name);\n if (binding && !t2.genericArgs)\n return findIntInRangeType1(\n binding.type1,\n min,\n max,\n binding.env,\n ctx,\n depth + 1\n );\n const defs = ruleDefs(ctx, t2.name);\n if (!defs) return undefined;\n let sawUnknown = false;\n let best: bigint | null = null;\n for (const def of defs) {\n if (!isPlainTypeEntry(def.body)) {\n sawUnknown = true;\n continue;\n }\n const defEnv = bindGenericsForDef(def, t2.genericArgs, env);\n const r = findIntInRangeType(\n def.body.value,\n min,\n max,\n defEnv,\n ctx,\n depth + 1\n );\n if (typeof r === 'bigint' && (best === null || r < best)) best = r;\n if (r === undefined) sawUnknown = true;\n }\n return best ?? (sawUnknown ? undefined : null);\n }\n case 'enum': {\n const choices =\n t2.group.kind === 'ref'\n ? resolveGroupRef(t2.group, env, ctx)\n : plainChoices(t2.group, env);\n if (!choices) return undefined;\n let sawUnknown = false;\n let best: bigint | null = null;\n for (const { entries, env: choiceEnv } of choices) {\n for (const entry of entries) {\n if (entry.kind !== 'entry') {\n sawUnknown = true;\n continue;\n }\n const r = findIntInRangeType(\n entry.value,\n min,\n max,\n choiceEnv,\n ctx,\n depth + 1\n );\n if (typeof r === 'bigint' && (best === null || r < best)) best = r;\n if (r === undefined) sawUnknown = true;\n }\n }\n return best ?? (sawUnknown ? undefined : null);\n }\n default:\n return undefined;\n }\n}\n\nfunction findIntInRangeType(\n type: CddlType,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth: number\n): bigint | null | undefined {\n let sawUnknown = false;\n let best: bigint | null = null;\n for (const alt of type.alternatives) {\n const r = findIntInRangeType1(alt, min, max, env, ctx, depth);\n if (typeof r === 'bigint' && (best === null || r < best)) best = r;\n if (r === undefined) sawUnknown = true;\n }\n return best ?? (sawUnknown ? undefined : null);\n}\n\nfunction findIntInRangeType1(\n t1: CddlType1,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth: number\n): bigint | null | undefined {\n if (!t1.op) return findIntInRange(t1.target, min, max, env, ctx, depth);\n if (t1.op.kind === 'ctl') {\n if (t1.op.name === 'bits')\n return findBitsIntersection(\n t1.target,\n t1.controller!,\n min,\n max,\n env,\n ctx,\n depth + 1\n );\n if (t1.op.name === 'size') {\n const candidate = findIntInRange(\n t1.target,\n min > 0n ? min : 0n,\n max,\n env,\n ctx,\n depth + 1\n );\n if (candidate === undefined || candidate === null) return candidate;\n const fits = existsIntGE(\n t1.controller!,\n BigInt(uintByteLength(candidate)),\n env,\n ctx,\n depth + 1\n );\n return fits === undefined ? undefined : fits ? candidate : null;\n }\n if (t1.op.name === 'feature') {\n const name = featureName(\n makeControlDeps(env, ctx, depth),\n t1.controller!\n );\n if (name === undefined) return undefined;\n if (!ctx.features.has(name)) {\n ctx.warnOnce(\n `feature \"${name}\" is not enabled (pass it in options.features to accept it)`,\n t1\n );\n return null;\n }\n return findIntInRange(t1.target, min, max, env, ctx, depth + 1);\n }\n if (t1.op.name === 'and' || t1.op.name === 'within')\n return findIntIntersection(\n t1.target,\n t1.controller!,\n min,\n max,\n env,\n ctx,\n depth + 1\n );\n if (t1.op.name === 'plus') {\n const left = resolveValue(t1.target, env, ctx);\n const right = resolveValue(t1.controller!, env, ctx);\n if (\n !left ||\n !right ||\n left.type === 'text' ||\n left.type === 'bytes' ||\n right.type === 'text' ||\n right.type === 'bytes'\n )\n return undefined;\n // .plus converts the result to the target's numeric type. A float\n // target therefore cannot produce the integer byte count sought here;\n // an integer target floors a mixed float sum (RFC 9165 §2.1).\n if (left.type === 'float') return null;\n const sum =\n right.type === 'int'\n ? BigInt(left.value) + BigInt(right.value)\n : BigInt(Math.floor(Number(left.value) + right.value));\n return sum >= min && (max === undefined || sum <= max) ? sum : null;\n }\n const bound = resolveValue(t1.controller!, env, ctx);\n if (!bound || bound.type !== 'int') return undefined;\n const value = BigInt(bound.value);\n switch (t1.op.name) {\n case 'eq':\n return findIntInRange(\n t1.target,\n value > min ? value : min,\n max === undefined || value < max ? value : max,\n env,\n ctx,\n depth + 1\n );\n case 'ne':\n case 'default': {\n const below = findIntInRange(\n t1.target,\n min,\n max === undefined || value - 1n < max ? value - 1n : max,\n env,\n ctx,\n depth + 1\n );\n if (typeof below === 'bigint') return below;\n const above = findIntInRange(\n t1.target,\n value + 1n > min ? value + 1n : min,\n max,\n env,\n ctx,\n depth + 1\n );\n if (typeof above === 'bigint') return above;\n return below === undefined || above === undefined ? undefined : null;\n }\n case 'lt':\n case 'le': {\n const upper = value - (t1.op.name === 'lt' ? 1n : 0n);\n return findIntInRange(\n t1.target,\n min,\n max === undefined || upper < max ? upper : max,\n env,\n ctx,\n depth + 1\n );\n }\n case 'gt':\n case 'ge': {\n const lower = value + (t1.op.name === 'gt' ? 1n : 0n);\n return findIntInRange(\n t1.target,\n lower > min ? lower : min,\n max,\n env,\n ctx,\n depth + 1\n );\n }\n default:\n return undefined;\n }\n }\n const lo = resolveValue(t1.target, env, ctx);\n const hi = resolveValue(t1.controller!, env, ctx);\n if (!lo || !hi || lo.type !== 'int' || hi.type !== 'int') return undefined;\n const loV = BigInt(lo.value);\n const hiV = BigInt(hi.value) - (t1.op.inclusive ? 0n : 1n);\n const lower = loV > min ? loV : min;\n const upper = max === undefined || hiV < max ? hiV : max;\n return lower <= upper ? lower : null;\n}\n\n/** First integer in the intersection of two analyzable integer types. */\nfunction findIntIntersection(\n left: CddlType2,\n right: CddlType2,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth: number\n): bigint | null | undefined {\n let cursor = min;\n // Each iteration advances to a boundary returned by one side. The guard\n // only protects malformed/cyclic analyses; ordinary finite unions\n // converge in at most their combined number of alternatives.\n for (let i = 0; i < 256; i++) {\n const a = findIntInRange(left, cursor, max, env, ctx, depth + 1);\n const b = findIntInRange(right, cursor, max, env, ctx, depth + 1);\n if (a === null || b === null) return null;\n if (a === undefined || b === undefined) return undefined;\n if (a === b) return a;\n cursor = a > b ? a : b;\n }\n return undefined;\n}\n\n/** First uint in the target whose set bits are all admitted by controller. */\nfunction findBitsIntersection(\n target: CddlType2,\n controller: CddlType2,\n min: bigint,\n max: bigint | undefined,\n env: Env,\n ctx: Ctx,\n depth: number\n): bigint | null | undefined {\n let allowedMask = 0n;\n for (let bit = 0; bit < 64; bit++) {\n const allowed = findIntInRange(\n controller,\n BigInt(bit),\n BigInt(bit),\n env,\n ctx,\n depth + 1\n );\n if (allowed === undefined) return undefined;\n if (allowed !== null) allowedMask |= 1n << BigInt(bit);\n }\n\n let cursor = min > 0n ? min : 0n;\n const upper =\n max === undefined || max > 0xffff_ffff_ffff_ffffn\n ? 0xffff_ffff_ffff_ffffn\n : max;\n for (let i = 0; i < 256; i++) {\n const fromTarget = findIntInRange(\n target,\n cursor,\n upper,\n env,\n ctx,\n depth + 1\n );\n const fromBits = nextAllowedBitValue(cursor, upper, allowedMask);\n if (fromTarget === undefined) return undefined;\n if (fromTarget === null || fromBits === null) return null;\n if (fromTarget === fromBits) return fromTarget;\n cursor = fromTarget > fromBits ? fromTarget : fromBits;\n }\n return undefined;\n}\n\n/** Smallest value >= min, <= max whose one-bits are a subset of mask. */\nfunction nextAllowedBitValue(\n min: bigint,\n max: bigint,\n mask: bigint\n): bigint | null {\n if (min < 0n) min = 0n;\n if (min > max) return null;\n\n const visit = (\n bit: number,\n greater: boolean,\n value: bigint\n ): bigint | null => {\n if (bit < 0) return value <= max ? value : null;\n const minBit = Number((min >> BigInt(bit)) & 1n);\n for (let chosen = 0; chosen <= 1; chosen++) {\n if (chosen === 1 && (mask & (1n << BigInt(bit))) === 0n) continue;\n if (!greater && chosen < minBit) continue;\n const found = visit(\n bit - 1,\n greater || chosen > minBit,\n chosen === 1 ? value | (1n << BigInt(bit)) : value\n );\n if (found !== null) return found;\n }\n return null;\n };\n return visit(63, false, 0n);\n}\n\nfunction uintByteLength(value: bigint): number {\n let bytes = 0;\n for (let v = value; v > 0n; v >>= 8n) bytes++;\n return bytes;\n}\n\nfunction matchRange(\n item: CborItem,\n t1: CddlType1,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n void depth;\n const op = t1.op as { kind: 'range'; inclusive: boolean };\n const lo = resolveValue(t1.target, env, ctx);\n const hi = resolveValue(t1.controller!, env, ctx);\n if (!lo || !hi) {\n ctx.warnOnce('range endpoints do not resolve to literal values', t1);\n return ctx.fail(path, item, t1, 'unresolvable range');\n }\n if (lo.type === 'int' && hi.type === 'int') {\n // Numeric comparison, including bignums (tags 2/3).\n const v = intValueOf(item);\n if (v === undefined)\n return ctx.fail(\n path,\n item,\n t1,\n `expected an integer in ${rangeText(t1)}`\n );\n const min = BigInt(lo.value);\n const max = BigInt(hi.value);\n if (v >= min && (op.inclusive ? v <= max : v < max)) return true;\n return ctx.fail(path, item, t1, `${v} is outside ${rangeText(t1)}`);\n }\n if (lo.type === 'float' && hi.type === 'float') {\n if (!(item instanceof CborFloat))\n return ctx.fail(path, item, t1, `expected a float in ${rangeText(t1)}`);\n const v = item.value;\n if (v >= lo.value && (op.inclusive ? v <= hi.value : v < hi.value))\n return true;\n return ctx.fail(path, item, t1, `${v} is outside ${rangeText(t1)}`);\n }\n ctx.warnOnce('range endpoints mix integer and float types', t1);\n return ctx.fail(path, item, t1, 'invalid range');\n}\n\nfunction rangeText(t1: CddlType1): string {\n const op = t1.op as { kind: 'range'; inclusive: boolean };\n return `${sourceText(t1.target)}${op.inclusive ? '..' : '...'}${sourceText(t1.controller!)}`;\n}\n\nfunction sourceText(t2: CddlType2): string {\n if (t2.kind === 'value') return t2.raw;\n if (t2.kind === 'ref') return t2.name;\n return '…';\n}\n\n// ─── Major types (#N[.ai]) ────────────────────────────────────────────────────\n\nconst FLOAT_AI: Record<string, bigint> = {\n half: 25n,\n single: 26n,\n double: 27n,\n};\n\nfunction matchMajor(\n item: CborItem,\n t2: Extract<CddlType2, { kind: 'major' }>,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n const matchHead = (n: bigint): boolean => {\n if (t2.ai === undefined) return true;\n if (typeof t2.ai === 'bigint') return t2.ai === n;\n return matchType(new CborUint(n), t2.ai, env, path, ctx, depth + 1);\n };\n const failKind = (what: string): false =>\n ctx.fail(path, item, t2, `expected ${what} (#${t2.major})`);\n\n switch (t2.major) {\n case 0:\n if (!(item instanceof CborUint)) return failKind('an unsigned integer');\n break;\n case 1:\n if (!(item instanceof CborNint)) return failKind('a negative integer');\n break;\n case 2:\n if (byteValue(item) === undefined) return failKind('a byte string');\n break;\n case 3:\n if (textValue(item) === undefined) return failKind('a text string');\n break;\n case 4:\n if (!(item instanceof CborArray)) return failKind('an array');\n break;\n case 5:\n if (!(item instanceof CborMap)) return failKind('a map');\n break;\n case 6: {\n if (!(item instanceof CborTag)) return failKind('a tagged item');\n if (!matchHead(item.tag))\n return ctx.fail(\n path,\n item,\n t2,\n `tag ${item.tag} does not match ${sourceMajor(t2)}`\n );\n return true;\n }\n case 7: {\n if (item instanceof CborSimple) {\n if (matchHead(BigInt(item.value))) return true;\n return ctx.fail(\n path,\n item,\n t2,\n `simple(${item.value}) does not match ${sourceMajor(t2)}`\n );\n }\n if (item instanceof CborFloat) {\n if (t2.ai === undefined) return true;\n // When no width was recorded (e.g. CDN input without an encoding\n // suffix), use the smallest width that represents the value\n // losslessly — its preferred serialization.\n const precision =\n item.precision ?? autoSelectFloatPrecision(item.value);\n if (matchHead(FLOAT_AI[precision]!)) return true;\n return ctx.fail(\n path,\n item,\n t2,\n `float does not match ${sourceMajor(t2)}`\n );\n }\n return failKind('a simple value or float');\n }\n default:\n return ctx.fail(path, item, t2, `#${t2.major} is not a valid major type`);\n }\n // Majors 0–5: an additional-information constraint is about encoding,\n // which Phase 2 does not check.\n if (t2.ai !== undefined && t2.major <= 5)\n ctx.warnOnce(\n `the additional-information constraint ${sourceMajor(t2)} is not checked (encoding-level)`,\n t2\n );\n return true;\n}\n\nfunction sourceMajor(t2: Extract<CddlType2, { kind: 'major' }>): string {\n return t2.raw ?? `#${t2.major}`;\n}\n\n// ─── Group matching: shared expansion ─────────────────────────────────────────\n\ninterface Occ {\n min: number;\n max: number;\n}\n\n/**\n * One group choice with the environment its entries are evaluated in.\n * The env is per choice because `//=` extensions of a generic rule may\n * name their parameters differently per definition.\n */\ninterface GroupChoice {\n entries: readonly CddlGroupEntry[];\n env: Env;\n}\n\nconst plainChoices = (group: CddlGroup, env: Env): GroupChoice[] =>\n group.choices.map((entries) => ({ entries, env }));\n\ntype SeqMatcher =\n | {\n kind: 'type';\n occur: Occ;\n memberKey?: CddlMemberKey;\n type: CddlType;\n env: Env;\n node: CddlNodeBase;\n }\n | {\n kind: 'group';\n occur: Occ;\n choices: readonly GroupChoice[];\n node: CddlNodeBase;\n };\n\nconst ONE: Occ = { min: 1, max: 1 };\n\nfunction occOf(entry: CddlGroupEntry): Occ {\n const o = entry.occur;\n if (!o) return ONE;\n if (o.marker === '?') return { min: 0, max: 1 };\n if (o.marker === '+') return { min: 1, max: Infinity };\n return { min: o.min ?? 0, max: o.max ?? Infinity };\n}\n\n/** Resolve a bare reference to a group-like rule (for splicing). */\nfunction resolveGroupRef(\n ref: CddlRef,\n env: Env,\n ctx: Ctx\n): GroupChoice[] | undefined {\n const defs = ruleDefs(ctx, ref.name);\n if (!defs) return undefined;\n if (!isGroupLike(defs)) return undefined;\n const choices: GroupChoice[] = [];\n for (const def of defs) {\n const defEnv = bindGenericsForDef(def, ref.genericArgs, env);\n for (const entries of choicesOfBody(def.body))\n choices.push({ entries, env: defEnv });\n }\n return choices;\n}\n\n/**\n * When an entry is a bare single reference, return the group it stands for\n * (group rule or unwrap) — the caller splices it into the sequence.\n */\nfunction asBareGroupRef(\n entry: CddlGroupEntry,\n env: Env,\n ctx: Ctx\n): GroupChoice[] | undefined {\n if (entry.kind !== 'entry' || entry.memberKey) return undefined;\n if (entry.value.alternatives.length !== 1) return undefined;\n const t1 = entry.value.alternatives[0]!;\n if (t1.op) return undefined;\n const target = t1.target;\n if (target.kind === 'ref') {\n if (env?.has(target.name) && !target.genericArgs) return undefined;\n const resolved = resolveGroupRef(target, env, ctx);\n if (resolved) return resolved;\n // An unplugged group socket is a choice with zero alternatives: it\n // matches nothing (which is why sockets are used as `* $$name`).\n if (target.name.startsWith('$$') && !ruleDefs(ctx, target.name)) return [];\n return undefined;\n }\n if (target.kind === 'unwrap')\n return resolveUnwrapGroup(target.ref, env, ctx, 0);\n return undefined;\n}\n\n/** ~ref: follow references to a map/array type and return its group. */\nfunction resolveUnwrapGroup(\n ref: CddlRef,\n env: Env,\n ctx: Ctx,\n depth: number\n): GroupChoice[] | undefined {\n if (depth > 32) return undefined;\n const defs = ruleDefs(ctx, ref.name);\n if (!defs || defs.length !== 1) return undefined;\n const body = defs[0]!.body;\n const newEnv = bindGenericsForDef(defs[0]!, ref.genericArgs, env);\n if (!isPlainTypeEntry(body)) {\n // Unwrapping a group rule: the group itself.\n return choicesOfBody(body).map((entries) => ({ entries, env: newEnv }));\n }\n if (body.value.alternatives.length !== 1) return undefined;\n const t1 = body.value.alternatives[0]!;\n if (t1.op) return undefined;\n if (t1.target.kind === 'map' || t1.target.kind === 'array')\n return plainChoices(t1.target.group, newEnv);\n if (t1.target.kind === 'ref')\n return resolveUnwrapGroup(t1.target, newEnv, ctx, depth + 1);\n return undefined;\n}\n\n/**\n * ~ref where the target is a tag rule: unwrapping removes the tag, exposing\n * the content type (RFC 8610 §3.7, e.g. `my-uri = ~uri` is a tstr).\n */\nfunction resolveUnwrapTagType(\n ref: CddlRef,\n env: Env,\n ctx: Ctx,\n depth: number\n): { type: CddlType; env: Env } | undefined {\n if (depth > 32) return undefined;\n const defs = ruleDefs(ctx, ref.name);\n if (!defs || defs.length !== 1) return undefined;\n const body = defs[0]!.body;\n if (!isPlainTypeEntry(body) || body.value.alternatives.length !== 1)\n return undefined;\n const t1 = body.value.alternatives[0]!;\n if (t1.op) return undefined;\n const newEnv = bindGenericsForDef(defs[0]!, ref.genericArgs, env);\n if (t1.target.kind === 'tagged') return { type: t1.target.item, env: newEnv };\n if (t1.target.kind === 'ref')\n return resolveUnwrapTagType(t1.target, newEnv, ctx, depth + 1);\n return undefined;\n}\n\nfunction expandEntry(entry: CddlGroupEntry, env: Env, ctx: Ctx): SeqMatcher {\n const occur = occOf(entry);\n if (entry.kind === 'entry-group')\n return {\n kind: 'group',\n occur,\n choices: plainChoices(entry.group, env),\n node: entry,\n };\n const groupRef = asBareGroupRef(entry, env, ctx);\n if (groupRef)\n return {\n kind: 'group',\n occur,\n choices: groupRef,\n node: entry,\n };\n return {\n kind: 'type',\n occur,\n ...(entry.memberKey ? { memberKey: entry.memberKey } : {}),\n type: entry.value,\n env,\n node: entry,\n };\n}\n\n// ─── Group matching: arrays (sequences) ───────────────────────────────────────\n\nfunction matchArrayGroup(\n arr: CborArray,\n group: CddlGroup,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n ctx.checkDepth(depth);\n const ends = seqEnds(\n arr.items,\n 0,\n plainChoices(group, env),\n path,\n ctx,\n depth\n );\n if (ends.has(arr.items.length)) return true;\n return ctx.fail(\n path,\n arr,\n group,\n `array of ${arr.items.length} item(s) does not match the group`\n );\n}\n\n/** All end positions reachable by matching the group's choices at `idx`. */\nfunction seqEnds(\n items: readonly CborItem[],\n idx: number,\n choices: readonly GroupChoice[],\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): Set<number> {\n const out = new Set<number>();\n for (const choice of choices) {\n const matchers = choice.entries.map((e) => expandEntry(e, choice.env, ctx));\n seqStep(items, idx, matchers, 0, path, ctx, depth, out);\n }\n return out;\n}\n\nfunction seqStep(\n items: readonly CborItem[],\n idx: number,\n ms: readonly SeqMatcher[],\n k: number,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number,\n out: Set<number>\n): void {\n if (k === ms.length) {\n out.add(idx);\n return;\n }\n const m = ms[k]!;\n\n const tryCount = (count: number, at: number): void => {\n ctx.step();\n if (count >= m.occur.min)\n seqStep(items, at, ms, k + 1, path, ctx, depth, out);\n if (count >= m.occur.max || at >= items.length) return;\n for (const end of matchOnceEnds(items, at, m, path, ctx, depth)) {\n // An empty match makes no progress; recursing on it would loop.\n if (end === at) continue;\n tryCount(count + 1, end);\n }\n };\n tryCount(0, idx);\n}\n\n/** End positions from matching a single occurrence of `m` at `at`. */\nfunction matchOnceEnds(\n items: readonly CborItem[],\n at: number,\n m: SeqMatcher,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): number[] {\n if (m.kind === 'type') {\n // Member keys inside arrays are documentation only (RFC 8610 §3.4).\n return matchType(items[at]!, m.type, m.env, [...path, at], ctx, depth)\n ? [at + 1]\n : [];\n }\n ctx.checkDepth(depth);\n const ends = seqEnds(items, at, m.choices, path, ctx, depth + 1);\n // Descending order: prefer greedy consumption first.\n return [...ends].sort((a, b) => b - a);\n}\n\n// ─── Group matching: maps ─────────────────────────────────────────────────────\n\nfunction matchMapGroup(\n map: CborMap,\n group: CddlGroup,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n ctx.checkDepth(depth);\n const consumed = new Array<boolean>(map.entries.length).fill(false);\n for (const choice of plainChoices(group, env)) {\n consumed.fill(false);\n if (\n mapSeq(\n map,\n choice.entries,\n 0,\n consumed,\n choice.env,\n path,\n ctx,\n depth,\n () => mapFullyConsumed(map, consumed, path, ctx, group)\n )\n )\n return true;\n }\n return false;\n}\n\nfunction mapFullyConsumed(\n map: CborMap,\n consumed: boolean[],\n path: readonly PathSeg[],\n ctx: Ctx,\n node: CddlNodeBase\n): boolean {\n for (let i = 0; i < consumed.length; i++) {\n if (consumed[i]) continue;\n const [k, v] = map.entries[i]!;\n // Leftover elided entries are what \"...\" stands for — ignore them.\n if (k instanceof CborEllipsis) continue;\n ctx.fail(\n [...path, keySeg(k, i)],\n v,\n node,\n `entry ${describeItem(k)} is not allowed by the group`\n );\n return false;\n }\n return true;\n}\n\n/**\n * Match the entries of one group choice against the map, in continuation\n * style so that sub-group choices and occurrence counts can backtrack when\n * downstream matchers (or the final completeness check) fail.\n *\n * Entry-to-member assignment itself is greedy in definition order and is\n * not backtracked (a deliberate heuristic — put wildcard members last).\n */\nfunction mapSeq(\n map: CborMap,\n entries: readonly CddlGroupEntry[],\n k: number,\n consumed: boolean[],\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number,\n cont: () => boolean\n): boolean {\n if (k === entries.length) return cont();\n const m = expandEntry(entries[k]!, env, ctx);\n\n if (m.kind === 'type') {\n if (!m.memberKey) {\n // A bare type as a map entry can only be `any` standing for a whole\n // entry — not expressible; report instead of silently ignoring.\n return ctx.fail(\n path,\n map,\n m.node,\n 'group entry without a member key cannot match a map entry'\n );\n }\n let count = 0;\n for (let i = 0; i < map.entries.length && count < m.occur.max; i++) {\n if (consumed[i]) continue;\n const [key, value] = map.entries[i]!;\n if (!keyMatches(m.memberKey, key, m.env, path, ctx, depth)) continue;\n const valuePath = [...path, keySeg(key, i)];\n if (matchType(value, m.type, m.env, valuePath, ctx, depth + 1)) {\n consumed[i] = true;\n count++;\n continue;\n }\n if (m.memberKey.cut) {\n // Cut: the key committed this entry to this member; a value\n // mismatch fails the whole map (§3.5.4).\n return ctx.fail(\n valuePath,\n value,\n m.node,\n `value for ${describeKey(m.memberKey)} does not match`\n );\n }\n }\n if (count < m.occur.min)\n return ctx.fail(\n path,\n map,\n m.node,\n `missing required entry ${describeKey(m.memberKey)}`\n );\n return mapSeq(map, entries, k + 1, consumed, env, path, ctx, depth, cont);\n }\n\n // Sub-group with an occurrence: backtrack over stop-vs-repeat and over\n // the sub-group's choices.\n ctx.checkDepth(depth);\n const consumedCount = (): number => {\n let n = 0;\n for (const c of consumed) if (c) n++;\n return n;\n };\n const tryIter = (iter: number): boolean => {\n ctx.step();\n if (\n iter >= m.occur.min &&\n mapSeq(map, entries, k + 1, consumed, env, path, ctx, depth, cont)\n )\n return true;\n if (iter >= m.occur.max) return false;\n const snapshot = consumed.slice();\n const before = consumedCount();\n for (const sub of m.choices) {\n if (\n mapSeq(\n map,\n sub.entries,\n 0,\n consumed,\n sub.env,\n path,\n ctx,\n depth + 1,\n () => {\n if (consumedCount() === before)\n // An empty iteration makes no progress; repeating it cannot\n // help, so treat the occurrence as satisfied and move on.\n return mapSeq(\n map,\n entries,\n k + 1,\n consumed,\n env,\n path,\n ctx,\n depth,\n cont\n );\n return tryIter(iter + 1);\n }\n )\n )\n return true;\n for (let i = 0; i < consumed.length; i++) consumed[i] = snapshot[i]!;\n }\n return false;\n };\n return tryIter(0);\n}\n\nfunction keyMatches(\n mk: CddlMemberKey,\n key: CborItem,\n env: Env,\n path: readonly PathSeg[],\n ctx: Ctx,\n depth: number\n): boolean {\n key = unwrapAppSeq(key);\n if (key instanceof CborEllipsis) return true;\n switch (mk.kind) {\n case 'bareword':\n return textValue(key) === mk.key;\n case 'value':\n return matchesLiteral(key, mk.key);\n case 'type1':\n return matchType1(key, mk.key, env, path, ctx, depth + 1);\n }\n}\n\nfunction describeKey(mk: CddlMemberKey): string {\n switch (mk.kind) {\n case 'bareword':\n return `'${mk.key}'`;\n case 'value':\n return mk.key.raw;\n case 'type1':\n return sourceText(mk.key.target);\n }\n}\n\nfunction keySeg(key: CborItem, index: number): PathSeg {\n const text = textValue(key);\n if (text !== undefined) return text;\n if (key instanceof CborUint || key instanceof CborNint) {\n const v = key.value;\n if (\n v >= BigInt(Number.MIN_SAFE_INTEGER) &&\n v <= BigInt(Number.MAX_SAFE_INTEGER)\n )\n return Number(v);\n }\n return index;\n}\n\nfunction describeItem(item: CborItem): string {\n const text = textValue(item);\n if (text !== undefined) return JSON.stringify(text);\n if (item instanceof CborUint || item instanceof CborNint)\n return item.value.toString();\n return item.constructor.name.replace(/^Cbor/, '').toLowerCase();\n}\n\n// ─── Control operator plumbing ────────────────────────────────────────────────\n\nfunction makeControlDeps(env: Env, ctx: Ctx, depth: number): ControlDeps {\n return {\n matchType2: (item, t2, path) =>\n matchType2(item, t2, env, path, ctx, depth + 1),\n matchEmbedded: (item, t2, path) => {\n ctx.embeddedDepth++;\n try {\n return matchType2(item, t2, env, path, ctx, depth + 1);\n } finally {\n ctx.embeddedDepth--;\n }\n },\n resolveValue: (t2) => resolveValue(t2, env, ctx),\n existsIntGE: (t2, min) => existsIntGE(t2, min, env, ctx),\n matchesLiteral,\n fail: (path, item, node, message) => ctx.fail(path, item, node, message),\n warnOnce: (message, node) => ctx.warnOnce(message, node),\n features: ctx.features,\n uint: (n) => new CborUint(n),\n };\n}\n","/**\n * CDDL compilation: rule table construction and static checks.\n *\n * `compile()` parses CDDL text and performs the semantic checks that do not\n * require a data item: duplicate rule detection, name resolution against the\n * user rules and the standard prelude, and generic arity checks. Validation\n * of CBOR data against a schema is a later phase.\n */\n\nimport { parseCDDL } from './parser';\nimport { getPreludeRules } from './prelude';\nimport { formatCddl, type CddlFormatOptions } from './writer';\nimport type { CddlComment } from './tokenizer';\nimport { validateItem, type ValidateOptions } from './validator';\nimport { CborItem } from '../ast/CborItem';\nimport { decodeCBOR } from '../cbor/decoder';\nimport { parseCDN } from '../cdn/parser';\nimport {\n CddlSemanticError,\n type CddlWarning,\n type ValidationResult,\n} from './errors';\nimport type {\n CddlGroup,\n CddlGroupEntry,\n CddlRef,\n CddlRule,\n CddlType,\n CddlType1,\n CddlType2,\n} from './ast';\n\nexport interface CompileOptions {\n /**\n * When true (the default), semantic problems (undefined names, duplicate\n * rules, generic arity mismatches) throw a {@link CddlSemanticError}.\n * When false, they are collected into {@link CddlSchema.warnings}.\n */\n strict?: boolean;\n}\n\n/**\n * A compiled CDDL data model.\n *\n * `rules` maps each rule name to its definitions in source order: the base\n * definition plus any `/=` / `//=` choice extensions. User rules shadow\n * prelude names; the prelude itself is available via `getPreludeRules()`.\n */\nexport class CddlSchema {\n /**\n * The CDDL source text this schema was compiled from. AST node offsets\n * (and validation errors' `schemaStart`/`schemaEnd`) index into it, so\n * tooling can render positions without carrying the text separately.\n */\n readonly source: string;\n /** `;` comments collected while parsing, in source order. */\n readonly comments: readonly CddlComment[];\n /** All rules in source order, as parsed (extensions unmerged). */\n readonly ast: readonly CddlRule[];\n /** Rule definitions by name (base definition first, then extensions). */\n readonly rules: ReadonlyMap<string, readonly CddlRule[]>;\n /**\n * The root of the data model: the first rule in the source (RFC 8610 §3.1).\n * Unset only for an empty model compiled with `strict: false`.\n */\n readonly root?: CddlRule;\n /** Semantic problems collected with `strict: false`; unset when clean. */\n readonly warnings?: CddlWarning[];\n\n /** @internal — use `CDDL.compile()`. */\n constructor(\n source: string,\n comments: readonly CddlComment[],\n ast: CddlRule[],\n rules: Map<string, CddlRule[]>,\n root: CddlRule | undefined,\n warnings: CddlWarning[]\n ) {\n this.source = source;\n this.comments = comments;\n this.ast = ast;\n this.rules = rules;\n if (root) this.root = root;\n if (warnings.length > 0) this.warnings = warnings;\n }\n\n /**\n * Serialize the data model back to CDDL text.\n *\n * Compact one-rule-per-line output by default; pass `indent` for a\n * pretty layout (one group entry per line) and `preserveComments` to\n * re-emit `;` comments.\n *\n * @example\n * CDDL.compile(text).format({ indent: 2, preserveComments: true });\n */\n format(options?: CddlFormatOptions): string {\n return formatCddl(this.ast, {\n ...options,\n source: this.source,\n comments: this.comments,\n });\n }\n\n /**\n * Validate a data item against this schema's root rule — the first rule\n * in source order (RFC 8610 §3.1). Pass `{ rule: 'otherName' }` to\n * validate against a different rule instead: any non-generic rule usable\n * as a type, defined in the schema or its prelude (e.g. `'uint'`).\n * Generic rules (`g<T> = ...`) and group-only rules are reported as\n * validation failures, as is an unknown name (see\n * {@link ValidateOptions.rule}).\n *\n * Accepts a CborItem, CBOR bytes (decoded with `decodeCBOR`), or CDN text\n * (parsed with `parseCDN`). Validation failures are reported in the\n * result, not thrown; decode/parse failures of the input throw as usual.\n *\n * @example\n * const schema = CDDL.compile('person = { name: tstr, ? age: uint }');\n * const result = schema.validate('{\"name\": \"kudo\", \"age\": 42}');\n * result.valid; // true\n *\n * @example\n * // Validate against a rule other than the root.\n * const schema = CDDL.compile(`\n * p1 = { name: tstr, ? addr: tstr }\n * p2 = { name: tstr, ? age: uint }\n * `);\n * schema.validate('{\"name\": \"kudo\", \"age\": 42}', { rule: 'p2' }).valid; // true\n */\n validate(\n input: CborItem | Uint8Array | string,\n options?: ValidateOptions\n ): ValidationResult {\n const item =\n input instanceof CborItem\n ? input\n : typeof input === 'string'\n ? parseCDN(input)\n : decodeCBOR(input);\n return validateItem(this, item, options);\n }\n}\n\n/**\n * Parse and compile CDDL text.\n *\n * Throws `CddlSyntaxError` on grammar errors. Semantic problems throw a\n * {@link CddlSemanticError} by default; pass `strict: false` to collect them\n * into `schema.warnings` instead.\n */\nexport function compile(text: string, options?: CompileOptions): CddlSchema {\n const { rules, comments } = parseCDDL(text);\n const warnings: CddlWarning[] = [];\n const prelude = getPreludeRules();\n\n if (rules.length === 0)\n warnings.push({\n code: 'no-rules',\n message:\n 'a CDDL data model needs at least one rule to provide the root of the definition',\n });\n\n // Rule table: base definition plus /= and //= extensions, in source order.\n const table = new Map<string, CddlRule[]>();\n for (const rule of rules) {\n const existing = table.get(rule.name);\n if (!existing) {\n table.set(rule.name, [rule]);\n continue;\n }\n if (rule.assign === '=')\n warnings.push({\n code: 'duplicate-rule',\n message: `rule '${rule.name}' is already defined; use /= or //= to extend it`,\n start: rule.start,\n end: rule.end,\n });\n existing.push(rule);\n }\n\n // Name resolution and generic arity, per rule (generic parameters are in\n // scope only within their own rule definition's body).\n const declaredArity = (name: string): number | undefined => {\n const defs = table.get(name);\n if (defs) return defs[0]!.generics?.length ?? 0;\n const preludeRule = prelude.get(name);\n if (preludeRule) return preludeRule.generics?.length ?? 0;\n return undefined;\n };\n\n for (const rule of rules) {\n const generics = rule.generics;\n walkEntry(rule.body, {\n onRef(ref: CddlRef): void {\n if (generics?.includes(ref.name)) return;\n // Type and group sockets ($name / $$name) may be referenced and\n // extended without ever being defined.\n if (ref.name.startsWith('$')) return;\n const arity = declaredArity(ref.name);\n if (arity === undefined) {\n warnings.push({\n code: 'undefined-name',\n message: `'${ref.name}' is not defined (and is not a prelude name)`,\n start: ref.start,\n end: ref.end,\n });\n return;\n }\n const given = ref.genericArgs?.length ?? 0;\n if (arity !== given)\n warnings.push({\n code: 'generic-arity',\n message: `'${ref.name}' takes ${arity} generic argument${arity === 1 ? '' : 's'} but is used with ${given}`,\n start: ref.start,\n end: ref.end,\n });\n },\n onMajor(major: number, start: number, end: number): void {\n if (major > 7)\n warnings.push({\n code: 'invalid-major',\n message: `#${major} is not a CBOR major type (0–7)`,\n start,\n end,\n });\n },\n });\n }\n\n // The first rule is the root of the data model, and \"there is no way to\n // use a group as a root -- it must be a type\" (RFC 8610 §2.2.4).\n const root = rules[0];\n if (root && !isTypeBody(root.body))\n warnings.push({\n code: 'invalid-root',\n message: `the first rule '${root.name}' is the root of the data model and must define a type, not a group (RFC 8610 §2.2.4)`,\n start: root.start,\n end: root.end,\n });\n\n if ((options?.strict ?? true) && warnings.length > 0)\n throw new CddlSemanticError(warnings);\n\n // An empty model has no root; `no-rules` was already reported above.\n return new CddlSchema(text, comments, rules, table, root, warnings);\n}\n\n/**\n * Whether a rule body is usable as a type: a plain entry (no occurrence, no\n * member key), or a parenthesized group that reduces to one such entry.\n * A trailing comma makes a parenthesized expression a group — `(int,)` is\n * never a parenthesized type.\n */\nfunction isTypeBody(entry: CddlGroupEntry): boolean {\n if (entry.kind === 'entry') return !entry.occur && !entry.memberKey;\n if (entry.occur || entry.group.trailingComma) return false;\n const { choices } = entry.group;\n return (\n choices.length === 1 &&\n choices[0]!.length === 1 &&\n isTypeBody(choices[0]![0]!)\n );\n}\n\n// ─── AST walk ─────────────────────────────────────────────────────────────────\n\ninterface WalkHooks {\n onRef(ref: CddlRef): void;\n onMajor(major: number, start: number, end: number): void;\n}\n\nfunction walkEntry(entry: CddlGroupEntry, hooks: WalkHooks): void {\n if (entry.kind === 'entry-group') {\n walkGroup(entry.group, hooks);\n return;\n }\n if (entry.memberKey?.kind === 'type1') walkType1(entry.memberKey.key, hooks);\n walkType(entry.value, hooks);\n}\n\nfunction walkGroup(group: CddlGroup, hooks: WalkHooks): void {\n for (const choice of group.choices)\n for (const entry of choice) walkEntry(entry, hooks);\n}\n\nfunction walkType(type: CddlType, hooks: WalkHooks): void {\n for (const alt of type.alternatives) walkType1(alt, hooks);\n}\n\nfunction walkType1(type1: CddlType1, hooks: WalkHooks): void {\n walkType2(type1.target, hooks);\n if (type1.controller) walkType2(type1.controller, hooks);\n}\n\nfunction walkType2(type2: CddlType2, hooks: WalkHooks): void {\n switch (type2.kind) {\n case 'value':\n case 'any':\n return;\n case 'ref':\n hooks.onRef(type2);\n for (const arg of type2.genericArgs ?? []) walkType1(arg, hooks);\n return;\n case 'paren':\n walkType(type2.type, hooks);\n return;\n case 'map':\n case 'array':\n walkGroup(type2.group, hooks);\n return;\n case 'unwrap':\n hooks.onRef(type2.ref);\n for (const arg of type2.ref.genericArgs ?? []) walkType1(arg, hooks);\n return;\n case 'enum':\n if (type2.group.kind === 'ref') {\n hooks.onRef(type2.group);\n for (const arg of type2.group.genericArgs ?? []) walkType1(arg, hooks);\n } else walkGroup(type2.group, hooks);\n return;\n case 'tagged':\n if (typeof type2.tag === 'object') walkType(type2.tag, hooks);\n walkType(type2.item, hooks);\n return;\n case 'major':\n hooks.onMajor(type2.major, type2.start, type2.end);\n if (typeof type2.ai === 'object') walkType(type2.ai, hooks);\n return;\n }\n}\n"],"mappings":"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"}