Project

General

Profile

Actions

Bug #22440

closed

Referencing an autoload constant from multiple Ractors dumps core

Bug #22440: Referencing an autoload constant from multiple Ractors dumps core

Added by mame (Yusuke Endoh) 1 day ago. Updated about 16 hours ago.

Status:
Closed
Target version:
-
[ruby-core:127108]

Description

Referencing an autoload constant from multiple Ractors in parallel may cause a SEGV:

# foo.rb
module Foo; end
# repro.rb
autoload :Foo, "./foo"
p 8.times.map { Ractor.new { Foo } }.map(&:value)
$ ruby repro.rb
repro.rb:2: [BUG] Segmentation fault at 0x0000000000000030

Reproduced with GCC 16 on Ubuntu 26.04. Not reproduced with GCC 13 / 15.

Cause:

  • GCC 16 computes the address of the TLS variable (ruby_current_ec) at the entry of rb_vm_opt_getconstant_path, and reuses it within the function.
  • When vm_get_ev_const_chain blocks waiting for an autoload, the M:N thread scheduler may resume the thread on a different native thread.
  • After that, GET_RACTOR() in vm_ic_update (inlined) reads the TLS of the previous native thread, refers to an invalid value, and SEGVs.

Proposed fix: pass ec (already an argument of rb_vm_opt_getconstant_path) to vm_ic_update, and use rb_ec_ractor_ptr(ec) instead of GET_RACTOR().

https://github.com/ruby/ruby/pull/19348

Note: the SEGV in #22439 is this issue, triggered by the autoload of Ruby::Prism. Since #22439 also involves another problem, I created this ticket dedicated to the autoload + Ractor issue.


Related issues 1 (0 open — 1 closed)

Related to Ruby - Bug #22439: Segfault in `Thread::Backtrace::Location#syntax_tree` (via `Exception#detailed_message` / error_highlight) when called from multiple RactorsClosedActions

Updated by mame (Yusuke Endoh) 1 day ago Actions #1

  • Related to Bug #22439: Segfault in `Thread::Backtrace::Location#syntax_tree` (via `Exception#detailed_message` / error_highlight) when called from multiple Ractors added

Updated by mame (Yusuke Endoh) about 16 hours ago Actions #2

  • Status changed from Assigned to Closed

Applied in changeset git|8a060f90ba36441cfeb509eacb10f609314f5bfe.


Fix SEGV when referencing an autoload constant from multiple Ractors

vm_ic_update used GET_RACTOR() after the constant lookup. The lookup may
block waiting for an autoload, and under the M:N thread scheduler the
thread may then be resumed on a different native thread. Since
vm_ic_update is inlined into rb_vm_opt_getconstant_path, a compiler can
reuse the TLS address computed at the function entry (GCC 16 does), so
GET_RACTOR() read the ec of the previous native thread and crashed.

autoload :Foo, "./foo"
p 8.times.map { Ractor.new { Foo } }.map(&:value)
#=> [BUG] Segmentation fault at 0x0000000000000030

Use the ec passed to rb_vm_opt_getconstant_path instead.

[Bug #22440]

Co-Authored-By: Claude Opus 5.5

Actions

Also available in: PDF Atom