mirah 0.0.12-java → 0.1.0-java

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
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
@@ -20,14 +20,14 @@ def rot13 (value:string)
20
20
  d = ' '.toCharArray[0]
21
21
  value.toCharArray.each do |c|
22
22
  testChar = Character.toLowerCase(c)
23
- if testChar <= 'm'.toCharArray[0] && testChar >= 'a'.toCharArray[0] then
23
+ if testChar <= 'm'.toCharArray[0] && testChar >= 'a'.toCharArray[0] then
24
24
  d = char(c + 13)
25
25
  end
26
- if testChar <= 'z'.toCharArray[0] && testChar >= 'n'.toCharArray[0] then
27
- d = char(c - 13)
28
- end
26
+ if testChar <= 'z'.toCharArray[0] && testChar >= 'n'.toCharArray[0] then
27
+ d = char(c - 13)
28
+ end
29
29
  result += d
30
- end
30
+ end
31
31
  result
32
32
  end
33
33
 
@@ -16,8 +16,8 @@
16
16
  import java.io.File
17
17
 
18
18
  filename = File.createTempFile('prefix', '.suffix')
19
-
19
+
20
20
  # Delete temp file when program exits
21
21
  filename.deleteOnExit()
22
-
22
+
23
23
  puts filename
@@ -16,7 +16,7 @@
16
16
  import java.util.Scanner
17
17
 
18
18
  puts 'Enter time to sleep in milliseconds: '
19
- ms = Scanner.new(System.in).nextInt()
19
+ ms = Scanner.new(System.in).nextInt()
20
20
  puts 'Sleeping...'
21
21
  Thread.sleep(ms)
22
22
  puts 'Awake!'
@@ -15,17 +15,17 @@
15
15
 
16
16
  /**
17
17
  * Java encodes strings in UTF-16, which represents each character with one
18
- * or two 16-bit values. The length method of String objects returns the
19
- * number of 16-bit values used to encode a string, so the number of bytes
18
+ * or two 16-bit values. The length method of String objects returns the
19
+ * number of 16-bit values used to encode a string, so the number of bytes
20
20
  * can be determined by doubling that number.
21
- */
21
+ */
22
22
 
23
23
  s = "Hello, world!"
24
24
  puts s.length() * 2
25
25
 
26
26
  /**
27
- * Another way to know the byte length of a string is to explicitly
27
+ * Another way to know the byte length of a string is to explicitly
28
28
  * specify the charset we desire.
29
- */
29
+ */
30
30
  puts s.getBytes("UTF-16").length
31
31
  puts s.getBytes("UTF-8").length
data/examples/swing.mirah CHANGED
@@ -32,4 +32,4 @@ def self.run
32
32
  end
33
33
  end
34
34
 
35
- run
35
+ run
data/examples/test.edb CHANGED
@@ -6,4 +6,4 @@
6
6
  <h1><%= @message %></h1>
7
7
  </body>
8
8
  </html>
9
-
9
+
Binary file
Binary file
Binary file
Binary file
data/lib/duby.rb CHANGED
@@ -14,4 +14,4 @@
14
14
  # limitations under the License.
15
15
 
16
16
  puts "WARNING: Duby is now Mirah. Please require 'mirah'."
17
- require File.dirname(__FILE__) + '/mirah'
17
+ require File.dirname(__FILE__) + '/mirah'
data/lib/mirah.rb CHANGED
@@ -15,18 +15,25 @@
15
15
 
16
16
  require 'fileutils'
17
17
  require 'rbconfig'
18
+ require 'bitescript'
19
+
20
+ $CLASSPATH << File.dirname(__FILE__) + '/../javalib/mirah-builtins.jar'
21
+ $CLASSPATH << File.dirname(__FILE__) + '/../javalib/mirah-parser.jar'
22
+ $CLASSPATH << File.dirname(__FILE__) + '/../javalib/mirah-bootstrap.jar'
23
+ $CLASSPATH << File.dirname(__FILE__) + '/../javalib/mirah-util.jar'
24
+ $CLASSPATH << File.dirname(__FILE__) + '/../javalib/dynalink-0.2.jar'
25
+
18
26
  require 'mirah/version'
