From 11e40ac54d8063f288fa8b42c5cc8d08f1b586ec Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Mon, 7 Aug 2023 22:02:56 +0100 Subject: [PATCH 01/20] Added include support for ohm-cli --- .../cli/src/commands/generateBundles/index.js | 37 ++++++++++++++++++- .../commands/generateBundles/index.test.js | 19 ++++++++++ .../testdata/include/grammar.ohm | 5 +++ .../testdata/include/recursive.ohm | 5 +++ .../testdata/include/superGrammar.ohm | 3 ++ 5 files changed, 68 insertions(+), 1 deletion(-) create mode 100644 packages/cli/src/commands/generateBundles/testdata/include/grammar.ohm create mode 100644 packages/cli/src/commands/generateBundles/testdata/include/recursive.ohm create mode 100644 packages/cli/src/commands/generateBundles/testdata/include/superGrammar.ohm diff --git a/packages/cli/src/commands/generateBundles/index.js b/packages/cli/src/commands/generateBundles/index.js index 536fe691..452888b3 100644 --- a/packages/cli/src/commands/generateBundles/index.js +++ b/packages/cli/src/commands/generateBundles/index.js @@ -6,6 +6,7 @@ import path from 'path'; import {generateTypes} from '../../helpers/generateTypes.js'; const OHM_FILE_EXT = '.ohm'; +const OMH_IMPORT_REGEX = new RegExp(/^(include)\s+'([\w/\\.]+\.ohm)'$/gmi); function assertFileExtensionEquals(filename, ext) { const actual = path.extname(filename); @@ -51,9 +52,15 @@ function generateBundles(patterns, opts) { // Don't process any files that don't have the right file extension. if (path.extname(sourcePath) !== OHM_FILE_EXT) continue; - const grammarSource = fs.readFileSync(sourcePath, 'utf-8'); + let grammarSource = fs.readFileSync(sourcePath, 'utf-8'); + + // Pre-processing + grammarSource = preprocessGrammarImports(sourcePath, grammarSource); + const grammars = ohm.grammars(grammarSource); + generateRecipe(sourceFilename, grammars, writer, isEsm); + if (withTypes) { generateTypesWithWriter(sourceFilename, grammars, writer); } @@ -62,6 +69,34 @@ function generateBundles(patterns, opts) { return plan.plan; } +function preprocessGrammarImports(grammarPath, grammarSource) { + // Check if imports are present + const importMatches = [...grammarSource.matchAll(OMH_IMPORT_REGEX)]; + + // False: return original input + if (!importMatches || importMatches.length === 0) { + return grammarSource; + } + + // True: process imports + for (let i = 0; i < importMatches.length; i++) { + const [originalString, , importPath] = importMatches[i]; + + const absoluteImportPath = path.resolve(path.dirname(grammarPath), importPath); + + // Read the contents of the import file + let importedGrammarSource = fs.readFileSync(absoluteImportPath, 'utf-8'); + + // Recursively preprocess the imported grammar source + importedGrammarSource = preprocessGrammarImports(absoluteImportPath, importedGrammarSource); + + // Replace the import statement in the original source with the imported content + grammarSource = grammarSource.replace(originalString, importedGrammarSource); + } + + return grammarSource; +} + function generateRecipe(grammarPath, grammars, writer, isEsm) { assertFileExtensionEquals(grammarPath, OHM_FILE_EXT); diff --git a/packages/cli/src/commands/generateBundles/index.test.js b/packages/cli/src/commands/generateBundles/index.test.js index ba32a39e..79676740 100644 --- a/packages/cli/src/commands/generateBundles/index.test.js +++ b/packages/cli/src/commands/generateBundles/index.test.js @@ -70,3 +70,22 @@ test('multiple grammars', t => { t.true(ns.G.match('G').succeeded()); t.true(ns.G2.match('G2').succeeded()); }); + +test('include grammar', t => { + const {filesToWrite} = generateBundles(['include/grammar.ohm'], {...baseOpts, withTypes: true}); + + t.deepEqual(Object.keys(filesToWrite), [ + 'include/grammar.ohm-bundle.js', + 'include/grammar.ohm-bundle.d.ts', + ]); +}); + +test('include grammar recursive', t => { + const {filesToWrite} = generateBundles(['include/recursive.ohm'], {...baseOpts, withTypes: true}); + + t.deepEqual(Object.keys(filesToWrite), [ + 'include/recursive.ohm-bundle.js', + 'include/recursive.ohm-bundle.d.ts', + ]); +}); + diff --git a/packages/cli/src/commands/generateBundles/testdata/include/grammar.ohm b/packages/cli/src/commands/generateBundles/testdata/include/grammar.ohm new file mode 100644 index 00000000..1388e300 --- /dev/null +++ b/packages/cli/src/commands/generateBundles/testdata/include/grammar.ohm @@ -0,0 +1,5 @@ +include 'superGrammar.ohm' + +Grammar <: SuperGrammar { + x := "G" +} \ No newline at end of file diff --git a/packages/cli/src/commands/generateBundles/testdata/include/recursive.ohm b/packages/cli/src/commands/generateBundles/testdata/include/recursive.ohm new file mode 100644 index 00000000..fccb8813 --- /dev/null +++ b/packages/cli/src/commands/generateBundles/testdata/include/recursive.ohm @@ -0,0 +1,5 @@ +include 'grammar.ohm' + +GrammarRecursive <: Grammar { + x := "G" +} \ No newline at end of file diff --git a/packages/cli/src/commands/generateBundles/testdata/include/superGrammar.ohm b/packages/cli/src/commands/generateBundles/testdata/include/superGrammar.ohm new file mode 100644 index 00000000..d45968c9 --- /dev/null +++ b/packages/cli/src/commands/generateBundles/testdata/include/superGrammar.ohm @@ -0,0 +1,3 @@ +SuperGrammar { + x = "X" +} \ No newline at end of file From afb04cb95fb6ee8220d55525660016af806fb513 Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Mon, 7 Aug 2023 22:19:08 +0100 Subject: [PATCH 02/20] Fixed Typo --- packages/cli/src/commands/generateBundles/index.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/cli/src/commands/generateBundles/index.js b/packages/cli/src/commands/generateBundles/index.js index 452888b3..1a259088 100644 --- a/packages/cli/src/commands/generateBundles/index.js +++ b/packages/cli/src/commands/generateBundles/index.js @@ -6,7 +6,7 @@ import path from 'path'; import {generateTypes} from '../../helpers/generateTypes.js'; const OHM_FILE_EXT = '.ohm'; -const OMH_IMPORT_REGEX = new RegExp(/^(include)\s+'([\w/\\.]+\.ohm)'$/gmi); +const OHM_IMPORT_REGEX = new RegExp(/^(include)\s+'([\w/\\.]+\.ohm)'$/gmi); function assertFileExtensionEquals(filename, ext) { const actual = path.extname(filename); @@ -71,7 +71,7 @@ function generateBundles(patterns, opts) { function preprocessGrammarImports(grammarPath, grammarSource) { // Check if imports are present - const importMatches = [...grammarSource.matchAll(OMH_IMPORT_REGEX)]; + const importMatches = [...grammarSource.matchAll(OHM_IMPORT_REGEX)]; // False: return original input if (!importMatches || importMatches.length === 0) { From d64f080ee2340915a2899e89c28484bee2c17307 Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Wed, 16 Aug 2023 14:01:14 +0100 Subject: [PATCH 03/20] Enforcing LF line endings on windows --- .gitattributes | 2 ++ .vscode/settings.json | 3 +++ ~/.gitconfig | 2 ++ 3 files changed, 7 insertions(+) create mode 100644 .gitattributes create mode 100644 .vscode/settings.json create mode 100644 ~/.gitconfig diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 00000000..623190de --- /dev/null +++ b/.gitattributes @@ -0,0 +1,2 @@ + text=lf + *.js linguist-vendored eol=lf \ No newline at end of file diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 00000000..37441bee --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,3 @@ +{ + "files.eol": "\n" +} \ No newline at end of file diff --git a/~/.gitconfig b/~/.gitconfig new file mode 100644 index 00000000..db37092e --- /dev/null +++ b/~/.gitconfig @@ -0,0 +1,2 @@ +[core] +autocrlf = false \ No newline at end of file From e3c3212c23f50e403539be7d19c09b85ee949193 Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Wed, 16 Aug 2023 14:02:33 +0100 Subject: [PATCH 04/20] Added support for include statement in the Ohm grammar --- packages/ohm-js/src/ohm-grammar.ohm | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index a5447fbf..27bfa249 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -1,10 +1,13 @@ Ohm { Grammars - = Grammar* - + = (IncludeStatement+)? Grammar* + Grammar - = ident SuperGrammar? "{" Rule* "}" + = ident SuperGrammar? "{" Rule* "}" + + IncludeStatement + = include "'" relativePath "'" SuperGrammar = "<:" ident @@ -61,6 +64,12 @@ Ohm { | terminal -- terminal | "(" Alt ")" -- paren + include + = caseInsensitive<"include"> + + relativePath + = ~"'" (letter | digit | "-" | "\\" | "/" | ".")+ + ruleDescr (a rule description) = "(" ruleDescrText ")" From 920cadfb24f3631a1d045228c0907c300c6b4dda Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Wed, 16 Aug 2023 14:05:49 +0100 Subject: [PATCH 05/20] Revert "Added include support for ohm-cli" This reverts commit 11e40ac54d8063f288fa8b42c5cc8d08f1b586ec. --- .../cli/src/commands/generateBundles/index.js | 37 +------------------ .../commands/generateBundles/index.test.js | 19 ---------- .../testdata/include/grammar.ohm | 5 --- .../testdata/include/recursive.ohm | 5 --- .../testdata/include/superGrammar.ohm | 3 -- 5 files changed, 1 insertion(+), 68 deletions(-) delete mode 100644 packages/cli/src/commands/generateBundles/testdata/include/grammar.ohm delete mode 100644 packages/cli/src/commands/generateBundles/testdata/include/recursive.ohm delete mode 100644 packages/cli/src/commands/generateBundles/testdata/include/superGrammar.ohm diff --git a/packages/cli/src/commands/generateBundles/index.js b/packages/cli/src/commands/generateBundles/index.js index 1a259088..536fe691 100644 --- a/packages/cli/src/commands/generateBundles/index.js +++ b/packages/cli/src/commands/generateBundles/index.js @@ -6,7 +6,6 @@ import path from 'path'; import {generateTypes} from '../../helpers/generateTypes.js'; const OHM_FILE_EXT = '.ohm'; -const OHM_IMPORT_REGEX = new RegExp(/^(include)\s+'([\w/\\.]+\.ohm)'$/gmi); function assertFileExtensionEquals(filename, ext) { const actual = path.extname(filename); @@ -52,15 +51,9 @@ function generateBundles(patterns, opts) { // Don't process any files that don't have the right file extension. if (path.extname(sourcePath) !== OHM_FILE_EXT) continue; - let grammarSource = fs.readFileSync(sourcePath, 'utf-8'); - - // Pre-processing - grammarSource = preprocessGrammarImports(sourcePath, grammarSource); - + const grammarSource = fs.readFileSync(sourcePath, 'utf-8'); const grammars = ohm.grammars(grammarSource); - generateRecipe(sourceFilename, grammars, writer, isEsm); - if (withTypes) { generateTypesWithWriter(sourceFilename, grammars, writer); } @@ -69,34 +62,6 @@ function generateBundles(patterns, opts) { return plan.plan; } -function preprocessGrammarImports(grammarPath, grammarSource) { - // Check if imports are present - const importMatches = [...grammarSource.matchAll(OHM_IMPORT_REGEX)]; - - // False: return original input - if (!importMatches || importMatches.length === 0) { - return grammarSource; - } - - // True: process imports - for (let i = 0; i < importMatches.length; i++) { - const [originalString, , importPath] = importMatches[i]; - - const absoluteImportPath = path.resolve(path.dirname(grammarPath), importPath); - - // Read the contents of the import file - let importedGrammarSource = fs.readFileSync(absoluteImportPath, 'utf-8'); - - // Recursively preprocess the imported grammar source - importedGrammarSource = preprocessGrammarImports(absoluteImportPath, importedGrammarSource); - - // Replace the import statement in the original source with the imported content - grammarSource = grammarSource.replace(originalString, importedGrammarSource); - } - - return grammarSource; -} - function generateRecipe(grammarPath, grammars, writer, isEsm) { assertFileExtensionEquals(grammarPath, OHM_FILE_EXT); diff --git a/packages/cli/src/commands/generateBundles/index.test.js b/packages/cli/src/commands/generateBundles/index.test.js index 79676740..ba32a39e 100644 --- a/packages/cli/src/commands/generateBundles/index.test.js +++ b/packages/cli/src/commands/generateBundles/index.test.js @@ -70,22 +70,3 @@ test('multiple grammars', t => { t.true(ns.G.match('G').succeeded()); t.true(ns.G2.match('G2').succeeded()); }); - -test('include grammar', t => { - const {filesToWrite} = generateBundles(['include/grammar.ohm'], {...baseOpts, withTypes: true}); - - t.deepEqual(Object.keys(filesToWrite), [ - 'include/grammar.ohm-bundle.js', - 'include/grammar.ohm-bundle.d.ts', - ]); -}); - -test('include grammar recursive', t => { - const {filesToWrite} = generateBundles(['include/recursive.ohm'], {...baseOpts, withTypes: true}); - - t.deepEqual(Object.keys(filesToWrite), [ - 'include/recursive.ohm-bundle.js', - 'include/recursive.ohm-bundle.d.ts', - ]); -}); - diff --git a/packages/cli/src/commands/generateBundles/testdata/include/grammar.ohm b/packages/cli/src/commands/generateBundles/testdata/include/grammar.ohm deleted file mode 100644 index 1388e300..00000000 --- a/packages/cli/src/commands/generateBundles/testdata/include/grammar.ohm +++ /dev/null @@ -1,5 +0,0 @@ -include 'superGrammar.ohm' - -Grammar <: SuperGrammar { - x := "G" -} \ No newline at end of file diff --git a/packages/cli/src/commands/generateBundles/testdata/include/recursive.ohm b/packages/cli/src/commands/generateBundles/testdata/include/recursive.ohm deleted file mode 100644 index fccb8813..00000000 --- a/packages/cli/src/commands/generateBundles/testdata/include/recursive.ohm +++ /dev/null @@ -1,5 +0,0 @@ -include 'grammar.ohm' - -GrammarRecursive <: Grammar { - x := "G" -} \ No newline at end of file diff --git a/packages/cli/src/commands/generateBundles/testdata/include/superGrammar.ohm b/packages/cli/src/commands/generateBundles/testdata/include/superGrammar.ohm deleted file mode 100644 index d45968c9..00000000 --- a/packages/cli/src/commands/generateBundles/testdata/include/superGrammar.ohm +++ /dev/null @@ -1,3 +0,0 @@ -SuperGrammar { - x = "X" -} \ No newline at end of file From 004df2af27a9e04a78ac5c1a207e211a432e1f16 Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Wed, 16 Aug 2023 14:06:21 +0100 Subject: [PATCH 06/20] Removed redundant whitespace --- packages/ohm-js/src/ohm-grammar.ohm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 27bfa249..927decc4 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -2,7 +2,7 @@ Ohm { Grammars = (IncludeStatement+)? Grammar* - + Grammar = ident SuperGrammar? "{" Rule* "}" From 50480e1ee925d2fcc7f9a7301ee48ee840286c8a Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Wed, 16 Aug 2023 14:07:10 +0100 Subject: [PATCH 07/20] Reordered rules in grammar --- packages/ohm-js/src/ohm-grammar.ohm | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 927decc4..677a310f 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -3,12 +3,12 @@ Ohm { Grammars = (IncludeStatement+)? Grammar* - Grammar - = ident SuperGrammar? "{" Rule* "}" - IncludeStatement = include "'" relativePath "'" + Grammar + = ident SuperGrammar? "{" Rule* "}" + SuperGrammar = "<:" ident From fb13e78de97081d4410ed5576fb898ec7d187bb7 Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Wed, 16 Aug 2023 14:07:48 +0100 Subject: [PATCH 08/20] Renamed lexical rule --- packages/ohm-js/src/ohm-grammar.ohm | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 677a310f..79eaa8fc 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -4,7 +4,7 @@ Ohm { = (IncludeStatement+)? Grammar* IncludeStatement - = include "'" relativePath "'" + = include "'" relativeFilePath "'" Grammar = ident SuperGrammar? "{" Rule* "}" @@ -67,7 +67,7 @@ Ohm { include = caseInsensitive<"include"> - relativePath + relativeFilePath = ~"'" (letter | digit | "-" | "\\" | "/" | ".")+ ruleDescr (a rule description) From f2b87d929409d44505c6b4493d4a92b8e7e6f9fc Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Wed, 16 Aug 2023 14:08:16 +0100 Subject: [PATCH 09/20] Removed redundant whitespace --- packages/ohm-js/src/ohm-grammar.ohm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 79eaa8fc..09cfcbdf 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -7,7 +7,7 @@ Ohm { = include "'" relativeFilePath "'" Grammar - = ident SuperGrammar? "{" Rule* "}" + = ident SuperGrammar? "{" Rule* "}" SuperGrammar = "<:" ident From 7d04b35cb33670cb774bdae99345f8493c88152d Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Wed, 16 Aug 2023 14:14:39 +0000 Subject: [PATCH 10/20] Added new Rule that encompasses Includes and Grammas into a "Document". --- packages/ohm-js/dist/ohm-grammar.js | 2 +- packages/ohm-js/src/ohm-grammar.ohm | 12 +++++++++--- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/packages/ohm-js/dist/ohm-grammar.js b/packages/ohm-js/dist/ohm-grammar.js index 072cd950..cde32880 100644 --- a/packages/ohm-js/dist/ohm-grammar.js +++ b/packages/ohm-js/dist/ohm-grammar.js @@ -1,2 +1,2 @@ import {makeRecipe} from '../src/main-kernel.js'; -export default makeRecipe(["grammar",{"source":"Ohm {\n\n Grammars\n = Grammar*\n\n Grammar\n = ident SuperGrammar? \"{\" Rule* \"}\"\n\n SuperGrammar\n = \"<:\" ident\n\n Rule\n = ident Formals? ruleDescr? \"=\" RuleBody -- define\n | ident Formals? \":=\" OverrideRuleBody -- override\n | ident Formals? \"+=\" RuleBody -- extend\n\n RuleBody\n = \"|\"? NonemptyListOf\n\n TopLevelTerm\n = Seq caseName -- inline\n | Seq\n\n OverrideRuleBody\n = \"|\"? NonemptyListOf\n\n OverrideTopLevelTerm\n = \"...\" -- superSplice\n | TopLevelTerm\n\n Formals\n = \"<\" ListOf \">\"\n\n Params\n = \"<\" ListOf \">\"\n\n Alt\n = NonemptyListOf\n\n Seq\n = Iter*\n\n Iter\n = Pred \"*\" -- star\n | Pred \"+\" -- plus\n | Pred \"?\" -- opt\n | Pred\n\n Pred\n = \"~\" Lex -- not\n | \"&\" Lex -- lookahead\n | Lex\n\n Lex\n = \"#\" Base -- lex\n | Base\n\n Base\n = ident Params? ~(ruleDescr? \"=\" | \":=\" | \"+=\") -- application\n | oneCharTerminal \"..\" oneCharTerminal -- range\n | terminal -- terminal\n | \"(\" Alt \")\" -- paren\n\n ruleDescr (a rule description)\n = \"(\" ruleDescrText \")\"\n\n ruleDescrText\n = (~\")\" any)*\n\n caseName\n = \"--\" (~\"\\n\" space)* name (~\"\\n\" space)* (\"\\n\" | &\"}\")\n\n name (a name)\n = nameFirst nameRest*\n\n nameFirst\n = \"_\"\n | letter\n\n nameRest\n = \"_\"\n | alnum\n\n ident (an identifier)\n = name\n\n terminal\n = \"\\\"\" terminalChar* \"\\\"\"\n\n oneCharTerminal\n = \"\\\"\" terminalChar \"\\\"\"\n\n terminalChar\n = escapeChar\n | ~\"\\\\\" ~\"\\\"\" ~\"\\n\" \"\\u{0}\"..\"\\u{10FFFF}\"\n\n escapeChar (an escape sequence)\n = \"\\\\\\\\\" -- backslash\n | \"\\\\\\\"\" -- doubleQuote\n | \"\\\\\\'\" -- singleQuote\n | \"\\\\b\" -- backspace\n | \"\\\\n\" -- lineFeed\n | \"\\\\r\" -- carriageReturn\n | \"\\\\t\" -- tab\n | \"\\\\u{\" hexDigit hexDigit? hexDigit?\n hexDigit? hexDigit? hexDigit? \"}\" -- unicodeCodePoint\n | \"\\\\u\" hexDigit hexDigit hexDigit hexDigit -- unicodeEscape\n | \"\\\\x\" hexDigit hexDigit -- hexEscape\n\n space\n += comment\n\n comment\n = \"//\" (~\"\\n\" any)* &(\"\\n\" | end) -- singleLine\n | \"/*\" (~\"*/\" any)* \"*/\" -- multiLine\n\n tokens = token*\n\n token = caseName | comment | ident | operator | punctuation | terminal | any\n\n operator = \"<:\" | \"=\" | \":=\" | \"+=\" | \"*\" | \"+\" | \"?\" | \"~\" | \"&\"\n\n punctuation = \"<\" | \">\" | \",\" | \"--\"\n}"},"Ohm",null,"Grammars",{"Grammars":["define",{"sourceInterval":[9,32]},null,[],["star",{"sourceInterval":[24,32]},["app",{"sourceInterval":[24,31]},"Grammar",[]]]],"Grammar":["define",{"sourceInterval":[36,83]},null,[],["seq",{"sourceInterval":[50,83]},["app",{"sourceInterval":[50,55]},"ident",[]],["opt",{"sourceInterval":[56,69]},["app",{"sourceInterval":[56,68]},"SuperGrammar",[]]],["terminal",{"sourceInterval":[70,73]},"{"],["star",{"sourceInterval":[74,79]},["app",{"sourceInterval":[74,78]},"Rule",[]]],["terminal",{"sourceInterval":[80,83]},"}"]]],"SuperGrammar":["define",{"sourceInterval":[87,116]},null,[],["seq",{"sourceInterval":[106,116]},["terminal",{"sourceInterval":[106,110]},"<:"],["app",{"sourceInterval":[111,116]},"ident",[]]]],"Rule_define":["define",{"sourceInterval":[131,181]},null,[],["seq",{"sourceInterval":[131,170]},["app",{"sourceInterval":[131,136]},"ident",[]],["opt",{"sourceInterval":[137,145]},["app",{"sourceInterval":[137,144]},"Formals",[]]],["opt",{"sourceInterval":[146,156]},["app",{"sourceInterval":[146,155]},"ruleDescr",[]]],["terminal",{"sourceInterval":[157,160]},"="],["app",{"sourceInterval":[162,170]},"RuleBody",[]]]],"Rule_override":["define",{"sourceInterval":[188,248]},null,[],["seq",{"sourceInterval":[188,235]},["app",{"sourceInterval":[188,193]},"ident",[]],["opt",{"sourceInterval":[194,202]},["app",{"sourceInterval":[194,201]},"Formals",[]]],["terminal",{"sourceInterval":[214,218]},":="],["app",{"sourceInterval":[219,235]},"OverrideRuleBody",[]]]],"Rule_extend":["define",{"sourceInterval":[255,305]},null,[],["seq",{"sourceInterval":[255,294]},["app",{"sourceInterval":[255,260]},"ident",[]],["opt",{"sourceInterval":[261,269]},["app",{"sourceInterval":[261,268]},"Formals",[]]],["terminal",{"sourceInterval":[281,285]},"+="],["app",{"sourceInterval":[286,294]},"RuleBody",[]]]],"Rule":["define",{"sourceInterval":[120,305]},null,[],["alt",{"sourceInterval":[131,305]},["app",{"sourceInterval":[131,170]},"Rule_define",[]],["app",{"sourceInterval":[188,235]},"Rule_override",[]],["app",{"sourceInterval":[255,294]},"Rule_extend",[]]]],"RuleBody":["define",{"sourceInterval":[309,362]},null,[],["seq",{"sourceInterval":[324,362]},["opt",{"sourceInterval":[324,328]},["terminal",{"sourceInterval":[324,327]},"|"]],["app",{"sourceInterval":[329,362]},"NonemptyListOf",[["app",{"sourceInterval":[344,356]},"TopLevelTerm",[]],["terminal",{"sourceInterval":[358,361]},"|"]]]]],"TopLevelTerm_inline":["define",{"sourceInterval":[385,408]},null,[],["seq",{"sourceInterval":[385,397]},["app",{"sourceInterval":[385,388]},"Seq",[]],["app",{"sourceInterval":[389,397]},"caseName",[]]]],"TopLevelTerm":["define",{"sourceInterval":[366,418]},null,[],["alt",{"sourceInterval":[385,418]},["app",{"sourceInterval":[385,397]},"TopLevelTerm_inline",[]],["app",{"sourceInterval":[415,418]},"Seq",[]]]],"OverrideRuleBody":["define",{"sourceInterval":[422,491]},null,[],["seq",{"sourceInterval":[445,491]},["opt",{"sourceInterval":[445,449]},["terminal",{"sourceInterval":[445,448]},"|"]],["app",{"sourceInterval":[450,491]},"NonemptyListOf",[["app",{"sourceInterval":[465,485]},"OverrideTopLevelTerm",[]],["terminal",{"sourceInterval":[487,490]},"|"]]]]],"OverrideTopLevelTerm_superSplice":["define",{"sourceInterval":[522,543]},null,[],["terminal",{"sourceInterval":[522,527]},"..."]],"OverrideTopLevelTerm":["define",{"sourceInterval":[495,562]},null,[],["alt",{"sourceInterval":[522,562]},["app",{"sourceInterval":[522,527]},"OverrideTopLevelTerm_superSplice",[]],["app",{"sourceInterval":[550,562]},"TopLevelTerm",[]]]],"Formals":["define",{"sourceInterval":[566,606]},null,[],["seq",{"sourceInterval":[580,606]},["terminal",{"sourceInterval":[580,583]},"<"],["app",{"sourceInterval":[584,602]},"ListOf",[["app",{"sourceInterval":[591,596]},"ident",[]],["terminal",{"sourceInterval":[598,601]},","]]],["terminal",{"sourceInterval":[603,606]},">"]]],"Params":["define",{"sourceInterval":[610,647]},null,[],["seq",{"sourceInterval":[623,647]},["terminal",{"sourceInterval":[623,626]},"<"],["app",{"sourceInterval":[627,643]},"ListOf",[["app",{"sourceInterval":[634,637]},"Seq",[]],["terminal",{"sourceInterval":[639,642]},","]]],["terminal",{"sourceInterval":[644,647]},">"]]],"Alt":["define",{"sourceInterval":[651,685]},null,[],["app",{"sourceInterval":[661,685]},"NonemptyListOf",[["app",{"sourceInterval":[676,679]},"Seq",[]],["terminal",{"sourceInterval":[681,684]},"|"]]]],"Seq":["define",{"sourceInterval":[689,704]},null,[],["star",{"sourceInterval":[699,704]},["app",{"sourceInterval":[699,703]},"Iter",[]]]],"Iter_star":["define",{"sourceInterval":[719,736]},null,[],["seq",{"sourceInterval":[719,727]},["app",{"sourceInterval":[719,723]},"Pred",[]],["terminal",{"sourceInterval":[724,727]},"*"]]],"Iter_plus":["define",{"sourceInterval":[743,760]},null,[],["seq",{"sourceInterval":[743,751]},["app",{"sourceInterval":[743,747]},"Pred",[]],["terminal",{"sourceInterval":[748,751]},"+"]]],"Iter_opt":["define",{"sourceInterval":[767,783]},null,[],["seq",{"sourceInterval":[767,775]},["app",{"sourceInterval":[767,771]},"Pred",[]],["terminal",{"sourceInterval":[772,775]},"?"]]],"Iter":["define",{"sourceInterval":[708,794]},null,[],["alt",{"sourceInterval":[719,794]},["app",{"sourceInterval":[719,727]},"Iter_star",[]],["app",{"sourceInterval":[743,751]},"Iter_plus",[]],["app",{"sourceInterval":[767,775]},"Iter_opt",[]],["app",{"sourceInterval":[790,794]},"Pred",[]]]],"Pred_not":["define",{"sourceInterval":[809,824]},null,[],["seq",{"sourceInterval":[809,816]},["terminal",{"sourceInterval":[809,812]},"~"],["app",{"sourceInterval":[813,816]},"Lex",[]]]],"Pred_lookahead":["define",{"sourceInterval":[831,852]},null,[],["seq",{"sourceInterval":[831,838]},["terminal",{"sourceInterval":[831,834]},"&"],["app",{"sourceInterval":[835,838]},"Lex",[]]]],"Pred":["define",{"sourceInterval":[798,862]},null,[],["alt",{"sourceInterval":[809,862]},["app",{"sourceInterval":[809,816]},"Pred_not",[]],["app",{"sourceInterval":[831,838]},"Pred_lookahead",[]],["app",{"sourceInterval":[859,862]},"Lex",[]]]],"Lex_lex":["define",{"sourceInterval":[876,892]},null,[],["seq",{"sourceInterval":[876,884]},["terminal",{"sourceInterval":[876,879]},"#"],["app",{"sourceInterval":[880,884]},"Base",[]]]],"Lex":["define",{"sourceInterval":[866,903]},null,[],["alt",{"sourceInterval":[876,903]},["app",{"sourceInterval":[876,884]},"Lex_lex",[]],["app",{"sourceInterval":[899,903]},"Base",[]]]],"Base_application":["define",{"sourceInterval":[918,979]},null,[],["seq",{"sourceInterval":[918,963]},["app",{"sourceInterval":[918,923]},"ident",[]],["opt",{"sourceInterval":[924,931]},["app",{"sourceInterval":[924,930]},"Params",[]]],["not",{"sourceInterval":[932,963]},["alt",{"sourceInterval":[934,962]},["seq",{"sourceInterval":[934,948]},["opt",{"sourceInterval":[934,944]},["app",{"sourceInterval":[934,943]},"ruleDescr",[]]],["terminal",{"sourceInterval":[945,948]},"="]],["terminal",{"sourceInterval":[951,955]},":="],["terminal",{"sourceInterval":[958,962]},"+="]]]]],"Base_range":["define",{"sourceInterval":[986,1041]},null,[],["seq",{"sourceInterval":[986,1022]},["app",{"sourceInterval":[986,1001]},"oneCharTerminal",[]],["terminal",{"sourceInterval":[1002,1006]},".."],["app",{"sourceInterval":[1007,1022]},"oneCharTerminal",[]]]],"Base_terminal":["define",{"sourceInterval":[1048,1106]},null,[],["app",{"sourceInterval":[1048,1056]},"terminal",[]]],"Base_paren":["define",{"sourceInterval":[1113,1168]},null,[],["seq",{"sourceInterval":[1113,1124]},["terminal",{"sourceInterval":[1113,1116]},"("],["app",{"sourceInterval":[1117,1120]},"Alt",[]],["terminal",{"sourceInterval":[1121,1124]},")"]]],"Base":["define",{"sourceInterval":[907,1168]},null,[],["alt",{"sourceInterval":[918,1168]},["app",{"sourceInterval":[918,963]},"Base_application",[]],["app",{"sourceInterval":[986,1022]},"Base_range",[]],["app",{"sourceInterval":[1048,1056]},"Base_terminal",[]],["app",{"sourceInterval":[1113,1124]},"Base_paren",[]]]],"ruleDescr":["define",{"sourceInterval":[1172,1231]},"a rule description",[],["seq",{"sourceInterval":[1210,1231]},["terminal",{"sourceInterval":[1210,1213]},"("],["app",{"sourceInterval":[1214,1227]},"ruleDescrText",[]],["terminal",{"sourceInterval":[1228,1231]},")"]]],"ruleDescrText":["define",{"sourceInterval":[1235,1266]},null,[],["star",{"sourceInterval":[1255,1266]},["seq",{"sourceInterval":[1256,1264]},["not",{"sourceInterval":[1256,1260]},["terminal",{"sourceInterval":[1257,1260]},")"]],["app",{"sourceInterval":[1261,1264]},"any",[]]]]],"caseName":["define",{"sourceInterval":[1270,1338]},null,[],["seq",{"sourceInterval":[1285,1338]},["terminal",{"sourceInterval":[1285,1289]},"--"],["star",{"sourceInterval":[1290,1304]},["seq",{"sourceInterval":[1291,1302]},["not",{"sourceInterval":[1291,1296]},["terminal",{"sourceInterval":[1292,1296]},"\n"]],["app",{"sourceInterval":[1297,1302]},"space",[]]]],["app",{"sourceInterval":[1305,1309]},"name",[]],["star",{"sourceInterval":[1310,1324]},["seq",{"sourceInterval":[1311,1322]},["not",{"sourceInterval":[1311,1316]},["terminal",{"sourceInterval":[1312,1316]},"\n"]],["app",{"sourceInterval":[1317,1322]},"space",[]]]],["alt",{"sourceInterval":[1326,1337]},["terminal",{"sourceInterval":[1326,1330]},"\n"],["lookahead",{"sourceInterval":[1333,1337]},["terminal",{"sourceInterval":[1334,1337]},"}"]]]]],"name":["define",{"sourceInterval":[1342,1382]},"a name",[],["seq",{"sourceInterval":[1363,1382]},["app",{"sourceInterval":[1363,1372]},"nameFirst",[]],["star",{"sourceInterval":[1373,1382]},["app",{"sourceInterval":[1373,1381]},"nameRest",[]]]]],"nameFirst":["define",{"sourceInterval":[1386,1418]},null,[],["alt",{"sourceInterval":[1402,1418]},["terminal",{"sourceInterval":[1402,1405]},"_"],["app",{"sourceInterval":[1412,1418]},"letter",[]]]],"nameRest":["define",{"sourceInterval":[1422,1452]},null,[],["alt",{"sourceInterval":[1437,1452]},["terminal",{"sourceInterval":[1437,1440]},"_"],["app",{"sourceInterval":[1447,1452]},"alnum",[]]]],"ident":["define",{"sourceInterval":[1456,1489]},"an identifier",[],["app",{"sourceInterval":[1485,1489]},"name",[]]],"terminal":["define",{"sourceInterval":[1493,1531]},null,[],["seq",{"sourceInterval":[1508,1531]},["terminal",{"sourceInterval":[1508,1512]},"\""],["star",{"sourceInterval":[1513,1526]},["app",{"sourceInterval":[1513,1525]},"terminalChar",[]]],["terminal",{"sourceInterval":[1527,1531]},"\""]]],"oneCharTerminal":["define",{"sourceInterval":[1535,1579]},null,[],["seq",{"sourceInterval":[1557,1579]},["terminal",{"sourceInterval":[1557,1561]},"\""],["app",{"sourceInterval":[1562,1574]},"terminalChar",[]],["terminal",{"sourceInterval":[1575,1579]},"\""]]],"terminalChar":["define",{"sourceInterval":[1583,1660]},null,[],["alt",{"sourceInterval":[1602,1660]},["app",{"sourceInterval":[1602,1612]},"escapeChar",[]],["seq",{"sourceInterval":[1621,1660]},["not",{"sourceInterval":[1621,1626]},["terminal",{"sourceInterval":[1622,1626]},"\\"]],["not",{"sourceInterval":[1627,1632]},["terminal",{"sourceInterval":[1628,1632]},"\""]],["not",{"sourceInterval":[1633,1638]},["terminal",{"sourceInterval":[1634,1638]},"\n"]],["range",{"sourceInterval":[1639,1660]},"\u0000","􏿿"]]]],"escapeChar_backslash":["define",{"sourceInterval":[1703,1758]},null,[],["terminal",{"sourceInterval":[1703,1709]},"\\\\"]],"escapeChar_doubleQuote":["define",{"sourceInterval":[1765,1822]},null,[],["terminal",{"sourceInterval":[1765,1771]},"\\\""]],"escapeChar_singleQuote":["define",{"sourceInterval":[1829,1886]},null,[],["terminal",{"sourceInterval":[1829,1835]},"\\'"]],"escapeChar_backspace":["define",{"sourceInterval":[1893,1948]},null,[],["terminal",{"sourceInterval":[1893,1898]},"\\b"]],"escapeChar_lineFeed":["define",{"sourceInterval":[1955,2009]},null,[],["terminal",{"sourceInterval":[1955,1960]},"\\n"]],"escapeChar_carriageReturn":["define",{"sourceInterval":[2016,2076]},null,[],["terminal",{"sourceInterval":[2016,2021]},"\\r"]],"escapeChar_tab":["define",{"sourceInterval":[2083,2132]},null,[],["terminal",{"sourceInterval":[2083,2088]},"\\t"]],"escapeChar_unicodeCodePoint":["define",{"sourceInterval":[2139,2243]},null,[],["seq",{"sourceInterval":[2139,2221]},["terminal",{"sourceInterval":[2139,2145]},"\\u{"],["app",{"sourceInterval":[2146,2154]},"hexDigit",[]],["opt",{"sourceInterval":[2155,2164]},["app",{"sourceInterval":[2155,2163]},"hexDigit",[]]],["opt",{"sourceInterval":[2165,2174]},["app",{"sourceInterval":[2165,2173]},"hexDigit",[]]],["opt",{"sourceInterval":[2188,2197]},["app",{"sourceInterval":[2188,2196]},"hexDigit",[]]],["opt",{"sourceInterval":[2198,2207]},["app",{"sourceInterval":[2198,2206]},"hexDigit",[]]],["opt",{"sourceInterval":[2208,2217]},["app",{"sourceInterval":[2208,2216]},"hexDigit",[]]],["terminal",{"sourceInterval":[2218,2221]},"}"]]],"escapeChar_unicodeEscape":["define",{"sourceInterval":[2250,2309]},null,[],["seq",{"sourceInterval":[2250,2291]},["terminal",{"sourceInterval":[2250,2255]},"\\u"],["app",{"sourceInterval":[2256,2264]},"hexDigit",[]],["app",{"sourceInterval":[2265,2273]},"hexDigit",[]],["app",{"sourceInterval":[2274,2282]},"hexDigit",[]],["app",{"sourceInterval":[2283,2291]},"hexDigit",[]]]],"escapeChar_hexEscape":["define",{"sourceInterval":[2316,2371]},null,[],["seq",{"sourceInterval":[2316,2339]},["terminal",{"sourceInterval":[2316,2321]},"\\x"],["app",{"sourceInterval":[2322,2330]},"hexDigit",[]],["app",{"sourceInterval":[2331,2339]},"hexDigit",[]]]],"escapeChar":["define",{"sourceInterval":[1664,2371]},"an escape sequence",[],["alt",{"sourceInterval":[1703,2371]},["app",{"sourceInterval":[1703,1709]},"escapeChar_backslash",[]],["app",{"sourceInterval":[1765,1771]},"escapeChar_doubleQuote",[]],["app",{"sourceInterval":[1829,1835]},"escapeChar_singleQuote",[]],["app",{"sourceInterval":[1893,1898]},"escapeChar_backspace",[]],["app",{"sourceInterval":[1955,1960]},"escapeChar_lineFeed",[]],["app",{"sourceInterval":[2016,2021]},"escapeChar_carriageReturn",[]],["app",{"sourceInterval":[2083,2088]},"escapeChar_tab",[]],["app",{"sourceInterval":[2139,2221]},"escapeChar_unicodeCodePoint",[]],["app",{"sourceInterval":[2250,2291]},"escapeChar_unicodeEscape",[]],["app",{"sourceInterval":[2316,2339]},"escapeChar_hexEscape",[]]]],"space":["extend",{"sourceInterval":[2375,2394]},null,[],["app",{"sourceInterval":[2387,2394]},"comment",[]]],"comment_singleLine":["define",{"sourceInterval":[2412,2458]},null,[],["seq",{"sourceInterval":[2412,2443]},["terminal",{"sourceInterval":[2412,2416]},"//"],["star",{"sourceInterval":[2417,2429]},["seq",{"sourceInterval":[2418,2427]},["not",{"sourceInterval":[2418,2423]},["terminal",{"sourceInterval":[2419,2423]},"\n"]],["app",{"sourceInterval":[2424,2427]},"any",[]]]],["lookahead",{"sourceInterval":[2430,2443]},["alt",{"sourceInterval":[2432,2442]},["terminal",{"sourceInterval":[2432,2436]},"\n"],["app",{"sourceInterval":[2439,2442]},"end",[]]]]]],"comment_multiLine":["define",{"sourceInterval":[2465,2501]},null,[],["seq",{"sourceInterval":[2465,2487]},["terminal",{"sourceInterval":[2465,2469]},"/*"],["star",{"sourceInterval":[2470,2482]},["seq",{"sourceInterval":[2471,2480]},["not",{"sourceInterval":[2471,2476]},["terminal",{"sourceInterval":[2472,2476]},"*/"]],["app",{"sourceInterval":[2477,2480]},"any",[]]]],["terminal",{"sourceInterval":[2483,2487]},"*/"]]],"comment":["define",{"sourceInterval":[2398,2501]},null,[],["alt",{"sourceInterval":[2412,2501]},["app",{"sourceInterval":[2412,2443]},"comment_singleLine",[]],["app",{"sourceInterval":[2465,2487]},"comment_multiLine",[]]]],"tokens":["define",{"sourceInterval":[2505,2520]},null,[],["star",{"sourceInterval":[2514,2520]},["app",{"sourceInterval":[2514,2519]},"token",[]]]],"token":["define",{"sourceInterval":[2524,2600]},null,[],["alt",{"sourceInterval":[2532,2600]},["app",{"sourceInterval":[2532,2540]},"caseName",[]],["app",{"sourceInterval":[2543,2550]},"comment",[]],["app",{"sourceInterval":[2553,2558]},"ident",[]],["app",{"sourceInterval":[2561,2569]},"operator",[]],["app",{"sourceInterval":[2572,2583]},"punctuation",[]],["app",{"sourceInterval":[2586,2594]},"terminal",[]],["app",{"sourceInterval":[2597,2600]},"any",[]]]],"operator":["define",{"sourceInterval":[2604,2669]},null,[],["alt",{"sourceInterval":[2615,2669]},["terminal",{"sourceInterval":[2615,2619]},"<:"],["terminal",{"sourceInterval":[2622,2625]},"="],["terminal",{"sourceInterval":[2628,2632]},":="],["terminal",{"sourceInterval":[2635,2639]},"+="],["terminal",{"sourceInterval":[2642,2645]},"*"],["terminal",{"sourceInterval":[2648,2651]},"+"],["terminal",{"sourceInterval":[2654,2657]},"?"],["terminal",{"sourceInterval":[2660,2663]},"~"],["terminal",{"sourceInterval":[2666,2669]},"&"]]],"punctuation":["define",{"sourceInterval":[2673,2709]},null,[],["alt",{"sourceInterval":[2687,2709]},["terminal",{"sourceInterval":[2687,2690]},"<"],["terminal",{"sourceInterval":[2693,2696]},">"],["terminal",{"sourceInterval":[2699,2702]},","],["terminal",{"sourceInterval":[2705,2709]},"--"]]]}]); +export default makeRecipe(["grammar",{"source":"Ohm {\n\n Document\n = Includes? Grammars\n\n Includes\n = IncludeStatement+\n \n IncludeStatement\n = include \"'\" relativeFilePath \"'\"\n\n Grammars\n = Grammar*\n\n Grammar\n = ident SuperGrammar? \"{\" Rule* \"}\"\n\n SuperGrammar\n = \"<:\" ident\n\n Rule\n = ident Formals? ruleDescr? \"=\" RuleBody -- define\n | ident Formals? \":=\" OverrideRuleBody -- override\n | ident Formals? \"+=\" RuleBody -- extend\n\n RuleBody\n = \"|\"? NonemptyListOf\n\n TopLevelTerm\n = Seq caseName -- inline\n | Seq\n\n OverrideRuleBody\n = \"|\"? NonemptyListOf\n\n OverrideTopLevelTerm\n = \"...\" -- superSplice\n | TopLevelTerm\n\n Formals\n = \"<\" ListOf \">\"\n\n Params\n = \"<\" ListOf \">\"\n\n Alt\n = NonemptyListOf\n\n Seq\n = Iter*\n\n Iter\n = Pred \"*\" -- star\n | Pred \"+\" -- plus\n | Pred \"?\" -- opt\n | Pred\n\n Pred\n = \"~\" Lex -- not\n | \"&\" Lex -- lookahead\n | Lex\n\n Lex\n = \"#\" Base -- lex\n | Base\n\n Base\n = ident Params? ~(ruleDescr? \"=\" | \":=\" | \"+=\") -- application\n | oneCharTerminal \"..\" oneCharTerminal -- range\n | terminal -- terminal\n | \"(\" Alt \")\" -- paren\n\n include\n \t= caseInsensitive<\"include\">\n \n relativeFilePath \n \t= ~\"'\" (letter | digit | \"-\" | \"\\\\\" | \"/\" | \".\")+ \n\n ruleDescr (a rule description)\n = \"(\" ruleDescrText \")\"\n\n ruleDescrText\n = (~\")\" any)*\n\n caseName\n = \"--\" (~\"\\n\" space)* name (~\"\\n\" space)* (\"\\n\" | &\"}\")\n\n name (a name)\n = nameFirst nameRest*\n\n nameFirst\n = \"_\"\n | letter\n\n nameRest\n = \"_\"\n | alnum\n\n ident (an identifier)\n = name\n\n terminal\n = \"\\\"\" terminalChar* \"\\\"\"\n\n oneCharTerminal\n = \"\\\"\" terminalChar \"\\\"\"\n\n terminalChar\n = escapeChar\n | ~\"\\\\\" ~\"\\\"\" ~\"\\n\" \"\\u{0}\"..\"\\u{10FFFF}\"\n\n escapeChar (an escape sequence)\n = \"\\\\\\\\\" -- backslash\n | \"\\\\\\\"\" -- doubleQuote\n | \"\\\\\\'\" -- singleQuote\n | \"\\\\b\" -- backspace\n | \"\\\\n\" -- lineFeed\n | \"\\\\r\" -- carriageReturn\n | \"\\\\t\" -- tab\n | \"\\\\u{\" hexDigit hexDigit? hexDigit?\n hexDigit? hexDigit? hexDigit? \"}\" -- unicodeCodePoint\n | \"\\\\u\" hexDigit hexDigit hexDigit hexDigit -- unicodeEscape\n | \"\\\\x\" hexDigit hexDigit -- hexEscape\n\n space\n += comment\n\n comment\n = \"//\" (~\"\\n\" any)* &(\"\\n\" | end) -- singleLine\n | \"/*\" (~\"*/\" any)* \"*/\" -- multiLine\n\n tokens = token*\n\n token = caseName | comment | ident | operator | punctuation | terminal | any\n\n operator = \"<:\" | \"=\" | \":=\" | \"+=\" | \"*\" | \"+\" | \"?\" | \"~\" | \"&\"\n\n punctuation = \"<\" | \">\" | \",\" | \"--\"\n}"},"Ohm",null,"Document",{"Document":["define",{"sourceInterval":[9,42]},null,[],["seq",{"sourceInterval":[24,42]},["opt",{"sourceInterval":[24,33]},["app",{"sourceInterval":[24,32]},"Includes",[]]],["app",{"sourceInterval":[34,42]},"Grammars",[]]]],"Includes":["define",{"sourceInterval":[46,78]},null,[],["plus",{"sourceInterval":[61,78]},["app",{"sourceInterval":[61,77]},"IncludeStatement",[]]]],"IncludeStatement":["define",{"sourceInterval":[84,141]},null,[],["seq",{"sourceInterval":[109,141]},["app",{"sourceInterval":[109,116]},"include",[]],["terminal",{"sourceInterval":[117,120]},"'"],["app",{"sourceInterval":[121,137]},"relativeFilePath",[]],["terminal",{"sourceInterval":[138,141]},"'"]]],"Grammars":["define",{"sourceInterval":[145,168]},null,[],["star",{"sourceInterval":[160,168]},["app",{"sourceInterval":[160,167]},"Grammar",[]]]],"Grammar":["define",{"sourceInterval":[172,219]},null,[],["seq",{"sourceInterval":[186,219]},["app",{"sourceInterval":[186,191]},"ident",[]],["opt",{"sourceInterval":[192,205]},["app",{"sourceInterval":[192,204]},"SuperGrammar",[]]],["terminal",{"sourceInterval":[206,209]},"{"],["star",{"sourceInterval":[210,215]},["app",{"sourceInterval":[210,214]},"Rule",[]]],["terminal",{"sourceInterval":[216,219]},"}"]]],"SuperGrammar":["define",{"sourceInterval":[223,252]},null,[],["seq",{"sourceInterval":[242,252]},["terminal",{"sourceInterval":[242,246]},"<:"],["app",{"sourceInterval":[247,252]},"ident",[]]]],"Rule_define":["define",{"sourceInterval":[267,317]},null,[],["seq",{"sourceInterval":[267,306]},["app",{"sourceInterval":[267,272]},"ident",[]],["opt",{"sourceInterval":[273,281]},["app",{"sourceInterval":[273,280]},"Formals",[]]],["opt",{"sourceInterval":[282,292]},["app",{"sourceInterval":[282,291]},"ruleDescr",[]]],["terminal",{"sourceInterval":[293,296]},"="],["app",{"sourceInterval":[298,306]},"RuleBody",[]]]],"Rule_override":["define",{"sourceInterval":[324,384]},null,[],["seq",{"sourceInterval":[324,371]},["app",{"sourceInterval":[324,329]},"ident",[]],["opt",{"sourceInterval":[330,338]},["app",{"sourceInterval":[330,337]},"Formals",[]]],["terminal",{"sourceInterval":[350,354]},":="],["app",{"sourceInterval":[355,371]},"OverrideRuleBody",[]]]],"Rule_extend":["define",{"sourceInterval":[391,441]},null,[],["seq",{"sourceInterval":[391,430]},["app",{"sourceInterval":[391,396]},"ident",[]],["opt",{"sourceInterval":[397,405]},["app",{"sourceInterval":[397,404]},"Formals",[]]],["terminal",{"sourceInterval":[417,421]},"+="],["app",{"sourceInterval":[422,430]},"RuleBody",[]]]],"Rule":["define",{"sourceInterval":[256,441]},null,[],["alt",{"sourceInterval":[267,441]},["app",{"sourceInterval":[267,306]},"Rule_define",[]],["app",{"sourceInterval":[324,371]},"Rule_override",[]],["app",{"sourceInterval":[391,430]},"Rule_extend",[]]]],"RuleBody":["define",{"sourceInterval":[445,498]},null,[],["seq",{"sourceInterval":[460,498]},["opt",{"sourceInterval":[460,464]},["terminal",{"sourceInterval":[460,463]},"|"]],["app",{"sourceInterval":[465,498]},"NonemptyListOf",[["app",{"sourceInterval":[480,492]},"TopLevelTerm",[]],["terminal",{"sourceInterval":[494,497]},"|"]]]]],"TopLevelTerm_inline":["define",{"sourceInterval":[521,544]},null,[],["seq",{"sourceInterval":[521,533]},["app",{"sourceInterval":[521,524]},"Seq",[]],["app",{"sourceInterval":[525,533]},"caseName",[]]]],"TopLevelTerm":["define",{"sourceInterval":[502,554]},null,[],["alt",{"sourceInterval":[521,554]},["app",{"sourceInterval":[521,533]},"TopLevelTerm_inline",[]],["app",{"sourceInterval":[551,554]},"Seq",[]]]],"OverrideRuleBody":["define",{"sourceInterval":[558,627]},null,[],["seq",{"sourceInterval":[581,627]},["opt",{"sourceInterval":[581,585]},["terminal",{"sourceInterval":[581,584]},"|"]],["app",{"sourceInterval":[586,627]},"NonemptyListOf",[["app",{"sourceInterval":[601,621]},"OverrideTopLevelTerm",[]],["terminal",{"sourceInterval":[623,626]},"|"]]]]],"OverrideTopLevelTerm_superSplice":["define",{"sourceInterval":[658,679]},null,[],["terminal",{"sourceInterval":[658,663]},"..."]],"OverrideTopLevelTerm":["define",{"sourceInterval":[631,698]},null,[],["alt",{"sourceInterval":[658,698]},["app",{"sourceInterval":[658,663]},"OverrideTopLevelTerm_superSplice",[]],["app",{"sourceInterval":[686,698]},"TopLevelTerm",[]]]],"Formals":["define",{"sourceInterval":[702,742]},null,[],["seq",{"sourceInterval":[716,742]},["terminal",{"sourceInterval":[716,719]},"<"],["app",{"sourceInterval":[720,738]},"ListOf",[["app",{"sourceInterval":[727,732]},"ident",[]],["terminal",{"sourceInterval":[734,737]},","]]],["terminal",{"sourceInterval":[739,742]},">"]]],"Params":["define",{"sourceInterval":[746,783]},null,[],["seq",{"sourceInterval":[759,783]},["terminal",{"sourceInterval":[759,762]},"<"],["app",{"sourceInterval":[763,779]},"ListOf",[["app",{"sourceInterval":[770,773]},"Seq",[]],["terminal",{"sourceInterval":[775,778]},","]]],["terminal",{"sourceInterval":[780,783]},">"]]],"Alt":["define",{"sourceInterval":[787,821]},null,[],["app",{"sourceInterval":[797,821]},"NonemptyListOf",[["app",{"sourceInterval":[812,815]},"Seq",[]],["terminal",{"sourceInterval":[817,820]},"|"]]]],"Seq":["define",{"sourceInterval":[825,840]},null,[],["star",{"sourceInterval":[835,840]},["app",{"sourceInterval":[835,839]},"Iter",[]]]],"Iter_star":["define",{"sourceInterval":[855,872]},null,[],["seq",{"sourceInterval":[855,863]},["app",{"sourceInterval":[855,859]},"Pred",[]],["terminal",{"sourceInterval":[860,863]},"*"]]],"Iter_plus":["define",{"sourceInterval":[879,896]},null,[],["seq",{"sourceInterval":[879,887]},["app",{"sourceInterval":[879,883]},"Pred",[]],["terminal",{"sourceInterval":[884,887]},"+"]]],"Iter_opt":["define",{"sourceInterval":[903,919]},null,[],["seq",{"sourceInterval":[903,911]},["app",{"sourceInterval":[903,907]},"Pred",[]],["terminal",{"sourceInterval":[908,911]},"?"]]],"Iter":["define",{"sourceInterval":[844,930]},null,[],["alt",{"sourceInterval":[855,930]},["app",{"sourceInterval":[855,863]},"Iter_star",[]],["app",{"sourceInterval":[879,887]},"Iter_plus",[]],["app",{"sourceInterval":[903,911]},"Iter_opt",[]],["app",{"sourceInterval":[926,930]},"Pred",[]]]],"Pred_not":["define",{"sourceInterval":[945,960]},null,[],["seq",{"sourceInterval":[945,952]},["terminal",{"sourceInterval":[945,948]},"~"],["app",{"sourceInterval":[949,952]},"Lex",[]]]],"Pred_lookahead":["define",{"sourceInterval":[967,988]},null,[],["seq",{"sourceInterval":[967,974]},["terminal",{"sourceInterval":[967,970]},"&"],["app",{"sourceInterval":[971,974]},"Lex",[]]]],"Pred":["define",{"sourceInterval":[934,998]},null,[],["alt",{"sourceInterval":[945,998]},["app",{"sourceInterval":[945,952]},"Pred_not",[]],["app",{"sourceInterval":[967,974]},"Pred_lookahead",[]],["app",{"sourceInterval":[995,998]},"Lex",[]]]],"Lex_lex":["define",{"sourceInterval":[1012,1028]},null,[],["seq",{"sourceInterval":[1012,1020]},["terminal",{"sourceInterval":[1012,1015]},"#"],["app",{"sourceInterval":[1016,1020]},"Base",[]]]],"Lex":["define",{"sourceInterval":[1002,1039]},null,[],["alt",{"sourceInterval":[1012,1039]},["app",{"sourceInterval":[1012,1020]},"Lex_lex",[]],["app",{"sourceInterval":[1035,1039]},"Base",[]]]],"Base_application":["define",{"sourceInterval":[1054,1115]},null,[],["seq",{"sourceInterval":[1054,1099]},["app",{"sourceInterval":[1054,1059]},"ident",[]],["opt",{"sourceInterval":[1060,1067]},["app",{"sourceInterval":[1060,1066]},"Params",[]]],["not",{"sourceInterval":[1068,1099]},["alt",{"sourceInterval":[1070,1098]},["seq",{"sourceInterval":[1070,1084]},["opt",{"sourceInterval":[1070,1080]},["app",{"sourceInterval":[1070,1079]},"ruleDescr",[]]],["terminal",{"sourceInterval":[1081,1084]},"="]],["terminal",{"sourceInterval":[1087,1091]},":="],["terminal",{"sourceInterval":[1094,1098]},"+="]]]]],"Base_range":["define",{"sourceInterval":[1122,1177]},null,[],["seq",{"sourceInterval":[1122,1158]},["app",{"sourceInterval":[1122,1137]},"oneCharTerminal",[]],["terminal",{"sourceInterval":[1138,1142]},".."],["app",{"sourceInterval":[1143,1158]},"oneCharTerminal",[]]]],"Base_terminal":["define",{"sourceInterval":[1184,1242]},null,[],["app",{"sourceInterval":[1184,1192]},"terminal",[]]],"Base_paren":["define",{"sourceInterval":[1249,1304]},null,[],["seq",{"sourceInterval":[1249,1260]},["terminal",{"sourceInterval":[1249,1252]},"("],["app",{"sourceInterval":[1253,1256]},"Alt",[]],["terminal",{"sourceInterval":[1257,1260]},")"]]],"Base":["define",{"sourceInterval":[1043,1304]},null,[],["alt",{"sourceInterval":[1054,1304]},["app",{"sourceInterval":[1054,1099]},"Base_application",[]],["app",{"sourceInterval":[1122,1158]},"Base_range",[]],["app",{"sourceInterval":[1184,1192]},"Base_terminal",[]],["app",{"sourceInterval":[1249,1260]},"Base_paren",[]]]],"include":["define",{"sourceInterval":[1308,1347]},null,[],["app",{"sourceInterval":[1321,1347]},"caseInsensitive",[["terminal",{"sourceInterval":[1337,1346]},"include"]]]],"relativeFilePath":["define",{"sourceInterval":[1355,1425]},null,[],["seq",{"sourceInterval":[1378,1425]},["not",{"sourceInterval":[1378,1382]},["terminal",{"sourceInterval":[1379,1382]},"'"]],["plus",{"sourceInterval":[1383,1425]},["alt",{"sourceInterval":[1384,1423]},["app",{"sourceInterval":[1384,1390]},"letter",[]],["app",{"sourceInterval":[1393,1398]},"digit",[]],["terminal",{"sourceInterval":[1401,1404]},"-"],["terminal",{"sourceInterval":[1407,1411]},"\\"],["terminal",{"sourceInterval":[1414,1417]},"/"],["terminal",{"sourceInterval":[1420,1423]},"."]]]]],"ruleDescr":["define",{"sourceInterval":[1430,1489]},"a rule description",[],["seq",{"sourceInterval":[1468,1489]},["terminal",{"sourceInterval":[1468,1471]},"("],["app",{"sourceInterval":[1472,1485]},"ruleDescrText",[]],["terminal",{"sourceInterval":[1486,1489]},")"]]],"ruleDescrText":["define",{"sourceInterval":[1493,1524]},null,[],["star",{"sourceInterval":[1513,1524]},["seq",{"sourceInterval":[1514,1522]},["not",{"sourceInterval":[1514,1518]},["terminal",{"sourceInterval":[1515,1518]},")"]],["app",{"sourceInterval":[1519,1522]},"any",[]]]]],"caseName":["define",{"sourceInterval":[1528,1596]},null,[],["seq",{"sourceInterval":[1543,1596]},["terminal",{"sourceInterval":[1543,1547]},"--"],["star",{"sourceInterval":[1548,1562]},["seq",{"sourceInterval":[1549,1560]},["not",{"sourceInterval":[1549,1554]},["terminal",{"sourceInterval":[1550,1554]},"\n"]],["app",{"sourceInterval":[1555,1560]},"space",[]]]],["app",{"sourceInterval":[1563,1567]},"name",[]],["star",{"sourceInterval":[1568,1582]},["seq",{"sourceInterval":[1569,1580]},["not",{"sourceInterval":[1569,1574]},["terminal",{"sourceInterval":[1570,1574]},"\n"]],["app",{"sourceInterval":[1575,1580]},"space",[]]]],["alt",{"sourceInterval":[1584,1595]},["terminal",{"sourceInterval":[1584,1588]},"\n"],["lookahead",{"sourceInterval":[1591,1595]},["terminal",{"sourceInterval":[1592,1595]},"}"]]]]],"name":["define",{"sourceInterval":[1600,1640]},"a name",[],["seq",{"sourceInterval":[1621,1640]},["app",{"sourceInterval":[1621,1630]},"nameFirst",[]],["star",{"sourceInterval":[1631,1640]},["app",{"sourceInterval":[1631,1639]},"nameRest",[]]]]],"nameFirst":["define",{"sourceInterval":[1644,1676]},null,[],["alt",{"sourceInterval":[1660,1676]},["terminal",{"sourceInterval":[1660,1663]},"_"],["app",{"sourceInterval":[1670,1676]},"letter",[]]]],"nameRest":["define",{"sourceInterval":[1680,1710]},null,[],["alt",{"sourceInterval":[1695,1710]},["terminal",{"sourceInterval":[1695,1698]},"_"],["app",{"sourceInterval":[1705,1710]},"alnum",[]]]],"ident":["define",{"sourceInterval":[1714,1747]},"an identifier",[],["app",{"sourceInterval":[1743,1747]},"name",[]]],"terminal":["define",{"sourceInterval":[1751,1789]},null,[],["seq",{"sourceInterval":[1766,1789]},["terminal",{"sourceInterval":[1766,1770]},"\""],["star",{"sourceInterval":[1771,1784]},["app",{"sourceInterval":[1771,1783]},"terminalChar",[]]],["terminal",{"sourceInterval":[1785,1789]},"\""]]],"oneCharTerminal":["define",{"sourceInterval":[1793,1837]},null,[],["seq",{"sourceInterval":[1815,1837]},["terminal",{"sourceInterval":[1815,1819]},"\""],["app",{"sourceInterval":[1820,1832]},"terminalChar",[]],["terminal",{"sourceInterval":[1833,1837]},"\""]]],"terminalChar":["define",{"sourceInterval":[1841,1918]},null,[],["alt",{"sourceInterval":[1860,1918]},["app",{"sourceInterval":[1860,1870]},"escapeChar",[]],["seq",{"sourceInterval":[1879,1918]},["not",{"sourceInterval":[1879,1884]},["terminal",{"sourceInterval":[1880,1884]},"\\"]],["not",{"sourceInterval":[1885,1890]},["terminal",{"sourceInterval":[1886,1890]},"\""]],["not",{"sourceInterval":[1891,1896]},["terminal",{"sourceInterval":[1892,1896]},"\n"]],["range",{"sourceInterval":[1897,1918]},"\u0000","􏿿"]]]],"escapeChar_backslash":["define",{"sourceInterval":[1961,2016]},null,[],["terminal",{"sourceInterval":[1961,1967]},"\\\\"]],"escapeChar_doubleQuote":["define",{"sourceInterval":[2023,2080]},null,[],["terminal",{"sourceInterval":[2023,2029]},"\\\""]],"escapeChar_singleQuote":["define",{"sourceInterval":[2087,2144]},null,[],["terminal",{"sourceInterval":[2087,2093]},"\\'"]],"escapeChar_backspace":["define",{"sourceInterval":[2151,2206]},null,[],["terminal",{"sourceInterval":[2151,2156]},"\\b"]],"escapeChar_lineFeed":["define",{"sourceInterval":[2213,2267]},null,[],["terminal",{"sourceInterval":[2213,2218]},"\\n"]],"escapeChar_carriageReturn":["define",{"sourceInterval":[2274,2334]},null,[],["terminal",{"sourceInterval":[2274,2279]},"\\r"]],"escapeChar_tab":["define",{"sourceInterval":[2341,2390]},null,[],["terminal",{"sourceInterval":[2341,2346]},"\\t"]],"escapeChar_unicodeCodePoint":["define",{"sourceInterval":[2397,2501]},null,[],["seq",{"sourceInterval":[2397,2479]},["terminal",{"sourceInterval":[2397,2403]},"\\u{"],["app",{"sourceInterval":[2404,2412]},"hexDigit",[]],["opt",{"sourceInterval":[2413,2422]},["app",{"sourceInterval":[2413,2421]},"hexDigit",[]]],["opt",{"sourceInterval":[2423,2432]},["app",{"sourceInterval":[2423,2431]},"hexDigit",[]]],["opt",{"sourceInterval":[2446,2455]},["app",{"sourceInterval":[2446,2454]},"hexDigit",[]]],["opt",{"sourceInterval":[2456,2465]},["app",{"sourceInterval":[2456,2464]},"hexDigit",[]]],["opt",{"sourceInterval":[2466,2475]},["app",{"sourceInterval":[2466,2474]},"hexDigit",[]]],["terminal",{"sourceInterval":[2476,2479]},"}"]]],"escapeChar_unicodeEscape":["define",{"sourceInterval":[2508,2567]},null,[],["seq",{"sourceInterval":[2508,2549]},["terminal",{"sourceInterval":[2508,2513]},"\\u"],["app",{"sourceInterval":[2514,2522]},"hexDigit",[]],["app",{"sourceInterval":[2523,2531]},"hexDigit",[]],["app",{"sourceInterval":[2532,2540]},"hexDigit",[]],["app",{"sourceInterval":[2541,2549]},"hexDigit",[]]]],"escapeChar_hexEscape":["define",{"sourceInterval":[2574,2629]},null,[],["seq",{"sourceInterval":[2574,2597]},["terminal",{"sourceInterval":[2574,2579]},"\\x"],["app",{"sourceInterval":[2580,2588]},"hexDigit",[]],["app",{"sourceInterval":[2589,2597]},"hexDigit",[]]]],"escapeChar":["define",{"sourceInterval":[1922,2629]},"an escape sequence",[],["alt",{"sourceInterval":[1961,2629]},["app",{"sourceInterval":[1961,1967]},"escapeChar_backslash",[]],["app",{"sourceInterval":[2023,2029]},"escapeChar_doubleQuote",[]],["app",{"sourceInterval":[2087,2093]},"escapeChar_singleQuote",[]],["app",{"sourceInterval":[2151,2156]},"escapeChar_backspace",[]],["app",{"sourceInterval":[2213,2218]},"escapeChar_lineFeed",[]],["app",{"sourceInterval":[2274,2279]},"escapeChar_carriageReturn",[]],["app",{"sourceInterval":[2341,2346]},"escapeChar_tab",[]],["app",{"sourceInterval":[2397,2479]},"escapeChar_unicodeCodePoint",[]],["app",{"sourceInterval":[2508,2549]},"escapeChar_unicodeEscape",[]],["app",{"sourceInterval":[2574,2597]},"escapeChar_hexEscape",[]]]],"space":["extend",{"sourceInterval":[2633,2652]},null,[],["app",{"sourceInterval":[2645,2652]},"comment",[]]],"comment_singleLine":["define",{"sourceInterval":[2670,2716]},null,[],["seq",{"sourceInterval":[2670,2701]},["terminal",{"sourceInterval":[2670,2674]},"//"],["star",{"sourceInterval":[2675,2687]},["seq",{"sourceInterval":[2676,2685]},["not",{"sourceInterval":[2676,2681]},["terminal",{"sourceInterval":[2677,2681]},"\n"]],["app",{"sourceInterval":[2682,2685]},"any",[]]]],["lookahead",{"sourceInterval":[2688,2701]},["alt",{"sourceInterval":[2690,2700]},["terminal",{"sourceInterval":[2690,2694]},"\n"],["app",{"sourceInterval":[2697,2700]},"end",[]]]]]],"comment_multiLine":["define",{"sourceInterval":[2723,2759]},null,[],["seq",{"sourceInterval":[2723,2745]},["terminal",{"sourceInterval":[2723,2727]},"/*"],["star",{"sourceInterval":[2728,2740]},["seq",{"sourceInterval":[2729,2738]},["not",{"sourceInterval":[2729,2734]},["terminal",{"sourceInterval":[2730,2734]},"*/"]],["app",{"sourceInterval":[2735,2738]},"any",[]]]],["terminal",{"sourceInterval":[2741,2745]},"*/"]]],"comment":["define",{"sourceInterval":[2656,2759]},null,[],["alt",{"sourceInterval":[2670,2759]},["app",{"sourceInterval":[2670,2701]},"comment_singleLine",[]],["app",{"sourceInterval":[2723,2745]},"comment_multiLine",[]]]],"tokens":["define",{"sourceInterval":[2763,2778]},null,[],["star",{"sourceInterval":[2772,2778]},["app",{"sourceInterval":[2772,2777]},"token",[]]]],"token":["define",{"sourceInterval":[2782,2858]},null,[],["alt",{"sourceInterval":[2790,2858]},["app",{"sourceInterval":[2790,2798]},"caseName",[]],["app",{"sourceInterval":[2801,2808]},"comment",[]],["app",{"sourceInterval":[2811,2816]},"ident",[]],["app",{"sourceInterval":[2819,2827]},"operator",[]],["app",{"sourceInterval":[2830,2841]},"punctuation",[]],["app",{"sourceInterval":[2844,2852]},"terminal",[]],["app",{"sourceInterval":[2855,2858]},"any",[]]]],"operator":["define",{"sourceInterval":[2862,2927]},null,[],["alt",{"sourceInterval":[2873,2927]},["terminal",{"sourceInterval":[2873,2877]},"<:"],["terminal",{"sourceInterval":[2880,2883]},"="],["terminal",{"sourceInterval":[2886,2890]},":="],["terminal",{"sourceInterval":[2893,2897]},"+="],["terminal",{"sourceInterval":[2900,2903]},"*"],["terminal",{"sourceInterval":[2906,2909]},"+"],["terminal",{"sourceInterval":[2912,2915]},"?"],["terminal",{"sourceInterval":[2918,2921]},"~"],["terminal",{"sourceInterval":[2924,2927]},"&"]]],"punctuation":["define",{"sourceInterval":[2931,2967]},null,[],["alt",{"sourceInterval":[2945,2967]},["terminal",{"sourceInterval":[2945,2948]},"<"],["terminal",{"sourceInterval":[2951,2954]},">"],["terminal",{"sourceInterval":[2957,2960]},","],["terminal",{"sourceInterval":[2963,2967]},"--"]]]}]); diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 09cfcbdf..57418932 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -1,10 +1,16 @@ Ohm { - Grammars - = (IncludeStatement+)? Grammar* + Document + = Includes? Grammars + Includes + = IncludeStatement+ + IncludeStatement - = include "'" relativeFilePath "'" + = include "'" relativeFilePath "'" + + Grammars + = Grammar* Grammar = ident SuperGrammar? "{" Rule* "}" From 3000e6368b558546cf1b7c4314190bee1ac7dce8 Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Wed, 16 Aug 2023 14:15:41 +0000 Subject: [PATCH 11/20] Matched naming of Grammars for Includes --- packages/ohm-js/src/ohm-grammar.ohm | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 57418932..5226ce05 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -4,9 +4,9 @@ Ohm { = Includes? Grammars Includes - = IncludeStatement+ + = Include+ - IncludeStatement + Include = include "'" relativeFilePath "'" Grammars From 0eda4072bbf5d387d251ee164cdb4a83ff14ed4e Mon Sep 17 00:00:00 2001 From: Liam Riddell Date: Wed, 16 Aug 2023 19:20:47 +0100 Subject: [PATCH 12/20] Remove case insensitive --- packages/ohm-js/src/ohm-grammar.ohm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 09cfcbdf..a3a5e0fe 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -65,7 +65,7 @@ Ohm { | "(" Alt ")" -- paren include - = caseInsensitive<"include"> + = "include" relativeFilePath = ~"'" (letter | digit | "-" | "\\" | "/" | ".")+ From 7c293f7537a735ab9685823860604aa112bd9f97 Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Wed, 16 Aug 2023 18:20:55 +0000 Subject: [PATCH 13/20] Removed case insensitive --- packages/ohm-js/src/ohm-grammar.ohm | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 5226ce05..81492368 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -1,10 +1,10 @@ Ohm { Document - = Includes? Grammars + = Includes Grammars Includes - = Include+ + = Include* Include = include "'" relativeFilePath "'" @@ -71,7 +71,7 @@ Ohm { | "(" Alt ")" -- paren include - = caseInsensitive<"include"> + = "include" relativeFilePath = ~"'" (letter | digit | "-" | "\\" | "/" | ".")+ From 4751dfccebdba5b8005a21cbcd69e118f644a0bc Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Wed, 16 Aug 2023 18:22:47 +0000 Subject: [PATCH 14/20] Added document to the examples unit tests --- packages/ohm-js/extras/extractExamples.js | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/packages/ohm-js/extras/extractExamples.js b/packages/ohm-js/extras/extractExamples.js index 1e0df72b..8aba4fc9 100644 --- a/packages/ohm-js/extras/extractExamples.js +++ b/packages/ohm-js/extras/extractExamples.js @@ -73,6 +73,14 @@ const semantics = grammars.OhmWithExamples.createSemantics().addOperation('hasEx }); semantics.addOperation('examples', { + Document(includesIter, grammarIter) + { + includesIter.examples(); + return grammarIter.examples(); + }, + Includes(includesIter) { + return includesIter.children.flatMap(c => c.examples()); + }, Grammars(grammarIter) { return grammarIter.children.flatMap(c => c.examples()); }, From 4f2b480ae5de9a0fb2082bea35fdb83e2858b6c9 Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Thu, 17 Aug 2023 11:01:40 +0000 Subject: [PATCH 15/20] WIP Commit --- packages/ohm-js/extras/extractExamples.js | 3 + packages/ohm-js/src/buildGrammar.js | 68 ++++++++++++++++++++++- packages/ohm-js/src/main.js | 26 ++++++--- packages/ohm-js/src/util.js | 14 +++++ packages/ohm-js/test/test-ohm-syntax.js | 36 +++++++++++- 5 files changed, 136 insertions(+), 11 deletions(-) diff --git a/packages/ohm-js/extras/extractExamples.js b/packages/ohm-js/extras/extractExamples.js index 8aba4fc9..f6aa6528 100644 --- a/packages/ohm-js/extras/extractExamples.js +++ b/packages/ohm-js/extras/extractExamples.js @@ -81,6 +81,9 @@ semantics.addOperation('examples', { Includes(includesIter) { return includesIter.children.flatMap(c => c.examples()); }, + Include(_, _la, relativePathNode, _ra) { + return null; + }, Grammars(grammarIter) { return grammarIter.children.flatMap(c => c.examples()); }, diff --git a/packages/ohm-js/src/buildGrammar.js b/packages/ohm-js/src/buildGrammar.js index f63ad649..15b2e1d0 100644 --- a/packages/ohm-js/src/buildGrammar.js +++ b/packages/ohm-js/src/buildGrammar.js @@ -4,6 +4,7 @@ import * as common from './common.js'; import * as errors from './errors.js'; import {Grammar} from './Grammar.js'; import * as pexprs from './pexprs.js'; +import { validateOption } from './util.js'; const superSplicePlaceholder = Object.create(pexprs.PExpr.prototype); @@ -19,16 +20,79 @@ function namespaceHas(ns, name) { // `tree`, which is the concrete syntax tree of a user-written grammar. // The grammar will be assigned into `namespace` under the name of the grammar // as specified in the source. -export function buildGrammar(match, namespace, optOhmGrammarForTesting) { +export function buildGrammar(match, namespace, options, optOhmGrammarForTesting) { const builder = new Builder(); let decl; let currentRuleName; let currentRuleFormals; let overriding = false; const metaGrammar = optOhmGrammarForTesting || ohmGrammar; + + const fetchGrammarInternal = (path) => { + if (!validateOption(options, 'fetchGrammar', 'function')) + { + throw new Error("Missing option 'fetchGrammar' of type `function` when trying to include."); + } + + const grammarContent = options.fetchGrammar(path); + + if (typeof grammarContent !== "string") + { + throw new Error(`Expected string from 'fetchGrammar' function, but got ${typeof(grammarContent)}`); + } + + return grammarContent.trim(); + } + + const rematchInput = (includes) => { + let modifiedGrammarSource = match.input; + + for (let i = 0; i < includes.length; i++) { + const [sourceString, fileContent] = includes[i]; + + // Always substitute the include even with a nothing to prevent infinite loop. + modifiedGrammarSource = modifiedGrammarSource.replace(sourceString, fileContent); + } + + const newMatch = ohmGrammar.match(modifiedGrammarSource); + + if (newMatch.failed()) { + throw errors.grammarSyntaxError(newMatch); + } + + helpers(newMatch).visit() + } // A visitor that produces a Grammar instance from the CST. const helpers = metaGrammar.createSemantics().addOperation('visit', { + Document(includesNode, grammarsNode) + { + const resolvedIncludes = includesNode.visit(); + + // We need to rebuild the grammar match with the resolved includes substituted. + // Note: It's important we prevent any deeper visits in this tree as it's now pointless. + if (resolvedIncludes.length > 0) { + rematchInput(resolvedIncludes); + return; + } + + return grammarsNode.visit(); + }, + Includes(includesIter) { + const resolvedIncludes = []; + + includesIter.children.flatMap(c => { + resolvedIncludes.push(c.visit()); + }) + + return resolvedIncludes; + }, + Include(_, _la, relativePathNode, _ra) { + return [ + this.sourceString, + fetchGrammarInternal(relativePathNode.sourceString) + ]; + }, Grammars(grammarIter) { return grammarIter.children.map(c => c.visit()); }, @@ -45,7 +109,6 @@ export function buildGrammar(match, namespace, optOhmGrammarForTesting) { namespace[grammarName] = g; return g; }, - SuperGrammar(_, n) { const superGrammarName = n.visit(); if (superGrammarName === 'null') { @@ -234,5 +297,6 @@ export function buildGrammar(match, namespace, optOhmGrammarForTesting) { return this.sourceString; }, }); + return helpers(match).visit(); } diff --git a/packages/ohm-js/src/main.js b/packages/ohm-js/src/main.js index 2fc8dffa..4dbddd62 100644 --- a/packages/ohm-js/src/main.js +++ b/packages/ohm-js/src/main.js @@ -11,21 +11,27 @@ import * as util from './util.js'; import './semanticsDeferredInit.js'; // TODO: Clean this up. Grammar.initApplicationParser(ohmGrammar, buildGrammar); +const DEFAULT_OPTIONS = { + fetchGrammar: undefined +}; + const isBuffer = obj => !!obj.constructor && typeof obj.constructor.isBuffer === 'function' && obj.constructor.isBuffer(obj); -function compileAndLoad(source, namespace) { - const m = ohmGrammar.match(source, 'Grammars'); +function compileAndLoad(source, namespace, options) { + const m = ohmGrammar.match(source); + if (m.failed()) { throw errors.grammarSyntaxError(m); } - return buildGrammar(m, namespace); + + return buildGrammar(m, namespace, options); } -export function grammar(source, optNamespace) { - const ns = grammars(source, optNamespace); +export function grammar(source, optNamespace, options = {}) { + const ns = grammars(source, optNamespace, options); // Ensure that the source contained no more than one grammar definition. const grammarNames = Object.keys(ns); @@ -42,8 +48,10 @@ export function grammar(source, optNamespace) { return ns[grammarNames[0]]; // Return the one and only grammar. } -export function grammars(source, optNamespace) { +export function grammars(source, optNamespace, options = {}) { + const ns = Object.create(optNamespace || {}); + if (typeof source !== 'string') { // For convenience, detect Node.js Buffer objects and automatically call toString(). if (isBuffer(source)) { @@ -54,7 +62,11 @@ export function grammars(source, optNamespace) { ); } } - compileAndLoad(source, ns); + + const mergedOptions = Object.assign({}, DEFAULT_OPTIONS, options); + + compileAndLoad(source, ns, mergedOptions); + return ns; } diff --git a/packages/ohm-js/src/util.js b/packages/ohm-js/src/util.js index dc0e144c..831b7881 100644 --- a/packages/ohm-js/src/util.js +++ b/packages/ohm-js/src/util.js @@ -171,3 +171,17 @@ export const uniqueId = (() => { let idCounter = 0; return prefix => '' + prefix + idCounter++; })(); + +export function validateOption(options, optionName, expectedType) { + if (!options.hasOwnProperty(optionName)) { + return false; + } + + const optionValue = options[optionName]; + + if (typeof optionValue !== expectedType) { + return false; + } + + return true; +} diff --git a/packages/ohm-js/test/test-ohm-syntax.js b/packages/ohm-js/test/test-ohm-syntax.js index f76777fc..040e1350 100644 --- a/packages/ohm-js/test/test-ohm-syntax.js +++ b/packages/ohm-js/test/test-ohm-syntax.js @@ -1442,9 +1442,41 @@ describe('bootstrap', test => { }); test('full bootstrap!', t => { - const g = buildGrammar(ns.Ohm.match(ohmGrammarSource, 'Grammar'), {}, ns.Ohm); - const gPrime = buildGrammar(g.match(ohmGrammarSource, 'Grammar'), {}, g); + const g = buildGrammar(ns.Ohm.match(ohmGrammarSource, 'Document'), {}, ns.Ohm); + const gPrime = buildGrammar(g.match(ohmGrammarSource, 'Document'), {}, g); gPrime.namespaceName = g.namespaceName; // make their namespaceName properties the same compareGrammars(t, g, gPrime); }); }); + +test('include', t => { + const g = ohm.grammar(` + include 'test.ohm' + `, {}, { + fetchGrammar: (path) => `G { X = "G" }` + }); + t.is(g.succeeded(), true); +}); + +test('multiple include', t => { + const g = ohm.grammars(` + include 'file-a.ohm' + include 'file-b.ohm' + `, {}, { + fetchGrammar: (path) => { + switch (path) { + case "file-a.ohm": + return `FileA { A = "A" }`; + + case "file-b.ohm": + return `FileB { B = "B" }`; + + default: + return ""; + } + } + }); + + // IMPLEMENT UNIT TEST For FileA, and FileB + // t.is(g.FileA.sourceString., true); +}); \ No newline at end of file From 87732d4ffa38856bb66bb8c4860218481f02a1a2 Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Fri, 18 Aug 2023 21:01:41 +0000 Subject: [PATCH 16/20] Added unit tests --- packages/ohm-js/test/test-ohm-syntax.js | 66 ++++++++++++++++--------- 1 file changed, 42 insertions(+), 24 deletions(-) diff --git a/packages/ohm-js/test/test-ohm-syntax.js b/packages/ohm-js/test/test-ohm-syntax.js index 040e1350..e7a88792 100644 --- a/packages/ohm-js/test/test-ohm-syntax.js +++ b/packages/ohm-js/test/test-ohm-syntax.js @@ -1382,21 +1382,21 @@ describe('bootstrap', test => { const ns = ohm.grammars(ohmGrammarSource); test('it can recognize arithmetic grammar', t => { - assertSucceeds(t, ns.Ohm.match(arithmeticGrammarSource, 'Grammar')); + assertSucceeds(t, ns.Ohm.match(arithmeticGrammarSource)); }); test('it can recognize itself', t => { - assertSucceeds(t, ns.Ohm.match(ohmGrammarSource, 'Grammar')); + assertSucceeds(t, ns.Ohm.match(ohmGrammarSource)); }); test('it can produce a grammar that works', t => { - const g = buildGrammar(ns.Ohm.match(ohmGrammarSource, 'Grammar'), {}, ns.Ohm); + const g = buildGrammar(ns.Ohm.match(ohmGrammarSource), ns.Ohm, {}); assertSucceeds( t, - g.match(ohmGrammarSource, 'Grammar'), + g.match(ohmGrammarSource), 'Ohm grammar can recognize itself', ); - const Arithmetic = buildGrammar(g.match(arithmeticGrammarSource, 'Grammar'), {}, g); + const Arithmetic = buildGrammar(g.match(arithmeticGrammarSource), {}, {}, g); const s = Arithmetic.createSemantics().addAttribute('v', { exp(expr) { return expr.v; @@ -1449,34 +1449,52 @@ describe('bootstrap', test => { }); }); -test('include', t => { - const g = ohm.grammar(` +describe('include', test => { + test('include', t => { + const g = ohm.grammar(` include 'test.ohm' `, {}, { - fetchGrammar: (path) => `G { X = "G" }` + fetchGrammar: (path) => `G { X = "G" }` + }); + + assertSucceeds(t, g.match('G')); }); - t.is(g.succeeded(), true); -}); -test('multiple include', t => { - const g = ohm.grammars(` + test('multiple', t => { + const grammars = ohm.grammars(` include 'file-a.ohm' include 'file-b.ohm' `, {}, { - fetchGrammar: (path) => { - switch (path) { - case "file-a.ohm": - return `FileA { A = "A" }`; + fetchGrammar: (path) => { + switch (path) { + case "file-a.ohm": + return 'FileA { A = "A" }'; + + case "file-b.ohm": + return 'FileB { B = "B" }'; + + default: + return ""; + } + } + }); - case "file-b.ohm": - return `FileB { B = "B" }`; + assertSucceeds(t, grammars.FileA.match('A')); + assertSucceeds(t, grammars.FileB.match('B')); + }); - default: - return ""; - } + test('supergrammar', t => { + const grammar = ohm.grammars(` + include 'supergrammar.ohm' + + ChildGrammar <: SuperGrammar { + S += "C" } - }); + `, {}, { + fetchGrammar: (path) => 'SuperGrammar { S = "S" }' + }); - // IMPLEMENT UNIT TEST For FileA, and FileB - // t.is(g.FileA.sourceString., true); + assertSucceeds(t, grammar.ChildGrammar.match('C')); + assertSucceeds(t, grammar.ChildGrammar.match('S')); + }); }); \ No newline at end of file From 1e1939869b606a210144d5f6ec473cf4c2401442 Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Fri, 18 Aug 2023 22:10:47 +0000 Subject: [PATCH 17/20] Grammar --- packages/ohm-js/dist/ohm-grammar.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/ohm-js/dist/ohm-grammar.js b/packages/ohm-js/dist/ohm-grammar.js index cde32880..30ca7022 100644 --- a/packages/ohm-js/dist/ohm-grammar.js +++ b/packages/ohm-js/dist/ohm-grammar.js @@ -1,2 +1,2 @@ import {makeRecipe} from '../src/main-kernel.js'; -export default makeRecipe(["grammar",{"source":"Ohm {\n\n Document\n = Includes? Grammars\n\n Includes\n = IncludeStatement+\n \n IncludeStatement\n = include \"'\" relativeFilePath \"'\"\n\n Grammars\n = Grammar*\n\n Grammar\n = ident SuperGrammar? \"{\" Rule* \"}\"\n\n SuperGrammar\n = \"<:\" ident\n\n Rule\n = ident Formals? ruleDescr? \"=\" RuleBody -- define\n | ident Formals? \":=\" OverrideRuleBody -- override\n | ident Formals? \"+=\" RuleBody -- extend\n\n RuleBody\n = \"|\"? NonemptyListOf\n\n TopLevelTerm\n = Seq caseName -- inline\n | Seq\n\n OverrideRuleBody\n = \"|\"? NonemptyListOf\n\n OverrideTopLevelTerm\n = \"...\" -- superSplice\n | TopLevelTerm\n\n Formals\n = \"<\" ListOf \">\"\n\n Params\n = \"<\" ListOf \">\"\n\n Alt\n = NonemptyListOf\n\n Seq\n = Iter*\n\n Iter\n = Pred \"*\" -- star\n | Pred \"+\" -- plus\n | Pred \"?\" -- opt\n | Pred\n\n Pred\n = \"~\" Lex -- not\n | \"&\" Lex -- lookahead\n | Lex\n\n Lex\n = \"#\" Base -- lex\n | Base\n\n Base\n = ident Params? ~(ruleDescr? \"=\" | \":=\" | \"+=\") -- application\n | oneCharTerminal \"..\" oneCharTerminal -- range\n | terminal -- terminal\n | \"(\" Alt \")\" -- paren\n\n include\n \t= caseInsensitive<\"include\">\n \n relativeFilePath \n \t= ~\"'\" (letter | digit | \"-\" | \"\\\\\" | \"/\" | \".\")+ \n\n ruleDescr (a rule description)\n = \"(\" ruleDescrText \")\"\n\n ruleDescrText\n = (~\")\" any)*\n\n caseName\n = \"--\" (~\"\\n\" space)* name (~\"\\n\" space)* (\"\\n\" | &\"}\")\n\n name (a name)\n = nameFirst nameRest*\n\n nameFirst\n = \"_\"\n | letter\n\n nameRest\n = \"_\"\n | alnum\n\n ident (an identifier)\n = name\n\n terminal\n = \"\\\"\" terminalChar* \"\\\"\"\n\n oneCharTerminal\n = \"\\\"\" terminalChar \"\\\"\"\n\n terminalChar\n = escapeChar\n | ~\"\\\\\" ~\"\\\"\" ~\"\\n\" \"\\u{0}\"..\"\\u{10FFFF}\"\n\n escapeChar (an escape sequence)\n = \"\\\\\\\\\" -- backslash\n | \"\\\\\\\"\" -- doubleQuote\n | \"\\\\\\'\" -- singleQuote\n | \"\\\\b\" -- backspace\n | \"\\\\n\" -- lineFeed\n | \"\\\\r\" -- carriageReturn\n | \"\\\\t\" -- tab\n | \"\\\\u{\" hexDigit hexDigit? hexDigit?\n hexDigit? hexDigit? hexDigit? \"}\" -- unicodeCodePoint\n | \"\\\\u\" hexDigit hexDigit hexDigit hexDigit -- unicodeEscape\n | \"\\\\x\" hexDigit hexDigit -- hexEscape\n\n space\n += comment\n\n comment\n = \"//\" (~\"\\n\" any)* &(\"\\n\" | end) -- singleLine\n | \"/*\" (~\"*/\" any)* \"*/\" -- multiLine\n\n tokens = token*\n\n token = caseName | comment | ident | operator | punctuation | terminal | any\n\n operator = \"<:\" | \"=\" | \":=\" | \"+=\" | \"*\" | \"+\" | \"?\" | \"~\" | \"&\"\n\n punctuation = \"<\" | \">\" | \",\" | \"--\"\n}"},"Ohm",null,"Document",{"Document":["define",{"sourceInterval":[9,42]},null,[],["seq",{"sourceInterval":[24,42]},["opt",{"sourceInterval":[24,33]},["app",{"sourceInterval":[24,32]},"Includes",[]]],["app",{"sourceInterval":[34,42]},"Grammars",[]]]],"Includes":["define",{"sourceInterval":[46,78]},null,[],["plus",{"sourceInterval":[61,78]},["app",{"sourceInterval":[61,77]},"IncludeStatement",[]]]],"IncludeStatement":["define",{"sourceInterval":[84,141]},null,[],["seq",{"sourceInterval":[109,141]},["app",{"sourceInterval":[109,116]},"include",[]],["terminal",{"sourceInterval":[117,120]},"'"],["app",{"sourceInterval":[121,137]},"relativeFilePath",[]],["terminal",{"sourceInterval":[138,141]},"'"]]],"Grammars":["define",{"sourceInterval":[145,168]},null,[],["star",{"sourceInterval":[160,168]},["app",{"sourceInterval":[160,167]},"Grammar",[]]]],"Grammar":["define",{"sourceInterval":[172,219]},null,[],["seq",{"sourceInterval":[186,219]},["app",{"sourceInterval":[186,191]},"ident",[]],["opt",{"sourceInterval":[192,205]},["app",{"sourceInterval":[192,204]},"SuperGrammar",[]]],["terminal",{"sourceInterval":[206,209]},"{"],["star",{"sourceInterval":[210,215]},["app",{"sourceInterval":[210,214]},"Rule",[]]],["terminal",{"sourceInterval":[216,219]},"}"]]],"SuperGrammar":["define",{"sourceInterval":[223,252]},null,[],["seq",{"sourceInterval":[242,252]},["terminal",{"sourceInterval":[242,246]},"<:"],["app",{"sourceInterval":[247,252]},"ident",[]]]],"Rule_define":["define",{"sourceInterval":[267,317]},null,[],["seq",{"sourceInterval":[267,306]},["app",{"sourceInterval":[267,272]},"ident",[]],["opt",{"sourceInterval":[273,281]},["app",{"sourceInterval":[273,280]},"Formals",[]]],["opt",{"sourceInterval":[282,292]},["app",{"sourceInterval":[282,291]},"ruleDescr",[]]],["terminal",{"sourceInterval":[293,296]},"="],["app",{"sourceInterval":[298,306]},"RuleBody",[]]]],"Rule_override":["define",{"sourceInterval":[324,384]},null,[],["seq",{"sourceInterval":[324,371]},["app",{"sourceInterval":[324,329]},"ident",[]],["opt",{"sourceInterval":[330,338]},["app",{"sourceInterval":[330,337]},"Formals",[]]],["terminal",{"sourceInterval":[350,354]},":="],["app",{"sourceInterval":[355,371]},"OverrideRuleBody",[]]]],"Rule_extend":["define",{"sourceInterval":[391,441]},null,[],["seq",{"sourceInterval":[391,430]},["app",{"sourceInterval":[391,396]},"ident",[]],["opt",{"sourceInterval":[397,405]},["app",{"sourceInterval":[397,404]},"Formals",[]]],["terminal",{"sourceInterval":[417,421]},"+="],["app",{"sourceInterval":[422,430]},"RuleBody",[]]]],"Rule":["define",{"sourceInterval":[256,441]},null,[],["alt",{"sourceInterval":[267,441]},["app",{"sourceInterval":[267,306]},"Rule_define",[]],["app",{"sourceInterval":[324,371]},"Rule_override",[]],["app",{"sourceInterval":[391,430]},"Rule_extend",[]]]],"RuleBody":["define",{"sourceInterval":[445,498]},null,[],["seq",{"sourceInterval":[460,498]},["opt",{"sourceInterval":[460,464]},["terminal",{"sourceInterval":[460,463]},"|"]],["app",{"sourceInterval":[465,498]},"NonemptyListOf",[["app",{"sourceInterval":[480,492]},"TopLevelTerm",[]],["terminal",{"sourceInterval":[494,497]},"|"]]]]],"TopLevelTerm_inline":["define",{"sourceInterval":[521,544]},null,[],["seq",{"sourceInterval":[521,533]},["app",{"sourceInterval":[521,524]},"Seq",[]],["app",{"sourceInterval":[525,533]},"caseName",[]]]],"TopLevelTerm":["define",{"sourceInterval":[502,554]},null,[],["alt",{"sourceInterval":[521,554]},["app",{"sourceInterval":[521,533]},"TopLevelTerm_inline",[]],["app",{"sourceInterval":[551,554]},"Seq",[]]]],"OverrideRuleBody":["define",{"sourceInterval":[558,627]},null,[],["seq",{"sourceInterval":[581,627]},["opt",{"sourceInterval":[581,585]},["terminal",{"sourceInterval":[581,584]},"|"]],["app",{"sourceInterval":[586,627]},"NonemptyListOf",[["app",{"sourceInterval":[601,621]},"OverrideTopLevelTerm",[]],["terminal",{"sourceInterval":[623,626]},"|"]]]]],"OverrideTopLevelTerm_superSplice":["define",{"sourceInterval":[658,679]},null,[],["terminal",{"sourceInterval":[658,663]},"..."]],"OverrideTopLevelTerm":["define",{"sourceInterval":[631,698]},null,[],["alt",{"sourceInterval":[658,698]},["app",{"sourceInterval":[658,663]},"OverrideTopLevelTerm_superSplice",[]],["app",{"sourceInterval":[686,698]},"TopLevelTerm",[]]]],"Formals":["define",{"sourceInterval":[702,742]},null,[],["seq",{"sourceInterval":[716,742]},["terminal",{"sourceInterval":[716,719]},"<"],["app",{"sourceInterval":[720,738]},"ListOf",[["app",{"sourceInterval":[727,732]},"ident",[]],["terminal",{"sourceInterval":[734,737]},","]]],["terminal",{"sourceInterval":[739,742]},">"]]],"Params":["define",{"sourceInterval":[746,783]},null,[],["seq",{"sourceInterval":[759,783]},["terminal",{"sourceInterval":[759,762]},"<"],["app",{"sourceInterval":[763,779]},"ListOf",[["app",{"sourceInterval":[770,773]},"Seq",[]],["terminal",{"sourceInterval":[775,778]},","]]],["terminal",{"sourceInterval":[780,783]},">"]]],"Alt":["define",{"sourceInterval":[787,821]},null,[],["app",{"sourceInterval":[797,821]},"NonemptyListOf",[["app",{"sourceInterval":[812,815]},"Seq",[]],["terminal",{"sourceInterval":[817,820]},"|"]]]],"Seq":["define",{"sourceInterval":[825,840]},null,[],["star",{"sourceInterval":[835,840]},["app",{"sourceInterval":[835,839]},"Iter",[]]]],"Iter_star":["define",{"sourceInterval":[855,872]},null,[],["seq",{"sourceInterval":[855,863]},["app",{"sourceInterval":[855,859]},"Pred",[]],["terminal",{"sourceInterval":[860,863]},"*"]]],"Iter_plus":["define",{"sourceInterval":[879,896]},null,[],["seq",{"sourceInterval":[879,887]},["app",{"sourceInterval":[879,883]},"Pred",[]],["terminal",{"sourceInterval":[884,887]},"+"]]],"Iter_opt":["define",{"sourceInterval":[903,919]},null,[],["seq",{"sourceInterval":[903,911]},["app",{"sourceInterval":[903,907]},"Pred",[]],["terminal",{"sourceInterval":[908,911]},"?"]]],"Iter":["define",{"sourceInterval":[844,930]},null,[],["alt",{"sourceInterval":[855,930]},["app",{"sourceInterval":[855,863]},"Iter_star",[]],["app",{"sourceInterval":[879,887]},"Iter_plus",[]],["app",{"sourceInterval":[903,911]},"Iter_opt",[]],["app",{"sourceInterval":[926,930]},"Pred",[]]]],"Pred_not":["define",{"sourceInterval":[945,960]},null,[],["seq",{"sourceInterval":[945,952]},["terminal",{"sourceInterval":[945,948]},"~"],["app",{"sourceInterval":[949,952]},"Lex",[]]]],"Pred_lookahead":["define",{"sourceInterval":[967,988]},null,[],["seq",{"sourceInterval":[967,974]},["terminal",{"sourceInterval":[967,970]},"&"],["app",{"sourceInterval":[971,974]},"Lex",[]]]],"Pred":["define",{"sourceInterval":[934,998]},null,[],["alt",{"sourceInterval":[945,998]},["app",{"sourceInterval":[945,952]},"Pred_not",[]],["app",{"sourceInterval":[967,974]},"Pred_lookahead",[]],["app",{"sourceInterval":[995,998]},"Lex",[]]]],"Lex_lex":["define",{"sourceInterval":[1012,1028]},null,[],["seq",{"sourceInterval":[1012,1020]},["terminal",{"sourceInterval":[1012,1015]},"#"],["app",{"sourceInterval":[1016,1020]},"Base",[]]]],"Lex":["define",{"sourceInterval":[1002,1039]},null,[],["alt",{"sourceInterval":[1012,1039]},["app",{"sourceInterval":[1012,1020]},"Lex_lex",[]],["app",{"sourceInterval":[1035,1039]},"Base",[]]]],"Base_application":["define",{"sourceInterval":[1054,1115]},null,[],["seq",{"sourceInterval":[1054,1099]},["app",{"sourceInterval":[1054,1059]},"ident",[]],["opt",{"sourceInterval":[1060,1067]},["app",{"sourceInterval":[1060,1066]},"Params",[]]],["not",{"sourceInterval":[1068,1099]},["alt",{"sourceInterval":[1070,1098]},["seq",{"sourceInterval":[1070,1084]},["opt",{"sourceInterval":[1070,1080]},["app",{"sourceInterval":[1070,1079]},"ruleDescr",[]]],["terminal",{"sourceInterval":[1081,1084]},"="]],["terminal",{"sourceInterval":[1087,1091]},":="],["terminal",{"sourceInterval":[1094,1098]},"+="]]]]],"Base_range":["define",{"sourceInterval":[1122,1177]},null,[],["seq",{"sourceInterval":[1122,1158]},["app",{"sourceInterval":[1122,1137]},"oneCharTerminal",[]],["terminal",{"sourceInterval":[1138,1142]},".."],["app",{"sourceInterval":[1143,1158]},"oneCharTerminal",[]]]],"Base_terminal":["define",{"sourceInterval":[1184,1242]},null,[],["app",{"sourceInterval":[1184,1192]},"terminal",[]]],"Base_paren":["define",{"sourceInterval":[1249,1304]},null,[],["seq",{"sourceInterval":[1249,1260]},["terminal",{"sourceInterval":[1249,1252]},"("],["app",{"sourceInterval":[1253,1256]},"Alt",[]],["terminal",{"sourceInterval":[1257,1260]},")"]]],"Base":["define",{"sourceInterval":[1043,1304]},null,[],["alt",{"sourceInterval":[1054,1304]},["app",{"sourceInterval":[1054,1099]},"Base_application",[]],["app",{"sourceInterval":[1122,1158]},"Base_range",[]],["app",{"sourceInterval":[1184,1192]},"Base_terminal",[]],["app",{"sourceInterval":[1249,1260]},"Base_paren",[]]]],"include":["define",{"sourceInterval":[1308,1347]},null,[],["app",{"sourceInterval":[1321,1347]},"caseInsensitive",[["terminal",{"sourceInterval":[1337,1346]},"include"]]]],"relativeFilePath":["define",{"sourceInterval":[1355,1425]},null,[],["seq",{"sourceInterval":[1378,1425]},["not",{"sourceInterval":[1378,1382]},["terminal",{"sourceInterval":[1379,1382]},"'"]],["plus",{"sourceInterval":[1383,1425]},["alt",{"sourceInterval":[1384,1423]},["app",{"sourceInterval":[1384,1390]},"letter",[]],["app",{"sourceInterval":[1393,1398]},"digit",[]],["terminal",{"sourceInterval":[1401,1404]},"-"],["terminal",{"sourceInterval":[1407,1411]},"\\"],["terminal",{"sourceInterval":[1414,1417]},"/"],["terminal",{"sourceInterval":[1420,1423]},"."]]]]],"ruleDescr":["define",{"sourceInterval":[1430,1489]},"a rule description",[],["seq",{"sourceInterval":[1468,1489]},["terminal",{"sourceInterval":[1468,1471]},"("],["app",{"sourceInterval":[1472,1485]},"ruleDescrText",[]],["terminal",{"sourceInterval":[1486,1489]},")"]]],"ruleDescrText":["define",{"sourceInterval":[1493,1524]},null,[],["star",{"sourceInterval":[1513,1524]},["seq",{"sourceInterval":[1514,1522]},["not",{"sourceInterval":[1514,1518]},["terminal",{"sourceInterval":[1515,1518]},")"]],["app",{"sourceInterval":[1519,1522]},"any",[]]]]],"caseName":["define",{"sourceInterval":[1528,1596]},null,[],["seq",{"sourceInterval":[1543,1596]},["terminal",{"sourceInterval":[1543,1547]},"--"],["star",{"sourceInterval":[1548,1562]},["seq",{"sourceInterval":[1549,1560]},["not",{"sourceInterval":[1549,1554]},["terminal",{"sourceInterval":[1550,1554]},"\n"]],["app",{"sourceInterval":[1555,1560]},"space",[]]]],["app",{"sourceInterval":[1563,1567]},"name",[]],["star",{"sourceInterval":[1568,1582]},["seq",{"sourceInterval":[1569,1580]},["not",{"sourceInterval":[1569,1574]},["terminal",{"sourceInterval":[1570,1574]},"\n"]],["app",{"sourceInterval":[1575,1580]},"space",[]]]],["alt",{"sourceInterval":[1584,1595]},["terminal",{"sourceInterval":[1584,1588]},"\n"],["lookahead",{"sourceInterval":[1591,1595]},["terminal",{"sourceInterval":[1592,1595]},"}"]]]]],"name":["define",{"sourceInterval":[1600,1640]},"a name",[],["seq",{"sourceInterval":[1621,1640]},["app",{"sourceInterval":[1621,1630]},"nameFirst",[]],["star",{"sourceInterval":[1631,1640]},["app",{"sourceInterval":[1631,1639]},"nameRest",[]]]]],"nameFirst":["define",{"sourceInterval":[1644,1676]},null,[],["alt",{"sourceInterval":[1660,1676]},["terminal",{"sourceInterval":[1660,1663]},"_"],["app",{"sourceInterval":[1670,1676]},"letter",[]]]],"nameRest":["define",{"sourceInterval":[1680,1710]},null,[],["alt",{"sourceInterval":[1695,1710]},["terminal",{"sourceInterval":[1695,1698]},"_"],["app",{"sourceInterval":[1705,1710]},"alnum",[]]]],"ident":["define",{"sourceInterval":[1714,1747]},"an identifier",[],["app",{"sourceInterval":[1743,1747]},"name",[]]],"terminal":["define",{"sourceInterval":[1751,1789]},null,[],["seq",{"sourceInterval":[1766,1789]},["terminal",{"sourceInterval":[1766,1770]},"\""],["star",{"sourceInterval":[1771,1784]},["app",{"sourceInterval":[1771,1783]},"terminalChar",[]]],["terminal",{"sourceInterval":[1785,1789]},"\""]]],"oneCharTerminal":["define",{"sourceInterval":[1793,1837]},null,[],["seq",{"sourceInterval":[1815,1837]},["terminal",{"sourceInterval":[1815,1819]},"\""],["app",{"sourceInterval":[1820,1832]},"terminalChar",[]],["terminal",{"sourceInterval":[1833,1837]},"\""]]],"terminalChar":["define",{"sourceInterval":[1841,1918]},null,[],["alt",{"sourceInterval":[1860,1918]},["app",{"sourceInterval":[1860,1870]},"escapeChar",[]],["seq",{"sourceInterval":[1879,1918]},["not",{"sourceInterval":[1879,1884]},["terminal",{"sourceInterval":[1880,1884]},"\\"]],["not",{"sourceInterval":[1885,1890]},["terminal",{"sourceInterval":[1886,1890]},"\""]],["not",{"sourceInterval":[1891,1896]},["terminal",{"sourceInterval":[1892,1896]},"\n"]],["range",{"sourceInterval":[1897,1918]},"\u0000","􏿿"]]]],"escapeChar_backslash":["define",{"sourceInterval":[1961,2016]},null,[],["terminal",{"sourceInterval":[1961,1967]},"\\\\"]],"escapeChar_doubleQuote":["define",{"sourceInterval":[2023,2080]},null,[],["terminal",{"sourceInterval":[2023,2029]},"\\\""]],"escapeChar_singleQuote":["define",{"sourceInterval":[2087,2144]},null,[],["terminal",{"sourceInterval":[2087,2093]},"\\'"]],"escapeChar_backspace":["define",{"sourceInterval":[2151,2206]},null,[],["terminal",{"sourceInterval":[2151,2156]},"\\b"]],"escapeChar_lineFeed":["define",{"sourceInterval":[2213,2267]},null,[],["terminal",{"sourceInterval":[2213,2218]},"\\n"]],"escapeChar_carriageReturn":["define",{"sourceInterval":[2274,2334]},null,[],["terminal",{"sourceInterval":[2274,2279]},"\\r"]],"escapeChar_tab":["define",{"sourceInterval":[2341,2390]},null,[],["terminal",{"sourceInterval":[2341,2346]},"\\t"]],"escapeChar_unicodeCodePoint":["define",{"sourceInterval":[2397,2501]},null,[],["seq",{"sourceInterval":[2397,2479]},["terminal",{"sourceInterval":[2397,2403]},"\\u{"],["app",{"sourceInterval":[2404,2412]},"hexDigit",[]],["opt",{"sourceInterval":[2413,2422]},["app",{"sourceInterval":[2413,2421]},"hexDigit",[]]],["opt",{"sourceInterval":[2423,2432]},["app",{"sourceInterval":[2423,2431]},"hexDigit",[]]],["opt",{"sourceInterval":[2446,2455]},["app",{"sourceInterval":[2446,2454]},"hexDigit",[]]],["opt",{"sourceInterval":[2456,2465]},["app",{"sourceInterval":[2456,2464]},"hexDigit",[]]],["opt",{"sourceInterval":[2466,2475]},["app",{"sourceInterval":[2466,2474]},"hexDigit",[]]],["terminal",{"sourceInterval":[2476,2479]},"}"]]],"escapeChar_unicodeEscape":["define",{"sourceInterval":[2508,2567]},null,[],["seq",{"sourceInterval":[2508,2549]},["terminal",{"sourceInterval":[2508,2513]},"\\u"],["app",{"sourceInterval":[2514,2522]},"hexDigit",[]],["app",{"sourceInterval":[2523,2531]},"hexDigit",[]],["app",{"sourceInterval":[2532,2540]},"hexDigit",[]],["app",{"sourceInterval":[2541,2549]},"hexDigit",[]]]],"escapeChar_hexEscape":["define",{"sourceInterval":[2574,2629]},null,[],["seq",{"sourceInterval":[2574,2597]},["terminal",{"sourceInterval":[2574,2579]},"\\x"],["app",{"sourceInterval":[2580,2588]},"hexDigit",[]],["app",{"sourceInterval":[2589,2597]},"hexDigit",[]]]],"escapeChar":["define",{"sourceInterval":[1922,2629]},"an escape sequence",[],["alt",{"sourceInterval":[1961,2629]},["app",{"sourceInterval":[1961,1967]},"escapeChar_backslash",[]],["app",{"sourceInterval":[2023,2029]},"escapeChar_doubleQuote",[]],["app",{"sourceInterval":[2087,2093]},"escapeChar_singleQuote",[]],["app",{"sourceInterval":[2151,2156]},"escapeChar_backspace",[]],["app",{"sourceInterval":[2213,2218]},"escapeChar_lineFeed",[]],["app",{"sourceInterval":[2274,2279]},"escapeChar_carriageReturn",[]],["app",{"sourceInterval":[2341,2346]},"escapeChar_tab",[]],["app",{"sourceInterval":[2397,2479]},"escapeChar_unicodeCodePoint",[]],["app",{"sourceInterval":[2508,2549]},"escapeChar_unicodeEscape",[]],["app",{"sourceInterval":[2574,2597]},"escapeChar_hexEscape",[]]]],"space":["extend",{"sourceInterval":[2633,2652]},null,[],["app",{"sourceInterval":[2645,2652]},"comment",[]]],"comment_singleLine":["define",{"sourceInterval":[2670,2716]},null,[],["seq",{"sourceInterval":[2670,2701]},["terminal",{"sourceInterval":[2670,2674]},"//"],["star",{"sourceInterval":[2675,2687]},["seq",{"sourceInterval":[2676,2685]},["not",{"sourceInterval":[2676,2681]},["terminal",{"sourceInterval":[2677,2681]},"\n"]],["app",{"sourceInterval":[2682,2685]},"any",[]]]],["lookahead",{"sourceInterval":[2688,2701]},["alt",{"sourceInterval":[2690,2700]},["terminal",{"sourceInterval":[2690,2694]},"\n"],["app",{"sourceInterval":[2697,2700]},"end",[]]]]]],"comment_multiLine":["define",{"sourceInterval":[2723,2759]},null,[],["seq",{"sourceInterval":[2723,2745]},["terminal",{"sourceInterval":[2723,2727]},"/*"],["star",{"sourceInterval":[2728,2740]},["seq",{"sourceInterval":[2729,2738]},["not",{"sourceInterval":[2729,2734]},["terminal",{"sourceInterval":[2730,2734]},"*/"]],["app",{"sourceInterval":[2735,2738]},"any",[]]]],["terminal",{"sourceInterval":[2741,2745]},"*/"]]],"comment":["define",{"sourceInterval":[2656,2759]},null,[],["alt",{"sourceInterval":[2670,2759]},["app",{"sourceInterval":[2670,2701]},"comment_singleLine",[]],["app",{"sourceInterval":[2723,2745]},"comment_multiLine",[]]]],"tokens":["define",{"sourceInterval":[2763,2778]},null,[],["star",{"sourceInterval":[2772,2778]},["app",{"sourceInterval":[2772,2777]},"token",[]]]],"token":["define",{"sourceInterval":[2782,2858]},null,[],["alt",{"sourceInterval":[2790,2858]},["app",{"sourceInterval":[2790,2798]},"caseName",[]],["app",{"sourceInterval":[2801,2808]},"comment",[]],["app",{"sourceInterval":[2811,2816]},"ident",[]],["app",{"sourceInterval":[2819,2827]},"operator",[]],["app",{"sourceInterval":[2830,2841]},"punctuation",[]],["app",{"sourceInterval":[2844,2852]},"terminal",[]],["app",{"sourceInterval":[2855,2858]},"any",[]]]],"operator":["define",{"sourceInterval":[2862,2927]},null,[],["alt",{"sourceInterval":[2873,2927]},["terminal",{"sourceInterval":[2873,2877]},"<:"],["terminal",{"sourceInterval":[2880,2883]},"="],["terminal",{"sourceInterval":[2886,2890]},":="],["terminal",{"sourceInterval":[2893,2897]},"+="],["terminal",{"sourceInterval":[2900,2903]},"*"],["terminal",{"sourceInterval":[2906,2909]},"+"],["terminal",{"sourceInterval":[2912,2915]},"?"],["terminal",{"sourceInterval":[2918,2921]},"~"],["terminal",{"sourceInterval":[2924,2927]},"&"]]],"punctuation":["define",{"sourceInterval":[2931,2967]},null,[],["alt",{"sourceInterval":[2945,2967]},["terminal",{"sourceInterval":[2945,2948]},"<"],["terminal",{"sourceInterval":[2951,2954]},">"],["terminal",{"sourceInterval":[2957,2960]},","],["terminal",{"sourceInterval":[2963,2967]},"--"]]]}]); +export default makeRecipe(["grammar",{"source":"Ohm {\n\n Document\n = Includes Grammars\n\n Includes\n = Include*\n \n Include\n = include \"'\" relativeFilePath \"'\"\n\n Grammars\n = Grammar*\n\n Grammar\n = ident SuperGrammar? \"{\" Rule* \"}\"\n\n SuperGrammar\n = \"<:\" ident\n\n Rule\n = ident Formals? ruleDescr? \"=\" RuleBody -- define\n | ident Formals? \":=\" OverrideRuleBody -- override\n | ident Formals? \"+=\" RuleBody -- extend\n\n RuleBody\n = \"|\"? NonemptyListOf\n\n TopLevelTerm\n = Seq caseName -- inline\n | Seq\n\n OverrideRuleBody\n = \"|\"? NonemptyListOf\n\n OverrideTopLevelTerm\n = \"...\" -- superSplice\n | TopLevelTerm\n\n Formals\n = \"<\" ListOf \">\"\n\n Params\n = \"<\" ListOf \">\"\n\n Alt\n = NonemptyListOf\n\n Seq\n = Iter*\n\n Iter\n = Pred \"*\" -- star\n | Pred \"+\" -- plus\n | Pred \"?\" -- opt\n | Pred\n\n Pred\n = \"~\" Lex -- not\n | \"&\" Lex -- lookahead\n | Lex\n\n Lex\n = \"#\" Base -- lex\n | Base\n\n Base\n = ident Params? ~(ruleDescr? \"=\" | \":=\" | \"+=\") -- application\n | oneCharTerminal \"..\" oneCharTerminal -- range\n | terminal -- terminal\n | \"(\" Alt \")\" -- paren\n\n include\n \t= \"include\"\n \n relativeFilePath \n \t= ~\"'\" (letter | digit | \"-\" | \"\\\\\" | \"/\" | \".\")+ \n\n ruleDescr (a rule description)\n = \"(\" ruleDescrText \")\"\n\n ruleDescrText\n = (~\")\" any)*\n\n caseName\n = \"--\" (~\"\\n\" space)* name (~\"\\n\" space)* (\"\\n\" | &\"}\")\n\n name (a name)\n = nameFirst nameRest*\n\n nameFirst\n = \"_\"\n | letter\n\n nameRest\n = \"_\"\n | alnum\n\n ident (an identifier)\n = name\n\n terminal\n = \"\\\"\" terminalChar* \"\\\"\"\n\n oneCharTerminal\n = \"\\\"\" terminalChar \"\\\"\"\n\n terminalChar\n = escapeChar\n | ~\"\\\\\" ~\"\\\"\" ~\"\\n\" \"\\u{0}\"..\"\\u{10FFFF}\"\n\n escapeChar (an escape sequence)\n = \"\\\\\\\\\" -- backslash\n | \"\\\\\\\"\" -- doubleQuote\n | \"\\\\\\'\" -- singleQuote\n | \"\\\\b\" -- backspace\n | \"\\\\n\" -- lineFeed\n | \"\\\\r\" -- carriageReturn\n | \"\\\\t\" -- tab\n | \"\\\\u{\" hexDigit hexDigit? hexDigit?\n hexDigit? hexDigit? hexDigit? \"}\" -- unicodeCodePoint\n | \"\\\\u\" hexDigit hexDigit hexDigit hexDigit -- unicodeEscape\n | \"\\\\x\" hexDigit hexDigit -- hexEscape\n\n space\n += comment\n\n comment\n = \"//\" (~\"\\n\" any)* &(\"\\n\" | end) -- singleLine\n | \"/*\" (~\"*/\" any)* \"*/\" -- multiLine\n\n tokens = token*\n\n token = caseName | comment | ident | operator | punctuation | terminal | any\n\n operator = \"<:\" | \"=\" | \":=\" | \"+=\" | \"*\" | \"+\" | \"?\" | \"~\" | \"&\"\n\n punctuation = \"<\" | \">\" | \",\" | \"--\"\n}"},"Ohm",null,"Document",{"Document":["define",{"sourceInterval":[9,41]},null,[],["seq",{"sourceInterval":[24,41]},["app",{"sourceInterval":[24,32]},"Includes",[]],["app",{"sourceInterval":[33,41]},"Grammars",[]]]],"Includes":["define",{"sourceInterval":[45,68]},null,[],["star",{"sourceInterval":[60,68]},["app",{"sourceInterval":[60,67]},"Include",[]]]],"Include":["define",{"sourceInterval":[74,122]},null,[],["seq",{"sourceInterval":[90,122]},["app",{"sourceInterval":[90,97]},"include",[]],["terminal",{"sourceInterval":[98,101]},"'"],["app",{"sourceInterval":[102,118]},"relativeFilePath",[]],["terminal",{"sourceInterval":[119,122]},"'"]]],"Grammars":["define",{"sourceInterval":[126,149]},null,[],["star",{"sourceInterval":[141,149]},["app",{"sourceInterval":[141,148]},"Grammar",[]]]],"Grammar":["define",{"sourceInterval":[153,200]},null,[],["seq",{"sourceInterval":[167,200]},["app",{"sourceInterval":[167,172]},"ident",[]],["opt",{"sourceInterval":[173,186]},["app",{"sourceInterval":[173,185]},"SuperGrammar",[]]],["terminal",{"sourceInterval":[187,190]},"{"],["star",{"sourceInterval":[191,196]},["app",{"sourceInterval":[191,195]},"Rule",[]]],["terminal",{"sourceInterval":[197,200]},"}"]]],"SuperGrammar":["define",{"sourceInterval":[204,233]},null,[],["seq",{"sourceInterval":[223,233]},["terminal",{"sourceInterval":[223,227]},"<:"],["app",{"sourceInterval":[228,233]},"ident",[]]]],"Rule_define":["define",{"sourceInterval":[248,298]},null,[],["seq",{"sourceInterval":[248,287]},["app",{"sourceInterval":[248,253]},"ident",[]],["opt",{"sourceInterval":[254,262]},["app",{"sourceInterval":[254,261]},"Formals",[]]],["opt",{"sourceInterval":[263,273]},["app",{"sourceInterval":[263,272]},"ruleDescr",[]]],["terminal",{"sourceInterval":[274,277]},"="],["app",{"sourceInterval":[279,287]},"RuleBody",[]]]],"Rule_override":["define",{"sourceInterval":[305,365]},null,[],["seq",{"sourceInterval":[305,352]},["app",{"sourceInterval":[305,310]},"ident",[]],["opt",{"sourceInterval":[311,319]},["app",{"sourceInterval":[311,318]},"Formals",[]]],["terminal",{"sourceInterval":[331,335]},":="],["app",{"sourceInterval":[336,352]},"OverrideRuleBody",[]]]],"Rule_extend":["define",{"sourceInterval":[372,422]},null,[],["seq",{"sourceInterval":[372,411]},["app",{"sourceInterval":[372,377]},"ident",[]],["opt",{"sourceInterval":[378,386]},["app",{"sourceInterval":[378,385]},"Formals",[]]],["terminal",{"sourceInterval":[398,402]},"+="],["app",{"sourceInterval":[403,411]},"RuleBody",[]]]],"Rule":["define",{"sourceInterval":[237,422]},null,[],["alt",{"sourceInterval":[248,422]},["app",{"sourceInterval":[248,287]},"Rule_define",[]],["app",{"sourceInterval":[305,352]},"Rule_override",[]],["app",{"sourceInterval":[372,411]},"Rule_extend",[]]]],"RuleBody":["define",{"sourceInterval":[426,479]},null,[],["seq",{"sourceInterval":[441,479]},["opt",{"sourceInterval":[441,445]},["terminal",{"sourceInterval":[441,444]},"|"]],["app",{"sourceInterval":[446,479]},"NonemptyListOf",[["app",{"sourceInterval":[461,473]},"TopLevelTerm",[]],["terminal",{"sourceInterval":[475,478]},"|"]]]]],"TopLevelTerm_inline":["define",{"sourceInterval":[502,525]},null,[],["seq",{"sourceInterval":[502,514]},["app",{"sourceInterval":[502,505]},"Seq",[]],["app",{"sourceInterval":[506,514]},"caseName",[]]]],"TopLevelTerm":["define",{"sourceInterval":[483,535]},null,[],["alt",{"sourceInterval":[502,535]},["app",{"sourceInterval":[502,514]},"TopLevelTerm_inline",[]],["app",{"sourceInterval":[532,535]},"Seq",[]]]],"OverrideRuleBody":["define",{"sourceInterval":[539,608]},null,[],["seq",{"sourceInterval":[562,608]},["opt",{"sourceInterval":[562,566]},["terminal",{"sourceInterval":[562,565]},"|"]],["app",{"sourceInterval":[567,608]},"NonemptyListOf",[["app",{"sourceInterval":[582,602]},"OverrideTopLevelTerm",[]],["terminal",{"sourceInterval":[604,607]},"|"]]]]],"OverrideTopLevelTerm_superSplice":["define",{"sourceInterval":[639,660]},null,[],["terminal",{"sourceInterval":[639,644]},"..."]],"OverrideTopLevelTerm":["define",{"sourceInterval":[612,679]},null,[],["alt",{"sourceInterval":[639,679]},["app",{"sourceInterval":[639,644]},"OverrideTopLevelTerm_superSplice",[]],["app",{"sourceInterval":[667,679]},"TopLevelTerm",[]]]],"Formals":["define",{"sourceInterval":[683,723]},null,[],["seq",{"sourceInterval":[697,723]},["terminal",{"sourceInterval":[697,700]},"<"],["app",{"sourceInterval":[701,719]},"ListOf",[["app",{"sourceInterval":[708,713]},"ident",[]],["terminal",{"sourceInterval":[715,718]},","]]],["terminal",{"sourceInterval":[720,723]},">"]]],"Params":["define",{"sourceInterval":[727,764]},null,[],["seq",{"sourceInterval":[740,764]},["terminal",{"sourceInterval":[740,743]},"<"],["app",{"sourceInterval":[744,760]},"ListOf",[["app",{"sourceInterval":[751,754]},"Seq",[]],["terminal",{"sourceInterval":[756,759]},","]]],["terminal",{"sourceInterval":[761,764]},">"]]],"Alt":["define",{"sourceInterval":[768,802]},null,[],["app",{"sourceInterval":[778,802]},"NonemptyListOf",[["app",{"sourceInterval":[793,796]},"Seq",[]],["terminal",{"sourceInterval":[798,801]},"|"]]]],"Seq":["define",{"sourceInterval":[806,821]},null,[],["star",{"sourceInterval":[816,821]},["app",{"sourceInterval":[816,820]},"Iter",[]]]],"Iter_star":["define",{"sourceInterval":[836,853]},null,[],["seq",{"sourceInterval":[836,844]},["app",{"sourceInterval":[836,840]},"Pred",[]],["terminal",{"sourceInterval":[841,844]},"*"]]],"Iter_plus":["define",{"sourceInterval":[860,877]},null,[],["seq",{"sourceInterval":[860,868]},["app",{"sourceInterval":[860,864]},"Pred",[]],["terminal",{"sourceInterval":[865,868]},"+"]]],"Iter_opt":["define",{"sourceInterval":[884,900]},null,[],["seq",{"sourceInterval":[884,892]},["app",{"sourceInterval":[884,888]},"Pred",[]],["terminal",{"sourceInterval":[889,892]},"?"]]],"Iter":["define",{"sourceInterval":[825,911]},null,[],["alt",{"sourceInterval":[836,911]},["app",{"sourceInterval":[836,844]},"Iter_star",[]],["app",{"sourceInterval":[860,868]},"Iter_plus",[]],["app",{"sourceInterval":[884,892]},"Iter_opt",[]],["app",{"sourceInterval":[907,911]},"Pred",[]]]],"Pred_not":["define",{"sourceInterval":[926,941]},null,[],["seq",{"sourceInterval":[926,933]},["terminal",{"sourceInterval":[926,929]},"~"],["app",{"sourceInterval":[930,933]},"Lex",[]]]],"Pred_lookahead":["define",{"sourceInterval":[948,969]},null,[],["seq",{"sourceInterval":[948,955]},["terminal",{"sourceInterval":[948,951]},"&"],["app",{"sourceInterval":[952,955]},"Lex",[]]]],"Pred":["define",{"sourceInterval":[915,979]},null,[],["alt",{"sourceInterval":[926,979]},["app",{"sourceInterval":[926,933]},"Pred_not",[]],["app",{"sourceInterval":[948,955]},"Pred_lookahead",[]],["app",{"sourceInterval":[976,979]},"Lex",[]]]],"Lex_lex":["define",{"sourceInterval":[993,1009]},null,[],["seq",{"sourceInterval":[993,1001]},["terminal",{"sourceInterval":[993,996]},"#"],["app",{"sourceInterval":[997,1001]},"Base",[]]]],"Lex":["define",{"sourceInterval":[983,1020]},null,[],["alt",{"sourceInterval":[993,1020]},["app",{"sourceInterval":[993,1001]},"Lex_lex",[]],["app",{"sourceInterval":[1016,1020]},"Base",[]]]],"Base_application":["define",{"sourceInterval":[1035,1096]},null,[],["seq",{"sourceInterval":[1035,1080]},["app",{"sourceInterval":[1035,1040]},"ident",[]],["opt",{"sourceInterval":[1041,1048]},["app",{"sourceInterval":[1041,1047]},"Params",[]]],["not",{"sourceInterval":[1049,1080]},["alt",{"sourceInterval":[1051,1079]},["seq",{"sourceInterval":[1051,1065]},["opt",{"sourceInterval":[1051,1061]},["app",{"sourceInterval":[1051,1060]},"ruleDescr",[]]],["terminal",{"sourceInterval":[1062,1065]},"="]],["terminal",{"sourceInterval":[1068,1072]},":="],["terminal",{"sourceInterval":[1075,1079]},"+="]]]]],"Base_range":["define",{"sourceInterval":[1103,1158]},null,[],["seq",{"sourceInterval":[1103,1139]},["app",{"sourceInterval":[1103,1118]},"oneCharTerminal",[]],["terminal",{"sourceInterval":[1119,1123]},".."],["app",{"sourceInterval":[1124,1139]},"oneCharTerminal",[]]]],"Base_terminal":["define",{"sourceInterval":[1165,1223]},null,[],["app",{"sourceInterval":[1165,1173]},"terminal",[]]],"Base_paren":["define",{"sourceInterval":[1230,1285]},null,[],["seq",{"sourceInterval":[1230,1241]},["terminal",{"sourceInterval":[1230,1233]},"("],["app",{"sourceInterval":[1234,1237]},"Alt",[]],["terminal",{"sourceInterval":[1238,1241]},")"]]],"Base":["define",{"sourceInterval":[1024,1285]},null,[],["alt",{"sourceInterval":[1035,1285]},["app",{"sourceInterval":[1035,1080]},"Base_application",[]],["app",{"sourceInterval":[1103,1139]},"Base_range",[]],["app",{"sourceInterval":[1165,1173]},"Base_terminal",[]],["app",{"sourceInterval":[1230,1241]},"Base_paren",[]]]],"include":["define",{"sourceInterval":[1289,1311]},null,[],["terminal",{"sourceInterval":[1302,1311]},"include"]],"relativeFilePath":["define",{"sourceInterval":[1319,1389]},null,[],["seq",{"sourceInterval":[1342,1389]},["not",{"sourceInterval":[1342,1346]},["terminal",{"sourceInterval":[1343,1346]},"'"]],["plus",{"sourceInterval":[1347,1389]},["alt",{"sourceInterval":[1348,1387]},["app",{"sourceInterval":[1348,1354]},"letter",[]],["app",{"sourceInterval":[1357,1362]},"digit",[]],["terminal",{"sourceInterval":[1365,1368]},"-"],["terminal",{"sourceInterval":[1371,1375]},"\\"],["terminal",{"sourceInterval":[1378,1381]},"/"],["terminal",{"sourceInterval":[1384,1387]},"."]]]]],"ruleDescr":["define",{"sourceInterval":[1394,1453]},"a rule description",[],["seq",{"sourceInterval":[1432,1453]},["terminal",{"sourceInterval":[1432,1435]},"("],["app",{"sourceInterval":[1436,1449]},"ruleDescrText",[]],["terminal",{"sourceInterval":[1450,1453]},")"]]],"ruleDescrText":["define",{"sourceInterval":[1457,1488]},null,[],["star",{"sourceInterval":[1477,1488]},["seq",{"sourceInterval":[1478,1486]},["not",{"sourceInterval":[1478,1482]},["terminal",{"sourceInterval":[1479,1482]},")"]],["app",{"sourceInterval":[1483,1486]},"any",[]]]]],"caseName":["define",{"sourceInterval":[1492,1560]},null,[],["seq",{"sourceInterval":[1507,1560]},["terminal",{"sourceInterval":[1507,1511]},"--"],["star",{"sourceInterval":[1512,1526]},["seq",{"sourceInterval":[1513,1524]},["not",{"sourceInterval":[1513,1518]},["terminal",{"sourceInterval":[1514,1518]},"\n"]],["app",{"sourceInterval":[1519,1524]},"space",[]]]],["app",{"sourceInterval":[1527,1531]},"name",[]],["star",{"sourceInterval":[1532,1546]},["seq",{"sourceInterval":[1533,1544]},["not",{"sourceInterval":[1533,1538]},["terminal",{"sourceInterval":[1534,1538]},"\n"]],["app",{"sourceInterval":[1539,1544]},"space",[]]]],["alt",{"sourceInterval":[1548,1559]},["terminal",{"sourceInterval":[1548,1552]},"\n"],["lookahead",{"sourceInterval":[1555,1559]},["terminal",{"sourceInterval":[1556,1559]},"}"]]]]],"name":["define",{"sourceInterval":[1564,1604]},"a name",[],["seq",{"sourceInterval":[1585,1604]},["app",{"sourceInterval":[1585,1594]},"nameFirst",[]],["star",{"sourceInterval":[1595,1604]},["app",{"sourceInterval":[1595,1603]},"nameRest",[]]]]],"nameFirst":["define",{"sourceInterval":[1608,1640]},null,[],["alt",{"sourceInterval":[1624,1640]},["terminal",{"sourceInterval":[1624,1627]},"_"],["app",{"sourceInterval":[1634,1640]},"letter",[]]]],"nameRest":["define",{"sourceInterval":[1644,1674]},null,[],["alt",{"sourceInterval":[1659,1674]},["terminal",{"sourceInterval":[1659,1662]},"_"],["app",{"sourceInterval":[1669,1674]},"alnum",[]]]],"ident":["define",{"sourceInterval":[1678,1711]},"an identifier",[],["app",{"sourceInterval":[1707,1711]},"name",[]]],"terminal":["define",{"sourceInterval":[1715,1753]},null,[],["seq",{"sourceInterval":[1730,1753]},["terminal",{"sourceInterval":[1730,1734]},"\""],["star",{"sourceInterval":[1735,1748]},["app",{"sourceInterval":[1735,1747]},"terminalChar",[]]],["terminal",{"sourceInterval":[1749,1753]},"\""]]],"oneCharTerminal":["define",{"sourceInterval":[1757,1801]},null,[],["seq",{"sourceInterval":[1779,1801]},["terminal",{"sourceInterval":[1779,1783]},"\""],["app",{"sourceInterval":[1784,1796]},"terminalChar",[]],["terminal",{"sourceInterval":[1797,1801]},"\""]]],"terminalChar":["define",{"sourceInterval":[1805,1882]},null,[],["alt",{"sourceInterval":[1824,1882]},["app",{"sourceInterval":[1824,1834]},"escapeChar",[]],["seq",{"sourceInterval":[1843,1882]},["not",{"sourceInterval":[1843,1848]},["terminal",{"sourceInterval":[1844,1848]},"\\"]],["not",{"sourceInterval":[1849,1854]},["terminal",{"sourceInterval":[1850,1854]},"\""]],["not",{"sourceInterval":[1855,1860]},["terminal",{"sourceInterval":[1856,1860]},"\n"]],["range",{"sourceInterval":[1861,1882]},"\u0000","􏿿"]]]],"escapeChar_backslash":["define",{"sourceInterval":[1925,1980]},null,[],["terminal",{"sourceInterval":[1925,1931]},"\\\\"]],"escapeChar_doubleQuote":["define",{"sourceInterval":[1987,2044]},null,[],["terminal",{"sourceInterval":[1987,1993]},"\\\""]],"escapeChar_singleQuote":["define",{"sourceInterval":[2051,2108]},null,[],["terminal",{"sourceInterval":[2051,2057]},"\\'"]],"escapeChar_backspace":["define",{"sourceInterval":[2115,2170]},null,[],["terminal",{"sourceInterval":[2115,2120]},"\\b"]],"escapeChar_lineFeed":["define",{"sourceInterval":[2177,2231]},null,[],["terminal",{"sourceInterval":[2177,2182]},"\\n"]],"escapeChar_carriageReturn":["define",{"sourceInterval":[2238,2298]},null,[],["terminal",{"sourceInterval":[2238,2243]},"\\r"]],"escapeChar_tab":["define",{"sourceInterval":[2305,2354]},null,[],["terminal",{"sourceInterval":[2305,2310]},"\\t"]],"escapeChar_unicodeCodePoint":["define",{"sourceInterval":[2361,2465]},null,[],["seq",{"sourceInterval":[2361,2443]},["terminal",{"sourceInterval":[2361,2367]},"\\u{"],["app",{"sourceInterval":[2368,2376]},"hexDigit",[]],["opt",{"sourceInterval":[2377,2386]},["app",{"sourceInterval":[2377,2385]},"hexDigit",[]]],["opt",{"sourceInterval":[2387,2396]},["app",{"sourceInterval":[2387,2395]},"hexDigit",[]]],["opt",{"sourceInterval":[2410,2419]},["app",{"sourceInterval":[2410,2418]},"hexDigit",[]]],["opt",{"sourceInterval":[2420,2429]},["app",{"sourceInterval":[2420,2428]},"hexDigit",[]]],["opt",{"sourceInterval":[2430,2439]},["app",{"sourceInterval":[2430,2438]},"hexDigit",[]]],["terminal",{"sourceInterval":[2440,2443]},"}"]]],"escapeChar_unicodeEscape":["define",{"sourceInterval":[2472,2531]},null,[],["seq",{"sourceInterval":[2472,2513]},["terminal",{"sourceInterval":[2472,2477]},"\\u"],["app",{"sourceInterval":[2478,2486]},"hexDigit",[]],["app",{"sourceInterval":[2487,2495]},"hexDigit",[]],["app",{"sourceInterval":[2496,2504]},"hexDigit",[]],["app",{"sourceInterval":[2505,2513]},"hexDigit",[]]]],"escapeChar_hexEscape":["define",{"sourceInterval":[2538,2593]},null,[],["seq",{"sourceInterval":[2538,2561]},["terminal",{"sourceInterval":[2538,2543]},"\\x"],["app",{"sourceInterval":[2544,2552]},"hexDigit",[]],["app",{"sourceInterval":[2553,2561]},"hexDigit",[]]]],"escapeChar":["define",{"sourceInterval":[1886,2593]},"an escape sequence",[],["alt",{"sourceInterval":[1925,2593]},["app",{"sourceInterval":[1925,1931]},"escapeChar_backslash",[]],["app",{"sourceInterval":[1987,1993]},"escapeChar_doubleQuote",[]],["app",{"sourceInterval":[2051,2057]},"escapeChar_singleQuote",[]],["app",{"sourceInterval":[2115,2120]},"escapeChar_backspace",[]],["app",{"sourceInterval":[2177,2182]},"escapeChar_lineFeed",[]],["app",{"sourceInterval":[2238,2243]},"escapeChar_carriageReturn",[]],["app",{"sourceInterval":[2305,2310]},"escapeChar_tab",[]],["app",{"sourceInterval":[2361,2443]},"escapeChar_unicodeCodePoint",[]],["app",{"sourceInterval":[2472,2513]},"escapeChar_unicodeEscape",[]],["app",{"sourceInterval":[2538,2561]},"escapeChar_hexEscape",[]]]],"space":["extend",{"sourceInterval":[2597,2616]},null,[],["app",{"sourceInterval":[2609,2616]},"comment",[]]],"comment_singleLine":["define",{"sourceInterval":[2634,2680]},null,[],["seq",{"sourceInterval":[2634,2665]},["terminal",{"sourceInterval":[2634,2638]},"//"],["star",{"sourceInterval":[2639,2651]},["seq",{"sourceInterval":[2640,2649]},["not",{"sourceInterval":[2640,2645]},["terminal",{"sourceInterval":[2641,2645]},"\n"]],["app",{"sourceInterval":[2646,2649]},"any",[]]]],["lookahead",{"sourceInterval":[2652,2665]},["alt",{"sourceInterval":[2654,2664]},["terminal",{"sourceInterval":[2654,2658]},"\n"],["app",{"sourceInterval":[2661,2664]},"end",[]]]]]],"comment_multiLine":["define",{"sourceInterval":[2687,2723]},null,[],["seq",{"sourceInterval":[2687,2709]},["terminal",{"sourceInterval":[2687,2691]},"/*"],["star",{"sourceInterval":[2692,2704]},["seq",{"sourceInterval":[2693,2702]},["not",{"sourceInterval":[2693,2698]},["terminal",{"sourceInterval":[2694,2698]},"*/"]],["app",{"sourceInterval":[2699,2702]},"any",[]]]],["terminal",{"sourceInterval":[2705,2709]},"*/"]]],"comment":["define",{"sourceInterval":[2620,2723]},null,[],["alt",{"sourceInterval":[2634,2723]},["app",{"sourceInterval":[2634,2665]},"comment_singleLine",[]],["app",{"sourceInterval":[2687,2709]},"comment_multiLine",[]]]],"tokens":["define",{"sourceInterval":[2727,2742]},null,[],["star",{"sourceInterval":[2736,2742]},["app",{"sourceInterval":[2736,2741]},"token",[]]]],"token":["define",{"sourceInterval":[2746,2822]},null,[],["alt",{"sourceInterval":[2754,2822]},["app",{"sourceInterval":[2754,2762]},"caseName",[]],["app",{"sourceInterval":[2765,2772]},"comment",[]],["app",{"sourceInterval":[2775,2780]},"ident",[]],["app",{"sourceInterval":[2783,2791]},"operator",[]],["app",{"sourceInterval":[2794,2805]},"punctuation",[]],["app",{"sourceInterval":[2808,2816]},"terminal",[]],["app",{"sourceInterval":[2819,2822]},"any",[]]]],"operator":["define",{"sourceInterval":[2826,2891]},null,[],["alt",{"sourceInterval":[2837,2891]},["terminal",{"sourceInterval":[2837,2841]},"<:"],["terminal",{"sourceInterval":[2844,2847]},"="],["terminal",{"sourceInterval":[2850,2854]},":="],["terminal",{"sourceInterval":[2857,2861]},"+="],["terminal",{"sourceInterval":[2864,2867]},"*"],["terminal",{"sourceInterval":[2870,2873]},"+"],["terminal",{"sourceInterval":[2876,2879]},"?"],["terminal",{"sourceInterval":[2882,2885]},"~"],["terminal",{"sourceInterval":[2888,2891]},"&"]]],"punctuation":["define",{"sourceInterval":[2895,2931]},null,[],["alt",{"sourceInterval":[2909,2931]},["terminal",{"sourceInterval":[2909,2912]},"<"],["terminal",{"sourceInterval":[2915,2918]},">"],["terminal",{"sourceInterval":[2921,2924]},","],["terminal",{"sourceInterval":[2927,2931]},"--"]]]}]); From 63ab3c6c048e3c21f50135f5375c6ae0dcd3675c Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Fri, 18 Aug 2023 22:54:37 +0000 Subject: [PATCH 18/20] Fixed tests due to `Document` changes --- packages/ohm-js/src/ohm-grammar.ohm | 2 +- packages/ohm-js/test/test-ohm-syntax.js | 14 +++++++------- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/packages/ohm-js/src/ohm-grammar.ohm b/packages/ohm-js/src/ohm-grammar.ohm index 81492368..53a389e2 100644 --- a/packages/ohm-js/src/ohm-grammar.ohm +++ b/packages/ohm-js/src/ohm-grammar.ohm @@ -136,4 +136,4 @@ Ohm { operator = "<:" | "=" | ":=" | "+=" | "*" | "+" | "?" | "~" | "&" punctuation = "<" | ">" | "," | "--" -} +} \ No newline at end of file diff --git a/packages/ohm-js/test/test-ohm-syntax.js b/packages/ohm-js/test/test-ohm-syntax.js index e7a88792..b78aca90 100644 --- a/packages/ohm-js/test/test-ohm-syntax.js +++ b/packages/ohm-js/test/test-ohm-syntax.js @@ -1390,14 +1390,14 @@ describe('bootstrap', test => { }); test('it can produce a grammar that works', t => { - const g = buildGrammar(ns.Ohm.match(ohmGrammarSource), ns.Ohm, {}); + const g = buildGrammar(ns.Ohm.match(ohmGrammarSource), {}, {}, ns.Ohm); assertSucceeds( t, - g.match(ohmGrammarSource), + g[0].match(ohmGrammarSource), 'Ohm grammar can recognize itself', ); - const Arithmetic = buildGrammar(g.match(arithmeticGrammarSource), {}, {}, g); - const s = Arithmetic.createSemantics().addAttribute('v', { + const Arithmetic = buildGrammar(g[0].match(arithmeticGrammarSource), {}, {}, g[0]); + const s = Arithmetic[0].createSemantics().addAttribute('v', { exp(expr) { return expr.v; }, @@ -1438,12 +1438,12 @@ describe('bootstrap', test => { return this.sourceString; }, }); - t.is(s(Arithmetic.match('10*(2+123)-4/5')).v, 1249.2); + t.is(s(Arithmetic[0].match('10*(2+123)-4/5')).v, 1249.2); }); test('full bootstrap!', t => { - const g = buildGrammar(ns.Ohm.match(ohmGrammarSource, 'Document'), {}, ns.Ohm); - const gPrime = buildGrammar(g.match(ohmGrammarSource, 'Document'), {}, g); + const g = buildGrammar(ns.Ohm.match(ohmGrammarSource, 'Grammar'), {}, {}, ns.Ohm); + const gPrime = buildGrammar(g.match(ohmGrammarSource, 'Grammar'), {}, {}, g); gPrime.namespaceName = g.namespaceName; // make their namespaceName properties the same compareGrammars(t, g, gPrime); }); From 293670832c17fbcadd9a7ae35b6286c14d241c0d Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Sat, 26 Aug 2023 10:15:31 +0000 Subject: [PATCH 19/20] Implemented review comments --- packages/ohm-js/extras/extractExamples.js | 11 +--- packages/ohm-js/src/buildGrammar.js | 69 ++++++++--------------- packages/ohm-js/src/main.js | 12 +--- 3 files changed, 26 insertions(+), 66 deletions(-) diff --git a/packages/ohm-js/extras/extractExamples.js b/packages/ohm-js/extras/extractExamples.js index f6aa6528..583d8d30 100644 --- a/packages/ohm-js/extras/extractExamples.js +++ b/packages/ohm-js/extras/extractExamples.js @@ -73,17 +73,10 @@ const semantics = grammars.OhmWithExamples.createSemantics().addOperation('hasEx }); semantics.addOperation('examples', { - Document(includesIter, grammarIter) - { - includesIter.examples(); + Document(_, grammarIter) + { return grammarIter.examples(); }, - Includes(includesIter) { - return includesIter.children.flatMap(c => c.examples()); - }, - Include(_, _la, relativePathNode, _ra) { - return null; - }, Grammars(grammarIter) { return grammarIter.children.flatMap(c => c.examples()); }, diff --git a/packages/ohm-js/src/buildGrammar.js b/packages/ohm-js/src/buildGrammar.js index 15b2e1d0..10ac34a5 100644 --- a/packages/ohm-js/src/buildGrammar.js +++ b/packages/ohm-js/src/buildGrammar.js @@ -4,7 +4,7 @@ import * as common from './common.js'; import * as errors from './errors.js'; import {Grammar} from './Grammar.js'; import * as pexprs from './pexprs.js'; -import { validateOption } from './util.js'; +import {validateOption} from './util.js'; const superSplicePlaceholder = Object.create(pexprs.PExpr.prototype); @@ -16,6 +16,17 @@ function namespaceHas(ns, name) { return false; } +// Compiles and loads a grammar from source or throws syntax error. +export function compileAndLoad(source, namespace, options) { + const m = ohmGrammar.match(source); + + if (m.failed()) { + throw errors.grammarSyntaxError(m); + } + + return buildGrammar(m, namespace, options); +} + // Returns a Grammar instance (i.e., an object with a `match` method) for // `tree`, which is the concrete syntax tree of a user-written grammar. // The grammar will be assigned into `namespace` under the name of the grammar @@ -28,70 +39,37 @@ export function buildGrammar(match, namespace, options, optOhmGrammarForTesting) let overriding = false; const metaGrammar = optOhmGrammarForTesting || ohmGrammar; - const fetchGrammarInternal = (path) => { - if (!validateOption(options, 'fetchGrammar', 'function')) - { + const fetchGrammarInternal = path => { + if (!validateOption(options, 'fetchGrammar', 'function')) { throw new Error("Missing option 'fetchGrammar' of type `function` when trying to include."); } const grammarContent = options.fetchGrammar(path); - if (typeof grammarContent !== "string") - { + if (typeof grammarContent !== 'string') { throw new Error(`Expected string from 'fetchGrammar' function, but got ${typeof(grammarContent)}`); } return grammarContent.trim(); } - const rematchInput = (includes) => { - let modifiedGrammarSource = match.input; - - for (let i = 0; i < includes.length; i++) { - const [sourceString, fileContent] = includes[i]; - - // Always substitute the include even with a nothing to prevent infinite loop. - modifiedGrammarSource = modifiedGrammarSource.replace(sourceString, fileContent); - } - - const newMatch = ohmGrammar.match(modifiedGrammarSource); - - if (newMatch.failed()) { - throw errors.grammarSyntaxError(newMatch); - } - - helpers(newMatch).visit() - } - // A visitor that produces a Grammar instance from the CST. const helpers = metaGrammar.createSemantics().addOperation('visit', { Document(includesNode, grammarsNode) { - const resolvedIncludes = includesNode.visit(); - - // We need to rebuild the grammar match with the resolved includes substituted. - // Note: It's important we prevent any deeper visits in this tree as it's now pointless. - if (resolvedIncludes.length > 0) { - rematchInput(resolvedIncludes); - return; - } - + includesNode.visit(); return grammarsNode.visit(); }, Includes(includesIter) { - const resolvedIncludes = []; - - includesIter.children.flatMap(c => { - resolvedIncludes.push(c.visit()); - }) - - return resolvedIncludes; + includesIter.children.flatMap(c => c.visit()); }, Include(_, _la, relativePathNode, _ra) { - return [ - this.sourceString, - fetchGrammarInternal(relativePathNode.sourceString) - ]; + const fileContent = fetchGrammarInternal(relativePathNode.sourceString); + + if (fileContent) + { + compileAndLoad(fileContent, namespace, options); + } }, Grammars(grammarIter) { return grammarIter.children.map(c => c.visit()); @@ -120,7 +98,6 @@ export function buildGrammar(match, namespace, options, optOhmGrammarForTesting) decl.withSuperGrammar(namespace[superGrammarName]); } }, - Rule_define(n, fs, d, _, b) { currentRuleName = n.visit(); currentRuleFormals = fs.children.map(c => c.visit())[0] || []; diff --git a/packages/ohm-js/src/main.js b/packages/ohm-js/src/main.js index 4dbddd62..b67bf5ac 100644 --- a/packages/ohm-js/src/main.js +++ b/packages/ohm-js/src/main.js @@ -1,7 +1,6 @@ import ohmGrammar from '../dist/ohm-grammar.js'; -import {buildGrammar} from './buildGrammar.js'; +import {buildGrammar,compileAndLoad} from './buildGrammar.js'; import * as common from './common.js'; -import * as errors from './errors.js'; import {Grammar} from './Grammar.js'; import * as pexprs from './pexprs.js'; import * as util from './util.js'; @@ -20,15 +19,6 @@ const isBuffer = obj => typeof obj.constructor.isBuffer === 'function' && obj.constructor.isBuffer(obj); -function compileAndLoad(source, namespace, options) { - const m = ohmGrammar.match(source); - - if (m.failed()) { - throw errors.grammarSyntaxError(m); - } - - return buildGrammar(m, namespace, options); -} export function grammar(source, optNamespace, options = {}) { const ns = grammars(source, optNamespace, options); From 9073f4e9814619e9312c90f9fd32fa036b9c0cc9 Mon Sep 17 00:00:00 2001 From: Liam Riddell <3812154+LiamRiddell@users.noreply.github.com> Date: Sat, 26 Aug 2023 10:16:35 +0000 Subject: [PATCH 20/20] Minor renaming --- packages/ohm-js/extras/extractExamples.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/ohm-js/extras/extractExamples.js b/packages/ohm-js/extras/extractExamples.js index 583d8d30..3574935c 100644 --- a/packages/ohm-js/extras/extractExamples.js +++ b/packages/ohm-js/extras/extractExamples.js @@ -73,9 +73,9 @@ const semantics = grammars.OhmWithExamples.createSemantics().addOperation('hasEx }); semantics.addOperation('examples', { - Document(_, grammarIter) + Document(_, grammarsNode) { - return grammarIter.examples(); + return grammarsNode.examples(); }, Grammars(grammarIter) { return grammarIter.children.flatMap(c => c.examples());