aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNobuyoshi Nakada <nobu@ruby-lang.org>2019-06-23 00:31:16 +0900
committerNobuyoshi Nakada <nobu@ruby-lang.org>2019-06-23 00:31:16 +0900
commitf3c81b4e90ec492382e299573f2c3ac272adbb5f (patch)
tree9ea5455129d2cf643290d81b564769d7032f6803
parentf5e29044710e74249e89bbb0f112dc22e5b91398 (diff)
downloadruby-f3c81b4e90ec492382e299573f2c3ac272adbb5f.tar.gz
Frozen objects in WeakMap
* gc.c (wmap_aset): bypass check for frozen and allow frozen object in WeakMap. [Bug #13498]
-rw-r--r--gc.c13
-rw-r--r--test/ruby/test_weakmap.rb6
2 files changed, 16 insertions, 3 deletions
diff --git a/gc.c b/gc.c
index 7b82a889f7..a1984f83f0 100644
--- a/gc.c
+++ b/gc.c
@@ -2937,13 +2937,20 @@ should_be_callable(VALUE block)
rb_obj_class(block));
}
}
+
static void
-should_be_finalizable(VALUE obj)
+should_be_finalizable_internal(VALUE obj)
{
if (!FL_ABLE(obj)) {
rb_raise(rb_eArgError, "cannot define finalizer for %s",
rb_obj_classname(obj));
}
+}
+
+static void
+should_be_finalizable(VALUE obj)
+{
+ should_be_finalizable_internal(obj);
rb_check_frozen(obj);
}
@@ -10399,8 +10406,8 @@ wmap_aset(VALUE self, VALUE wmap, VALUE orig)
struct weakmap *w;
TypedData_Get_Struct(self, struct weakmap, &weakmap_type, w);
- should_be_finalizable(orig);
- should_be_finalizable(wmap);
+ should_be_finalizable_internal(orig);
+ should_be_finalizable_internal(wmap);
define_final0(orig, w->final);
define_final0(wmap, w->final);
st_update(w->obj2wmap, (st_data_t)orig, wmap_aset_update, wmap);
diff --git a/test/ruby/test_weakmap.rb b/test/ruby/test_weakmap.rb
index fb57903c98..8eb32b574f 100644
--- a/test/ruby/test_weakmap.rb
+++ b/test/ruby/test_weakmap.rb
@@ -141,4 +141,10 @@ class TestWeakMap < Test::Unit::TestCase
assert_equal(2, @wm.__send__(m))
end
alias test_length test_size
+
+ def test_frozen_object
+ o = Object.new.freeze
+ assert_nothing_raised(FrozenError) {@wm[o] = 'foo'}
+ assert_nothing_raised(FrozenError) {@wm['foo'] = o}
+ end
end