diff options
| author | Remi Collet <remi@remirepo.net> | 2020-10-23 11:52:25 +0200 | 
|---|---|---|
| committer | Remi Collet <remi@remirepo.net> | 2020-10-23 11:52:25 +0200 | 
| commit | 1c79973b425e1c44a99a009e6a32f248261b685c (patch) | |
| tree | e31fb7f9383cc8a757d3ea3b4f7197e70dade144 | |
| parent | 1f10869530a63314352e256178511ee2251f7934 (diff) | |
backport fix for https://bugs.php.net/74083 from 7.4
  master PHP-fpm is stopped on multiple reloads
| -rw-r--r-- | php-7.3.24-fpm.patch | 219 | ||||
| -rw-r--r-- | php.spec | 10 | 
2 files changed, 228 insertions, 1 deletions
| diff --git a/php-7.3.24-fpm.patch b/php-7.3.24-fpm.patch new file mode 100644 index 0000000..1165970 --- /dev/null +++ b/php-7.3.24-fpm.patch @@ -0,0 +1,219 @@ +Fix for https://bugs.php.net/74083 master PHP-fpm is stopped on multiple reloads +backported for 7.4 from + +From ae5154c6c6af7ba7c592f8af006b7cadd0d66d6e Mon Sep 17 00:00:00 2001 +From: Maksim Nikulin <mnikulin@plesk.com> +Date: Wed, 24 Jul 2019 16:50:57 +0700 +Subject: [PATCH] Block signals during fpm master initialization +  +From e37bd5dcc2e8f269c6031d86429311c8cf243060 Mon Sep 17 00:00:00 2001 +From: Maksim Nikulin <mnikulin@plesk.com> +Date: Mon, 21 Oct 2019 14:23:29 +0700 +Subject: [PATCH] Do not let PHP-FPM children miss SIGTERM, SIGQUIT + + +diff -up ./sapi/fpm/fpm/fpm_children.c.fpmsig ./sapi/fpm/fpm/fpm_children.c +--- ./sapi/fpm/fpm/fpm_children.c.fpmsig	2020-10-23 10:36:31.423925856 +0200 ++++ ./sapi/fpm/fpm/fpm_children.c	2020-10-23 10:36:38.872900642 +0200 +@@ -404,6 +404,11 @@ int fpm_children_make(struct fpm_worker_ + 			return 2; + 		} +  ++		zlog(ZLOG_DEBUG, "blocking signals before child birth"); ++		if (0 > fpm_signals_child_block()) { ++			zlog(ZLOG_WARNING, "child may miss signals"); ++		} ++ + 		pid = fork(); +  + 		switch (pid) { +@@ -415,12 +420,16 @@ int fpm_children_make(struct fpm_worker_ + 				return 0; +  + 			case -1 : ++				zlog(ZLOG_DEBUG, "unblocking signals"); ++				fpm_signals_unblock(); + 				zlog(ZLOG_SYSERROR, "fork() failed"); +  + 				fpm_resources_discard(child); + 				return 2; +  + 			default : ++				zlog(ZLOG_DEBUG, "unblocking signals, child born"); ++				fpm_signals_unblock(); + 				child->pid = pid; + 				fpm_clock_get(&child->started); + 				fpm_parent_resources_use(child); +diff -up ./sapi/fpm/fpm/fpm_main.c.fpmsig ./sapi/fpm/fpm/fpm_main.c +--- ./sapi/fpm/fpm/fpm_main.c.fpmsig	2020-10-13 11:27:02.000000000 +0200 ++++ ./sapi/fpm/fpm/fpm_main.c	2020-10-23 10:36:38.873900639 +0200 +@@ -90,6 +90,7 @@ int __riscosify_control = __RISCOSIFY_ST + #include "fpm.h" + #include "fpm_request.h" + #include "fpm_status.h" ++#include "fpm_signals.h" + #include "fpm_conf.h" + #include "fpm_php.h" + #include "fpm_log.h" +@@ -1584,6 +1585,11 @@ int main(int argc, char *argv[]) + 								closes it.  in apache|apxs mode apache + 								does that for us!  thies@thieso.net + 								20000419 */ ++ ++	if (0 > fpm_signals_init_mask() || 0 > fpm_signals_block()) { ++		zlog(ZLOG_WARNING, "Could die in the case of too early reload signal"); ++	} ++	zlog(ZLOG_DEBUG, "Blocked some signals"); + #endif + #endif +  +diff -up ./sapi/fpm/fpm/fpm_process_ctl.c.fpmsig ./sapi/fpm/fpm/fpm_process_ctl.c +--- ./sapi/fpm/fpm/fpm_process_ctl.c.fpmsig	2020-10-13 11:27:02.000000000 +0200 ++++ ./sapi/fpm/fpm/fpm_process_ctl.c	2020-10-23 10:36:11.921991864 +0200 +@@ -77,6 +77,10 @@ static void fpm_pctl_exit() /* {{{ */ +  + static void fpm_pctl_exec() /* {{{ */ + { ++	zlog(ZLOG_DEBUG, "Blocking some signals before reexec"); ++	if (0 > fpm_signals_block()) { ++		zlog(ZLOG_WARNING, "concurrent reloads may be unstable"); ++	} +  + 	zlog(ZLOG_NOTICE, "reloading: execvp(\"%s\", {\"%s\"" + 			"%s%s%s" "%s%s%s" "%s%s%s" "%s%s%s" "%s%s%s" +diff -up ./sapi/fpm/fpm/fpm_signals.c.fpmsig ./sapi/fpm/fpm/fpm_signals.c +--- ./sapi/fpm/fpm/fpm_signals.c.fpmsig	2020-10-13 11:27:02.000000000 +0200 ++++ ./sapi/fpm/fpm/fpm_signals.c	2020-10-23 10:36:38.873900639 +0200 +@@ -19,6 +19,8 @@ + #include "zlog.h" +  + static int sp[2]; ++static sigset_t block_sigset; ++static sigset_t child_block_sigset; +  + const char *fpm_signal_names[NSIG + 1] = { + #ifdef SIGHUP +@@ -165,8 +167,11 @@ static void sig_handler(int signo) /* {{ + 	int saved_errno; +  + 	if (fpm_globals.parent_pid != getpid()) { +-		/* prevent a signal race condition when child process +-			have not set up it's own signal handler yet */ ++		/* Avoid using of signal handlers from the master process in a worker ++			before the child sets up its own signal handlers. ++			Normally it is prevented by the sigprocmask() calls ++			around fork(). This execution branch is a last resort trap ++			that has no protection against #76601. */ + 		return; + 	} +  +@@ -210,6 +215,11 @@ int fpm_signals_init_main() /* {{{ */ + 		zlog(ZLOG_SYSERROR, "failed to init signals: sigaction()"); + 		return -1; + 	} ++ ++	zlog(ZLOG_DEBUG, "Unblocking all signals"); ++	if (0 > fpm_signals_unblock()) { ++		return -1; ++	} + 	return 0; + } + /* }}} */ +@@ -241,6 +251,10 @@ int fpm_signals_init_child() /* {{{ */ + 	} +  + 	zend_signal_init(); ++ ++	if (0 > fpm_signals_unblock()) { ++		return -1; ++	} + 	return 0; + } + /* }}} */ +@@ -250,3 +264,72 @@ int fpm_signals_get_fd() /* {{{ */ + 	return sp[0]; + } + /* }}} */ ++ ++int fpm_signals_init_mask() /* {{{ */ ++{ ++	/* Subset of signals from fpm_signals_init_main() and fpm_got_signal() ++		blocked to avoid unexpected death during early init ++		or during reload just after execvp() or fork */ ++	int init_signal_array[] = { SIGUSR1, SIGUSR2, SIGCHLD }; ++	size_t size = sizeof(init_signal_array)/sizeof(init_signal_array[0]); ++	size_t i = 0; ++	if (0 > sigemptyset(&block_sigset) || ++	    0 > sigemptyset(&child_block_sigset)) { ++		zlog(ZLOG_SYSERROR, "failed to prepare signal block mask: sigemptyset()"); ++		return -1; ++	} ++	for (i = 0; i < size; ++i) { ++		int sig_i = init_signal_array[i]; ++		if (0 > sigaddset(&block_sigset, sig_i) || ++		    0 > sigaddset(&child_block_sigset, sig_i)) { ++			if (sig_i <= NSIG && fpm_signal_names[sig_i] != NULL) { ++				zlog(ZLOG_SYSERROR, "failed to prepare signal block mask: sigaddset(%s)", ++						fpm_signal_names[sig_i]); ++			} else { ++				zlog(ZLOG_SYSERROR, "failed to prepare signal block mask: sigaddset(%d)", sig_i); ++			} ++			return -1; ++		} ++	} ++	if (0 > sigaddset(&child_block_sigset, SIGTERM) || ++	    0 > sigaddset(&child_block_sigset, SIGQUIT)) { ++		zlog(ZLOG_SYSERROR, "failed to prepare child signal block mask: sigaddset()"); ++		return -1; ++	} ++	return 0; ++} ++/* }}} */ ++ ++int fpm_signals_block() /* {{{ */ ++{ ++	if (0 > sigprocmask(SIG_BLOCK, &block_sigset, NULL)) { ++		zlog(ZLOG_SYSERROR, "failed to block signals"); ++		return -1; ++	} ++	return 0; ++} ++/* }}} */ ++ ++int fpm_signals_child_block() /* {{{ */ ++{ ++	if (0 > sigprocmask(SIG_BLOCK, &child_block_sigset, NULL)) { ++		zlog(ZLOG_SYSERROR, "failed to block child signals"); ++		return -1; ++	} ++	return 0; ++} ++/* }}} */ ++ ++int fpm_signals_unblock() /* {{{ */ ++{ ++	/* Ensure that during reload after upgrade all signals are unblocked. ++		block_sigset could have different value before execve() */ ++	sigset_t all_signals; ++	sigfillset(&all_signals); ++	if (0 > sigprocmask(SIG_UNBLOCK, &all_signals, NULL)) { ++		zlog(ZLOG_SYSERROR, "failed to unblock signals"); ++		return -1; ++	} ++	return 0; ++} ++/* }}} */ +diff -up ./sapi/fpm/fpm/fpm_signals.h.fpmsig ./sapi/fpm/fpm/fpm_signals.h +--- ./sapi/fpm/fpm/fpm_signals.h.fpmsig	2020-10-13 11:27:02.000000000 +0200 ++++ ./sapi/fpm/fpm/fpm_signals.h	2020-10-23 10:36:38.873900639 +0200 +@@ -8,6 +8,10 @@ + int fpm_signals_init_main(); + int fpm_signals_init_child(); + int fpm_signals_get_fd(); ++int fpm_signals_init_mask(); ++int fpm_signals_block(); ++int fpm_signals_child_block(); ++int fpm_signals_unblock(); +  + extern const char *fpm_signal_names[NSIG + 1]; +  @@ -141,7 +141,7 @@  Summary: PHP scripting language for creating dynamic web sites  Name:    %{?scl_prefix}php  Version: %{upver}%{?rcver:~%{rcver}} -Release: 1%{?dist} +Release: 2%{?dist}  # All files licensed under PHP version 3.01, except  # Zend is licensed under Zend  # TSRM is licensed under BSD @@ -195,6 +195,9 @@ Patch46: php-7.3.20-fixheader.patch  Patch47: php-7.3.20-phpinfo.patch  # backport PDOStatement::getColumnMeta from 7.4  Patch48: php-7.3.3-pdooci.patch +# backport FPM signals changes from 7.4 +# https://bugs.php.net/74083 master PHP-fpm is stopped on multiple reloads +Patch49: php-7.3.24-fpm.patch  # RC Patch  Patch91: php-7.2.0-oci8conf.patch @@ -962,6 +965,7 @@ sed -e 's/php-devel/%{?scl_prefix}php-devel/' -i scripts/phpize.in  %patch46 -p1 -b .fixheader  %patch47 -p1 -b .phpinfo  %patch48 -p1 -b .pdooci +%patch49 -p1 -b .fpmsig  %patch91 -p1 -b .remi-oci8 @@ -1919,6 +1923,10 @@ fi  %changelog +* Fri Oct 23 2020 Remi Collet <remi@remirepo.net> - 7.3.24~RC1-2 +- backport fix for https://bugs.php.net/74083 from 7.4 +  master PHP-fpm is stopped on multiple reloads +  * Tue Oct 13 2020 Remi Collet <remi@remirepo.net> - 7.3.24~RC1-1  - update to 7.3.24RC1 | 
