From b781b33a9eee9f2bdb70f8fc51f6d1ec5ebbbd02 Mon Sep 17 00:00:00 2001 From: Bruno Haible Date: Sat, 24 Sep 2011 01:07:22 +0200 Subject: [PATCH] sigprocmask: Avoid crashes through signal() on MSVC 9. * lib/sigprocmask.c: Include msvc-inval.h. (signal_nothrow): New function. (signal): Redefine it. * m4/signalblocking.m4 (gl_PREREQ_SIGPROCMASK): Require AC_C_INLINE. * modules/sigprocmask (Depends-on): Add msvc-inval. * doc/posix-functions/signal.texi: Mention the problem on MSVC. --- ChangeLog | 10 ++++++++++ doc/posix-functions/signal.texi | 3 +++ lib/sigprocmask.c | 25 +++++++++++++++++++++++++ m4/signalblocking.m4 | 6 ++++-- modules/sigprocmask | 1 + 5 files changed, 43 insertions(+), 2 deletions(-) diff --git a/ChangeLog b/ChangeLog index 5b399a918..32b8c040e 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,15 @@ 2011-09-23 Bruno Haible + sigprocmask: Avoid crashes through signal() on MSVC 9. + * lib/sigprocmask.c: Include msvc-inval.h. + (signal_nothrow): New function. + (signal): Redefine it. + * m4/signalblocking.m4 (gl_PREREQ_SIGPROCMASK): Require AC_C_INLINE. + * modules/sigprocmask (Depends-on): Add msvc-inval. + * doc/posix-functions/signal.texi: Mention the problem on MSVC. + +2011-09-23 Bruno Haible + Tests for module 'raise'. * modules/raise-tests: New file. * tests/test-raise.c: New file. diff --git a/doc/posix-functions/signal.texi b/doc/posix-functions/signal.texi index 3a32cc9c3..e6de69a4a 100644 --- a/doc/posix-functions/signal.texi +++ b/doc/posix-functions/signal.texi @@ -13,6 +13,9 @@ Portability problems fixed by Gnulib: Portability problems not fixed by Gnulib: @itemize @item +This function crashes when invoked with invalid arguments on some platforms: +MSVC 9. +@item On System V platforms, when the signal is triggered, the kernel uninstalls the handler (i.e.@: resets the signal's action to SIG_DFL) before invoking the handler. This opens the door to race conditions: undesired things happen diff --git a/lib/sigprocmask.c b/lib/sigprocmask.c index 6780a37b1..f1adc54e7 100644 --- a/lib/sigprocmask.c +++ b/lib/sigprocmask.c @@ -24,6 +24,8 @@ #include #include +#include "msvc-inval.h" + /* We assume that a platform without POSIX signal blocking functions also does not have the POSIX sigaction() function, only the signal() function. We also assume signal() has SysV semantics, @@ -58,6 +60,28 @@ typedef void (*handler_t) (int); +#if HAVE_MSVC_INVALID_PARAMETER_HANDLER +static inline handler_t +signal_nothrow (int sig, handler_t handler) +{ + handler_t result; + + TRY_MSVC_INVAL + { + result = signal (sig, handler); + } + CATCH_MSVC_INVAL + { + result = SIG_ERR; + errno = EINVAL; + } + DONE_MSVC_INVAL; + + return result; +} +# define signal signal_nothrow +#endif + /* Handling of gnulib defined signals. */ #if GNULIB_defined_SIGPIPE @@ -80,6 +104,7 @@ ext_signal (int sig, handler_t handler) return signal (sig, handler); } } +# undef signal # define signal ext_signal #endif diff --git a/m4/signalblocking.m4 b/m4/signalblocking.m4 index 15b74253b..eda856d04 100644 --- a/m4/signalblocking.m4 +++ b/m4/signalblocking.m4 @@ -1,4 +1,4 @@ -# signalblocking.m4 serial 12 +# signalblocking.m4 serial 13 dnl Copyright (C) 2001-2002, 2006-2011 Free Software Foundation, Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, @@ -22,4 +22,6 @@ AC_DEFUN([gl_SIGNALBLOCKING], ]) # Prerequisites of lib/sigprocmask.c. -AC_DEFUN([gl_PREREQ_SIGPROCMASK], [:]) +AC_DEFUN([gl_PREREQ_SIGPROCMASK], [ + AC_REQUIRE([AC_C_INLINE]) +]) diff --git a/modules/sigprocmask b/modules/sigprocmask index ba12f393b..cdcd17c6c 100644 --- a/modules/sigprocmask +++ b/modules/sigprocmask @@ -9,6 +9,7 @@ Depends-on: signal stdint [test $HAVE_POSIX_SIGNALBLOCKING = 0] raise [test $HAVE_POSIX_SIGNALBLOCKING = 0] +msvc-inval [test $HAVE_POSIX_SIGNALBLOCKING = 0] configure.ac: gl_SIGNALBLOCKING -- 2.11.0