ytljit 0.0.3 → 0.0.4

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.
@@ -43,6 +43,15 @@ module YTLJit
43
43
  attr :local_label_tab
44
44
 
45
45
  attr_accessor :not_reached_pos
46
+
47
+ def import_object(klass, name, value)
48
+ ctn = ClassTopNode.get_class_top_node(klass)
49
+ if ctn == nil then
50
+ ctn = ClassTopNode.new(@the_top, klass, klass.name)
51
+ end
52
+ valnode = LiteralNode.new(ctn, value)
53
+ ctn.get_constant_tab[name] = valnode
54
+ end
46
55
  end
47
56
 
48
57
  class YARVTranslatorBase
@@ -164,16 +173,30 @@ module YTLJit
164
173
 
165
174
  def visit_getdynamic(code, ins, context)
166
175
  # + 3 mean prtv_env/pointer to block function/self
167
- offset = code.header['misc'][:local_size] + 3 - ins[1]
168
- node = LocalVarRefNode.new(context.current_node, offset, ins[2])
176
+ dep = ins[2]
177
+ curcode = code
178
+ dep.times do
179
+ curcode = curcode.parent
180
+ end
181
+ offset = curcode.header['misc'][:local_size] + 3 - ins[1]
182
+ node = LocalVarRefNode.new(context.current_node, offset, dep)
169
183
  context.expstack.push node
170
184
  end
171
185
 
172
186
  def visit_setdynamic(code, ins, context)
187
+ dep = ins[2]
188
+ curcode = code
189
+ dep.times do
190
+ curcode = curcode.parent
191
+ end
173
192
  val = context.expstack.pop
174
193
  curnode = context.current_node
175
- offset = code.header['misc'][:local_size] + 3 - ins[1]
176
- node = LocalAssignNode.new(curnode, offset, ins[2], val)
194
+ offset = curcode.header['misc'][:local_size] + 3 - ins[1]
195
+ node = LocalAssignNode.new(curnode, offset, dep, val)
196
+ if context.expstack[-1] == val then
197
+ varref = LocalVarRefNode.new(context.current_node, offset, dep)
198
+ context.expstack[-1] = varref
199
+ end
177
200
  curnode.body = node
178
201
  context.current_node = node
179
202
  end
@@ -188,23 +211,35 @@ module YTLJit
188
211
 
189
212
  # getclassvariable
190
213
  # setclassvariable
191
-
192
- def visit_getconstant(code, ins, context)
214
+
215
+ def get_self_object(context)
193
216
  klass = context.expstack.pop
194
217
  case klass
195
218
  when ConstantRefNode
196
219
  klass = klass.value_node
197
220
 
198
-
199
221
  when LiteralNode
200
222
  klass = klass.value
201
223
  if klass == nil then
202
224
  klass = context.current_class_node
203
225
  end
204
226
 
227
+ when SpecialObjectNode
228
+ if klass.kind == 3 then
229
+ klass = context.current_class_node
230
+ else
231
+ raise "Unkown special object kind = #{klass.kind}"
232
+ end
233
+
205
234
  else
206
235
  raise "Umkonwn node #{klass.class}"
207
236
  end
237
+
238
+ klass
239
+ end
240
+
241
+ def visit_getconstant(code, ins, context)
242
+ klass = get_self_object(context)
208
243
  name = ins[1]
209
244
  curnode = context.current_node
210
245
  node = ConstantRefNode.new(curnode, klass, name)
@@ -212,6 +247,13 @@ module YTLJit
212
247
  end
213
248
 
214
249
  def visit_setconstant(code, ins, context)
250
+ klass = get_self_object(context)
251
+ value = context.expstack.pop
252
+ name = ins[1]
253
+ curnode = context.current_node
254
+ node = ConstantAssignNode.new(curnode, klass, name, value)
255
+ curnode.body = node
256
+ context.current_node = node
215
257
  end
216
258
 
217
259
  # getglobal
@@ -246,9 +288,9 @@ module YTLJit
246
288
  when :block
247
289
  mtopnode = BlockTopNode.new(curnode)
248
290
  when :method
249
- mtopnode = MethodTopNode.new(curnode)
291
+ mtopnode = MethodTopNode.new(curnode, body.header['name'].to_sym)
250
292
  when :class
251
- mtopnode = ClassTopNode.new(curnode)
293
+ mtopnode = ClassTopNode.new(curnode, body.header['name'].to_sym)
252
294
  when :top
253
295
  raise "Maybe bug not appear top block."
254
296
  end
@@ -289,10 +331,17 @@ module YTLJit
289
331
 
290
332
  def visit_pop(code, ins, context)
291
333
  node = context.expstack.pop
