Skip to content

Commit 9a1d6cc

Browse files
authored
ZJIT: Add CallableMethodEntry to type lattice (rubyGH-13459)
This will be useful when we split Send into Lookup+Call. For reasoning about various method types during optimization.
1 parent b5f5672 commit 9a1d6cc

4 files changed

Lines changed: 51 additions & 24 deletions

File tree

zjit/src/cruby.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -573,6 +573,11 @@ impl VALUE {
573573
ptr
574574
}
575575

576+
pub fn cme_p(self) -> bool {
577+
if self == VALUE(0) { return false; }
578+
unsafe { rb_IMEMO_TYPE_P(self, imemo_ment) == 1 }
579+
}
580+
576581
/// Assert that `self` is a method entry in debug builds
577582
pub fn as_cme(self) -> *const rb_callable_method_entry_t {
578583
let ptr: *const rb_callable_method_entry_t = self.as_ptr();

zjit/src/hir_type/gen_hir_type.rb

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,7 @@ def to_graphviz type
4848
# Build the Ruby object universe.
4949
value = any.subtype "RubyValue"
5050
undef_ = value.subtype "Undef"
51+
value.subtype "CallableMethodEntry" # rb_callable_method_entry_t*
5152
basic_object = value.subtype "BasicObject"
5253
basic_object_exact = basic_object.subtype "BasicObjectExact"
5354
basic_object_subclass = basic_object.subtype "BasicObjectSubclass"

zjit/src/hir_type/hir_type.inc.rs

Lines changed: 27 additions & 24 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

zjit/src/hir_type/mod.rs

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,11 @@ impl Type {
163163
else if val == Qnil { types::NilClassExact }
164164
else if val == Qtrue { types::TrueClassExact }
165165
else if val == Qfalse { types::FalseClassExact }
166+
else if val.cme_p() {
167+
// NB: Checking for CME has to happen before looking at class_of because that's not
168+
// valid on imemo.
169+
Type { bits: bits::CallableMethodEntry, spec: Specialization::Object(val) }
170+
}
166171
else if val.class_of() == unsafe { rb_cInteger } {
167172
Type { bits: bits::Bignum, spec: Specialization::Object(val) }
168173
}
@@ -682,6 +687,19 @@ mod tests {
682687
});
683688
}
684689

690+
#[test]
691+
fn cme() {
692+
use crate::cruby::{rb_callable_method_entry, ID};
693+
crate::cruby::with_rubyvm(|| {
694+
let cme = unsafe { rb_callable_method_entry(rb_cInteger, ID!(to_s)) };
695+
assert!(!cme.is_null());
696+
let cme_value: VALUE = cme.into();
697+
let ty = Type::from_value(cme_value);
698+
assert_subtype(ty, types::CallableMethodEntry);
699+
assert!(ty.ruby_object_known());
700+
});
701+
}
702+
685703
#[test]
686704
fn union_specialized_with_no_relation_returns_unspecialized() {
687705
crate::cruby::with_rubyvm(|| {

0 commit comments

Comments
 (0)