duby 0.0.2-java → 0.0.3-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.
- data/History.txt +7 -0
- data/README.txt +18 -7
- data/Rakefile +72 -0
- data/examples/ant/example-build.xml +7 -0
- data/examples/appengine/Rakefile +8 -67
- data/examples/appengine/Readme +4 -3
- data/examples/appengine/lib/duby/appengine_tasks.rb +173 -0
- data/examples/appengine/lib/duby/plugin/datastore.rb +92 -31
- data/examples/appengine/lib/duby_task.rb +61 -0
- data/examples/appengine/src/com/ribrdb/DubyApp.duby +32 -6
- data/examples/appengine/src/com/ribrdb/list.dhtml +2 -2
- data/examples/appengine/{config.ru → src/config.ru} +0 -0
- data/examples/bintrees.duby +66 -0
- data/examples/dynamic.duby +17 -0
- data/examples/fib.duby +3 -11
- data/examples/fields.duby +3 -3
- data/examples/fractal.duby +1 -3
- data/examples/sort_closure.duby +7 -0
- data/examples/swing.duby +11 -11
- data/javalib/duby-bootstrap.jar +0 -0
- data/javalib/dynalang-invoke-0.1.jar +0 -0
- data/lib/duby.rb +168 -35
- data/lib/duby/ast.rb +224 -27
- data/lib/duby/ast/call.rb +85 -25
- data/lib/duby/ast/class.rb +112 -28
- data/lib/duby/ast/flow.rb +65 -44
- data/lib/duby/ast/intrinsics.rb +223 -21
- data/lib/duby/ast/literal.rb +67 -16
- data/lib/duby/ast/local.rb +36 -40
- data/lib/duby/ast/method.rb +83 -67
- data/lib/duby/ast/structure.rb +105 -23
- data/lib/duby/compiler.rb +83 -28
- data/lib/duby/env.rb +33 -0
- data/lib/duby/jvm/base.rb +210 -0
- data/lib/duby/jvm/compiler.rb +293 -219
- data/lib/duby/jvm/method_lookup.rb +77 -67
- data/lib/duby/jvm/source_compiler.rb +250 -157
- data/lib/duby/jvm/source_generator/builder.rb +53 -49
- data/lib/duby/jvm/source_generator/loops.rb +9 -9
- data/lib/duby/jvm/source_generator/precompile.rb +35 -25
- data/lib/duby/jvm/typer.rb +19 -10
- data/lib/duby/jvm/types.rb +127 -68
- data/lib/duby/jvm/types/basic_types.rb +26 -13
- data/lib/duby/jvm/types/enumerable.rb +6 -4
- data/lib/duby/jvm/types/factory.rb +49 -13
- data/lib/duby/jvm/types/floats.rb +16 -0
- data/lib/duby/jvm/types/integers.rb +63 -2
- data/lib/duby/jvm/types/intrinsics.rb +43 -21
- data/lib/duby/jvm/types/methods.rb +326 -86
- data/lib/duby/jvm/types/number.rb +3 -0
- data/lib/duby/nbcompiler.rb +1 -1
- data/lib/duby/plugin/edb.rb +1 -1
- data/lib/duby/plugin/java.rb +10 -1
- data/lib/duby/transform.rb +134 -46
- data/lib/duby/typer.rb +75 -50
- data/test/test_ast.rb +106 -106
- data/test/test_compilation.rb +46 -32
- data/test/test_env.rb +42 -0
- data/test/test_java_typer.rb +35 -51
- data/test/test_javac_compiler.rb +4 -1
- data/test/test_jvm_compiler.rb +564 -133
- data/test/test_typer.rb +68 -92
- metadata +37 -21
- data/examples/README +0 -16
- data/lib/duby/c/compiler.rb +0 -134
- data/lib/duby/old/compiler_old.rb +0 -845
- data/lib/duby/old/declaration.rb +0 -72
- data/lib/duby/old/mapper.rb +0 -72
- data/lib/duby/old/signature.rb +0 -52
- data/lib/duby/old/typer_old.rb +0 -163
- data/lib/duby/plugin/math.rb +0 -84
- data/test/test_math_plugin.rb +0 -87
data/lib/duby/compiler.rb
CHANGED
@@ -10,7 +10,16 @@ module Duby
|
|
10
10
|
end
|
11
11
|
end
|
12
12
|
end
|
13
|
-
|
13
|
+
|
14
|
+
class Regexp
|
15
|
+
def compile(compiler, expression)
|
16
|
+
if expression
|
17
|
+
compiler.line(line_number)
|
18
|
+
compiler.regexp(literal)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
14
23
|
class String
|
15
24
|
def compile(compiler, expression)
|
16
25
|
if expression
|
@@ -19,7 +28,19 @@ module Duby
|
|
19
28
|
end
|
20
29
|
end
|
21
30
|
end
|
22
|
-
|
31
|
+
|
32
|
+
class StringConcat
|
33
|
+
def compile(compiler, expression)
|
34
|
+
compiler.build_string(children, expression)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
class ToString
|
39
|
+
def compile(compiler, expression)
|
40
|
+
compiler.to_string(body, expression)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
23
44
|
class Float
|
24
45
|
def compile(compiler, expression)
|
25
46
|
if expression
|
@@ -28,7 +49,7 @@ module Duby
|
|
28
49
|
end
|
29
50
|
end
|
30
51
|
end
|
31
|
-
|
52
|
+
|
32
53
|
class Boolean
|
33
54
|
def compile(compiler, expression)
|
34
55
|
if expression
|
@@ -43,7 +64,7 @@ module Duby
|
|
43
64
|
compiler.array(self, expression)
|
44
65
|
end
|
45
66
|
end
|
46
|
-
|
67
|
+
|
47
68
|
class Body
|
48
69
|
def compile(compiler, expression)
|
49
70
|
compiler.line(line_number)
|
@@ -51,6 +72,13 @@ module Duby
|
|
51
72
|
end
|
52
73
|
end
|
53
74
|
|
75
|
+
class ScopedBody
|
76
|
+
def compile(compiler, expression)
|
77
|
+
compiler.line(line_number)
|
78
|
+
compiler.scoped_body(self, expression)
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
54
82
|
class Import
|
55
83
|
def compile(compiler, expression)
|
56
84
|
# TODO: what does it mean for import to be an expression?
|
@@ -74,12 +102,16 @@ module Duby
|
|
74
102
|
compiler.print(self)
|
75
103
|
end
|
76
104
|
end
|
77
|
-
|
105
|
+
|
78
106
|
class Local
|
79
107
|
def compile(compiler, expression)
|
80
108
|
if expression
|
81
109
|
compiler.line(line_number)
|
82
|
-
|
110
|
+
if captured? && scope.has_binding?
|
111
|
+
compiler.captured_local(containing_scope, name, inferred_type)
|
112
|
+
else
|
113
|
+
compiler.local(containing_scope, name, inferred_type)
|
114
|
+
end
|
83
115
|
end
|
84
116
|
end
|
85
117
|
end
|
@@ -87,58 +119,66 @@ module Duby
|
|
87
119
|
class LocalDeclaration
|
88
120
|
def compile(compiler, expression)
|
89
121
|
compiler.line(line_number)
|
90
|
-
|
122
|
+
if captured? && scope.has_binding?
|
123
|
+
compiler.captured_local_declare(containing_scope, name, type)
|
124
|
+
else
|
125
|
+
compiler.local_declare(containing_scope, name, type)
|
126
|
+
end
|
91
127
|
end
|
92
128
|
end
|
93
|
-
|
129
|
+
|
94
130
|
class LocalAssignment
|
95
131
|
def compile(compiler, expression)
|
96
132
|
compiler.line(line_number)
|
97
|
-
|
133
|
+
if captured? && scope.has_binding?
|
134
|
+
compiler.captured_local_assign(self, expression)
|
135
|
+
else
|
136
|
+
compiler.local_assign(containing_scope, name, inferred_type, expression, value)
|
137
|
+
end
|
98
138
|
end
|
99
139
|
end
|
100
|
-
|
140
|
+
|
101
141
|
class Script
|
102
142
|
def compile(compiler, expression)
|
103
143
|
# TODO: what does it mean for a script to be an expression? possible?
|
104
|
-
compiler.define_main(
|
144
|
+
compiler.define_main(self)
|
105
145
|
end
|
106
146
|
end
|
107
|
-
|
147
|
+
|
108
148
|
class MethodDefinition
|
109
149
|
def compile(compiler, expression)
|
110
150
|
# TODO: what does it mean for a method to be an expression?
|
111
151
|
compiler.define_method(self)
|
112
152
|
end
|
113
153
|
end
|
114
|
-
|
154
|
+
|
115
155
|
class ConstructorDefinition
|
116
156
|
def compile(compiler, expression)
|
117
157
|
compiler.constructor(self)
|
118
158
|
end
|
119
159
|
end
|
120
|
-
|
160
|
+
|
121
161
|
class Arguments
|
122
162
|
def compile(compiler, expression)
|
123
163
|
# TODO: what does it mean for a method to be an expression?
|
124
164
|
args.each {|arg| compiler.declare_argument(arg.name, arg.inferred_type)} if args
|
125
165
|
end
|
126
166
|
end
|
127
|
-
|
167
|
+
|
128
168
|
class Noop
|
129
169
|
def compile(compiler, expression)
|
130
170
|
# TODO: what does it mean for a noop to be an expression
|
131
171
|
# nothing
|
132
172
|
end
|
133
173
|
end
|
134
|
-
|
174
|
+
|
135
175
|
class If
|
136
176
|
def compile(compiler, expression)
|
137
177
|
compiler.line(line_number)
|
138
178
|
compiler.branch(self, expression)
|
139
179
|
end
|
140
180
|
end
|
141
|
-
|
181
|
+
|
142
182
|
class Condition
|
143
183
|
def compile(compiler, expression)
|
144
184
|
# TODO: can a condition ever be an expression? I don't think it can...
|
@@ -146,14 +186,14 @@ module Duby
|
|
146
186
|
predicate.compile(compiler, expression)
|
147
187
|
end
|
148
188
|
end
|
149
|
-
|
189
|
+
|
150
190
|
class FunctionalCall
|
151
191
|
def compile(compiler, expression)
|
152
192
|
compiler.line(line_number)
|
153
193
|
compiler.self_call(self, expression)
|
154
194
|
end
|
155
195
|
end
|
156
|
-
|
196
|
+
|
157
197
|
class Call
|
158
198
|
def compile(compiler, expression)
|
159
199
|
compiler.line(line_number)
|
@@ -167,20 +207,26 @@ module Duby
|
|
167
207
|
compiler.super_call(self, expression)
|
168
208
|
end
|
169
209
|
end
|
170
|
-
|
210
|
+
|
171
211
|
class Loop
|
172
212
|
def compile(compiler, expression)
|
173
213
|
compiler.line(line_number)
|
174
214
|
compiler.loop(self, expression)
|
175
215
|
end
|
176
216
|
end
|
177
|
-
|
217
|
+
|
178
218
|
class ClassDefinition
|
179
219
|
def compile(compiler, expression)
|
180
220
|
compiler.define_class(self, expression)
|
181
221
|
end
|
182
222
|
end
|
183
223
|
|
224
|
+
class ClosureDefinition
|
225
|
+
def compile(compiler, expression)
|
226
|
+
compiler.define_closure(self, expression)
|
227
|
+
end
|
228
|
+
end
|
229
|
+
|
184
230
|
class FieldDeclaration
|
185
231
|
def compile(compiler, expression)
|
186
232
|
compiler.field_declare(name, inferred_type, annotations)
|
@@ -218,7 +264,7 @@ module Duby
|
|
218
264
|
end
|
219
265
|
end
|
220
266
|
end
|
221
|
-
|
267
|
+
|
222
268
|
class Null
|
223
269
|
def compile(compiler, expression)
|
224
270
|
if expression
|
@@ -227,21 +273,21 @@ module Duby
|
|
227
273
|
end
|
228
274
|
end
|
229
275
|
end
|
230
|
-
|
276
|
+
|
231
277
|
class Break
|
232
278
|
def compile(compiler, expression)
|
233
279
|
compiler.line(line_number)
|
234
280
|
compiler.break(self)
|
235
281
|
end
|
236
282
|
end
|
237
|
-
|
283
|
+
|
238
284
|
class Next
|
239
285
|
def compile(compiler, expression)
|
240
286
|
compiler.line(line_number)
|
241
287
|
compiler.next(self)
|
242
288
|
end
|
243
289
|
end
|
244
|
-
|
290
|
+
|
245
291
|
class Redo
|
246
292
|
def compile(compiler, expression)
|
247
293
|
compiler.line(line_number)
|
@@ -252,7 +298,7 @@ module Duby
|
|
252
298
|
class Raise
|
253
299
|
def compile(compiler, expression)
|
254
300
|
compiler.line(line_number)
|
255
|
-
compiler._raise(
|
301
|
+
compiler._raise(exception)
|
256
302
|
end
|
257
303
|
end
|
258
304
|
|
@@ -262,14 +308,14 @@ module Duby
|
|
262
308
|
compiler.rescue(self, expression)
|
263
309
|
end
|
264
310
|
end
|
265
|
-
|
311
|
+
|
266
312
|
class Ensure
|
267
313
|
def compile(compiler, expression)
|
268
314
|
compiler.line(line_number)
|
269
315
|
compiler.ensure(self, expression)
|
270
316
|
end
|
271
317
|
end
|
272
|
-
|
318
|
+
|
273
319
|
class Self
|
274
320
|
def compile(compiler, expression)
|
275
321
|
if expression
|
@@ -278,5 +324,14 @@ module Duby
|
|
278
324
|
end
|
279
325
|
end
|
280
326
|
end
|
327
|
+
|
328
|
+
class BindingReference
|
329
|
+
def compile(compiler, expression)
|
330
|
+
if expression
|
331
|
+
compiler.line(line_number)
|
332
|
+
compiler.binding_reference
|
333
|
+
end
|
334
|
+
end
|
335
|
+
end
|
281
336
|
end
|
282
337
|
end
|
data/lib/duby/env.rb
ADDED
@@ -0,0 +1,33 @@
|
|
1
|
+
require 'rbconfig'
|
2
|
+
|
3
|
+
module Duby
|
4
|
+
module Env
|
5
|
+
|
6
|
+
# Returns the system PATH_SEPARATOR environment variable value. This is used when
|
7
|
+
# separating multiple paths in one string. If none is defined then a : (colon)
|
8
|
+
# is returned
|
9
|
+
def self.path_seperator
|
10
|
+
ps = RbConfig::CONFIG['PATH_SEPARATOR']
|
11
|
+
ps = ':' if ps.nil? || ps == ''
|
12
|
+
ps
|
13
|
+
end
|
14
|
+
|
15
|
+
# Takes an array of strings and joins them using the path_separator returning
|
16
|
+
# a single string value
|
17
|
+
def self.encode_paths(paths)
|
18
|
+
paths.join(path_seperator)
|
19
|
+
end
|
20
|
+
|
21
|
+
# Takes a single string value "paths" and returns an array of strings containing the
|
22
|
+
# original string separated using the path_separator. An option second parameter
|
23
|
+
# is an array that will have the strings appended to it. If the optional array parameter
|
24
|
+
# is supplied it is returned as the result
|
25
|
+
def self.decode_paths(paths, dest = nil)
|
26
|
+
result = dest ? dest : []
|
27
|
+
paths.split(path_seperator).each do |path|
|
28
|
+
result << path
|
29
|
+
end
|
30
|
+
result
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,210 @@
|
|
1
|
+
module Duby
|
2
|
+
module Compiler
|
3
|
+
class JVMCompilerBase
|
4
|
+
attr_accessor :filename, :method, :static, :class
|
5
|
+
|
6
|
+
def initialize(filename)
|
7
|
+
@filename = File.basename(filename)
|
8
|
+
@static = true
|
9
|
+
classname = JVM.classname_from_filename(filename)
|
10
|
+
@type = AST::type(classname)
|
11
|
+
@jump_scope = []
|
12
|
+
@bindings = Hash.new {|h, type| h[type] = type.define(@file)}
|
13
|
+
@captured_locals = Hash.new {|h, binding| h[binding] = {}}
|
14
|
+
end
|
15
|
+
|
16
|
+
def compile(ast, expression = false)
|
17
|
+
ast.compile(self, expression)
|
18
|
+
log "Compilation successful!"
|
19
|
+
end
|
20
|
+
|
21
|
+
def log(message); JVM.log(message); end
|
22
|
+
|
23
|
+
def toplevel_class
|
24
|
+
@class = @type.define(@file)
|
25
|
+
end
|
26
|
+
|
27
|
+
def generate
|
28
|
+
log "Generating #{output_type}..."
|
29
|
+
@file.generate do |filename, builder|
|
30
|
+
log " #{builder.class_name}"
|
31
|
+
if block_given?
|
32
|
+
yield filename, builder
|
33
|
+
else
|
34
|
+
File.open(filename, 'w') {|f| f.write(builder.generate)}
|
35
|
+
end
|
36
|
+
end
|
37
|
+
log "...done!"
|
38
|
+
end
|
39
|
+
|
40
|
+
def define_main(script)
|
41
|
+
body = script.body
|
42
|
+
body = body[0] if body.children.size == 1
|
43
|
+
if body.class != AST::ClassDefinition
|
44
|
+
@class = @type.define(@file)
|
45
|
+
with :method => @class.main do
|
46
|
+
log "Starting main method"
|
47
|
+
|
48
|
+
@method.start
|
49
|
+
@current_scope = script.static_scope
|
50
|
+
begin_main
|
51
|
+
|
52
|
+
prepare_binding(script) do
|
53
|
+
body.compile(self, false)
|
54
|
+
end
|
55
|
+
|
56
|
+
finish_main
|
57
|
+
@method.stop
|
58
|
+
end
|
59
|
+
@class.stop
|
60
|
+
else
|
61
|
+
body.compile(self, false)
|
62
|
+
end
|
63
|
+
|
64
|
+
log "Main method complete!"
|
65
|
+
end
|
66
|
+
|
67
|
+
def begin_main; end
|
68
|
+
def finish_main; end
|
69
|
+
|
70
|
+
def define_method(node, args_are_types)
|
71
|
+
name, signature, args = node.name, node.signature, node.arguments.args
|
72
|
+
if name == "initialize" && node.static?
|
73
|
+
name = "<clinit>"
|
74
|
+
end
|
75
|
+
if args_are_types
|
76
|
+
arg_types = args.map { |arg| arg.inferred_type } if args
|
77
|
+
else
|
78
|
+
arg_types = args
|
79
|
+
end
|
80
|
+
arg_types ||= []
|
81
|
+
return_type = signature[:return]
|
82
|
+
exceptions = signature[:throws]
|
83
|
+
puts "exceptions: #{exceptions.inspect}" if exceptions && exceptions.size > 0
|
84
|
+
|
85
|
+
with :static => @static || node.static?, :current_scope => node.static_scope do
|
86
|
+
if @static
|
87
|
+
method = @class.public_static_method(name.to_s, exceptions, return_type, *arg_types)
|
88
|
+
else
|
89
|
+
method = @class.public_method(name.to_s, exceptions, return_type, *arg_types)
|
90
|
+
end
|
91
|
+
annotate(method, node.annotations)
|
92
|
+
yield method, arg_types
|
93
|
+
end
|
94
|
+
|
95
|
+
arg_types_for_opt = []
|
96
|
+
args_for_opt = []
|
97
|
+
if args
|
98
|
+
args.each do |arg|
|
99
|
+
if AST::OptionalArgument === arg
|
100
|
+
new_args = if args_are_types
|
101
|
+
arg_types_for_opt
|
102
|
+
else
|
103
|
+
args_for_opt
|
104
|
+
end
|
105
|
+
if @static
|
106
|
+
method = @class.public_static_method(name.to_s, exceptions, return_type, *new_args)
|
107
|
+
else
|
108
|
+
method = @class.public_method(name.to_s, exceptions, return_type, *new_args)
|
109
|
+
end
|
110
|
+
|
111
|
+
with :method => method do
|
112
|
+
log "Starting new method #{name}(#{arg_types_for_opt})"
|
113
|
+
|
114
|
+
annotate(method, node.annotations)
|
115
|
+
@method.start
|
116
|
+
|
117
|
+
define_optarg_chain(name, arg,
|
118
|
+
return_type,
|
119
|
+
args_for_opt,
|
120
|
+
arg_types_for_opt)
|
121
|
+
|
122
|
+
@method.stop
|
123
|
+
end
|
124
|
+
end
|
125
|
+
arg_types_for_opt << arg.inferred_type
|
126
|
+
args_for_opt << arg
|
127
|
+
end
|
128
|
+
end
|
129
|
+
end
|
130
|
+
|
131
|
+
def constructor(node, args_are_types)
|
132
|
+
args = node.arguments.args || []
|
133
|
+
arg_types = if args_are_types
|
134
|
+
args.map { |arg| arg.inferred_type }
|
135
|
+
else
|
136
|
+
args
|
137
|
+
end
|
138
|
+
exceptions = node.signature[:throws]
|
139
|
+
method = @class.public_constructor(exceptions, *arg_types)
|
140
|
+
annotate(method, node.annotations)
|
141
|
+
with :current_scope => node.static_scope do
|
142
|
+
yield(method, args)
|
143
|
+
end
|
144
|
+
end
|
145
|
+
|
146
|
+
def define_class(class_def, expression)
|
147
|
+
with(:type => class_def.inferred_type,
|
148
|
+
:class => class_def.inferred_type.define(@file),
|
149
|
+
:static => false) do
|
150
|
+
annotate(@class, class_def.annotations)
|
151
|
+
class_def.body.compile(self, false) if class_def.body
|
152
|
+
@class.stop
|
153
|
+
end
|
154
|
+
end
|
155
|
+
|
156
|
+
def declare_argument(name, type)
|
157
|
+
# declare local vars for arguments here
|
158
|
+
end
|
159
|
+
|
160
|
+
def body(body, expression)
|
161
|
+
# all except the last element in a body of code is treated as a statement
|
162
|
+
i, last = 0, body.children.size - 1
|
163
|
+
while i < last
|
164
|
+
body.children[i].compile(self, false)
|
165
|
+
i += 1
|
166
|
+
end
|
167
|
+
yield body.children[last] if last >= 0
|
168
|
+
end
|
169
|
+
|
170
|
+
def scoped_body(scope, expression)
|
171
|
+
body(scope, expression)
|
172
|
+
end
|
173
|
+
|
174
|
+
def scoped_local_name(name, scope=nil)
|
175
|
+
if scope.nil? || scope == @current_scope
|
176
|
+
name
|
177
|
+
else
|
178
|
+
"#{name}$#{scope.object_id}"
|
179
|
+
end
|
180
|
+
end
|
181
|
+
|
182
|
+
def import(short, long)
|
183
|
+
end
|
184
|
+
|
185
|
+
def get_binding(type)
|
186
|
+
@bindings[type]
|
187
|
+
end
|
188
|
+
|
189
|
+
def declared_captures(binding=nil)
|
190
|
+
@captured_locals[binding || @binding]
|
191
|
+
end
|
192
|
+
|
193
|
+
def with(vars)
|
194
|
+
orig_values = {}
|
195
|
+
begin
|
196
|
+
vars.each do |name, new_value|
|
197
|
+
name = "@#{name}"
|
198
|
+
orig_values[name] = instance_variable_get name
|
199
|
+
instance_variable_set name, new_value
|
200
|
+
end
|
201
|
+
yield
|
202
|
+
ensure
|
203
|
+
orig_values.each do |name, value|
|
204
|
+
instance_variable_set name, value
|
205
|
+
end
|
206
|
+
end
|
207
|
+
end
|
208
|
+
end
|
209
|
+
end
|
210
|
+
end
|