334
+ if node == nil then
335
+ # Maybe push instruction deleted by optimize
336
+ node = LiteralNode.new(nil, nil)
337
+ end
338
+
292
339
  curnode = context.current_node
293
340
  node.parent = curnode
294
341
  curnode.body = node
295
- context.current_node = node
342
+ if node.is_a?(HaveChildlenMixin) then
343
+ context.current_node = node
344
+ end
296
345
 
297
346
  context
298
347
  end
@@ -370,6 +419,7 @@ module YTLJit
370
419
  end
371
420
  RubyType::define_wraped_class(klassobj, RubyType::RubyTypeBoxed)
372
421
  cnode = ClassTopNode.new(context.current_class_node, klassobj, name)
422
+ context.current_class_node.constant_tab[name] = cnode
373
423
 
374
424
  body = VMLib::InstSeqTree.new(code, ins[2])
375
425
  ncontext = YARVContext.new
@@ -381,7 +431,6 @@ module YTLJit
381
431
  tr = self.class.new([body])
382
432
  tr.translate(ncontext)
383
433
 
384
- context.current_class_node.constant_tab[name] = cnode
385
434
  curnode = context.current_node
386
435
  cvnode = ClassValueNode.new(curnode, cnode)
387
436
  context.expstack.push cvnode
@@ -393,6 +442,7 @@ module YTLJit
393
442
  blk_iseq = ins[3]
394
443
  curnode = context.current_node
395
444
  numarg = ins[2]
445
+ seqno = ins[5]
396
446
 
397
447
  # regular arguments
398
448
  arg = []
@@ -409,7 +459,7 @@ module YTLJit
409
459
  body = VMLib::InstSeqTree.new(code, blk_iseq)
410
460
  ncontext = YARVContext.new
411
461
  ncontext.current_file_name = context.current_file_name
412
- ncontext.current_class_node = curnode
462
+ ncontext.current_class_node = context.current_class_node
413
463
  btn = ncontext.current_node = BlockTopNode.new(curnode)
414
464
  ncontext.top_nodes.push btn
415
465
 
@@ -427,7 +477,7 @@ module YTLJit
427
477
 
428
478
  func = MethodSelectNode.new(curnode, ins[1])
429
479
  op_flag = ins[4]
430
- sn = SendNode.make_send_node(curnode, func, arg, op_flag)
480
+ sn = SendNode.make_send_node(curnode, func, arg, op_flag, seqno)
431
481
  func.set_reciever(sn)
432
482
  context.expstack.push sn
433
483
 
@@ -442,6 +492,7 @@ module YTLJit
442
492
  func = YieldNode.new(curnode)
443
493
  numarg = ins[1]
444
494
  op_flag = ins[2]
495
+ seqno = ins[3]
445
496
 
446
497
  # regular arguments
447
498
  args = []
@@ -455,17 +506,17 @@ module YTLJit
455
506
  framelayout = frameinfo.frame_layout
456
507
 
457
508
  # self
458
- args.push framelayout[roff + 2]
509
+ args.push LiteralNode.new(curnode, nil)
459
510
 
460
511
  # block
461
- args.push framelayout[roff + 1]
512
+ args.push LiteralNode.new(curnode, nil)
462
513
 
463
514
  # perv env
464
- args.push framelayout[roff]
515
+ args.push LiteralNode.new(curnode, nil)
465
516
 
466
517
  args = args.reverse
467
518
 
468
- nnode = SendNode.new(curnode, func, args, op_flag)
519
+ nnode = SendNode.new(curnode, func, args, op_flag, seqno)
469
520
  func.parent = nnode
470
521
  context.expstack.push nnode
471
522
 
@@ -473,9 +524,17 @@ module YTLJit
473
524
  end
474
525
 
475
526
  def visit_leave(code, ins, context)
476
- curnode = context.current_node
527
+ curnode = nil
528
+ vnode = nil
529
+ if context.top_nodes.last.name == :initialize then
530
+ visit_pop(code, ins, context)
531
+ curnode = context.current_node
532
+ vnode = SelfRefNode.new(curnode)
533
+ else
534
+ curnode = context.current_node
535
+ vnode = context.expstack.pop
536
+ end
477
537
 
478
- vnode = context.expstack.pop
479
538
  srnode = SetResultNode.new(curnode, vnode)
480
539
  curnode.body = srnode
481
540
 
@@ -504,6 +563,7 @@ module YTLJit
504
563
  nllab = get_vmnode_from_label(context, ins[1])
505
564
 
506
565
  jpnode = JumpNode.new(curnode, nllab)
566
+ jpnode.body = nllab
507
567
 
508
568
  val = context.expstack.pop
509
569
  nllab.come_from[jpnode] = val