19
27
  require 'mirah/transform'
20
28
  require 'mirah/ast'
21
- require 'mirah/typer'
22
29
  require 'mirah/compiler'
23
30
  require 'mirah/env'
24
31
  require 'mirah/errors'
25
- require 'bitescript'
32
+ require 'mirah/typer'
33
+ require 'mirah/jvm/types'
26
34
 
27
35
  require 'mirah/jvm/compiler'
28
- require 'mirah/jvm/typer'
29
- Dir[File.dirname(__FILE__) + "/mirah/plugin/*"].each {|file| require "#{file}" if file =~ /\.rb$/}
36
+ #Dir[File.dirname(__FILE__) + "/mirah/plugin/*"].each {|file| require "#{file}" if file =~ /\.rb$/}
30
37
  require 'jruby'
31
38
 
32
39
  require 'mirah/commands'
@@ -57,30 +64,45 @@ module Mirah
57
64
  puts message
58
65
  return
59
66
  end
60
- puts "#{position.file}:#{position.start_line}: #{message}"
61
- file_offset = 0
62
- startline = position.start_line - 1
63
- endline = position.end_line - 1
64
- start_col = position.start_col - 1
65
- end_col = position.end_col - 1
66
- # don't try to search dash_e
67
- # TODO: show dash_e source the same way
68
- if File.exist? position.file
69
- File.open(position.file).each_with_index do |line, lineno|
70
- if lineno >= startline && lineno <= endline
71
- puts line.chomp
72
- if lineno == startline
73
- print ' ' * start_col
74
- else
75
- start_col = 0
76
- end
77
- if lineno < endline
78
- puts '^' * (line.size - start_col)
79
- else
80
- puts '^' * [end_col - start_col, 1].max
81
- end
82
- end
83
- end
67
+ puts "#{position.source.name}:#{position.start_line}: #{message}"
68
+ puts underline(position)
69
+ end
70
+
71
+ def self.underline(position)
72
+ start_line = position.start_line - position.source.initial_line
73
+ end_line = position.end_line - position.source.initial_line
74
+
75
+ start_col = position.start_column
76
+ end_col = position.end_column
77
+ adjustment = if start_line == 0
78
+ position.source.initial_column
79
+ else
80
+ 1
81
+ end
82
+
83
+ start_col -= adjustment
84
+ end_col -= adjustment
85
+
86
+ result = ""
87
+ position.source.contents.each_line.with_index do |line, lineno|
88
+ break if lineno > end_line
89
+ next if lineno < start_line
90
+
91
+ chomped = line.chomp
92
+ result << chomped
93
+ result << "\n"
94
+
95
+ start = 0
96
+ start = start_col if lineno == start_line
97
+
98
+ result << " " * start
99
+
100
+ endcol = chomped.size
101
+ endcol = end_col if lineno == end_line
102
+
103
+ result << "^" * [endcol - start, 1].max
104
+ result << "\n"
84
105
  end
106
+ result
85
107
  end
86
108
  end
data/lib/mirah/ast.rb CHANGED
@@ -16,7 +16,6 @@
16
16
  require 'mirah/util/delegate'
17
17
  require 'mirah/transform'
18
18
  require 'mirah/ast/scope'
19
- require 'jruby/core_ext'
20
19
 
21
20
  module Mirah
22
21
  module AST
@@ -24,610 +23,21 @@ module Mirah
24
23
  attr_accessor :verbose
25
24
  end
26
25
 
