summaryrefslogtreecommitdiff
path: root/class.c
diff options
context:
space:
mode:
authorAaron Patterson <[email protected]>2025-05-22 16:07:21 -0700
committerAaron Patterson <[email protected]>2025-05-22 22:12:42 -0700
commite32054736fcdb2a7729dc770ec0c7ad6a4654135 (patch)
tree625bb53e0dd8d256012dc6146150d9968235c210 /class.c
parent9583b7af8f4934397913e2197a1c40e91c1d853e (diff)
Remove assertion on field in `class_duplicate_iclass_classext`
`ext` is newly allocated so it shouldn't need an assertion. The class ext (which is always from the module) that we're passing to `class_duplicate_iclass_classext` could legitimately have instance variables on it. We just want to avoid copying them. The assertion was making this crash: ``` $ RUBY_NAMESPACE=1 ./miniruby -e1 ```
Notes
Notes: Merged: https://github.com/ruby/ruby/pull/13419
Diffstat (limited to 'class.c')
-rw-r--r--class.c11
1 files changed, 8 insertions, 3 deletions
diff --git a/class.c b/class.c
index d743fb3fbb..1e436e6c96 100644
--- a/class.c
+++ b/class.c
@@ -256,6 +256,8 @@ duplicate_classext_subclasses(rb_classext_t *orig, rb_classext_t *copy)
static void
class_duplicate_iclass_classext(VALUE iclass, rb_classext_t *mod_ext, const rb_namespace_t *ns)
{
+ RUBY_ASSERT(RB_TYPE_P(iclass, T_ICLASS));
+
rb_classext_t *src = RCLASS_EXT_PRIME(iclass);
rb_classext_t *ext = RCLASS_EXT_TABLE_LOOKUP_INTERNAL(iclass, ns);
int first_set = 0;
@@ -282,8 +284,6 @@ class_duplicate_iclass_classext(VALUE iclass, rb_classext_t *mod_ext, const rb_n
RCLASSEXT_CONST_TBL(ext) = RCLASSEXT_CONST_TBL(mod_ext);
RCLASSEXT_CVC_TBL(ext) = RCLASSEXT_CVC_TBL(mod_ext);
- RUBY_ASSERT(!RCLASSEXT_FIELDS(mod_ext));
-
// Those are cache and should be recreated when methods are called
// RCLASSEXT_CALLABLE_M_TBL(ext) = NULL;
// RCLASSEXT_CC_TBL(ext) = NULL;
@@ -319,11 +319,14 @@ rb_class_duplicate_classext(rb_classext_t *orig, VALUE klass, const rb_namespace
// TODO: consider shapes for performance
if (RCLASSEXT_FIELDS(orig)) {
+ RUBY_ASSERT(!RB_TYPE_P(klass, T_ICLASS));
RCLASSEXT_FIELDS(ext) = (VALUE *)st_copy((st_table *)RCLASSEXT_FIELDS(orig));
rb_autoload_copy_table_for_namespace((st_table *)RCLASSEXT_FIELDS(ext), ns);
}
else {
- RCLASSEXT_FIELDS(ext) = (VALUE *)st_init_numtable();
+ if (!RB_TYPE_P(klass, T_ICLASS)) {
+ RCLASSEXT_FIELDS(ext) = (VALUE *)st_init_numtable();
+ }
}
if (RCLASSEXT_SHARED_CONST_TBL(orig)) {
@@ -380,6 +383,8 @@ rb_class_duplicate_classext(rb_classext_t *orig, VALUE klass, const rb_namespace
if (subclass_entry->klass && RB_TYPE_P(subclass_entry->klass, T_ICLASS)) {
iclass = subclass_entry->klass;
if (RBASIC_CLASS(iclass) == klass) {
+ // Is the subclass an ICLASS including this module into another class
+ // If so we need to re-associate it under our namespace with the new ext
class_duplicate_iclass_classext(iclass, ext, ns);
}
}