@@ -1,13 +1,12 @@
1
1
  module YTLJit
2
2
  module TypeUtil
3
3
  class KlassTree
4
- def initialize(defkey = [], defval = [])
4
+ def initialize(defkey = [], defval = [[], []])
5
5
  @node = KlassTreeNode.new(defkey, defval)
6
6
  end
7
7
 
8
8
  def add(key, value)
9
9
  cnode = @node
10
- snode = @node
11
10
  ocnode = nil
12
11
  while cnode
13
12
  ocnode = cnode
@@ -15,13 +14,11 @@ module YTLJit
15
14
  return cnode
16
15
  end
17
16
 
18
- if key.zip(cnode.key).all? {|k, n| k.is_a?(n.class)} then
17
+ if key.zip(cnode.key).all? {|k, n| k.is_a?(n.class)} and false then
19
18
  cnode = cnode.same_klass
20
19
  if cnode == nil then
21
20
  ocnode.same_klass = KlassTreeNode.new(key, value)
22
21
  return ocnode.same_klass
23
- else
24
- snode = cnode
25
22
  end
26
23
  else
27
24
  cnode = cnode.next_klass
@@ -35,13 +32,13 @@ module YTLJit
35
32
 
36
33
  def search(key)
37
34
  cnode = @node
38
-
35
+
39
36
  while cnode
40
37
  if key == cnode.key then
41
38
  return cnode
42
39
  end
43
40
 
44
- if key.zip(cnode.key).all? {|a, b|
41
+ if key.zip(cnode.key).all? {|a, b|
45
42
  if a then
46
43
  atype = a.ruby_type
47
44
 
@@ -52,9 +49,10 @@ module YTLJit
52
49
  nil
53
50
  end
54
51
  else
52
+ raise "foo"
55
53
  return !b
56
54
  end
57
- } then
55
+ } and false then
58
56
  cnode = cnode.same_klass
59
57
  else
60
58
  cnode = cnode.next_klass
@@ -77,7 +75,7 @@ module YTLJit
77
75
  attr_accessor :same_klass
78
76
  attr_accessor :next_klass
79
77
  attr :key
80
- attr_accessor :value
78
+ attr :value
81
79
  end
82
80
 
83
81
  class TypeContainer
@@ -93,16 +91,16 @@ module YTLJit
93
91
  @types_tree.search(key)
94
92
  end
95
93
 
96
- def add_type(key, type)
94
+ def add_type(key, type, pos)
97
95
  tvs = @types_tree.search(key)
98
96
  if tvs then
99
- tvsv = tvs.value
97
+ tvsv = tvs.value[pos]
100
98
  if !tvsv.include? type then
101
99
  tvsv.push type
102
100
  end
103
101
  else
104
102
  # inherit types of most similar signature
105
- ival = []
103
+ ival = [[], []]
106
104
  simnode = @types_tree.add(key, ival)
107
105
  =begin
108
106
  simnode.value.each do |ele|
@@ -111,14 +109,14 @@ module YTLJit
111
109
  =end
112
110
 
113
111
  if !ival.include? type then
114
- ival.push type
112
+ ival[pos].push type
115
113
  end
116
114
  end
117
115
  end
118
116
 
119
117
  def add_node(key)
120
118
  # inherit types of most similar signature
121
- ival = []
119
+ ival = [[], []]
122
120
  simnode = @types_tree.add(key, ival)
123
121
  =begin
124
122
  simnode.value.each do |ele|
@@ -134,7 +132,7 @@ module YTLJit
134
132
  if res == nil then
135
133
  res = add_node(key)
136
134
  end
137
-
135
+
138
136
  res
139
137
  end
140
138
  end
@@ -173,6 +171,11 @@ module YTLJit
173
171
  end
174
172
 
175
173
  def self.related_ruby_class(klass, base)
174
+ if @@base_type_tab[klass] then
175
+ return [@@base_type_tab[klass],
176
+ @@boxed_type_tab[klass],
177
+ @@unboxed_type_tab[klass]]
178
+ end
176
179
  baseslf = base.new(klass)
177
180
  boxslf = RubyTypeBoxed.new(klass)
178
181
  unboxslf = RubyTypeUnboxed.new(klass)
@@ -205,7 +208,7 @@ module YTLJit
205
208
  @@boxed_type_tab[klass] = boxslf
206
209
  @@unboxed_type_tab[klass] = unboxslf
207
210
 
208
- [boxslf, unboxslf]
211
+ [baseslf, boxslf, unboxslf]
209
212
  end
210
213
 
211
214
  def self.from_object(obj)
@@ -215,7 +218,9 @@ module YTLJit
215
218
  def self.from_ruby_class(rcls)
