[newlib-cygwin] newlib: Unlock the mutex while calling atexit()'ed functions

Takashi Yano tyan0@sourceware.org
Fri Nov 21 09:08:43 GMT 2025


https://sourceware.org/git/gitweb.cgi?p=newlib-cygwin.git;h=a2a8bc771f2f5c1c17f05d55a3d04ac09b022127

commit a2a8bc771f2f5c1c17f05d55a3d04ac09b022127
Author: Takashi Yano <takashi.yano@nifty.ne.jp>
Date:   Tue Nov 18 22:18:00 2025 +0900

    newlib: Unlock the mutex while calling atexit()'ed functions
    
    The atexit()'ed function may deadlock if it waits for another thread
    which calls atexit() in the current __call_atexit.c code. This patch
    unlock __atexit_recursive_mutex while calling atexit()'ed functions
    to avoid the deadlock mentioned above. glibc and Darwin do the same,
    so it sounds reasonable.
    
    Addresses: https://cygwin.com/pipermail/cygwin/2025-October/258930.html
    Reported-by: Tomohiro Kashiwada <tomohiro-kashiwada@ezweb.ne.jp>
    Reviewed-by: Corinna Vinschen <corinna@vinschen.de>
    Signed-off-by: Takashi Yano <takashi.yano@nifty.ne.jp>

Diff:
---
 newlib/libc/stdlib/__call_atexit.c | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/newlib/libc/stdlib/__call_atexit.c b/newlib/libc/stdlib/__call_atexit.c
index 710440389..44f1f6acc 100644
--- a/newlib/libc/stdlib/__call_atexit.c
+++ b/newlib/libc/stdlib/__call_atexit.c
@@ -114,6 +114,11 @@ __call_exitprocs (int code, void *d)
 
 	  ind = p->_ind;
 
+#ifndef __SINGLE_THREAD__
+	  /* Unlock __atexit_recursive_mutex; otherwise, the function fn() may
+	     deadlock if it waits for another thread which calls atexit(). */
+	  __lock_release_recursive(__atexit_recursive_mutex);
+#endif
 	  /* Call the function.  */
 	  if (!args || (args->_fntypes & i) == 0)
 	    fn ();
@@ -121,6 +126,9 @@ __call_exitprocs (int code, void *d)
 	    (*((void (*)(int, void *)) fn))(code, args->_fnargs[n]);
 	  else
 	    (*((void (*)(void *)) fn))(args->_fnargs[n]);
+#ifndef __SINGLE_THREAD__
+	  __lock_acquire_recursive(__atexit_recursive_mutex);
+#endif
 
 	  /* The function we called call atexit and registered another
 	     function (or functions).  Call these new functions before


More information about the Newlib-cvs mailing list