Skip to content

Commit

Permalink
YJIT: Fix false object collection when setting ivar
Browse files Browse the repository at this point in the history
Previously, setinstancevariable could generate code that calls
`rb_ensure_iv_list_size()` without first updating `cfp->sp`. This means
in the event that a GC start from within said routine the top few
objects would not be marked, causing them to be falsly collected.

Call `jit_prepare_routine_call()` first.

[Bug #19601]
  • Loading branch information
XrXr committed Apr 14, 2023
1 parent 6c1b604 commit 294adde
Show file tree
Hide file tree
Showing 2 changed files with 29 additions and 0 deletions.
24 changes: 24 additions & 0 deletions bootstraptest/test_yjit.rb
Original file line number Diff line number Diff line change
@@ -1,3 +1,27 @@
# Regression test for GC mishap while doing shape transition
assert_equal '[:ok]', %q{
# [Bug #19601]
class RegressionTest
def initialize
@a = @b = @fourth_ivar_does_shape_transition = nil
end
def extender
@first_extended_ivar = [:ok]
end
end
test = RegressionTest.new
# Fill up transient heap (32 MiB), so rb_ensure_iv_list_size()
# listens to GC.stress and yields to the GC.
fill = Array.new(0x400000)
GC.stress = true
# Used to crash due to GC run in rb_ensure_iv_list_size()
# not marking the newly allocated [:ok].
test.extender.itself
}

assert_equal 'true', %q{
# regression test for tracking type of locals for too long
def local_setting_cmp(five)
Expand Down
5 changes: 5 additions & 0 deletions yjit/src/codegen.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2342,6 +2342,11 @@ fn gen_setinstancevariable(
if needs_extension {
// Generate the C call so that runtime code will increase
// the capacity and set the buffer.
asm.comment("call rb_ensure_iv_list_size");

// It allocates so can trigger GC, which takes the VM lock
// so could yield to a different ractor.
jit_prepare_routine_call(jit, asm);
asm.spill_temps(); // for ccall
asm.ccall(rb_ensure_iv_list_size as *const u8,
vec![
Expand Down

0 comments on commit 294adde

Please sign in to comment.