diff options
Diffstat (limited to 'modules/pam_unix/support.c')
-rw-r--r-- | modules/pam_unix/support.c | 18 |
1 files changed, 18 insertions, 0 deletions
diff --git a/modules/pam_unix/support.c b/modules/pam_unix/support.c index 5998c7db..98536d21 100644 --- a/modules/pam_unix/support.c +++ b/modules/pam_unix/support.c @@ -16,6 +16,7 @@ #include <limits.h> #include <utmp.h> #include <errno.h> +#include <signal.h> #include <security/_pam_macros.h> #include <security/pam_modules.h> @@ -434,6 +435,7 @@ static int _unix_run_helper_binary(pam_handle_t *pamh, const char *passwd, unsigned int ctrl, const char *user) { int retval, child, fds[2]; + void (*sighandler)(int) = NULL; D(("called.")); /* create a pipe for the password */ @@ -442,6 +444,18 @@ static int _unix_run_helper_binary(pam_handle_t *pamh, const char *passwd, return PAM_AUTH_ERR; } + if (off(UNIX_NOREAP, ctrl)) { + /* + * This code arranges that the demise of the child does not cause + * the application to receive a signal it is not expecting - which + * may kill the application or worse. + * + * The "noreap" module argument is provided so that the admin can + * override this behavior. + */ + sighandler = signal(SIGCHLD, SIG_IGN); + } + /* fork */ child = fork(); if (child == 0) { @@ -486,6 +500,10 @@ static int _unix_run_helper_binary(pam_handle_t *pamh, const char *passwd, retval = PAM_AUTH_ERR; } + if (sighandler != NULL) { + (void) signal(SIGCHLD, sighandler); /* restore old signal handler */ + } + D(("returning %d", retval)); return retval; } |