The reproduction procedure could be simplified.

A segmentation fault (SIGSEGV) occurs when running a Ruby script using
Ruby 3.4.2 (test package) on Cygwin 3.6.3-1 (x86_64), where Thread.new
is used to require 'openssl' inside a thread.

The crash path leads from OpenSSL’s OPENSSL_thread_stop() to
CRYPTO_THREAD_write_lock() and then pthread_rwlock_wrlock(), which
invokes pthread_testcancel(). At that point, a NULL pointer
dereference seems to occur, possibly during access to TLS data.

# Reproduction
Save as repro.rb and run:

```ruby
Thread.new do
require 'openssl'
end.join

GC.start
sleep 0.1
```

```
$ uname -srvmpio
CYGWIN_NT-10.0-22000-ARM64 3.6.3-1.x86_64 2025-06-05 11:45 UTC x86_64
unknown unknown Cygwin
$ /usr/bin/ruby -v
ruby 3.4.2 (2025-02-15 revision d2930f8e7a) +PRISM [x86_64-cygwin]
$ cygcheck -cd libssl3
Cygwin Package Information
Package Version
libssl3 3.0.16-1
$ gdb -nx /usr/bin/ruby -v
(gdb) run repro.rb
:
Thread 8 "repro.rb:1" received signal SIGSEGV, Segmentation fault.
[Switching to Thread 7380.0x25e4]
0x0000000000000000 in ?? ()
(gdb) where
#0 0x0000000000000000 in ?? ()
#1 0x00007ffe4ad2a0e4 in pthread_testcancel () at
/usr/src/debug/cygwin-3.6.3-1/winsup/cygwin/thread.cc:399
#2 pthread_rwlock_wrlock (rwlock=0xa002a9010) at
/usr/src/debug/cygwin-3.6.3-1/winsup/cygwin/thread.cc:4352
#3 0x00007ffe4ae0b0d4 in _sigfe () at sigfe.s:35
#4 0x00000003ff54e3f9 in CRYPTO_THREAD_write_lock (lock=<optimized
out>) at crypto/threads_pthread.c:110
#5 0x00000003ff541922 in init_thread_remove_handlers
(handsin=handsin@entry=0x0) at crypto/initthread.c:178
#6 0x00000003ff541d43 in OPENSSL_thread_stop () at crypto/initthread.c:235
#7 0x00000003ff53fdd3 in DllMain (hinstDLL=<optimized out>,
fdwReason=<optimized out>, lpvReserved=<optimized out>)
at crypto/dllmain.c:38
#8 0x00007ffe8f2fd6ac in ?? ()
#9 0x00007ffe8f38b590 in ?? ()
#10 0x00007ffe8f38b590 in ?? ()
#11 0x0000000000000000 in ?? ()
(gdb) up
#1 0x00007ffe4ad2a0e4 in pthread_testcancel () at
/usr/src/debug/cygwin-3.6.3-1/winsup/cygwin/thread.cc:399
399 return thread;
(gdb) list
394 if (!thread)
395 {
396 thread = pthread_null::get_null_pthread ();
397 thread->set_tls_self_pointer ();
398 }
399 return thread;
400 }
401
402 void
403 pthread::set_tls_self_pointer ()
(gdb) list 394
389
390 pthread *
391 pthread::self ()
392 {
393 pthread *thread = _my_tls.tid;
394 if (!thread)
395 {
396 thread = pthread_null::get_null_pthread ();
397 thread->set_tls_self_pointer ();
398 }

```

Running without gdb, the child process seems to crash silently and
exits with code 0 — the crash goes undetected by the parent process.

```
$ /usr/bin/ruby repro.rb
$ echo $?
0
```

