rubyjs 0.7.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (144) hide show
  1. data/README +128 -0
  2. data/Rakefile +9 -0
  3. data/bin/rubyjs +140 -0
  4. data/examples/ex1/Rakefile +7 -0
  5. data/examples/ex1/ex1.js +771 -0
  6. data/examples/ex1/ex1.rb +42 -0
  7. data/examples/ex1/index.html +7 -0
  8. data/examples/hw/Rakefile +9 -0
  9. data/examples/hw/hw.js +635 -0
  10. data/examples/hw/hw.rb +7 -0
  11. data/examples/hw/index.html +7 -0
  12. data/patches/parse_tree.rb.diff +34 -0
  13. data/rubyjs.gemspec +24 -0
  14. data/src/rubyjs.rb +4 -0
  15. data/src/rubyjs/code_generator.rb +474 -0
  16. data/src/rubyjs/compiler.rb +2007 -0
  17. data/src/rubyjs/debug_name_generator.rb +75 -0
  18. data/src/rubyjs/encoder.rb +171 -0
  19. data/src/rubyjs/eval_into.rb +59 -0
  20. data/src/rubyjs/lib/core.rb +1008 -0
  21. data/src/rubyjs/lib/json.rb +101 -0
  22. data/src/rubyjs/model.rb +287 -0
  23. data/src/rubyjs/name_generator.rb +71 -0
  24. data/src/rwt/AbsolutePanel.rb +161 -0
  25. data/src/rwt/DOM.Konqueror.rb +89 -0
  26. data/src/rwt/DOM.Opera.rb +65 -0
  27. data/src/rwt/DOM.rb +1044 -0
  28. data/src/rwt/Event.Opera.rb +35 -0
  29. data/src/rwt/Event.rb +429 -0
  30. data/src/rwt/HTTPRequest.IE6.rb +5 -0
  31. data/src/rwt/HTTPRequest.rb +74 -0
  32. data/src/rwt/Label.rb +164 -0
  33. data/src/rwt/Panel.rb +90 -0
  34. data/src/rwt/RootPanel.rb +16 -0
  35. data/src/rwt/UIObject.rb +495 -0
  36. data/src/rwt/Widget.rb +193 -0
  37. data/src/rwt/ported-from/AbsolutePanel.java +158 -0
  38. data/src/rwt/ported-from/DOM.java +571 -0
  39. data/src/rwt/ported-from/DOMImpl.java +426 -0
  40. data/src/rwt/ported-from/DOMImplOpera.java +82 -0
  41. data/src/rwt/ported-from/DOMImplStandard.java +234 -0
  42. data/src/rwt/ported-from/HTTPRequest.java +81 -0
  43. data/src/rwt/ported-from/HTTPRequestImpl.java +103 -0
  44. data/src/rwt/ported-from/Label.java +163 -0
  45. data/src/rwt/ported-from/Panel.java +99 -0
  46. data/src/rwt/ported-from/UIObject.java +614 -0
  47. data/src/rwt/ported-from/Widget.java +221 -0
  48. data/test/benchmark/bm_call_conv1.js +16 -0
  49. data/test/benchmark/bm_call_conv2.js +14 -0
  50. data/test/benchmark/bm_var_acc1.js +13 -0
  51. data/test/benchmark/bm_var_acc2.js +11 -0
  52. data/test/benchmark/bm_vm1_block.js +15 -0
  53. data/test/benchmark/bm_vm1_block.rb +15 -0
  54. data/test/benchmark/bm_vm1_const.js +13 -0
  55. data/test/benchmark/bm_vm1_const.rb +13 -0
  56. data/test/benchmark/bm_vm1_ensure.js +17 -0
  57. data/test/benchmark/bm_vm1_ensure.rb +15 -0
  58. data/test/benchmark/common.js +4 -0
  59. data/test/benchmark/common.rb +5 -0
  60. data/test/benchmark/params.yaml +7 -0
  61. data/test/browser.test.html +4059 -0
  62. data/test/browser.test.js +3225 -0
  63. data/test/common.Browser.rb +13 -0
  64. data/test/common.rb +8 -0
  65. data/test/gen_browser_test_suite.rb +129 -0
  66. data/test/gen_test_suite.rb +41 -0
  67. data/test/run_benchs.rb +58 -0
  68. data/test/run_tests.rb +22 -0
  69. data/test/test_args.rb +24 -0
  70. data/test/test_array.rb +26 -0
  71. data/test/test_case.rb +35 -0
  72. data/test/test_class.rb +55 -0
  73. data/test/test_eql.rb +9 -0
  74. data/test/test_exception.rb +61 -0
  75. data/test/test_expr.rb +12 -0
  76. data/test/test_hash.rb +29 -0
  77. data/test/test_if.rb +28 -0
  78. data/test/test_inspect.rb +10 -0
  79. data/test/test_lebewesen.rb +39 -0
  80. data/test/test_massign.rb +66 -0
  81. data/test/test_new.rb +12 -0
  82. data/test/test_range.rb +53 -0
  83. data/test/test_regexp.rb +22 -0
  84. data/test/test_send.rb +65 -0
  85. data/test/test_simple_output.rb +5 -0
  86. data/test/test_splat.rb +21 -0
  87. data/test/test_string.rb +51 -0
  88. data/test/test_yield.rb +152 -0
  89. data/utils/js/Makefile +9 -0
  90. data/utils/js/RunScript.class +0 -0
  91. data/utils/js/RunScript.java +73 -0
  92. data/utils/js/js.jar +0 -0
  93. data/utils/js/run.sh +3 -0
  94. data/utils/jsc/Makefile +7 -0
  95. data/utils/jsc/README +3 -0
  96. data/utils/jsc/RunScript.c +93 -0
  97. data/utils/jsc/run.sh +15 -0
  98. data/utils/yuicompressor/README +1 -0
  99. data/utils/yuicompressor/yuicompressor-2.2.5.jar +0 -0
  100. data/vendor/ParseTree-1.7.1-patched/History.txt +217 -0
  101. data/vendor/ParseTree-1.7.1-patched/Manifest.txt +22 -0
  102. data/vendor/ParseTree-1.7.1-patched/README.txt +110 -0
  103. data/vendor/ParseTree-1.7.1-patched/Rakefile +41 -0
  104. data/vendor/ParseTree-1.7.1-patched/bin/parse_tree_abc +89 -0
  105. data/vendor/ParseTree-1.7.1-patched/bin/parse_tree_audit +28 -0
  106. data/vendor/ParseTree-1.7.1-patched/bin/parse_tree_deps +62 -0
  107. data/vendor/ParseTree-1.7.1-patched/bin/parse_tree_show +49 -0
  108. data/vendor/ParseTree-1.7.1-patched/demo/printer.rb +20 -0
  109. data/vendor/ParseTree-1.7.1-patched/lib/composite_sexp_processor.rb +49 -0
  110. data/vendor/ParseTree-1.7.1-patched/lib/parse_tree.rb +1013 -0
  111. data/vendor/ParseTree-1.7.1-patched/lib/sexp.rb +235 -0
  112. data/vendor/ParseTree-1.7.1-patched/lib/sexp_processor.rb +330 -0
  113. data/vendor/ParseTree-1.7.1-patched/lib/unique.rb +15 -0
  114. data/vendor/ParseTree-1.7.1-patched/test/pt_testcase.rb +1221 -0
  115. data/vendor/ParseTree-1.7.1-patched/test/something.rb +53 -0
  116. data/vendor/ParseTree-1.7.1-patched/test/test_all.rb +13 -0
  117. data/vendor/ParseTree-1.7.1-patched/test/test_composite_sexp_processor.rb +69 -0
  118. data/vendor/ParseTree-1.7.1-patched/test/test_parse_tree.rb +216 -0
  119. data/vendor/ParseTree-1.7.1-patched/test/test_sexp.rb +291 -0
  120. data/vendor/ParseTree-1.7.1-patched/test/test_sexp_processor.rb +244 -0
  121. data/vendor/ParseTree-1.7.1-patched/validate.sh +31 -0
  122. data/vendor/ParseTree-1.7.1/History.txt +217 -0
  123. data/vendor/ParseTree-1.7.1/Manifest.txt +22 -0
  124. data/vendor/ParseTree-1.7.1/README.txt +110 -0
  125. data/vendor/ParseTree-1.7.1/Rakefile +41 -0
  126. data/vendor/ParseTree-1.7.1/bin/parse_tree_abc +89 -0
  127. data/vendor/ParseTree-1.7.1/bin/parse_tree_audit +28 -0
  128. data/vendor/ParseTree-1.7.1/bin/parse_tree_deps +62 -0
  129. data/vendor/ParseTree-1.7.1/bin/parse_tree_show +49 -0
  130. data/vendor/ParseTree-1.7.1/demo/printer.rb +20 -0
  131. data/vendor/ParseTree-1.7.1/lib/composite_sexp_processor.rb +49 -0
  132. data/vendor/ParseTree-1.7.1/lib/parse_tree.rb +1004 -0
  133. data/vendor/ParseTree-1.7.1/lib/sexp.rb +235 -0
  134. data/vendor/ParseTree-1.7.1/lib/sexp_processor.rb +330 -0
  135. data/vendor/ParseTree-1.7.1/lib/unique.rb +15 -0
  136. data/vendor/ParseTree-1.7.1/test/pt_testcase.rb +1221 -0
  137. data/vendor/ParseTree-1.7.1/test/something.rb +53 -0
  138. data/vendor/ParseTree-1.7.1/test/test_all.rb +13 -0
  139. data/vendor/ParseTree-1.7.1/test/test_composite_sexp_processor.rb +69 -0
  140. data/vendor/ParseTree-1.7.1/test/test_parse_tree.rb +216 -0
  141. data/vendor/ParseTree-1.7.1/test/test_sexp.rb +291 -0
  142. data/vendor/ParseTree-1.7.1/test/test_sexp_processor.rb +244 -0
  143. data/vendor/ParseTree-1.7.1/validate.sh +31 -0
  144. metadata +230 -0