27
- # The top of the AST class hierarchy, this represents an abstract AST node.
28
- # It provides accessors for _children_, an array of all child nodes,
29
- # _parent_, a reference to this node's parent (nil if none), and _newline_,
30
- # whether this node represents a new line.
31
- class Node
32
- include Java::DubyLangCompiler.Node
33
- include Enumerable
26
+ java_import 'mirah.lang.ast.Array'
27
+ java_import 'mirah.lang.ast.Annotation'
28
+ java_import 'mirah.lang.ast.Constant'
29
+ java_import 'mirah.lang.ast.EmptyArray'
30
+ java_import 'mirah.lang.ast.Fixnum'
31
+ java_import 'mirah.lang.ast.HashEntry'
32
+ java_import 'mirah.lang.ast.LocalAccess'
33
+ java_import 'mirah.lang.ast.Node'
34
+ java_import 'mirah.lang.ast.NodeList'
35
+ java_import 'mirah.lang.ast.Noop'
36
+ java_import 'mirah.lang.ast.OptionalArgument'
37
+ java_import 'mirah.lang.ast.Position'
38
+ java_import 'mirah.lang.ast.SimpleString'
39
+ java_import 'mirah.lang.ast.TypeName'
40
+ java_import 'mirah.lang.ast.TypeRef'
34
41
 