216
219
  tobj = @@base_type_tab[rcls]
217
220
  if tobj == nil then
218
- DefaultType0.new
221
+ RubyType::define_wraped_class(rcls, RubyTypeBoxed)
222
+ tobj = @@base_type_tab[rcls]
223
+ tobj.instance
219
224
  else
220
225
  tobj.instance
221
226
  end
@@ -242,11 +247,11 @@ module YTLJit
242
247
  end
243
248
 
244
249
  def to_unbox
245
- self
250
+ @@unboxed_type_tab[@ruby_type].instance
246
251
  end
247
252
 
248
253
  def to_box
249
- self
254
+ @@boxed_type_tab[@ruby_type].instance
250
255
  end
251
256
 
252
257
  def ==(other)
@@ -304,5 +309,6 @@ module YTLJit
304
309
  define_wraped_class(Hash, RubyTypeBoxed)
305
310
  define_wraped_class(Module, RubyTypeBoxed)
306
311
  define_wraped_class(Class, RubyTypeBoxed)
312
+ define_wraped_class(Object, RubyTypeBoxed)
307
313
  end
308
314
  end
@@ -86,7 +86,13 @@ module YTLJit
86
86
  end
87
87
 
88
88
  def gen_unboxing(context)
89
- p "inboxing"
89
+ asm = context.assembler
90
+ fobj = TypedData.new(InternalRubyType::RFloat, context.ret_reg)
91
+ asm.with_retry do
92
+ asm.movsd(XMM0, fobj[:float_value])
93
+ end
94
+
95
+ context.ret_reg = XMM0
90
96
  context
91
97
  end
92
98
  end
@@ -98,6 +104,8 @@ module YTLJit
98
104
  asm = context.assembler
99
105
  val = context.ret_reg
100
106
  vnode = context.ret_node
107
+ context.start_using_reg(TMPR2)
108
+ context.start_using_reg(TMPR3)
101
109
  context.start_using_reg(FUNC_FLOAT_ARG[0])
102
110
  rbfloatnew = OpMemAddress.new(address_of("rb_float_new"))
103
111
  asm.with_retry do
@@ -105,6 +113,8 @@ module YTLJit
105
113
  asm.call_with_arg(rbfloatnew, 1)
106
114
  end
107
115
  context.end_using_reg(FUNC_FLOAT_ARG[0])
116
+ context.end_using_reg(TMPR3)
117
+ context.end_using_reg(TMPR2)
108
118
  context.ret_reg = RETR
109
119
  context
110
120
  end
@@ -135,7 +145,21 @@ module YTLJit
135
145
  end
136
146
 
137
147
  def gen_copy(context)
138
- p "copy"
148
+ asm = context.assembler
149
+ val = context.ret_reg
150
+ context.start_using_reg(TMPR2)
151
+ context.start_using_reg(TMPR3)
152
+ context.start_using_reg(FUNC_ARG[0])
153
+ rbarydup = OpMemAddress.new(address_of("rb_ary_dup"))
154
+ asm.with_retry do
155
+ asm.mov(FUNC_ARG[0], val)
156
+ asm.call_with_arg(rbarydup, 1)
157
+ end
158
+ context.end_using_reg(FUNC_ARG[0])
159
+ context.end_using_reg(TMPR3)
160
+ context.end_using_reg(TMPR2)
161
+ context.ret_reg = RETR
162
+
139
163
  context
140
164
  end
141
165
 
@@ -144,6 +168,35 @@ module YTLJit
144
168
  self.class == other.class and
145
169
  @element_type == other.element_type
146
170
  end
171
+
172
+ def eql?(other)
173
+ other.is_a?(self.class) and
174
+ self.class == other.class and
175
+ @element_type == other.element_type
176
+ end
177
+ end
178
+
179
+ module StringTypeBoxedCodeGen
180
+ include AbsArch
181
+
182
+ def gen_copy(context)
183
+ asm = context.assembler
184
+ val = context.ret_reg
185
+ context.start_using_reg(TMPR2)
186
+ context.start_using_reg(TMPR3)
187
+ context.start_using_reg(FUNC_ARG[0])
188
+ rbstrresurrect = OpMemAddress.new(address_of("rb_str_resurrect"))
189
+ asm.with_retry do
190
+ asm.mov(FUNC_ARG[0], val)
191
+ asm.call_with_arg(rbstrresurrect, 1)
192
+ end
193
+ context.end_using_reg(FUNC_ARG[0])
194
+ context.end_using_reg(TMPR3)
195
+ context.end_using_reg(TMPR2)
196
+ context.ret_reg = RETR
197
+
198
+ context
199
+ end
147
200
  end
148
201
 
149
202
  module ArrayTypeUnboxedCodeGen