duby 0.0.2-java

Sign up to get free protection for your applications and to get access to all the features.
Files changed (77) hide show
  1. data/History.txt +8 -0
  2. data/README.txt +39 -0
  3. data/Rakefile +13 -0
  4. data/bin/duby +9 -0
  5. data/bin/dubyc +9 -0
  6. data/bin/dubyp +9 -0
  7. data/examples/README +16 -0
  8. data/examples/appengine/Rakefile +72 -0
  9. data/examples/appengine/Readme +27 -0
  10. data/examples/appengine/config.ru +7 -0
  11. data/examples/appengine/lib/duby/plugin/datastore.rb +171 -0
  12. data/examples/appengine/src/com/google/appengine/ext/duby/db/Model.duby +132 -0
  13. data/examples/appengine/src/com/ribrdb/DubyApp.duby +28 -0
  14. data/examples/appengine/src/com/ribrdb/list.dhtml +15 -0
  15. data/examples/construction.duby +8 -0
  16. data/examples/edb.duby +3 -0
  17. data/examples/fib.duby +24 -0
  18. data/examples/fields.duby +22 -0
  19. data/examples/fractal.duby +57 -0
  20. data/examples/java_thing.duby +13 -0
  21. data/examples/simple_class.duby +12 -0
  22. data/examples/swing.duby +20 -0
  23. data/examples/tak.duby +15 -0
  24. data/examples/test.edb +9 -0
  25. data/javalib/JRubyParser.jar +0 -0
  26. data/lib/duby.rb +168 -0
  27. data/lib/duby/ast.rb +386 -0
  28. data/lib/duby/ast/call.rb +145 -0
  29. data/lib/duby/ast/class.rb +154 -0
  30. data/lib/duby/ast/flow.rb +332 -0
  31. data/lib/duby/ast/intrinsics.rb +56 -0
  32. data/lib/duby/ast/literal.rb +97 -0
  33. data/lib/duby/ast/local.rb +92 -0
  34. data/lib/duby/ast/method.rb +244 -0
  35. data/lib/duby/ast/structure.rb +62 -0
  36. data/lib/duby/ast/type.rb +93 -0
  37. data/lib/duby/c/compiler.rb +134 -0
  38. data/lib/duby/compiler.rb +282 -0
  39. data/lib/duby/jvm/compiler.rb +766 -0
  40. data/lib/duby/jvm/method_lookup.rb +193 -0
  41. data/lib/duby/jvm/source_compiler.rb +605 -0
  42. data/lib/duby/jvm/source_generator/builder.rb +387 -0
  43. data/lib/duby/jvm/source_generator/loops.rb +110 -0
  44. data/lib/duby/jvm/source_generator/precompile.rb +170 -0
  45. data/lib/duby/jvm/source_generator/typer.rb +11 -0
  46. data/lib/duby/jvm/typer.rb +131 -0
  47. data/lib/duby/jvm/types.rb +331 -0
  48. data/lib/duby/jvm/types/basic_types.rb +19 -0
  49. data/lib/duby/jvm/types/boolean.rb +11 -0
  50. data/lib/duby/jvm/types/enumerable.rb +63 -0
  51. data/lib/duby/jvm/types/factory.rb +155 -0
  52. data/lib/duby/jvm/types/floats.rb +70 -0
  53. data/lib/duby/jvm/types/integers.rb +110 -0
  54. data/lib/duby/jvm/types/intrinsics.rb +230 -0
  55. data/lib/duby/jvm/types/literals.rb +82 -0
  56. data/lib/duby/jvm/types/methods.rb +381 -0
  57. data/lib/duby/jvm/types/number.rb +92 -0
  58. data/lib/duby/nbcompiler.rb +29 -0
  59. data/lib/duby/old/compiler_old.rb +845 -0
  60. data/lib/duby/old/declaration.rb +72 -0
  61. data/lib/duby/old/mapper.rb +72 -0
  62. data/lib/duby/old/signature.rb +52 -0
  63. data/lib/duby/old/typer_old.rb +163 -0
  64. data/lib/duby/plugin/edb.rb +25 -0
  65. data/lib/duby/plugin/java.rb +42 -0
  66. data/lib/duby/plugin/math.rb +84 -0
  67. data/lib/duby/transform.rb +1028 -0
  68. data/lib/duby/typer.rb +369 -0
  69. data/test/TestUser.class +0 -0
  70. data/test/test_ast.rb +391 -0
  71. data/test/test_compilation.rb +98 -0
  72. data/test/test_java_typer.rb +199 -0
  73. data/test/test_javac_compiler.rb +58 -0
  74. data/test/test_jvm_compiler.rb +1770 -0
  75. data/test/test_math_plugin.rb +87 -0
  76. data/test/test_typer.rb +246 -0
  77. metadata +156 -0
