summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohn Hawthorn <john@hawthorn.email>2025-08-21 10:55:44 -0700
committerJohn Hawthorn <john@hawthorn.email>2025-08-21 15:42:14 -0700
commit823d55a8279aad5ad0eb2b83d45885443edfec83 (patch)
tree1f376c2b60383f2b41cfe70015ee06f7aa7e8031
parent2c6363c946005402f42d876a09ba9989dc23d86f (diff)
Add lock-free fastpath to callable_method_entry...
-rw-r--r--vm_method.c19
1 files changed, 19 insertions, 0 deletions
diff --git a/vm_method.c b/vm_method.c
index 03fb79cddd..fb217ef43d 100644
--- a/vm_method.c
+++ b/vm_method.c
@@ -1822,6 +1822,25 @@ callable_method_entry_or_negative(VALUE klass, ID mid, VALUE *defined_class_ptr)
const rb_callable_method_entry_t *cme;
VM_ASSERT_TYPE2(klass, T_CLASS, T_ICLASS);
+
+ /* Fast path: lock-free read from cache */
+ VALUE cc_tbl = RUBY_ATOMIC_VALUE_LOAD(RCLASS_WRITABLE_CC_TBL(klass));
+ if (cc_tbl) {
+ VALUE ccs_data;
+ if (rb_managed_id_table_lookup(cc_tbl, mid, &ccs_data)) {
+ struct rb_class_cc_entries *ccs = (struct rb_class_cc_entries *)ccs_data;
+ VM_ASSERT(vm_ccs_p(ccs));
+
+ if (LIKELY(!METHOD_ENTRY_INVALIDATED(ccs->cme))) {
+ VM_ASSERT(ccs->cme->called_id == mid);
+ if (defined_class_ptr != NULL) *defined_class_ptr = ccs->cme->defined_class;
+ RB_DEBUG_COUNTER_INC(ccs_found);
+ return ccs->cme;
+ }
+ }
+ }
+
+ /* Slow path: need to lock and potentially populate cache */
RB_VM_LOCKING() {
cme = cached_callable_method_entry(klass, mid);