From: ko1@... Date: 2015-12-16T08:06:19+00:00 Subject: [ruby-core:72180] [Ruby trunk - Bug #11740] ObjectSpace.each_object exposes internal metaclasses Issue #11740 has been updated by Koichi Sasada. ```diff Index: class.c =================================================================== --- class.c (revision 53150) +++ class.c (working copy) @@ -442,6 +442,12 @@ rb_singleton_class_attached(VALUE klass, */ #define META_CLASS_OF_CLASS_CLASS_P(k) (METACLASS_OF(k) == (k)) +int +rb_singleton_class_has_metaclass_p(VALUE sklass) +{ + return rb_ivar_get(METACLASS_OF(sklass), id_attached) == sklass; +} + /*! * whether k has a metaclass * @retval 1 if \a k has a metaclass @@ -449,7 +455,13 @@ rb_singleton_class_attached(VALUE klass, */ #define HAVE_METACLASS_P(k) \ (FL_TEST(METACLASS_OF(k), FL_SINGLETON) && \ - rb_ivar_get(METACLASS_OF(k), id_attached) == (k)) + rb_singleton_class_has_metaclass_p(k)) + +int +rb_class_has_metaclass_p(VALUE klass) +{ + return HAVE_METACLASS_P(klass); +} /*! * ensures \a klass belongs to its own eigenclass. Index: gc.c =================================================================== --- gc.c (revision 53150) +++ gc.c (working copy) @@ -2400,6 +2400,13 @@ internal_object_p(VALUE obj) case T_NODE: case T_ZOMBIE: break; + case T_CLASS: + { + if (FL_TEST(obj, FL_SINGLETON)) { + int rb_singleton_class_has_metaclass_p(VALUE sklass); + return rb_singleton_class_has_metaclass_p(obj) == 0; + } + } default: if (!p->as.basic.klass) break; return 0; ``` This patch solves this problem. Could you check it? ---------------------------------------- Bug #11740: ObjectSpace.each_object exposes internal metaclasses https://bugs.ruby-lang.org/issues/11740#change-55594 * Author: Benoit Daloze * Status: Open * Priority: Normal * Assignee: Koichi Sasada * ruby -v: ruby 2.3.0dev (2015-11-19 trunk 52672) [x86_64-linux] * Backport: 2.0.0: UNKNOWN, 2.1: UNKNOWN, 2.2: UNKNOWN ---------------------------------------- ObjectSpace.each_object exposes internal metaclasses and this might result in assumptions being violated since the metaclass structure is not well preserved. See the attached script for an example. The #bla method should always be defined on the metaclass of "klass". See https://bugs.ruby-lang.org/issues/11360#note-2 as well in which I warned against this problem ;) ---Files-------------------------------- objspace_expose_intern_meta.rb (413 Bytes) -- https://bugs.ruby-lang.org/