-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathgrammar.js
79 lines (64 loc) · 2.53 KB
/
grammar.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
function escapeRegex(string) {
return string.replace(/[/\-\\^$*+?.()|[\]{}]/g, '\\$&');
}
function literal(keyword) {
keyword = escapeRegex(keyword);
return new RegExp(keyword, 'i');
};
const builtin_oprs = ["=", "+", "-", "/", "*", "*/", ">", "<"];
const builtin_core = ["include", "!", "#", "#>", "#S", "'", "*/MOD", "+!", "+LOOP",
",", ".", ".\"", "/MOD", "0<", "0=", "1+", "1-", "2!", "2*", "2/", "2@", "2DROP",
"2DUP", "2OVER", "2SWAP", "<#", ">BODY", ">IN", ">NUMBER", ">R", "?DUP", "@",
"ABORT", "ABORT\"", "ABS", "ACCEPT", "ALIGN", "ALIGNED", "ALLOT", "AND", "BASE",
"BEGIN", "BL", "C!", "C,", "C@", "CELL+", "CELLS", "CHAR", "CHAR+", "CHARS",
"CONSTANT", "COUNT", "CR", "CREATE", "DECIMAL", "DEPTH", "DO", "DOES>", "DROP",
"DUP", "ELSE", "EMIT", "ENVIRONMENT?", "EVALUATE", "EXECUTE", "EXIT", "FILL",
"FIND", "FM/MOD", "HERE", "HOLD", "I", "IF", "IMMEDIATE", "INVERT", "J", "KEY",
"LEAVE", "LOOP", "LSHIFT", "M*", "MAX", "MIN", "MOD", "MOVE", "NEGATE", "OR",
"OVER", "POSTPONE", "QUIT", "R>", "R@", "RECURSE", "REPEAT", "ROT", "RSHIFT",
"S\"", "S>D", "SIGN", "SM/REM", "SOURCE", "SPACE", "SPACES", "STATE", "SWAP",
"THEN", "TYPE", "U.", "U<", "UM*", "UM/MOD", "UNLOOP", "UNTIL", "VARIABLE",
"WHILE", "WORD", "XOR", "[", "[']", "[CHAR]", ".(\"", ".R", ".S", "0<>", "0>",
"2>R", "2R>", "2R@", ":NONAME", "<>", "?DO", "ACTION-OF", "AGAIN", "BUFFER:",
"C\"", "CASE", "COMPILE,", "DEFER", "DEFER!", "DEFER@", "ENDCASE", "ENDOF",
"ERASE", "FALSE", "HEX", "HOLDS", "IS", "MARKER", "NIP", "OF", "PAD", "PARSE",
"PARSE-NAME", "PICK", "REFILL", "RESTORE-INPUT", "ROLL", "S\\\"", "SAVE-INPUT",
"SOURCE-ID", "TO", "TRUE", "TUCK", "U.R", "U>", "UNUSED", "VALUE", "WITHIN", "[COMPILE]" ];
module.exports = grammar({
name: 'forth',
rules: {
source_file: $ => repeat($._definition),
_definition: $ => choice(
$.word_definition,
$._tokens,
),
_tokens: $ => choice(
$.string,
$.number,
$.builtin,
$.word,
$.comment
),
string: $ => /s"[ ]+.*"/,
number: $ => /('\w')|(0[xX][0-9a-fA-F]+)|(\$[0-9a-fA-F]+)|(%[01]+)|(&\d+)|\d+/,
builtin: $ => choice(
$.core,
$.operator,
),
start_definition: $ => ":",
end_definition: $ => ";",
word_definition: $ => seq(
$.start_definition,
$.word,
repeat1($._tokens),
$.end_definition
),
comment: $ => choice(
/\\.*/,
/\(.*\)/,
),
core: $ => choice(...builtin_core.map(x => literal(x))),
operator: _ => choice(...builtin_oprs),
word: $ => /\S+/,
}
});