@@ -0,0 +1,170 @@
1
+ require 'duby/ast'
2
+
3
+ module Duby::AST
4
+ class TempValue
5
+ def initialize(node, compiler=nil, value=nil)
6
+ if compiler.nil?
7
+ @tempname = node
8
+ else
9
+ @tempname = compiler.temp(node, value)
10
+ @tempvalue = value || node
11
+ end
12
+ end
13
+
14
+ def compile(compiler, expression)
15
+ if expression
16
+ compiler.method.print @tempname
17
+ end
18
+ end
19
+
20
+ def reload(compiler)
21
+ compiler.assign(@tempname, @tempvalue)
22
+ end
23
+ end
24
+
25
+ class Node
26
+ def expr?(compiler)
27
+ true
28
+ end
29
+
30
+ def precompile(compiler)
31
+ if expr?(compiler)
32
+ self
33
+ else
34
+ temp(compiler)
35
+ end
36
+ end
37
+
38
+ def temp(compiler, value=nil)
39
+ TempValue.new(self, compiler, value)
40
+ end
41
+ end
42
+
43
+ class Body
44
+ def expr?(compiler)
45
+ false
46
+ end
47
+ end
48
+
49
+ class If
50
+ def expr?(compiler)
51
+ return false unless condition.predicate.expr?(compiler)
52
+ return false unless body.nil? || body.expr?(compiler)
53
+ return false unless self.else.nil? || self.else.expr?(compiler)
54
+ true
55
+ end
56
+ end
57
+
58
+ class Loop
59
+ def expr?(compiler)
60
+ false
61
+ end
62
+
63
+ def precompile(compiler)
64
+ compile(compiler, false)
65
+ temp(compiler, 'null')
66
+ end
67
+ end
68
+
69
+ class Call
70
+ def method(compiler=nil)
71
+ @method ||= begin
72
+ arg_types = parameters.map {|p| p.inferred_type}
73
+ target.inferred_type.get_method(name, arg_types)
74
+ end
75
+ end
76
+
77
+ def expr?(compiler)
78
+ target.expr?(compiler) &&
79
+ parameters.all? {|p| p.expr?(compiler)} &&
80
+ !method.return_type.kind_of?(Duby::AST::InlineCode) &&
81
+ !method.actual_return_type.void?
82
+ end
83
+ end
84
+
85
+ class FunctionalCall
86
+ def method(compiler)
87
+ @method ||= begin
88
+ arg_types = parameters.map {|p| p.inferred_type}
89
+ compiler.self_type.get_method(name, arg_types)
90
+ end
91
+ end
92
+
93
+ def expr?(compiler)
94
+ parameters.all? {|p| p.expr?(compiler)} &&
95
+ (cast? || !method(compiler).actual_return_type.void?)
96
+ end
97
+ end
98
+
99
+ # TODO merge with FunctionalCall logic (almost identical)
100
+ class Super
101
+ def method(compiler)
102
+ @method ||= begin
103
+ arg_types = parameters.map {|p| p.inferred_type}
104
+ compiler.self_type.superclass.get_method(name, arg_types)
105
+ end
106
+ end
107
+
108
+ def expr?(compiler)
109
+ parameters.all? {|p| p.expr?(compiler)} &&
110
+ !method(compiler).actual_return_type.void?
111
+ end
112
+ end
113
+
114
+ class EmtpyArray
115
+ def expr?(compiler)
116
+ size.expr?(compiler)
117
+ end
118
+ end
119
+
120
+ class LocalAssignment
121
+ def expr?(compiler)
122
+ compiler.method.local?(name) && value.expr?(compiler)
123
+ end
124
+
125
+ def precompile(compiler)
126
+ if expr?(compiler)
127
+ self
128
+ else
129
+ compile(compiler, false)
130
+ TempValue.new(name)
131
+ end
132
+ end
133
+ end
134
+
135
+ class Return
136
+ def expr?(compiler)
137
+ false
138
+ end
139
+ end
140
+
141
+ class Raise
142
+ def expr?(compiler)
143
+ false
144
+ end
145
+ end
146
+
147
+ class Rescue
148
+ def expr?(compiler)
149
+ false
150
+ end
151
+ end
152
+
153
+ class Ensure
154
+ def expr?(compiler)
155
+ false
156
+ end
157
+ end
158
+
159
+ class FieldAssignment
160
+ def expr?(compiler)
161
+ false
162
+ end
163
+ end
164
+
165
+ class LocalAssignment
166
+ def expr?(compiler)
167
+ false
168
+ end
169
+ end
170
+ end
@@ -0,0 +1,11 @@
1
+ require 'duby/jvm/typer'
2
+ require 'duby/jvm/source_generator/builder'
3
+
4
+ module Duby
5
+ module Typer
6
+ class JavaSource < JVM
7
+ include Duby::JVM::Types
8
+
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,131 @@
1
+ require 'duby/typer'
2
+ require 'duby/jvm/types'
3
+ require 'duby/jvm/types/factory'
4
+
5
+ module Duby
6
+ module Typer
7
+ class JVM < Simple
8
+ include Duby::JVM::Types
9
+
10
+ attr_reader :transformer
11
+
12
+ def initialize(filename, transformer)
13
+ @factory = AST.type_factory
14
+ @transformer = transformer
15
+ unless @factory.kind_of? TypeFactory
16
+ raise "TypeFactory not installed"
17
+ end
18
+ @known_types = @factory.known_types
19
+ classname = File.basename(filename, '.duby')
20
+ main_class = @factory.declare_type(classname)
21
+ @known_types['self'] = main_class.meta
22
+ @errors = []
23
+ end
24
+
25
+ def type_reference(name, array=false, meta=false)
26
+ @factory.type(name, array, meta)
27
+ end
28
+
29
+ def alias_types(short, long)
30
+ @known_types[short] = type_reference(long)
31
+ end
32
+
33
+ def name
34
+ "JVM"
35
+ end
36
+
37
+ def type_definition(name, superclass, interfaces)
38
+ @known_types[name]
39
+ end
40
+
41
+ def null_type
42
+ Null
43
+ end
44
+
45
+ def no_type
46
+ Void
47
+ end
48
+
49
+ def array_type
50
+ # TODO: allow other types for pre-1.2 profiles
51
+ type_reference("java.util.List")
52
+ end
53
+
54
+ def hash_type
55
+ # TODO: allow other types for pre-1.2 profiles
56
+ type_reference("java.util.Map")
57
+ end
58
+
59
+ def learn_method_type(target_type, name, parameter_types, type, exceptions)
60
+ static = target_type.meta?
61
+ unless target_type.unmeta.kind_of?(TypeDefinition)
62
+ raise "Method defined on #{target_type}"
63
+ end
64
+ if static
65
+ target_type.unmeta.declare_static_method(name, parameter_types, type, exceptions)
66
+ else
67
+ target_type.declare_method(name, parameter_types, type, exceptions)
68
+ end
69
+ super
70
+ end
71
+
72
+ def infer_signature(method_def)
73
+ signature = method_def.signature
74
+ sig_args = signature.dup
75
+ return_type = sig_args.delete(:return)
76
+ exceptions = sig_args.delete(:throws)
77
+ args = method_def.arguments.args || []
78
+ static = method_def.kind_of? Duby::AST::StaticMethodDefinition
79
+ if sig_args.size != args.size
80
+ # If the superclass declares one method with the same name and
81
+ # same number of arguments, assume we're overriding it.
82
+ found = nil
83
+ ambiguous = false
84
+ classes = [self_type.superclass] + self_type.interfaces
85
+ while classes.size > 0
86
+ cls = classes.pop
87
+ if static
88
+ methods = cls.declared_class_methods
89
+ else
90
+ methods = cls.declared_instance_methods
91
+ end
92
+ methods.each do |method|
93
+ if method.name == method_def.name &&
94
+ method.argument_types.size == args.size
95
+ if found && found.argument_types != method.argument_types
96
+ ambiguous = true
97
+ else
98
+ found ||= method
99
+ end
100
+ end
101
+ end
102
+ classes << cls.superclass if cls.superclass
103
+ end
104
+ if found && !ambiguous
105
+ signature[:return] = found.actual_return_type
106
+ signature[:throws] = found.exceptions
107
+ args.zip(found.argument_types) do |arg, type|
108
+ signature[arg.name.intern] = type
109
+ end
110
+ end
111
+ elsif signature[:return].nil? && !static
112
+ arg_types = args.map do |arg|
113
+ signature[arg.name.intern]
114
+ end
115
+ method = self_type.find_method(
116
+ self_type, method_def.name, arg_types, false)
117
+ interfaces = self_type.interfaces.dup
118
+ until method || interfaces.empty?
119
+ interface = interfaces.pop
120
+ method = interface.find_method(
121
+ interface, method_def.name, arg_types, false)
122
+ end
123
+ if method
124
+ signature[:return] = method.actual_return_type
125
+ signature[:throws] = method.exceptions
126
+ end
127
+ end
128
+ end
129
+ end
130
+ end
131
+ end
@@ -0,0 +1,331 @@
1
+ require 'bitescript'
2
+ require 'duby/ast'
3
+ require 'duby/jvm/method_lookup'
4
+ require 'duby/jvm/compiler'
5
+
6
+ class Object
7
+ def class_builder?
8
+ self.class.name =~ /::ClassBuilder$/
9
+ end
10
+ end
11
+
12
+ module Duby
13
+ module JVM
14
+ module Types
15
+ class Type < AST::TypeReference
16
+ include Duby::JVM::MethodLookup
17
+
18
+ def log(message)
19
+ puts "* [JVM::Types] #{message}" if Duby::Compiler::JVM.verbose
20
+ end
21
+
22
+ def initialize(java_type)
23
+ orig_type = java_type
24
+ if !(java_type.kind_of?(Java::JavaClass) ||
25
+ java_type.class_builder?)
26
+ java_type = java_type.java_class
27
+ end
28
+ super(java_type.name, false, false)
29
+ raise ArgumentError, "Bad type #{orig_type}" if name =~ /Java::/
30
+ @type = java_type
31
+ end
32
+
33
+ def jvm_type
34
+ @type
35
+ end
36
+
37
+ def void?
38
+ false
39
+ end
40
+
41
+ def meta?
42
+ false
43
+ end
44
+
45
+ def array?
46
+ false
47
+ end
48
+
49
+ def primitive?
50
+ false
51
+ end
52
+
53
+ def interface?
54
+ @type.interface?
55
+ end
56
+
57
+ def is_parent(other)
58
+ assignable_from?(other)
59
+ end
60
+
61
+ def compatible?(other)
62
+ assignable_from?(other)
63
+ end
64
+
65
+ def assignable_from?(other)
66
+ return true if !primitive? && other == Null
67
+ return true if other == self
68
+ return true if other.error? || other.unreachable?
69
+ begin
70
+ jvm_type.assignable_from?(other.jvm_type)
71
+ rescue
72
+ assignable_from?(other.superclass) ||
73
+ other.interfaces.any? {|i| assignable_from?(i)}
74
+ end
75
+ end
76
+
77
+ def iterable?
78
+ ['java.lang.Iterable',
79
+ 'java.util.Iterator',
80
+ 'java.util.Enumeration'].any? {|n| AST.type(n).assignable_from(self)}
81
+ end
82
+
83
+ def component_type
84
+ AST.type('java.lang.Object') if iterable?
85
+ end
86
+
87
+ def meta
88
+ @meta ||= MetaType.new(self)
89
+ end
90
+
91
+ def unmeta
92
+ self
93
+ end
94
+
95
+ def basic_type
96
+ self
97
+ end
98
+
99
+ def array_type
100
+ @array_type ||= ArrayType.new(self)
101
+ end
102
+
103
+ def prefix
104
+ 'a'
105
+ end
106
+
107
+ # is this a 64 bit type?
108
+ def wide?
109
+ false
110
+ end
111
+
112
+ def inspect(indent=0)
113
+ "#{' ' * indent}#<#{self.class.name} #{name}>"
114
+ end
115
+
116
+ def newarray(method)
117
+ method.anewarray(self)
118
+ end
119
+
120
+ def superclass
121
+ raise "Incomplete type #{self}" unless jvm_type
122
+ AST.type(jvm_type.superclass) if jvm_type.superclass
123
+ end
124
+
125
+ def interfaces
126
+ @interfaces ||= jvm_type.interfaces.map do |interface|
127
+ AST.type(interface)
128
+ end
129
+ end
130
+
131
+ def astore(builder)
132
+ if primitive?
133
+ builder.send "#{name[0,1]}astore"
134
+ else
135
+ builder.aastore
136
+ end
137
+ end
138
+
139
+ def aload(builder)
140
+ if primitive?
141
+ builder.send "#{name[0,1]}aload"
142
+ else
143
+ builder.aaload
144
+ end
145
+ end
146
+ end
147
+
148
+ class PrimitiveType < Type
149
+ def initialize(type, wrapper)
150
+ @wrapper = wrapper
151
+ super(type)
152
+ end
153
+
154
+ def primitive?
155
+ true
156
+ end
157
+
158
+ def primitive_type
159
+ @wrapper::TYPE
160
+ end
161
+
162
+ def newarray(method)
163
+ method.send "new#{name}array"
164
+ end
165
+
166
+ def interfaces
167
+ []
168
+ end
169
+
170
+ def convertible_to?(type)
171
+ return true if type == self
172
+ a, b = TYPE_ORDERING.index(self), TYPE_ORDERING.index(type)
173
+ a && b && b > a
174
+ end
175
+ end
176
+
177
+ class MetaType < Type
178
+ attr_reader :unmeta
179
+
180
+ def initialize(unmeta)
181
+ @name = unmeta.name
182
+ @unmeta = unmeta
183
+ end
184
+
185
+ def basic_type
186
+ @unmeta.basic_type
187
+ end
188
+
189
+ def meta?
190
+ true
191
+ end
192
+
193
+ def meta
194
+ self
195
+ end
196
+
197
+ def superclass
198
+ @unmeta.superclass.meta if @unmeta.superclass
199
+ end
200
+
201
+ def interfaces
202
+ []
203
+ end
204
+
205
+ def jvm_type
206
+ unmeta.jvm_type
207
+ end
208
+ end
209
+
210
+ class NullType < Type
211
+ def initialize
212
+ super(java.lang.Object)
213
+ end
214
+
215
+ def compatible?(other)
216
+ !other.primitive?
217
+ end
218
+ end
219
+
220
+ class VoidType < PrimitiveType
221
+ def initialize
222
+ super(Java::JavaLang::Void, Java::JavaLang::Void)
223
+ @name = "void"
224
+ end
225
+
226
+ def void?
227
+ true
228
+ end
229
+
230
+ def return(builder)
231
+ builder.returnvoid
232
+ end
233
+ end
234
+
235
+ class ArrayType < Type
236
+ attr_reader :component_type
237
+
238
+ def initialize(component_type)
239
+ @component_type = component_type
240
+ @name = component_type.name
241
+ end
242
+
243
+ def jvm_type
244
+ @component_type.jvm_type
245
+ end
246
+
247
+ def array?
248
+ true
249
+ end
250
+
251
+ def iterable?
252
+ true
253
+ end
254
+
255
+ def basic_type
256
+ component_type.basic_type
257
+ end
258
+
259
+ def superclass
260
+ Object
261
+ end
262
+ end
263
+
264
+ class TypeDefinition < Type
265
+ attr_accessor :node
266
+
267
+ def initialize(name, node)
268
+ if name.class_builder?
269
+ super(name)
270
+ else
271
+ raise ArgumentError, "Bad name #{name}" if name[0,1] == '.'
272
+ @name = name
273
+ end
274
+ @node = node
275
+ raise ArgumentError, "Bad type #{name}" if self.name =~ /Java::/
276
+ end
277
+
278
+ def name
279
+ if @type
280
+ @type.name
281
+ else
282
+ @name
283
+ end
284
+ end
285
+
286
+ def superclass
287
+ (node && node.superclass) || Object
288
+ end
289
+
290
+ def interfaces
291
+ if node
292
+ node.interfaces
293
+ else
294
+ []
295
+ end
296
+ end
297
+
298
+ def define(builder)
299
+ class_name = @name.tr('.', '/')
300
+ @type ||= builder.public_class(class_name, superclass, *interfaces)
301
+ end
302
+
303
+ def meta
304
+ @meta ||= TypeDefMeta.new(self)
305
+ end
306
+ end
307
+
308
+ class InterfaceDefinition < TypeDefinition
309
+ def initialize(name, node)
310
+ super(name, node)
311
+ end
312
+
313
+ def define(builder)
314
+ @type ||= builder.public_interface(@name, *interfaces)
315
+ end
316
+ end
317
+
318
+ class TypeDefMeta < MetaType
319
+ end
320
+ end
321
+ end
322
+ end
323
+
324
+ require 'duby/jvm/types/intrinsics'
325
+ require 'duby/jvm/types/methods'
326
+ require 'duby/jvm/types/number'
327
+ require 'duby/jvm/types/integers'
328
+ require 'duby/jvm/types/boolean'
329
+ require 'duby/jvm/types/floats'
330
+ require 'duby/jvm/types/basic_types'
331
+ require 'duby/jvm/types/literals'