diff options
author | Takashi Kokubun <[email protected]> | 2023-02-21 00:19:37 -0800 |
---|---|---|
committer | Takashi Kokubun <[email protected]> | 2023-03-05 23:28:59 -0800 |
commit | 8d29b0635bd87cb8e0521cb0ffdc617382e3cccb (patch) | |
tree | e1d677401447a0e030cf51a0e822b6bfbe369bda | |
parent | 32e6f15bebf120635d575986fdded1a3943395d0 (diff) |
Implement putstring
Notes
Notes:
Merged: https://github.com/ruby/ruby/pull/7448
-rw-r--r-- | lib/ruby_vm/mjit/exit_compiler.rb | 6 | ||||
-rw-r--r-- | lib/ruby_vm/mjit/insn_compiler.rb | 28 | ||||
-rw-r--r-- | lib/ruby_vm/mjit/invariants.rb | 3 | ||||
-rw-r--r-- | lib/ruby_vm/mjit/jit_state.rb | 8 | ||||
-rw-r--r-- | mjit_c.rb | 4 |
5 files changed, 37 insertions, 12 deletions
diff --git a/lib/ruby_vm/mjit/exit_compiler.rb b/lib/ruby_vm/mjit/exit_compiler.rb index bf85a340d7..742d8b6376 100644 --- a/lib/ruby_vm/mjit/exit_compiler.rb +++ b/lib/ruby_vm/mjit/exit_compiler.rb @@ -1,9 +1,5 @@ module RubyVM::MJIT class ExitCompiler - def initialize - @gc_refs = [] # TODO: GC offsets? - end - # Used for invalidating a block on entry. # @param pc [Integer] # @param asm [RubyVM::MJIT::Assembler] @@ -133,7 +129,7 @@ module RubyVM::MJIT end def to_value(obj) - @gc_refs << obj + GC_REFS << obj C.to_value(obj) end diff --git a/lib/ruby_vm/mjit/insn_compiler.rb b/lib/ruby_vm/mjit/insn_compiler.rb index 0ed0924519..e718f267d6 100644 --- a/lib/ruby_vm/mjit/insn_compiler.rb +++ b/lib/ruby_vm/mjit/insn_compiler.rb @@ -5,7 +5,6 @@ module RubyVM::MJIT def initialize(cb, ocb, exit_compiler) @ocb = ocb @exit_compiler = exit_compiler - @gc_refs = [] # TODO: GC offsets? @full_cfunc_return = Assembler.new.then do |asm| @exit_compiler.compile_full_cfunc_return(asm) @@ -23,7 +22,7 @@ module RubyVM::MJIT asm.incr_counter(:mjit_insns_count) asm.comment("Insn: #{insn.name}") - # 55/101 + # 56/101 case insn.name when :nop then nop(jit, ctx, asm) when :getlocal then getlocal(jit, ctx, asm) @@ -46,7 +45,7 @@ module RubyVM::MJIT when :putself then putself(jit, ctx, asm) when :putobject then putobject(jit, ctx, asm) # putspecialobject - # putstring + when :putstring then putstring(jit, ctx, asm) # concatstrings # anytostring # toregexp @@ -299,7 +298,26 @@ module RubyVM::MJIT end # putspecialobject - # putstring + + # @param jit [RubyVM::MJIT::JITState] + # @param ctx [RubyVM::MJIT::Context] + # @param asm [RubyVM::MJIT::Assembler] + def putstring(jit, ctx, asm) + put_val = jit.operand(0, ruby: true) + + # Save the PC and SP because the callee will allocate + jit_prepare_routine_call(jit, ctx, asm) + + asm.mov(C_ARGS[0], EC) + asm.mov(C_ARGS[1], to_value(put_val)) + asm.call(C.rb_ec_str_resurrect) + + stack_top = ctx.stack_push + asm.mov(stack_top, C_RET) + + KeepCompiling + end + # concatstrings # anytostring # toregexp @@ -2508,7 +2526,7 @@ module RubyVM::MJIT end def to_value(obj) - @gc_refs << obj + GC_REFS << obj C.to_value(obj) end end diff --git a/lib/ruby_vm/mjit/invariants.rb b/lib/ruby_vm/mjit/invariants.rb index 21f70d00a2..648044f027 100644 --- a/lib/ruby_vm/mjit/invariants.rb +++ b/lib/ruby_vm/mjit/invariants.rb @@ -82,6 +82,9 @@ module RubyVM::MJIT end def on_update_references + # Give up. In order to support GC.compact, you'd have to update ISEQ + # addresses in BranchStub, etc. Ideally, we'd need to update moved + # pointers in JITed code here, but we just invalidate all for now. invalidate_all end diff --git a/lib/ruby_vm/mjit/jit_state.rb b/lib/ruby_vm/mjit/jit_state.rb index 3e5fe996fa..aec4e51c48 100644 --- a/lib/ruby_vm/mjit/jit_state.rb +++ b/lib/ruby_vm/mjit/jit_state.rb @@ -13,9 +13,13 @@ module RubyVM::MJIT Compiler.decode_insn(C.VALUE.new(pc).*) end - def operand(index, signed: false) + def operand(index, signed: false, ruby: false) addr = pc + (index + 1) * Fiddle::SIZEOF_VOIDP - Fiddle::Pointer.new(addr)[0, Fiddle::SIZEOF_VOIDP].unpack(signed ? 'q' : 'Q')[0] + value = Fiddle::Pointer.new(addr)[0, Fiddle::SIZEOF_VOIDP].unpack(signed ? 'q' : 'Q')[0] + if ruby + value = C.to_ruby(value) + end + value end def at_current_insn? @@ -199,6 +199,10 @@ module RubyVM::MJIT # :nodoc: all } end + def rb_ec_str_resurrect + Primitive.cexpr! 'SIZET2NUM((size_t)rb_ec_str_resurrect)' + end + #======================================================================================== # # Old stuff |