mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
Revert incorrect string-guard optimisation. (#5969)
Also add jhawthorn's test to for this bug. Fix String#to_s invalidation test
This commit is contained in:
parent
1177665e62
commit
9d18661e1d
Notes:
git
2022-06-01 23:22:37 +09:00
Merged-By: maximecb <maximecb@ruby-lang.org>
2 changed files with 31 additions and 27 deletions
|
@ -1339,12 +1339,42 @@ assert_equal 'foo123', %q{
|
|||
|
||||
# test that invalidation of String#to_s doesn't crash
|
||||
assert_equal 'meh', %q{
|
||||
def inval_method
|
||||
"".to_s
|
||||
end
|
||||
|
||||
inval_method
|
||||
|
||||
class String
|
||||
def to_s
|
||||
"meh"
|
||||
end
|
||||
end
|
||||
"".to_s
|
||||
|
||||
inval_method
|
||||
}
|
||||
|
||||
# test that overriding to_s on a String subclass isn't over-optimised
|
||||
assert_equal 'meh', %q{
|
||||
class MyString < String
|
||||
def to_s
|
||||
"meh"
|
||||
end
|
||||
end
|
||||
|
||||
def test_to_s(obj)
|
||||
obj.to_s
|
||||
end
|
||||
|
||||
OBJ = MyString.new
|
||||
|
||||
# Should return 'meh' both times
|
||||
test_to_s("")
|
||||
test_to_s("")
|
||||
|
||||
# Can return '' if YJIT optimises String#to_s too aggressively
|
||||
test_to_s(OBJ)
|
||||
test_to_s(OBJ)
|
||||
}
|
||||
|
||||
# test string interpolation with overridden to_s
|
||||
|
|
|
@ -3421,32 +3421,6 @@ fn jit_guard_known_klass(
|
|||
jit_chain_guard(JCC_JNE, jit, ctx, cb, ocb, max_chain_depth, side_exit);
|
||||
ctx.upgrade_opnd_type(insn_opnd, Type::Flonum);
|
||||
}
|
||||
} else if unsafe { known_klass == rb_cString } && sample_instance.string_p() {
|
||||
assert!(!val_type.is_imm());
|
||||
if val_type != Type::String {
|
||||
assert!(val_type.is_unknown());
|
||||
|
||||
// Need the check for immediate, because trying to look up the klass field of an immediate will segfault
|
||||
if !val_type.is_heap() {
|
||||
add_comment(cb, "guard not immediate (for string)");
|
||||
assert!(Qfalse.as_i32() < Qnil.as_i32());
|
||||
test(cb, REG0, imm_opnd(RUBY_IMMEDIATE_MASK as i64));
|
||||
jit_chain_guard(JCC_JNZ, jit, ctx, cb, ocb, max_chain_depth, side_exit);
|
||||
cmp(cb, REG0, imm_opnd(Qnil.into()));
|
||||
jit_chain_guard(JCC_JBE, jit, ctx, cb, ocb, max_chain_depth, side_exit);
|
||||
}
|
||||
|
||||
add_comment(cb, "guard object is string");
|
||||
let klass_opnd = mem_opnd(64, REG0, RUBY_OFFSET_RBASIC_KLASS);
|
||||
mov(cb, REG1, uimm_opnd(unsafe { rb_cString }.into()));
|
||||
cmp(cb, klass_opnd, REG1);
|
||||
jit_chain_guard(JCC_JNE, jit, ctx, cb, ocb, max_chain_depth, side_exit);
|
||||
|
||||
// Upgrading here causes an error with invalidation writing past end of block
|
||||
ctx.upgrade_opnd_type(insn_opnd, Type::String);
|
||||
} else {
|
||||
add_comment(cb, "skip guard - known to be a string");
|
||||
}
|
||||
} else if unsafe {
|
||||
FL_TEST(known_klass, VALUE(RUBY_FL_SINGLETON)) != VALUE(0)
|
||||
&& sample_instance == rb_attr_get(known_klass, id__attached__ as ID)
|
||||
|
|
Loading…
Add table
Reference in a new issue