Skip to content

Ruby 2.7 conformance: ObjectSpace::WeakMap is broken for FixNum keys #7862

@JasonLunn

Description

@JasonLunn
  • JRuby version: Reproducible on 9.4.3.0 release

Expected Behavior

Per https://github.com/rubyreferences/rubychanges/blob/master/2.7.md#objectspaceweakmap-now-accepts-non-gc-able-objects as of Ruby 2.7, ObjectSpace::WeakMap should be able to accept numeric keys.

Actual Behavior

Accessor functions like #key? and #[] behave as though a numeric key is not present when queried, except if the instance of the key that appears in #keys is used.

foo = Object.new
m=ObjectSpace::WeakMap.new
original_key = 105553124374448
m[original_key] = foo
puts "m.key?(105553124374448) #{m.key? 105553124374448}"
puts m.inspect
puts m.keys.inspect
puts m.values.inspect
puts "m.key?(m.keys.first) #{m.key? m.keys.first}"
puts "m.key?(original_key) #{m.key? original_key}"

Outputs:

m.key?(105553124374448) false
#<ObjectSpace::WeakMap:0x799f354a: 105553124374448 => #<Object:0x45e140ae>>
Keys [105553124374448]
Values [#<Object:0x45e140ae>]
m.key?(m.keys.first) true
m.key?(original_key) false

After investigation, the root cause seems to be that the underlying backing map is java.util.IdentityHashMap, which uses System.identityHashCode(Object)) to compare keys. System.identityHashCode(Object)) does not return identical values for two org.jruby.RubyFixnum instances that have identical values for IRubyObject.id() or Object.hashCode().

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions