GNU bug report logs -
#41948
Shepherd deadlocks
Previous Next
Reported by: Mathieu Othacehe <othacehe <at> gnu.org>
Date: Fri, 19 Jun 2020 08:42:01 UTC
Severity: important
Done: Ludovic Courtès <ludo <at> gnu.org>
Bug is archived. No further changes may be made.
Full log
View this message in rfc822 format
[Message part 1 (text/plain, inline)]
Hi,
Mathieu Othacehe <othacehe <at> gnu.org> skribis:
> Those two finalizer threads share the same pipe. When we try to
> stop the finalizer thread in Shepherd, right before forking a new
> process, we send a '\1' byte to the finalizer pipe.
>
> 1 write(6, "\1", 1 <unfinished ...>
>
>
> which is received by (line 183597):
>
> 253 <... read resumed>"\1", 1) = 1
>
> the marionette finalizer thread. Then, we pthread_join the Shepherd
> finalizer thread, which never stops! Quite unfortunate.
And here’s the patch for this pipe: it closes the finalizer pipe
pre-fork, and it gets reopened lazily.
Together with the ‘sleep_pipe’ patch, it appears to fix the problems
described here.
Ludo’.
[Message part 2 (text/x-patch, inline)]
diff --git a/libguile/finalizers.c b/libguile/finalizers.c
index 0ae165fd1..5ddc7dbef 100644
--- a/libguile/finalizers.c
+++ b/libguile/finalizers.c
@@ -24,6 +24,7 @@
# include <config.h>
#endif
+#include <assert.h>
#include <errno.h>
#include <fcntl.h>
#include <full-write.h>
@@ -170,7 +171,7 @@ queue_finalizer_async (void)
#if SCM_USE_PTHREAD_THREADS
-static int finalization_pipe[2];
+static int finalization_pipe[2] = { -1, -1 };
static scm_i_pthread_mutex_t finalization_thread_lock =
SCM_I_PTHREAD_MUTEX_INITIALIZER;
static pthread_t finalization_thread;
@@ -254,6 +255,13 @@ start_finalization_thread (void)
scm_i_pthread_mutex_lock (&finalization_thread_lock);
if (!finalization_thread_is_running)
{
+ assert (finalization_pipe[0] == -1);
+
+ if (pipe2 (finalization_pipe, O_CLOEXEC) != 0)
+ scm_syserror (NULL);
+
+ GC_set_finalizer_notifier (notify_finalizers_to_run);
+
/* Use the raw pthread API and scm_with_guile, because we don't want
to block on any lock that scm_spawn_thread might want to take,
and we don't want to inherit the dynamic state (fluids) of the
@@ -276,6 +284,12 @@ stop_finalization_thread (void)
notify_about_to_fork ();
if (pthread_join (finalization_thread, NULL))
perror ("joining finalization thread");
+
+ close (finalization_pipe[0]);
+ close (finalization_pipe[1]);
+ finalization_pipe[0] = -1;
+ finalization_pipe[1] = -1;
+
finalization_thread_is_running = 0;
}
scm_i_pthread_mutex_unlock (&finalization_thread_lock);
@@ -284,7 +298,6 @@ stop_finalization_thread (void)
static void
spawn_finalizer_thread (void)
{
- GC_set_finalizer_notifier (notify_finalizers_to_run);
start_finalization_thread ();
}
@@ -368,8 +381,6 @@ scm_set_automatic_finalization_enabled (int enabled_p)
if (enabled_p)
{
#if SCM_USE_PTHREAD_THREADS
- if (pipe2 (finalization_pipe, O_CLOEXEC) != 0)
- scm_syserror (NULL);
GC_set_finalizer_notifier (spawn_finalizer_thread);
#else
GC_set_finalizer_notifier (queue_finalizer_async);
@@ -381,10 +392,6 @@ scm_set_automatic_finalization_enabled (int enabled_p)
#if SCM_USE_PTHREAD_THREADS
stop_finalization_thread ();
- close (finalization_pipe[0]);
- close (finalization_pipe[1]);
- finalization_pipe[0] = -1;
- finalization_pipe[1] = -1;
#endif
}
@@ -423,10 +430,6 @@ scm_init_finalizer_thread (void)
{
#if SCM_USE_PTHREAD_THREADS
if (automatic_finalization_p)
- {
- if (pipe2 (finalization_pipe, O_CLOEXEC) != 0)
- scm_syserror (NULL);
GC_set_finalizer_notifier (spawn_finalizer_thread);
- }
#endif
}
This bug report was last modified 4 years and 75 days ago.
Previous Next
GNU bug tracking system
Copyright (C) 1999 Darren O. Benham,
1997,2003 nCipher Corporation Ltd,
1994-97 Ian Jackson.