35
- attr_accessor :children
36
- attr_accessor :parent
37
- attr_accessor :position
38
- attr_accessor :newline
39
- attr_accessor :inferred_type
40
-
41
- # defines children of a node by name,
42
- # respecting call order.
43
- #
44
- # @param [Symbol] name the name of the child node
45
- def self.child(name)
46
- @children ||= []
47
- index = @children.size
48
- class_eval <<-EOF
49
- def #{name}
50
- @children[#{index}]
51
- end
52
-
53
- def #{name}=(node)
54
- @children[#{index}] = _set_parent(node)
55
- end
56
- EOF
57
- @children << name
58
- end
59
-
60
- def self.child_name(i)
61
- @children[i] if @children
62
- end
63
-
64
- def child_nodes
65
- java.util.ArrayList.new(@children)
66
- end
67
-
68
- #
69
- # @param [Mirah::AST::Node] parent the parent node
70
- # @param [JMetaPosition] position the location in the source code of the node
71
- # @param [Array] children the list of child nodes
72
- # @yield [self] yields the node being initialized, expects the list of children as the result.
73
- # takes priority over the `children` argument.
74
- #
75
- def initialize(parent, position, children = [])
76
- # JRuby 1.6.x doesn't seem to like become_java! as much (see bottom of class)
77
- if JRUBY_VERSION < '1.7'
78
- JRuby.reference(self.class).setRubyClassAllocator(JRuby.reference(self.class).reified_class)
79
- end
80
-
81
- unless parent.nil? || Mirah::AST::Node === parent
82
- raise "Mirah::AST::Node.new parent #{parent.class} must be nil or === Mirah::AST::Node."
83
- end
84
-
85
- @parent = parent
86
- @newline = false
87
- @inferred_type = nil
88
- @resolved = false
89
- @position = position
90
- if block_given?
91
- @children ||= []
92
- @children = yield(self) || []
93
- else
94
- @children = children
95
- end
96
- end
97
-
98
- def _dump(depth)
99
- to_skip = %w(@parent @newline @inferred_type @resolved @proxy @scope @class_scope @static_scope @typer)
100
- vars = {}
101
- instance_variables.each do |name|
102
- next if to_skip.include?(name)
103
- vars[name] = instance_variable_get(name)
104
- begin
105
- Mirah::AST::Unquote.extract_values do
106
- Marshal.dump(vars[name]) if AST.verbose
107
- end
108
- rescue
109
- puts "#{self}: Failed to marshal #{name}"
110
- puts inspect
111
- puts $!, $@
112
- raise $!
113
- end
114
- end
115
- Marshal.dump(vars)
116
- end
117
-
118
- def self._load(vars)
119
- node = self.allocate
120
- Marshal.load(vars).each do |name, value|
121
- node.instance_variable_set(name, value)
122
- end
123
- node.children.each do |child|
124
- node._set_parent(child)
125
- end
126
- node.validate_children
127
- node
128
- end
129
-
130
- def validate_children
131
- validate_name if respond_to?(:validate_name)
132
- children.each_with_index do |child, i|
133
- validate_child(child, i)
134
- end
135
- end
136
-
137
- def validate_child(child, i)
138
- name = self.class.child_name(i)
139
- validator = :"validate_#{name}"
140
- if name && respond_to?(validator)
141
- send validator
142
- else
143
- if UnquotedValue === child
144
- self[i] = child.node
145
- end
146
- end
147
- end
148
-
149
- def line_number
150
- if @position
151
- @position.start_line + 1
152
- else
153
- 0
154
- end
155
- end
156
-
157
- def log(message)
158
- puts "* [AST] [#{simple_name}] " + message if AST.verbose
159
- end
160
-
161
- def inspect_children(indent = 0)
162
- indent_str = ' ' * indent
163
- str = ''
164
- children.each_with_index do |child, i|
165
- extra_indent = 0
166
- if child
167
- name = self.class.child_name(i)
168
-
169
- wrong_parent = lambda do |child|
170
- if Node === child && child.parent != self
171
- "\n#{indent_str} (wrong parent)"
172
- else
173
- ""
174
- end
175
- end
176
-
177
- if Mirah::AST.verbose && name
178
- str << "\n#{indent_str} #{name}:"
179
- extra_indent = 1
180
- end
181
-
182
- case child
183
- when ::Array
184
- child.each do |ary_child|
185
-
186
- str << wrong_parent[ary_child] if Mirah::AST.verbose
187
-
188
- str << "\n#{ary_child.inspect(indent + extra_indent + 1)}"
189
- end
190
- when ::Hash, ::String
191
- str << "\n#{indent_str} #{child.inspect}"
192
- else
193
- str << wrong_parent[child] if Mirah::AST.verbose
194
-
195
- begin
196
- str << "\n#{child.inspect(indent + extra_indent + 1)}"
197
- rescue ArgumentError => ex
198
- str << "\n#{indent_str} #{child.inspect}"
199
- end
200
- end
201
- end
202
- end
203
- str
204
- end
205
-
206
- def inspect(indent = 0)
207
- indent_str = ' ' * indent
208
- indent_str << to_s << inspect_children(indent)
209
- end
210
-
211
- def simple_name
212
- self.class.name.split("::")[-1]
213
- end
214
-
215
- def to_s; simple_name; end
216
-
217
- def string_value
218
- raise Mirah::SyntaxError.new("Can't use #{self.class} as string literal")
219
- end
220
-
221
- def [](index) children[index] end
222
-
223
- def []=(index, node)
224
- node.parent = self
225
- @children[index] = node
226
- end
227
-
228
- def each(&b) children.each(&b) end
229
-
230
- def <<(node)
231
- @children << _set_parent(node)
232
- self
233
- end
234
-
235
- def insert(index, node)
236
- node.parent = self
237
- @children.insert(index, node)
238
- end
239
-
240
- def empty?
241
- @children.empty?
242
- end
243
-
244
- def resolved!(typer=nil)
245
- log "#{to_s} resolved!"
246
- @resolved = true
247
- end
248
-
249
- def resolved?; @resolved end
250
-
251
- def resolve_if(typer)
252
- unless resolved?
253
- @inferred_type = yield
254
- @inferred_type ? resolved!(typer) : typer.defer(self)
255
- end
256
- @inferred_type
257
- end
258
-
259
- def self.===(other)
260
- super || (other.kind_of?(NodeProxy) && (self === other.__getobj__))
261
- end
262
-
263
- def _set_parent(node)
264
- case node
265
- when Node
266
- node.parent = self
267
- when ::Array
268
- node.each {|x| x.parent = self if x}
269
- end
270
- node
271
- end
272
-
273
- def initialize_copy(other)
274
- # bug: node is deferred, but it's parent isn't
275
- # parent gets duped
276
- # duped parent is inferred so it's children aren't
277
- # original node gets inferred, but not the duplicate child
278
- @inferred_type = @resolved = nil
279
- @parent = nil
280
- @children = []
281
- other.children.each do |child|
282
- case child
283
- when ::Array
284
- self << child.map {|x| x.dup}
285
- when nil
286
- self << nil
287
- else
288
- self << child.dup
289
- end
290
- end
291
- end
292
-
293
- def inferred_type!
294
- unless @inferred_type
295
- raise Mirah::InternalCompilerError.new(
296
- "Internal Error: #{self.class} never inferred", self)
297
- end
298
- inferred_type
299
- end
300
-
301
- def top_level?
302
- false
303
- end
304
-
305
- if JRUBY_VERSION >= '1.7'
306
- become_java!
307
- end
308
- end
309
-
310
- class ErrorNode < Node
311
- def initialize(parent, error)
312
- super(parent, error.position)
313
- @error = error
314
- @inferred_type = TypeReference::ErrorType
315
- @resolved = true
316
- end
317
-
318
- def infer(typer, expression)
319
- end
320
- end
321
-
322
- module Named
323
- attr_reader :name
324
-
325
- def name=(name)
326
- if Node === name
327
- name.parent = self
328
- end
329
- @name = name
330
- end
331
-
332
- def to_s
333
- "#{super}(#{name})"
334
- end
335
-
336
- def string_value
337
- name
338
- end
339
-
340
- def validate_name
341
- if UnquotedValue === @name
342
- @name = @name.name
343
- end
344
- end
345
- end
346
-
347
- module Typed
348
- attr_accessor :type
349
- end
350
-
351
- module Valued
352
- include Typed
353
- attr_accessor :value
354
- end
355
-
356
- module Literal
357
- include Typed
358
- attr_accessor :literal
359
-
360
- def to_s
361
- "#{super}(#{literal.inspect})"
362
- end
363
-
364
- def string_value
365
- literal.to_s
366
- end
367
- end
368
-
369
- module Annotated
370
- attr_accessor :annotations
371
-
372
- def annotation(name)
373
- name = name.to_s
374
- annotations.find {|a| a.name == name}
375
- end
376
- end
377
-
378
- module Binding
379
- def binding_type(mirah=nil)
380
- static_scope.binding_type(defining_class, mirah)
381
- end
382
-
383
- def binding_type=(type)
384
- static_scope.binding_type = type
385
- end
386
-
387
- def has_binding?
388
- static_scope.has_binding?
389
- end
390
- end
391
-
392
- class NodeProxy < Mirah::Util::DelegateClass(Node)
393
- include Java::DubyLangCompiler::Node
394
- include Java::DubyLangCompiler.Call
395
-
396
- def __inline__(node)
397
- node.parent = parent
398
- __setobj__(node)
399
- end
400
-
401
- def dup
402
- value = __getobj__.dup
403
- if value.respond_to?(:proxy=)
404
- new = super
405
- new.__setobj__(value)
406
- new.proxy = new
407
- new
408
- else
409
- value
410
- end
411
- end
412
-
413
- def _dump(depth)
414
- Marshal.dump(__getobj__)
415
- end
416
-
417
- def self._load(str)
418
- value = Marshal.load(str)
419
- if value.respond_to?(:proxy=)
420
- proxy = NodeProxy.new(value)
421
- proxy.proxy = proxy
422
- else
423
- value
424
- end
425
- end
426
- end
427
-
428
- class TypeReference < Node
429
- include Named
430
- attr_accessor :array
431
- alias array? array
432
- attr_accessor :meta
433
- alias meta? meta
434
-
435
- def initialize(name, array = false, meta = false, position=nil)
436
- super(nil, position)
437
- self.name = name
438
- @array = array
439
- @meta = meta
440
- end
441
-
442
- def type_reference(typer)
443
- typer.type_reference(nil, name, array, meta)
444
- end
445
-
446
- def to_s
447
- "Type(#{name}#{array? ? ' array' : ''}#{meta? ? ' meta' : ''})"
448
- end
449
-
450
- def full_name
451
- "#{name}#{array ? '[]' : ''}"
452
- end
453
-
454
- def ==(other)
455
- to_s == other.to_s
456
- end
457
-
458
- def eql?(other)
459
- self == other
460
- end
461
-
462
- def hash
463
- to_s.hash
464
- end
465
-
466
- def is_parent(other)
467
- # default behavior now is to disallow any polymorphic types
468
- self == other
469
- end
470
-
471
- def compatible?(other)
472
- # default behavior is only exact match right now
473
- self == other ||
474
- error? || other.error? ||
475
- unreachable? || other.unreachable?
476
- end
477
-
478
- def iterable?
479
- array?
480
- end
481
-
482
- def component_type
483
- AST.type(nil, name) if array?
484
- end
485
-
486
- def basic_type
487
- if array? || meta?
488
- TypeReference.new(name, false, false)
489
- else
490
- self
491
- end
492
- end
493
-
494
- def narrow(other)
495
- # only exact match allowed for now, so narrowing is a noop
496
- if error? || unreachable?
497
- other
498
- else
499
- self
500
- end
501
- end
502
-
503
- def unmeta
504
- TypeReference.new(name, array, false)
505
- end
506
-
507
- def meta
508
- TypeReference.new(name, array, true)
509
- end
510
-
511
- def void?
512
- name == :void
513
- end
514
-
515
- def error?
516
- name == :error
517
- end
518
-
519
- def null?
520
- name == :null
521
- end
522
-
523
- def unreachable?
524
- name == :unreachable
525
- end
526
-
527
- def block?
528
- name == :block
529
- end
530
-
531
- def primitive?
532
- true
533
- end
534
-
535
- def _dump(depth)
536
- Marshal.dump([name, array?, meta?])
537
- end
538
-
539
- def self._load(str)
540
- AST::Type(*Marshal.load(str))
541
- end
542
-
543
- NoType = TypeReference.new(:notype)
544
- NullType = TypeReference.new(:null)
545
- ErrorType = TypeReference.new(:error)
546
- UnreachableType = TypeReference.new(:unreachable)
547
- BlockType = TypeReference.new(:block)
548
- end
549
-
550
- class TypeDefinition < TypeReference
551
- attr_accessor :superclass, :interfaces
552
-
553
- def initialize(name, superclass, interfaces)
554
- super(name, false)
555
-
556
- @superclass = superclass
557
- @interfaces = interfaces
558
- end
559
- end
560
-
561
- def self.type_factory
562
- Thread.current[:ast_type_factory]
563
- end
564
-
565
- def self.type_factory=(factory)
566
- Thread.current[:ast_type_factory] = factory
567
- end
568
-
569
- # Shortcut method to construct type references
570
- def self.type(scope, typesym, array = false, meta = false)
571
- factory = type_factory
572
- if factory
573
- factory.type(scope, typesym, array, meta)
574
- else
575
- TypeReference.new(typesym, array, meta)
576
- end
577
- end
578
-
579
- def self.no_type
580
- factory = type_factory
581
- if factory
582
- factory.no_type
583
- else
584
- TypeReference::NoType
585
- end
586
- end
587
-
588
- def self.error_type
589
- TypeReference::ErrorType
590
- end
591
-
592
- def self.unreachable_type
593
- factory = type_factory
594
- if factory
595
- factory.unreachable_type
596
- else
597
- TypeReference::UnreachableType
598
- end
599
- end
600
-
601
- def self.block_type
602
- TypeReference::BlockType
603
- end
604
-
605
- def self.fixnum(parent, position, literal)
606
- Fixnum.new(parent, position, literal)
607
- end
608
-
609
- def self.float(parent, position, literal)
610
- Float.new(parent, position, literal)
611
- end
612
-
613
- def self.defmacro(name, &block)
614
- @macros ||= {}
615
- raise "Conflicting macros for #{name}" if @macros[name]
616
- @macros[name] = block
617
- end
618
-
619
- def self.macro(name)
620
- @macros[name]
621
- end
622
42
  end
623
43
  end
624
-
625
- require 'mirah/ast/local'
626
- require 'mirah/ast/call'
627
- require 'mirah/ast/flow'
628
- require 'mirah/ast/literal'
629
- require 'mirah/ast/method'
630
- require 'mirah/ast/class'
631
- require 'mirah/ast/structure'
632
- require 'mirah/ast/type'
633
- require 'mirah/ast/intrinsics'