mirah 0.0.12-java → 0.1.0-java

Sign up to get free protection for your applications and to get access to all the features.
Files changed (171) hide show
  1. data/History.txt +372 -0
  2. data/README.txt +4 -5
  3. data/Rakefile +178 -55
  4. data/examples/appengine/Readme +3 -3
  5. data/examples/appengine/src/org/mirah/MirahApp.mirah +1 -1
  6. data/examples/appengine/src/org/mirah/list.dhtml +1 -1
  7. data/examples/bintrees.mirah +1 -1
  8. data/examples/edb.mirah +1 -1
  9. data/examples/fib.mirah +1 -1
  10. data/examples/interfaces.mirah +1 -1
  11. data/examples/macros/{string-each-char.mirah → string_each_char.mirah} +4 -5
  12. data/examples/maven/README.txt +1 -1
  13. data/examples/maven/src/main/mirah/hello_mirah.mirah +1 -1
  14. data/examples/plugins/appengine/Rakefile +1 -1
  15. data/examples/plugins/appengine/src/com/google/appengine/ext/duby/db/MetaModel.mirah +1 -1
  16. data/examples/plugins/appengine/src/com/google/appengine/ext/duby/db/Model.duby +1 -1
  17. data/examples/plugins/appengine/test/com/google/appengine/ext/duby/db/ModelTest.duby +1 -1
  18. data/examples/rosettacode/100-doors.mirah +6 -6
  19. data/examples/rosettacode/README.txt +3 -3
  20. data/examples/rosettacode/boolean-values.mirah +1 -1
  21. data/examples/rosettacode/comments.mirah +1 -1
  22. data/examples/rosettacode/count-occurrences-of-a-substring.mirah +1 -1
  23. data/examples/rosettacode/factorial.mirah +1 -1
  24. data/examples/rosettacode/fibonacci.mirah +1 -1
  25. data/examples/rosettacode/fizz-buzz.mirah +2 -2
  26. data/examples/rosettacode/flatten-a-list.mirah +4 -4
  27. data/examples/rosettacode/guess-the-number.mirah +2 -2
  28. data/examples/rosettacode/hamming-numbers.mirah +4 -4
  29. data/examples/rosettacode/is-string-numeric.mirah +22 -22
  30. data/examples/rosettacode/palindrome.mirah +2 -2
  31. data/examples/rosettacode/random-numbers.mirah +1 -1
  32. data/examples/rosettacode/repeat-a-string.mirah +1 -1
  33. data/examples/rosettacode/reverse-a-string.mirah +1 -1
  34. data/examples/rosettacode/rot-13.mirah +5 -5
  35. data/examples/rosettacode/secure-temporary-file.mirah +2 -2
  36. data/examples/rosettacode/sleep.mirah +1 -1
  37. data/examples/rosettacode/string-length.mirah +5 -5
  38. data/examples/swing.mirah +1 -1
  39. data/examples/test.edb +1 -1
  40. data/javalib/mirah-bootstrap.jar +0 -0
  41. data/javalib/mirah-builtins.jar +0 -0
  42. data/javalib/mirah-parser.jar +0 -0
  43. data/javalib/mirah-util.jar +0 -0
  44. data/lib/duby.rb +1 -1
  45. data/lib/mirah.rb +50 -28
  46. data/lib/mirah/ast.rb +15 -605
  47. data/lib/mirah/ast/scope.rb +98 -69
  48. data/lib/mirah/commands.rb +1 -1
  49. data/lib/mirah/commands/base.rb +7 -7
  50. data/lib/mirah/commands/compile.rb +3 -3
  51. data/lib/mirah/commands/parse.rb +7 -5
  52. data/lib/mirah/commands/run.rb +12 -19
  53. data/lib/mirah/compiler.rb +15 -23
  54. data/lib/mirah/errors.rb +16 -1
  55. data/lib/mirah/generator.rb +79 -39
  56. data/lib/mirah/jvm/compiler.rb +1 -19
  57. data/lib/mirah/jvm/compiler/base.rb +233 -90
  58. data/lib/mirah/jvm/compiler/jvm_bytecode.rb +675 -363
  59. data/lib/mirah/jvm/method_lookup.rb +134 -65
  60. data/lib/mirah/jvm/typer.rb +10 -5
  61. data/lib/mirah/jvm/types.rb +10 -2
  62. data/lib/mirah/jvm/types/array_type.rb +10 -12
  63. data/lib/mirah/{compiler/type.rb → jvm/types/ast_ext.rb} +12 -8
  64. data/lib/mirah/jvm/types/basic_types.rb +26 -33
  65. data/lib/mirah/jvm/types/bitescript_ext.rb +1 -1
  66. data/lib/mirah/jvm/types/block_type.rb +15 -0
  67. data/lib/mirah/jvm/types/boolean.rb +8 -4
  68. data/lib/mirah/jvm/types/dynamic_type.rb +12 -13
  69. data/lib/mirah/jvm/types/enumerable.rb +7 -7
  70. data/lib/mirah/jvm/types/extensions.rb +11 -6
  71. data/lib/mirah/jvm/types/factory.rb +624 -94
  72. data/lib/mirah/jvm/types/floats.rb +21 -15
  73. data/lib/mirah/jvm/types/generic_type.rb +72 -0
  74. data/lib/mirah/jvm/types/implicit_nil_type.rb +29 -0
  75. data/lib/mirah/jvm/types/integers.rb +26 -71
  76. data/lib/mirah/jvm/types/interface_definition.rb +3 -3
  77. data/lib/mirah/jvm/types/intrinsics.rb +203 -168
  78. data/lib/mirah/jvm/types/literals.rb +6 -6
  79. data/lib/mirah/jvm/types/meta_type.rb +13 -4
  80. data/lib/mirah/jvm/types/methods.rb +281 -93
  81. data/lib/mirah/jvm/types/null_type.rb +17 -5
  82. data/lib/mirah/jvm/types/number.rb +10 -7
  83. data/lib/mirah/jvm/types/primitive_type.rb +17 -6
  84. data/lib/mirah/jvm/types/source_mirror.rb +12 -7
  85. data/lib/mirah/jvm/types/type.rb +107 -23
  86. data/lib/mirah/jvm/types/type_definition.rb +25 -10
  87. data/lib/mirah/jvm/types/unreachable_type.rb +1 -1
  88. data/lib/mirah/jvm/types/void_type.rb +3 -3
  89. data/lib/mirah/parser.rb +154 -16
  90. data/lib/mirah/plugin/edb.rb +1 -1
  91. data/lib/mirah/transform.rb +1 -2
  92. data/lib/mirah/transform/ast_ext.rb +24 -43
  93. data/lib/mirah/transform/transformer.rb +29 -224
  94. data/lib/mirah/typer.rb +2 -16
  95. data/lib/mirah/util/argument_processor.rb +25 -10
  96. data/lib/mirah/util/class_loader.rb +1 -1
  97. data/lib/mirah/util/compilation_state.rb +16 -17
  98. data/lib/mirah/util/delegate.rb +2 -2
  99. data/lib/mirah/util/logging.rb +110 -0
  100. data/lib/mirah/util/process_errors.rb +69 -11
  101. data/lib/mirah/version.rb +1 -1
  102. data/test/core/commands_test.rb +6 -24
  103. data/test/core/env_test.rb +5 -5
  104. data/{lib/mirah/jvm/source_generator/typer.rb → test/core/generator_test.rb} +9 -9
  105. data/test/core/typer_test.rb +196 -158
  106. data/test/core/util/argument_processor_test.rb +10 -10
  107. data/test/core/util/class_loader_test.rb +6 -5
  108. data/test/fixtures/org/foo/LowerCaseInnerClass$inner.class +0 -0
  109. data/test/fixtures/org/foo/LowerCaseInnerClass.class +0 -0
  110. data/test/fixtures/org/foo/LowerCaseInnerClass.java +7 -0
  111. data/test/jvm/annotations_test.rb +5 -5
  112. data/test/jvm/blocks_test.rb +140 -88
  113. data/test/jvm/bytecode_test_helper.rb +112 -94
  114. data/test/jvm/cast_test.rb +162 -0
  115. data/test/jvm/constructors_test.rb +18 -8
  116. data/test/jvm/enumerable_test.rb +77 -44
  117. data/test/jvm/example_test.rb +53 -0
  118. data/test/jvm/factory_test.rb +7 -1
  119. data/test/jvm/generics_test.rb +57 -0
  120. data/test/jvm/hash_test.rb +106 -0
  121. data/test/jvm/import_test.rb +81 -0
  122. data/test/jvm/interface_test.rb +73 -0
  123. data/test/jvm/java_typer_test.rb +92 -66
  124. data/{lib/mirah/typer/base.rb → test/jvm/jvm_commands_test.rb} +6 -10
  125. data/test/jvm/jvm_compiler_test.rb +170 -604
  126. data/test/jvm/list_extensions_test.rb +23 -0
  127. data/test/jvm/macros_test.rb +197 -32
  128. data/test/jvm/main_method_test.rb +4 -4
  129. data/test/jvm/numeric_extensions_test.rb +13 -0
  130. data/test/jvm/rescue_test.rb +73 -16
  131. data/test/jvm/varargs_test.rb +65 -0
  132. data/test/test_helper.rb +1 -2
  133. metadata +234 -251
  134. data/examples/SortClosure$__xform_tmp_1.class +0 -0
  135. data/examples/SortClosure$__xform_tmp_2.class +0 -0
  136. data/examples/SortClosure.class +0 -0
  137. data/examples/macros/StringEachChar$Extension1.class +0 -0
  138. data/lib/mirah/ast/call.rb +0 -345
  139. data/lib/mirah/ast/class.rb +0 -359
  140. data/lib/mirah/ast/flow.rb +0 -381
  141. data/lib/mirah/ast/intrinsics.rb +0 -563
  142. data/lib/mirah/ast/literal.rb +0 -178
  143. data/lib/mirah/ast/local.rb +0 -112
  144. data/lib/mirah/ast/method.rb +0 -408
  145. data/lib/mirah/ast/structure.rb +0 -387
  146. data/lib/mirah/ast/type.rb +0 -146
  147. data/lib/mirah/commands/base.rb~ +0 -57
  148. data/lib/mirah/compiler/call.rb +0 -45
  149. data/lib/mirah/compiler/class.rb +0 -81
  150. data/lib/mirah/compiler/flow.rb +0 -109
  151. data/lib/mirah/compiler/literal.rb +0 -130
  152. data/lib/mirah/compiler/local.rb +0 -59
  153. data/lib/mirah/compiler/method.rb +0 -44
  154. data/lib/mirah/compiler/structure.rb +0 -65
  155. data/lib/mirah/jvm/compiler/java_source.rb +0 -787
  156. data/lib/mirah/jvm/method_lookup.rb~ +0 -247
  157. data/lib/mirah/jvm/source_generator/builder.rb +0 -468
  158. data/lib/mirah/jvm/source_generator/loops.rb +0 -131
  159. data/lib/mirah/jvm/source_generator/precompile.rb +0 -210
  160. data/lib/mirah/plugin/gwt.rb +0 -189
  161. data/lib/mirah/plugin/java.rb +0 -70
  162. data/lib/mirah/transform/error.rb +0 -13
  163. data/lib/mirah/transform/helper.rb +0 -765
  164. data/lib/mirah/typer/simple.rb +0 -384
  165. data/lib/mirah/version.rb~ +0 -18
  166. data/test/core/ast_test.rb +0 -382
  167. data/test/core/compilation_test.rb +0 -130
  168. data/test/core/macros_test.rb +0 -61
  169. data/test/jvm/javac_test_helper.rb +0 -89
  170. data/test/jvm/jvm_compiler_test.rb~ +0 -2181
  171. data/test/plugins/gwt_test.rb +0 -69
