diff --git a/src/compiler/compiler.ts b/src/compiler/compiler.ts index be939cf..2e62450 100644 --- a/src/compiler/compiler.ts +++ b/src/compiler/compiler.ts @@ -75,6 +75,7 @@ export class Compiler { if (DEBUG) { const bytecodeString = bytecodeToString(this.bytecode) console.log(`\n🤖 bytecode:\n----------------\n${bytecodeString}\n\n`) + console.log(`\n🤖 bytecode:\n----------------\n${this.instructions}\n\n`) } } catch (error) { if (error instanceof CompilerError) { @@ -281,13 +282,27 @@ export class Compiler { const opValue = input.slice(operator.from, operator.to) switch (opValue) { - case '+=': instructions.push(['ADD']); break - case '-=': instructions.push(['SUB']); break - case '*=': instructions.push(['MUL']); break - case '/=': instructions.push(['DIV']); break - case '%=': instructions.push(['MOD']); break + case '+=': + instructions.push(['ADD']) + break + case '-=': + instructions.push(['SUB']) + break + case '*=': + instructions.push(['MUL']) + break + case '/=': + instructions.push(['DIV']) + break + case '%=': + instructions.push(['MOD']) + break default: - throw new CompilerError(`Unknown compound operator: ${opValue}`, operator.from, operator.to) + throw new CompilerError( + `Unknown compound operator: ${opValue}`, + operator.from, + operator.to + ) } // DUP and store (same as regular assignment) @@ -305,10 +320,8 @@ export class Compiler { } case terms.FunctionDef: { - const { paramNames, bodyNodes, catchVariable, catchBody, finallyBody } = getFunctionDefParts( - node, - input - ) + const { paramNames, bodyNodes, catchVariable, catchBody, finallyBody } = + getFunctionDefParts(node, input) const instructions: ProgramItem[] = [] const functionLabel: Label = `.func_${this.fnLabelCount++}` const afterLabel: Label = `.after_${functionLabel}` @@ -331,7 +344,13 @@ export class Compiler { if (catchVariable || finallyBody) { // If function has catch or finally, wrap body in try/catch/finally instructions.push( - ...this.#compileTryCatchFinally(compileFunctionBody, catchVariable, catchBody, finallyBody, input) + ...this.#compileTryCatchFinally( + compileFunctionBody, + catchVariable, + catchBody, + finallyBody, + input + ) ) } else { instructions.push(...compileFunctionBody()) @@ -414,8 +433,9 @@ export class Compiler { instructions.push(['JUMP', afterLabel]) instructions.push([`${fnLabel}:`]) instructions.push( - ...block.filter(x => x.type.name !== 'keyword') - .map(x => this.#compileNode(x!, input)) + ...block + .filter((x) => x.type.name !== 'keyword') + .map((x) => this.#compileNode(x!, input)) .flat() ) instructions.push(['RETURN']) @@ -435,15 +455,16 @@ export class Compiler { body = [ ...body.slice(0, startSlice), ['MAKE_FUNCTION', [], fnLabel], - ...body.slice(startSlice) + ...body.slice(startSlice), ] // @ts-ignore body[body.length - 3]![1] += 1 instructions.push(...body) - } else { - throw new Error(`FunctionCallWithBlock: Expected FunctionCallOrIdentifier or FunctionCall`) + throw new Error( + `FunctionCallWithBlock: Expected FunctionCallOrIdentifier or FunctionCall` + ) } return instructions @@ -636,13 +657,13 @@ export class Compiler { } case terms.Array: { - const children = getAllChildren(node) + const children = getAllChildren(node).filter((n) => n.type.id !== terms.Comment) // We can easily parse [=] as an empty dict, but `[ = ]` is tougher. // = can be a valid word, and is also valid inside words, so for now we cheat // and check for arrays that look like `[ = ]` to interpret them as // empty dicts - if (children.length === 1 && children[0]!.name === 'Word') { + if (children.length === 1 && children[0]!.type.id === terms.Word) { const child = children[0]! if (input.slice(child.from, child.to) === '=') { return [['MAKE_DICT', 0]] @@ -655,7 +676,7 @@ export class Compiler { } case terms.Dict: { - const children = getAllChildren(node) + const children = getAllChildren(node).filter((n) => n.type.id !== terms.Comment) const instructions: ProgramItem[] = [] children.forEach((node) => { @@ -691,6 +712,10 @@ export class Compiler { return instructions } + case terms.Comment: { + return [] // ignore comments + } + default: throw new CompilerError( `Compiler doesn't know how to handle a "${node.type.name}" node.`, diff --git a/src/compiler/tests/compiler.test.ts b/src/compiler/tests/compiler.test.ts index 743f738..ad62392 100644 --- a/src/compiler/tests/compiler.test.ts +++ b/src/compiler/tests/compiler.test.ts @@ -304,9 +304,12 @@ describe('default params', () => { }) test.skip('dict default', () => { - expect('make-person = do person=[name=Bob age=60]: person end; make-person') - .toEvaluateTo({ name: 'Bob', age: 60 }) - expect('make-person = do person=[name=Bob age=60]: person end; make-person [name=Jon age=21]') - .toEvaluateTo({ name: 'Jon', age: 21 }) + expect('make-person = do person=[name=Bob age=60]: person end; make-person').toEvaluateTo({ + name: 'Bob', + age: 60, + }) + expect( + 'make-person = do person=[name=Bob age=60]: person end; make-person [name=Jon age=21]' + ).toEvaluateTo({ name: 'Jon', age: 21 }) }) -}) \ No newline at end of file +}) diff --git a/src/compiler/tests/literals.test.ts b/src/compiler/tests/literals.test.ts index 666a4b5..c1dc14b 100644 --- a/src/compiler/tests/literals.test.ts +++ b/src/compiler/tests/literals.test.ts @@ -66,8 +66,8 @@ describe('array literals', () => { }) test('comments within arrays', () => { - expect(`[1 # first - 2 # second + expect(`[1 + 2 ]`).toEvaluateTo([1, 2]) }) diff --git a/src/parser/tests/literals.test.ts b/src/parser/tests/literals.test.ts index 693da17..3a63381 100644 --- a/src/parser/tests/literals.test.ts +++ b/src/parser/tests/literals.test.ts @@ -150,8 +150,11 @@ describe('array literals', () => { 2 # second ]`).toMatchTree(` Array + Comment # something... Number 1 + Comment # first Number 2 + Comment # second `) }) @@ -397,12 +400,15 @@ c=3]`).toMatchTree(` c=3 ]`).toMatchTree(` Dict + Comment # something... NamedArg NamedArgPrefix a= Number 1 + Comment # first NamedArg NamedArgPrefix b= Number 2 + Comment # second NamedArg NamedArgPrefix c= Number 3 diff --git a/vscode-extension/shrimp-0.0.1.vsix b/vscode-extension/shrimp-0.0.1.vsix new file mode 100644 index 0000000..730cc92 Binary files /dev/null and b/vscode-extension/shrimp-0.0.1.vsix differ