summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authornozomemein <b8yukifsukeo999n@gmail.com>2026-01-09 09:56:11 +0900
committerTakashi Kokubun <takashikkbn@gmail.com>2026-01-15 09:00:53 -0800
commit065db7cf61cfb69d869f4b403b49b1efc314eead (patch)
tree0194a4b4e1375b6bd7076b58944441b376d852f5
parent11edc286d837f66b37433e7d51c8b8f500e1be84 (diff)
ZJIT: Rename ArrayArefFixnum -> ArrayAref
-rw-r--r--zjit/src/codegen.rs7
-rw-r--r--zjit/src/cruby_methods.rs3
-rw-r--r--zjit/src/hir.rs23
-rw-r--r--zjit/src/hir/opt_tests.rs45
-rw-r--r--zjit/src/hir/tests.rs8
-rw-r--r--zjit/src/hir_type/mod.rs11
6 files changed, 60 insertions, 37 deletions
diff --git a/zjit/src/codegen.rs b/zjit/src/codegen.rs
index 16ac2573f2..25cccd1bd1 100644
--- a/zjit/src/codegen.rs
+++ b/zjit/src/codegen.rs
@@ -374,7 +374,7 @@ fn gen_insn(cb: &mut CodeBlock, jit: &mut JITState, asm: &mut Assembler, functio
Insn::NewRange { low, high, flag, state } => gen_new_range(jit, asm, opnd!(low), opnd!(high), *flag, &function.frame_state(*state)),
Insn::NewRangeFixnum { low, high, flag, state } => gen_new_range_fixnum(asm, opnd!(low), opnd!(high), *flag, &function.frame_state(*state)),
Insn::ArrayDup { val, state } => gen_array_dup(asm, opnd!(val), &function.frame_state(*state)),
- Insn::ArrayArefFixnum { array, index, .. } => gen_aref_fixnum(asm, opnd!(array), opnd!(index)),
+ Insn::ArrayAref { array, index, .. } => gen_array_aref(asm, opnd!(array), opnd!(index)),
Insn::ArrayAset { array, index, val } => {
no_output!(gen_array_aset(asm, opnd!(array), opnd!(index), opnd!(val)))
}
@@ -1560,13 +1560,12 @@ fn gen_new_array(
}
/// Compile array access (`array[index]`)
-fn gen_aref_fixnum(
+fn gen_array_aref(
asm: &mut Assembler,
array: Opnd,
index: Opnd,
) -> lir::Opnd {
- let unboxed_idx = asm.rshift(index, Opnd::UImm(1));
- asm_ccall!(asm, rb_ary_entry, array, unboxed_idx)
+ asm_ccall!(asm, rb_ary_entry, array, index)
}
fn gen_array_aset(
diff --git a/zjit/src/cruby_methods.rs b/zjit/src/cruby_methods.rs
index 40b9d13854..5f89a5f20e 100644
--- a/zjit/src/cruby_methods.rs
+++ b/zjit/src/cruby_methods.rs
@@ -326,7 +326,8 @@ fn inline_array_aref(fun: &mut hir::Function, block: hir::BlockId, recv: hir::In
if let &[index] = args {
if fun.likely_a(index, types::Fixnum, state) {
let index = fun.coerce_to(block, index, types::Fixnum, state);
- let result = fun.push_insn(block, hir::Insn::ArrayArefFixnum { array: recv, index });
+ let index = fun.push_insn(block, hir::Insn::UnboxFixnum { val: index });
+ let result = fun.push_insn(block, hir::Insn::ArrayAref { array: recv, index });
return Some(result);
}
}
diff --git a/zjit/src/hir.rs b/zjit/src/hir.rs
index 48f85c4f23..4a81ce641c 100644
--- a/zjit/src/hir.rs
+++ b/zjit/src/hir.rs
@@ -759,7 +759,7 @@ pub enum Insn {
ArrayExtend { left: InsnId, right: InsnId, state: InsnId },
/// Push `val` onto `array`, where `array` is already `Array`.
ArrayPush { array: InsnId, val: InsnId, state: InsnId },
- ArrayArefFixnum { array: InsnId, index: InsnId },
+ ArrayAref { array: InsnId, index: InsnId },
ArrayAset { array: InsnId, index: InsnId, val: InsnId },
ArrayPop { array: InsnId, state: InsnId },
/// Return the length of the array as a C `long` ([`types::CInt64`])
@@ -1163,8 +1163,8 @@ impl<'a> std::fmt::Display for InsnPrinter<'a> {
}
Ok(())
}
- Insn::ArrayArefFixnum { array, index, .. } => {
- write!(f, "ArrayArefFixnum {array}, {index}")
+ Insn::ArrayAref { array, index, .. } => {
+ write!(f, "ArrayAref {array}, {index}")
}
Insn::ArrayAset { array, index, val, ..} => {
write!(f, "ArrayAset {array}, {index}, {val}")
@@ -2150,7 +2150,7 @@ impl Function {
&NewHash { ref elements, state } => NewHash { elements: find_vec!(elements), state: find!(state) },
&NewRange { low, high, flag, state } => NewRange { low: find!(low), high: find!(high), flag, state: find!(state) },
&NewRangeFixnum { low, high, flag, state } => NewRangeFixnum { low: find!(low), high: find!(high), flag, state: find!(state) },
- &ArrayArefFixnum { array, index } => ArrayArefFixnum { array: find!(array), index: find!(index) },
+ &ArrayAref { array, index } => ArrayAref { array: find!(array), index: find!(index) },
&ArrayAset { array, index, val } => ArrayAset { array: find!(array), index: find!(index), val: find!(val) },
&ArrayPop { array, state } => ArrayPop { array: find!(array), state: find!(state) },
&ArrayLength { array } => ArrayLength { array: find!(array) },
@@ -2263,7 +2263,7 @@ impl Function {
Insn::ToRegexp { .. } => types::RegexpExact,
Insn::NewArray { .. } => types::ArrayExact,
Insn::ArrayDup { .. } => types::ArrayExact,
- Insn::ArrayArefFixnum { .. } => types::BasicObject,
+ Insn::ArrayAref { .. } => types::BasicObject,
Insn::ArrayPop { .. } => types::BasicObject,
Insn::ArrayLength { .. } => types::CInt64,
Insn::HashAref { .. } => types::BasicObject,
@@ -4073,11 +4073,11 @@ impl Function {
_ => None,
})
}
- Insn::ArrayArefFixnum { array, index } if self.type_of(array).ruby_object_known()
+ Insn::ArrayAref { array, index } if self.type_of(array).ruby_object_known()
&& self.type_of(index).ruby_object_known() => {
let array_obj = self.type_of(array).ruby_object().unwrap();
if array_obj.is_frozen() {
- let index = self.type_of(index).fixnum_value().unwrap();
+ let index = self.type_of(index).cint64_value().unwrap();
let val = unsafe { rb_yarv_ary_entry_internal(array_obj, index) };
self.new_insn(Insn::Const { val: Const::Value(val) })
} else {
@@ -4271,7 +4271,7 @@ impl Function {
worklist.push_back(val);
worklist.push_back(state);
}
- &Insn::ArrayArefFixnum { array, index } => {
+ &Insn::ArrayAref { array, index } => {
worklist.push_back(array);
worklist.push_back(index);
}
@@ -4995,9 +4995,9 @@ impl Function {
| Insn::ArrayLength { array, .. } => {
self.assert_subtype(insn_id, array, types::Array)
}
- Insn::ArrayArefFixnum { array, index } => {
+ Insn::ArrayAref { array, index } => {
self.assert_subtype(insn_id, array, types::Array)?;
- self.assert_subtype(insn_id, index, types::Fixnum)
+ self.assert_subtype(insn_id, index, types::CInt64)
}
Insn::ArrayAset { array, index, .. } => {
self.assert_subtype(insn_id, array, types::ArrayExact)?;
@@ -6544,7 +6544,8 @@ pub fn iseq_to_hir(iseq: *const rb_iseq_t) -> Result<Function, ParseError> {
// TODO(max): Add a short-cut path for long indices into an array where the
// index is known to be in-bounds
let index = fun.push_insn(block, Insn::Const { val: Const::Value(VALUE::fixnum_from_usize(i.try_into().unwrap())) });
- let element = fun.push_insn(block, Insn::ArrayArefFixnum { array, index });
+ let index = fun.push_insn(block, Insn::UnboxFixnum { val: index });
+ let element = fun.push_insn(block, Insn::ArrayAref { array, index });
state.stack_push(element);
}
}
diff --git a/zjit/src/hir/opt_tests.rs b/zjit/src/hir/opt_tests.rs
index 138bbde718..4086a57833 100644
--- a/zjit/src/hir/opt_tests.rs
+++ b/zjit/src/hir/opt_tests.rs
@@ -1606,10 +1606,11 @@ mod hir_opt_tests {
PatchPoint NoSingletonClass(Array@0x1000)
PatchPoint MethodRedefined(Array@0x1000, []@0x1008, cme:0x1010)
v25:ArrayExact = GuardType v9, ArrayExact
- v26:BasicObject = ArrayArefFixnum v25, v14
+ v26:CInt64 = UnboxFixnum v14
+ v27:BasicObject = ArrayAref v25, v26
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v26
+ Return v27
");
assert_snapshot!(inspect("test [1,2,3]"), @"1");
}
@@ -4734,10 +4735,11 @@ mod hir_opt_tests {
v13:Fixnum[0] = Const Value(0)
PatchPoint NoSingletonClass(Array@0x1010)
PatchPoint MethodRedefined(Array@0x1010, []@0x1018, cme:0x1020)
- v27:BasicObject = ArrayArefFixnum v23, v13
+ v27:CInt64 = UnboxFixnum v13
+ v28:BasicObject = ArrayAref v23, v27
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v27
+ Return v28
");
// TODO(max): Check the result of `S[0] = 5; test` using `inspect` to make sure that we
// actually do the load at run-time.
@@ -4763,10 +4765,11 @@ mod hir_opt_tests {
v13:Fixnum[1] = Const Value(1)
PatchPoint NoSingletonClass(Array@0x1008)
PatchPoint MethodRedefined(Array@0x1008, []@0x1010, cme:0x1018)
- v26:Fixnum[5] = Const Value(5)
+ v24:CInt64 = UnboxFixnum v13
+ v25:BasicObject = ArrayAref v11, v24
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v26
+ Return v25
");
}
@@ -4790,10 +4793,11 @@ mod hir_opt_tests {
v13:Fixnum[-3] = Const Value(-3)
PatchPoint NoSingletonClass(Array@0x1008)
PatchPoint MethodRedefined(Array@0x1008, []@0x1010, cme:0x1018)
- v26:Fixnum[4] = Const Value(4)
+ v24:CInt64 = UnboxFixnum v13
+ v25:BasicObject = ArrayAref v11, v24
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v26
+ Return v25
");
}
@@ -4817,10 +4821,11 @@ mod hir_opt_tests {
v13:Fixnum[-10] = Const Value(-10)
PatchPoint NoSingletonClass(Array@0x1008)
PatchPoint MethodRedefined(Array@0x1008, []@0x1010, cme:0x1018)
- v26:NilClass = Const Value(nil)
+ v24:CInt64 = UnboxFixnum v13
+ v25:BasicObject = ArrayAref v11, v24
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v26
+ Return v25
");
}
@@ -4844,10 +4849,11 @@ mod hir_opt_tests {
v13:Fixnum[10] = Const Value(10)
PatchPoint NoSingletonClass(Array@0x1008)
PatchPoint MethodRedefined(Array@0x1008, []@0x1010, cme:0x1018)
- v26:NilClass = Const Value(nil)
+ v24:CInt64 = UnboxFixnum v13
+ v25:BasicObject = ArrayAref v11, v24
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v26
+ Return v25
");
}
@@ -6735,10 +6741,11 @@ mod hir_opt_tests {
v19:Fixnum[0] = Const Value(0)
PatchPoint NoSingletonClass(Array@0x1008)
PatchPoint MethodRedefined(Array@0x1008, []@0x1010, cme:0x1018)
- v30:BasicObject = ArrayArefFixnum v14, v19
+ v30:CInt64 = UnboxFixnum v19
+ v31:BasicObject = ArrayAref v14, v30
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v30
+ Return v31
");
}
@@ -6766,10 +6773,11 @@ mod hir_opt_tests {
PatchPoint MethodRedefined(Array@0x1000, []@0x1008, cme:0x1010)
v27:ArrayExact = GuardType v11, ArrayExact
v28:Fixnum = GuardType v12, Fixnum
- v29:BasicObject = ArrayArefFixnum v27, v28
+ v29:CInt64 = UnboxFixnum v28
+ v30:BasicObject = ArrayAref v27, v29
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v29
+ Return v30
");
}
@@ -6798,10 +6806,11 @@ mod hir_opt_tests {
PatchPoint MethodRedefined(C@0x1000, []@0x1008, cme:0x1010)
v27:ArraySubclass[class_exact:C] = GuardType v11, ArraySubclass[class_exact:C]
v28:Fixnum = GuardType v12, Fixnum
- v29:BasicObject = ArrayArefFixnum v27, v28
+ v29:CInt64 = UnboxFixnum v28
+ v30:BasicObject = ArrayAref v27, v29
IncrCounter inline_cfunc_optimized_send_count
CheckInterrupts
- Return v29
+ Return v30
");
}
diff --git a/zjit/src/hir/tests.rs b/zjit/src/hir/tests.rs
index 14a7777623..6a26b69051 100644
--- a/zjit/src/hir/tests.rs
+++ b/zjit/src/hir/tests.rs
@@ -3566,9 +3566,11 @@ pub mod hir_build_tests {
v22:CInt64 = ArrayLength v21
v23:CInt64[2] = GuardBitEquals v22, CInt64(2)
v24:Fixnum[1] = Const Value(1)
- v25:BasicObject = ArrayArefFixnum v21, v24
- v26:Fixnum[0] = Const Value(0)
- v27:BasicObject = ArrayArefFixnum v21, v26
+ v25:CInt64 = UnboxFixnum v24
+ v26:BasicObject = ArrayAref v21, v25
+ v27:Fixnum[0] = Const Value(0)
+ v28:CInt64 = UnboxFixnum v27
+ v29:BasicObject = ArrayAref v21, v28
PatchPoint NoEPEscape(test)
CheckInterrupts
Return v13
diff --git a/zjit/src/hir_type/mod.rs b/zjit/src/hir_type/mod.rs
index 061fe16578..d339674d98 100644
--- a/zjit/src/hir_type/mod.rs
+++ b/zjit/src/hir_type/mod.rs
@@ -395,6 +395,17 @@ impl Type {
}
}
+ pub fn cint64_value(&self) -> Option<i64> {
+ if self.is_subtype(types::CInt64) {
+ match self.spec {
+ Specialization::Int(val) => Some(val as i64),
+ _ => None,
+ }
+ } else {
+ None
+ }
+ }
+
/// Return true if the Type has object specialization and false otherwise.
pub fn ruby_object_known(&self) -> bool {
matches!(self.spec, Specialization::Object(_))