@@ -1,70 +0,0 @@
1
- # Copyright (c) 2010 The Mirah project authors. All Rights Reserved.
2
- # All contributing project authors may be found in the NOTICE file.
3
- #
4
- # Licensed under the Apache License, Version 2.0 (the "License");
5
- # you may not use this file except in compliance with the License.
6
- # You may obtain a copy of the License at
7
- #
8
- # http://www.apache.org/licenses/LICENSE-2.0
9
- #
10
- # Unless required by applicable law or agreed to in writing, software
11
- # distributed under the License is distributed on an "AS IS" BASIS,
12
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
- # See the License for the specific language governing permissions and
14
- # limitations under the License.
15
-
16
- require 'mirah/typer'
17
- require 'mirah/jvm/method_lookup'
18
- require 'mirah/jvm/types'
19
- require 'java'
20
-
21
- module Mirah
22
- module Typer
23
- class JavaTyper < Base
24
- include Mirah::JVM::MethodLookup
25
- include Mirah::JVM::Types
26
-
27
- def initialize
28
- end
29
-
30
- def name
31
- "Java"
32
- end
33
-
34
- def method_type(typer, target_type, name, parameter_types)
35
- return if target_type.nil? or parameter_types.any? {|t| t.nil?}
36
- if target_type.respond_to? :get_method
37
- method = target_type.get_method(name, parameter_types)
38
- unless method || target_type.basic_type.kind_of?(TypeDefinition)
39
- raise NoMethodError, "Cannot find %s method %s(%s) on %s" %
40
- [ target_type.meta? ? "static" : "instance",
41
- name,
42
- parameter_types.map{|t| t.full_name}.join(', '),
43
- target_type.full_name
44
- ]
45
- end
46
- if method
47
- result = method.return_type
48
- elsif typer.last_chance && target_type.meta? &&
49
- name == 'new' && parameter_types == []
50
- unmeta = target_type.unmeta
51
- if unmeta.respond_to?(:default_constructor)
52
- result = unmeta.default_constructor
53
- typer.last_chance = false if result
54
- end
55
- end
56
- end
57
-
58
- if result
59
- log "Method type for \"#{name}\" #{parameter_types} on #{target_type} = #{result}"
60
- else
61
- log "Method type for \"#{name}\" #{parameter_types} on #{target_type} not found"
62
- end
63
-
64
- result
65
- end
66
- end
67
- end
68
-
69
- typer_plugins << Typer::JavaTyper.new
70
- end
@@ -1,13 +0,0 @@
1
- module Mirah
2
- module Transform
3
- class Error < Mirah::MirahError
4
- attr_reader :position
5
- def initialize(msg, position, cause=nil)
6
- position = position.position if position.respond_to? :position
7
- super(msg, position)
8
- self.cause = cause
9
- end
10
- end
11
- end
12
- TransformError = Transform::Error
13
- end
@@ -1,765 +0,0 @@
1
- # Copyright (c) 2010 The Mirah project authors. All Rights Reserved.
2
- # All contributing project authors may be found in the NOTICE file.
3
- #
4
- # Licensed under the Apache License, Version 2.0 (the "License");
5
- # you may not use this file except in compliance with the License.
6
- # You may obtain a copy of the License at
7
- #
8
- # http://www.apache.org/licenses/LICENSE-2.0
9
- #
10
- # Unless required by applicable law or agreed to in writing, software
11
- # distributed under the License is distributed on an "AS IS" BASIS,
12
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
- # See the License for the specific language governing permissions and
14
- # limitations under the License.
15
-
16
- module Mirah
17
- module Transform
18
- class Helper
19
- java_import 'jmeta.Ast'
20
- def initialize(transformer)
21
- @mirah = transformer
22
- end
23
-
24
- def position(node)
25
- @mirah.position(node)
26
- end
27
-
28
- def transformer
29
- @mirah
30
- end
31
-
32
- def transform(node, parent)
33
- @mirah.transform(node, parent)
34
- end
35
-
36
- def transform_script(node, parent)
37
- Mirah::AST::Script.new(parent, position(node)) do |script|
38
- script.filename = transformer.filename
39
- [@mirah.transform(node.children[0], script)]
40
- end
41
- end
42
-
43
- def transform_fixnum(node, parent)
44
- Mirah::AST::fixnum(parent, position(node), node[1])
45
- end
46
-
47
- def transform_float(node, parent)
48
- Mirah::AST::float(parent, position(node), node[1])
49
- end
50
-
51
- def transform_true(node, parent)
52
- Mirah::AST::Boolean.new(parent, position(node), true)
53
- end
54
-
55
- def transform_false(node, parent)
56
- Mirah::AST::Boolean.new(parent, position(node), false)
57
- end
58
-
59
- def transform_nil(node, parent)
60
- Mirah::AST::Null.new(parent, position(node))
61
- end
62
-
63
- def transform_self(node, parent)
64
- Mirah::AST::Self.new(parent, position(node))
65
- end
66
-
67
- def transform_string(node, parent)
68
- Mirah::AST::String.new(parent, position(node), node[1])
69
- end
70
-
71
- def transform_symbol(node, parent)
72
- Mirah::AST::String.new(parent, position(node), node[1])
73
- end
74
-
75
- def transform_body(node, parent)
76
- Mirah::AST::Body.new(parent, position(node)) do |body|
77
- node.children.map {|child| @mirah.transform(child, body)}
78
- end
79
- end
80
-
81
- def transform_begin(node, parent)
82
- @mirah.transform(node[1], parent)
83
- end
84
-
85
- def transform_break(node, parent)
86
- Mirah::AST::Break.new(parent, position(node))
87
- end
88
-
89
- def transform_arguments(node, parent)
90
- Mirah::AST::Arguments.new(parent, position(node)) do |args_node|
91
- node.children.map do |child|
92
- if child.nil?
93
- nil
94
- elsif child.kind_of?(Ast)
95
- @mirah.transform(child, args_node)
96
- else
97
- child.map {|x| @mirah.transform(x, args_node)}
98
- end
99
- end
100
- end
101
- end
102
-
103
- def transform_required_argument(node, parent)
104
- name = node[1]
105
- name = transform(name, nil) unless name.kind_of?(::String)
106
- type = node[2]
107
- type_node = transform(type, parent) if type
108
- if Mirah::AST::Unquote === name && type.nil?
109
- name
110
- else
111
- Mirah::AST::RequiredArgument.new(parent, position(node), name, type_node)
112
- end
113
- end
114
-
115
- def transform_opt_arg(node, parent)
116
- name = node[1]
117
- name = transform(name, nil) unless name.kind_of?(::String)
118
- type = node[2]
119
- value = node[3]
120
- Mirah::AST::OptionalArgument.new(parent, position(node), name) do |optarg|
121
- [
122
- type ? transform(type, optarg) : nil,
123
- transform(value, optarg),
124
- ]
125
- end
126
- end
127
-
128
- def transform_rest_arg(node, parent)
129
- name = node[1]
130
- name = transform(name, nil) unless name.kind_of?(::String)
131
- type = node[2]
132
- Mirah::AST::RestArgument.new(parent, position(node), name) do |restarg|
133
- [type ? transform(type, restarg) : nil]
134
- end
135
- end
136
-
137
- def transform_block_arg(node, parent)
138
- name = node[1]
139
- name = transform(name, nil) unless name.kind_of?(::String)
140
- type = node[2]
141
- Mirah::AST::BlockArgument.new(parent, position(node), name) do |blkarg|
142
- [type ? transform(type, blkarg) : nil]
143
- end
144
- end
145
-
146
- def transform_opt_block_arg(node, parent)
147
- block_arg = transform_block_arg(node, parent)
148
- block_arg.optional = true
149
- return block_arg
150
- end
151
-
152
- # TODO UnnamedRestArg
153
-
154
- def transform_sclass(node, parent)
155
- Mirah::AST::ClassAppendSelf.new(parent, position(node)) do |class_append_self|
156
- raise "Singleton class not supported" unless node[1][0] == 'Self'
157
-
158
- [transformer.transform(node[2], class_append_self)]
159
- end
160
- end
161
-
162
- def transform_zarray(node, parent)
163
- Mirah::AST::Array.new(parent, position(node))
164
- end
165
-
166
- def transform_array(node, parent)
167
- Mirah::AST::Array.new(parent, position(node)) do |array|
168
- node.children.map {|child| transformer.transform(child, array)}
169
- end
170
- end
171
-
172
- def transform_attr_assign(node, parent)
173
- name = node[1]
174
- target = node[2]
175
- args = node[3] + [node[4]]
176
- position = position(node)
177
- case name
178
- when '[]='
179
- Mirah::AST::Call.new(parent, position, name) do |call|
180
- [
181
- transformer.transform(target, call),
182
- args.map {|arg| transformer.transform(arg, call)},
183
- nil
184
- ]
185
- end
186
- else
187
- new_name = name[0..-2] + '_set'
188
- Mirah::AST::Call.new(parent, position, new_name) do |call|
189
- [
190
- transformer.transform(target, call),
191
- args.map {|arg| transformer.transform(arg, call)},
192
- nil
193
- ]
194
- end
195
- end
196
- end
197
-
198
- def transform_class(node, parent)
199
- cpath = node[1]
200
- body_node = node[2]
201
- super_node = node[3]
202
- if cpath[0] == 'Constant'
203
- name = cpath[1]
204
- elsif cpath[0] == 'Unquote'
205
- name = cpath
206
- else
207
- raise "Unsupported class name #{cpath[0]}"
208
- end
209
- name = transform(name, nil) unless name.kind_of?(::String)
210
- Mirah::AST::ClassDefinition.new(parent, position(node),
211
- name,
212
- transformer.annotations) do |class_def|
213
- [
214
- super_node ? transform(super_node, class_def) : nil,
215
- body_node ? transform(body_node, class_def) : nil
216
- ]
217
- end
218
- end
219
-
220
- def transform_def(node, parent)
221
- name, args_node, type_node, body_node = node[1], node[2], node[3], node[4]
222
- name = transform(name, nil) unless name.kind_of?(::String)
223
- position = position(node)
224
- actual_name = name
225
- if name =~ /=$/ && name != '[]='
226
- actual_name = name[0..-2] + '_set'
227
- end
228
- if name == 'initialize'
229
- klass = Mirah::AST::ConstructorDefinition
230
- else
231
- klass = Mirah::AST::MethodDefinition
232
- end
233
- klass.new(parent,
234
- position,
235
- actual_name,
236
- transformer.annotations) do |defn|
237
- defn.signature = signature = {:return => nil}
238
- defn.return_type = transform(type_node, defn) if type_node
239
- [
240
- signature,
241
- args_node ? transformer.transform(args_node, defn) : nil,
242
- body_node ? transformer.transform(body_node, defn) : nil,
243
- ]
244
- end
245
- end
246
-
247
- def transform_def_static(node, parent)
248
- name, args_node, type_node, body_node = node[1], node[2], node[3], node[4]
249
- name = transform(name, nil) unless name.kind_of?(::String)
250
- position = position(node)
251
- actual_name = name
252
- if name =~ /=$/
253
- actual_name = name[0..-2] + '_set'
254
- end
255
- Mirah::AST::StaticMethodDefinition.new(parent,
256
- position,
257
- actual_name,
258
- transformer.annotations) do |defn|
259
- defn.signature = signature = {:return => nil}
260
- defn.return_type = transform(type_node, defn) if type_node
261
- [
262
- signature,
263
- args_node ? transformer.transform(args_node, defn) : nil,
264
- body_node ? transformer.transform(body_node, defn) : nil,
265
- ]
266
- end
267
- end
268
-
269
- def transform_fcall(node, parent)
270
- if node.respond_to?(:declaration?) && node.declaration?
271
- return Mirah::AST::Noop.new(parent, position(node))
272
- end
273
-
274
- name = node[1]
275
- name = transform(name, nil) unless name.kind_of?(::String)
276
- args = node[2]
277
- iter_node = node[3]
278
- fcall = Mirah::AST::FunctionalCall.new(parent, position(node), name) do |call|
279
- [
280
- args ? args.map {|arg| transformer.transform(arg, call)} : [],
281
- iter_node ? transformer.transform(iter_node, call) : nil
282
- ]
283
- end
284
- macro = Mirah::AST.macro(name)
285
- if macro
286
- transformer.expand(fcall, parent, &macro)
287
- else
288
- fcall
289
- end
290
- end
291
-
292
- def transform_call(node, parent)
293
- name = node[1]
294
- name = transform(name, nil) unless name.kind_of?(::String)
295
- target = node[2]
296
- args = node[3]
297
- args = [args] if args && args[0].kind_of?(String)
298
- iter_node = node[4]
299
- position = position(node)
300
-
301
- actual_name = name
302
- case actual_name
303
- when '[]'
304
- # could be array instantiation
305
- case target[0]
306
- when 'Identifier'
307
- case target[1]
308
- when 'boolean', 'byte', 'short', 'char', 'int', 'long', 'float', 'double'
309
- if args.nil? || args.size == 0
310
- constant = Mirah::AST::Constant.new(parent, position, target[1])
311
- constant.array = true
312
- return constant
313
- elsif args && args.size == 1
314
- return Mirah::AST::EmptyArray.new(parent, position) do |array|
315
- [transform(target, array), transform(args[0], array)]
316
- end
317
- end
318
- # TODO look for imported, lower case class names
319
- end
320
- when 'Constant'
321
- if args.nil? || args.size == 0
322
- constant = Mirah::AST::Constant.new(parent, position, target[1])
323
- constant.array = true
324
- return constant
325
- elsif args && args.size == 1
326
- return Mirah::AST::EmptyArray.new(parent, position) do |array|
327
- [transform(target, array), transform(args[0], array)]
328
- end
329
- end
330
- end
331
- when /=$/
332
- if name.size > 2 || name =~ /^\w/
333
- actual_name = name[0..-2] + '_set'
334
- end
335
- end
336
-
337
- Mirah::AST::Call.new(parent, position, actual_name) do |call|
338
- [
339
- transformer.transform(target, call),
340
- args ? args.map {|arg| transformer.transform(arg, call)} : [],
341
- iter_node ? transformer.transform(iter_node, call) : nil
342
- ]
343
- end
344
- end
345
-
346
- def transform_constant(node, parent)
347
- Mirah::AST::Constant.new(parent, position(node), node[1])
348
- end
349
-
350
- def transform_colon2const(node, parent)
351
- name = node[2]
352
- name = transform(name, nil) unless name.kind_of?(::String)
353
- target = node[1]
354
- Mirah::AST::Colon2.new(parent, position(node), name) do |colon2|
355
- [ transform(target, colon2) ]
356
- end
357
- end
358
-
359
- def transform_identifier(node, parent)
360
- name = node[1]
361
- position = position(node)
362
- if name == 'raise'
363
- Mirah::AST::Raise.new(parent, position) do
364
- []
365
- end
366
- elsif name == 'null'
367
- Mirah::AST::Null.new(parent, position)
368
- elsif ['public', 'private', 'protected'].include?(name)
369
- Mirah::AST::AccessLevel.new(parent, position, name)
370
- else
371
- macro = Mirah::AST.macro(name)
372
- fcall = Mirah::AST::FunctionalCall.new(parent, position, name) do |call|
373
- [
374
- [],
375
- nil
376
- ]
377
- end
378
- if macro
379
- transformer.expand(fcall, parent, &macro)
380
- else
381
- fcall
382
- end
383
- end
384
- end
385
-
386
- def transform_local_assign(node, parent)
387
- name = node[1]
388
- value_node = node[2]
389
- position = position(node)
390
- case value_node[0]
391
- when 'Symbol', 'Constant'
392
- Mirah::AST::LocalDeclaration.new(parent, position, name) {|local_decl| [transform(value_node, local_decl)]}
393
- else
394
- Mirah::AST::LocalAssignment.new(parent, position, name) {|local| [transform(value_node, local)]}
395
- end
396
- end
397
-
398
- def transform_local(node, parent)
399
- name = node[1]
400
- Mirah::AST::Local.new(parent, position(node), name)
401
- end
402
-
403
- def transform_iter(node, parent)
404
- args = node[1]
405
- body = node[2]
406
- Mirah::AST::Block.new(parent, position(node)) do |block|
407
- [
408
- args ? transformer.transform(args, block) : Mirah::AST::Arguments.new(block, position(node)),
409
- body ? transformer.transform(body, block) : Mirah::AST::Body.new(block, position(node)),
410
- ]
411
- end
412
- end
413
-
414
- def transform_inst_var(node, parent)
415
- name = node[1]
416
- name = transform(name, nil) unless name.kind_of?(::String)
417
- Mirah::AST::Field.new(parent, position(node), name, transformer.annotations)
418
- end
419
-
420
- def transform_inst_var_assign(node, parent)
421
- name = node[1]
422
- name = transform(name, nil) unless name.kind_of?(::String)
423
- value_node = node[2]
424
- position = position(node)
425
- case value_node[0]
426
- when 'Symbol', 'Constant'
427
- Mirah::AST::FieldDeclaration.new(parent, position,
428
- name, transformer.annotations) do |field_decl|
429
- [transform(value_node, field_decl)]
430
- end
431
- else
432
- Mirah::AST::FieldAssignment.new(parent, position, name, transformer.annotations) {|field| [transformer.transform(value_node, field)]}
433
- end
434
- end
435
-
436
- def transform_class_var(node, parent)
437
- name = node[1]
438
- name = transform(name, nil) unless name.kind_of?(::String)
439
- Mirah::AST::Field.new(parent, position(node), name, transformer.annotations, true)
440
- end
441
-
442
- def transform_class_var_assign(node, parent)
443
- name = node[1]
444
- name = transform(name, nil) unless name.kind_of?(::String)
445
- value_node = node[2]
446
- position = position(node)
447
- case value_node[0]
448
- when 'Symbol', 'Constant'
449
- Mirah::AST::FieldDeclaration.new(parent, position,
450
- name, transformer.annotations, true) do |field_decl|
451
- [transform(value_node, field_decl)]
452
- end
453
- else
454
- Mirah::AST::FieldAssignment.new(parent, position, name, transformer.annotations, true) {|field| [transformer.transform(value_node, field)]}
455
- end
456
- end
457
-
458
- def transform_if(node, parent)
459
- condition = node[1]
460
- then_body = node[2]
461
- else_body = node[3]
462
- Mirah::AST::If.new(parent, position(node)) do |iff|
463
- [
464
- Mirah::AST::Condition.new(iff, position(condition)) {|cond| [transformer.transform(condition, cond)]},
465
- then_body ? transformer.transform(then_body, iff) : nil,
466
- else_body ? transformer.transform(else_body, iff) : nil
467
- ]
468
- end
469
- end
470
-
471
- def transform_zsuper(node, parent)
472
- Mirah::AST::Super.new(parent, position(node))
473
- end
474
-
475
- def transform_super(node, parent)
476
- args = node[1]
477
- iter = node[2]
478
- Mirah::AST::Super.new(parent, position(node)) do |s|
479
- [args ? args.map {|arg| transformer.transform(arg, s)} : []]
480
- end
481
- end
482
-
483
- def transform_return(node, parent)
484
- value_node = node[1] if node.size > 1
485
- Mirah::AST::Return.new(parent, position(node)) do |ret|
486
- [value_node ? transform(value_node, ret) : nil]
487
- end
488
- end
489
-
490
- def transform_dstring(node, parent)
491
- Mirah::AST::StringConcat.new(parent, position(node)) do |p|
492
- node.children.map{|n| transform(n, p)}
493
- end
494
- end
495
-
496
- def transform_ev_string(node, parent)
497
- Mirah::AST::ToString.new(parent, position(node)) do |p|
498
- [transform(node[1], p)]
499
- end
500
- end
501
-
502
- def transform_and(node, parent)
503
- first_node = node[1]
504
- second_node = node[2]
505
- Mirah::AST::If.new(parent, position(node)) do |iff|
506
- [
507
- Mirah::AST::Condition.new(iff, position(first_node)) {|cond| [transform(first_node, cond)]},
508
- transform(second_node, iff),
509
- nil
510
- ]
511
- end
512
- end
513
-
514
- def transform_or(node, parent)
515
- first_node = node[1]
516
- second_node = node[2]
517
- Mirah::AST::Body.new(parent, position(node)) do |block|
518
- temp = transformer.tmp
519
- [
520
- Mirah::AST::LocalAssignment.new(block, position(first_node), temp) do |l|
521
- [transform(first_node, l)]
522
- end,
523
- Mirah::AST::If.new(parent, position(node)) do |iff|
524
- [
525
- Mirah::AST::Condition.new(iff, position(first_node)) do |cond|
526
- [Mirah::AST::Local.new(cond, position(first_node), temp)]
527
- end,
528
- Mirah::AST::Local.new(iff, position(first_node), temp),
529
- transform(second_node, iff)
530
- ]
531
- end
532
- ]
533
- end
534
- end
535
-
536
- def transform_next(node, parent)
537
- Mirah::AST::Next.new(parent, position(node))
538
- end
539
-
540
- def transform_not(node, parent)
541
- # TODO it's probably better to keep a not node
542
- # and actually implement compiling it properly.
543
- # Bonus points for optimizing branches that use Not's.
544
- Mirah::AST::If.new(parent, position(node)) do |iff|
545
- [
546
- Mirah::AST::Condition.new(iff, position(node)) do |cond|
547
- [ transform(node[1], cond) ]
548
- end,
549
- Mirah::AST::Boolean.new(iff, position(node), false),
550
- Mirah::AST::Boolean.new(iff, position(node), true)
551
- ]
552
- end
553
- end
554
-
555
- def transform_redo(node, parent)
556
- Mirah::AST::Redo.new(parent, position(node))
557
- end
558
-
559
- def transform_regex(node, parent)
560
- contents = node[1]
561
- modifiers = node[2]
562
- if contents.size == 1 && contents[0][0] == 'String'
563
- value = contents[0][1]
564
- Mirah::AST::Regexp.new(parent, position(node), value)
565
- else
566
- raise "Unsupported regex #{node}"
567
- end
568
- end
569
-
570
- def transform_ensure(node, parent)
571
- Mirah::AST::Ensure.new(parent, position(node)) do |n|
572
- node.children.map {|c| transform(c, n)}
573
- end
574
- end
575
-
576
- def evaluate_at_start?(node)
577
- if node[0] =~ /Mod$/ && node[2] && node[2][0] == 'Begin'
578
- false
579
- else
580
- true
581
- end
582
- end
583
-
584
- def transform_while(node, parent)
585
- condition_node = node[1]
586
- body_node = node[2]
587
- Mirah::AST::Loop.new(parent, position(node), evaluate_at_start?(node), false) do |loop|
588
- [
589
- Mirah::AST::Condition.new(loop, position(condition_node)) {|cond| [transform(condition_node, cond)]},
590
- transform(body_node, loop)
591
- ]
592
- end
593
- end
594
- def transform_while_mod(node, parent)
595
- transform_while(node, parent)
596
- end
597
-
598
- def transform_until(node, parent)
599
- condition_node = node[1]
600
- body_node = node[2]
601
- Mirah::AST::Loop.new(parent, position(node), evaluate_at_start?(node), true) do |loop|
602
- [
603
- Mirah::AST::Condition.new(loop, position(condition_node)) {|cond| [transform(condition_node, cond)]},
604
- transform(body_node, loop)
605
- ]
606
- end
607
- end
608
- def transform_until_mod(node, parent)
609
- transform_until(node, parent)
610
- end
611
-
612
- def transform_for(node, parent)
613
- var_node = node[1]
614
- body_node = node[2]
615
- iter_node = node[3]
616
- Mirah::AST::Call.new(parent, position(node), 'each') do |each|
617
- [
618
- transformer.transform(iter_node, each),
619
- [],
620
- Mirah::AST::Block.new(each, position(body_node)) do |block|
621
- [
622
- Mirah::AST::Arguments.new(block, position(var_node)) do |args|
623
- [
624
- # TODO support for multiple assignment?
625
- [Mirah::AST::RequiredArgument.new(args,
626
- position(var_node),
627
- var_node[1])
628
- ]
629
- ]
630
- end,
631
- transformer.transform(body_node, block)
632
- ]
633
- end
634
- ]
635
- end
636
- end
637
-
638
- def transform_rescue(node, parent)
639
- body_node = node[1]
640
- clauses = node[2]
641
- else_node = node[3]
642
- Mirah::AST::Rescue.new(parent, position(node)) do |node|
643
- [
644
- transformer.transform(body_node, node),
645
- clauses.map {|clause| transformer.transform(clause, node)},
646
- transformer.transform(else_node, node)
647
- ]
648
- end
649
- end
650
-
651
- def transform_rescue_clause(node, parent)
652
- exceptions = node[1]
653
- var_name = node[2]
654
- name = transform(var_name, nil) unless var_name.nil? || var_name.kind_of?(::String)
655
- body = node[3]
656
- Mirah::AST::RescueClause.new(parent, position(node)) do |clause|
657
- clause.name = var_name if var_name
658
- [
659
- if exceptions.size == 0
660
- [Mirah::AST::String.new(clause, position(node), 'java.lang.Exception')]
661
- else
662
- exceptions.map {|name| Mirah::AST::Constant.new(clause, position(node), name)}
663
- end,
664
- body ? transformer.transform(body, clause) : Mirah::AST::Null.new(clause, position(node))
665
- ]
666
- end
667
- end
668
-
669
- def transform_hash(node, parent)
670
- Mirah::AST::Call.new(parent, position(node), 'new_hash') do |call|
671
- [
672
- Mirah::AST::Builtin.new(call, position(node)),
673
- [
674
- Mirah::AST::Array.new(call, position(node)) do |array|
675
- values = []
676
- node.children.each do |assoc|
677
- assoc.children.each do |child|
678
- values << transform(child, array)
679
- end
680
- end
681
- values
682
- end
683
- ]
684
- ]
685
- end
686
- end
687
-
688
- def transform_op_assign(node, parent)
689
- target = node[1]
690
- attribute = node[2]
691
- op = node[3]
692
- value = node[4]
693
- temp = transformer.tmp
694
- tempval = transformer.tmp
695
- position = position(node)
696
- setter = "#{attribute}="
697
- getter = attribute
698
- Mirah::AST::Body.new(parent, position) do |body|
699
- [
700
- Mirah::AST::LocalAssignment.new(body, position, temp) {|l| transform(target, l)},
701
- Mirah::AST::LocalAssignment.new(body, position, tempval) do |l|
702
- Mirah::AST::Call.new(l, position, op) do |op_call|
703
- [
704
- Mirah::AST::Call.new(op_call, position, getter) do |get_call|
705
- [
706
- Mirah::AST::Local.new(get_call, position, temp),
707
- []
708
- ]
709
- end,
710
- [transform(value, op_call)],
711
- ]
712
- end
713
- end,
714
- Mirah::AST::Call.new(body, position, setter) do |set_call|
715
- [
716
- Mirah::AST::Local.new(set_call, position, temp),
717
- [ Mirah::AST::Local.new(set_call, position, tempval) ],
718
- ]
719
- end,
720
- Mirah::AST::Local.new(body, position, tempval),
721
- ]
722
- end
723
- end
724
-
725
- def transform_unquote(node, parent)
726
- Mirah::AST::Unquote.new(parent, position(node)) do |unquote|
727
- [transform(node[1], unquote)]
728
- end
729
- end
730
-
731
- def transform_unquote_assign(node, parent)
732
- name, value = node[1], node[2]
733
- Mirah::AST::UnquoteAssign.new(parent, position(node)) do |unquote|
734
- [transform(name, unquote), transform(value, unquote)]
735
- end
736
- end
737
-
738
- def transform_block_pass(node, parent)
739
- Mirah::AST::BlockPass.new(parent, position(node)) do |blockpass|
740
- [transform(node[1], blockpass)]
741
- end
742
- end
743
-
744
- def transform_annotation(node, parent)
745
- classname = node[1]
746
- values = if node[2]
747
- node[2].children
748
- else
749
- []
750
- end
751
- annotation = Mirah::AST::Annotation.new(parent, position(node)) do |anno|
752
- [Mirah::AST::String.new(anno, position(node), classname)]
753
- end
754
- values.each do |assoc|
755
- key = assoc[1]
756
- value = assoc[2]
757
- name = key[1]
758
- annotation[name] = transform(value, annotation)
759
- end
760
- transformer.add_annotation(annotation)
761
- return Mirah::AST::Noop.new(parent, position(node))
762
- end
763
- end
764
- end
765
- end