On Thu, Apr 10, 2025 at 10:48 PM Daisuke Fujimura
<booleanla...@gmail.com> wrote:
>
> Thank you for the advice.
>
> I updated cygwin and ran again.
>
> ```
> $ uname -srvmpio
> CYGWIN_NT-10.0-22000-ARM64 3.6.1-1.x86_64 2025-04-09 11:31 UTC x86_64
> unknown unknown Cygwin
> (snip)
> $ gdb /usr/bin/ruby
> (gdb) set cygwin-exceptions on
> (gdb) run /usr/bin/gem install -V --local --ignore-dependencies
> --document=rdoc,ri --build-root
> /tmp/cygport-ruby-debug_inspector/ruby-debug_inspector-1.2.0-1.x86_64/inst
> --install-dir /usr/share/gems --bindir /usr/bin
> debug_inspector-1.2.0.gem
> :
> Building native extensions. This could take a while...
> current directory:
> /tmp/cygport-ruby-debug_inspector/ruby-debug_inspector-1.2.0-1.x86_64/inst/usr/share/gems/gems/debug_inspector-1.2.0/ext/debug_inspector
> ["/usr/bin/ruby.exe", "-I/usr/share/rubygems", "extconf.rb"]
> [New Thread 5284.0x2200]
> [New Thread 5284.0xe10]
> [New Thread 5284.0x50c]
> creating Makefile
> current directory:
> /tmp/cygport-ruby-debug_inspector/ruby-debug_inspector-1.2.0-1.x86_64/inst/usr/share/gems/gems/debug_inspector-1.2.0/ext/debug_inspector
> ["make", "DESTDIR=", "sitearchdir=./.gem.20250410-1545-swemh8",
> "sitelibdir=./.gem.20250410-1545-swemh8", "clean"]
>
> Thread 11 "ruby" received signal SIGSEGV, Segmentation fault.
> [Switching to Thread 5284.0xe10]
> 0x0000000000000000 in ?? ()
> (gdb) where
> #0  0x0000000000000000 in ?? ()
> #1  0x00007ffef1609fb4 in pthread_testcancel () at
> /usr/src/debug/cygwin-3.6.1-1/winsup/cygwin/thread.cc:399
> #2  pthread_rwlock_wrlock (rwlock=0xa003a9a00) at
> /usr/src/debug/cygwin-3.6.1-1/winsup/cygwin/thread.cc:4352
> #3  0x00007ffef16eacd4 in _sigfe () at sigfe.s:35
> #4  0x00000003ff54e3f9 in cygcrypto-3!CRYPTO_THREAD_write_lock () from
> /usr/bin/cygcrypto-3.dll
> #5  0x00000003ff541922 in cygcrypto-3!OPENSSL_atexit () from
> /usr/bin/cygcrypto-3.dll
> #6  0x00000003ff541d43 in cygcrypto-3!OPENSSL_thread_stop () from
> /usr/bin/cygcrypto-3.dll
> #7  0x00000003ff53fdd3 in ossl_DER_w_end_sequence () from
> /usr/bin/cygcrypto-3.dll
> #8  0x00007fff4d63d6ac in ?? ()
> #9  0x00007fff4d6cb590 in ?? ()
> #10 0x00007fff4d6cb590 in ?? ()
> #11 0x0000000000000000 in ?? ()
> (gdb)
> ```
>
>
> On Sat, Feb 22, 2025 at 2:11 AM Jon Turney <jon.tur...@dronecode.org.uk> 
> wrote:
> >
> > On 20/02/2025 15:33, Daisuke Fujimura via Cygwin wrote:
> > > Reproduction:
> > > - Use ruby-3.4.2-1 (test)
> > > - Install gem containing native libraries
> > >
> > > ```
> > > $ uname -srvmpio
> > > CYGWIN_NT-10.0-22000 3.5.7-1.x86_64 2025-01-29 19:46 UTC x86_64
> > > unknown unknown Cygwin
> > > $ ruby -v
> > > ruby 3.4.2 (2025-02-15 revision d2930f8e7a) +PRISM [x86_64-cygwin]
> > > $ gem -v
> > > 3.5.11
> > > $ cd /tmp
> > > $ git clone https://cygwin.com/git/cygwin-packages/ruby-debug_inspector
> > > # Any gem that contains native libraries
> > > $ cd ruby-debug_inspector
> > > $ cygport ruby-debug_inspector.cygport fetch prep compile # preparation
> > > $ cygport ruby-debug_inspector.cygport install
> > > :
> > > ```
> > >
> > > The process spawned inside `gem install` seems to raise SIGSEGV
> > > internally and exits.
> > >
> > > ```
> > > $ gdb /usr/bin/ruby
> > > :
> > > (gdb) run /usr/bin/gem install -V --local --ignore-dependencies
> > > --document=rdoc,ri --build-root
> > > /tmp/ruby-debug_inspector/ruby-debug_inspector-1.1.0-1.x86_64/inst
> > > --install-dir /usr/share/gems --bindir /usr/bin
> > > debug_inspector-1.1.0.gem #
> > > https://github.com/cygwin/cygport/blob/0.36.9/cygclass/rubygem.cygclass#L134
> > > :
> > > :
> > > Building native extensions. This could take a while...
> > > current directory:
> > > /tmp/ruby-debug_inspector/ruby-debug_inspector-1.1.0-1.x86_64/inst/usr/share/gems/gems/debug_inspector-1.1.0/ext/debug_inspector
> > > ["/usr/bin/ruby.exe", "-I/usr/share/rubygems", "extconf.rb"]
> > > [New Thread 3600.0x23a0]
> > > [New Thread 3600.0x1278]
> > > [New Thread 3600.0x2794]
> > > creating Makefile
> > >
> > > Thread 11 "ruby" received signal SIGSEGV, Segmentation fault.
> > > [Switching to Thread 3600.0x1278]
> > > 0x0000000000000000 in ?? ()
> > >
> > [...]
> >
> > >
> > > SIGSEGV seems to occur inside the cygwin DLL.
> >
> > You might get more useful backtrace information after the exception with
> > the gdb setting 'set cygwin-exceptions on' (See [1]).
> >
> > [1] https://cygwin.com/faq.html#faq.programming.debugging-cygwin
> >
> > (It would be a nice project for someone to work on to see if is possible
> > improve this gdb (mis)feature so it only ignores exceptions inside the
> > cygwin DLL where exception::myfault() is on the SEH stack [which is used
> > to implement things like "POSIX defines that this function returns
> > EFAULT when you hand it an invalid pointer"], not all of them).
> >
> > > This problem also occurs with ruby-3.3.2-3 (test).
> > >
> > > We have confirmed that it also occurs in cygwin-3.6.
> >

-- 
Problem reports:      https://cygwin.com/problems.html
FAQ:                  https://cygwin.com/faq/
Documentation:        https://cygwin.com/docs.html
Unsubscribe info:     https://cygwin.com/ml/#unsubscribe-simple

Reply via email to