bds.js
Version:
A simple interpreter written to simulate and run BDScript Language in JavaScript
86 lines (85 loc) • 2.56 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.Parser = void 0;
class Parser {
constructor() { }
get isBusy() { return this.busy; }
;
parseToAst(tokens, runtime) {
if (this.busy)
throw new Error("Parser is busy!");
this.tokens = tokens;
this.busy = true;
let arr = [];
while (!this.eof()) {
arr.push(this.parseAtom(runtime));
}
return { type: "program", child: arr };
}
peek(offset = 0) {
return this.tokens[offset];
}
shift() {
return this.tokens.shift();
}
eof() {
return !(this.tokens.length > 0);
}
last(arr) {
return arr[arr.length - 1];
}
readArgument(runtime) {
let arr = [];
let end = false;
let arg = { type: "argument", child: [] };
this.shift();
while (!this.eof()) {
if (this.peek()?.type === "close") {
end = true;
this.shift();
break;
}
if (this.peek()?.type === "newArg") {
arr.push(arg);
arg = { type: "argument", child: [] };
this.shift();
continue;
}
arg.child.push(this.parseAtom(runtime));
}
if (arg) {
arr.push(arg);
arg = void 0;
}
if (end === false)
throw new Error(`Expected ']', got none`);
return arr;
}
parseParen(runtime) {
return this.readArgument(runtime);
}
;
parseAtom(runtime) {
let token = this.shift();
if (token.type === "string")
return token;
if (token.type === "number")
return token;
if (token.type === "operator")
return token;
if (token.type === "call") {
if (this.peek()?.type === "open")
token.child = this.parseParen(runtime);
return token;
}
if (runtime.options.alwaysStrict === false)
switch (token.type) {
case "open": return { value: "[", type: "string" };
case "close": return { value: "]", type: "string" };
case "newArg": return { value: ";", type: "string" };
}
throw new Error(`Unexpected token of ${token.type} at ${token.pos}:${token.line}`);
}
;
}
exports.Parser = Parser;