Cygwin: convert malloc lock to SRWLOCK

Per https://cygwin.com/pipermail/cygwin-developers/2021-October/012429.html,
we may encounter a crash when starting multiple threads during process
startup (here: fhandler_fifo::fixup_after_{fork,exec}) which in turn
allocate memory via malloc.

The problem is concurrent usage of malloc before the malloc muto has
been initialized.

To fix this issue, convert the muto to a SRWLOCK and make sure it is
statically initalized.  Thus, malloc can be called as early as necessary
and malloc_init is only required to check for user space provided malloc.

Note that this requires to implement a __malloc_trylock macro to be
called from fork.

Signed-off-by: Corinna Vinschen <corinna@vinschen.de>
This commit is contained in:
Corinna Vinschen 2021-10-26 17:53:08 +02:00
parent 23b1400f83
commit 44a79a6eca
7 changed files with 12 additions and 9 deletions

View File

@ -36,9 +36,11 @@ void *mmap64 (void *, size_t, int, int, int, off_t);
#elif defined (__INSIDE_CYGWIN__) #elif defined (__INSIDE_CYGWIN__)
# define __malloc_lock() mallock.acquire () # define __malloc_lock() AcquireSRWLockExclusive (&mallock)
# define __malloc_unlock() mallock.release () # define __malloc_trylock() TryAcquireSRWLockExclusive (&mallock)
extern muto mallock; # define __malloc_unlock() ReleaseSRWLockExclusive (&mallock)
extern SRWLOCK NO_COPY mallock;
void malloc_init ();
#endif #endif

View File

@ -29,6 +29,7 @@ details. */
#include "shared_info.h" #include "shared_info.h"
#include "cygwin_version.h" #include "cygwin_version.h"
#include "dll_init.h" #include "dll_init.h"
#include "cygmalloc.h"
#include "heap.h" #include "heap.h"
#include "tls_pbuf.h" #include "tls_pbuf.h"
#include "exception.h" #include "exception.h"

View File

@ -296,7 +296,7 @@ frok::parent (volatile char * volatile stack_here)
si.lpReserved2 = (LPBYTE) &ch; si.lpReserved2 = (LPBYTE) &ch;
si.cbReserved2 = sizeof (ch); si.cbReserved2 = sizeof (ch);
bool locked = __malloc_lock (); bool locked = __malloc_trylock ();
/* Remove impersonation */ /* Remove impersonation */
cygheap->user.deimpersonate (); cygheap->user.deimpersonate ();

View File

@ -230,7 +230,6 @@ user_heap_info::init ()
debug_printf ("heap base %p, heap top %p, heap size %ly (%lu)", debug_printf ("heap base %p, heap top %p, heap size %ly (%lu)",
base, top, chunk, chunk); base, top, chunk, chunk);
page_const--; page_const--;
// malloc_init ();
} }
#define pround(n) (((size_t)(n) + page_const) & ~page_const) #define pround(n) (((size_t)(n) + page_const) & ~page_const)

View File

@ -10,7 +10,6 @@ details. */
/* Heap management. */ /* Heap management. */
void heap_init (); void heap_init ();
void malloc_init ();
#define inheap(s) \ #define inheap(s) \
(cygheap->user_heap.ptr && s \ (cygheap->user_heap.ptr && s \

View File

@ -269,13 +269,11 @@ strdup (const char *s)
newlib will call __malloc_lock and __malloc_unlock at appropriate newlib will call __malloc_lock and __malloc_unlock at appropriate
times. */ times. */
muto NO_COPY mallock; SRWLOCK NO_COPY mallock = SRWLOCK_INIT;
void void
malloc_init () malloc_init ()
{ {
mallock.init ("mallock");
/* Check if malloc is provided by application. If so, redirect all /* Check if malloc is provided by application. If so, redirect all
calls to malloc/free/realloc to application provided. This may calls to malloc/free/realloc to application provided. This may
happen if some other dll calls cygwin's malloc, but main code provides happen if some other dll calls cygwin's malloc, but main code provides

View File

@ -78,3 +78,7 @@ Bug Fixes
- Fix access violation that can sometimes occur when copy/pasting between - Fix access violation that can sometimes occur when copy/pasting between
32-bit and 64-bit Cygwin environments. Align clipboard descriptor layouts. 32-bit and 64-bit Cygwin environments. Align clipboard descriptor layouts.
Addresses: https://cygwin.com/pipermail/cygwin-patches/2021q4/011517.html Addresses: https://cygwin.com/pipermail/cygwin-patches/2021q4/011517.html
- Fix a synchronization issue when running multiple threads from DLL
initialization which in turn call malloc.
Addresses: https://cygwin.com/pipermail/cygwin/2021-October/249635.html