This is the mail archive of the
libc-alpha@sourceware.org
mailing list for the glibc project.
Re: [PATCH] Fix possible deadlock in stdio locking code
- From: Siddhesh Poyarekar <spoyarek at redhat dot com>
- To: Jonathan Nieder <jrnieder at gmail dot com>
- Cc: Andreas Schwab <schwab at redhat dot com>, libc-alpha at sourceware dot org
- Date: Fri, 11 Nov 2011 15:26:30 +0530
- Subject: Re: [PATCH] Fix possible deadlock in stdio locking code
- References: <20111018140922.GA5701@spoyarek.pnq.redhat.com><m3vcrmgxcc.fsf@hase.home><20111107123054.GA9524@spoyarek.redhat.com><20111111090938.GA14122@elie.hsd1.il.comcast.net>
On Fri, Nov 11, 2011 at 03:09:40AM -0600, Jonathan Nieder wrote:
> Siddhesh Poyarekar wrote:
>
> > while(1) {
> > int child = fork();
> >
> > if (child == 0)
> > exit(0);
>
> POSIX explains (under fork()):
>
> If a multi-threaded process calls fork( ), the new process
> shall contain a replica of the calling thread and its entire
> address space, possibly including the states of mutexes and
> other resources. Consequently, to avoid errors, the child
> process may only execute async-signal-safe operations until
> such time as one of the exec functions is called.
>
> exit() is not async-signal-safe, though _exit() is. I don't think
> that glibc is the right tool to diagnose or work around application
> problems like this. (Maybe helgrind could be tweaked to make the
> diagnosis.)
Thanks, the problem is not due to this though. I believe Andreas has
already fixed it; I was wrong (and careless) when I thought that it
could not have been fixed inside _IO_flush_all_lockp:
commit 7583a88d1c7170caad26966bcea8bfc2c92093ba
Author: Andreas Schwab <schwab@redhat.com>
Date: Mon Nov 7 15:07:31 2011 +0100
Fix locking in _IO_flush_all_lockp
diff --git a/libio/genops.c b/libio/genops.c
index 5d21c42..bb40c34 100644
--- a/libio/genops.c
+++ b/libio/genops.c
@@ -826,7 +826,7 @@ _IO_flush_all_lockp (int do_lock)
int last_stamp;
#ifdef _IO_MTSAFE_IO
- _IO_cleanup_region_start_noarg (flush_cleanup);
+ __libc_cleanup_region_start (do_lock, flush_cleanup, 0);
if (do_lock)
_IO_lock_lock (list_all_lock);
#endif
@@ -866,7 +866,7 @@ _IO_flush_all_lockp (int do_lock)
#ifdef _IO_MTSAFE_IO
if (do_lock)
_IO_lock_unlock (list_all_lock);
- _IO_cleanup_region_end (0);
+ __libc_cleanup_region_end (0);
#endif
return result;
--
Siddhesh