heist 0.1.0 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/History.txt +17 -0
- data/Manifest.txt +23 -19
- data/README.txt +84 -52
- data/lib/builtin/library.scm +208 -10
- data/lib/builtin/primitives.rb +154 -92
- data/lib/builtin/syntax.scm +22 -5
- data/lib/heist.rb +49 -17
- data/lib/parser/nodes.rb +47 -24
- data/lib/parser/ruby.rb +29 -0
- data/lib/parser/scheme.rb +455 -143
- data/lib/parser/scheme.tt +23 -5
- data/lib/repl.rb +19 -16
- data/lib/runtime/binding.rb +24 -2
- data/lib/runtime/callable/continuation.rb +23 -2
- data/lib/runtime/callable/function.rb +122 -21
- data/lib/runtime/callable/macro.rb +169 -123
- data/lib/runtime/callable/macro/expansion.rb +137 -2
- data/lib/runtime/callable/macro/matches.rb +125 -41
- data/lib/runtime/callable/macro/tree.rb +141 -0
- data/lib/runtime/callable/syntax.rb +44 -0
- data/lib/runtime/data/cons.rb +234 -0
- data/lib/runtime/data/expression.rb +15 -6
- data/lib/runtime/data/identifier.rb +19 -2
- data/lib/runtime/frame.rb +102 -35
- data/lib/runtime/runtime.rb +44 -19
- data/lib/runtime/scope.rb +145 -30
- data/lib/runtime/stack.rb +103 -1
- data/lib/runtime/stackless.rb +48 -6
- data/test/arithmetic.scm +11 -2
- data/test/continuations.scm +16 -2
- data/test/equivalence.scm +34 -0
- data/test/functional.scm +4 -0
- data/test/lists.scm +78 -0
- data/test/macro-helpers.scm +1 -0
- data/test/macros.scm +111 -24
- data/test/numbers.scm +30 -8
- data/test/test_heist.rb +67 -12
- metadata +25 -21
- data/lib/builtin/syntax.rb +0 -166
- data/lib/runtime/callable/macro/splice.rb +0 -56
- data/lib/runtime/data/list.rb +0 -36
data/lib/parser/nodes.rb
CHANGED
@@ -1,6 +1,16 @@
|
|
1
1
|
module Heist
|
2
|
+
# The +Scheme+ module hosts various classes used by the +SchemeParser+ class,
|
3
|
+
# which is generated from a parsing expression grammar using +Treetop+. (See
|
4
|
+
# <tt>lib/parser/scheme.tt</tt>.) The classes map syntax structures generated
|
5
|
+
# by +Treetop+ to Heist runtime objects for execution. All the classes except
|
6
|
+
# +Program+ are evaluated without a runtime environment; evaluating them
|
7
|
+
# simply casts to non-Treetop objects in the Heist library, or to raw Ruby
|
8
|
+
# objects. Evaluating a +Program+ requires a +Runtime+ in which to do so.
|
2
9
|
module Scheme
|
3
10
|
|
11
|
+
# Any list-generating shorthands present in the grammar should be listed here.
|
12
|
+
# In Scheme, this list includes the various quoting symbols that can be used
|
13
|
+
# as shorthands for calling quoting functions.
|
4
14
|
SHORTHANDS = {
|
5
15
|
"'" => :quote,
|
6
16
|
"`" => :quasiquote,
|
@@ -8,50 +18,63 @@ module Heist
|
|
8
18
|
",@" => :'unquote-splicing'
|
9
19
|
}
|
10
20
|
|
21
|
+
# +Program+ is the root of the parse tree; parsing any string of Scheme code
|
22
|
+
# produces one of these.
|
11
23
|
class Program < Treetop::Runtime::SyntaxNode
|
24
|
+
# Evaluates all the expressions in the +Program+ in order, returning the
|
25
|
+
# result of the last expression.
|
12
26
|
def eval(scope)
|
13
27
|
convert!
|
14
28
|
@data.map { |part| Heist.evaluate(part, scope) }.last
|
15
29
|
end
|
16
30
|
|
31
|
+
# Converts all the +Treetop+ objects in the +Program+ to Heist objects
|
32
|
+
# and raw Ruby data ready for interpretation using a +Runtime+.
|
17
33
|
def convert!
|
18
34
|
return if @data
|
19
|
-
@data =
|
20
|
-
elements.each_with_index { |cell, i| self[i] = cell.eval }
|
21
|
-
end
|
22
|
-
|
23
|
-
def [](index)
|
24
|
-
@data[index]
|
25
|
-
end
|
26
|
-
|
27
|
-
def []=(index, value)
|
28
|
-
value.exists_at!(self, index) if Runtime::Expression === value
|
29
|
-
@data[index] = value
|
35
|
+
@data = Runtime::Cons.construct(elements, true) { |c| c.eval }
|
30
36
|
end
|
31
37
|
end
|
32
38
|
|
39
|
+
# A +List+ has an array of +cells+, and optionally a +tail+ if it's an
|
40
|
+
# improper list or a dotted pair.
|
33
41
|
module List
|
42
|
+
# Evaluating a +List+ produces a Heist +Cons+ object.
|
34
43
|
def eval
|
35
|
-
list = Runtime::
|
36
|
-
|
44
|
+
list = Runtime::Cons.construct(cells, true) { |c| c.eval }
|
45
|
+
list.tail.cdr = tail.cell.eval if tail.respond_to?(:dot)
|
37
46
|
list
|
38
47
|
end
|
39
48
|
|
40
49
|
def cells
|
41
|
-
@cells ||= elements[1].elements
|
50
|
+
@cells ||= elements[1].elements[0].elements
|
51
|
+
end
|
52
|
+
|
53
|
+
def tail
|
54
|
+
@tail ||= elements[1].elements[1]
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
# <tt>QuotedCell</tt> are generated using the quoting shorthands.
|
59
|
+
class QuotedCell < Treetop::Runtime::SyntaxNode
|
60
|
+
# Evaluating a +QuotedCell+ produces a +Cons+ that expresses a function
|
61
|
+
# call to the appropriate quoting function, with the cell as the argument.
|
62
|
+
def eval
|
63
|
+
quote = elements[1].text_value
|
64
|
+
cell = elements[2].eval
|
65
|
+
Runtime::Cons.construct([Runtime::Identifier.new(SHORTHANDS[quote]), cell])
|
42
66
|
end
|
43
67
|
end
|
44
68
|
|
69
|
+
# <tt>Cells</tt> are any piece of Scheme data: numbers, booleans, strings,
|
70
|
+
# lists. Any building block of Scheme code goes in a +Cell+.
|
45
71
|
class Cell < Treetop::Runtime::SyntaxNode
|
46
72
|
def eval
|
47
|
-
|
48
|
-
string = elements[1].text_value
|
49
|
-
SHORTHANDS.has_key?(string) ?
|
50
|
-
Runtime::List.new([Runtime::Identifier.new(SHORTHANDS[string]), result]) :
|
51
|
-
result
|
73
|
+
elements[1].eval
|
52
74
|
end
|
53
75
|
end
|
54
76
|
|
77
|
+
# A +Datum+ is any piece of atomic literal data.
|
55
78
|
class Datum < Treetop::Runtime::SyntaxNode
|
56
79
|
def eval
|
57
80
|
elements[0].eval
|
@@ -66,25 +89,25 @@ module Heist
|
|
66
89
|
|
67
90
|
class Complex < Treetop::Runtime::SyntaxNode
|
68
91
|
def eval
|
69
|
-
|
92
|
+
@value ||= Heist.complex(real.eval, imaginary.eval)
|
70
93
|
end
|
71
94
|
end
|
72
95
|
|
73
96
|
class Real < Treetop::Runtime::SyntaxNode
|
74
97
|
def eval
|
75
|
-
@value ||=
|
98
|
+
@value ||= text_value.to_f
|
76
99
|
end
|
77
100
|
end
|
78
101
|
|
79
102
|
class Rational < Treetop::Runtime::SyntaxNode
|
80
103
|
def eval
|
81
|
-
@value ||= numerator.eval
|
104
|
+
@value ||= Heist.rational(numerator.eval, denominator.eval)
|
82
105
|
end
|
83
106
|
end
|
84
107
|
|
85
108
|
class Integer < Treetop::Runtime::SyntaxNode
|
86
109
|
def eval
|
87
|
-
@value ||=
|
110
|
+
@value ||= text_value.to_i
|
88
111
|
end
|
89
112
|
end
|
90
113
|
|
@@ -94,7 +117,7 @@ module Heist
|
|
94
117
|
end
|
95
118
|
end
|
96
119
|
|
97
|
-
|
120
|
+
module Identifier
|
98
121
|
def eval
|
99
122
|
Runtime::Identifier.new(text_value)
|
100
123
|
end
|
data/lib/parser/ruby.rb
ADDED
@@ -0,0 +1,29 @@
|
|
1
|
+
module Heist
|
2
|
+
# +RubyParser+ parses non-string code given as Ruby data such as arrays. It
|
3
|
+
# allows Lisp-style code to be expressed inline with Ruby, for example:
|
4
|
+
#
|
5
|
+
# scheme = Heist::Runtime.new
|
6
|
+
# scheme.exec [:define, [:square, :x], [:*, :x, :x]]
|
7
|
+
# scheme.exec [:square, 9]
|
8
|
+
# #=> 81
|
9
|
+
#
|
10
|
+
# The above API uses +RubyParser+ behind the scenes to turn Ruby data into
|
11
|
+
# Heist runtime objects such as +Cons+ based lists before execution.
|
12
|
+
#
|
13
|
+
class RubyParser
|
14
|
+
|
15
|
+
# Parses a single piece of Ruby data in
|
16
|
+
def parse(source)
|
17
|
+
case source
|
18
|
+
when Array then
|
19
|
+
Runtime::Cons.construct(source) { |cell| parse(cell) }
|
20
|
+
when Symbol then
|
21
|
+
Runtime::Identifier.new(source)
|
22
|
+
else
|
23
|
+
source
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
data/lib/parser/scheme.rb
CHANGED
@@ -1,5 +1,5 @@
|
|
1
1
|
module Heist
|
2
|
-
module Scheme
|
2
|
+
module Scheme #:nodoc:
|
3
3
|
include Treetop::Runtime
|
4
4
|
|
5
5
|
def root
|
@@ -30,17 +30,27 @@ module Heist
|
|
30
30
|
return r0
|
31
31
|
end
|
32
32
|
|
33
|
-
module Cell0
|
33
|
+
module Cell0 #:nodoc:
|
34
34
|
def ignore
|
35
35
|
elements[0]
|
36
36
|
end
|
37
37
|
|
38
|
-
def
|
38
|
+
def quote
|
39
|
+
elements[1]
|
40
|
+
end
|
41
|
+
|
42
|
+
def cell
|
39
43
|
elements[2]
|
40
44
|
end
|
45
|
+
end
|
41
46
|
|
47
|
+
module Cell1 #:nodoc:
|
42
48
|
def ignore
|
43
|
-
elements[
|
49
|
+
elements[0]
|
50
|
+
end
|
51
|
+
|
52
|
+
def ignore
|
53
|
+
elements[2]
|
44
54
|
end
|
45
55
|
end
|
46
56
|
|
@@ -52,48 +62,64 @@ module Heist
|
|
52
62
|
return cached
|
53
63
|
end
|
54
64
|
|
55
|
-
i0
|
56
|
-
|
57
|
-
|
58
|
-
|
65
|
+
i0 = index
|
66
|
+
i1, s1 = index, []
|
67
|
+
r2 = _nt_ignore
|
68
|
+
s1 << r2
|
69
|
+
if r2
|
59
70
|
r3 = _nt_quote
|
71
|
+
s1 << r3
|
60
72
|
if r3
|
61
|
-
|
62
|
-
|
63
|
-
r2 = SyntaxNode.new(input, index...index)
|
73
|
+
r4 = _nt_cell
|
74
|
+
s1 << r4
|
64
75
|
end
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
76
|
+
end
|
77
|
+
if s1.last
|
78
|
+
r1 = (QuotedCell).new(input, i1...index, s1)
|
79
|
+
r1.extend(Cell0)
|
80
|
+
else
|
81
|
+
self.index = i1
|
82
|
+
r1 = nil
|
83
|
+
end
|
84
|
+
if r1
|
85
|
+
r0 = r1
|
86
|
+
else
|
87
|
+
i5, s5 = index, []
|
88
|
+
r6 = _nt_ignore
|
89
|
+
s5 << r6
|
90
|
+
if r6
|
91
|
+
i7 = index
|
92
|
+
r8 = _nt_list
|
93
|
+
if r8
|
94
|
+
r7 = r8
|
95
|
+
else
|
96
|
+
r9 = _nt_atom
|
97
|
+
if r9
|
98
|
+
r7 = r9
|
74
99
|
else
|
75
|
-
|
76
|
-
|
77
|
-
r5 = r7
|
78
|
-
else
|
79
|
-
self.index = i5
|
80
|
-
r5 = nil
|
81
|
-
end
|
82
|
-
end
|
83
|
-
s0 << r5
|
84
|
-
if r5
|
85
|
-
r8 = _nt_ignore
|
86
|
-
s0 << r8
|
100
|
+
self.index = i7
|
101
|
+
r7 = nil
|
87
102
|
end
|
88
103
|
end
|
104
|
+
s5 << r7
|
105
|
+
if r7
|
106
|
+
r10 = _nt_ignore
|
107
|
+
s5 << r10
|
108
|
+
end
|
109
|
+
end
|
110
|
+
if s5.last
|
111
|
+
r5 = (Cell).new(input, i5...index, s5)
|
112
|
+
r5.extend(Cell1)
|
113
|
+
else
|
114
|
+
self.index = i5
|
115
|
+
r5 = nil
|
116
|
+
end
|
117
|
+
if r5
|
118
|
+
r0 = r5
|
119
|
+
else
|
120
|
+
self.index = i0
|
121
|
+
r0 = nil
|
89
122
|
end
|
90
|
-
end
|
91
|
-
if s0.last
|
92
|
-
r0 = (Cell).new(input, i0...index, s0)
|
93
|
-
r0.extend(Cell0)
|
94
|
-
else
|
95
|
-
self.index = i0
|
96
|
-
r0 = nil
|
97
123
|
end
|
98
124
|
|
99
125
|
node_cache[:cell][start_index] = r0
|
@@ -162,10 +188,39 @@ module Heist
|
|
162
188
|
return r0
|
163
189
|
end
|
164
190
|
|
165
|
-
|
191
|
+
def _nt_dot
|
192
|
+
start_index = index
|
193
|
+
if node_cache[:dot].has_key?(index)
|
194
|
+
cached = node_cache[:dot][index]
|
195
|
+
@index = cached.interval.end if cached
|
196
|
+
return cached
|
197
|
+
end
|
198
|
+
|
199
|
+
if input.index(".", index) == index
|
200
|
+
r0 = (SyntaxNode).new(input, index...(index + 1))
|
201
|
+
@index += 1
|
202
|
+
else
|
203
|
+
terminal_parse_failure(".")
|
204
|
+
r0 = nil
|
205
|
+
end
|
206
|
+
|
207
|
+
node_cache[:dot][start_index] = r0
|
208
|
+
|
209
|
+
return r0
|
166
210
|
end
|
167
211
|
|
168
|
-
module
|
212
|
+
module List0 #:nodoc:
|
213
|
+
def cells
|
214
|
+
elements[1]
|
215
|
+
end
|
216
|
+
|
217
|
+
end
|
218
|
+
|
219
|
+
module List1 #:nodoc:
|
220
|
+
def cells
|
221
|
+
elements[1]
|
222
|
+
end
|
223
|
+
|
169
224
|
end
|
170
225
|
|
171
226
|
def _nt_list
|
@@ -187,26 +242,17 @@ module Heist
|
|
187
242
|
end
|
188
243
|
s1 << r2
|
189
244
|
if r2
|
190
|
-
|
191
|
-
loop do
|
192
|
-
r4 = _nt_cell
|
193
|
-
if r4
|
194
|
-
s3 << r4
|
195
|
-
else
|
196
|
-
break
|
197
|
-
end
|
198
|
-
end
|
199
|
-
r3 = SyntaxNode.new(input, i3...index, s3)
|
245
|
+
r3 = _nt_cells
|
200
246
|
s1 << r3
|
201
247
|
if r3
|
202
248
|
if input.index(")", index) == index
|
203
|
-
|
249
|
+
r4 = (SyntaxNode).new(input, index...(index + 1))
|
204
250
|
@index += 1
|
205
251
|
else
|
206
252
|
terminal_parse_failure(")")
|
207
|
-
|
253
|
+
r4 = nil
|
208
254
|
end
|
209
|
-
s1 <<
|
255
|
+
s1 << r4
|
210
256
|
end
|
211
257
|
end
|
212
258
|
if s1.last
|
@@ -220,47 +266,38 @@ module Heist
|
|
220
266
|
r0 = r1
|
221
267
|
r0.extend(List)
|
222
268
|
else
|
223
|
-
|
269
|
+
i5, s5 = index, []
|
224
270
|
if input.index("[", index) == index
|
225
|
-
|
271
|
+
r6 = (SyntaxNode).new(input, index...(index + 1))
|
226
272
|
@index += 1
|
227
273
|
else
|
228
274
|
terminal_parse_failure("[")
|
229
|
-
|
275
|
+
r6 = nil
|
230
276
|
end
|
231
|
-
|
232
|
-
if
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
if r9
|
237
|
-
s8 << r9
|
238
|
-
else
|
239
|
-
break
|
240
|
-
end
|
241
|
-
end
|
242
|
-
r8 = SyntaxNode.new(input, i8...index, s8)
|
243
|
-
s6 << r8
|
244
|
-
if r8
|
277
|
+
s5 << r6
|
278
|
+
if r6
|
279
|
+
r7 = _nt_cells
|
280
|
+
s5 << r7
|
281
|
+
if r7
|
245
282
|
if input.index("]", index) == index
|
246
|
-
|
283
|
+
r8 = (SyntaxNode).new(input, index...(index + 1))
|
247
284
|
@index += 1
|
248
285
|
else
|
249
286
|
terminal_parse_failure("]")
|
250
|
-
|
287
|
+
r8 = nil
|
251
288
|
end
|
252
|
-
|
289
|
+
s5 << r8
|
253
290
|
end
|
254
291
|
end
|
255
|
-
if
|
256
|
-
|
257
|
-
|
292
|
+
if s5.last
|
293
|
+
r5 = (SyntaxNode).new(input, i5...index, s5)
|
294
|
+
r5.extend(List1)
|
258
295
|
else
|
259
|
-
self.index =
|
260
|
-
|
296
|
+
self.index = i5
|
297
|
+
r5 = nil
|
261
298
|
end
|
262
|
-
if
|
263
|
-
r0 =
|
299
|
+
if r5
|
300
|
+
r0 = r5
|
264
301
|
r0.extend(List)
|
265
302
|
else
|
266
303
|
self.index = i0
|
@@ -273,6 +310,122 @@ module Heist
|
|
273
310
|
return r0
|
274
311
|
end
|
275
312
|
|
313
|
+
module Cells0 #:nodoc:
|
314
|
+
def dot
|
315
|
+
elements[0]
|
316
|
+
end
|
317
|
+
|
318
|
+
def space
|
319
|
+
elements[1]
|
320
|
+
end
|
321
|
+
|
322
|
+
def cell
|
323
|
+
elements[2]
|
324
|
+
end
|
325
|
+
end
|
326
|
+
|
327
|
+
module Cells1 #:nodoc:
|
328
|
+
end
|
329
|
+
|
330
|
+
module Cells2 #:nodoc:
|
331
|
+
def ignore
|
332
|
+
elements[1]
|
333
|
+
end
|
334
|
+
end
|
335
|
+
|
336
|
+
def _nt_cells
|
337
|
+
start_index = index
|
338
|
+
if node_cache[:cells].has_key?(index)
|
339
|
+
cached = node_cache[:cells][index]
|
340
|
+
@index = cached.interval.end if cached
|
341
|
+
return cached
|
342
|
+
end
|
343
|
+
|
344
|
+
i0 = index
|
345
|
+
i1, s1 = index, []
|
346
|
+
s2, i2 = [], index
|
347
|
+
loop do
|
348
|
+
r3 = _nt_cell
|
349
|
+
if r3
|
350
|
+
s2 << r3
|
351
|
+
else
|
352
|
+
break
|
353
|
+
end
|
354
|
+
end
|
355
|
+
if s2.empty?
|
356
|
+
self.index = i2
|
357
|
+
r2 = nil
|
358
|
+
else
|
359
|
+
r2 = SyntaxNode.new(input, i2...index, s2)
|
360
|
+
end
|
361
|
+
s1 << r2
|
362
|
+
if r2
|
363
|
+
i4, s4 = index, []
|
364
|
+
r5 = _nt_dot
|
365
|
+
s4 << r5
|
366
|
+
if r5
|
367
|
+
r6 = _nt_space
|
368
|
+
s4 << r6
|
369
|
+
if r6
|
370
|
+
r7 = _nt_cell
|
371
|
+
s4 << r7
|
372
|
+
end
|
373
|
+
end
|
374
|
+
if s4.last
|
375
|
+
r4 = (SyntaxNode).new(input, i4...index, s4)
|
376
|
+
r4.extend(Cells0)
|
377
|
+
else
|
378
|
+
self.index = i4
|
379
|
+
r4 = nil
|
380
|
+
end
|
381
|
+
s1 << r4
|
382
|
+
end
|
383
|
+
if s1.last
|
384
|
+
r1 = (SyntaxNode).new(input, i1...index, s1)
|
385
|
+
r1.extend(Cells1)
|
386
|
+
else
|
387
|
+
self.index = i1
|
388
|
+
r1 = nil
|
389
|
+
end
|
390
|
+
if r1
|
391
|
+
r0 = r1
|
392
|
+
else
|
393
|
+
i8, s8 = index, []
|
394
|
+
s9, i9 = [], index
|
395
|
+
loop do
|
396
|
+
r10 = _nt_cell
|
397
|
+
if r10
|
398
|
+
s9 << r10
|
399
|
+
else
|
400
|
+
break
|
401
|
+
end
|
402
|
+
end
|
403
|
+
r9 = SyntaxNode.new(input, i9...index, s9)
|
404
|
+
s8 << r9
|
405
|
+
if r9
|
406
|
+
r11 = _nt_ignore
|
407
|
+
s8 << r11
|
408
|
+
end
|
409
|
+
if s8.last
|
410
|
+
r8 = (SyntaxNode).new(input, i8...index, s8)
|
411
|
+
r8.extend(Cells2)
|
412
|
+
else
|
413
|
+
self.index = i8
|
414
|
+
r8 = nil
|
415
|
+
end
|
416
|
+
if r8
|
417
|
+
r0 = r8
|
418
|
+
else
|
419
|
+
self.index = i0
|
420
|
+
r0 = nil
|
421
|
+
end
|
422
|
+
end
|
423
|
+
|
424
|
+
node_cache[:cells][start_index] = r0
|
425
|
+
|
426
|
+
return r0
|
427
|
+
end
|
428
|
+
|
276
429
|
def _nt_atom
|
277
430
|
start_index = index
|
278
431
|
if node_cache[:atom].has_key?(index)
|
@@ -300,10 +453,10 @@ module Heist
|
|
300
453
|
return r0
|
301
454
|
end
|
302
455
|
|
303
|
-
module Datum0
|
456
|
+
module Datum0 #:nodoc:
|
304
457
|
end
|
305
458
|
|
306
|
-
module Datum1
|
459
|
+
module Datum1 #:nodoc:
|
307
460
|
end
|
308
461
|
|
309
462
|
def _nt_datum
|
@@ -462,12 +615,12 @@ module Heist
|
|
462
615
|
return r0
|
463
616
|
end
|
464
617
|
|
465
|
-
module Complex0
|
618
|
+
module Complex0 #:nodoc:
|
466
619
|
def real
|
467
620
|
elements[0]
|
468
621
|
end
|
469
622
|
|
470
|
-
def
|
623
|
+
def imaginary
|
471
624
|
elements[2]
|
472
625
|
end
|
473
626
|
|
@@ -482,29 +635,53 @@ module Heist
|
|
482
635
|
end
|
483
636
|
|
484
637
|
i0, s0 = index, []
|
485
|
-
|
638
|
+
i1 = index
|
639
|
+
r2 = _nt_real
|
640
|
+
if r2
|
641
|
+
r1 = r2
|
642
|
+
else
|
643
|
+
r3 = _nt_integer
|
644
|
+
if r3
|
645
|
+
r1 = r3
|
646
|
+
else
|
647
|
+
self.index = i1
|
648
|
+
r1 = nil
|
649
|
+
end
|
650
|
+
end
|
486
651
|
s0 << r1
|
487
652
|
if r1
|
488
653
|
if input.index("+", index) == index
|
489
|
-
|
654
|
+
r4 = (SyntaxNode).new(input, index...(index + 1))
|
490
655
|
@index += 1
|
491
656
|
else
|
492
657
|
terminal_parse_failure("+")
|
493
|
-
|
658
|
+
r4 = nil
|
494
659
|
end
|
495
|
-
s0 <<
|
496
|
-
if
|
497
|
-
|
498
|
-
|
499
|
-
if
|
660
|
+
s0 << r4
|
661
|
+
if r4
|
662
|
+
i5 = index
|
663
|
+
r6 = _nt_real
|
664
|
+
if r6
|
665
|
+
r5 = r6
|
666
|
+
else
|
667
|
+
r7 = _nt_integer
|
668
|
+
if r7
|
669
|
+
r5 = r7
|
670
|
+
else
|
671
|
+
self.index = i5
|
672
|
+
r5 = nil
|
673
|
+
end
|
674
|
+
end
|
675
|
+
s0 << r5
|
676
|
+
if r5
|
500
677
|
if input.index("i", index) == index
|
501
|
-
|
678
|
+
r8 = (SyntaxNode).new(input, index...(index + 1))
|
502
679
|
@index += 1
|
503
680
|
else
|
504
681
|
terminal_parse_failure("i")
|
505
|
-
|
682
|
+
r8 = nil
|
506
683
|
end
|
507
|
-
s0 <<
|
684
|
+
s0 << r8
|
508
685
|
end
|
509
686
|
end
|
510
687
|
end
|
@@ -521,10 +698,10 @@ module Heist
|
|
521
698
|
return r0
|
522
699
|
end
|
523
700
|
|
524
|
-
module Real0
|
701
|
+
module Real0 #:nodoc:
|
525
702
|
end
|
526
703
|
|
527
|
-
module Real1
|
704
|
+
module Real1 #:nodoc:
|
528
705
|
def integer
|
529
706
|
elements[0]
|
530
707
|
end
|
@@ -592,7 +769,7 @@ module Heist
|
|
592
769
|
return r0
|
593
770
|
end
|
594
771
|
|
595
|
-
module Rational0
|
772
|
+
module Rational0 #:nodoc:
|
596
773
|
def numerator
|
597
774
|
elements[0]
|
598
775
|
end
|
@@ -640,10 +817,10 @@ module Heist
|
|
640
817
|
return r0
|
641
818
|
end
|
642
819
|
|
643
|
-
module Integer0
|
820
|
+
module Integer0 #:nodoc:
|
644
821
|
end
|
645
822
|
|
646
|
-
module Integer1
|
823
|
+
module Integer1 #:nodoc:
|
647
824
|
end
|
648
825
|
|
649
826
|
def _nt_integer
|
@@ -730,7 +907,7 @@ module Heist
|
|
730
907
|
return r0
|
731
908
|
end
|
732
909
|
|
733
|
-
module String0
|
910
|
+
module String0 #:nodoc:
|
734
911
|
end
|
735
912
|
|
736
913
|
def _nt_string
|
@@ -809,7 +986,16 @@ module Heist
|
|
809
986
|
return r0
|
810
987
|
end
|
811
988
|
|
812
|
-
module Identifier0
|
989
|
+
module Identifier0 #:nodoc:
|
990
|
+
end
|
991
|
+
|
992
|
+
module Identifier1 #:nodoc:
|
993
|
+
end
|
994
|
+
|
995
|
+
module Identifier2 #:nodoc:
|
996
|
+
end
|
997
|
+
|
998
|
+
module Identifier3 #:nodoc:
|
813
999
|
end
|
814
1000
|
|
815
1001
|
def _nt_identifier
|
@@ -820,47 +1006,126 @@ module Heist
|
|
820
1006
|
return cached
|
821
1007
|
end
|
822
1008
|
|
823
|
-
|
824
|
-
|
825
|
-
|
826
|
-
|
827
|
-
|
828
|
-
|
829
|
-
|
1009
|
+
i0 = index
|
1010
|
+
i1, s1 = index, []
|
1011
|
+
i2, s2 = index, []
|
1012
|
+
i3 = index
|
1013
|
+
r4 = _nt_delimiter
|
1014
|
+
if r4
|
1015
|
+
r3 = nil
|
1016
|
+
else
|
1017
|
+
self.index = i3
|
1018
|
+
r3 = SyntaxNode.new(input, index...index)
|
1019
|
+
end
|
1020
|
+
s2 << r3
|
1021
|
+
if r3
|
1022
|
+
if index < input_length
|
1023
|
+
r5 = (SyntaxNode).new(input, index...(index + 1))
|
1024
|
+
@index += 1
|
830
1025
|
else
|
831
|
-
|
832
|
-
|
1026
|
+
terminal_parse_failure("any character")
|
1027
|
+
r5 = nil
|
833
1028
|
end
|
834
|
-
|
835
|
-
|
1029
|
+
s2 << r5
|
1030
|
+
end
|
1031
|
+
if s2.last
|
1032
|
+
r2 = (SyntaxNode).new(input, i2...index, s2)
|
1033
|
+
r2.extend(Identifier0)
|
1034
|
+
else
|
1035
|
+
self.index = i2
|
1036
|
+
r2 = nil
|
1037
|
+
end
|
1038
|
+
s1 << r2
|
1039
|
+
if r2
|
1040
|
+
s6, i6 = [], index
|
1041
|
+
loop do
|
1042
|
+
i7, s7 = index, []
|
1043
|
+
i8 = index
|
1044
|
+
r9 = _nt_delimiter
|
1045
|
+
if r9
|
1046
|
+
r8 = nil
|
1047
|
+
else
|
1048
|
+
self.index = i8
|
1049
|
+
r8 = SyntaxNode.new(input, index...index)
|
1050
|
+
end
|
1051
|
+
s7 << r8
|
1052
|
+
if r8
|
1053
|
+
if index < input_length
|
1054
|
+
r10 = (SyntaxNode).new(input, index...(index + 1))
|
1055
|
+
@index += 1
|
1056
|
+
else
|
1057
|
+
terminal_parse_failure("any character")
|
1058
|
+
r10 = nil
|
1059
|
+
end
|
1060
|
+
s7 << r10
|
1061
|
+
end
|
1062
|
+
if s7.last
|
1063
|
+
r7 = (SyntaxNode).new(input, i7...index, s7)
|
1064
|
+
r7.extend(Identifier1)
|
1065
|
+
else
|
1066
|
+
self.index = i7
|
1067
|
+
r7 = nil
|
1068
|
+
end
|
1069
|
+
if r7
|
1070
|
+
s6 << r7
|
1071
|
+
else
|
1072
|
+
break
|
1073
|
+
end
|
1074
|
+
end
|
1075
|
+
if s6.empty?
|
1076
|
+
self.index = i6
|
1077
|
+
r6 = nil
|
1078
|
+
else
|
1079
|
+
r6 = SyntaxNode.new(input, i6...index, s6)
|
1080
|
+
end
|
1081
|
+
s1 << r6
|
1082
|
+
end
|
1083
|
+
if s1.last
|
1084
|
+
r1 = (SyntaxNode).new(input, i1...index, s1)
|
1085
|
+
r1.extend(Identifier2)
|
1086
|
+
else
|
1087
|
+
self.index = i1
|
1088
|
+
r1 = nil
|
1089
|
+
end
|
1090
|
+
if r1
|
1091
|
+
r0 = r1
|
1092
|
+
r0.extend(Identifier)
|
1093
|
+
else
|
1094
|
+
i11, s11 = index, []
|
1095
|
+
i12 = index
|
1096
|
+
r13 = _nt_reserved
|
1097
|
+
if r13
|
1098
|
+
r12 = nil
|
1099
|
+
else
|
1100
|
+
self.index = i12
|
1101
|
+
r12 = SyntaxNode.new(input, index...index)
|
1102
|
+
end
|
1103
|
+
s11 << r12
|
1104
|
+
if r12
|
836
1105
|
if index < input_length
|
837
|
-
|
1106
|
+
r14 = (SyntaxNode).new(input, index...(index + 1))
|
838
1107
|
@index += 1
|
839
1108
|
else
|
840
1109
|
terminal_parse_failure("any character")
|
841
|
-
|
1110
|
+
r14 = nil
|
842
1111
|
end
|
843
|
-
|
1112
|
+
s11 << r14
|
844
1113
|
end
|
845
|
-
if
|
846
|
-
|
847
|
-
|
1114
|
+
if s11.last
|
1115
|
+
r11 = (SyntaxNode).new(input, i11...index, s11)
|
1116
|
+
r11.extend(Identifier3)
|
848
1117
|
else
|
849
|
-
self.index =
|
850
|
-
|
1118
|
+
self.index = i11
|
1119
|
+
r11 = nil
|
851
1120
|
end
|
852
|
-
if
|
853
|
-
|
1121
|
+
if r11
|
1122
|
+
r0 = r11
|
1123
|
+
r0.extend(Identifier)
|
854
1124
|
else
|
855
|
-
|
1125
|
+
self.index = i0
|
1126
|
+
r0 = nil
|
856
1127
|
end
|
857
1128
|
end
|
858
|
-
if s0.empty?
|
859
|
-
self.index = i0
|
860
|
-
r0 = nil
|
861
|
-
else
|
862
|
-
r0 = Identifier.new(input, i0...index, s0)
|
863
|
-
end
|
864
1129
|
|
865
1130
|
node_cache[:identifier][start_index] = r0
|
866
1131
|
|
@@ -887,6 +1152,33 @@ module Heist
|
|
887
1152
|
return r0
|
888
1153
|
end
|
889
1154
|
|
1155
|
+
def _nt_reserved
|
1156
|
+
start_index = index
|
1157
|
+
if node_cache[:reserved].has_key?(index)
|
1158
|
+
cached = node_cache[:reserved][index]
|
1159
|
+
@index = cached.interval.end if cached
|
1160
|
+
return cached
|
1161
|
+
end
|
1162
|
+
|
1163
|
+
i0 = index
|
1164
|
+
r1 = _nt_dot
|
1165
|
+
if r1
|
1166
|
+
r0 = r1
|
1167
|
+
else
|
1168
|
+
r2 = _nt_delimiter
|
1169
|
+
if r2
|
1170
|
+
r0 = r2
|
1171
|
+
else
|
1172
|
+
self.index = i0
|
1173
|
+
r0 = nil
|
1174
|
+
end
|
1175
|
+
end
|
1176
|
+
|
1177
|
+
node_cache[:reserved][start_index] = r0
|
1178
|
+
|
1179
|
+
return r0
|
1180
|
+
end
|
1181
|
+
|
890
1182
|
def _nt_delimiter
|
891
1183
|
start_index = index
|
892
1184
|
if node_cache[:delimiter].has_key?(index)
|
@@ -896,21 +1188,21 @@ module Heist
|
|
896
1188
|
end
|
897
1189
|
|
898
1190
|
i0 = index
|
899
|
-
|
900
|
-
r1 = (SyntaxNode).new(input, index...(index + 1))
|
901
|
-
@index += 1
|
902
|
-
else
|
903
|
-
r1 = nil
|
904
|
-
end
|
1191
|
+
r1 = _nt_quote
|
905
1192
|
if r1
|
906
1193
|
r0 = r1
|
907
1194
|
else
|
908
|
-
r2 =
|
1195
|
+
r2 = _nt_paren
|
909
1196
|
if r2
|
910
1197
|
r0 = r2
|
911
1198
|
else
|
912
|
-
|
913
|
-
|
1199
|
+
r3 = _nt_space
|
1200
|
+
if r3
|
1201
|
+
r0 = r3
|
1202
|
+
else
|
1203
|
+
self.index = i0
|
1204
|
+
r0 = nil
|
1205
|
+
end
|
914
1206
|
end
|
915
1207
|
end
|
916
1208
|
|
@@ -919,6 +1211,26 @@ module Heist
|
|
919
1211
|
return r0
|
920
1212
|
end
|
921
1213
|
|
1214
|
+
def _nt_paren
|
1215
|
+
start_index = index
|
1216
|
+
if node_cache[:paren].has_key?(index)
|
1217
|
+
cached = node_cache[:paren][index]
|
1218
|
+
@index = cached.interval.end if cached
|
1219
|
+
return cached
|
1220
|
+
end
|
1221
|
+
|
1222
|
+
if input.index(Regexp.new('[\\(\\)\\[\\]]'), index) == index
|
1223
|
+
r0 = (SyntaxNode).new(input, index...(index + 1))
|
1224
|
+
@index += 1
|
1225
|
+
else
|
1226
|
+
r0 = nil
|
1227
|
+
end
|
1228
|
+
|
1229
|
+
node_cache[:paren][start_index] = r0
|
1230
|
+
|
1231
|
+
return r0
|
1232
|
+
end
|
1233
|
+
|
922
1234
|
def _nt_space
|
923
1235
|
start_index = index
|
924
1236
|
if node_cache[:space].has_key?(index)
|
@@ -939,7 +1251,7 @@ module Heist
|
|
939
1251
|
return r0
|
940
1252
|
end
|
941
1253
|
|
942
|
-
module Ignore0
|
1254
|
+
module Ignore0 #:nodoc:
|
943
1255
|
end
|
944
1256
|
|
945
1257
|
def _nt_ignore
|
@@ -984,10 +1296,10 @@ module Heist
|
|
984
1296
|
return r0
|
985
1297
|
end
|
986
1298
|
|
987
|
-
module Comment0
|
1299
|
+
module Comment0 #:nodoc:
|
988
1300
|
end
|
989
1301
|
|
990
|
-
module Comment1
|
1302
|
+
module Comment1 #:nodoc:
|
991
1303
|
def ignore
|
992
1304
|
elements[2]
|
993
1305
|
end
|