@@ -0,0 +1,1013 @@
1
+ #!/usr/local/bin/ruby -w
2
+
3
+ abort "*** Sorry, ParseTree doesn't work with ruby #{RUBY_VERSION}" if
4
+ RUBY_VERSION >= "1.9"
5
+
6
+ begin require 'rubygems'; rescue LoadError; end
7
+
8
+ require 'inline'
9
+
10
+ ##
11
+ # ParseTree is a RubyInline-style extension that accesses and
12
+ # traverses the internal parse tree created by ruby.
13
+ #
14
+ # class Example
15
+ # def blah
16
+ # return 1 + 1
17
+ # end
18
+ # end
19
+ #
20
+ # ParseTree.new.parse_tree(Example)
21
+ # => [[:class, :Example, :Object,
22
+ # [:defn,
23
+ # "blah",
24
+ # [:scope,
25
+ # [:block,
26
+ # [:args],
27
+ # [:return, [:call, [:lit, 1], "+", [:array, [:lit, 1]]]]]]]]]
28
+
29
+ class ParseTree
30
+
31
+ VERSION = '1.7.1'
32
+
33
+ ##
34
+ # Front end translation method.
35
+
36
+ def self.translate(klass_or_str, method=nil)
37
+ pt = self.new(false)
38
+ case klass_or_str
39
+ when String then
40
+ sexp = pt.parse_tree_for_string(klass_or_str).first
41
+ if method then
42
+ # class, scope, block, *methods
43
+ sexp.last.last[1..-1].find do |defn|
44
+ defn[1] == method
45
+ end
46
+ else
47
+ sexp
48
+ end
49
+ else
50
+ unless method.nil? then
51
+ if method.to_s =~ /^self\./ then
52
+ method = method.to_s[5..-1].intern
53
+ pt.parse_tree_for_method(klass_or_str, method, true)
54
+ else
55
+ pt.parse_tree_for_method(klass_or_str, method)
56
+ end
57
+ else
58
+ pt.parse_tree(klass_or_str).first
59
+ end
60
+ end
61
+ end
62
+
63
+ ##
64
+ # Initializes a ParseTree instance. Includes newline nodes if
65
+ # +include_newlines+ which defaults to +$DEBUG+.
66
+
67
+ def initialize(include_newlines=$DEBUG)
68
+ if include_newlines then
69
+ warn "WARNING: include_newlines=true from #{caller[0..9].join(', ')}"
70
+ end
71
+ @include_newlines = include_newlines
72
+ end
73
+
74
+ ##
75
+ # Main driver for ParseTree. Returns an array of arrays containing
76
+ # the parse tree for +klasses+.
77
+ #
78
+ # Structure:
79
+ #
80
+ # [[:class, classname, superclassname, [:defn :method1, ...], ...], ...]
81
+ #
82
+ # NOTE: v1.0 - v1.1 had the signature (klass, meth=nil). This wasn't
83
+ # used much at all and since parse_tree_for_method already existed,
84
+ # it was deemed more useful to expand this method to do multiple
85
+ # classes.
86
+
87
+ def parse_tree(*klasses)
88
+ result = []
89
+ klasses.each do |klass|
90
+ # TODO: remove this on v 1.1
91
+ raise "You should call parse_tree_for_method(#{klasses.first}, #{klass}) instead of parse_tree" if Symbol === klass or String === klass
92
+ klassname = klass.name rescue '' # HACK klass.name should never be nil
93
+ # Tempfile's DelegateClass(File) seems to
94
+ # cause this
95
+ klassname = "UnnamedClass_#{klass.object_id}" if klassname.empty?
96
+ klassname = klassname.to_sym
97
+
98
+ code = if Class === klass then
99
+ sc = klass.superclass
100
+ sc_name = ((sc.nil? or sc.name.empty?) ? "nil" : sc.name).intern
101
+ [:class, klassname, [:const, sc_name]]
102
+ else
103
+ [:module, klassname]
104
+ end
105
+
106
+ method_names = []
107
+ method_names += klass.instance_methods false
108
+ method_names += klass.private_instance_methods false
109
+ # protected methods are included in instance_methods, go figure!
110
+
111
+ method_names.sort.each do |m|
112
+ code << parse_tree_for_method(klass, m.to_sym)
113
+ end
114
+
115
+ klass.singleton_methods(false).sort.each do |m|
116
+ code << parse_tree_for_method(klass, m.to_sym, true)
117
+ end
118
+
119
+ result << code
120
+ end
121
+ return result
122
+ end
123
+
124
+ ##
125
+ # Returns the parse tree for just one +method+ of a class +klass+.
126
+ #
127
+ # Format:
128
+ #
129
+ # [:defn, :name, :body]
130
+
131
+ def parse_tree_for_method(klass, method, is_cls_meth=false)
132
+ $stderr.puts "** parse_tree_for_method(#{klass}, #{method}):" if $DEBUG
133
+ r = parse_tree_for_meth(klass, method.to_sym, @include_newlines, is_cls_meth)
134
+ r[1] = :"self.#{r[1]}" if is_cls_meth
135
+ r
136
+ end
137
+
138
+ ##
139
+ # Returns the parse tree for a string +source+.
140
+ #
141
+ # Format:
142
+ #
143
+ # [[sexps] ... ]
144
+
145
+ def parse_tree_for_string(source, filename = nil, line = nil,
146
+ newlines = false)
147
+ filename ||= '(string)'
148
+ line ||= 1
149
+ return parse_tree_for_str(source, filename, line, newlines)
150
+ end
151
+
152
+ if RUBY_VERSION < "1.8.4" then
153
+ inline do |builder|
154
+ builder.add_type_converter("bool", '', '')
155
+ builder.c_singleton "
156
+ bool has_alloca() {
157
+ (void)self;
158
+ #ifdef C_ALLOCA
159
+ return Qtrue;
160
+ #else
161
+ return Qfalse;
162
+ #endif
163
+ }"
164
+ end
165
+ else
166
+ def self.has_alloca
167
+ true
168
+ end
169
+ end
170
+
171
+
172
+ NODE_NAMES = [
173
+ # 00
174
+ :method, :fbody, :cfunc, :scope, :block,
175
+ :if, :case, :when, :opt_n, :while,
176
+ # 10
177
+ :until, :iter, :for, :break, :next,
178
+ :redo, :retry, :begin, :rescue, :resbody,
179
+ # 20
180
+ :ensure, :and, :or, :not, :masgn,
181
+ :lasgn, :dasgn, :dasgn_curr, :gasgn, :iasgn,
182
+ # 30
183
+ :cdecl, :cvasgn, :cvdecl, :op_asgn1, :op_asgn2,
184
+ :op_asgn_and, :op_asgn_or, :call, :fcall, :vcall,
185
+ # 40
186
+ :super, :zsuper, :array, :zarray, :hash,
187
+ :return, :yield, :lvar, :dvar, :gvar,
188
+ # 50
189
+ :ivar, :const, :cvar, :nth_ref, :back_ref,
190
+ :match, :match2, :match3, :lit, :str,
191
+ # 60
192
+ :dstr, :xstr, :dxstr, :evstr, :dregx,
193
+ :dregx_once, :args, :argscat, :argspush, :splat,
194
+ # 70
195
+ :to_ary, :svalue, :block_arg, :block_pass, :defn,
196
+ :defs, :alias, :valias, :undef, :class,
197
+ # 80
198
+ :module, :sclass, :colon2, :colon3, :cref,
199
+ :dot2, :dot3, :flip2, :flip3, :attrset,
200
+ # 90
201
+ :self, :nil, :true, :false, :defined,
202
+ # 95
203
+ :newline, :postexe, :alloca, :dmethod, :bmethod,
204
+ # 100
205
+ :memo, :ifunc, :dsym, :attrasgn,
206
+ :last
207
+ ]
208
+
209
+ if RUBY_VERSION < "1.8.4" then
210
+ NODE_NAMES.delete :alloca unless has_alloca
211
+ end
212
+
213
+ if RUBY_VERSION > "1.9" then
214
+ NODE_NAMES.insert NODE_NAMES.index(:hash), :values
215
+ NODE_NAMES.insert NODE_NAMES.index(:defined), :errinfo
216
+ NODE_NAMES.insert NODE_NAMES.index(:last), :prelude, :lambda
217
+ NODE_NAMES.delete :dmethod
218
+ NODE_NAMES[128] = NODE_NAMES.delete :newline
219
+ end
220
+
221
+ ############################################################
222
+ # END of rdoc methods
223
+ ############################################################
224
+
225
+ inline do |builder|
226
+ builder.add_type_converter("bool", '', '')
227
+ builder.add_type_converter("ID *", '', '')
228
+ builder.add_type_converter("NODE *", '(NODE *)', '(VALUE)')
229
+ builder.include '"intern.h"'
230
+ builder.include '"version.h"'
231
+ builder.include '"rubysig.h"'
232
+ builder.include '"node.h"'
233
+ builder.include '"st.h"'
234
+ builder.include '"env.h"'
235
+ builder.add_compile_flags "-Wall"
236
+ builder.add_compile_flags "-W"
237
+ builder.add_compile_flags "-Wpointer-arith"
238
+ builder.add_compile_flags "-Wcast-qual"
239
+ builder.add_compile_flags "-Wcast-align"
240
+ builder.add_compile_flags "-Wwrite-strings"
241
+ builder.add_compile_flags "-Wmissing-noreturn"
242
+ # NOTE: If you get weird compiler errors like:
243
+ # dereferencing type-punned pointer will break strict-aliasing rules
244
+ # PLEASE do one of the following:
245
+ # 1) Get me a login on your box so I can repro this and get it fixed.
246
+ # 2) Fix it and send me the patch
247
+ # 3) (quick, but dirty and bad), comment out the following line:
248
+ builder.add_compile_flags "-Werror"
249
+ # NOTE: this flag doesn't work w/ gcc 2.95.x - the FreeBSD default
250
+ # builder.add_compile_flags "-Wno-strict-aliasing"
251
+ # ruby.h screws these up hardcore:
252
+ # builder.add_compile_flags "-Wundef"
253
+ # builder.add_compile_flags "-Wconversion"
254
+ # builder.add_compile_flags "-Wstrict-prototypes"
255
+ # builder.add_compile_flags "-Wmissing-prototypes"
256
+ # builder.add_compile_flags "-Wsign-compare"
257
+
258
+ def self.if_version(test, version, str)
259
+ RUBY_VERSION.send(test, version) ? str : ""
260
+ end
261
+
262
+ builder.prefix %{
263
+ #define nd_3rd u3.node
264
+ static unsigned case_level = 0;
265
+ }
266
+
267
+ builder.prefix %{
268
+ static VALUE wrap_into_node(const char * name, VALUE val) {
269
+ VALUE n = rb_ary_new();
270
+ rb_ary_push(n, ID2SYM(rb_intern(name)));
271
+ rb_ary_push(n, val);
272
+ return n;
273
+ }
274
+ }
275
+
276
+ builder.prefix %{
277
+ struct METHOD {
278
+ VALUE klass, rklass;
279
+ VALUE recv;
280
+ ID id, oid;
281
+ #{if_version :>, "1.8.2", "int safe_level;"}
282
+ NODE *body;
283
+ };
284
+
285
+ struct BLOCK {
286
+ NODE *var;
287
+ NODE *body;
288
+ VALUE self;
289
+ struct FRAME frame;
290
+ struct SCOPE *scope;
291
+ VALUE klass;
292
+ NODE *cref;
293
+ int iter;
294
+ int vmode;
295
+ int flags;
296
+ int uniq;
297
+ struct RVarmap *dyna_vars;
298
+ VALUE orig_thread;
299
+ VALUE wrapper;
300
+ VALUE block_obj;
301
+ struct BLOCK *outer;
302
+ struct BLOCK *prev;
303
+ };
304
+ } unless RUBY_VERSION >= "1.9" # we got matz to add this to env.h
305
+
306
+ ##
307
+ # add_to_parse_tree(ary, node, include_newlines, local_variables)
308
+
309
+ builder.c_raw %Q@
310
+ static void add_to_parse_tree(VALUE ary,
311
+ NODE * n,
312
+ VALUE newlines,
313
+ ID * locals) {
314
+ NODE * volatile node = n;
315
+ NODE * volatile contnode = NULL;
316
+ VALUE old_ary = Qnil;
317
+ VALUE current;
318
+ VALUE node_name;
319
+ static VALUE node_names = Qnil;
320
+
321
+ if (NIL_P(node_names)) {
322
+ node_names = rb_const_get_at(rb_path2class("ParseTree"),rb_intern("NODE_NAMES"));
323
+ }
324
+
325
+ if (!node) return;
326
+
327
+ again:
328
+
329
+ if (node) {
330
+ node_name = rb_ary_entry(node_names, nd_type(node));
331
+ if (RTEST(ruby_debug)) {
332
+ fprintf(stderr, "%15s: %s%s%s\\n",
333
+ rb_id2name(SYM2ID(node_name)),
334
+ (RNODE(node)->u1.node != NULL ? "u1 " : " "),
335
+ (RNODE(node)->u2.node != NULL ? "u2 " : " "),
336
+ (RNODE(node)->u3.node != NULL ? "u3 " : " "));
337
+ }
338
+ } else {
339
+ node_name = ID2SYM(rb_intern("ICKY"));
340
+ }
341
+
342
+ current = rb_ary_new();
343
+ rb_ary_push(ary, current);
344
+ rb_ary_push(current, node_name);
345
+
346
+ again_no_block:
347
+
348
+ switch (nd_type(node)) {
349
+
350
+ case NODE_BLOCK:
351
+ if (contnode) {
352
+ add_to_parse_tree(current, node, newlines, locals);
353
+ break;
354
+ }
355
+ contnode = node->nd_next;
356
+
357
+ // FIX: this will break the moment there is a block w/in a block
358
+ old_ary = ary;
359
+ ary = current;
360
+ node = node->nd_head;
361
+ if (nd_type(node) == NODE_DASGN_CURR
362
+ && (!node->nd_value || nd_type(node->nd_value) == NODE_DASGN_CURR)) {
363
+ goto finish;
364
+ }
365
+ goto again;
366
+ break;
367
+
368
+ case NODE_FBODY:
369
+ case NODE_DEFINED:
370
+ add_to_parse_tree(current, node->nd_head, newlines, locals);
371
+ break;
372
+
373
+ case NODE_COLON2:
374
+ add_to_parse_tree(current, node->nd_head, newlines, locals);
375
+ rb_ary_push(current, ID2SYM(node->nd_mid));
376
+ break;
377
+
378
+ case NODE_MATCH2:
379
+ case NODE_MATCH3:
380
+ add_to_parse_tree(current, node->nd_recv, newlines, locals);
381
+ add_to_parse_tree(current, node->nd_value, newlines, locals);
382
+ break;
383
+
384
+ case NODE_BEGIN:
385
+ case NODE_OPT_N:
386
+ case NODE_NOT:
387
+ add_to_parse_tree(current, node->nd_body, newlines, locals);
388
+ break;
389
+
390
+ case NODE_IF:
391
+ add_to_parse_tree(current, node->nd_cond, newlines, locals);
392
+ if (node->nd_body) {
393
+ add_to_parse_tree(current, node->nd_body, newlines, locals);
394
+ } else {
395
+ rb_ary_push(current, Qnil);
396
+ }
397
+ if (node->nd_else) {
398
+ add_to_parse_tree(current, node->nd_else, newlines, locals);
399
+ } else {
400
+ rb_ary_push(current, Qnil);
401
+ }
402
+ break;
403
+
404
+ case NODE_CASE:
405
+ case_level++;
406
+ if (node->nd_head != NULL) {
407
+ add_to_parse_tree(current, node->nd_head, newlines, locals); /* expr */
408
+ } else {
409
+ rb_ary_push(current, Qnil);
410
+ }
411
+ node = node->nd_body;
412
+ while (node) {
413
+ add_to_parse_tree(current, node, newlines, locals);
414
+ if (nd_type(node) == NODE_WHEN) { /* when */
415
+ node = node->nd_next;
416
+ } else {
417
+ break; /* else */
418
+ }
419
+ if (! node) {
420
+ rb_ary_push(current, Qnil); /* no else */
421
+ }
422
+ }
423
+ case_level--;
424
+ break;
425
+
426
+ case NODE_WHEN:
427
+ if (!case_level) { /* when without case, ie, no expr in case */
428
+ rb_ary_pop(ary); /* reset what current is pointing at */
429
+ node = NEW_CASE(0, node);
430
+ goto again;
431
+ }
432
+ add_to_parse_tree(current, node->nd_head, newlines, locals); /* args */
433
+ if (node->nd_body) {
434
+ add_to_parse_tree(current, node->nd_body, newlines, locals); /* body */
435
+ } else {
436
+ rb_ary_push(current, Qnil);
437
+ }
438
+ break;
439
+
440
+ case NODE_WHILE:
441
+ case NODE_UNTIL:
442
+ add_to_parse_tree(current, node->nd_cond, newlines, locals);
443
+ if (node->nd_body) {
444
+ add_to_parse_tree(current, node->nd_body, newlines, locals);
445
+ } else {
446
+ rb_ary_push(current, Qnil);
447
+ }
448
+ rb_ary_push(current, node->nd_3rd == 0 ? Qfalse : Qtrue);
449
+ break;
450
+
451
+ case NODE_BLOCK_PASS:
452
+ add_to_parse_tree(current, node->nd_body, newlines, locals);
453
+ add_to_parse_tree(current, node->nd_iter, newlines, locals);
454
+ break;
455
+
456
+ case NODE_ITER:
457
+ case NODE_FOR:
458
+ add_to_parse_tree(current, node->nd_iter, newlines, locals);
459
+ if (node->nd_var != (NODE *)1
460
+ && node->nd_var != (NODE *)2
461
+ && node->nd_var != NULL) {
462
+ add_to_parse_tree(current, node->nd_var, newlines, locals);
463
+ } else {
464
+ if (node->nd_var == NULL)
465
+ {
466
+ // e.g. proc {}
467
+ rb_ary_push(current, Qnil);
468
+ }
469
+ else
470
+ {
471
+ // e.g. proc {||}
472
+ rb_ary_push(current, ID2SYM(rb_intern("zero_arguments")));
473
+ }
474
+ }
475
+ add_to_parse_tree(current, node->nd_body, newlines, locals);
476
+ break;
477
+
478
+ case NODE_BREAK:
479
+ case NODE_NEXT:
480
+ case NODE_YIELD:
481
+ if (node->nd_stts)
482
+ add_to_parse_tree(current, node->nd_stts, newlines, locals);
483
+ break;
484
+
485
+ case NODE_RESCUE:
486
+ add_to_parse_tree(current, node->nd_1st, newlines, locals);
487
+ add_to_parse_tree(current, node->nd_2nd, newlines, locals);
488
+ add_to_parse_tree(current, node->nd_3rd, newlines, locals);
489
+ break;
490
+
491
+ // rescue body:
492
+ // begin stmt rescue exception => var; stmt; [rescue e2 => v2; s2;]* end
493
+ // stmt rescue stmt
494
+ // a = b rescue c
495
+
496
+ case NODE_RESBODY:
497
+ if (node->nd_3rd) {
498
+ add_to_parse_tree(current, node->nd_3rd, newlines, locals);
499
+ } else {
500
+ rb_ary_push(current, Qnil);
501
+ }
502
+ add_to_parse_tree(current, node->nd_2nd, newlines, locals);
503
+ add_to_parse_tree(current, node->nd_1st, newlines, locals);
504
+ break;
505
+
506
+ case NODE_ENSURE:
507
+ add_to_parse_tree(current, node->nd_head, newlines, locals);
508
+ if (node->nd_ensr) {
509
+ add_to_parse_tree(current, node->nd_ensr, newlines, locals);
510
+ }
511
+ break;
512
+
513
+ case NODE_AND:
514
+ case NODE_OR:
515
+ add_to_parse_tree(current, node->nd_1st, newlines, locals);
516
+ add_to_parse_tree(current, node->nd_2nd, newlines, locals);
517
+ break;
518
+
519
+ case NODE_DOT2:
520
+ case NODE_DOT3:
521
+ case NODE_FLIP2:
522
+ case NODE_FLIP3:
523
+ add_to_parse_tree(current, node->nd_beg, newlines, locals);
524
+ add_to_parse_tree(current, node->nd_end, newlines, locals);
525
+ break;
526
+
527
+ case NODE_RETURN:
528
+ if (node->nd_stts)
529
+ add_to_parse_tree(current, node->nd_stts, newlines, locals);
530
+ break;
531
+
532
+ case NODE_ARGSCAT:
533
+ case NODE_ARGSPUSH:
534
+ add_to_parse_tree(current, node->nd_head, newlines, locals);
535
+ add_to_parse_tree(current, node->nd_body, newlines, locals);
536
+ break;
537
+
538
+ case NODE_CALL:
539
+ case NODE_FCALL:
540
+ case NODE_VCALL:
541
+ if (nd_type(node) != NODE_FCALL)
542
+ add_to_parse_tree(current, node->nd_recv, newlines, locals);
543
+ rb_ary_push(current, ID2SYM(node->nd_mid));
544
+ if (node->nd_args || nd_type(node) != NODE_FCALL)
545
+ add_to_parse_tree(current, node->nd_args, newlines, locals);
546
+ break;
547
+
548
+ case NODE_SUPER:
549
+ add_to_parse_tree(current, node->nd_args, newlines, locals);
550
+ break;
551
+
552
+ case NODE_BMETHOD:
553
+ {
554
+ struct BLOCK *data;
555
+ Data_Get_Struct(node->nd_cval, struct BLOCK, data);
556
+ add_to_parse_tree(current, data->var, newlines, locals);
557
+ add_to_parse_tree(current, data->body, newlines, locals);
558
+ break;
559
+ }
560
+ break;
561
+
562
+ #{if_version :>, "1.9", '#if 0'}
563
+ case NODE_DMETHOD:
564
+ {
565
+ struct METHOD *data;
566
+ Data_Get_Struct(node->nd_cval, struct METHOD, data);
567
+ rb_ary_push(current, ID2SYM(data->id));
568
+ add_to_parse_tree(current, data->body, newlines, locals);
569
+ break;
570
+ }
571
+ #{if_version :>, "1.9", '#endif'}
572
+
573
+ case NODE_METHOD:
574
+ fprintf(stderr, "u1 = %p u2 = %p u3 = %p\\n", node->nd_1st, node->nd_2nd, node->nd_3rd);
575
+ add_to_parse_tree(current, node->nd_3rd, newlines, locals);
576
+ break;
577
+
578
+ case NODE_SCOPE:
579
+ add_to_parse_tree(current, node->nd_next, newlines, node->nd_tbl);
580
+ break;
581
+
582
+ case NODE_OP_ASGN1:
583
+ add_to_parse_tree(current, node->nd_recv, newlines, locals);
584
+ #{if_version :>, "1.8.4", "#if 0"}
585
+ #{if_version :<=, "1.8.4", "#if 1"}
586
+ add_to_parse_tree(current, node->nd_args->nd_next, newlines, locals);
587
+ rb_ary_pop(rb_ary_entry(current, -1)); // no idea why I need this
588
+ #else
589
+ add_to_parse_tree(current, node->nd_args->nd_2nd, newlines, locals);
590
+ #endif
591
+ switch (node->nd_mid) {
592
+ case 0:
593
+ rb_ary_push(current, ID2SYM(rb_intern("||")));
594
+ break;
595
+ case 1:
596
+ rb_ary_push(current, ID2SYM(rb_intern("&&")));
597
+ break;
598
+ default:
599
+ rb_ary_push(current, ID2SYM(node->nd_mid));
600
+ break;
601
+ }
602
+ add_to_parse_tree(current, node->nd_args->nd_head, newlines, locals);
603
+ break;
604
+
605
+ case NODE_OP_ASGN2:
606
+ add_to_parse_tree(current, node->nd_recv, newlines, locals);
607
+ rb_ary_push(current, ID2SYM(node->nd_next->nd_aid));
608
+
609
+ switch (node->nd_next->nd_mid) {
610
+ case 0:
611
+ rb_ary_push(current, ID2SYM(rb_intern("||")));
612
+ break;
613
+ case 1:
614
+ rb_ary_push(current, ID2SYM(rb_intern("&&")));
615
+ break;
616
+ default:
617
+ rb_ary_push(current, ID2SYM(node->nd_next->nd_mid));
618
+ break;
619
+ }
620
+
621
+ add_to_parse_tree(current, node->nd_value, newlines, locals);
622
+ break;
623
+
624
+ case NODE_OP_ASGN_AND:
625
+ case NODE_OP_ASGN_OR:
626
+ add_to_parse_tree(current, node->nd_head, newlines, locals);
627
+ add_to_parse_tree(current, node->nd_value, newlines, locals);
628
+ break;
629
+
630
+ case NODE_MASGN:
631
+ add_to_parse_tree(current, node->nd_head, newlines, locals);
632
+ if (node->nd_args && node->nd_args != (NODE *)-1) {
633
+ add_to_parse_tree(current, node->nd_args, newlines, locals);
634
+ }
635
+ add_to_parse_tree(current, node->nd_value, newlines, locals);
636
+ break;
637
+
638
+ case NODE_LASGN:
639
+ case NODE_IASGN:
640
+ case NODE_DASGN:
641
+ case NODE_DASGN_CURR:
642
+ case NODE_CDECL:
643
+ case NODE_CVASGN:
644
+ case NODE_CVDECL:
645
+ case NODE_GASGN:
646
+ rb_ary_push(current, ID2SYM(node->nd_vid));
647
+ add_to_parse_tree(current, node->nd_value, newlines, locals);
648
+ break;
649
+
650
+ case NODE_VALIAS: // u1 u2 (alias $global $global2)
651
+ #{if_version :>, "1.8.4", "#if 0"}
652
+ #{if_version :<=, "1.8.4", "#if 1"}
653
+ rb_ary_push(current, ID2SYM(node->u2.id));
654
+ rb_ary_push(current, ID2SYM(node->u1.id));
655
+ #else
656
+ rb_ary_push(current, ID2SYM(node->u1.id));
657
+ rb_ary_push(current, ID2SYM(node->u2.id));
658
+ #endif
659
+ break;
660
+ case NODE_ALIAS: // u1 u2 (alias :blah :blah2)
661
+ #{if_version :>, "1.8.4", "#if 0"}
662
+ #{if_version :<=, "1.8.4", "#if 1"}
663
+ rb_ary_push(current, wrap_into_node("lit", ID2SYM(node->u2.id)));
664
+ rb_ary_push(current, wrap_into_node("lit", ID2SYM(node->u1.id)));
665
+ #else
666
+ add_to_parse_tree(current, node->nd_1st, newlines, locals);
667
+ add_to_parse_tree(current, node->nd_2nd, newlines, locals);
668
+ #endif
669
+ break;
670
+
671
+ case NODE_UNDEF: // u2 (undef name, ...)
672
+ #{if_version :>, "1.8.4", "#if 0"}
673
+ #{if_version :<=, "1.8.4", "#if 1"}
674
+ rb_ary_push(current, wrap_into_node("lit", ID2SYM(node->u2.id)));
675
+ #else
676
+ add_to_parse_tree(current, node->nd_value, newlines, locals);
677
+ #endif
678
+ break;
679
+
680
+ case NODE_COLON3: // u2 (::OUTER_CONST)
681
+ rb_ary_push(current, ID2SYM(node->u2.id));
682
+ break;
683
+
684
+ case NODE_HASH:
685
+ {
686
+ NODE *list;
687
+
688
+ list = node->nd_head;
689
+ while (list) {
690
+ add_to_parse_tree(current, list->nd_head, newlines, locals);
691
+ list = list->nd_next;
692
+ if (list == 0)
693
+ rb_bug("odd number list for Hash");
694
+ add_to_parse_tree(current, list->nd_head, newlines, locals);
695
+ list = list->nd_next;
696
+ }
697
+ }
698
+ break;
699
+
700
+ case NODE_ARRAY:
701
+ while (node) {
702
+ add_to_parse_tree(current, node->nd_head, newlines, locals);
703
+ node = node->nd_next;
704
+ }
705
+ break;
706
+
707
+ case NODE_DSTR:
708
+ case NODE_DSYM:
709
+ case NODE_DXSTR:
710
+ case NODE_DREGX:
711
+ case NODE_DREGX_ONCE:
712
+ {
713
+ NODE *list = node->nd_next;
714
+ rb_ary_push(current, rb_str_new3(node->nd_lit));
715
+ while (list) {
716
+ if (list->nd_head) {
717
+ switch (nd_type(list->nd_head)) {
718
+ case NODE_STR:
719
+ add_to_parse_tree(current, list->nd_head, newlines, locals);
720
+ break;
721
+ case NODE_EVSTR:
722
+ add_to_parse_tree(current, list->nd_head->nd_body, newlines, locals);
723
+ break;
724
+ default:
725
+ add_to_parse_tree(current, list->nd_head, newlines, locals);
726
+ break;
727
+ }
728
+ }
729
+ list = list->nd_next;
730
+ }
731
+ }
732
+ break;
733
+
734
+ case NODE_DEFN:
735
+ case NODE_DEFS:
736
+ if (node->nd_defn) {
737
+ if (nd_type(node) == NODE_DEFS)
738
+ add_to_parse_tree(current, node->nd_recv, newlines, locals);
739
+ rb_ary_push(current, ID2SYM(node->nd_mid));
740
+ add_to_parse_tree(current, node->nd_defn, newlines, locals);
741
+ }
742
+ break;
743
+
744
+ case NODE_CLASS:
745
+ case NODE_MODULE:
746
+ rb_ary_push(current, ID2SYM((ID)node->nd_cpath->nd_mid));
747
+ if (nd_type(node) == NODE_CLASS) {
748
+ if (node->nd_super) {
749
+ add_to_parse_tree(current, node->nd_super, newlines, locals);
750
+ } else {
751
+ rb_ary_push(current, Qnil);
752
+ }
753
+ }
754
+ add_to_parse_tree(current, node->nd_body, newlines, locals);
755
+ break;
756
+
757
+ case NODE_SCLASS:
758
+ add_to_parse_tree(current, node->nd_recv, newlines, locals);
759
+ add_to_parse_tree(current, node->nd_body, newlines, locals);
760
+ break;
761
+
762
+ case NODE_ARGS: {
763
+ long arg_count = (long)node->nd_rest;
764
+ if (locals && (node->nd_cnt || node->nd_opt || arg_count != -1)) {
765
+ int i;
766
+ int max_args;
767
+ NODE *optnode;
768
+
769
+ max_args = node->nd_cnt;
770
+ for (i = 0; i < max_args; i++) {
771
+ // regular arg names
772
+ rb_ary_push(current, ID2SYM(locals[i + 3]));
773
+ }
774
+
775
+ optnode = node->nd_opt;
776
+ while (optnode) {
777
+ // optional arg names
778
+ rb_ary_push(current, ID2SYM(locals[i + 3]));
779
+ i++;
780
+ optnode = optnode->nd_next;
781
+ }
782
+
783
+ if (arg_count > 0) {
784
+ // *arg name
785
+ VALUE sym = rb_str_intern(rb_str_plus(rb_str_new2("*"), rb_str_new2(rb_id2name(locals[i + 3]))));
786
+ rb_ary_push(current, sym);
787
+ } else if (arg_count == 0) {
788
+ // nothing to do in this case, empty list
789
+ } else if (arg_count == -1) {
790
+ // nothing to do in this case, handled above
791
+ } else if (arg_count == -2) {
792
+ // nothing to do in this case, no name == no use
793
+ } else {
794
+ rb_raise(rb_eArgError,
795
+ "not a clue what this arg value is: %ld", arg_count);
796
+ }
797
+
798
+ optnode = node->nd_opt;
799
+ // block?
800
+ if (optnode) {
801
+ add_to_parse_tree(current, node->nd_opt, newlines, locals);
802
+ }
803
+ }
804
+ } break;
805
+
806
+ case NODE_LVAR:
807
+ case NODE_DVAR:
808
+ case NODE_IVAR:
809
+ case NODE_CVAR:
810
+ case NODE_GVAR:
811
+ case NODE_CONST:
812
+ case NODE_ATTRSET:
813
+ rb_ary_push(current, ID2SYM(node->nd_vid));
814
+ break;
815
+
816
+ case NODE_XSTR: // u1 (%x{ls})
817
+ case NODE_STR: // u1
818
+ case NODE_LIT:
819
+ rb_ary_push(current, node->nd_lit);
820
+ break;
821
+
822
+ case NODE_MATCH: // u1 -> [:lit, u1]
823
+ {
824
+ rb_ary_push(current, wrap_into_node("lit", node->nd_lit));
825
+ }
826
+ break;
827
+
828
+ case NODE_NEWLINE:
829
+ rb_ary_push(current, INT2FIX(nd_line(node)));
830
+ rb_ary_push(current, rb_str_new2(node->nd_file));
831
+
832
+ if (! RTEST(newlines)) rb_ary_pop(ary); // nuke it
833
+
834
+ node = node->nd_next;
835
+ goto again;
836
+ break;
837
+
838
+ case NODE_NTH_REF: // u2 u3 ($1) - u3 is local_cnt('~') ignorable?
839
+ rb_ary_push(current, INT2FIX(node->nd_nth));
840
+ break;
841
+
842
+ case NODE_BACK_REF: // u2 u3 ($& etc)
843
+ {
844
+ char c = node->nd_nth;
845
+ rb_ary_push(current, rb_str_intern(rb_str_new(&c, 1)));
846
+ }
847
+ break;
848
+
849
+ case NODE_BLOCK_ARG: // u1 u3 (def x(&b)
850
+ rb_ary_push(current, ID2SYM(node->u1.id));
851
+ break;
852
+
853
+ // these nodes are empty and do not require extra work:
854
+ case NODE_RETRY:
855
+ case NODE_FALSE:
856
+ case NODE_NIL:
857
+ case NODE_SELF:
858
+ case NODE_TRUE:
859
+ case NODE_ZARRAY:
860
+ case NODE_ZSUPER:
861
+ case NODE_REDO:
862
+ break;
863
+
864
+ case NODE_SPLAT:
865
+ case NODE_TO_ARY:
866
+ case NODE_SVALUE: // a = b, c
867
+ add_to_parse_tree(current, node->nd_head, newlines, locals);
868
+ break;
869
+
870
+ case NODE_ATTRASGN: // literal.meth = y u1 u2 u3
871
+ // node id node
872
+ if (node->nd_1st == RNODE(1)) {
873
+ add_to_parse_tree(current, NEW_SELF(), newlines, locals);
874
+ } else {
875
+ add_to_parse_tree(current, node->nd_1st, newlines, locals);
876
+ }
877
+ rb_ary_push(current, ID2SYM(node->u2.id));
878
+ add_to_parse_tree(current, node->nd_3rd, newlines, locals);
879
+ break;
880
+
881
+ case NODE_EVSTR:
882
+ add_to_parse_tree(current, node->nd_2nd, newlines, locals);
883
+ break;
884
+
885
+ case NODE_POSTEXE: // END { ... }
886
+ // Nothing to do here... we are in an iter block
887
+ break;
888
+
889
+ case NODE_CFUNC:
890
+ rb_ary_push(current, INT2FIX(node->nd_cfnc));
891
+ rb_ary_push(current, INT2FIX(node->nd_argc));
892
+ break;
893
+
894
+ #{if_version :<, "1.9", "#if 0"}
895
+ case NODE_ERRINFO:
896
+ case NODE_VALUES:
897
+ case NODE_PRELUDE:
898
+ case NODE_LAMBDA:
899
+ puts("no worky in 1.9 yet");
900
+ break;
901
+ #{if_version :<, "1.9", "#endif"}
902
+
903
+ // Nodes we found but have yet to decypher
904
+ // I think these are all runtime only... not positive but...
905
+ case NODE_MEMO: // enum.c zip
906
+ case NODE_CREF:
907
+ case NODE_IFUNC:
908
+ // #defines:
909
+ // case NODE_LMASK:
910
+ // case NODE_LSHIFT:
911
+ default:
912
+ rb_warn("Unhandled node #%d type '%s'", nd_type(node), rb_id2name(SYM2ID(rb_ary_entry(node_names, nd_type(node)))));
913
+ if (RNODE(node)->u1.node != NULL) rb_warning("unhandled u1 value");
914
+ if (RNODE(node)->u2.node != NULL) rb_warning("unhandled u2 value");
915
+ if (RNODE(node)->u3.node != NULL) rb_warning("unhandled u3 value");
916
+ if (RTEST(ruby_debug)) fprintf(stderr, "u1 = %p u2 = %p u3 = %p\\n", node->nd_1st, node->nd_2nd, node->nd_3rd);
917
+ rb_ary_push(current, INT2FIX(-99));
918
+ rb_ary_push(current, INT2FIX(nd_type(node)));
919
+ break;
920
+ }
921
+
922
+ finish:
923
+ if (contnode) {
924
+ node = contnode;
925
+ contnode = NULL;
926
+ current = ary;
927
+ ary = old_ary;
928
+ old_ary = Qnil;
929
+ goto again_no_block;
930
+ }
931
+ }
932
+ @ # end of add_to_parse_tree block
933
+
934
+ builder.c %Q{
935
+ static VALUE parse_tree_for_meth(VALUE klass, VALUE method, VALUE newlines, VALUE is_cls_meth) {
936
+ VALUE n;
937
+ NODE *node = NULL;
938
+ ID id;
939
+ VALUE result = rb_ary_new();
940
+ VALUE version = rb_const_get_at(rb_cObject,rb_intern("RUBY_VERSION"));
941
+
942
+ (void) self; // quell warnings
943
+
944
+ if (strcmp(StringValuePtr(version), #{RUBY_VERSION.inspect})) {
945
+ rb_fatal("bad version, %s != #{RUBY_VERSION}\\n", StringValuePtr(version));
946
+ }
947
+
948
+ id = rb_to_id(method);
949
+ if (RTEST(is_cls_meth)) { // singleton method
950
+ klass = CLASS_OF(klass);
951
+ }
952
+ if (st_lookup(RCLASS(klass)->m_tbl, id, &n)) {
953
+ node = (NODE*)n;
954
+ rb_ary_push(result, ID2SYM(rb_intern("defn")));
955
+ rb_ary_push(result, ID2SYM(id));
956
+ add_to_parse_tree(result, node->nd_body, newlines, NULL);
957
+ } else {
958
+ rb_ary_push(result, Qnil);
959
+ }
960
+
961
+ return result;
962
+ }
963
+ }
964
+
965
+ builder.prefix " extern NODE *ruby_eval_tree_begin; " \
966
+ if RUBY_VERSION < '1.9.0'
967
+
968
+ builder.c %Q{
969
+ static VALUE parse_tree_for_str(VALUE source, VALUE filename, VALUE line,
970
+ VALUE newlines) {
971
+ VALUE tmp;
972
+ VALUE result = rb_ary_new();
973
+ NODE *node = NULL;
974
+ int critical;
975
+
976
+ (void) self; // quell warnings
977
+
978
+ tmp = rb_check_string_type(filename);
979
+ if (NIL_P(tmp)) {
980
+ filename = rb_str_new2("(string)");
981
+ }
982
+
983
+ if (NIL_P(line)) {
984
+ line = LONG2FIX(1);
985
+ }
986
+
987
+ newlines = RTEST(newlines);
988
+
989
+ ruby_nerrs = 0;
990
+ StringValue(source);
991
+ critical = rb_thread_critical;
992
+ rb_thread_critical = Qtrue;
993
+ ruby_in_eval++;
994
+ node = rb_compile_string(StringValuePtr(filename), source, NUM2INT(line));
995
+ ruby_in_eval--;
996
+ rb_thread_critical = critical;
997
+
998
+ if (ruby_nerrs > 0) {
999
+ ruby_nerrs = 0;
1000
+ #if RUBY_VERSION_CODE < 190
1001
+ ruby_eval_tree_begin = 0;
1002
+ #endif
1003
+ rb_exc_raise(ruby_errinfo);
1004
+ }
1005
+
1006
+ add_to_parse_tree(result, node, newlines, NULL);
1007
+
1008
+ return result;
1009
+ }
1010
+ }
1011
+
1012
+ end # inline call
1013
+ end # ParseTree class