Mercurial > repos > tabletprog
annotate interp.js @ 280:23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
author | Michael Pavone <pavone@retrodev.com> |
---|---|
date | Mon, 21 Jul 2014 19:30:23 -0700 |
parents | 0dc7322590da |
children | f6dfb85e80e5 |
rev | line source |
---|---|
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
1 Number.prototype['tpmeth_+'] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
2 return this + other; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
3 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
4 Number.prototype['tpmeth_-'] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
5 return this - other; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
6 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
7 Number.prototype['tpmeth_*'] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
8 return this * other; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
9 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
10 Number.prototype['tpmeth_/'] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
11 return this / other; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
12 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
13 Number.prototype['tpmeth_='] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
14 return this == other ? tptrue : tpfalse; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
15 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
16 Number.prototype['tpmeth_>'] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
17 return this > other ? tptrue : tpfalse; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
18 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
19 Number.prototype['tpmeth_<'] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
20 return this < other ? tptrue : tpfalse; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
21 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
22 Number.prototype['tpmeth_>='] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
23 return this >= other ? tptrue : tpfalse; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
24 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
25 Number.prototype['tpmeth_<='] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
26 return this <= other ? tptrue : tpfalse; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
27 }; |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
28 Number.prototype.tpmeth_asStringChar = function() { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
29 return String.fromCharCode(this); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
30 }; |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
31 Number.prototype['tpmeth_isString?'] = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
32 return false; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
33 }; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
34 Number.prototype.tpmeth_string = function() { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
35 return '' + this; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
36 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
37 Number.prototype.tpmeth_print = function() { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
38 print(this); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
39 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
40 |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
41 String.prototype['tpmeth_.'] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
42 return this + other; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
43 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
44 String.prototype['tpmeth_='] = function(other) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
45 return this == other ? tptrue : tpfalse; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
46 }; |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
47 String.prototype.tpmeth_length = function() { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
48 return this.length; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
49 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
50 String.prototype.tpmeth_byte_length = function() { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
51 return this.length; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
52 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
53 String.prototype.tpmeth_byte = function(index) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
54 return this.charCodeAt(index); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
55 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
56 String.prototype['tpmeth_from:withLength'] = function(pos, length) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
57 return this.substr(pos, length); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
58 }; |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
59 String.prototype['tpmeth_isString?'] = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
60 return true; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
61 }; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
62 String.prototype.tpmeth_print = function() { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
63 print(this); |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
64 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
65 |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
66 Function.prototype['tpmeth_while:do'] = function(body) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
67 var ret = null; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
68 for (;;) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
69 var res = this.call(null); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
70 if (res != tptrue) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
71 break; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
72 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
73 ret = body.call(null); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
74 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
75 return ret; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
76 }; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
77 |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
78 var tptrue = null; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
79 var tpfalse = null; |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
80 var tplist = null; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
81 |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
82 function topenv(moduledirs) |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
83 { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
84 this.names = {}; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
85 this.modules = {}; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
86 for (var dirnum in moduledirs) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
87 var results = os.system("ls", [moduledirs[dirnum]]).split('\n'); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
88 for (var i in results) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
89 var tpidx = results[i].indexOf('.tp') |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
90 if (tpidx > 0 && tpidx == results[i].length - 3) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
91 this.names[results[i].substr(0, tpidx)] = moduledirs[dirnum] + "/" + results[i]; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
92 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
93 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
94 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
95 if (!tptrue) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
96 tptrue = this.find('true'); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
97 tptrue.valueOf = function() { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
98 return true; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
99 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
100 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
101 if (!tpfalse) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
102 tpfalse = this.find('false'); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
103 tpfalse.valueOf = function() { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
104 return false; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
105 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
106 } |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
107 if (!tplist) { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
108 tplist = this.find('list'); |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
109 if (tplist instanceof Function) { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
110 tplist = tplist.call(null); |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
111 } |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
112 } |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
113 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
114 |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
115 topenv.prototype = { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
116 find: function(name) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
117 if (name in this.modules) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
118 return this.modules[name]; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
119 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
120 if (name in this.names) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
121 var parsed = parseFile(this.names[name]); |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
122 var ret = parsed.macroexpand(this).eval(this); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
123 if (typeof ret == 'function') { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
124 ret = ret(); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
125 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
126 this.modules[name] = ret; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
127 return ret; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
128 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
129 return null; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
130 }, |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
131 findNoTop: function(name) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
132 return null; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
133 }, |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
134 findSetPresent: function(name, val) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
135 return false; |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
136 }, |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
137 findMacro: function(name) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
138 return null; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
139 }, |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
140 findQuoteTrans: function(name) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
141 return null; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
142 } |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
143 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
144 |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
145 function environment(parent) |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
146 { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
147 this.parent = parent; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
148 this.syms = {}; |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
149 this.macros = {}; |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
150 this.quotetrans = {}; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
151 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
152 |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
153 environment.prototype = { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
154 find: function(name) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
155 if (name in this.syms) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
156 return this.syms[name]; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
157 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
158 if (this.parent) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
159 return this.parent.find(name); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
160 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
161 return null; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
162 }, |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
163 findNoTop: function(name) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
164 if (name in this.syms) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
165 return this.syms[name]; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
166 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
167 if (this.parent) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
168 return this.parent.findNoTop(name); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
169 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
170 return null; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
171 }, |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
172 findSet: function(name, val) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
173 if (name in this.syms |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
174 || !this.parent |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
175 || !this.parent.findSetPresent(name, val)) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
176 this.syms[name] = val; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
177 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
178 }, |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
179 findSetPresent: function(name, val) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
180 if (name in this.syms) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
181 this.syms[name] = val; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
182 return true; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
183 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
184 if (this.parent) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
185 return this.parent.findSetPresent(name, val); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
186 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
187 return false; |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
188 }, |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
189 findMacro: function(name) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
190 if (name in this.syms) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
191 if (name in this.macros) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
192 return this.syms[name]; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
193 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
194 return null; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
195 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
196 if (this.parent) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
197 return this.parent.findMacro(name); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
198 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
199 return null; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
200 }, |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
201 findQuoteTrans: function(name) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
202 if (name in this.quotetrans) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
203 return this.quotetrans[name]; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
204 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
205 if (this.parent) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
206 return this.parent.findQuoteTrans(name); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
207 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
208 return null; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
209 }, |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
210 defMacro: function(name, def) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
211 this.syms[name] = def; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
212 this.macros[name] = true; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
213 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
214 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
215 |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
216 function makeASTNode(val) |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
217 { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
218 if (typeof val == 'number') { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
219 return new intlit(val); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
220 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
221 if (typeof val == 'string') { |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
222 return new strlit(val); |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
223 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
224 if (val instanceof Array) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
225 return new arraylit(val); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
226 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
227 if (val == tptrue) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
228 return new symbol('true'); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
229 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
230 if (val == tpfalse) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
231 return new symbol('false'); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
232 } |
221
218b11ec8fa2
Better handling for weird values being inserted into AST due to quoting
Michael Pavone <pavone@retrodev.com>
parents:
219
diff
changeset
|
233 if ('makeHygienic' in val) { |
218b11ec8fa2
Better handling for weird values being inserted into AST due to quoting
Michael Pavone <pavone@retrodev.com>
parents:
219
diff
changeset
|
234 return val; |
218b11ec8fa2
Better handling for weird values being inserted into AST due to quoting
Michael Pavone <pavone@retrodev.com>
parents:
219
diff
changeset
|
235 } |
218b11ec8fa2
Better handling for weird values being inserted into AST due to quoting
Michael Pavone <pavone@retrodev.com>
parents:
219
diff
changeset
|
236 return null; |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
237 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
238 |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
239 op.prototype.eval = function(env) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
240 var l = this.left.eval(env); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
241 var name = this.op; |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
242 if (name == '&&' || name == '||') { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
243 var r = (new lambda([], [this.right])).eval(env); |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
244 } else { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
245 var r = this.right.eval(env); |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
246 } |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
247 var fun = env.findNoTop(name); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
248 var ret; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
249 if (fun) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
250 ret = fun(l,r) |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
251 } else { |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
252 if (name == '&&') { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
253 name = 'if' |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
254 } else if (name == '||') { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
255 name = 'ifnot' |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
256 } else if (name == '|') { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
257 return r['tpmeth_|'](l); |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
258 } |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
259 ret = l['tpmeth_'+name](r); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
260 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
261 return ret; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
262 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
263 |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
264 op.prototype.macroexpand = function(env) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
265 this.left = this.left.macroexpand(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
266 this.right = this.right.macroexpand(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
267 return this; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
268 }; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
269 |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
270 op.prototype.quote = function(env) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
271 var left = this.left.quote(env); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
272 var right = this.right.quote(env); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
273 return new op(left, this.op, right); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
274 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
275 |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
276 op.prototype.makeHygienic = function(env) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
277 var left = this.left.makeHygienic(env); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
278 var right = this.right.makeHygienic(env); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
279 return new op(left, this.op, right); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
280 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
281 |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
282 op.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
283 return "op"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
284 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
285 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
286 op.prototype.tpmeth_left = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
287 return this.left; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
288 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
289 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
290 op.prototype.tpmeth_right = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
291 return this.right; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
292 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
293 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
294 op.prototype.tpmeth_opName = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
295 return this.op; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
296 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
297 |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
298 var quote_prefix = 0; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
299 |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
300 symbol.prototype.eval = function(env) { |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
301 var res = env.find(this.name); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
302 if (res === null) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
303 throw new Error('Symbol ' + this.name + ' is not bound'); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
304 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
305 return res; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
306 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
307 |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
308 symbol.prototype.quote = function(env) { |
280
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
309 if (this.cleanName() != 'self') { |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
310 var val = env.find(this.name); |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
311 if (val !== null) { |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
312 var newnode = makeASTNode(val); |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
313 if (!newnode) { |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
314 throw new Error(this.name + ' contains a value ' + val + ' that could not be converted to an AST node'); |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
315 } |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
316 return newnode; |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
317 } else { |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
318 this.dirty = true; |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
319 return this; |
221
218b11ec8fa2
Better handling for weird values being inserted into AST due to quoting
Michael Pavone <pavone@retrodev.com>
parents:
219
diff
changeset
|
320 } |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
321 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
322 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
323 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
324 symbol.prototype.makeHygienic = function(env) { |
240
dc5f487247ee
Don't rename the symbol self in quote blocks
Mike Pavone <pavone@retrodev.com>
parents:
238
diff
changeset
|
325 if (this.dirty && this.cleanName() != 'self') { |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
326 var hygenic = env.findQuoteTrans(this.cleanName()); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
327 if (hygenic) |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
328 { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
329 return new symbol(hygenic, this.symbols); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
330 } else { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
331 return this; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
332 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
333 } else { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
334 return this; |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
335 } |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
336 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
337 |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
338 symbol.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
339 return "symbol"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
340 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
341 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
342 symbol.prototype.tpmeth_name = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
343 return this.cleanName(); |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
344 }; |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
345 symbol.prototype['tpmeth_name!'] = function(val) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
346 this.name = val; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
347 return this; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
348 }; |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
349 |
255
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
350 intlit.prototype.isconstant = |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
351 floatlit.prototype.isconstant = |
280
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
352 strlit.prototype.isconstant = |
255
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
353 lambda.prototype.isconstant = function() { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
354 return true; |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
355 }; |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
356 |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
357 object.prototype.isconstant = |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
358 symbol.prototype.isconstant = |
280
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
359 funcall.prototype.isconstant = |
23b52d2d05a0
Don't try to replace self in a macro expansion since it's unlikely to be the desired behavior. A more explicit means of specifying what variables should be replaced in a quote expression is needed.
Michael Pavone <pavone@retrodev.com>
parents:
273
diff
changeset
|
360 op.prototype.isconstant = |
255
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
361 assignment.prototype.isconstant = function() { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
362 return false; |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
363 } |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
364 |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
365 arraylit.prototype.isconstant = |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
366 listlit.prototype.isconstant = function() { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
367 for (var idx = 0; idx < this.val.length; ++idx) { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
368 if (!this.val[idx].isconstant()) { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
369 return false; |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
370 } |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
371 } |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
372 return true; |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
373 }; |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
374 |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
375 intlit.prototype.eval = |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
376 floatlit.prototype.eval = |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
377 strlit.prototype.eval = |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
378 arraylit.prototype.eval = function(env) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
379 return this.val; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
380 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
381 |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
382 listlit.prototype.eval = function(env) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
383 var cur = tplist.tpmeth_empty(); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
384 for (var idx = this.val.length - 1; idx >= 0; --idx) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
385 cur = tplist['tpmeth_node:withTail'](this.val[idx].eval(env), cur); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
386 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
387 return cur; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
388 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
389 |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
390 symbol.prototype.macroexpand = |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
391 intlit.prototype.macroexpand = |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
392 floatlit.prototype.macroexpand = |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
393 strlit.prototype.macroexpand = function(env) { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
394 return this; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
395 }; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
396 |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
397 |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
398 arraylit.prototype.macroexpand = |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
399 listlit.prototype.macroexpand = function(env) { |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
400 for (var i = 0; i < this.val.length; i++) { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
401 this.val[i] = this.val[i].macroexpand(env); |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
402 } |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
403 return this; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
404 }; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
405 |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
406 intlit.prototype.quote = |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
407 floatlit.prototype.quote = |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
408 strlit.prototype.quote = |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
409 arraylit.prototype.quote = |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
410 listlit.prototype.quote = function(env) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
411 return this; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
412 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
413 |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
414 intlit.prototype.makeHygienic = |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
415 floatlit.prototype.makeHygienic = |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
416 strlit.prototype.makeHygienic = |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
417 arraylit.prototype.makeHygienic = |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
418 listlit.prototype.makeHygienic = function(env) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
419 return this; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
420 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
421 |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
422 intlit.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
423 return "intlit"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
424 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
425 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
426 floatlit.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
427 return "floatlit"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
428 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
429 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
430 strlit.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
431 return "strlit"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
432 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
433 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
434 arraylit.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
435 return "arraylit"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
436 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
437 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
438 listlit.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
439 return "strlit"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
440 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
441 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
442 intlit.prototype.tpmeth_value = |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
443 floatlit.prototype.tpmeth_value = |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
444 strlit.prototype.tpmeth_value = |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
445 arraylit.prototype.tpmeth_value = function() { |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
446 return this.val; |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
447 }; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
448 |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
449 listlit.prototype.tpmeth_value = function() { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
450 var cur = tplist.tpmeth_empty(); |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
451 for (var idx = this.val.length - 1; idx >= 0; --idx) { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
452 cur = tplist['tpmeth_node:withTail'](this.val[idx], cur); |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
453 } |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
454 return cur; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
455 }; |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
456 |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
457 funcall.prototype.eval = function(env) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
458 var args = []; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
459 var name = this.name; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
460 if (name[name.length-1] == ":") { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
461 name = name.substr(0, name.length-1); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
462 } |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
463 if (name == 'quote') { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
464 if (this.receiver) { |
224
97c3e33cd3f4
Support macro expansion inside quoted code
Michael Pavone <pavone@retrodev.com>
parents:
221
diff
changeset
|
465 return this.receiver.quote(env).macroexpand(env); |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
466 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
467 if (this.args.length) { |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
468 var cur = env; |
224
97c3e33cd3f4
Support macro expansion inside quoted code
Michael Pavone <pavone@retrodev.com>
parents:
221
diff
changeset
|
469 return this.args[0].quote(env).macroexpand(env); |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
470 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
471 throw new Error('quote takes an argument'); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
472 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
473 if (name == 'macro') { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
474 return null; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
475 } |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
476 if (this.receiver) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
477 args.push(this.receiver.eval(env)); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
478 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
479 for (var i = 0; i < this.args.length; i++) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
480 args.push(this.args[i].eval(env)); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
481 } |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
482 if (name == 'eval:else') { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
483 try { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
484 var res = args[0].eval(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
485 } catch(e) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
486 return args[2].call(null); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
487 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
488 return args[1].call(null, res); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
489 } |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
490 var fun = env.findNoTop(name); |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
491 if (fun && (fun.numargs === undefined || fun.numargs == args.length)) { |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
492 return fun.apply(null, args); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
493 } else { |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
494 //if (typeof args[0]'tpmeth_'+name in args[0]) { |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
495 try { |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
496 return args[0]['tpmeth_'+name].apply(args[0], args.slice(1)); |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
497 } catch(e) { |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
498 var msg = 'Error, \n\t' + e.message.split('\n').join('\n\t') + '\ninvoking method ' + name + ' on object ' + args[0]; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
499 if (typeof args[0] == 'object') { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
500 msg += ' with keys ' + JSON.stringify(Object.keys(args[0]) + ' and constructor ' + args[0].constructor.name); |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
501 } |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
502 throw new Error(msg); |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
503 } |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
504 /*} else {JSON.stringify |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
505 throw new Error('No method named ' + name + ' on object ' + JSON.stringify(args[0])); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
506 }*/ |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
507 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
508 }; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
509 |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
510 funcall.prototype.macroexpand = function(env) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
511 var name = this.name; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
512 if (name[name.length-1] == ":") { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
513 name = name.substr(0, name.length-1); |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
514 } |
224
97c3e33cd3f4
Support macro expansion inside quoted code
Michael Pavone <pavone@retrodev.com>
parents:
221
diff
changeset
|
515 if (name == 'quote') { |
97c3e33cd3f4
Support macro expansion inside quoted code
Michael Pavone <pavone@retrodev.com>
parents:
221
diff
changeset
|
516 return this; |
97c3e33cd3f4
Support macro expansion inside quoted code
Michael Pavone <pavone@retrodev.com>
parents:
221
diff
changeset
|
517 } |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
518 var macro = env.findMacro(name); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
519 if (this.receiver) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
520 this.receiver = this.receiver.macroexpand(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
521 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
522 for (var i = 0; i < this.args.length; i++) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
523 this.args[i] = this.args[i].macroexpand(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
524 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
525 if (!macro) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
526 return this; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
527 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
528 var args = []; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
529 if (this.receiver) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
530 args.push(this.receiver); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
531 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
532 for (var i = 0; i < this.args.length; i++) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
533 args.push(this.args[i]); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
534 } |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
535 var ret = makeASTNode(macro.apply(null, args)); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
536 ret = ret.makeHygienic(env); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
537 quote_prefix++; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
538 return ret; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
539 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
540 |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
541 funcall.prototype.quote = function(env) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
542 var receiver = this.receiver ? this.receiver.quote(env) : null; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
543 var args = []; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
544 for (var i = 0; i < this.args.length; i++) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
545 args.push(this.args[i].quote(env)); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
546 } |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
547 var name = this.name; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
548 if (name[name.length-1] == ":") { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
549 name = name.substr(0, name.length-1); |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
550 } |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
551 var fun = env.find(name); |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
552 if (fun) { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
553 fun = makeASTNode(fun); |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
554 if (fun instanceof symbol) { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
555 name = fun.cleanName(); |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
556 } else if (fun instanceof lambda) { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
557 throw new Error('FIXME'); |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
558 } |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
559 } else { |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
560 this.dirty = true; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
561 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
562 var ret = new funcall(name, args); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
563 ret.receiver = receiver; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
564 return ret; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
565 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
566 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
567 funcall.prototype.makeHygienic = function(env) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
568 var receiver = this.receiver ? this.receiver.makeHygienic(env) : null; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
569 var args = []; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
570 for (var i = 0; i < this.args.length; i++) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
571 args.push(this.args[i].makeHygienic(env)); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
572 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
573 var name = this.name; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
574 if (name[name.length-1] == ":") { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
575 name = name.substr(0, name.length-1); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
576 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
577 var hygienic = env.findQuoteTrans(name); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
578 if (hygienic) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
579 name = hygienic; |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
580 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
581 var ret = new funcall(name, args); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
582 ret.receiver = receiver; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
583 return ret; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
584 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
585 |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
586 funcall.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
587 return "funcall"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
588 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
589 |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
590 funcall.prototype['tpmeth_args!'] = function(arglist) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
591 this.args = []; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
592 //TODO: Finish this |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
593 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
594 |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
595 object.prototype.eval = function(parentenv) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
596 var env = new environment(parentenv); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
597 var obj = {env: env}; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
598 for (var i = 0; i < this.messages.length; i++) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
599 var msg = this.messages[i]; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
600 if (msg instanceof assignment) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
601 if (msg.expression instanceof lambda) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
602 obj['tpmeth_' + msg.symbol.name] = msg.expression.eval(env); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
603 (function(name) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
604 env.syms[name] = function() { |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
605 var ret = obj['tpmeth_' + name].apply(obj, arguments); |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
606 return ret; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
607 }; |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
608 env.syms[name].numargs = msg.expression.numArgs(); |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
609 })(msg.symbol.name); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
610 } else { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
611 var makeProp = function(obj, name) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
612 obj['tprop_' + name] = msg.expression.eval(env); |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
613 obj['tpmeth_' + name] = function() { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
614 return this['tprop_'+name]; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
615 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
616 var setname = name+'!'; |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
617 obj['tpmeth_' + setname] = function(val) { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
618 this['tprop_'+name] = val; |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
619 return this; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
620 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
621 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
622 makeProp(obj, msg.symbol.name); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
623 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
624 } else { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
625 throw new Error('pseudo function calls in object definitions not implemented yet'); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
626 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
627 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
628 return obj; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
629 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
630 |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
631 object.prototype.macroexpand = function(parentenv) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
632 var env = new environment(parentenv); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
633 var obj = {env: env}; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
634 var outmessages = []; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
635 for (var i = 0; i < this.messages.length; i++) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
636 var msg = this.messages[i].macroexpand(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
637 if (msg instanceof assignment) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
638 if (msg.expression instanceof lambda) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
639 (function(name, expr) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
640 env.syms[name] = function() { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
641 if (!obj['tpmeth_' + name]) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
642 obj['tpmeth_' + name] = expr.eval(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
643 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
644 return obj['tpmeth_' + name].apply(obj, arguments); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
645 }; |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
646 env.syms[name].numargs = expr.numArgs(); |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
647 })(msg.symbol.name, msg.expression); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
648 outmessages.push(msg); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
649 } else if (msg.expression instanceof funcall && msg.expression.name == 'macro:') { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
650 env.defMacro(msg.symbol.name, msg.expression.args[0].eval(env)); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
651 } else { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
652 outmessages.push(msg); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
653 /* |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
654 var makeProp = function(obj, name) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
655 obj['tprop_' + name] = msg.expression.eval(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
656 name = 'tpmeth_' + name; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
657 obj[name] = function() { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
658 return this[name]; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
659 }; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
660 var setname = name+'!'; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
661 obj[setname] = function(val) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
662 this[setname] = val; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
663 return this; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
664 }; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
665 }; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
666 makeProp(obj, msg.symbol.name);*/ |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
667 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
668 } else { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
669 outmessages.push(msg); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
670 //throw new Error('pseudo function calls in object definitions not implemented yet'); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
671 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
672 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
673 this.messages = outmessages; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
674 return this; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
675 }; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
676 |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
677 object.prototype.quote = function(parentenv) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
678 var env = new environment(parentenv); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
679 var outmessages = []; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
680 for (var i = 0; i < this.messages.length; i++) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
681 var msg = this.messages[i]; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
682 if (msg instanceof assignment) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
683 env.syms[msg.symbol.name] = null; |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
684 if (!(msg.expression instanceof lambda)) { |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
685 env.syms[msg.symbol.name + '!'] = null; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
686 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
687 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
688 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
689 for (var i = 0; i < this.messages.length; i++) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
690 var msg = this.messages[i]; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
691 if (msg instanceof assignment) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
692 outmessages.push(new assignment(msg.symbol, msg.expression.quote(env))); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
693 } else { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
694 outmessages.push(msg.quote(env)); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
695 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
696 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
697 return new object(outmessages); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
698 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
699 |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
700 object.prototype.makeHygienic = function(parentenv) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
701 var env = new environment(parentenv); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
702 var outmessages = []; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
703 for (var i = 0; i < this.messages.length; i++) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
704 var msg = this.messages[i]; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
705 if (msg instanceof assignment) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
706 env.syms[msg.symbol.name] = null; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
707 //make sure method names don't get translated for hygiene |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
708 env.quotetrans[msg.symbol.name] = null; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
709 if (!(msg.expression instanceof lambda)) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
710 env.syms[msg.symbol.name + '!'] = null; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
711 env.quotetrans[msg.symbol.name + '!'] = null; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
712 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
713 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
714 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
715 for (var i = 0; i < this.messages.length; i++) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
716 var msg = this.messages[i]; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
717 if (msg instanceof assignment) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
718 outmessages.push(new assignment(msg.symbol, msg.expression.makeHygienic(env))); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
719 } else { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
720 outmessages.push(msg.makeHygienic(env)); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
721 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
722 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
723 return new object(outmessages); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
724 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
725 |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
726 object.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
727 return "object"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
728 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
729 |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
730 object.prototype.tpmeth_addMessage = function(message) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
731 this.messages.push(makeASTNode(message)); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
732 return this; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
733 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
734 |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
735 lambda.prototype.eval = function(parentenv) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
736 var args = this.args; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
737 var exprs = this.expressions; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
738 return function() { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
739 var env = new environment(parentenv); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
740 for (var i = 0, j = 0; i < arguments.length && j < args.length; i++, j++) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
741 while (j < args.length && args[j].cleanName() == 'self') { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
742 j++; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
743 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
744 env.syms[args[j].cleanName()] = arguments[i]; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
745 } |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
746 if (this != null) { |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
747 env.syms['self'] = this; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
748 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
749 var res = null; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
750 for (var i = 0; i < exprs.length; i++) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
751 res = exprs[i].eval(env); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
752 } |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
753 return res; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
754 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
755 }; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
756 |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
757 lambda.prototype.macroexpand = function(parentenv) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
758 var env = new environment(parentenv); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
759 for (var i = 0; i < this.args.length; i++) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
760 env.syms[this.args[i].cleanName()] = {}; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
761 } |
273
0dc7322590da
Make import:from actually work. Fix some macro bugs. Add a cpointer primitive type for storing an opaque pointer to a C object.
Michael Pavone <pavone@retrodev.com>
parents:
255
diff
changeset
|
762 var outexprs = [] |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
763 for (var i = 0; i < this.expressions.length; i++) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
764 var expr = this.expressions[i]; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
765 if (expr instanceof assignment) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
766 if (expr.expression instanceof funcall && expr.expression.name == 'macro:') { |
273
0dc7322590da
Make import:from actually work. Fix some macro bugs. Add a cpointer primitive type for storing an opaque pointer to a C object.
Michael Pavone <pavone@retrodev.com>
parents:
255
diff
changeset
|
767 env.defMacro(expr.symbol.name, expr.expression.args[0].eval(env)); |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
768 } else { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
769 env.syms[expr.symbol.cleanName()] = {}; |
273
0dc7322590da
Make import:from actually work. Fix some macro bugs. Add a cpointer primitive type for storing an opaque pointer to a C object.
Michael Pavone <pavone@retrodev.com>
parents:
255
diff
changeset
|
770 outexprs.push(expr.macroexpand(env)); |
255
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
771 try { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
772 if (this.expressions[i].expression.isconstant()) { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
773 env.syms[expr.symbol.cleanName()] = this.expressions[i].expression.eval(env); |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
774 } else { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
775 env.syms[expr.symbol.cleanName()] = null; |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
776 } |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
777 } catch(e) { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
778 var msg = 'Error, \n\t' + e.message.split('\n').join('\n\t') + '\nevaling node ' + this.expressions[i].expression |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
779 if (typeof this.expressions[i].expression == 'object') { |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
780 msg += ' with keys ' + JSON.stringify(Object.keys(this.expressions[i].expression) + ' and constructor ' + this.expressions[i].expression.constructor.name); |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
781 } |
08081b0a9382
Actual working implementation of isconstant check
Michael Pavone <pavone@retrodev.com>
parents:
254
diff
changeset
|
782 throw new Error(msg); |
238
3bfc00e4f5e5
Eval lambda assignments at macro expandion time so they can be called by macros
Mike Pavone <pavone@retrodev.com>
parents:
224
diff
changeset
|
783 } |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
784 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
785 } else { |
273
0dc7322590da
Make import:from actually work. Fix some macro bugs. Add a cpointer primitive type for storing an opaque pointer to a C object.
Michael Pavone <pavone@retrodev.com>
parents:
255
diff
changeset
|
786 outexprs.push(expr.macroexpand(env)); |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
787 } |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
788 } |
273
0dc7322590da
Make import:from actually work. Fix some macro bugs. Add a cpointer primitive type for storing an opaque pointer to a C object.
Michael Pavone <pavone@retrodev.com>
parents:
255
diff
changeset
|
789 this.expressions = outexprs; |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
790 return this; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
791 }; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
792 |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
793 lambda.prototype.quote = function(parentenv) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
794 var args = []; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
795 var expressions = []; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
796 var env = new environment(parentenv); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
797 for (var i = 0; i < this.args.length; i++) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
798 env.syms[this.args[i].cleanName()] = null; |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
799 var sym = new symbol(this.args[i].name, this.args[i].symbols); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
800 sym.dirty = true; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
801 args.push(sym); |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
802 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
803 for (var i = 0; i < this.expressions.length; i++) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
804 expressions.push(this.expressions[i].quote(env)); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
805 } |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
806 return new lambda(args, expressions); |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
807 }; |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
808 |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
809 lambda.prototype.makeHygienic = function(parentenv) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
810 var args = []; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
811 var expressions = []; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
812 var env = new environment(parentenv); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
813 for (var i = 0; i < this.args.length; i++) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
814 env.syms[this.args[i].cleanName()] = null; |
240
dc5f487247ee
Don't rename the symbol self in quote blocks
Mike Pavone <pavone@retrodev.com>
parents:
238
diff
changeset
|
815 if (this.args[i].dirty && this.args[i].cleanName() != 'self') { |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
816 var hygienic = '' + quote_prefix + this.args[i].cleanName(); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
817 env.quotetrans[this.args[i].cleanName()] = hygienic; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
818 args.push(new symbol(hygienic, this.args[i].symbols)); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
819 } else { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
820 args.push(this.args[i]); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
821 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
822 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
823 for (var i = 0; i < this.expressions.length; i++) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
824 expressions.push(this.expressions[i].makeHygienic(env)); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
825 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
826 return new lambda(args, expressions); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
827 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
828 |
210
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
829 lambda.prototype.numArgs = function() { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
830 var num = this.args.length; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
831 if (num && (this.args[0].cleanName() == 'self')) { |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
832 --num; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
833 } |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
834 return num; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
835 }; |
d0848563f25d
Fix some bugs and allow proper access to list literals in interpreter/macro expander
Mike Pavone <pavone@retrodev.com>
parents:
209
diff
changeset
|
836 |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
837 lambda.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
838 return "lambda"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
839 }; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
840 |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
841 lambda.prototype.tpmeth_args = function() { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
842 var cur = tplist.tpmeth_empty(); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
843 for (var idx = this.args.length - 1; idx >= 0; --idx) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
844 cur = tplist['tpmeth_node:withTail'](this.args[idx], cur); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
845 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
846 return cur; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
847 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
848 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
849 lambda.prototype.tpmeth_expressions = function() { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
850 var cur = tplist.tpmeth_empty(); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
851 for (var idx = this.expressions.length - 1; idx >= 0; --idx) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
852 cur = tplist['tpmeth_node:withTail'](this.expressions[idx], cur); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
853 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
854 return cur; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
855 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
856 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
857 lambda.prototype['tpmeth_expressions!'] = function(exprs) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
858 var expressions = []; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
859 while (!exprs['tpmeth_empty?']().valueOf()) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
860 expressions.push(makeASTNode(exprs.tpmeth_value())); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
861 exprs = exprs.tpmeth_tail(); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
862 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
863 this.expressions = expressions; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
864 return this; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
865 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
866 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
867 lambda.prototype.tpmeth_addExpression = function(expr) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
868 this.expressions.push(makeASTNode(expr)); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
869 return this; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
870 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
871 |
206
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
872 assignment.prototype.eval = function(env) { |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
873 var val = this.expression.eval(env); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
874 env.findSet(this.symbol.name, val); |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
875 return val; |
b4a9d4e405c5
Implemented a simple interpreter to be used for macro expansion and a driver for testing it
Mike Pavone <pavone@retrodev.com>
parents:
diff
changeset
|
876 }; |
207
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
877 |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
878 assignment.prototype.macroexpand = function(env) { |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
879 this.expression = this.expression.macroexpand(env); |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
880 return this; |
60eff5f81d9a
Basic implementation of macros is now working
Mike Pavone <pavone@retrodev.com>
parents:
206
diff
changeset
|
881 }; |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
882 |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
883 assignment.prototype.quote = function(env) { |
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
884 var name = this.symbol.cleanName(); |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
885 var val = env.find(name); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
886 var dirty = true; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
887 if (val) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
888 var node = makeASTNode(val); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
889 if (!(node instanceof symbol)) { |
221
218b11ec8fa2
Better handling for weird values being inserted into AST due to quoting
Michael Pavone <pavone@retrodev.com>
parents:
219
diff
changeset
|
890 throw new Error('Left hand side of assignment expression must be a symbol not a '+ node.constructor.name + ' '+(typeof node) + ', old name was ' + name); |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
891 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
892 name = node.cleanName(); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
893 dirty = node.dirty; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
894 } |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
895 env.syms[name] = null; |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
896 var sym = new symbol(name, this.symbol.symbols); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
897 sym.dirty = dirty; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
898 return new assignment(sym, this.expression.quote(env)); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
899 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
900 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
901 assignment.prototype.makeHygienic = function(env) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
902 var name = this.symbol.cleanName(); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
903 env.syms[name] = null; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
904 if (this.symbol.dirty) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
905 name = env.quotetrans[name] = '' + quote_prefix + name; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
906 } |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
907 return new assignment(new symbol(name, this.symbol.symbols), this.expression.makeHygienic(env)); |
208
a1b4a2bc8d72
Initial work on pattern match macrosfor the new parser
Mike Pavone <pavone@retrodev.com>
parents:
207
diff
changeset
|
908 }; |
209
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
909 |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
910 assignment.prototype.tpmeth_nodeType = function() { |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
911 return "assignment"; |
4b3b57f39f10
Implement zeroPlus macro
Michael Pavone <pavone@retrodev.com>
parents:
208
diff
changeset
|
912 }; |
217
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
913 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
914 assignment.prototype.tpmeth_symbol = function() { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
915 return this.symbol; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
916 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
917 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
918 assignment.prototype['tpmeth_symbol!'] = function(val) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
919 this.symbol = makeASTNode(val); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
920 return this; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
921 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
922 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
923 assignment.prototype.tpmeth_expression = function() { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
924 return this.expression; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
925 }; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
926 |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
927 assignment.prototype['tpmeth_expression!'] = function(val) { |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
928 this.expression = makeASTNode(val); |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
929 return this; |
adad61ea2f3a
Switched to a less hacky implementation of hygiene and exposed more AST properties to macros
Michael Pavone <pavone@retrodev.com>
parents:
213
diff
changeset
|
930 }; |