summaryrefslogtreecommitdiff
path: root/libguile/scmsigs.c
diff options
context:
space:
mode:
authorAndy Wingo <wingo@pobox.com>2011-06-23 11:23:46 +0200
committerAndy Wingo <wingo@pobox.com>2011-06-23 11:31:03 +0200
commit43adb591f4c3b30d2c59845f18f6fa19e1deeb54 (patch)
tree0d1a643147b7cd408fbd3ed505d0321001041b2d /libguile/scmsigs.c
parent78f0ef20a77dd745a8fa4c1ac1fae4d42b481adf (diff)
downloadguile-43adb591f4c3b30d2c59845f18f6fa19e1deeb54.tar.gz
allow gc <= 7.1 to stop the signal delivery thread
* configure.ac: Add a check for GC_get_suspend_signal(). * libguile/scmsigs.c (GC_get_suspend_signal): Define a fallback implementation if one isn't available. (signal_delivery_thread): Unmask the suspend signal so that GC can stop the world. Fixes test-pthread-create on libgc 7.1 and earlier. Thanks to Frank Terbeck <ft@bewatermyfriend.org> for the report.
Diffstat (limited to 'libguile/scmsigs.c')
-rw-r--r--libguile/scmsigs.c25
1 files changed, 25 insertions, 0 deletions
diff --git a/libguile/scmsigs.c b/libguile/scmsigs.c
index 723d6a8c5..c324aaa0f 100644
--- a/libguile/scmsigs.c
+++ b/libguile/scmsigs.c
@@ -150,6 +150,26 @@ struct signal_pipe_data
int err;
};
+#ifndef HAVE_GC_GET_SUSPEND_SIGNAL
+static int
+GC_get_suspend_signal (void)
+{
+#if defined SIG_SUSPEND
+ return SIG_SUSPEND;
+#elif defined SIGPWR
+ return SIGPWR;
+#elif defined SIGLOST
+ return SIGLOST;
+#elif defined _SIGRTMIN
+ return _SIGRTMIN + 6;
+#elif defined SIGRTMIN
+ return SIGRTMIN + 6;
+#else
+#error what suspend signal to use?
+#endif
+}
+#endif /* HAVE_GC_GET_SUSPEND_SIGNAL */
+
static void*
read_signal_pipe_data (void * data)
{
@@ -168,6 +188,11 @@ signal_delivery_thread (void *data)
#if HAVE_PTHREAD_SIGMASK /* not on mingw, see notes above */
sigset_t all_sigs;
sigfillset (&all_sigs);
+ /* On libgc 7.1 and earlier, GC_do_blocking doesn't actually do
+ anything. So in that case, libgc will want to suspend the signal
+ delivery thread, so we need to allow it to do so by unmasking the
+ suspend signal. */
+ sigdelset (&all_sigs, GC_get_suspend_signal ());
scm_i_pthread_sigmask (SIG_SETMASK, &all_sigs, NULL);
#endif