-
Notifications
You must be signed in to change notification settings - Fork 1
/
jscesk.js
81 lines (62 loc) · 2.31 KB
/
jscesk.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
80
81
/* -*- Mode: js2; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
import * as esprima from './esprima-es6';
import * as b from './ast-builder';
import * as fs from 'fs';
import { dumpStatements, unimplemented, error, setDebug } from './utils';
import { assignNext, wrap, CESKDone } from './ast';
import { State } from './state';
import { Store } from './store';
import { Environment } from './env';
import { HaltKont } from './kont';
import { resetPointers } from './pointer';
import { initES6Env } from './es6';
// CESK = (C)ode, (E)nvironment, (S)tore, and K(C)ontinuation
//
// Code : just our AST, helpfully converted to ANF, and with a _nextStmt for each statement
// Environment : a stack of frames, mapping from name to address
// Store : a global store mapping from address to type(s)
// Kontinuation: a stack used to match return statements to the call, as well as throw statements to handlers.
//
// we don't do this at the moment, so take care when crafting tests
function toANF(ast) {
return ast;
}
function execute(toplevel) {
resetPointers();
// create an initial store (this also initializes the store's NullPointer)
let store0 = new Store();
// allocate an initial frame pointer
let fp0 = new Environment();
initES6Env(fp0, store0);
// get the Halt continuation
let halt = new HaltKont();
// create our initial state
let state = new State(toplevel, fp0, store0, halt);
// Run until termination:
while (!state.stmt.done) {
state = state.next();
}
}
function runcesk(name, program_text) {
var test = esprima.parse(program_text);
var cesktest = wrap(test);
assignNext(cesktest, new CESKDone());
cesktest = toANF(cesktest);
dumpStatements(cesktest);
let timer = `runcesk ${name}`;
console.time(timer);
execute(cesktest);
console.timeEnd(timer);
}
let args = process.argv.slice();
args.shift(); // get rid of argv0
args.shift(); // get rid of argv1
if (args.length > 0 && args[0] == '-d') {
args.shift(); // get rid of -d
setDebug(true);
}
if (args.length === 0)
error('must specify test to run on command line, ex: ./jscesk.exe tests/func-call.js');
let test_file = args[0];
let test_contents = fs.readFileSync(test_file, 'utf-8');
runcesk(test_file, test_contents);