1 diff -urNp -x '*.orig' php-5.2.17.org/configure.in php-5.2.17/configure.in
2 --- php-5.2.17.org/configure.in 2021-10-23 19:09:17.423125073 +0200
3 +++ php-5.2.17/configure.in 2021-10-23 19:09:19.823125073 +0200
4 @@ -295,6 +295,12 @@ if test "$enable_maintainer_zts" = "yes"
8 +if test "$PHP_FASTCGI" = "yes" -a "$PHP_FPM" = "yes"; then
9 + PHP_CONFIGURE_PART(Running FastCGI Process Manager checks)
10 + sinclude(sapi/cgi/fpm/acinclude.m4)
11 + sinclude(sapi/cgi/fpm/config.m4)
16 dnl ## In diversion 3 we check for compile-time options to the PHP
17 @@ -510,6 +516,7 @@ AC_CHECK_FUNCS(
25 @@ -1247,6 +1254,8 @@ PHP_SUBST_OLD(EXTENSION_DIR)
26 PHP_SUBST_OLD(EXTRA_LDFLAGS)
27 PHP_SUBST_OLD(EXTRA_LDFLAGS_PROGRAM)
28 PHP_SUBST_OLD(EXTRA_LIBS)
29 +PHP_SUBST_OLD(SAPI_EXTRA_LIBS)
30 +PHP_SUBST_OLD(SAPI_EXTRA_DEPS)
31 PHP_SUBST_OLD(ZEND_EXTRA_LIBS)
32 PHP_SUBST_OLD(INCLUDES)
33 PHP_SUBST_OLD(EXTRA_INCLUDES)
34 @@ -1343,7 +1352,7 @@ case $PHP_SAPI in
35 install_targets="$PHP_INSTALL_CLI_TARGET $install_targets"
38 - install_targets="install-sapi $PHP_INSTALL_CLI_TARGET $install_targets"
39 + install_targets="install-sapi $install_fpm $PHP_INSTALL_CLI_TARGET $install_targets"
43 diff -urNp -x '*.orig' php-5.2.17.org/main/php_config.h.in php-5.2.17/main/php_config.h.in
44 --- php-5.2.17.org/main/php_config.h.in 2011-01-07 00:04:47.000000000 +0100
45 +++ php-5.2.17/main/php_config.h.in 2021-10-23 19:09:19.826458407 +0200
47 /* Define if you have the chroot function. */
50 +/* Define if you have the clearenv function. */
53 /* Define if you have the crypt function. */
60 +/* Is experimental fastcgi process manager code activated */
61 +#undef PHP_FASTCGI_PM
64 #undef FORCE_CGI_REDIRECT
68 #undef ENABLE_PATHINFO_CHECK
70 +/* do we have libxml? */
73 +/* do we have prctl? */
76 +/* do we have clock_gettime? */
77 +#undef HAVE_CLOCK_GETTIME
79 +/* do we have clock_get_time? */
80 +#undef HAVE_CLOCK_GET_TIME
82 +/* do we have ptrace? */
85 +/* do we have mach_vm_read? */
86 +#undef HAVE_MACH_VM_READ
88 +/* /proc/pid/mem interface */
91 /* Define if system uses EBCDIC */
94 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/Makefile.frag php-5.2.17/sapi/cgi/Makefile.frag
95 --- php-5.2.17.org/sapi/cgi/Makefile.frag 2021-10-23 19:09:17.386458407 +0200
96 +++ php-5.2.17/sapi/cgi/Makefile.frag 2021-10-23 19:09:19.826458407 +0200
98 -$(SAPI_CGI_PATH): libphp_common.la $(PHP_SAPI_OBJS)
99 +$(SAPI_CGI_PATH): libphp_common.la $(PHP_SAPI_OBJS) $(SAPI_EXTRA_DEPS)
101 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/cgi_main.c php-5.2.17/sapi/cgi/cgi_main.c
102 --- php-5.2.17.org/sapi/cgi/cgi_main.c 2021-10-23 19:09:17.429791741 +0200
103 +++ php-5.2.17/sapi/cgi/cgi_main.c 2021-10-23 19:09:19.826458407 +0200
106 #include <sys/wait.h>
112 #include "zend_extensions.h"
114 @@ -85,6 +88,11 @@ int __riscosify_control = __RISCOSIFY_ST
119 +#include "fpm/fpm.h"
120 +#include "fpm/fpm_request.h"
124 /* XXX this will need to change later when threaded fastcgi is
125 implemented. shane */
126 @@ -122,8 +130,12 @@ static int parent_waiting = 0;
130 +static int request_body_fd;
134 +static char *sapi_cgibin_getenv(char *name, size_t name_len TSRMLS_DC);
136 #define PHP_MODE_STANDARD 1
137 #define PHP_MODE_HIGHLIGHT 2
138 #define PHP_MODE_INDENT 3
139 @@ -153,6 +165,10 @@ static const opt_struct OPTIONS[] = {
141 {'?', 0, "usage"},/* help alias (both '?' and 'usage') */
145 + {'y', 1, "fpm-config"},
147 {'z', 1, "zend-extension"},
150 @@ -177,6 +193,7 @@ typedef struct _php_cgi_globals_struct {
151 zend_bool impersonate;
154 + char *error_header;
155 } php_cgi_globals_struct;
158 @@ -481,7 +498,28 @@ static int sapi_cgi_read_post(char *buff
160 if (fcgi_is_fastcgi()) {
161 fcgi_request *request = (fcgi_request*) SG(server_context);
162 - tmp_read_bytes = fcgi_read(request, buffer + read_bytes, count_bytes - read_bytes);
164 + if (request_body_fd == -1) {
165 + char *request_body_filename = sapi_cgibin_getenv((char *) "REQUEST_BODY_FILE",
166 + sizeof("REQUEST_BODY_FILE")-1 TSRMLS_CC);
168 + if (request_body_filename && *request_body_filename) {
169 + request_body_fd = open(request_body_filename, O_RDONLY);
171 + if (0 > request_body_fd) {
172 + php_error(E_WARNING, "REQUEST_BODY_FILE: open('%s') failed: %s (%d)",
173 + request_body_filename, strerror(errno), errno);
179 + /* If REQUEST_BODY_FILE variable not available - read post body from fastcgi stream */
180 + if (request_body_fd < 0) {
181 + tmp_read_bytes = fcgi_read(request, buffer + read_bytes, count_bytes - read_bytes);
183 + tmp_read_bytes = read(request_body_fd, buffer + read_bytes, count_bytes - read_bytes);
186 tmp_read_bytes = read(STDIN_FILENO, buffer + read_bytes, count_bytes - read_bytes);
188 @@ -796,7 +834,12 @@ static void php_cgi_usage(char *argv0)
189 " -s Display colour syntax highlighted source.\n"
190 " -v Version number\n"
191 " -w Display source with stripped comments and whitespace.\n"
192 - " -z <file> Load Zend extension <file>.\n"
194 + " -x, --fpm Run in FastCGI process manager mode.\n"
195 + " -y, --fpm-config <file>\n"
196 + " Specify alternative path to FastCGI process manager config file.\n"
198 + " -z <file> Load Zend extension <file>.\n"
200 " -T <count> Measure execution time of script repeated <count> times.\n"
202 @@ -1262,6 +1305,7 @@ PHP_INI_BEGIN()
204 STD_PHP_INI_ENTRY("fastcgi.impersonate", "0", PHP_INI_SYSTEM, OnUpdateBool, impersonate, php_cgi_globals_struct, php_cgi_globals)
206 + STD_PHP_INI_ENTRY("fastcgi.error_header", NULL, PHP_INI_SYSTEM, OnUpdateString, error_header, php_cgi_globals_struct, php_cgi_globals)
210 @@ -1284,6 +1328,7 @@ static void php_cgi_globals_ctor(php_cgi
212 php_cgi_globals->impersonate = 0;
214 + php_cgi_globals->error_header = NULL;
218 @@ -1316,9 +1361,47 @@ static PHP_MSHUTDOWN_FUNCTION(cgi)
219 static PHP_MINFO_FUNCTION(cgi)
221 DISPLAY_INI_ENTRIES();
225 +#include "fpm/fpm_autoconf.h"
227 + php_info_print_table_start();
228 + php_info_print_table_row(2, "php-fpm", fpm ? "active" : "inactive");
229 + php_info_print_table_row(2, "php-fpm version", PHP_FPM_VERSION);
230 + php_info_print_table_end();
237 +PHP_FUNCTION(fastcgi_finish_request)
239 + fcgi_request *request = (fcgi_request*) SG(server_context);
241 + if (fcgi_is_fastcgi() && request->fd >= 0) {
243 + php_end_ob_buffers(1 TSRMLS_CC);
244 + php_header(TSRMLS_C);
246 + fcgi_flush(request, 1);
247 + fcgi_close(request, 0, 0);
256 +function_entry cgi_fcgi_sapi_functions[] = {
258 + PHP_FE(fastcgi_finish_request, NULL)
263 static zend_module_entry cgi_module_entry = {
264 STANDARD_MODULE_HEADER,
266 @@ -1326,7 +1409,7 @@ static zend_module_entry cgi_module_entr
271 + cgi_fcgi_sapi_functions,
275 @@ -1365,6 +1448,7 @@ int main(int argc, char *argv[])
276 int fastcgi = fcgi_is_fastcgi();
277 char *bindpath = NULL;
278 fcgi_request request;
279 + char *fpm_config = NULL;
282 #if HAVE_GETTIMEOFDAY
283 @@ -1502,6 +1586,14 @@ int main(int argc, char *argv[])
284 case 's': /* generate highlighted HTML from source */
285 behavior = PHP_MODE_HIGHLIGHT;
289 + fpm_config = php_optarg;
298 @@ -1566,6 +1658,19 @@ consult the installation file that came
299 #endif /* FORCE_CGI_REDIRECT */
304 + if (0 > fpm_init(argc, argv, fpm_config)) {
308 + fcgi_fd = fpm_run(&max_requests);
310 + fcgi_set_is_fastcgi(fastcgi = 1);
316 fcgi_fd = fcgi_listen(bindpath, 128);
318 @@ -1580,6 +1685,9 @@ consult the installation file that came
321 /* How many times to run PHP scripts before dying */
325 if (getenv("PHP_FCGI_MAX_REQUESTS")) {
326 max_requests = atoi(getenv("PHP_FCGI_MAX_REQUESTS"));
327 if (max_requests < 0) {
328 @@ -1597,6 +1705,9 @@ consult the installation file that came
331 /* Pre-fork, if required */
335 if (getenv("PHP_FCGI_CHILDREN")) {
336 char * children_str = getenv("PHP_FCGI_CHILDREN");
337 children = atoi(children_str);
338 @@ -1754,6 +1865,8 @@ consult the installation file that came
342 + request_body_fd = -1;
344 SG(server_context) = (void *) &request;
346 SG(server_context) = (void *) 1; /* avoid server_context==NULL checks */
347 @@ -1761,6 +1874,10 @@ consult the installation file that came
348 init_request_info(TSRMLS_C);
352 + if (fpm) fpm_request_info();
358 @@ -2043,6 +2160,10 @@ consult the installation file that came
363 + if (fpm) fpm_request_executing();
367 case PHP_MODE_STANDARD:
368 php_execute_script(&file_handle TSRMLS_CC);
369 @@ -2095,6 +2216,10 @@ consult the installation file that came
372 fastcgi_request_done:
374 + if (request_body_fd != -1) close(request_body_fd);
376 + request_body_fd = -2;
379 char *path_translated;
380 @@ -2108,6 +2233,16 @@ fastcgi_request_done:
381 SG(request_info).path_translated = path_translated;
384 + if (EG(exit_status) == 255) {
385 + if (CGIG(error_header) && *CGIG(error_header)) {
386 + sapi_header_line ctr = {0};
388 + ctr.line = CGIG(error_header);
389 + ctr.line_len = strlen(CGIG(error_header));
390 + sapi_header_op(SAPI_HEADER_REPLACE, &ctr TSRMLS_CC);
394 php_request_shutdown((void *) 0);
395 if (exit_status == 0) {
396 exit_status = EG(exit_status);
397 @@ -2145,15 +2280,20 @@ fastcgi_request_done:
401 - if (max_requests != 1) {
402 - /* no need to return exit_status of the last request */
407 /* end of fastcgi loop */
411 + if (fcgi_in_shutdown() || /* graceful shutdown by a signal */
412 + (max_requests && (requests == max_requests)) /* we were told to process max_requests and we are done */
421 if (cgi_sapi_module.php_ini_path_override) {
422 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/config9.m4 php-5.2.17/sapi/cgi/config9.m4
423 --- php-5.2.17.org/sapi/cgi/config9.m4 2021-10-23 19:09:17.386458407 +0200
424 +++ php-5.2.17/sapi/cgi/config9.m4 2021-10-23 19:09:19.826458407 +0200
425 @@ -22,6 +22,10 @@ PHP_ARG_ENABLE(path-info-check,,
426 [ --disable-path-info-check CGI: If this is disabled, paths such as
427 /info.php/test?a=b will fail to work], yes, no)
429 +PHP_ARG_ENABLE(fpm,,
430 +[ --enable-fpm FastCGI: If this is enabled, the fastcgi support
431 + will include experimental process manager code], no, no)
436 @@ -54,6 +58,20 @@ if test "$PHP_SAPI" = "default"; then
437 AC_DEFINE_UNQUOTED(PHP_FASTCGI, $PHP_ENABLE_FASTCGI, [ ])
438 AC_MSG_RESULT($PHP_FASTCGI)
441 + if test "$PHP_FASTCGI" = "yes"; then
442 + AC_MSG_CHECKING(whether to enable FastCGI Process Manager)
443 + if test "$PHP_FPM" = "yes"; then
448 + AC_MSG_RESULT($PHP_FPM)
452 + AC_DEFINE_UNQUOTED(PHP_FASTCGI_PM, $PHP_FASTCGI_PM, [Is experimental fastcgi process manager code activated])
454 dnl --enable-force-cgi-redirect
455 AC_MSG_CHECKING(whether to force Apache CGI redirect)
456 if test "$PHP_FORCE_CGI_REDIRECT" = "yes"; then
457 @@ -93,10 +111,10 @@ if test "$PHP_SAPI" = "default"; then
458 BUILD_CGI="echo '\#! .' > php.sym && echo >>php.sym && nm -BCpg \`echo \$(PHP_GLOBAL_OBJS) \$(PHP_SAPI_OBJS) | sed 's/\([A-Za-z0-9_]*\)\.lo/\1.o/g'\` | \$(AWK) '{ if (((\$\$2 == \"T\") || (\$\$2 == \"D\") || (\$\$2 == \"B\")) && (substr(\$\$3,1,1) != \".\")) { print \$\$3 } }' | sort -u >> php.sym && \$(LIBTOOL) --mode=link \$(CC) -export-dynamic \$(CFLAGS_CLEAN) \$(EXTRA_CFLAGS) \$(EXTRA_LDFLAGS_PROGRAM) \$(LDFLAGS) -Wl,-brtl -Wl,-bE:php.sym \$(PHP_RPATHS) \$(PHP_GLOBAL_OBJS) \$(PHP_SAPI_OBJS) \$(EXTRA_LIBS) \$(ZEND_EXTRA_LIBS) -o \$(SAPI_CGI_PATH)"
461 - BUILD_CGI="\$(CC) \$(CFLAGS_CLEAN) \$(EXTRA_CFLAGS) \$(EXTRA_LDFLAGS_PROGRAM) \$(LDFLAGS) \$(NATIVE_RPATHS) \$(PHP_GLOBAL_OBJS:.lo=.o) \$(PHP_SAPI_OBJS:.lo=.o) \$(PHP_FRAMEWORKS) \$(EXTRA_LIBS) \$(ZEND_EXTRA_LIBS) -o \$(SAPI_CGI_PATH)"
462 + BUILD_CGI="\$(CC) \$(CFLAGS_CLEAN) \$(EXTRA_CFLAGS) \$(EXTRA_LDFLAGS_PROGRAM) \$(LDFLAGS) \$(NATIVE_RPATHS) \$(PHP_GLOBAL_OBJS:.lo=.o) \$(PHP_SAPI_OBJS:.lo=.o) \$(PHP_FRAMEWORKS) \$(EXTRA_LIBS) \$(SAPI_EXTRA_LIBS) \$(ZEND_EXTRA_LIBS) -o \$(SAPI_CGI_PATH)"
465 - BUILD_CGI="\$(LIBTOOL) --mode=link \$(CC) -export-dynamic \$(CFLAGS_CLEAN) \$(EXTRA_CFLAGS) \$(EXTRA_LDFLAGS_PROGRAM) \$(LDFLAGS) \$(PHP_RPATHS) libphp_common.la \$(PHP_SAPI_OBJS) \$(EXTRA_LIBS) \$(ZEND_EXTRA_LIBS) -o \$(SAPI_CGI_PATH)"
466 + BUILD_CGI="\$(LIBTOOL) --mode=link \$(CC) -export-dynamic \$(CFLAGS_CLEAN) \$(EXTRA_CFLAGS) \$(EXTRA_LDFLAGS_PROGRAM) \$(LDFLAGS) \$(PHP_RPATHS) libphp_common.la \$(PHP_SAPI_OBJS) \$(EXTRA_LIBS) \$(SAPI_EXTRA_LIBS) \$(ZEND_EXTRA_LIBS) -o \$(SAPI_CGI_PATH)"
470 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fastcgi.c php-5.2.17/sapi/cgi/fastcgi.c
471 --- php-5.2.17.org/sapi/cgi/fastcgi.c 2010-01-03 10:23:27.000000000 +0100
472 +++ php-5.2.17/sapi/cgi/fastcgi.c 2021-10-23 19:09:19.826458407 +0200
478 +#include "fpm/fpm.h"
479 +#include "fpm/fpm_request.h"
485 @@ -234,6 +239,8 @@ int fcgi_init(void)
487 return is_fastcgi = 0;
490 + fcgi_set_allowed_clients(getenv("FCGI_WEB_SERVER_ADDRS"));
494 @@ -249,14 +256,26 @@ int fcgi_is_fastcgi(void)
498 +void fcgi_set_is_fastcgi(int new_value)
500 + is_fastcgi = new_value;
503 +void fcgi_set_in_shutdown(int new_value)
505 + in_shutdown = new_value;
508 void fcgi_shutdown(void)
510 if (is_initialized) {
511 zend_hash_destroy(&fcgi_mgmt_vars);
515 if (allowed_clients) {
516 free(allowed_clients);
517 + allowed_clients = 0;
521 @@ -330,6 +349,41 @@ out_fail:
525 +void fcgi_set_allowed_clients(char *ip)
535 + if (*cur == ',') n++;
538 + if (allowed_clients) free(allowed_clients);
539 + allowed_clients = malloc(sizeof(in_addr_t) * (n+2));
543 + end = strchr(cur, ',');
548 + allowed_clients[n] = inet_addr(cur);
549 + if (allowed_clients[n] == INADDR_NONE) {
550 + fprintf(stderr, "Wrong IP address '%s' in FCGI_WEB_SERVER_ADDRS\n", cur);
555 + allowed_clients[n] = INADDR_NONE;
560 static int is_port_number(const char *bindpath)
563 @@ -458,38 +512,6 @@ int fcgi_listen(const char *path, int ba
568 - char *ip = getenv("FCGI_WEB_SERVER_ADDRS");
577 - if (*cur == ',') n++;
580 - allowed_clients = malloc(sizeof(in_addr_t) * (n+2));
584 - end = strchr(cur, ',');
589 - allowed_clients[n] = inet_addr(cur);
590 - if (allowed_clients[n] == INADDR_NONE) {
591 - fprintf(stderr, "Wrong IP address '%s' in FCGI_WEB_SERVER_ADDRS\n", cur);
596 - allowed_clients[n] = INADDR_NONE;
601 if (!is_initialized) {
602 @@ -866,7 +888,7 @@ int fcgi_read(fcgi_request *req, char *s
606 -static inline void fcgi_close(fcgi_request *req, int force, int destroy)
607 +void fcgi_close(fcgi_request *req, int force, int destroy)
610 zend_hash_destroy(&req->env);
611 @@ -906,6 +928,10 @@ static inline void fcgi_close(fcgi_reque
617 + if (fpm) fpm_request_finished();
622 @@ -953,6 +979,10 @@ int fcgi_accept_request(fcgi_request *re
624 socklen_t len = sizeof(sa);
627 + if (fpm) fpm_request_accepting();
630 FCGI_LOCK(req->listen_socket);
631 req->fd = accept(listen_socket, (struct sockaddr *)&sa, &len);
632 FCGI_UNLOCK(req->listen_socket);
633 @@ -988,6 +1018,11 @@ int fcgi_accept_request(fcgi_request *re
639 + if (fpm) fpm_request_reading_headers();
642 #if defined(HAVE_SYS_POLL_H) && defined(HAVE_POLL)
645 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fastcgi.h php-5.2.17/sapi/cgi/fastcgi.h
646 --- php-5.2.17.org/sapi/cgi/fastcgi.h 2010-01-03 10:23:27.000000000 +0100
647 +++ php-5.2.17/sapi/cgi/fastcgi.h 2021-10-23 19:09:19.826458407 +0200
648 @@ -114,6 +114,9 @@ typedef struct _fcgi_request {
650 void fcgi_shutdown(void);
651 int fcgi_is_fastcgi(void);
652 +void fcgi_set_is_fastcgi(int);
653 +void fcgi_set_in_shutdown(int);
654 +void fcgi_set_allowed_clients(char *);
655 int fcgi_in_shutdown(void);
656 int fcgi_listen(const char *path, int backlog);
657 void fcgi_init_request(fcgi_request *req, int listen_socket);
658 @@ -128,6 +131,8 @@ int fcgi_read(fcgi_request *req, char *s
659 int fcgi_write(fcgi_request *req, fcgi_request_type type, const char *str, int len);
660 int fcgi_flush(fcgi_request *req, int close);
662 +void fcgi_close(fcgi_request *req, int force, int destroy);
665 void fcgi_impersonate(void);
667 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/Makefile.frag php-5.2.17/sapi/cgi/fpm/Makefile.frag
668 --- php-5.2.17.org/sapi/cgi/fpm/Makefile.frag 1970-01-01 01:00:00.000000000 +0100
669 +++ php-5.2.17/sapi/cgi/fpm/Makefile.frag 2021-10-23 19:09:19.826458407 +0200
672 +install-fpm: sapi/cgi/fpm/php-fpm.conf sapi/cgi/fpm/php-fpm
673 + @echo "Installing FPM config: $(INSTALL_ROOT)$(php_fpm_conf_path)"
674 + -@$(mkinstalldirs) \
675 + $(INSTALL_ROOT)$(prefix)/sbin \
676 + `dirname "$(INSTALL_ROOT)$(php_fpm_conf_path)"` \
677 + `dirname "$(INSTALL_ROOT)$(php_fpm_log_path)"` \
678 + `dirname "$(INSTALL_ROOT)$(php_fpm_pid_path)"`
679 + -@if test -r "$(INSTALL_ROOT)$(php_fpm_conf_path)" ; then \
680 + dest=`basename "$(php_fpm_conf_path)"`.default ; \
681 + echo " (installing as $$dest)" ; \
683 + dest=`basename "$(php_fpm_conf_path)"` ; \
685 + $(INSTALL_DATA) $(top_builddir)/sapi/cgi/fpm/php-fpm.conf $(INSTALL_ROOT)`dirname "$(php_fpm_conf_path)"`/$$dest
686 + @echo "Installing init.d script: $(INSTALL_ROOT)$(prefix)/sbin/php-fpm"
687 + -@$(INSTALL) -m 0755 $(top_builddir)/sapi/cgi/fpm/php-fpm $(INSTALL_ROOT)$(prefix)/sbin/php-fpm
689 +$(top_builddir)/libevent/libevent.a: $(top_builddir)/libevent/Makefile
690 + cd $(top_builddir)/libevent && $(MAKE) libevent.a
692 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/acinclude.m4 php-5.2.17/sapi/cgi/fpm/acinclude.m4
693 --- php-5.2.17.org/sapi/cgi/fpm/acinclude.m4 1970-01-01 01:00:00.000000000 +0100
694 +++ php-5.2.17/sapi/cgi/fpm/acinclude.m4 2021-10-23 19:09:19.826458407 +0200
697 +AC_DEFUN([AC_FPM_CHECK_FUNC],
699 + SAVED_CFLAGS="$CFLAGS"
700 + CFLAGS="$CFLAGS $2"
704 + AC_CHECK_FUNC([$1],[$4],[$5])
706 + CFLAGS="$SAVED_CFLAGS"
710 +AC_DEFUN([AC_FPM_LIBEVENT],
712 + AC_ARG_WITH([libevent],
713 + [ --with-libevent=DIR FPM: libevent install directory])
716 + LIBEVENT_LIBS="-levent"
717 + LIBEVENT_INCLUDE_PATH=""
719 + if test "$with_libevent" != "no" -a -n "$with_libevent"; then
720 + LIBEVENT_CFLAGS="-I$with_libevent/include"
721 + LIBEVENT_LIBS="-L$with_libevent/lib $LIBEVENT_LIBS"
722 + LIBEVENT_INCLUDE_PATH="$with_libevent/include"
725 + AC_MSG_CHECKING([for event.h])
729 + for dir in "$LIBEVENT_INCLUDE_PATH" /usr/include ; do
730 + if test -r "$dir/event.h" ; then
736 + AC_MSG_RESULT([$found])
738 + AC_FPM_CHECK_FUNC([event_set], [$LIBEVENT_CFLAGS], [$LIBEVENT_LIBS], ,
739 + [AC_MSG_ERROR([Failed to link with libevent. Perhaps --with-libevent=DIR option could help.])])
741 + AC_FPM_CHECK_FUNC([event_base_free], [$LIBEVENT_CFLAGS], [$LIBEVENT_LIBS], ,
742 + [AC_MSG_ERROR([You have too old version. libevent version >= 1.2 is required.])])
746 +AC_DEFUN([AC_FPM_LIBXML],
748 + AC_MSG_RESULT([checking for XML configuration])
750 + AC_ARG_WITH(xml-config,
751 + [ --with-xml-config=PATH FPM: use xml-config in PATH to find libxml],
752 + [XMLCONFIG="$withval"],
753 + [AC_PATH_PROGS(XMLCONFIG, [xml2-config xml-config], "")]
756 + if test "x$XMLCONFIG" = "x"; then
757 + AC_MSG_ERROR([XML configuration could not be found])
759 + AC_MSG_CHECKING([for libxml library])
761 + if test ! -x "$XMLCONFIG"; then
762 + AC_MSG_ERROR([$XMLCONFIG cannot be executed])
765 + LIBXML_LIBS="`$XMLCONFIG --libs`"
766 + LIBXML_CFLAGS="`$XMLCONFIG --cflags`"
767 + LIBXML_VERSION="`$XMLCONFIG --version`"
769 + AC_MSG_RESULT([yes, $LIBXML_VERSION])
771 + AC_FPM_CHECK_FUNC([xmlParseFile], [$LIBXML_CFLAGS], [$LIBXML_LIBS], ,
772 + [AC_MSG_ERROR([Failed to link with libxml])])
774 + AC_DEFINE(HAVE_LIBXML, 1, [do we have libxml?])
778 +AC_DEFUN([AC_FPM_JUDY],
780 + AC_ARG_WITH([Judy],
781 + [ --with-Judy=DIR FPM: Judy install directory])
785 + JUDY_INCLUDE_PATH=""
787 + if test "$with_Judy" != "no" -a -n "$with_Judy"; then
788 + JUDY_INCLUDE_PATH="$with_Judy/include"
789 + JUDY_CFLAGS="-I$with_Judy/include $JUDY_CFLAGS"
790 + JUDY_LIBS="-L$with_Judy/lib $JUDY_LIBS"
793 + AC_MSG_CHECKING([for Judy.h])
797 + for dir in "$JUDY_INCLUDE_PATH" /usr/include ; do
798 + if test -r "$dir/Judy.h" ; then
804 + AC_MSG_RESULT([$found])
806 + AC_FPM_CHECK_FUNC([JudyLCount], [$JUDY_CFLAGS], [$JUDY_LIBS], ,
807 + [AC_MSG_ERROR([Failed to link with Judy])])
811 +AC_DEFUN([AC_FPM_CLOCK],
813 + have_clock_gettime=no
815 + AC_MSG_CHECKING([for clock_gettime])
817 + AC_TRY_LINK([ #include <time.h> ], [struct timespec ts; clock_gettime(CLOCK_MONOTONIC, &ts);], [
818 + have_clock_gettime=yes
819 + AC_MSG_RESULT([yes])
821 + AC_MSG_RESULT([no])
824 + if test "$have_clock_gettime" = "no"; then
825 + AC_MSG_CHECKING([for clock_gettime in -lrt])
830 + AC_TRY_LINK([ #include <time.h> ], [struct timespec ts; clock_gettime(CLOCK_MONOTONIC, &ts);], [
831 + have_clock_gettime=yes
832 + AC_MSG_RESULT([yes])
835 + AC_MSG_RESULT([no])
839 + if test "$have_clock_gettime" = "yes"; then
840 + AC_DEFINE([HAVE_CLOCK_GETTIME], 1, [do we have clock_gettime?])
843 + have_clock_get_time=no
845 + if test "$have_clock_gettime" = "no"; then
846 + AC_MSG_CHECKING([for clock_get_time])
848 + AC_TRY_RUN([ #include <mach/mach.h>
849 + #include <mach/clock.h>
850 + #include <mach/mach_error.h>
854 + kern_return_t ret; clock_serv_t aClock; mach_timespec_t aTime;
855 + ret = host_get_clock_service(mach_host_self(), REALTIME_CLOCK, &aClock);
857 + if (ret != KERN_SUCCESS) {
861 + ret = clock_get_time(aClock, &aTime);
862 + if (ret != KERN_SUCCESS) {
869 + have_clock_get_time=yes
870 + AC_MSG_RESULT([yes])
872 + AC_MSG_RESULT([no])
876 + if test "$have_clock_get_time" = "yes"; then
877 + AC_DEFINE([HAVE_CLOCK_GET_TIME], 1, [do we have clock_get_time?])
881 +AC_DEFUN([AC_FPM_TRACE],
884 + have_broken_ptrace=no
886 + AC_MSG_CHECKING([for ptrace])
889 + #include <sys/types.h>
890 + #include <sys/ptrace.h> ], [ptrace(0, 0, (void *) 0, 0);], [
892 + AC_MSG_RESULT([yes])
894 + AC_MSG_RESULT([no])
897 + if test "$have_ptrace" = "yes"; then
898 + AC_MSG_CHECKING([whether ptrace works])
901 + #include <unistd.h>
902 + #include <signal.h>
903 + #include <sys/wait.h>
904 + #include <sys/types.h>
905 + #include <sys/ptrace.h>
908 + #if !defined(PTRACE_ATTACH) && defined(PT_ATTACH)
909 + #define PTRACE_ATTACH PT_ATTACH
912 + #if !defined(PTRACE_DETACH) && defined(PT_DETACH)
913 + #define PTRACE_DETACH PT_DETACH
916 + #if !defined(PTRACE_PEEKDATA) && defined(PT_READ_D)
917 + #define PTRACE_PEEKDATA PT_READ_D
922 + long v1 = (unsigned int) -1; /* copy will fail if sizeof(long) == 8 and we've got "int ptrace()" */
927 + if ( (child = fork()) ) { /* parent */
930 + if (0 > ptrace(PTRACE_ATTACH, child, 0, 0)) {
934 + waitpid(child, &status, 0);
937 + struct ptrace_io_desc ptio = {
938 + .piod_op = PIOD_READ_D,
941 + .piod_len = sizeof(v1)
944 + if (0 > ptrace(PT_IO, child, (void *) &ptio, 0)) {
950 + v2 = ptrace(PTRACE_PEEKDATA, child, (void *) &v1, 0);
956 + ptrace(PTRACE_DETACH, child, (void *) 1, 0);
958 + kill(child, SIGKILL);
960 + return ret ? ret : (v1 != v2);
968 + AC_MSG_RESULT([yes])
971 + have_broken_ptrace=yes
972 + AC_MSG_RESULT([no])
976 + if test "$have_ptrace" = "yes"; then
977 + AC_DEFINE([HAVE_PTRACE], 1, [do we have ptrace?])
980 + have_mach_vm_read=no
982 + if test "$have_broken_ptrace" = "yes"; then
983 + AC_MSG_CHECKING([for mach_vm_read])
985 + AC_TRY_COMPILE([ #include <mach/mach.h>
986 + #include <mach/mach_vm.h>
988 + mach_vm_read((vm_map_t)0, (mach_vm_address_t)0, (mach_vm_size_t)0, (vm_offset_t *)0, (mach_msg_type_number_t*)0);
990 + have_mach_vm_read=yes
991 + AC_MSG_RESULT([yes])
993 + AC_MSG_RESULT([no])
997 + if test "$have_mach_vm_read" = "yes"; then
998 + AC_DEFINE([HAVE_MACH_VM_READ], 1, [do we have mach_vm_read?])
1003 + if test -r /proc/$$/mem ; then
1004 + proc_mem_file="mem"
1006 + if test -r /proc/$$/as ; then
1007 + proc_mem_file="as"
1011 + if test -n "$proc_mem_file" ; then
1012 + AC_MSG_CHECKING([for proc mem file])
1015 + #define _GNU_SOURCE
1016 + #define _FILE_OFFSET_BITS 64
1017 + #include <stdint.h>
1018 + #include <unistd.h>
1019 + #include <sys/types.h>
1020 + #include <sys/stat.h>
1021 + #include <fcntl.h>
1022 + #include <stdio.h>
1025 + long v1 = (unsigned int) -1, v2 = 0;
1028 + sprintf(buf, "/proc/%d/$proc_mem_file", getpid());
1029 + fd = open(buf, O_RDONLY);
1033 + if (sizeof(long) != pread(fd, &v2, sizeof(long), (uintptr_t) &v1)) {
1041 + AC_MSG_RESULT([$proc_mem_file])
1044 + AC_MSG_RESULT([no])
1048 + if test -n "$proc_mem_file"; then
1049 + AC_DEFINE_UNQUOTED([PROC_MEM_FILE], "$proc_mem_file", [/proc/pid/mem interface])
1052 + if test "$have_ptrace" = "yes"; then
1053 + FPM_SOURCES="$FPM_SOURCES fpm_trace.c fpm_trace_ptrace.c"
1054 + elif test -n "$proc_mem_file"; then
1055 + FPM_SOURCES="$FPM_SOURCES fpm_trace.c fpm_trace_pread.c"
1056 + elif test "$have_mach_vm_read" = "yes" ; then
1057 + FPM_SOURCES="$FPM_SOURCES fpm_trace.c fpm_trace_mach.c"
1062 +AC_DEFUN([AC_FPM_PRCTL],
1064 + AC_MSG_CHECKING([for prctl])
1066 + AC_TRY_COMPILE([ #include <sys/prctl.h> ], [prctl(0, 0, 0, 0, 0);], [
1067 + AC_DEFINE([HAVE_PRCTL], 1, [do we have prctl?])
1068 + AC_MSG_RESULT([yes])
1070 + AC_MSG_RESULT([no])
1073 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/conf/php-fpm.conf.in php-5.2.17/sapi/cgi/fpm/conf/php-fpm.conf.in
1074 --- php-5.2.17.org/sapi/cgi/fpm/conf/php-fpm.conf.in 1970-01-01 01:00:00.000000000 +0100
1075 +++ php-5.2.17/sapi/cgi/fpm/conf/php-fpm.conf.in 2021-10-23 19:09:19.829791741 +0200
1077 +<?xml version="1.0" ?>
1080 + All relative paths in this config are relative to php's install prefix
1082 + <section name="global_options">
1085 + <value name="pid_file">@php_fpm_pid_path@</value>
1088 + <value name="error_log">@php_fpm_log_path@</value>
1091 + <value name="log_level">notice</value>
1093 + When this amount of php processes exited with SIGSEGV or SIGBUS ...
1094 + <value name="emergency_restart_threshold">10</value>
1096 + ... in a less than this interval of time, a graceful restart will be initiated.
1097 + Useful to work around accidental curruptions in accelerator's shared memory.
1098 + <value name="emergency_restart_interval">1m</value>
1100 + Time limit on waiting child's reaction on signals from master
1101 + <value name="process_control_timeout">5s</value>
1103 + Set to 'no' to debug fpm
1104 + <value name="daemonize">yes</value>
1110 + <section name="pool">
1112 + Name of pool. Used in logs and stats.
1113 + <value name="name">default</value>
1115 + Address to accept fastcgi requests on.
1116 + Valid syntax is 'ip.ad.re.ss:port' or just 'port' or '/path/to/unix/socket'
1117 + <value name="listen_address">127.0.0.1:9000</value>
1119 + <value name="listen_options">
1121 + Set listen(2) backlog
1122 + <value name="backlog">-1</value>
1124 + Set permissions for unix socket, if one used.
1125 + In Linux read/write permissions must be set in order to allow connections from web server.
1126 + Many BSD-derrived systems allow connections regardless of permissions.
1127 + <value name="owner"></value>
1128 + <value name="group"></value>
1129 + <value name="mode">0666</value>
1132 + Additional php.ini defines, specific to this pool of workers.
1133 + <value name="php_defines">
1134 + <!-- <value name="sendmail_path">/usr/sbin/sendmail -t -i</value> -->
1135 + <!-- <value name="display_errors">0</value> -->
1138 + Unix user of processes
1139 + <!-- <value name="user">nobody</value> -->
1141 + Unix group of processes
1142 + <!-- <value name="group">@php_fpm_group@</value> -->
1144 + Process manager settings
1147 + Sets style of controling worker process count.
1148 + Valid values are 'static' and 'apache-like'
1149 + <value name="style">static</value>
1151 + Sets the limit on the number of simultaneous requests that will be served.
1152 + Equivalent to Apache MaxClients directive.
1153 + Equivalent to PHP_FCGI_CHILDREN environment in original php.fcgi
1154 + Used with any pm_style.
1155 + <value name="max_children">5</value>
1157 + Settings group for 'apache-like' pm style
1158 + <value name="apache_like">
1160 + Sets the number of server processes created on startup.
1161 + Used only when 'apache-like' pm_style is selected
1162 + <value name="StartServers">20</value>
1164 + Sets the desired minimum number of idle server processes.
1165 + Used only when 'apache-like' pm_style is selected
1166 + <value name="MinSpareServers">5</value>
1168 + Sets the desired maximum number of idle server processes.
1169 + Used only when 'apache-like' pm_style is selected
1170 + <value name="MaxSpareServers">35</value>
1176 + The timeout (in seconds) for serving a single request after which the worker process will be terminated
1177 + Should be used when 'max_execution_time' ini option does not stop script execution for some reason
1179 + <value name="request_terminate_timeout">0s</value>
1181 + The timeout (in seconds) for serving of single request after which a php backtrace will be dumped to slow.log file
1183 + <value name="request_slowlog_timeout">0s</value>
1185 + The log file for slow requests
1186 + <value name="slowlog">logs/slow.log</value>
1188 + Set open file desc rlimit
1189 + <value name="rlimit_files">1024</value>
1191 + Set max core size rlimit
1192 + <value name="rlimit_core">0</value>
1194 + Chroot to this directory at the start, absolute path
1195 + <value name="chroot"></value>
1197 + Chdir to this directory at the start, absolute path
1198 + <value name="chdir"></value>
1200 + Redirect workers' stdout and stderr into main error log.
1201 + If not set, they will be redirected to /dev/null, according to FastCGI specs
1202 + <value name="catch_workers_output">yes</value>
1204 + How much requests each process should execute before respawn.
1205 + Useful to work around memory leaks in 3rd party libraries.
1206 + For endless request processing please specify 0
1207 + Equivalent to PHP_FCGI_MAX_REQUESTS
1208 + <value name="max_requests">500</value>
1210 + Comma separated list of ipv4 addresses of FastCGI clients that allowed to connect.
1211 + Equivalent to FCGI_WEB_SERVER_ADDRS environment in original php.fcgi (5.2.2+)
1212 + Makes sense only with AF_INET listening socket.
1213 + <value name="allowed_clients">127.0.0.1</value>
1215 + Pass environment variables like LD_LIBRARY_PATH
1216 + All $VARIABLEs are taken from current environment
1217 + <value name="environment">
1218 + <value name="HOSTNAME">$HOSTNAME</value>
1219 + <value name="PATH">/usr/local/bin:/usr/bin:/bin</value>
1220 + <value name="TMP">/tmp</value>
1221 + <value name="TMPDIR">/tmp</value>
1222 + <value name="TEMP">/tmp</value>
1223 + <value name="OSTYPE">$OSTYPE</value>
1224 + <value name="MACHTYPE">$MACHTYPE</value>
1225 + <value name="MALLOC_CHECK_">2</value>
1233 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/config.m4 php-5.2.17/sapi/cgi/fpm/config.m4
1234 --- php-5.2.17.org/sapi/cgi/fpm/config.m4 1970-01-01 01:00:00.000000000 +0100
1235 +++ php-5.2.17/sapi/cgi/fpm/config.m4 2021-10-23 19:09:19.829791741 +0200
1238 +FPM_VERSION="0.5.14"
1240 +PHP_ARG_WITH(fpm-conf, for php-fpm config file path,
1241 +[ --with-fpm-conf=PATH Set the path for php-fpm configuration file [PREFIX/etc/php-fpm.conf]], \$prefix/etc/php-fpm.conf, no)
1243 +PHP_ARG_WITH(fpm-log, for php-fpm log file path,
1244 +[ --with-fpm-log=PATH Set the path for php-fpm log file [PREFIX/logs/php-fpm.log]], \$prefix/logs/php-fpm.log, no)
1246 +PHP_ARG_WITH(fpm-pid, for php-fpm pid file path,
1247 +[ --with-fpm-pid=PATH Set the path for php-fpm pid file [PREFIX/logs/php-fpm.pid]], \$prefix/logs/php-fpm.pid, no)
1249 +FPM_SOURCES="fpm.c \
1253 + fpm_worker_pool.c \
1262 + fpm_process_ctl.c \
1270 +dnl AC_FPM_LIBEVENT
1278 +LIBEVENT_LIBS="-levent"
1280 +SAPI_EXTRA_DEPS="$LIBEVENT_LIBS"
1282 +FPM_CFLAGS="$LIBEVENT_CFLAGS $LIBXML_CFLAGS $JUDY_CFLAGS"
1284 +dnl FPM_CFLAGS="$FPM_CFLAGS -DJUDYERROR_NOTEST" # for Judy
1285 +FPM_CFLAGS="$FPM_CFLAGS -I$abs_srcdir/sapi/cgi" # for fastcgi.h
1287 +if test "$ICC" = "yes" ; then
1288 + FPM_ADD_CFLAGS="-Wall -wd279,310,869,810,981"
1289 +elif test "$GCC" = "yes" ; then
1290 + FPM_ADD_CFLAGS="-Wall -Wpointer-arith -Wno-unused-parameter -Wunused-variable -Wunused-value -fno-strict-aliasing"
1293 +if test -n "$FPM_WERROR" ; then
1294 + FPM_ADD_CFLAGS="$FPM_ADD_CFLAGS -Werror"
1297 +FPM_CFLAGS="$FPM_ADD_CFLAGS $FPM_CFLAGS"
1299 +PHP_ADD_MAKEFILE_FRAGMENT($abs_srcdir/sapi/cgi/fpm/Makefile.frag)
1301 +PHP_ADD_SOURCES(sapi/cgi/fpm, $FPM_SOURCES, $FPM_CFLAGS, sapi)
1303 +PHP_ADD_BUILD_DIR(sapi/cgi/fpm)
1305 +install_fpm="install-fpm"
1307 +SAPI_EXTRA_LIBS="$LIBEVENT_LIBS $LIBXML_LIBS $JUDY_LIBS"
1310 +if test "$prefix" = "NONE" ; then
1311 + fpm_prefix=/usr/local
1313 + fpm_prefix="$prefix"
1316 +if test "$PHP_FPM_CONF" = "\$prefix/etc/php-fpm.conf" ; then
1317 + php_fpm_conf_path="$fpm_prefix/etc/php-fpm.conf"
1319 + php_fpm_conf_path="$PHP_FPM_CONF"
1322 +if test "$PHP_FPM_LOG" = "\$prefix/logs/php-fpm.log" ; then
1323 + php_fpm_log_path="$fpm_prefix/logs/php-fpm.log"
1325 + php_fpm_log_path="$PHP_FPM_LOG"
1328 +if test "$PHP_FPM_PID" = "\$prefix/logs/php-fpm.pid" ; then
1329 + php_fpm_pid_path="$fpm_prefix/logs/php-fpm.pid"
1331 + php_fpm_pid_path="$PHP_FPM_PID"
1335 +if grep nobody /etc/group >/dev/null 2>&1; then
1336 + php_fpm_group=nobody
1338 + if grep nogroup /etc/group >/dev/null 2>&1; then
1339 + php_fpm_group=nogroup
1341 + php_fpm_group=nobody
1345 +PHP_SUBST_OLD(php_fpm_conf_path)
1346 +PHP_SUBST_OLD(php_fpm_log_path)
1347 +PHP_SUBST_OLD(php_fpm_pid_path)
1348 +PHP_SUBST_OLD(php_fpm_group)
1349 +PHP_SUBST_OLD(FPM_VERSION)
1351 +PHP_OUTPUT(sapi/cgi/fpm/fpm_autoconf.h)
1352 +PHP_OUTPUT(sapi/cgi/fpm/php-fpm.conf:sapi/cgi/fpm/conf/php-fpm.conf.in)
1353 +PHP_OUTPUT(sapi/cgi/fpm/php-fpm:sapi/cgi/fpm/init.d/php-fpm.in)
1354 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm.c php-5.2.17/sapi/cgi/fpm/fpm.c
1355 --- php-5.2.17.org/sapi/cgi/fpm/fpm.c 1970-01-01 01:00:00.000000000 +0100
1356 +++ php-5.2.17/sapi/cgi/fpm/fpm.c 2021-10-23 19:09:19.829791741 +0200
1360 + /* (c) 2007,2008 Andrei Nigmatulin */
1362 +#include "fpm_config.h"
1364 +#include <stdlib.h> /* for exit */
1367 +#include "fpm_children.h"
1368 +#include "fpm_signals.h"
1369 +#include "fpm_env.h"
1370 +#include "fpm_events.h"
1371 +#include "fpm_cleanup.h"
1372 +#include "fpm_php.h"
1373 +#include "fpm_sockets.h"
1374 +#include "fpm_unix.h"
1375 +#include "fpm_process_ctl.h"
1376 +#include "fpm_conf.h"
1377 +#include "fpm_worker_pool.h"
1378 +#include "fpm_stdio.h"
1383 +struct fpm_globals_s fpm_globals;
1385 +int fpm_init(int argc, char **argv, char *config)
1387 + fpm_globals.argc = argc;
1388 + fpm_globals.argv = argv;
1389 + fpm_globals.config = config;
1391 + if (0 > fpm_php_init_main() ||
1392 + 0 > fpm_stdio_init_main() ||
1393 + 0 > fpm_conf_init_main() ||
1394 + 0 > fpm_unix_init_main() ||
1395 + 0 > fpm_env_init_main() ||
1396 + 0 > fpm_signals_init_main() ||
1397 + 0 > fpm_pctl_init_main() ||
1398 + 0 > fpm_children_init_main() ||
1399 + 0 > fpm_sockets_init_main() ||
1400 + 0 > fpm_worker_pool_init_main() ||
1401 + 0 > fpm_event_init_main()) {
1405 + if (0 > fpm_conf_write_pid()) {
1409 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "fpm is running, pid %d", (int) fpm_globals.parent_pid);
1414 +/* children: return listening socket
1415 + parent: never return */
1416 +int fpm_run(int *max_requests)
1418 + struct fpm_worker_pool_s *wp;
1420 + /* create initial children in all pools */
1421 + for (wp = fpm_worker_all_pools; wp; wp = wp->next) {
1424 + is_parent = fpm_children_create_initial(wp);
1431 + /* run event loop forever */
1434 +run_child: /* only workers reach this point */
1436 + fpm_cleanups_run(FPM_CLEANUP_CHILD);
1438 + *max_requests = fpm_globals.max_requests;
1439 + return fpm_globals.listening_socket;
1442 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm.h php-5.2.17/sapi/cgi/fpm/fpm.h
1443 --- php-5.2.17.org/sapi/cgi/fpm/fpm.h 1970-01-01 01:00:00.000000000 +0100
1444 +++ php-5.2.17/sapi/cgi/fpm/fpm.h 2021-10-23 19:09:19.829791741 +0200
1448 + /* (c) 2007,2008 Andrei Nigmatulin */
1453 +#include <unistd.h>
1455 +int fpm_run(int *max_requests);
1456 +int fpm_init(int argc, char **argv, char *config);
1458 +struct fpm_globals_s {
1463 + int running_children;
1466 + int listening_socket; /* for this child */
1467 + int max_requests; /* for this child */
1471 +extern struct fpm_globals_s fpm_globals;
1476 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_arrays.h php-5.2.17/sapi/cgi/fpm/fpm_arrays.h
1477 --- php-5.2.17.org/sapi/cgi/fpm/fpm_arrays.h 1970-01-01 01:00:00.000000000 +0100
1478 +++ php-5.2.17/sapi/cgi/fpm/fpm_arrays.h 2021-10-23 19:09:19.829791741 +0200
1482 + /* (c) 2007,2008 Andrei Nigmatulin */
1484 +#ifndef FPM_ARRAYS_H
1485 +#define FPM_ARRAYS_H 1
1487 +#include <stdlib.h>
1488 +#include <string.h>
1490 +struct fpm_array_s {
1497 +static inline struct fpm_array_s *fpm_array_init(struct fpm_array_s *a, unsigned int sz, unsigned int initial_num)
1499 + void *allocated = 0;
1502 + a = malloc(sizeof(struct fpm_array_s));
1513 + a->data = calloc(sz, initial_num);
1520 + a->allocated = initial_num;
1526 +static inline void *fpm_array_item(struct fpm_array_s *a, unsigned int n)
1530 + ret = (char *) a->data + a->sz * n;
1535 +static inline void *fpm_array_item_last(struct fpm_array_s *a)
1537 + return fpm_array_item(a, a->used - 1);
1540 +static inline int fpm_array_item_remove(struct fpm_array_s *a, unsigned int n)
1544 + if (n < a->used - 1) {
1545 + void *last = fpm_array_item(a, a->used - 1);
1546 + void *to_remove = fpm_array_item(a, n);
1548 + memcpy(to_remove, last, a->sz);
1558 +static inline void *fpm_array_push(struct fpm_array_s *a)
1562 + if (a->used == a->allocated) {
1563 + size_t new_allocated = a->allocated ? a->allocated * 2 : 20;
1564 + void *new_ptr = realloc(a->data, a->sz * new_allocated);
1570 + a->data = new_ptr;
1571 + a->allocated = new_allocated;
1574 + ret = fpm_array_item(a, a->used);
1581 +static inline void fpm_array_free(struct fpm_array_s *a)
1586 + a->used = a->allocated = 0;
1590 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_atomic.h php-5.2.17/sapi/cgi/fpm/fpm_atomic.h
1591 --- php-5.2.17.org/sapi/cgi/fpm/fpm_atomic.h 1970-01-01 01:00:00.000000000 +0100
1592 +++ php-5.2.17/sapi/cgi/fpm/fpm_atomic.h 2021-10-23 19:09:19.829791741 +0200
1596 + /* (c) 2007,2008 Andrei Nigmatulin */
1598 +#ifndef FPM_ATOMIC_H
1599 +#define FPM_ATOMIC_H 1
1601 +#include <stdint.h>
1604 +#if ( __i386__ || __i386 )
1606 +typedef int32_t atomic_int_t;
1607 +typedef uint32_t atomic_uint_t;
1608 +typedef volatile atomic_uint_t atomic_t;
1611 +static inline atomic_int_t atomic_fetch_add(atomic_t *value, atomic_int_t add)
1613 + __asm__ volatile ( "lock;" "xaddl %0, %1;" :
1614 + "+r" (add) : "m" (*value) : "memory");
1619 +static inline atomic_uint_t atomic_cmp_set(atomic_t *lock, atomic_uint_t old, atomic_uint_t set)
1621 + unsigned char res;
1623 + __asm__ volatile ( "lock;" "cmpxchgl %3, %1;" "sete %0;" :
1624 + "=a" (res) : "m" (*lock), "a" (old), "r" (set) : "memory");
1629 +#elif ( __amd64__ || __amd64 )
1631 +typedef int64_t atomic_int_t;
1632 +typedef uint64_t atomic_uint_t;
1633 +typedef volatile atomic_uint_t atomic_t;
1635 +static inline atomic_int_t atomic_fetch_add(atomic_t *value, atomic_int_t add)
1637 + __asm__ volatile ( "lock;" "xaddq %0, %1;" :
1638 + "+r" (add) : "m" (*value) : "memory");
1643 +static inline atomic_uint_t atomic_cmp_set(atomic_t *lock, atomic_uint_t old, atomic_uint_t set)
1645 + unsigned char res;
1647 + __asm__ volatile ( "lock;" "cmpxchgq %3, %1;" "sete %0;" :
1648 + "=a" (res) : "m" (*lock), "a" (old), "r" (set) : "memory");
1655 +#error unsupported processor. please write a patch and send it to me
1659 +static inline int fpm_spinlock(atomic_t *lock, int try_once)
1662 + return atomic_cmp_set(lock, 0, 1) ? 0 : -1;
1667 + if (atomic_cmp_set(lock, 0, 1)) {
1679 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_autoconf.h.in php-5.2.17/sapi/cgi/fpm/fpm_autoconf.h.in
1680 --- php-5.2.17.org/sapi/cgi/fpm/fpm_autoconf.h.in 1970-01-01 01:00:00.000000000 +0100
1681 +++ php-5.2.17/sapi/cgi/fpm/fpm_autoconf.h.in 2021-10-23 19:09:19.829791741 +0200
1685 + /* (c) 2007,2008 Andrei Nigmatulin */
1687 +#define PHP_FPM_VERSION "@FPM_VERSION@"
1688 +#define PHP_FPM_CONF_PATH "@php_fpm_conf_path@"
1689 +#define PHP_FPM_LOG_PATH "@php_fpm_log_path@"
1690 +#define PHP_FPM_PID_PATH "@php_fpm_pid_path@"
1692 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_children.c php-5.2.17/sapi/cgi/fpm/fpm_children.c
1693 --- php-5.2.17.org/sapi/cgi/fpm/fpm_children.c 1970-01-01 01:00:00.000000000 +0100
1694 +++ php-5.2.17/sapi/cgi/fpm/fpm_children.c 2021-10-23 19:09:19.829791741 +0200
1698 + /* (c) 2007,2008 Andrei Nigmatulin */
1700 +#include "fpm_config.h"
1702 +#include <sys/types.h>
1703 +#include <sys/wait.h>
1705 +#include <unistd.h>
1706 +#include <string.h>
1710 +#include "fpm_children.h"
1711 +#include "fpm_signals.h"
1712 +#include "fpm_worker_pool.h"
1713 +#include "fpm_sockets.h"
1714 +#include "fpm_process_ctl.h"
1715 +#include "fpm_php.h"
1716 +#include "fpm_conf.h"
1717 +#include "fpm_cleanup.h"
1718 +#include "fpm_events.h"
1719 +#include "fpm_clock.h"
1720 +#include "fpm_stdio.h"
1721 +#include "fpm_unix.h"
1722 +#include "fpm_env.h"
1723 +#include "fpm_shm_slots.h"
1727 +static time_t *last_faults;
1730 +static int fpm_children_make(struct fpm_worker_pool_s *wp, int in_event_loop);
1732 +static void fpm_children_cleanup(int which, void *arg)
1734 + free(last_faults);
1737 +static struct fpm_child_s *fpm_child_alloc()
1739 + struct fpm_child_s *ret;
1741 + ret = malloc(sizeof(struct fpm_child_s));
1743 + if (!ret) return 0;
1745 + memset(ret, 0, sizeof(*ret));
1750 +static void fpm_child_free(struct fpm_child_s *child)
1755 +static void fpm_child_close(struct fpm_child_s *child, int in_event_loop)
1757 + if (child->fd_stdout != -1) {
1758 + if (in_event_loop) {
1759 + fpm_event_fire(&child->ev_stdout);
1761 + if (child->fd_stdout != -1) {
1762 + close(child->fd_stdout);
1766 + if (child->fd_stderr != -1) {
1767 + if (in_event_loop) {
1768 + fpm_event_fire(&child->ev_stderr);
1770 + if (child->fd_stderr != -1) {
1771 + close(child->fd_stderr);
1775 + fpm_child_free(child);
1778 +static void fpm_child_link(struct fpm_child_s *child)
1780 + struct fpm_worker_pool_s *wp = child->wp;
1782 + ++wp->running_children;
1783 + ++fpm_globals.running_children;
1785 + child->next = wp->children;
1786 + if (child->next) child->next->prev = child;
1788 + wp->children = child;
1791 +static void fpm_child_unlink(struct fpm_child_s *child)
1793 + --child->wp->running_children;
1794 + --fpm_globals.running_children;
1796 + if (child->prev) child->prev->next = child->next;
1797 + else child->wp->children = child->next;
1798 + if (child->next) child->next->prev = child->prev;
1802 +static struct fpm_child_s *fpm_child_find(pid_t pid)
1804 + struct fpm_worker_pool_s *wp;
1805 + struct fpm_child_s *child = 0;
1807 + for (wp = fpm_worker_all_pools; wp; wp = wp->next) {
1809 + for (child = wp->children; child; child = child->next) {
1810 + if (child->pid == pid) {
1825 +static void fpm_child_init(struct fpm_worker_pool_s *wp)
1827 + fpm_globals.max_requests = wp->config->max_requests;
1829 + if (0 > fpm_stdio_init_child(wp) ||
1830 + 0 > fpm_unix_init_child(wp) ||
1831 + 0 > fpm_signals_init_child() ||
1832 + 0 > fpm_env_init_child(wp) ||
1833 + 0 > fpm_php_init_child(wp)) {
1835 + zlog(ZLOG_STUFF, ZLOG_ERROR, "child failed to initialize (pool %s)", wp->config->name);
1840 +int fpm_children_free(struct fpm_child_s *child)
1842 + struct fpm_child_s *next;
1844 + for (; child; child = next) {
1845 + next = child->next;
1846 + fpm_child_close(child, 0 /* in_event_loop */);
1852 +void fpm_children_bury()
1856 + struct fpm_child_s *child;
1858 + while ( (pid = waitpid(-1, &status, WNOHANG | WUNTRACED)) > 0) {
1860 + int severity = ZLOG_NOTICE;
1862 + child = fpm_child_find(pid);
1864 + if (WIFEXITED(status)) {
1866 + snprintf(buf, sizeof(buf), "with code %d", WEXITSTATUS(status));
1868 + if (WEXITSTATUS(status) != 0) {
1869 + severity = ZLOG_WARNING;
1873 + else if (WIFSIGNALED(status)) {
1874 + const char *signame = fpm_signal_names[WTERMSIG(status)];
1875 + const char *have_core = WCOREDUMP(status) ? " (core dumped)" : "";
1877 + if (signame == NULL) {
1881 + snprintf(buf, sizeof(buf), "on signal %d %s%s", WTERMSIG(status), signame, have_core);
1883 + if (WTERMSIG(status) != SIGQUIT) { /* possible request loss */
1884 + severity = ZLOG_WARNING;
1887 + else if (WIFSTOPPED(status)) {
1889 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "child %d stopped for tracing", (int) pid);
1891 + if (child && child->tracer) {
1892 + child->tracer(child);
1899 + struct fpm_worker_pool_s *wp = child->wp;
1900 + struct timeval tv1, tv2;
1902 + fpm_child_unlink(child);
1904 + fpm_shm_slots_discard_slot(child);
1906 + fpm_clock_get(&tv1);
1908 + timersub(&tv1, &child->started, &tv2);
1910 + zlog(ZLOG_STUFF, severity, "child %d (pool %s) exited %s after %ld.%06d seconds from start", (int) pid,
1911 + child->wp->config->name, buf, tv2.tv_sec, (int) tv2.tv_usec);
1913 + fpm_child_close(child, 1 /* in event_loop */);
1915 + fpm_pctl_child_exited();
1917 + if (last_faults && (WTERMSIG(status) == SIGSEGV || WTERMSIG(status) == SIGBUS)) {
1918 + time_t now = tv1.tv_sec;
1919 + int restart_condition = 1;
1922 + last_faults[fault++] = now;
1924 + if (fault == fpm_global_config.emergency_restart_threshold) {
1928 + for (i = 0; i < fpm_global_config.emergency_restart_threshold; i++) {
1929 + if (now - last_faults[i] > fpm_global_config.emergency_restart_interval) {
1930 + restart_condition = 0;
1935 + if (restart_condition) {
1937 + zlog(ZLOG_STUFF, ZLOG_WARNING, "failed processes threshold (%d in %d sec) is reached, initiating reload",
1938 + fpm_global_config.emergency_restart_threshold, fpm_global_config.emergency_restart_interval);
1940 + fpm_pctl(FPM_PCTL_STATE_RELOADING, FPM_PCTL_ACTION_SET);
1944 + fpm_children_make(wp, 1 /* in event loop */);
1946 + if (fpm_globals.is_child) {
1951 + zlog(ZLOG_STUFF, ZLOG_ALERT, "oops, unknown child exited %s", buf);
1957 +static struct fpm_child_s *fpm_resources_prepare(struct fpm_worker_pool_s *wp)
1959 + struct fpm_child_s *c;
1961 + c = fpm_child_alloc();
1964 + zlog(ZLOG_STUFF, ZLOG_ERROR, "malloc failed (pool %s)", wp->config->name);
1969 + c->fd_stdout = -1; c->fd_stderr = -1;
1971 + if (0 > fpm_stdio_prepare_pipes(c)) {
1972 + fpm_child_free(c);
1976 + if (0 > fpm_shm_slots_prepare_slot(c)) {
1977 + fpm_stdio_discard_pipes(c);
1978 + fpm_child_free(c);
1985 +static void fpm_resources_discard(struct fpm_child_s *child)
1987 + fpm_shm_slots_discard_slot(child);
1988 + fpm_stdio_discard_pipes(child);
1989 + fpm_child_free(child);
1992 +static void fpm_child_resources_use(struct fpm_child_s *child)
1994 + fpm_shm_slots_child_use_slot(child);
1995 + fpm_stdio_child_use_pipes(child);
1996 + fpm_child_free(child);
1999 +static void fpm_parent_resources_use(struct fpm_child_s *child)
2001 + fpm_shm_slots_parent_use_slot(child);
2002 + fpm_stdio_parent_use_pipes(child);
2003 + fpm_child_link(child);
2006 +static int fpm_children_make(struct fpm_worker_pool_s *wp, int in_event_loop)
2010 + struct fpm_child_s *child;
2012 + while (!enough && fpm_pctl_can_spawn_children() && wp->running_children < wp->config->pm->max_children) {
2014 + child = fpm_resources_prepare(wp);
2026 + fpm_child_resources_use(child);
2027 + fpm_globals.is_child = 1;
2028 + if (in_event_loop) {
2029 + fpm_event_exit_loop();
2031 + fpm_child_init(wp);
2035 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "fork() failed");
2038 + fpm_resources_discard(child);
2040 + break; /* dont try any more on error */
2044 + fpm_clock_get(&child->started);
2045 + fpm_parent_resources_use(child);
2047 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "child %d (pool %s) started", (int) pid, wp->config->name);
2052 + return 1; /* we are done */
2055 +int fpm_children_create_initial(struct fpm_worker_pool_s *wp)
2057 + return fpm_children_make(wp, 0 /* not in event loop yet */);
2060 +int fpm_children_init_main()
2062 + if (fpm_global_config.emergency_restart_threshold &&
2063 + fpm_global_config.emergency_restart_interval) {
2065 + last_faults = malloc(sizeof(time_t) * fpm_global_config.emergency_restart_threshold);
2067 + if (!last_faults) {
2071 + memset(last_faults, 0, sizeof(time_t) * fpm_global_config.emergency_restart_threshold);
2074 + if (0 > fpm_cleanup_add(FPM_CLEANUP_ALL, fpm_children_cleanup, 0)) {
2081 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_children.h php-5.2.17/sapi/cgi/fpm/fpm_children.h
2082 --- php-5.2.17.org/sapi/cgi/fpm/fpm_children.h 1970-01-01 01:00:00.000000000 +0100
2083 +++ php-5.2.17/sapi/cgi/fpm/fpm_children.h 2021-10-23 19:09:19.829791741 +0200
2087 + /* (c) 2007,2008 Andrei Nigmatulin */
2089 +#ifndef FPM_CHILDREN_H
2090 +#define FPM_CHILDREN_H 1
2092 +#include <sys/time.h>
2093 +#include <sys/types.h>
2096 +#include "fpm_worker_pool.h"
2098 +int fpm_children_create_initial(struct fpm_worker_pool_s *wp);
2099 +int fpm_children_free(struct fpm_child_s *child);
2100 +void fpm_children_bury();
2101 +int fpm_children_init_main();
2103 +struct fpm_child_s;
2105 +struct fpm_child_s {
2106 + struct fpm_child_s *prev, *next;
2107 + struct timeval started;
2108 + struct fpm_worker_pool_s *wp;
2109 + struct event ev_stdout, ev_stderr;
2111 + int fd_stdout, fd_stderr;
2112 + void (*tracer)(struct fpm_child_s *);
2113 + struct timeval slow_logged;
2118 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_cleanup.c php-5.2.17/sapi/cgi/fpm/fpm_cleanup.c
2119 --- php-5.2.17.org/sapi/cgi/fpm/fpm_cleanup.c 1970-01-01 01:00:00.000000000 +0100
2120 +++ php-5.2.17/sapi/cgi/fpm/fpm_cleanup.c 2021-10-23 19:09:19.829791741 +0200
2124 + /* (c) 2007,2008 Andrei Nigmatulin */
2126 +#include "fpm_config.h"
2128 +#include <stdlib.h>
2130 +#include "fpm_arrays.h"
2131 +#include "fpm_cleanup.h"
2136 + void (*cleanup)(int, void *);
2140 +static struct fpm_array_s cleanups = { .sz = sizeof(struct cleanup_s) };
2142 +int fpm_cleanup_add(int type, void (*cleanup)(int, void *), void *arg)
2144 + struct cleanup_s *c;
2146 + c = fpm_array_push(&cleanups);
2153 + c->cleanup = cleanup;
2159 +void fpm_cleanups_run(int type)
2161 + struct cleanup_s *c = fpm_array_item_last(&cleanups);
2162 + int cl = cleanups.used;
2164 + for ( ; cl--; c--) {
2165 + if (c->type & type) {
2166 + c->cleanup(type, c->arg);
2170 + fpm_array_free(&cleanups);
2173 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_cleanup.h php-5.2.17/sapi/cgi/fpm/fpm_cleanup.h
2174 --- php-5.2.17.org/sapi/cgi/fpm/fpm_cleanup.h 1970-01-01 01:00:00.000000000 +0100
2175 +++ php-5.2.17/sapi/cgi/fpm/fpm_cleanup.h 2021-10-23 19:09:19.829791741 +0200
2179 + /* (c) 2007,2008 Andrei Nigmatulin */
2181 +#ifndef FPM_CLEANUP_H
2182 +#define FPM_CLEANUP_H 1
2184 +int fpm_cleanup_add(int type, void (*cleanup)(int, void *), void *);
2185 +void fpm_cleanups_run(int type);
2188 + FPM_CLEANUP_CHILD = (1 << 0),
2189 + FPM_CLEANUP_PARENT_EXIT = (1 << 1),
2190 + FPM_CLEANUP_PARENT_EXIT_MAIN = (1 << 2),
2191 + FPM_CLEANUP_PARENT_EXEC = (1 << 3),
2192 + FPM_CLEANUP_PARENT = (1 << 1) | (1 << 2) | (1 << 3),
2193 + FPM_CLEANUP_ALL = ~0,
2198 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_clock.c php-5.2.17/sapi/cgi/fpm/fpm_clock.c
2199 --- php-5.2.17.org/sapi/cgi/fpm/fpm_clock.c 1970-01-01 01:00:00.000000000 +0100
2200 +++ php-5.2.17/sapi/cgi/fpm/fpm_clock.c 2021-10-23 19:09:19.829791741 +0200
2204 + /* (c) 2007,2008 Andrei Nigmatulin */
2206 +#include "fpm_config.h"
2208 +#if defined(HAVE_CLOCK_GETTIME)
2209 +#include <time.h> /* for CLOCK_MONOTONIC */
2212 +#include "fpm_clock.h"
2216 +/* posix monotonic clock - preferred source of time */
2217 +#if defined(HAVE_CLOCK_GETTIME) && defined(CLOCK_MONOTONIC)
2219 +static int monotonic_works;
2221 +int fpm_clock_init()
2223 + struct timespec ts;
2225 + monotonic_works = 0;
2227 + if (0 == clock_gettime(CLOCK_MONOTONIC, &ts)) {
2228 + monotonic_works = 1;
2234 +int fpm_clock_get(struct timeval *tv)
2236 + if (monotonic_works) {
2237 + struct timespec ts;
2239 + if (0 > clock_gettime(CLOCK_MONOTONIC, &ts)) {
2240 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "clock_gettime() failed");
2244 + tv->tv_sec = ts.tv_sec;
2245 + tv->tv_usec = ts.tv_nsec / 1000;
2249 + return gettimeofday(tv, 0);
2253 +#elif defined(HAVE_CLOCK_GET_TIME)
2255 +#include <mach/mach.h>
2256 +#include <mach/clock.h>
2257 +#include <mach/mach_error.h>
2259 +static clock_serv_t mach_clock;
2261 +/* this code borrowed from here: http://lists.apple.com/archives/Darwin-development/2002/Mar/msg00746.html */
2262 +/* mach_clock also should be re-initialized in child process after fork */
2263 +int fpm_clock_init()
2265 + kern_return_t ret;
2266 + mach_timespec_t aTime;
2268 + ret = host_get_clock_service(mach_host_self(), REALTIME_CLOCK, &mach_clock);
2270 + if (ret != KERN_SUCCESS) {
2271 + zlog(ZLOG_STUFF, ZLOG_ERROR, "host_get_clock_service() failed: %s", mach_error_string(ret));
2275 + /* test if it works */
2276 + ret = clock_get_time(mach_clock, &aTime);
2278 + if (ret != KERN_SUCCESS) {
2279 + zlog(ZLOG_STUFF, ZLOG_ERROR, "clock_get_time() failed: %s", mach_error_string(ret));
2286 +int fpm_clock_get(struct timeval *tv)
2288 + kern_return_t ret;
2289 + mach_timespec_t aTime;
2291 + ret = clock_get_time(mach_clock, &aTime);
2293 + if (ret != KERN_SUCCESS) {
2294 + zlog(ZLOG_STUFF, ZLOG_ERROR, "clock_get_time() failed: %s", mach_error_string(ret));
2298 + tv->tv_sec = aTime.tv_sec;
2299 + tv->tv_usec = aTime.tv_nsec / 1000;
2304 +#else /* no clock */
2306 +int fpm_clock_init()
2311 +int fpm_clock_get(struct timeval *tv)
2313 + return gettimeofday(tv, 0);
2317 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_clock.h php-5.2.17/sapi/cgi/fpm/fpm_clock.h
2318 --- php-5.2.17.org/sapi/cgi/fpm/fpm_clock.h 1970-01-01 01:00:00.000000000 +0100
2319 +++ php-5.2.17/sapi/cgi/fpm/fpm_clock.h 2021-10-23 19:09:19.829791741 +0200
2323 + /* (c) 2007,2008 Andrei Nigmatulin */
2325 +#ifndef FPM_CLOCK_H
2326 +#define FPM_CLOCK_H 1
2328 +#include <sys/time.h>
2330 +int fpm_clock_init();
2331 +int fpm_clock_get(struct timeval *tv);
2334 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_conf.c php-5.2.17/sapi/cgi/fpm/fpm_conf.c
2335 --- php-5.2.17.org/sapi/cgi/fpm/fpm_conf.c 1970-01-01 01:00:00.000000000 +0100
2336 +++ php-5.2.17/sapi/cgi/fpm/fpm_conf.c 2021-10-23 19:09:19.829791741 +0200
2340 + /* (c) 2007,2008 Andrei Nigmatulin */
2342 +#include "fpm_config.h"
2344 +#include <sys/types.h>
2345 +#include <sys/stat.h>
2347 +#include <string.h>
2348 +#include <stdlib.h>
2349 +#include <stddef.h>
2350 +#include <stdint.h>
2352 +#include <unistd.h>
2355 +#include "fpm_conf.h"
2356 +#include "fpm_stdio.h"
2357 +#include "fpm_worker_pool.h"
2358 +#include "fpm_cleanup.h"
2359 +#include "fpm_php.h"
2360 +#include "fpm_sockets.h"
2361 +#include "xml_config.h"
2365 +struct fpm_global_config_s fpm_global_config;
2367 +static void *fpm_global_config_ptr()
2369 + return &fpm_global_config;
2372 +static char *fpm_conf_set_log_level(void **conf, char *name, void *vv, intptr_t offset)
2376 + if (!strcmp(value, "debug")) {
2377 + fpm_globals.log_level = ZLOG_DEBUG;
2379 + else if (!strcmp(value, "notice")) {
2380 + fpm_globals.log_level = ZLOG_NOTICE;
2382 + else if (!strcmp(value, "warn")) {
2383 + fpm_globals.log_level = ZLOG_WARNING;
2385 + else if (!strcmp(value, "error")) {
2386 + fpm_globals.log_level = ZLOG_ERROR;
2388 + else if (!strcmp(value, "alert")) {
2389 + fpm_globals.log_level = ZLOG_ALERT;
2392 + return "invalid value for 'log_level'";
2398 +static struct xml_conf_section xml_section_fpm_global_options = {
2399 + .conf = &fpm_global_config_ptr,
2400 + .path = "/configuration/global_options",
2401 + .parsers = (struct xml_value_parser []) {
2402 + { XML_CONF_SCALAR, "emergency_restart_threshold", &xml_conf_set_slot_integer, offsetof(struct fpm_global_config_s, emergency_restart_threshold) },
2403 + { XML_CONF_SCALAR, "emergency_restart_interval", &xml_conf_set_slot_time, offsetof(struct fpm_global_config_s, emergency_restart_interval) },
2404 + { XML_CONF_SCALAR, "process_control_timeout", &xml_conf_set_slot_time, offsetof(struct fpm_global_config_s, process_control_timeout) },
2405 + { XML_CONF_SCALAR, "daemonize", &xml_conf_set_slot_boolean, offsetof(struct fpm_global_config_s, daemonize) },
2406 + { XML_CONF_SCALAR, "pid_file", &xml_conf_set_slot_string, offsetof(struct fpm_global_config_s, pid_file) },
2407 + { XML_CONF_SCALAR, "error_log", &xml_conf_set_slot_string, offsetof(struct fpm_global_config_s, error_log) },
2408 + { XML_CONF_SCALAR, "log_level", &fpm_conf_set_log_level, 0 },
2413 +static char *fpm_conf_set_pm_style(void **conf, char *name, void *vv, intptr_t offset)
2416 + struct fpm_pm_s *c = *conf;
2418 + if (!strcmp(value, "static")) {
2419 + c->style = PM_STYLE_STATIC;
2421 + else if (!strcmp(value, "apache-like")) {
2422 + c->style = PM_STYLE_APACHE_LIKE;
2425 + return "invalid value for 'style'";
2431 +static char *fpm_conf_set_rlimit_core(void **conf, char *name, void *vv, intptr_t offset)
2434 + struct fpm_worker_pool_config_s *c = *conf;
2436 + if (!strcmp(value, "unlimited")) {
2437 + c->rlimit_core = -1;
2441 + void *subconf = &int_value;
2444 + error = xml_conf_set_slot_integer(&subconf, name, vv, 0);
2446 + if (error) return error;
2448 + if (int_value < 0) return "invalid value for 'rlimit_core'";
2450 + c->rlimit_core = int_value;
2456 +static char *fpm_conf_set_catch_workers_output(void **conf, char *name, void *vv, intptr_t offset)
2458 + struct fpm_worker_pool_config_s *c = *conf;
2460 + void *subconf = &int_value;
2463 + error = xml_conf_set_slot_boolean(&subconf, name, vv, 0);
2465 + if (error) return error;
2467 + c->catch_workers_output = int_value;
2472 +static struct xml_conf_section fpm_conf_set_apache_like_subsection_conf = {
2473 + .path = "apache_like somewhere", /* fixme */
2474 + .parsers = (struct xml_value_parser []) {
2475 + { XML_CONF_SCALAR, "StartServers", &xml_conf_set_slot_integer, offsetof(struct fpm_pm_s, options_apache_like.StartServers) },
2476 + { XML_CONF_SCALAR, "MinSpareServers", &xml_conf_set_slot_integer, offsetof(struct fpm_pm_s, options_apache_like.MinSpareServers) },
2477 + { XML_CONF_SCALAR, "MaxSpareServers", &xml_conf_set_slot_integer, offsetof(struct fpm_pm_s, options_apache_like.MaxSpareServers) },
2482 +static char *fpm_conf_set_apache_like_subsection(void **conf, char *name, void *xml_node, intptr_t offset)
2484 + return xml_conf_parse_section(conf, &fpm_conf_set_apache_like_subsection_conf, xml_node);
2487 +static struct xml_conf_section fpm_conf_set_listen_options_subsection_conf = {
2488 + .path = "listen options somewhere", /* fixme */
2489 + .parsers = (struct xml_value_parser []) {
2490 + { XML_CONF_SCALAR, "backlog", &xml_conf_set_slot_integer, offsetof(struct fpm_listen_options_s, backlog) },
2491 + { XML_CONF_SCALAR, "owner", &xml_conf_set_slot_string, offsetof(struct fpm_listen_options_s, owner) },
2492 + { XML_CONF_SCALAR, "group", &xml_conf_set_slot_string, offsetof(struct fpm_listen_options_s, group) },
2493 + { XML_CONF_SCALAR, "mode", &xml_conf_set_slot_string, offsetof(struct fpm_listen_options_s, mode) },
2498 +static char *fpm_conf_set_listen_options_subsection(void **conf, char *name, void *xml_node, intptr_t offset)
2500 + void *subconf = (char *) *conf + offset;
2501 + struct fpm_listen_options_s *lo;
2503 + lo = malloc(sizeof(*lo));
2506 + return "malloc() failed";
2509 + memset(lo, 0, sizeof(*lo));
2513 + * (struct fpm_listen_options_s **) subconf = lo;
2517 + return xml_conf_parse_section(&subconf, &fpm_conf_set_listen_options_subsection_conf, xml_node);
2520 +static struct xml_conf_section fpm_conf_set_pm_subsection_conf = {
2521 + .path = "pm settings somewhere", /* fixme */
2522 + .parsers = (struct xml_value_parser []) {
2523 + { XML_CONF_SCALAR, "style", &fpm_conf_set_pm_style, 0 },
2524 + { XML_CONF_SCALAR, "max_children", &xml_conf_set_slot_integer, offsetof(struct fpm_pm_s, max_children) },
2525 + { XML_CONF_SUBSECTION, "apache_like", &fpm_conf_set_apache_like_subsection, offsetof(struct fpm_pm_s, options_apache_like) },
2530 +static char *fpm_conf_set_pm_subsection(void **conf, char *name, void *xml_node, intptr_t offset)
2532 + void *subconf = (char *) *conf + offset;
2533 + struct fpm_pm_s *pm;
2535 + pm = malloc(sizeof(*pm));
2538 + return "fpm_conf_set_pm_subsection(): malloc failed";
2541 + memset(pm, 0, sizeof(*pm));
2543 + * (struct fpm_pm_s **) subconf = pm;
2547 + return xml_conf_parse_section(&subconf, &fpm_conf_set_pm_subsection_conf, xml_node);
2550 +static char *xml_conf_set_slot_key_value_pair(void **conf, char *name, void *vv, intptr_t offset)
2553 + struct key_value_s *kv;
2554 + struct key_value_s ***parent = (struct key_value_s ***) conf;
2556 + kv = malloc(sizeof(*kv));
2559 + return "malloc() failed";
2562 + memset(kv, 0, sizeof(*kv));
2564 + kv->key = strdup(name);
2565 + kv->value = strdup(value);
2567 + if (!kv->key || !kv->value) {
2568 + return "xml_conf_set_slot_key_value_pair(): strdup() failed";
2573 + *parent = &kv->next;
2578 +static struct xml_conf_section fpm_conf_set_key_value_pairs_subsection_conf = {
2579 + .path = "key_value_pairs somewhere", /* fixme */
2580 + .parsers = (struct xml_value_parser []) {
2581 + { XML_CONF_SCALAR, 0, &xml_conf_set_slot_key_value_pair, 0 },
2586 +static char *fpm_conf_set_key_value_pairs_subsection(void **conf, char *name, void *xml_node, intptr_t offset)
2588 + void *next_kv = (char *) *conf + offset;
2590 + return xml_conf_parse_section(&next_kv, &fpm_conf_set_key_value_pairs_subsection_conf, xml_node);
2593 +static void *fpm_worker_pool_config_alloc()
2595 + static struct fpm_worker_pool_s *current_wp = 0;
2596 + struct fpm_worker_pool_s *wp;
2598 + wp = fpm_worker_pool_alloc();
2600 + if (!wp) return 0;
2602 + wp->config = malloc(sizeof(struct fpm_worker_pool_config_s));
2604 + if (!wp->config) return 0;
2606 + memset(wp->config, 0, sizeof(struct fpm_worker_pool_config_s));
2608 + if (current_wp) current_wp->next = wp;
2612 + return wp->config;
2615 +int fpm_worker_pool_config_free(struct fpm_worker_pool_config_s *wpc)
2617 + struct key_value_s *kv, *kv_next;
2620 + free(wpc->listen_address);
2621 + if (wpc->listen_options) {
2622 + free(wpc->listen_options->owner);
2623 + free(wpc->listen_options->group);
2624 + free(wpc->listen_options->mode);
2625 + free(wpc->listen_options);
2627 + for (kv = wpc->php_defines; kv; kv = kv_next) {
2628 + kv_next = kv->next;
2633 + for (kv = wpc->environment; kv; kv = kv_next) {
2634 + kv_next = kv->next;
2642 + free(wpc->chroot);
2644 + free(wpc->allowed_clients);
2645 + free(wpc->slowlog);
2650 +static struct xml_conf_section xml_section_fpm_worker_pool_config = {
2651 + .conf = &fpm_worker_pool_config_alloc,
2652 + .path = "/configuration/workers/pool",
2653 + .parsers = (struct xml_value_parser []) {
2654 + { XML_CONF_SCALAR, "name", &xml_conf_set_slot_string, offsetof(struct fpm_worker_pool_config_s, name) },
2655 + { XML_CONF_SCALAR, "listen_address", &xml_conf_set_slot_string, offsetof(struct fpm_worker_pool_config_s, listen_address) },
2656 + { XML_CONF_SUBSECTION, "listen_options", &fpm_conf_set_listen_options_subsection, offsetof(struct fpm_worker_pool_config_s, listen_options) },
2657 + { XML_CONF_SUBSECTION, "php_defines", &fpm_conf_set_key_value_pairs_subsection, offsetof(struct fpm_worker_pool_config_s, php_defines) },
2658 + { XML_CONF_SCALAR, "user", &xml_conf_set_slot_string, offsetof(struct fpm_worker_pool_config_s, user) },
2659 + { XML_CONF_SCALAR, "group", &xml_conf_set_slot_string, offsetof(struct fpm_worker_pool_config_s, group) },
2660 + { XML_CONF_SCALAR, "chroot", &xml_conf_set_slot_string, offsetof(struct fpm_worker_pool_config_s, chroot) },
2661 + { XML_CONF_SCALAR, "chdir", &xml_conf_set_slot_string, offsetof(struct fpm_worker_pool_config_s, chdir) },
2662 + { XML_CONF_SCALAR, "allowed_clients", &xml_conf_set_slot_string, offsetof(struct fpm_worker_pool_config_s, allowed_clients) },
2663 + { XML_CONF_SUBSECTION, "environment", &fpm_conf_set_key_value_pairs_subsection, offsetof(struct fpm_worker_pool_config_s, environment) },
2664 + { XML_CONF_SCALAR, "request_terminate_timeout", &xml_conf_set_slot_time, offsetof(struct fpm_worker_pool_config_s, request_terminate_timeout) },
2665 + { XML_CONF_SCALAR, "request_slowlog_timeout", &xml_conf_set_slot_time, offsetof(struct fpm_worker_pool_config_s, request_slowlog_timeout) },
2666 + { XML_CONF_SCALAR, "slowlog", &xml_conf_set_slot_string, offsetof(struct fpm_worker_pool_config_s, slowlog) },
2667 + { XML_CONF_SCALAR, "rlimit_files", &xml_conf_set_slot_integer, offsetof(struct fpm_worker_pool_config_s, rlimit_files) },
2668 + { XML_CONF_SCALAR, "rlimit_core", &fpm_conf_set_rlimit_core, 0 },
2669 + { XML_CONF_SCALAR, "max_requests", &xml_conf_set_slot_integer, offsetof(struct fpm_worker_pool_config_s, max_requests) },
2670 + { XML_CONF_SCALAR, "catch_workers_output", &fpm_conf_set_catch_workers_output, 0 },
2671 + { XML_CONF_SUBSECTION, "pm", &fpm_conf_set_pm_subsection, offsetof(struct fpm_worker_pool_config_s, pm) },
2676 +static struct xml_conf_section *fpm_conf_all_sections[] = {
2677 + &xml_section_fpm_global_options,
2678 + &xml_section_fpm_worker_pool_config,
2682 +static int fpm_evaluate_full_path(char **path)
2684 + if (**path != '/') {
2687 + full_path = malloc(sizeof(PHP_PREFIX) + strlen(*path) + 1);
2689 + if (!full_path) return -1;
2691 + sprintf(full_path, "%s/%s", PHP_PREFIX, *path);
2695 + *path = full_path;
2701 +static int fpm_conf_process_all_pools()
2703 + struct fpm_worker_pool_s *wp;
2705 + if (!fpm_worker_all_pools) {
2706 + zlog(ZLOG_STUFF, ZLOG_ERROR, "at least one pool section must be specified in config file");
2710 + for (wp = fpm_worker_all_pools; wp; wp = wp->next) {
2712 + if (wp->config->listen_address && *wp->config->listen_address) {
2714 + wp->listen_address_domain = fpm_sockets_domain_from_address(wp->config->listen_address);
2716 + if (wp->listen_address_domain == FPM_AF_UNIX && *wp->config->listen_address != '/') {
2717 + fpm_evaluate_full_path(&wp->config->listen_address);
2723 + wp->is_template = 1;
2727 + if (wp->config->request_slowlog_timeout) {
2729 + if (! (wp->config->slowlog && *wp->config->slowlog)) {
2730 + zlog(ZLOG_STUFF, ZLOG_ERROR, "pool %s: 'slowlog' must be specified for use with 'request_slowlog_timeout'",
2731 + wp->config->name);
2735 + static int warned = 0;
2738 + zlog(ZLOG_STUFF, ZLOG_WARNING, "pool %s: 'request_slowlog_timeout' is not supported on your system",
2739 + wp->config->name);
2743 + wp->config->request_slowlog_timeout = 0;
2747 + if (wp->config->request_slowlog_timeout && wp->config->slowlog && *wp->config->slowlog) {
2750 + fpm_evaluate_full_path(&wp->config->slowlog);
2752 + if (wp->config->request_slowlog_timeout) {
2753 + fd = open(wp->config->slowlog, O_WRONLY | O_APPEND | O_CREAT, S_IRUSR | S_IWUSR);
2756 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "open(%s) failed", wp->config->slowlog);
2767 +int fpm_conf_unlink_pid()
2769 + if (fpm_global_config.pid_file) {
2771 + if (0 > unlink(fpm_global_config.pid_file)) {
2772 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "unlink(\"%s\") failed", fpm_global_config.pid_file);
2781 +int fpm_conf_write_pid()
2785 + if (fpm_global_config.pid_file) {
2789 + unlink(fpm_global_config.pid_file);
2791 + fd = creat(fpm_global_config.pid_file, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
2794 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "creat(\"%s\") failed", fpm_global_config.pid_file);
2798 + len = sprintf(buf, "%d", (int) fpm_globals.parent_pid);
2800 + if (len != write(fd, buf, len)) {
2801 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "write() failed");
2811 +static int fpm_conf_post_process()
2813 + if (fpm_global_config.pid_file) {
2814 + fpm_evaluate_full_path(&fpm_global_config.pid_file);
2817 + if (!fpm_global_config.error_log) {
2818 + fpm_global_config.error_log = strdup(PHP_FPM_LOG_PATH);
2821 + fpm_evaluate_full_path(&fpm_global_config.error_log);
2823 + if (0 > fpm_stdio_open_error_log(0)) {
2827 + return fpm_conf_process_all_pools();
2830 +static void fpm_conf_cleanup(int which, void *arg)
2832 + free(fpm_global_config.pid_file);
2833 + free(fpm_global_config.error_log);
2834 + fpm_global_config.pid_file = 0;
2835 + fpm_global_config.error_log = 0;
2838 +int fpm_conf_init_main()
2840 + char *filename = fpm_globals.config;
2843 + if (0 > xml_conf_sections_register(fpm_conf_all_sections)) {
2847 + if (filename == NULL) {
2848 + filename = PHP_FPM_CONF_PATH;
2851 + err = xml_conf_load_file(filename);
2854 + zlog(ZLOG_STUFF, ZLOG_ERROR, "failed to load configuration file: %s", err);
2858 + if (0 > fpm_conf_post_process()) {
2864 + if (0 > fpm_cleanup_add(FPM_CLEANUP_ALL, fpm_conf_cleanup, 0)) {
2870 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_conf.h php-5.2.17/sapi/cgi/fpm/fpm_conf.h
2871 --- php-5.2.17.org/sapi/cgi/fpm/fpm_conf.h 1970-01-01 01:00:00.000000000 +0100
2872 +++ php-5.2.17/sapi/cgi/fpm/fpm_conf.h 2021-10-23 19:09:19.829791741 +0200
2876 + /* (c) 2007,2008 Andrei Nigmatulin */
2879 +#define FPM_CONF_H 1
2881 +struct key_value_s;
2883 +struct key_value_s {
2884 + struct key_value_s *next;
2889 +struct fpm_global_config_s {
2890 + int emergency_restart_threshold;
2891 + int emergency_restart_interval;
2892 + int process_control_timeout;
2898 +extern struct fpm_global_config_s fpm_global_config;
2905 + int MinSpareServers;
2906 + int MaxSpareServers;
2907 + } options_apache_like;
2910 +struct fpm_listen_options_s {
2917 +struct fpm_worker_pool_config_s {
2919 + char *listen_address;
2920 + struct fpm_listen_options_s *listen_options;
2921 + struct key_value_s *php_defines;
2926 + char *allowed_clients;
2927 + struct key_value_s *environment;
2928 + struct fpm_pm_s *pm;
2929 + int request_terminate_timeout;
2930 + int request_slowlog_timeout;
2935 + unsigned catch_workers_output:1;
2938 +enum { PM_STYLE_STATIC = 1, PM_STYLE_APACHE_LIKE = 2 };
2940 +int fpm_conf_init_main();
2941 +int fpm_worker_pool_config_free(struct fpm_worker_pool_config_s *wpc);
2942 +int fpm_conf_write_pid();
2943 +int fpm_conf_unlink_pid();
2947 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_config.h php-5.2.17/sapi/cgi/fpm/fpm_config.h
2948 --- php-5.2.17.org/sapi/cgi/fpm/fpm_config.h 1970-01-01 01:00:00.000000000 +0100
2949 +++ php-5.2.17/sapi/cgi/fpm/fpm_config.h 2021-10-23 19:09:19.829791741 +0200
2953 + /* (c) 2007,2008 Andrei Nigmatulin */
2955 +#include "php_config.h"
2956 +#include "fpm_autoconf.h"
2959 +/* Solaris does not have it */
2960 +#ifndef INADDR_NONE
2961 +#define INADDR_NONE (-1)
2965 +/* If we're not using GNU C, elide __attribute__ */
2967 +# define __attribute__(x) /*NOTHING*/
2971 +/* Solaris does not have it */
2973 +#define timersub(tvp, uvp, vvp) \
2975 + (vvp)->tv_sec = (tvp)->tv_sec - (uvp)->tv_sec; \
2976 + (vvp)->tv_usec = (tvp)->tv_usec - (uvp)->tv_usec; \
2977 + if ((vvp)->tv_usec < 0) { \
2978 + (vvp)->tv_sec--; \
2979 + (vvp)->tv_usec += 1000000; \
2984 +#if defined(HAVE_PTRACE) || defined(PROC_MEM_FILE) || defined(HAVE_MACH_VM_READ)
2985 +#define HAVE_FPM_TRACE 1
2987 +#define HAVE_FPM_TRACE 0
2990 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_env.c php-5.2.17/sapi/cgi/fpm/fpm_env.c
2991 --- php-5.2.17.org/sapi/cgi/fpm/fpm_env.c 1970-01-01 01:00:00.000000000 +0100
2992 +++ php-5.2.17/sapi/cgi/fpm/fpm_env.c 2021-10-23 19:09:19.829791741 +0200
2996 + /* (c) 2007,2008 Andrei Nigmatulin */
2998 +#include "fpm_config.h"
3000 +#ifdef HAVE_ALLOCA_H
3001 +#include <alloca.h>
3004 +#include <stdlib.h>
3005 +#include <string.h>
3007 +#include "fpm_env.h"
3010 +#ifndef HAVE_SETENV
3011 +int setenv(char *name, char *value, int overwrite)
3013 + int name_len = strlen(name);
3014 + int value_len = strlen(value);
3015 + char *var = alloca(name_len + 1 + value_len + 1);
3017 + memcpy(var, name, name_len);
3019 + var[name_len] = '=';
3021 + memcpy(var + name_len + 1, value, value_len);
3023 + var[name_len + 1 + value_len] = '\0';
3025 + return putenv(var);
3029 +#ifndef HAVE_CLEARENV
3035 + /* this algo is the only one known to me
3036 + that works well on all systems */
3037 + while (*(envp = environ)) {
3038 + char *eq = strchr(*envp, '=');
3040 + s = strdup(*envp);
3042 + if (eq) s[eq - *envp] = '\0';
3052 +int fpm_env_init_child(struct fpm_worker_pool_s *wp)
3054 + struct key_value_s *kv;
3058 + for (kv = wp->config->environment; kv; kv = kv->next) {
3059 + setenv(kv->key, kv->value, 1);
3063 + setenv("USER", wp->user, 1);
3067 + setenv("HOME", wp->home, 1);
3073 +static int fpm_env_conf_wp(struct fpm_worker_pool_s *wp)
3075 + struct key_value_s *kv;
3077 + kv = wp->config->environment;
3079 + for (kv = wp->config->environment; kv; kv = kv->next) {
3080 + if (*kv->value == '$') {
3081 + char *value = getenv(kv->value + 1);
3083 + if (!value) value = "";
3086 + kv->value = strdup(value);
3089 + /* autodetected values should be removed
3090 + if these vars specified in config */
3091 + if (!strcmp(kv->key, "USER")) {
3096 + if (!strcmp(kv->key, "HOME")) {
3105 +int fpm_env_init_main()
3107 + struct fpm_worker_pool_s *wp;
3109 + for (wp = fpm_worker_all_pools; wp; wp = wp->next) {
3111 + if (0 > fpm_env_conf_wp(wp)) {
3119 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_env.h php-5.2.17/sapi/cgi/fpm/fpm_env.h
3120 --- php-5.2.17.org/sapi/cgi/fpm/fpm_env.h 1970-01-01 01:00:00.000000000 +0100
3121 +++ php-5.2.17/sapi/cgi/fpm/fpm_env.h 2021-10-23 19:09:19.829791741 +0200
3125 + /* (c) 2007,2008 Andrei Nigmatulin */
3128 +#define FPM_ENV_H 1
3130 +#include "fpm_worker_pool.h"
3132 +int fpm_env_init_child(struct fpm_worker_pool_s *wp);
3133 +int fpm_env_init_main();
3135 +extern char **environ;
3137 +#ifndef HAVE_SETENV
3138 +int setenv(char *name, char *value, int overwrite);
3141 +#ifndef HAVE_CLEARENV
3147 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_events.c php-5.2.17/sapi/cgi/fpm/fpm_events.c
3148 --- php-5.2.17.org/sapi/cgi/fpm/fpm_events.c 1970-01-01 01:00:00.000000000 +0100
3149 +++ php-5.2.17/sapi/cgi/fpm/fpm_events.c 2021-10-23 19:09:19.829791741 +0200
3153 + /* (c) 2007,2008 Andrei Nigmatulin */
3155 +#include "fpm_config.h"
3157 +#include <unistd.h>
3159 +#include <stdlib.h> /* for putenv */
3160 +#include <string.h>
3161 +#include <sys/types.h> /* for event.h below */
3165 +#include "fpm_process_ctl.h"
3166 +#include "fpm_events.h"
3167 +#include "fpm_cleanup.h"
3168 +#include "fpm_stdio.h"
3169 +#include "fpm_signals.h"
3170 +#include "fpm_children.h"
3173 +static void fpm_event_cleanup(int which, void *arg)
3175 + event_base_free(0);
3178 +static void fpm_got_signal(int fd, short ev, void *arg)
3186 + res = read(fd, &c, 1);
3187 + } while (res == -1 && errno == EINTR);
3190 + if (res < 0 && errno != EAGAIN && errno != EWOULDBLOCK) {
3191 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "read() failed");
3197 + case 'C' : /* SIGCHLD */
3198 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "received SIGCHLD");
3199 + fpm_children_bury();
3201 + case 'I' : /* SIGINT */
3202 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "received SIGINT");
3203 + fpm_pctl(FPM_PCTL_STATE_TERMINATING, FPM_PCTL_ACTION_SET);
3205 + case 'T' : /* SIGTERM */
3206 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "received SIGTERM");
3207 + fpm_pctl(FPM_PCTL_STATE_TERMINATING, FPM_PCTL_ACTION_SET);
3209 + case 'Q' : /* SIGQUIT */
3210 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "received SIGQUIT");
3211 + fpm_pctl(FPM_PCTL_STATE_FINISHING, FPM_PCTL_ACTION_SET);
3213 + case '1' : /* SIGUSR1 */
3214 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "received SIGUSR1");
3215 + if (0 == fpm_stdio_open_error_log(1)) {
3216 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "log file re-opened");
3219 + case '2' : /* SIGUSR2 */
3220 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "received SIGUSR2");
3221 + fpm_pctl(FPM_PCTL_STATE_RELOADING, FPM_PCTL_ACTION_SET);
3225 + if (fpm_globals.is_child) {
3234 +int fpm_event_init_main()
3238 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "libevent: using %s", event_get_method());
3240 + if (0 > fpm_cleanup_add(FPM_CLEANUP_ALL, fpm_event_cleanup, 0)) {
3247 +int fpm_event_loop()
3249 + static struct event signal_fd_event;
3251 + event_set(&signal_fd_event, fpm_signals_get_fd(), EV_PERSIST | EV_READ, &fpm_got_signal, 0);
3253 + event_add(&signal_fd_event, 0);
3255 + fpm_pctl_heartbeat(-1, 0, 0);
3257 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "libevent: entering main loop");
3264 +int fpm_event_add(int fd, struct event *ev, void (*callback)(int, short, void *), void *arg)
3266 + event_set(ev, fd, EV_PERSIST | EV_READ, callback, arg);
3268 + return event_add(ev, 0);
3271 +int fpm_event_del(struct event *ev)
3273 + return event_del(ev);
3276 +void fpm_event_exit_loop()
3278 + event_loopbreak();
3281 +void fpm_event_fire(struct event *ev)
3283 + (*ev->ev_callback)( (int) ev->ev_fd, (short) ev->ev_res, ev->ev_arg);
3286 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_events.h php-5.2.17/sapi/cgi/fpm/fpm_events.h
3287 --- php-5.2.17.org/sapi/cgi/fpm/fpm_events.h 1970-01-01 01:00:00.000000000 +0100
3288 +++ php-5.2.17/sapi/cgi/fpm/fpm_events.h 2021-10-23 19:09:19.829791741 +0200
3292 + /* (c) 2007,2008 Andrei Nigmatulin */
3294 +#ifndef FPM_EVENTS_H
3295 +#define FPM_EVENTS_H 1
3297 +void fpm_event_exit_loop();
3298 +int fpm_event_loop();
3299 +int fpm_event_add(int fd, struct event *ev, void (*callback)(int, short, void *), void *arg);
3300 +int fpm_event_del(struct event *ev);
3301 +void fpm_event_fire(struct event *ev);
3302 +int fpm_event_init_main();
3306 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_php.c php-5.2.17/sapi/cgi/fpm/fpm_php.c
3307 --- php-5.2.17.org/sapi/cgi/fpm/fpm_php.c 1970-01-01 01:00:00.000000000 +0100
3308 +++ php-5.2.17/sapi/cgi/fpm/fpm_php.c 2021-10-23 19:09:19.829791741 +0200
3312 + /* (c) 2007,2008 Andrei Nigmatulin */
3314 +#include "fpm_config.h"
3316 +#include <stdlib.h>
3317 +#include <string.h>
3321 +#include "php_main.h"
3322 +#include "php_ini.h"
3323 +#include "ext/standard/dl.h"
3325 +#include "fastcgi.h"
3328 +#include "fpm_php.h"
3329 +#include "fpm_cleanup.h"
3330 +#include "fpm_worker_pool.h"
3332 +static int zend_ini_alter_master(char *name, int name_length, char *new_value, int new_value_length, int stage TSRMLS_DC)
3334 + zend_ini_entry *ini_entry;
3337 + if (zend_hash_find(EG(ini_directives), name, name_length, (void **) &ini_entry) == FAILURE) {
3341 + duplicate = strdup(new_value);
3343 + if (!ini_entry->on_modify
3344 + || ini_entry->on_modify(ini_entry, duplicate, new_value_length,
3345 + ini_entry->mh_arg1, ini_entry->mh_arg2, ini_entry->mh_arg3, stage TSRMLS_CC) == SUCCESS) {
3346 + ini_entry->value = duplicate;
3347 + ini_entry->value_length = new_value_length;
3355 +static void fpm_php_disable(char *value, int (*zend_disable)(char *, uint TSRMLS_DC) TSRMLS_DC)
3357 + char *s = 0, *e = value;
3365 + zend_disable(s, e - s TSRMLS_CC);
3379 + zend_disable(s, e - s TSRMLS_CC);
3383 +static int fpm_php_apply_defines(struct fpm_worker_pool_s *wp)
3386 + struct key_value_s *kv;
3388 + for (kv = wp->config->php_defines; kv; kv = kv->next) {
3389 + char *name = kv->key;
3390 + char *value = kv->value;
3391 + int name_len = strlen(name);
3392 + int value_len = strlen(value);
3394 + if (!strcmp(name, "extension") && *value) {
3397 +#if defined(PHP_VERSION_ID) && (PHP_VERSION_ID >= 50300)
3398 + php_dl(value, MODULE_PERSISTENT, &zv, 1 TSRMLS_CC);
3401 + ZVAL_STRINGL(&filename, value, value_len, 0);
3402 +#if (PHP_MAJOR_VERSION >= 5)
3403 + php_dl(&filename, MODULE_PERSISTENT, &zv, 1 TSRMLS_CC);
3405 + php_dl(&filename, MODULE_PERSISTENT, &zv TSRMLS_CC);
3411 + zend_ini_alter_master(name, name_len + 1, value, value_len, PHP_INI_STAGE_ACTIVATE TSRMLS_CC);
3413 + if (!strcmp(name, "disable_functions") && *value) {
3414 + char *v = strdup(value);
3415 +#if (PHP_MAJOR_VERSION >= 5)
3416 + PG(disable_functions) = v;
3418 + fpm_php_disable(v, zend_disable_function TSRMLS_CC);
3420 + else if (!strcmp(name, "disable_classes") && *value) {
3421 + char *v = strdup(value);
3422 +#if (PHP_MAJOR_VERSION >= 5)
3423 + PG(disable_classes) = v;
3425 + fpm_php_disable(v, zend_disable_class TSRMLS_CC);
3432 +static int fpm_php_set_allowed_clients(struct fpm_worker_pool_s *wp)
3434 + if (wp->listen_address_domain == FPM_AF_INET) {
3435 + fcgi_set_allowed_clients(wp->config->allowed_clients);
3441 +static int fpm_php_set_fcgi_mgmt_vars(struct fpm_worker_pool_s *wp)
3443 + char max_workers[10 + 1]; /* 4294967295 */
3446 + len = sprintf(max_workers, "%u", (unsigned int) wp->config->pm->max_children);
3448 + fcgi_set_mgmt_var("FCGI_MAX_CONNS", sizeof("FCGI_MAX_CONNS")-1, max_workers, len);
3449 + fcgi_set_mgmt_var("FCGI_MAX_REQS", sizeof("FCGI_MAX_REQS")-1, max_workers, len);
3454 +char *fpm_php_script_filename(TSRMLS_D)
3456 + return SG(request_info).path_translated;
3459 +char *fpm_php_request_method(TSRMLS_D)
3461 + return (char *) SG(request_info).request_method;
3464 +size_t fpm_php_content_length(TSRMLS_D)
3466 + return SG(request_info).content_length;
3469 +static void fpm_php_cleanup(int which, void *arg)
3472 + php_module_shutdown(TSRMLS_C);
3476 +void fpm_php_soft_quit()
3478 + fcgi_set_in_shutdown(1);
3481 +int fpm_php_init_main()
3483 + if (0 > fpm_cleanup_add(FPM_CLEANUP_PARENT, fpm_php_cleanup, 0)) {
3490 +int fpm_php_init_child(struct fpm_worker_pool_s *wp)
3492 + if (0 > fpm_php_apply_defines(wp) ||
3493 + 0 > fpm_php_set_allowed_clients(wp) ||
3494 + 0 > fpm_php_set_fcgi_mgmt_vars(wp)) {
3500 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_php.h php-5.2.17/sapi/cgi/fpm/fpm_php.h
3501 --- php-5.2.17.org/sapi/cgi/fpm/fpm_php.h 1970-01-01 01:00:00.000000000 +0100
3502 +++ php-5.2.17/sapi/cgi/fpm/fpm_php.h 2021-10-23 19:09:19.829791741 +0200
3506 + /* (c) 2007,2008 Andrei Nigmatulin */
3509 +#define FPM_PHP_H 1
3513 +#include "build-defs.h" /* for PHP_ defines */
3515 +struct fpm_worker_pool_s;
3517 +int fpm_php_init_child(struct fpm_worker_pool_s *wp);
3518 +char *fpm_php_script_filename(TSRMLS_D);
3519 +char *fpm_php_request_method(TSRMLS_D);
3520 +size_t fpm_php_content_length(TSRMLS_D);
3521 +void fpm_php_soft_quit();
3522 +int fpm_php_init_main();
3526 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_php_trace.c php-5.2.17/sapi/cgi/fpm/fpm_php_trace.c
3527 --- php-5.2.17.org/sapi/cgi/fpm/fpm_php_trace.c 1970-01-01 01:00:00.000000000 +0100
3528 +++ php-5.2.17/sapi/cgi/fpm/fpm_php_trace.c 2021-10-23 19:09:19.829791741 +0200
3532 + /* (c) 2007,2008 Andrei Nigmatulin */
3534 +#include "fpm_config.h"
3539 +#include "php_main.h"
3542 +#include <stddef.h>
3543 +#include <stdint.h>
3544 +#include <unistd.h>
3545 +#include <sys/time.h>
3546 +#include <sys/types.h>
3549 +#include "fpm_trace.h"
3550 +#include "fpm_php_trace.h"
3551 +#include "fpm_children.h"
3552 +#include "fpm_worker_pool.h"
3553 +#include "fpm_process_ctl.h"
3558 +#define valid_ptr(p) ((p) && 0 == ((p) & (sizeof(long) - 1)))
3560 +#if SIZEOF_LONG == 4
3561 +#define PTR_FMT "08"
3562 +#elif SIZEOF_LONG == 8
3563 +#define PTR_FMT "016"
3567 +static int fpm_php_trace_dump(struct fpm_child_s *child, FILE *slowlog TSRMLS_DC)
3569 + int callers_limit = 20;
3570 + pid_t pid = child->pid;
3571 + struct timeval tv;
3572 + static const int buf_size = 1024;
3573 + char buf[buf_size];
3574 + long execute_data;
3577 + gettimeofday(&tv, 0);
3579 + zlog_print_time(&tv, buf, buf_size);
3581 + fprintf(slowlog, "\n%s pid %d (pool %s)\n", buf, (int) pid, child->wp->config->name);
3583 + if (0 > fpm_trace_get_strz(buf, buf_size, (long) &SG(request_info).path_translated)) {
3587 + fprintf(slowlog, "script_filename = %s\n", buf);
3589 + if (0 > fpm_trace_get_long((long) &EG(current_execute_data), &l)) {
3595 + while (execute_data) {
3599 + fprintf(slowlog, "[0x%" PTR_FMT "lx] ", execute_data);
3601 + if (0 > fpm_trace_get_long(execute_data + offsetof(zend_execute_data, function_state.function), &l)) {
3607 + if (valid_ptr(function)) {
3608 + if (0 > fpm_trace_get_strz(buf, buf_size, function + offsetof(zend_function, common.function_name))) {
3612 + fprintf(slowlog, "%s()", buf);
3615 + fprintf(slowlog, "???");
3618 + if (0 > fpm_trace_get_long(execute_data + offsetof(zend_execute_data, op_array), &l)) {
3624 + if (valid_ptr(l)) {
3625 + long op_array = l;
3627 + if (0 > fpm_trace_get_strz(buf, buf_size, op_array + offsetof(zend_op_array, filename))) {
3632 + if (0 > fpm_trace_get_long(execute_data + offsetof(zend_execute_data, opline), &l)) {
3636 + if (valid_ptr(l)) {
3638 + uint *lu = (uint *) &l;
3640 + if (0 > fpm_trace_get_long(opline + offsetof(struct _zend_op, lineno), &l)) {
3647 + fprintf(slowlog, " %s:%u\n", *buf ? buf : "unknown", lineno);
3649 + if (0 > fpm_trace_get_long(execute_data + offsetof(zend_execute_data, prev_execute_data), &l)) {
3655 + if (0 == --callers_limit) {
3663 +void fpm_php_trace(struct fpm_child_s *child)
3668 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "about to trace %d", (int) child->pid);
3670 + slowlog = fopen(child->wp->config->slowlog, "a+");
3673 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "fopen(%s) failed", child->wp->config->slowlog);
3677 + if (0 > fpm_trace_ready(child->pid)) {
3681 + if (0 > fpm_php_trace_dump(child, slowlog TSRMLS_CC)) {
3682 + fprintf(slowlog, "+++ dump failed\n");
3685 + if (0 > fpm_trace_close(child->pid)) {
3693 + fpm_pctl_kill(child->pid, FPM_PCTL_CONT);
3694 + child->tracer = 0;
3696 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "finished trace of %d", (int) child->pid);
3701 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_php_trace.h php-5.2.17/sapi/cgi/fpm/fpm_php_trace.h
3702 --- php-5.2.17.org/sapi/cgi/fpm/fpm_php_trace.h 1970-01-01 01:00:00.000000000 +0100
3703 +++ php-5.2.17/sapi/cgi/fpm/fpm_php_trace.h 2021-10-23 19:09:19.829791741 +0200
3707 + /* (c) 2007,2008 Andrei Nigmatulin */
3709 +#ifndef FPM_PHP_TRACE_H
3710 +#define FPM_PHP_TRACE_H 1
3712 +struct fpm_child_s;
3714 +void fpm_php_trace(struct fpm_child_s *);
3718 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_process_ctl.c php-5.2.17/sapi/cgi/fpm/fpm_process_ctl.c
3719 --- php-5.2.17.org/sapi/cgi/fpm/fpm_process_ctl.c 1970-01-01 01:00:00.000000000 +0100
3720 +++ php-5.2.17/sapi/cgi/fpm/fpm_process_ctl.c 2021-10-23 19:09:19.829791741 +0200
3724 + /* (c) 2007,2008 Andrei Nigmatulin */
3726 +#include "fpm_config.h"
3728 +#include <sys/types.h>
3729 +#include <signal.h>
3730 +#include <unistd.h>
3731 +#include <stdlib.h>
3734 +#include "fpm_clock.h"
3735 +#include "fpm_children.h"
3736 +#include "fpm_signals.h"
3737 +#include "fpm_events.h"
3738 +#include "fpm_process_ctl.h"
3739 +#include "fpm_cleanup.h"
3740 +#include "fpm_request.h"
3741 +#include "fpm_worker_pool.h"
3745 +static int fpm_state = FPM_PCTL_STATE_NORMAL;
3746 +static int fpm_signal_sent = 0;
3749 +static const char *fpm_state_names[] = {
3750 + [FPM_PCTL_STATE_NORMAL] = "normal",
3751 + [FPM_PCTL_STATE_RELOADING] = "reloading",
3752 + [FPM_PCTL_STATE_TERMINATING] = "terminating",
3753 + [FPM_PCTL_STATE_FINISHING] = "finishing"
3756 +static int saved_argc;
3757 +static char **saved_argv;
3759 +static void fpm_pctl_cleanup(int which, void *arg)
3763 + if (which != FPM_CLEANUP_PARENT_EXEC) {
3765 + for (i = 0; i < saved_argc; i++) {
3766 + free(saved_argv[i]);
3774 +static struct event pctl_event;
3776 +static void fpm_pctl_action(int fd, short which, void *arg)
3778 + evtimer_del(&pctl_event);
3780 + memset(&pctl_event, 0, sizeof(pctl_event));
3782 + fpm_pctl(FPM_PCTL_STATE_UNSPECIFIED, FPM_PCTL_ACTION_TIMEOUT);
3785 +static int fpm_pctl_timeout_set(int sec)
3787 + struct timeval tv = { .tv_sec = sec, .tv_usec = 0 };
3789 + if (evtimer_initialized(&pctl_event)) {
3790 + evtimer_del(&pctl_event);
3793 + evtimer_set(&pctl_event, &fpm_pctl_action, 0);
3795 + evtimer_add(&pctl_event, &tv);
3800 +static void fpm_pctl_exit()
3802 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "exiting, bye-bye!");
3804 + fpm_conf_unlink_pid();
3806 + fpm_cleanups_run(FPM_CLEANUP_PARENT_EXIT_MAIN);
3811 +#define optional_arg(c) (saved_argc > c ? ", \"" : ""), (saved_argc > c ? saved_argv[c] : ""), (saved_argc > c ? "\"" : "")
3813 +static void fpm_pctl_exec()
3816 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "reloading: execvp(\"%s\", {\"%s\""
3817 + "%s%s%s" "%s%s%s" "%s%s%s" "%s%s%s" "%s%s%s"
3818 + "%s%s%s" "%s%s%s" "%s%s%s" "%s%s%s" "%s%s%s"
3820 + saved_argv[0], saved_argv[0],
3833 + fpm_cleanups_run(FPM_CLEANUP_PARENT_EXEC);
3835 + execvp(saved_argv[0], saved_argv);
3837 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "execvp() failed");
3842 +static void fpm_pctl_action_last()
3844 + switch (fpm_state) {
3846 + case FPM_PCTL_STATE_RELOADING :
3851 + case FPM_PCTL_STATE_FINISHING :
3853 + case FPM_PCTL_STATE_TERMINATING :
3860 +int fpm_pctl_kill(pid_t pid, int how)
3865 + case FPM_PCTL_TERM :
3868 + case FPM_PCTL_STOP :
3871 + case FPM_PCTL_CONT :
3878 + return kill(pid, s);
3881 +static void fpm_pctl_kill_all(int signo)
3883 + struct fpm_worker_pool_s *wp;
3884 + int alive_children = 0;
3886 + for (wp = fpm_worker_all_pools; wp; wp = wp->next) {
3887 + struct fpm_child_s *child;
3889 + for (child = wp->children; child; child = child->next) {
3891 + int res = kill(child->pid, signo);
3893 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "sending signal %d %s to child %d (pool %s)", signo,
3894 + fpm_signal_names[signo] ? fpm_signal_names[signo] : "",
3895 + (int) child->pid, child->wp->config->name);
3897 + if (res == 0) ++alive_children;
3901 + if (alive_children) {
3902 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "%d %s still alive", alive_children, alive_children == 1 ? "child is" : "children are");
3906 +static void fpm_pctl_action_next()
3910 + if (!fpm_globals.running_children) fpm_pctl_action_last();
3912 + if (fpm_signal_sent == 0) {
3913 + if (fpm_state == FPM_PCTL_STATE_TERMINATING) {
3919 + timeout = fpm_global_config.process_control_timeout;
3922 + if (fpm_signal_sent == SIGQUIT) {
3931 + fpm_pctl_kill_all(sig);
3933 + fpm_signal_sent = sig;
3935 + fpm_pctl_timeout_set(timeout);
3938 +void fpm_pctl(int new_state, int action)
3942 + case FPM_PCTL_ACTION_SET :
3944 + if (fpm_state == new_state) { /* already in progress - just ignore duplicate signal */
3948 + switch (fpm_state) { /* check which states can be overridden */
3950 + case FPM_PCTL_STATE_NORMAL :
3952 + /* 'normal' can be overridden by any other state */
3955 + case FPM_PCTL_STATE_RELOADING :
3957 + /* 'reloading' can be overridden by 'finishing' */
3958 + if (new_state == FPM_PCTL_STATE_FINISHING) break;
3960 + case FPM_PCTL_STATE_FINISHING :
3962 + /* 'reloading' and 'finishing' can be overridden by 'terminating' */
3963 + if (new_state == FPM_PCTL_STATE_TERMINATING) break;
3965 + case FPM_PCTL_STATE_TERMINATING :
3967 + /* nothing can override 'terminating' state */
3968 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "not switching to '%s' state, because already in '%s' state",
3969 + fpm_state_names[new_state], fpm_state_names[fpm_state]);
3974 + fpm_signal_sent = 0;
3975 + fpm_state = new_state;
3977 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "switching to '%s' state", fpm_state_names[fpm_state]);
3981 + case FPM_PCTL_ACTION_TIMEOUT :
3983 + fpm_pctl_action_next();
3987 + case FPM_PCTL_ACTION_LAST_CHILD_EXITED :
3989 + fpm_pctl_action_last();
3996 +int fpm_pctl_can_spawn_children()
3998 + return fpm_state == FPM_PCTL_STATE_NORMAL;
4001 +int fpm_pctl_child_exited()
4003 + if (fpm_state == FPM_PCTL_STATE_NORMAL) return 0;
4005 + if (!fpm_globals.running_children) {
4006 + fpm_pctl(FPM_PCTL_STATE_UNSPECIFIED, FPM_PCTL_ACTION_LAST_CHILD_EXITED);
4012 +int fpm_pctl_init_main()
4016 + saved_argc = fpm_globals.argc;
4018 + saved_argv = malloc(sizeof(char *) * (saved_argc + 1));
4020 + if (!saved_argv) {
4024 + for (i = 0; i < saved_argc; i++) {
4025 + saved_argv[i] = strdup(fpm_globals.argv[i]);
4027 + if (!saved_argv[i]) {
4032 + saved_argv[i] = 0;
4034 + if (0 > fpm_cleanup_add(FPM_CLEANUP_ALL, fpm_pctl_cleanup, 0)) {
4041 +static void fpm_pctl_check_request_timeout(struct timeval *now)
4043 + struct fpm_worker_pool_s *wp;
4045 + for (wp = fpm_worker_all_pools; wp; wp = wp->next) {
4046 + int terminate_timeout = wp->config->request_terminate_timeout;
4047 + int slowlog_timeout = wp->config->request_slowlog_timeout;
4048 + struct fpm_child_s *child;
4050 + if (terminate_timeout || slowlog_timeout) {
4051 + for (child = wp->children; child; child = child->next) {
4052 + fpm_request_check_timed_out(child, now, terminate_timeout, slowlog_timeout);
4059 +void fpm_pctl_heartbeat(int fd, short which, void *arg)
4061 + static struct event heartbeat;
4062 + struct timeval tv = { .tv_sec = 0, .tv_usec = 130000 };
4063 + struct timeval now;
4065 + if (which == EV_TIMEOUT) {
4066 + evtimer_del(&heartbeat);
4067 + fpm_clock_get(&now);
4068 + fpm_pctl_check_request_timeout(&now);
4071 + evtimer_set(&heartbeat, &fpm_pctl_heartbeat, 0);
4073 + evtimer_add(&heartbeat, &tv);
4076 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_process_ctl.h php-5.2.17/sapi/cgi/fpm/fpm_process_ctl.h
4077 --- php-5.2.17.org/sapi/cgi/fpm/fpm_process_ctl.h 1970-01-01 01:00:00.000000000 +0100
4078 +++ php-5.2.17/sapi/cgi/fpm/fpm_process_ctl.h 2021-10-23 19:09:19.829791741 +0200
4082 + /* (c) 2007,2008 Andrei Nigmatulin */
4084 +#ifndef FPM_PROCESS_CTL_H
4085 +#define FPM_PROCESS_CTL_H 1
4087 +struct fpm_child_s;
4089 +void fpm_pctl(int new_state, int action);
4090 +int fpm_pctl_can_spawn_children();
4091 +int fpm_pctl_kill(pid_t pid, int how);
4092 +void fpm_pctl_heartbeat(int fd, short which, void *arg);
4093 +int fpm_pctl_child_exited();
4094 +int fpm_pctl_init_main();
4098 + FPM_PCTL_STATE_UNSPECIFIED,
4099 + FPM_PCTL_STATE_NORMAL,
4100 + FPM_PCTL_STATE_RELOADING,
4101 + FPM_PCTL_STATE_TERMINATING,
4102 + FPM_PCTL_STATE_FINISHING
4106 + FPM_PCTL_ACTION_SET,
4107 + FPM_PCTL_ACTION_TIMEOUT,
4108 + FPM_PCTL_ACTION_LAST_CHILD_EXITED
4119 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_request.c php-5.2.17/sapi/cgi/fpm/fpm_request.c
4120 --- php-5.2.17.org/sapi/cgi/fpm/fpm_request.c 1970-01-01 01:00:00.000000000 +0100
4121 +++ php-5.2.17/sapi/cgi/fpm/fpm_request.c 2021-10-23 19:09:19.829791741 +0200
4125 + /* (c) 2007,2008 Andrei Nigmatulin */
4127 +#include "fpm_config.h"
4129 +#include "fpm_php.h"
4130 +#include "fpm_str.h"
4131 +#include "fpm_clock.h"
4132 +#include "fpm_conf.h"
4133 +#include "fpm_trace.h"
4134 +#include "fpm_php_trace.h"
4135 +#include "fpm_process_ctl.h"
4136 +#include "fpm_children.h"
4137 +#include "fpm_shm_slots.h"
4138 +#include "fpm_request.h"
4142 +void fpm_request_accepting()
4144 + struct fpm_shm_slot_s *slot;
4146 + slot = fpm_shm_slots_acquire(0, 0);
4148 + slot->request_stage = FPM_REQUEST_ACCEPTING;
4150 + fpm_clock_get(&slot->tv);
4151 + memset(slot->request_method, 0, sizeof(slot->request_method));
4152 + slot->content_length = 0;
4153 + memset(slot->script_filename, 0, sizeof(slot->script_filename));
4155 + fpm_shm_slots_release(slot);
4158 +void fpm_request_reading_headers()
4160 + struct fpm_shm_slot_s *slot;
4162 + slot = fpm_shm_slots_acquire(0, 0);
4164 + slot->request_stage = FPM_REQUEST_READING_HEADERS;
4166 + fpm_clock_get(&slot->tv);
4167 + slot->accepted = slot->tv;
4169 + fpm_shm_slots_release(slot);
4172 +void fpm_request_info()
4175 + struct fpm_shm_slot_s *slot;
4176 + char *request_method = fpm_php_request_method(TSRMLS_C);
4177 + char *script_filename = fpm_php_script_filename(TSRMLS_C);
4179 + slot = fpm_shm_slots_acquire(0, 0);
4181 + slot->request_stage = FPM_REQUEST_INFO;
4183 + fpm_clock_get(&slot->tv);
4185 + if (request_method) {
4186 + cpystrn(slot->request_method, request_method, sizeof(slot->request_method));
4189 + slot->content_length = fpm_php_content_length(TSRMLS_C);
4191 + /* if cgi.fix_pathinfo is set to "1" and script cannot be found (404)
4192 + the sapi_globals.request_info.path_translated is set to NULL */
4193 + if (script_filename) {
4194 + cpystrn(slot->script_filename, script_filename, sizeof(slot->script_filename));
4197 + fpm_shm_slots_release(slot);
4200 +void fpm_request_executing()
4202 + struct fpm_shm_slot_s *slot;
4204 + slot = fpm_shm_slots_acquire(0, 0);
4206 + slot->request_stage = FPM_REQUEST_EXECUTING;
4208 + fpm_clock_get(&slot->tv);
4210 + fpm_shm_slots_release(slot);
4213 +void fpm_request_finished()
4215 + struct fpm_shm_slot_s *slot;
4217 + slot = fpm_shm_slots_acquire(0, 0);
4219 + slot->request_stage = FPM_REQUEST_FINISHED;
4221 + fpm_clock_get(&slot->tv);
4222 + memset(&slot->accepted, 0, sizeof(slot->accepted));
4224 + fpm_shm_slots_release(slot);
4227 +void fpm_request_check_timed_out(struct fpm_child_s *child, struct timeval *now, int terminate_timeout, int slowlog_timeout)
4229 + struct fpm_shm_slot_s *slot;
4230 + struct fpm_shm_slot_s slot_c;
4232 + slot = fpm_shm_slot(child);
4234 + if (!fpm_shm_slots_acquire(slot, 1)) {
4240 + fpm_shm_slots_release(slot);
4243 + if (child->slow_logged.tv_sec) {
4244 + if (child->slow_logged.tv_sec != slot_c.accepted.tv_sec || child->slow_logged.tv_usec != slot_c.accepted.tv_usec) {
4245 + child->slow_logged.tv_sec = 0;
4246 + child->slow_logged.tv_usec = 0;
4251 + if (slot_c.request_stage > FPM_REQUEST_ACCEPTING && slot_c.request_stage < FPM_REQUEST_FINISHED) {
4252 + char purified_script_filename[sizeof(slot_c.script_filename)];
4253 + struct timeval tv;
4255 + timersub(now, &slot_c.accepted, &tv);
4258 + if (child->slow_logged.tv_sec == 0 && slowlog_timeout &&
4259 + slot_c.request_stage == FPM_REQUEST_EXECUTING && tv.tv_sec >= slowlog_timeout) {
4261 + str_purify_filename(purified_script_filename, slot_c.script_filename, sizeof(slot_c.script_filename));
4263 + child->slow_logged = slot_c.accepted;
4264 + child->tracer = fpm_php_trace;
4266 + fpm_trace_signal(child->pid);
4268 + zlog(ZLOG_STUFF, ZLOG_WARNING, "child %d, script '%s' (pool %s) executing too slow (%d.%06d sec), logging",
4269 + (int) child->pid, purified_script_filename, child->wp->config->name, (int) tv.tv_sec, (int) tv.tv_usec);
4274 + if (terminate_timeout && tv.tv_sec >= terminate_timeout) {
4276 + str_purify_filename(purified_script_filename, slot_c.script_filename, sizeof(slot_c.script_filename));
4278 + fpm_pctl_kill(child->pid, FPM_PCTL_TERM);
4280 + zlog(ZLOG_STUFF, ZLOG_WARNING, "child %d, script '%s' (pool %s) execution timed out (%d.%06d sec), terminating",
4281 + (int) child->pid, purified_script_filename, child->wp->config->name, (int) tv.tv_sec, (int) tv.tv_usec);
4287 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_request.h php-5.2.17/sapi/cgi/fpm/fpm_request.h
4288 --- php-5.2.17.org/sapi/cgi/fpm/fpm_request.h 1970-01-01 01:00:00.000000000 +0100
4289 +++ php-5.2.17/sapi/cgi/fpm/fpm_request.h 2021-10-23 19:09:19.829791741 +0200
4293 + /* (c) 2007,2008 Andrei Nigmatulin */
4295 +#ifndef FPM_REQUEST_H
4296 +#define FPM_REQUEST_H 1
4298 +void fpm_request_accepting(); /* hanging in accept() */
4299 +void fpm_request_reading_headers(); /* start reading fastcgi request from very first byte */
4300 +void fpm_request_info(); /* not a stage really but a point in the php code, where all request params have become known to sapi */
4301 +void fpm_request_executing(); /* the script is executing */
4302 +void fpm_request_finished(); /* request processed: script response have been sent to web server */
4304 +struct fpm_child_s;
4307 +void fpm_request_check_timed_out(struct fpm_child_s *child, struct timeval *tv, int terminate_timeout, int slowlog_timeout);
4309 +enum fpm_request_stage_e {
4310 + FPM_REQUEST_ACCEPTING = 1,
4311 + FPM_REQUEST_READING_HEADERS,
4313 + FPM_REQUEST_EXECUTING,
4314 + FPM_REQUEST_FINISHED
4318 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_shm.c php-5.2.17/sapi/cgi/fpm/fpm_shm.c
4319 --- php-5.2.17.org/sapi/cgi/fpm/fpm_shm.c 1970-01-01 01:00:00.000000000 +0100
4320 +++ php-5.2.17/sapi/cgi/fpm/fpm_shm.c 2021-10-23 19:09:19.829791741 +0200
4324 + /* (c) 2007,2008 Andrei Nigmatulin */
4326 +#include "fpm_config.h"
4328 +#include <unistd.h>
4329 +#include <sys/mman.h>
4330 +#include <stdlib.h>
4332 +#include "fpm_shm.h"
4336 +/* MAP_ANON is depricated, but not in macosx */
4337 +#if defined(MAP_ANON) && !defined(MAP_ANONYMOUS)
4338 +#define MAP_ANONYMOUS MAP_ANON
4342 +struct fpm_shm_s *fpm_shm_alloc(size_t sz)
4344 + struct fpm_shm_s *shm;
4346 + shm = malloc(sizeof(*shm));
4352 + shm->mem = mmap(0, sz, PROT_READ | PROT_WRITE, MAP_ANONYMOUS | MAP_SHARED, -1, 0);
4355 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "mmap(MAP_ANONYMOUS | MAP_SHARED) failed");
4366 +static void fpm_shm_free(struct fpm_shm_s *shm, int do_unmap)
4369 + munmap(shm->mem, shm->sz);
4375 +void fpm_shm_free_list(struct fpm_shm_s *shm, void *mem)
4377 + struct fpm_shm_s *next;
4379 + for (; shm; shm = next) {
4382 + fpm_shm_free(shm, mem != shm->mem);
4386 +void *fpm_shm_alloc_chunk(struct fpm_shm_s **head, size_t sz, void **mem)
4388 + size_t pagesize = getpagesize();
4389 + static const size_t cache_line_size = 16;
4390 + size_t aligned_sz;
4391 + struct fpm_shm_s *shm;
4394 + sz = (sz + cache_line_size - 1) & -cache_line_size;
4398 + if (0 == shm || shm->sz - shm->used < sz) {
4399 + /* allocate one more shm segment */
4401 + aligned_sz = (sz + pagesize - 1) & -pagesize;
4403 + shm = fpm_shm_alloc(aligned_sz);
4409 + shm->next = *head;
4410 + if (shm->next) shm->next->prev = shm;
4416 + ret = (char *) shm->mem + shm->used;
4422 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_shm.h php-5.2.17/sapi/cgi/fpm/fpm_shm.h
4423 --- php-5.2.17.org/sapi/cgi/fpm/fpm_shm.h 1970-01-01 01:00:00.000000000 +0100
4424 +++ php-5.2.17/sapi/cgi/fpm/fpm_shm.h 2021-10-23 19:09:19.829791741 +0200
4428 + /* (c) 2007,2008 Andrei Nigmatulin */
4431 +#define FPM_SHM_H 1
4436 + struct fpm_shm_s *prev, *next;
4442 +struct fpm_shm_s *fpm_shm_alloc(size_t sz);
4443 +void fpm_shm_free_list(struct fpm_shm_s *, void *);
4444 +void *fpm_shm_alloc_chunk(struct fpm_shm_s **head, size_t sz, void **mem);
4448 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_shm_slots.c php-5.2.17/sapi/cgi/fpm/fpm_shm_slots.c
4449 --- php-5.2.17.org/sapi/cgi/fpm/fpm_shm_slots.c 1970-01-01 01:00:00.000000000 +0100
4450 +++ php-5.2.17/sapi/cgi/fpm/fpm_shm_slots.c 2021-10-23 19:09:19.829791741 +0200
4454 + /* (c) 2007,2008 Andrei Nigmatulin */
4456 +#include "fpm_config.h"
4458 +#include "fpm_atomic.h"
4459 +#include "fpm_worker_pool.h"
4460 +#include "fpm_children.h"
4461 +#include "fpm_shm.h"
4462 +#include "fpm_shm_slots.h"
4465 +static void *shm_mem;
4466 +static struct fpm_shm_slot_s *shm_slot;
4468 +int fpm_shm_slots_prepare_slot(struct fpm_child_s *child)
4470 + struct fpm_worker_pool_s *wp = child->wp;
4471 + struct fpm_shm_slot_ptr_s *shm_slot_ptr;
4473 + child->shm_slot_i = wp->slots_used.used;
4475 + shm_slot_ptr = fpm_array_push(&wp->slots_used);
4477 + if (0 == shm_slot_ptr) {
4481 + if (0 == wp->slots_free.used) {
4482 + shm_slot_ptr->shm_slot = fpm_shm_alloc_chunk(&wp->shm_list, sizeof(struct fpm_shm_slot_s), &shm_slot_ptr->mem);
4484 + if (!shm_slot_ptr->shm_slot) {
4489 + *shm_slot_ptr = *(struct fpm_shm_slot_ptr_s *) fpm_array_item_last(&wp->slots_free);
4491 + --wp->slots_free.used;
4494 + memset(shm_slot_ptr->shm_slot, 0, sizeof(struct fpm_shm_slot_s));
4496 + shm_slot_ptr->child = child;
4501 +void fpm_shm_slots_discard_slot(struct fpm_child_s *child)
4503 + struct fpm_shm_slot_ptr_s *shm_slot_ptr;
4504 + struct fpm_worker_pool_s *wp = child->wp;
4507 + shm_slot_ptr = fpm_array_push(&wp->slots_free);
4509 + if (shm_slot_ptr) {
4511 + struct fpm_shm_slot_ptr_s *shm_slot_ptr_used;
4513 + shm_slot_ptr_used = fpm_array_item(&wp->slots_used, child->shm_slot_i);
4515 + *shm_slot_ptr = *shm_slot_ptr_used;
4517 + shm_slot_ptr->child = 0;
4521 + n = fpm_array_item_remove(&wp->slots_used, child->shm_slot_i);
4524 + shm_slot_ptr = fpm_array_item(&wp->slots_used, n);
4526 + shm_slot_ptr->child->shm_slot_i = n;
4530 +void fpm_shm_slots_child_use_slot(struct fpm_child_s *child)
4532 + struct fpm_shm_slot_ptr_s *shm_slot_ptr;
4533 + struct fpm_worker_pool_s *wp = child->wp;
4535 + shm_slot_ptr = fpm_array_item(&wp->slots_used, child->shm_slot_i);
4537 + shm_slot = shm_slot_ptr->shm_slot;
4538 + shm_mem = shm_slot_ptr->mem;
4541 +void fpm_shm_slots_parent_use_slot(struct fpm_child_s *child)
4543 + /* nothing to do */
4546 +void *fpm_shm_slots_mem()
4551 +struct fpm_shm_slot_s *fpm_shm_slot(struct fpm_child_s *child)
4553 + struct fpm_shm_slot_ptr_s *shm_slot_ptr;
4554 + struct fpm_worker_pool_s *wp = child->wp;
4556 + shm_slot_ptr = fpm_array_item(&wp->slots_used, child->shm_slot_i);
4558 + return shm_slot_ptr->shm_slot;
4561 +struct fpm_shm_slot_s *fpm_shm_slots_acquire(struct fpm_shm_slot_s *s, int nohang)
4567 + if (0 > fpm_spinlock(&s->lock, nohang)) {
4574 +void fpm_shm_slots_release(struct fpm_shm_slot_s *s)
4579 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_shm_slots.h php-5.2.17/sapi/cgi/fpm/fpm_shm_slots.h
4580 --- php-5.2.17.org/sapi/cgi/fpm/fpm_shm_slots.h 1970-01-01 01:00:00.000000000 +0100
4581 +++ php-5.2.17/sapi/cgi/fpm/fpm_shm_slots.h 2021-10-23 19:09:19.833125073 +0200
4585 + /* (c) 2007,2008 Andrei Nigmatulin */
4587 +#ifndef FPM_SHM_SLOTS_H
4588 +#define FPM_SHM_SLOTS_H 1
4590 +#include "fpm_atomic.h"
4591 +#include "fpm_worker_pool.h"
4592 +#include "fpm_request.h"
4594 +struct fpm_child_s;
4596 +struct fpm_shm_slot_s {
4601 + enum fpm_request_stage_e request_stage;
4602 + struct timeval accepted;
4603 + struct timeval tv;
4604 + char request_method[16];
4605 + size_t content_length; /* used with POST only */
4606 + char script_filename[256];
4609 +struct fpm_shm_slot_ptr_s {
4611 + struct fpm_shm_slot_s *shm_slot;
4612 + struct fpm_child_s *child;
4615 +int fpm_shm_slots_prepare_slot(struct fpm_child_s *child);
4616 +void fpm_shm_slots_discard_slot(struct fpm_child_s *child);
4617 +void fpm_shm_slots_child_use_slot(struct fpm_child_s *child);
4618 +void fpm_shm_slots_parent_use_slot(struct fpm_child_s *child);
4619 +void *fpm_shm_slots_mem();
4620 +struct fpm_shm_slot_s *fpm_shm_slot(struct fpm_child_s *child);
4621 +struct fpm_shm_slot_s *fpm_shm_slots_acquire(struct fpm_shm_slot_s *, int nohang);
4622 +void fpm_shm_slots_release(struct fpm_shm_slot_s *);
4626 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_signals.c php-5.2.17/sapi/cgi/fpm/fpm_signals.c
4627 --- php-5.2.17.org/sapi/cgi/fpm/fpm_signals.c 1970-01-01 01:00:00.000000000 +0100
4628 +++ php-5.2.17/sapi/cgi/fpm/fpm_signals.c 2021-10-23 19:09:19.833125073 +0200
4632 + /* (c) 2007,2008 Andrei Nigmatulin */
4634 +#include "fpm_config.h"
4636 +#include <signal.h>
4638 +#include <sys/types.h>
4639 +#include <sys/socket.h>
4640 +#include <stdlib.h>
4641 +#include <string.h>
4643 +#include <unistd.h>
4647 +#include "fpm_signals.h"
4648 +#include "fpm_sockets.h"
4649 +#include "fpm_php.h"
4654 +const char *fpm_signal_names[NSIG + 1] = {
4656 + [SIGHUP] = "SIGHUP",
4659 + [SIGINT] = "SIGINT",
4662 + [SIGQUIT] = "SIGQUIT",
4665 + [SIGILL] = "SIGILL",
4668 + [SIGTRAP] = "SIGTRAP",
4671 + [SIGABRT] = "SIGABRT",
4674 + [SIGEMT] = "SIGEMT",
4677 + [SIGBUS] = "SIGBUS",
4680 + [SIGFPE] = "SIGFPE",
4683 + [SIGKILL] = "SIGKILL",
4686 + [SIGUSR1] = "SIGUSR1",
4689 + [SIGSEGV] = "SIGSEGV",
4692 + [SIGUSR2] = "SIGUSR2",
4695 + [SIGPIPE] = "SIGPIPE",
4698 + [SIGALRM] = "SIGALRM",
4701 + [SIGTERM] = "SIGTERM",
4704 + [SIGCHLD] = "SIGCHLD",
4707 + [SIGCONT] = "SIGCONT",
4710 + [SIGSTOP] = "SIGSTOP",
4713 + [SIGTSTP] = "SIGTSTP",
4716 + [SIGTTIN] = "SIGTTIN",
4719 + [SIGTTOU] = "SIGTTOU",
4722 + [SIGURG] = "SIGURG",
4725 + [SIGXCPU] = "SIGXCPU",
4728 + [SIGXFSZ] = "SIGXFSZ",
4731 + [SIGVTALRM] = "SIGVTALRM",
4734 + [SIGPROF] = "SIGPROF",
4737 + [SIGWINCH] = "SIGWINCH",
4740 + [SIGINFO] = "SIGINFO",
4743 + [SIGIO] = "SIGIO",
4746 + [SIGPWR] = "SIGPWR",
4749 + [SIGSYS] = "SIGSYS",
4752 + [SIGWAITING] = "SIGWAITING",
4755 + [SIGLWP] = "SIGLWP",
4758 + [SIGFREEZE] = "SIGFREEZE",
4761 + [SIGTHAW] = "SIGTHAW",
4764 + [SIGCANCEL] = "SIGCANCEL",
4767 + [SIGLOST] = "SIGLOST",
4771 +static void sig_soft_quit(int signo)
4773 + int saved_errno = errno;
4775 + /* closing fastcgi listening socket will force fcgi_accept() exit immediately */
4777 + socket(AF_UNIX, SOCK_STREAM, 0);
4779 + fpm_php_soft_quit();
4781 + errno = saved_errno;
4784 +static void sig_handler(int signo)
4786 + static const char sig_chars[NSIG + 1] = {
4797 + if (fpm_globals.parent_pid != getpid()) {
4798 + /* prevent a signal race condition when child process
4799 + have not set up it's own signal handler yet */
4803 + saved_errno = errno;
4805 + s = sig_chars[signo];
4807 + write(sp[1], &s, sizeof(s));
4809 + errno = saved_errno;
4812 +int fpm_signals_init_main()
4814 + struct sigaction act;
4816 + if (0 > socketpair(AF_UNIX, SOCK_STREAM, 0, sp)) {
4817 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "socketpair() failed");
4821 + if (0 > fd_set_blocked(sp[0], 0) || 0 > fd_set_blocked(sp[1], 0)) {
4822 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "fd_set_blocked() failed");
4826 + if (0 > fcntl(sp[0], F_SETFD, FD_CLOEXEC) || 0 > fcntl(sp[1], F_SETFD, FD_CLOEXEC)) {
4827 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "fcntl(F_SETFD, FD_CLOEXEC) failed");
4831 + memset(&act, 0, sizeof(act));
4832 + act.sa_handler = sig_handler;
4833 + sigfillset(&act.sa_mask);
4835 + if (0 > sigaction(SIGTERM, &act, 0) ||
4836 + 0 > sigaction(SIGINT, &act, 0) ||
4837 + 0 > sigaction(SIGUSR1, &act, 0) ||
4838 + 0 > sigaction(SIGUSR2, &act, 0) ||
4839 + 0 > sigaction(SIGCHLD, &act, 0) ||
4840 + 0 > sigaction(SIGQUIT, &act, 0)) {
4842 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "sigaction() failed");
4849 +int fpm_signals_init_child()
4851 + struct sigaction act, act_dfl;
4853 + memset(&act, 0, sizeof(act));
4854 + memset(&act_dfl, 0, sizeof(act_dfl));
4856 + act.sa_handler = &sig_soft_quit;
4857 + act.sa_flags |= SA_RESTART;
4859 + act_dfl.sa_handler = SIG_DFL;
4864 + if (0 > sigaction(SIGTERM, &act_dfl, 0) ||
4865 + 0 > sigaction(SIGINT, &act_dfl, 0) ||
4866 + 0 > sigaction(SIGUSR1, &act_dfl, 0) ||
4867 + 0 > sigaction(SIGUSR2, &act_dfl, 0) ||
4868 + 0 > sigaction(SIGCHLD, &act_dfl, 0) ||
4869 + 0 > sigaction(SIGQUIT, &act, 0)) {
4871 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "sigaction() failed");
4878 +int fpm_signals_get_fd()
4882 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_signals.h php-5.2.17/sapi/cgi/fpm/fpm_signals.h
4883 --- php-5.2.17.org/sapi/cgi/fpm/fpm_signals.h 1970-01-01 01:00:00.000000000 +0100
4884 +++ php-5.2.17/sapi/cgi/fpm/fpm_signals.h 2021-10-23 19:09:19.833125073 +0200
4888 + /* (c) 2007,2008 Andrei Nigmatulin */
4890 +#ifndef FPM_SIGNALS_H
4891 +#define FPM_SIGNALS_H 1
4893 +#include <signal.h>
4895 +int fpm_signals_init_main();
4896 +int fpm_signals_init_child();
4897 +int fpm_signals_get_fd();
4899 +extern const char *fpm_signal_names[NSIG + 1];
4902 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_sockets.c php-5.2.17/sapi/cgi/fpm/fpm_sockets.c
4903 --- php-5.2.17.org/sapi/cgi/fpm/fpm_sockets.c 1970-01-01 01:00:00.000000000 +0100
4904 +++ php-5.2.17/sapi/cgi/fpm/fpm_sockets.c 2021-10-23 19:09:19.833125073 +0200
4908 + /* (c) 2007,2008 Andrei Nigmatulin */
4910 +#include "fpm_config.h"
4912 +#ifdef HAVE_ALLOCA_H
4913 +#include <alloca.h>
4915 +#include <sys/types.h>
4916 +#include <sys/stat.h> /* for chmod(2) */
4917 +#include <sys/socket.h>
4918 +#include <netinet/in.h>
4919 +#include <arpa/inet.h>
4920 +#include <sys/un.h>
4923 +#include <stdlib.h>
4924 +#include <string.h>
4926 +#include <unistd.h>
4929 +#include "fpm_arrays.h"
4930 +#include "fpm_sockets.h"
4931 +#include "fpm_worker_pool.h"
4932 +#include "fpm_unix.h"
4933 +#include "fpm_str.h"
4934 +#include "fpm_env.h"
4935 +#include "fpm_cleanup.h"
4937 +struct listening_socket_s {
4944 +static struct fpm_array_s sockets_list;
4946 +static int fpm_sockets_resolve_af_inet(char *node, char *service, struct sockaddr_in *addr)
4948 + struct addrinfo *res;
4949 + struct addrinfo hints;
4952 + memset(&hints, 0, sizeof(hints));
4954 + hints.ai_family = AF_INET;
4956 + ret = getaddrinfo(node, service, &hints, &res);
4959 + zlog(ZLOG_STUFF, ZLOG_ERROR, "can't resolve hostname '%s%s%s': getaddrinfo said: %s%s%s\n",
4960 + node, service ? ":" : "", service ? service : "",
4961 + gai_strerror(ret), ret == EAI_SYSTEM ? ", system error: " : "", ret == EAI_SYSTEM ? strerror(errno) : "");
4965 + *addr = *(struct sockaddr_in *) res->ai_addr;
4967 + freeaddrinfo(res);
4972 +enum { FPM_GET_USE_SOCKET = 1, FPM_STORE_SOCKET = 2, FPM_STORE_USE_SOCKET = 3 };
4974 +static void fpm_sockets_cleanup(int which, void *arg)
4977 + char *env_value = 0;
4979 + struct listening_socket_s *ls = sockets_list.data;
4981 + for (i = 0; i < sockets_list.used; i++, ls++) {
4983 + if (which != FPM_CLEANUP_PARENT_EXEC) {
4988 + else { /* on PARENT EXEC we want socket fds to be inherited through environment variable */
4990 + sprintf(fd, "%d", ls->sock);
4991 + env_value = realloc(env_value, p + (p ? 1 : 0) + strlen(ls->key) + 1 + strlen(fd) + 1);
4992 + p += sprintf(env_value + p, "%s%s=%s", p ? "," : "", ls->key, fd);
4995 + if (which == FPM_CLEANUP_PARENT_EXIT_MAIN) {
4997 + if (ls->type == FPM_AF_UNIX) {
5007 + setenv("FPM_SOCKETS", env_value, 1);
5011 + fpm_array_free(&sockets_list);
5014 +static int fpm_sockets_hash_op(int sock, struct sockaddr *sa, char *key, int type, int op)
5017 + if (key == NULL) {
5021 + case FPM_AF_INET : {
5022 + struct sockaddr_in *sa_in = (struct sockaddr_in *) sa;
5024 + key = alloca(sizeof("xxx.xxx.xxx.xxx:ppppp"));
5026 + sprintf(key, "%u.%u.%u.%u:%u", IPQUAD(&sa_in->sin_addr), (unsigned int) ntohs(sa_in->sin_port));
5031 + case FPM_AF_UNIX : {
5032 + struct sockaddr_un *sa_un = (struct sockaddr_un *) sa;
5034 + key = alloca(strlen(sa_un->sun_path) + 1);
5036 + strcpy(key, sa_un->sun_path);
5050 + case FPM_GET_USE_SOCKET :
5054 + struct listening_socket_s *ls = sockets_list.data;
5056 + for (i = 0; i < sockets_list.used; i++, ls++) {
5058 + if (!strcmp(ls->key, key)) {
5067 + case FPM_STORE_SOCKET : /* inherited socket */
5068 + case FPM_STORE_USE_SOCKET : /* just created */
5071 + struct listening_socket_s *ls;
5073 + ls = fpm_array_push(&sockets_list);
5079 + if (op == FPM_STORE_SOCKET) {
5087 + ls->key = strdup(key);
5098 +static int fpm_sockets_new_listening_socket(struct fpm_worker_pool_s *wp, struct sockaddr *sa, int socklen)
5103 + mode_t saved_umask;
5105 + /* we have custom backlog value */
5106 + if (wp->config->listen_options) {
5107 + backlog = wp->config->listen_options->backlog;
5110 + sock = socket(sa->sa_family, SOCK_STREAM, 0);
5113 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "socket() failed");
5117 + setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &flags, sizeof(flags));
5119 + if (wp->listen_address_domain == FPM_AF_UNIX) {
5120 + unlink( ((struct sockaddr_un *) sa)->sun_path);
5123 + saved_umask = umask(0777 ^ wp->socket_mode);
5125 + if (0 > bind(sock, sa, socklen)) {
5126 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "bind() for address '%s' failed", wp->config->listen_address);
5130 + if (wp->listen_address_domain == FPM_AF_UNIX) {
5132 + char *path = ((struct sockaddr_un *) sa)->sun_path;
5134 + if (wp->socket_uid != -1 || wp->socket_gid != -1) {
5136 + if (0 > chown(path, wp->socket_uid, wp->socket_gid)) {
5137 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "chown() for address '%s' failed", wp->config->listen_address);
5145 + umask(saved_umask);
5147 + if (0 > listen(sock, backlog)) {
5148 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "listen() for address '%s' failed", wp->config->listen_address);
5155 +static int fpm_sockets_get_listening_socket(struct fpm_worker_pool_s *wp, struct sockaddr *sa, int socklen)
5159 + sock = fpm_sockets_hash_op(0, sa, 0, wp->listen_address_domain, FPM_GET_USE_SOCKET);
5161 + if (sock >= 0) return sock;
5163 + sock = fpm_sockets_new_listening_socket(wp, sa, socklen);
5165 + fpm_sockets_hash_op(sock, sa, 0, wp->listen_address_domain, FPM_STORE_USE_SOCKET);
5170 +enum fpm_address_domain fpm_sockets_domain_from_address(char *address)
5172 + if (strchr(address, ':')) return FPM_AF_INET;
5174 + if (strlen(address) == strspn(address, "0123456789")) return FPM_AF_INET;
5176 + return FPM_AF_UNIX;
5179 +static int fpm_socket_af_inet_listening_socket(struct fpm_worker_pool_s *wp)
5181 + struct sockaddr_in sa_in;
5182 + char *dup_address = strdup(wp->config->listen_address);
5183 + char *port_str = strchr(dup_address, ':');
5184 + char *addr = NULL;
5187 + if (port_str) { /* this is host:port pair */
5188 + *port_str++ = '\0';
5189 + port = atoi(port_str);
5190 + addr = dup_address;
5192 + else if (strlen(dup_address) == strspn(dup_address, "0123456789")) { /* this is port */
5193 + port = atoi(dup_address);
5194 + port_str = dup_address;
5198 + zlog(ZLOG_STUFF, ZLOG_ERROR, "invalid port value '%s'", port_str);
5202 + memset(&sa_in, 0, sizeof(sa_in));
5206 + sa_in.sin_addr.s_addr = inet_addr(addr);
5208 + if (sa_in.sin_addr.s_addr == INADDR_NONE) { /* do resolve */
5209 + if (0 > fpm_sockets_resolve_af_inet(addr, NULL, &sa_in)) {
5212 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "address '%s' resolved as %u.%u.%u.%u", addr, IPQUAD(&sa_in.sin_addr));
5217 + sa_in.sin_addr.s_addr = htonl(INADDR_ANY);
5221 + sa_in.sin_family = AF_INET;
5222 + sa_in.sin_port = htons(port);
5224 + free(dup_address);
5226 + return fpm_sockets_get_listening_socket(wp, (struct sockaddr *) &sa_in, sizeof(struct sockaddr_in));
5229 +static int fpm_socket_af_unix_listening_socket(struct fpm_worker_pool_s *wp)
5231 + struct sockaddr_un sa_un;
5233 + memset(&sa_un, 0, sizeof(sa_un));
5235 + cpystrn(sa_un.sun_path, wp->config->listen_address, sizeof(sa_un.sun_path));
5236 + sa_un.sun_family = AF_UNIX;
5238 + return fpm_sockets_get_listening_socket(wp, (struct sockaddr *) &sa_un, sizeof(struct sockaddr_un));
5241 +int fpm_sockets_init_main()
5244 + struct fpm_worker_pool_s *wp;
5245 + char *inherited = getenv("FPM_SOCKETS");
5246 + struct listening_socket_s *ls;
5248 + if (0 == fpm_array_init(&sockets_list, sizeof(struct listening_socket_s), 10)) {
5252 + /* import inherited sockets */
5253 + while (inherited && *inherited) {
5254 + char *comma = strchr(inherited, ',');
5258 + if (comma) *comma = '\0';
5260 + eq = strchr(inherited, '=');
5265 + fd_no = atoi(eq + 1);
5267 + type = fpm_sockets_domain_from_address(inherited);
5269 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "using inherited socket fd=%d, \"%s\"", fd_no, inherited);
5271 + fpm_sockets_hash_op(fd_no, 0, inherited, type, FPM_STORE_SOCKET);
5274 + if (comma) inherited = comma + 1;
5275 + else inherited = 0;
5278 + /* create all required sockets */
5279 + for (wp = fpm_worker_all_pools; wp; wp = wp->next) {
5281 + if (!wp->is_template) {
5283 + switch (wp->listen_address_domain) {
5285 + case FPM_AF_INET :
5287 + wp->listening_socket = fpm_socket_af_inet_listening_socket(wp);
5290 + case FPM_AF_UNIX :
5292 + if (0 > fpm_unix_resolve_socket_premissions(wp)) {
5296 + wp->listening_socket = fpm_socket_af_unix_listening_socket(wp);
5301 + if (wp->listening_socket == -1) {
5308 + /* close unused sockets that was inherited */
5309 + ls = sockets_list.data;
5311 + for (i = 0; i < sockets_list.used; ) {
5313 + if (ls->refcount == 0) {
5315 + if (ls->type == FPM_AF_UNIX) {
5319 + fpm_array_item_remove(&sockets_list, i);
5327 + if (0 > fpm_cleanup_add(FPM_CLEANUP_ALL, fpm_sockets_cleanup, 0)) {
5333 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_sockets.h php-5.2.17/sapi/cgi/fpm/fpm_sockets.h
5334 --- php-5.2.17.org/sapi/cgi/fpm/fpm_sockets.h 1970-01-01 01:00:00.000000000 +0100
5335 +++ php-5.2.17/sapi/cgi/fpm/fpm_sockets.h 2021-10-23 19:09:19.833125073 +0200
5339 + /* (c) 2007,2008 Andrei Nigmatulin */
5342 +#define FPM_MISC_H 1
5344 +#include <unistd.h>
5347 +#include "fpm_worker_pool.h"
5349 +enum fpm_address_domain fpm_sockets_domain_from_address(char *addr);
5350 +int fpm_sockets_init_main();
5353 +static inline int fd_set_blocked(int fd, int blocked)
5355 + int flags = fcntl(fd, F_GETFL);
5357 + if (flags < 0) return -1;
5360 + flags &= ~O_NONBLOCK;
5362 + flags |= O_NONBLOCK;
5364 + return fcntl(fd, F_SETFL, flags);
5367 +#define IPQUAD(sin_addr) \
5368 + (unsigned int) ((unsigned char *) &(sin_addr)->s_addr)[0], \
5369 + (unsigned int) ((unsigned char *) &(sin_addr)->s_addr)[1], \
5370 + (unsigned int) ((unsigned char *) &(sin_addr)->s_addr)[2], \
5371 + (unsigned int) ((unsigned char *) &(sin_addr)->s_addr)[3]
5374 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_stdio.c php-5.2.17/sapi/cgi/fpm/fpm_stdio.c
5375 --- php-5.2.17.org/sapi/cgi/fpm/fpm_stdio.c 1970-01-01 01:00:00.000000000 +0100
5376 +++ php-5.2.17/sapi/cgi/fpm/fpm_stdio.c 2021-10-23 19:09:19.833125073 +0200
5380 + /* (c) 2007,2008 Andrei Nigmatulin */
5382 +#include "fpm_config.h"
5384 +#include <sys/types.h>
5385 +#include <sys/stat.h>
5386 +#include <string.h>
5388 +#include <unistd.h>
5392 +#include "fpm_children.h"
5393 +#include "fpm_events.h"
5394 +#include "fpm_sockets.h"
5395 +#include "fpm_stdio.h"
5398 +static int fd_stdout[2];
5399 +static int fd_stderr[2];
5401 +int fpm_stdio_init_main()
5403 + int fd = open("/dev/null", O_RDWR);
5406 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "open(\"/dev/null\") failed");
5410 + if (0 > dup2(fd, STDIN_FILENO) || 0 > dup2(fd, STDOUT_FILENO)) {
5411 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "dup2() failed");
5420 +int fpm_stdio_init_final()
5422 + if (fpm_global_config.daemonize) {
5424 + if (fpm_globals.error_log_fd != STDERR_FILENO) {
5425 + /* there might be messages to stderr from libevent, we need to log them all */
5426 + if (0 > dup2(fpm_globals.error_log_fd, STDERR_FILENO)) {
5427 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "dup2() failed");
5432 + zlog_set_level(fpm_globals.log_level);
5434 + zlog_set_fd(fpm_globals.error_log_fd);
5440 +int fpm_stdio_init_child(struct fpm_worker_pool_s *wp)
5442 + close(fpm_globals.error_log_fd);
5443 + fpm_globals.error_log_fd = -1;
5446 + if (wp->listening_socket != STDIN_FILENO) {
5447 + if (0 > dup2(wp->listening_socket, STDIN_FILENO)) {
5448 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "dup2() failed");
5456 +static void fpm_stdio_child_said(int fd, short which, void *arg)
5458 + static const int max_buf_size = 1024;
5459 + char buf[max_buf_size];
5460 + struct fpm_child_s *child = arg;
5461 + int is_stdout = fd == child->fd_stdout;
5462 + struct event *ev = is_stdout ? &child->ev_stdout : &child->ev_stderr;
5463 + int fifo_in = 1, fifo_out = 1;
5464 + int is_last_message = 0;
5469 + zlog(ZLOG_STUFF, ZLOG_DEBUG, "child %d said %s", (int) child->pid, is_stdout ? "stdout" : "stderr");
5472 + while (fifo_in || fifo_out) {
5476 + res = read(fd, buf + in_buf, max_buf_size - 1 - in_buf);
5478 + if (res <= 0) { /* no data */
5481 + if (res < 0 && (errno == EAGAIN || errno == EWOULDBLOCK)) {
5482 + /* just no more data ready */
5484 + else { /* error or pipe is closed */
5486 + if (res < 0) { /* error */
5487 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "read() failed");
5490 + fpm_event_del(ev);
5491 + is_last_message = 1;
5494 + close(child->fd_stdout);
5495 + child->fd_stdout = -1;
5498 + close(child->fd_stderr);
5499 + child->fd_stderr = -1;
5503 + if (in_buf == 0 && !fpm_globals.is_child) {
5504 + zlog(ZLOG_STUFF, ZLOG_DEBUG, "child %d (pool %s) %s pipe is closed", (int) child->pid,
5505 + child->wp->config->name, is_stdout ? "stdout" : "stderr");
5516 + if (in_buf == 0) {
5521 + int should_print = 0;
5522 + buf[in_buf] = '\0';
5524 + /* FIXME: there might be binary data */
5526 + /* we should print if no more space in the buffer */
5527 + if (in_buf == max_buf_size - 1) {
5531 + /* we should print if no more data to come */
5536 + nl = strchr(buf, '\n');
5538 + if (nl || should_print) {
5544 + zlog(ZLOG_STUFF, ZLOG_WARNING, "child %d (pool %s) said into %s: \"%s\"%s", (int) child->pid,
5545 + child->wp->config->name, is_stdout ? "stdout" : "stderr", buf, is_last_message ? ", pipe is closed" : "");
5548 + int out_buf = 1 + nl - buf;
5549 + memmove(buf, buf + out_buf, in_buf - out_buf);
5550 + in_buf -= out_buf;
5562 +int fpm_stdio_prepare_pipes(struct fpm_child_s *child)
5564 + if (0 == child->wp->config->catch_workers_output) { /* not required */
5568 + if (0 > pipe(fd_stdout)) {
5569 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "pipe() failed");
5573 + if (0 > pipe(fd_stderr)) {
5574 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "pipe() failed");
5575 + close(fd_stdout[0]); close(fd_stdout[1]);
5579 + if (0 > fd_set_blocked(fd_stdout[0], 0) || 0 > fd_set_blocked(fd_stderr[0], 0)) {
5580 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "fd_set_blocked() failed");
5581 + close(fd_stdout[0]); close(fd_stdout[1]);
5582 + close(fd_stderr[0]); close(fd_stderr[1]);
5589 +int fpm_stdio_parent_use_pipes(struct fpm_child_s *child)
5591 + if (0 == child->wp->config->catch_workers_output) { /* not required */
5595 + close(fd_stdout[1]);
5596 + close(fd_stderr[1]);
5598 + child->fd_stdout = fd_stdout[0];
5599 + child->fd_stderr = fd_stderr[0];
5601 + fpm_event_add(child->fd_stdout, &child->ev_stdout, fpm_stdio_child_said, child);
5602 + fpm_event_add(child->fd_stderr, &child->ev_stderr, fpm_stdio_child_said, child);
5607 +int fpm_stdio_discard_pipes(struct fpm_child_s *child)
5609 + if (0 == child->wp->config->catch_workers_output) { /* not required */
5613 + close(fd_stdout[1]);
5614 + close(fd_stderr[1]);
5616 + close(fd_stdout[0]);
5617 + close(fd_stderr[0]);
5622 +void fpm_stdio_child_use_pipes(struct fpm_child_s *child)
5624 + if (child->wp->config->catch_workers_output) {
5625 + dup2(fd_stdout[1], STDOUT_FILENO);
5626 + dup2(fd_stderr[1], STDERR_FILENO);
5627 + close(fd_stdout[0]); close(fd_stdout[1]);
5628 + close(fd_stderr[0]); close(fd_stderr[1]);
5631 + /* stdout of parent is always /dev/null */
5632 + dup2(STDOUT_FILENO, STDERR_FILENO);
5636 +int fpm_stdio_open_error_log(int reopen)
5640 + fd = open(fpm_global_config.error_log, O_WRONLY | O_APPEND | O_CREAT, S_IRUSR | S_IWUSR);
5643 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "open(\"%s\") failed", fpm_global_config.error_log);
5648 + if (fpm_global_config.daemonize) {
5649 + dup2(fd, STDERR_FILENO);
5652 + dup2(fd, fpm_globals.error_log_fd);
5654 + fd = fpm_globals.error_log_fd; /* for FD_CLOSEXEC to work */
5657 + fpm_globals.error_log_fd = fd;
5660 + fcntl(fd, F_SETFD, fcntl(fd, F_GETFD) | FD_CLOEXEC);
5664 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_stdio.h php-5.2.17/sapi/cgi/fpm/fpm_stdio.h
5665 --- php-5.2.17.org/sapi/cgi/fpm/fpm_stdio.h 1970-01-01 01:00:00.000000000 +0100
5666 +++ php-5.2.17/sapi/cgi/fpm/fpm_stdio.h 2021-10-23 19:09:19.833125073 +0200
5670 + /* (c) 2007,2008 Andrei Nigmatulin */
5672 +#ifndef FPM_STDIO_H
5673 +#define FPM_STDIO_H 1
5675 +#include "fpm_worker_pool.h"
5677 +int fpm_stdio_init_main();
5678 +int fpm_stdio_init_final();
5679 +int fpm_stdio_init_child(struct fpm_worker_pool_s *wp);
5680 +int fpm_stdio_prepare_pipes(struct fpm_child_s *child);
5681 +void fpm_stdio_child_use_pipes(struct fpm_child_s *child);
5682 +int fpm_stdio_parent_use_pipes(struct fpm_child_s *child);
5683 +int fpm_stdio_discard_pipes(struct fpm_child_s *child);
5684 +int fpm_stdio_open_error_log(int reopen);
5688 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_str.h php-5.2.17/sapi/cgi/fpm/fpm_str.h
5689 --- php-5.2.17.org/sapi/cgi/fpm/fpm_str.h 1970-01-01 01:00:00.000000000 +0100
5690 +++ php-5.2.17/sapi/cgi/fpm/fpm_str.h 2021-10-23 19:09:19.833125073 +0200
5694 + /* (c) 2007,2008 Andrei Nigmatulin */
5697 +#define FPM_STR_H 1
5699 +static inline char *cpystrn(char *dst, const char *src, size_t dst_size)
5703 + if (!dst_size) return dst;
5706 + end = dst + dst_size - 1;
5708 + for (; d < end; ++d, ++src) {
5709 + if (!(*d = *src)) {
5719 +static inline char *str_purify_filename(char *dst, char *src, size_t size)
5724 + end = dst + size - 1;
5726 + for (; d < end && *src; ++d, ++src) {
5727 + if (* (unsigned char *) src < ' ' || * (unsigned char *) src > '\x7f') {
5741 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_trace.c php-5.2.17/sapi/cgi/fpm/fpm_trace.c
5742 --- php-5.2.17.org/sapi/cgi/fpm/fpm_trace.c 1970-01-01 01:00:00.000000000 +0100
5743 +++ php-5.2.17/sapi/cgi/fpm/fpm_trace.c 2021-10-23 19:09:19.833125073 +0200
5747 + /* (c) 2007,2008 Andrei Nigmatulin */
5749 +#include "fpm_config.h"
5751 +#include <sys/types.h>
5753 +#include "fpm_trace.h"
5755 +int fpm_trace_get_strz(char *buf, size_t sz, long addr)
5759 + char *lc = (char *) &l;
5761 + if (0 > fpm_trace_get_long(addr, &l)) {
5765 + i = l % SIZEOF_LONG;
5769 + for (addr = l; ; addr += SIZEOF_LONG) {
5771 + if (0 > fpm_trace_get_long(addr, &l)) {
5775 + for ( ; i < SIZEOF_LONG; i++) {
5778 + if (sz && lc[i]) {
5791 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_trace.h php-5.2.17/sapi/cgi/fpm/fpm_trace.h
5792 --- php-5.2.17.org/sapi/cgi/fpm/fpm_trace.h 1970-01-01 01:00:00.000000000 +0100
5793 +++ php-5.2.17/sapi/cgi/fpm/fpm_trace.h 2021-10-23 19:09:19.833125073 +0200
5797 + /* (c) 2007,2008 Andrei Nigmatulin */
5799 +#ifndef FPM_TRACE_H
5800 +#define FPM_TRACE_H 1
5802 +#include <unistd.h>
5804 +int fpm_trace_signal(pid_t pid);
5805 +int fpm_trace_ready(pid_t pid);
5806 +int fpm_trace_close(pid_t pid);
5807 +int fpm_trace_get_long(long addr, long *data);
5808 +int fpm_trace_get_strz(char *buf, size_t sz, long addr);
5812 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_trace_mach.c php-5.2.17/sapi/cgi/fpm/fpm_trace_mach.c
5813 --- php-5.2.17.org/sapi/cgi/fpm/fpm_trace_mach.c 1970-01-01 01:00:00.000000000 +0100
5814 +++ php-5.2.17/sapi/cgi/fpm/fpm_trace_mach.c 2021-10-23 19:09:19.833125073 +0200
5818 + /* (c) 2007,2008 Andrei Nigmatulin */
5820 +#include "fpm_config.h"
5822 +#include <mach/mach.h>
5823 +#include <mach/mach_vm.h>
5825 +#include <unistd.h>
5827 +#include "fpm_trace.h"
5828 +#include "fpm_process_ctl.h"
5829 +#include "fpm_unix.h"
5833 +static mach_port_name_t target;
5834 +static vm_offset_t target_page_base;
5835 +static vm_offset_t local_page;
5836 +static mach_msg_type_number_t local_size;
5838 +static void fpm_mach_vm_deallocate()
5841 + mach_vm_deallocate(mach_task_self(), local_page, local_size);
5842 + target_page_base = 0;
5848 +static int fpm_mach_vm_read_page(vm_offset_t page)
5852 + kr = mach_vm_read(target, page, fpm_pagesize, &local_page, &local_size);
5854 + if (kr != KERN_SUCCESS) {
5855 + zlog(ZLOG_STUFF, ZLOG_ERROR, "mach_vm_read() failed: %s (%d)", mach_error_string(kr), kr);
5862 +int fpm_trace_signal(pid_t pid)
5864 + if (0 > fpm_pctl_kill(pid, FPM_PCTL_STOP)) {
5865 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "kill(SIGSTOP) failed");
5872 +int fpm_trace_ready(pid_t pid)
5876 + kr = task_for_pid(mach_task_self(), pid, &target);
5878 + if (kr != KERN_SUCCESS) {
5881 + if (kr == KERN_FAILURE) {
5882 + msg = " It seems that master process does not have enough privileges to trace processes.";
5885 + zlog(ZLOG_STUFF, ZLOG_ERROR, "task_for_pid() failed: %s (%d)%s", mach_error_string(kr), kr, msg);
5892 +int fpm_trace_close(pid_t pid)
5894 + fpm_mach_vm_deallocate();
5901 +int fpm_trace_get_long(long addr, long *data)
5903 + size_t offset = ((uintptr_t) (addr) % fpm_pagesize);
5904 + vm_offset_t base = (uintptr_t) (addr) - offset;
5906 + if (base != target_page_base) {
5907 + fpm_mach_vm_deallocate();
5908 + if (0 > fpm_mach_vm_read_page(base)) {
5913 + *data = * (long *) (local_page + offset);
5918 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_trace_pread.c php-5.2.17/sapi/cgi/fpm/fpm_trace_pread.c
5919 --- php-5.2.17.org/sapi/cgi/fpm/fpm_trace_pread.c 1970-01-01 01:00:00.000000000 +0100
5920 +++ php-5.2.17/sapi/cgi/fpm/fpm_trace_pread.c 2021-10-23 19:09:19.833125073 +0200
5924 + /* (c) 2007,2008 Andrei Nigmatulin */
5926 +#define _GNU_SOURCE
5927 +#define _FILE_OFFSET_BITS 64
5929 +#include "fpm_config.h"
5931 +#include <unistd.h>
5935 +#include <stdint.h>
5937 +#include "fpm_trace.h"
5938 +#include "fpm_process_ctl.h"
5942 +static int mem_file = -1;
5944 +int fpm_trace_signal(pid_t pid)
5946 + if (0 > fpm_pctl_kill(pid, FPM_PCTL_STOP)) {
5947 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "kill(SIGSTOP) failed");
5954 +int fpm_trace_ready(pid_t pid)
5958 + sprintf(buf, "/proc/%d/" PROC_MEM_FILE, (int) pid);
5960 + mem_file = open(buf, O_RDONLY);
5962 + if (0 > mem_file) {
5963 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "open(%s) failed", buf);
5970 +int fpm_trace_close(pid_t pid)
5979 +int fpm_trace_get_long(long addr, long *data)
5981 + if (sizeof(*data) != pread(mem_file, (void *) data, sizeof(*data), (uintptr_t) addr)) {
5982 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "pread() failed");
5989 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_trace_ptrace.c php-5.2.17/sapi/cgi/fpm/fpm_trace_ptrace.c
5990 --- php-5.2.17.org/sapi/cgi/fpm/fpm_trace_ptrace.c 1970-01-01 01:00:00.000000000 +0100
5991 +++ php-5.2.17/sapi/cgi/fpm/fpm_trace_ptrace.c 2021-10-23 19:09:19.833125073 +0200
5995 + /* (c) 2007,2008 Andrei Nigmatulin */
5997 +#include "fpm_config.h"
5999 +#include <sys/wait.h>
6000 +#include <sys/ptrace.h>
6001 +#include <unistd.h>
6004 +#if defined(PT_ATTACH) && !defined(PTRACE_ATTACH)
6005 +#define PTRACE_ATTACH PT_ATTACH
6008 +#if defined(PT_DETACH) && !defined(PTRACE_DETACH)
6009 +#define PTRACE_DETACH PT_DETACH
6012 +#if defined(PT_READ_D) && !defined(PTRACE_PEEKDATA)
6013 +#define PTRACE_PEEKDATA PT_READ_D
6016 +#include "fpm_trace.h"
6019 +static pid_t traced_pid;
6021 +int fpm_trace_signal(pid_t pid)
6023 + if (0 > ptrace(PTRACE_ATTACH, pid, 0, 0)) {
6024 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "ptrace(ATTACH) failed");
6031 +int fpm_trace_ready(pid_t pid)
6038 +int fpm_trace_close(pid_t pid)
6040 + if (0 > ptrace(PTRACE_DETACH, pid, (void *) 1, 0)) {
6041 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "ptrace(DETACH) failed");
6050 +int fpm_trace_get_long(long addr, long *data)
6053 + struct ptrace_io_desc ptio = {
6054 + .piod_op = PIOD_READ_D,
6055 + .piod_offs = (void *) addr,
6056 + .piod_addr = (void *) data,
6057 + .piod_len = sizeof(long)
6060 + if (0 > ptrace(PT_IO, traced_pid, (void *) &ptio, 0)) {
6061 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "ptrace(PT_IO) failed");
6067 + *data = ptrace(PTRACE_PEEKDATA, traced_pid, (void *) addr, 0);
6070 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "ptrace(PEEKDATA) failed");
6078 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_unix.c php-5.2.17/sapi/cgi/fpm/fpm_unix.c
6079 --- php-5.2.17.org/sapi/cgi/fpm/fpm_unix.c 1970-01-01 01:00:00.000000000 +0100
6080 +++ php-5.2.17/sapi/cgi/fpm/fpm_unix.c 2021-10-23 19:09:19.833125073 +0200
6084 + /* (c) 2007,2008 Andrei Nigmatulin */
6086 +#include "fpm_config.h"
6088 +#include <string.h>
6089 +#include <sys/time.h>
6090 +#include <sys/resource.h>
6091 +#include <stdlib.h>
6092 +#include <unistd.h>
6093 +#include <sys/types.h>
6098 +#include <sys/prctl.h>
6102 +#include "fpm_conf.h"
6103 +#include "fpm_cleanup.h"
6104 +#include "fpm_clock.h"
6105 +#include "fpm_stdio.h"
6106 +#include "fpm_unix.h"
6109 +size_t fpm_pagesize;
6111 +int fpm_unix_resolve_socket_premissions(struct fpm_worker_pool_s *wp)
6113 + struct fpm_listen_options_s *lo = wp->config->listen_options;
6115 + /* uninitialized */
6116 + wp->socket_uid = -1;
6117 + wp->socket_gid = -1;
6118 + wp->socket_mode = 0666;
6120 + if (!lo) return 0;
6122 + if (lo->owner && *lo->owner) {
6123 + struct passwd *pwd;
6125 + pwd = getpwnam(lo->owner);
6128 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "cannot get uid for user '%s', pool '%s'", lo->owner, wp->config->name);
6132 + wp->socket_uid = pwd->pw_uid;
6133 + wp->socket_gid = pwd->pw_gid;
6136 + if (lo->group && *lo->group) {
6137 + struct group *grp;
6139 + grp = getgrnam(lo->group);
6142 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "cannot get gid for group '%s', pool '%s'", lo->group, wp->config->name);
6146 + wp->socket_gid = grp->gr_gid;
6149 + if (lo->mode && *lo->mode) {
6150 + wp->socket_mode = strtoul(lo->mode, 0, 8);
6156 +static int fpm_unix_conf_wp(struct fpm_worker_pool_s *wp)
6158 + int is_root = !geteuid();
6161 + if (wp->config->user && *wp->config->user) {
6163 + if (strlen(wp->config->user) == strspn(wp->config->user, "0123456789")) {
6164 + wp->set_uid = strtoul(wp->config->user, 0, 10);
6167 + struct passwd *pwd;
6169 + pwd = getpwnam(wp->config->user);
6172 + zlog(ZLOG_STUFF, ZLOG_ERROR, "cannot get uid for user '%s', pool '%s'", wp->config->user, wp->config->name);
6176 + wp->set_uid = pwd->pw_uid;
6177 + wp->set_gid = pwd->pw_gid;
6179 + wp->user = strdup(pwd->pw_name);
6180 + wp->home = strdup(pwd->pw_dir);
6184 + if (wp->config->group && *wp->config->group) {
6186 + if (strlen(wp->config->group) == strspn(wp->config->group, "0123456789")) {
6187 + wp->set_gid = strtoul(wp->config->group, 0, 10);
6190 + struct group *grp;
6192 + grp = getgrnam(wp->config->group);
6195 + zlog(ZLOG_STUFF, ZLOG_ERROR, "cannot get gid for group '%s', pool '%s'", wp->config->group, wp->config->name);
6199 + wp->set_gid = grp->gr_gid;
6203 +#ifndef I_REALLY_WANT_ROOT_PHP
6204 + if (wp->set_uid == 0 || wp->set_gid == 0) {
6205 + zlog(ZLOG_STUFF, ZLOG_ERROR, "please specify user and group other than root, pool '%s'", wp->config->name);
6210 + else { /* not root */
6211 + if (wp->config->user && *wp->config->user) {
6212 + zlog(ZLOG_STUFF, ZLOG_WARNING, "'user' directive is ignored, pool '%s'", wp->config->name);
6214 + if (wp->config->group && *wp->config->group) {
6215 + zlog(ZLOG_STUFF, ZLOG_WARNING, "'group' directive is ignored, pool '%s'", wp->config->name);
6217 + if (wp->config->chroot && *wp->config->chroot) {
6218 + zlog(ZLOG_STUFF, ZLOG_WARNING, "'chroot' directive is ignored, pool '%s'", wp->config->name);
6221 + { /* set up HOME and USER anyway */
6222 + struct passwd *pwd;
6224 + pwd = getpwuid(getuid());
6227 + wp->user = strdup(pwd->pw_name);
6228 + wp->home = strdup(pwd->pw_dir);
6236 +int fpm_unix_init_child(struct fpm_worker_pool_s *wp)
6238 + int is_root = !geteuid();
6239 + int made_chroot = 0;
6241 + if (wp->config->rlimit_files) {
6244 + getrlimit(RLIMIT_NOFILE, &r);
6246 + r.rlim_cur = (rlim_t) wp->config->rlimit_files;
6247 + r.rlim_max = r.rlim_cur;
6248 + if (0 > setrlimit(RLIMIT_NOFILE, &r)) {
6249 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "setrlimit(RLIMIT_NOFILE) failed");
6253 + if (wp->config->rlimit_core) {
6256 + getrlimit(RLIMIT_CORE, &r);
6258 + r.rlim_cur = wp->config->rlimit_core == -1 ? (rlim_t) RLIM_INFINITY : (rlim_t) wp->config->rlimit_core;
6259 + r.rlim_max = r.rlim_cur;
6260 + if (0 > setrlimit(RLIMIT_CORE, &r)) {
6261 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "setrlimit(RLIMIT_CORE) failed");
6265 + if (is_root && wp->config->chroot && *wp->config->chroot) {
6266 + if (0 > chroot(wp->config->chroot)) {
6267 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "chroot(%s) failed", wp->config->chroot);
6273 + if (wp->config->chdir && *wp->config->chdir) {
6274 + if (0 > chdir(wp->config->chdir)) {
6275 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "chdir(%s) failed", wp->config->chdir);
6279 + else if (made_chroot) {
6284 + if (wp->set_gid) {
6285 + if (0 > setgid(wp->set_gid)) {
6286 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "setgid(%d) failed", wp->set_gid);
6290 + if (wp->set_uid) {
6291 + if (0 > initgroups(wp->config->user, wp->set_gid)) {
6292 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "initgroups(%s, %d) failed", wp->config->user, wp->set_gid);
6295 + if (0 > setuid(wp->set_uid)) {
6296 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "setuid(%d) failed", wp->set_uid);
6303 + if (0 > prctl(PR_SET_DUMPABLE, 1, 0, 0, 0)) {
6304 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "prctl(PR_SET_DUMPABLE) failed");
6308 + if (0 > fpm_clock_init()) {
6315 +int fpm_unix_init_main()
6317 + struct fpm_worker_pool_s *wp;
6319 + fpm_pagesize = getpagesize();
6321 + if (fpm_global_config.daemonize) {
6327 + zlog(ZLOG_STUFF, ZLOG_SYSERROR, "fork() failed");
6336 + fpm_cleanups_run(FPM_CLEANUP_PARENT_EXIT);
6345 + if (0 > fpm_clock_init()) {
6349 + fpm_globals.parent_pid = getpid();
6351 + for (wp = fpm_worker_all_pools; wp; wp = wp->next) {
6353 + if (0 > fpm_unix_conf_wp(wp)) {
6359 + fpm_stdio_init_final();
6363 + getrlimit(RLIMIT_NOFILE, &r);
6365 + zlog(ZLOG_STUFF, ZLOG_NOTICE, "getrlimit(nofile): max:%lld, cur:%lld",
6366 + (long long) r.rlim_max, (long long) r.rlim_cur);
6371 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_unix.h php-5.2.17/sapi/cgi/fpm/fpm_unix.h
6372 --- php-5.2.17.org/sapi/cgi/fpm/fpm_unix.h 1970-01-01 01:00:00.000000000 +0100
6373 +++ php-5.2.17/sapi/cgi/fpm/fpm_unix.h 2021-10-23 19:09:19.833125073 +0200
6377 + /* (c) 2007,2008 Andrei Nigmatulin */
6380 +#define FPM_UNIX_H 1
6382 +#include "fpm_worker_pool.h"
6384 +int fpm_unix_resolve_socket_premissions(struct fpm_worker_pool_s *wp);
6385 +int fpm_unix_init_child(struct fpm_worker_pool_s *wp);
6386 +int fpm_unix_init_main();
6388 +extern size_t fpm_pagesize;
6392 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_worker_pool.c php-5.2.17/sapi/cgi/fpm/fpm_worker_pool.c
6393 --- php-5.2.17.org/sapi/cgi/fpm/fpm_worker_pool.c 1970-01-01 01:00:00.000000000 +0100
6394 +++ php-5.2.17/sapi/cgi/fpm/fpm_worker_pool.c 2021-10-23 19:09:19.833125073 +0200
6398 + /* (c) 2007,2008 Andrei Nigmatulin */
6400 +#include "fpm_config.h"
6402 +#include <string.h>
6403 +#include <stdlib.h>
6404 +#include <unistd.h>
6406 +#include "fpm_worker_pool.h"
6407 +#include "fpm_cleanup.h"
6408 +#include "fpm_children.h"
6409 +#include "fpm_shm.h"
6410 +#include "fpm_shm_slots.h"
6411 +#include "fpm_conf.h"
6413 +struct fpm_worker_pool_s *fpm_worker_all_pools;
6415 +static void fpm_worker_pool_cleanup(int which, void *arg)
6417 + struct fpm_worker_pool_s *wp, *wp_next;
6419 + for (wp = fpm_worker_all_pools; wp; wp = wp_next) {
6420 + wp_next = wp->next;
6421 + fpm_worker_pool_config_free(wp->config);
6422 + fpm_children_free(wp->children);
6423 + fpm_array_free(&wp->slots_used);
6424 + fpm_array_free(&wp->slots_free);
6425 + fpm_shm_free_list(wp->shm_list, which == FPM_CLEANUP_CHILD ? fpm_shm_slots_mem() : 0);
6432 + fpm_worker_all_pools = 0;
6435 +struct fpm_worker_pool_s *fpm_worker_pool_alloc()
6437 + struct fpm_worker_pool_s *ret;
6439 + ret = malloc(sizeof(struct fpm_worker_pool_s));
6445 + memset(ret, 0, sizeof(struct fpm_worker_pool_s));
6447 + if (!fpm_worker_all_pools) {
6448 + fpm_worker_all_pools = ret;
6451 + fpm_array_init(&ret->slots_used, sizeof(struct fpm_shm_slot_ptr_s), 50);
6452 + fpm_array_init(&ret->slots_free, sizeof(struct fpm_shm_slot_ptr_s), 50);
6457 +int fpm_worker_pool_init_main()
6459 + if (0 > fpm_cleanup_add(FPM_CLEANUP_ALL, fpm_worker_pool_cleanup, 0)) {
6465 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/fpm_worker_pool.h php-5.2.17/sapi/cgi/fpm/fpm_worker_pool.h
6466 --- php-5.2.17.org/sapi/cgi/fpm/fpm_worker_pool.h 1970-01-01 01:00:00.000000000 +0100
6467 +++ php-5.2.17/sapi/cgi/fpm/fpm_worker_pool.h 2021-10-23 19:09:19.833125073 +0200
6471 + /* (c) 2007,2008 Andrei Nigmatulin */
6473 +#ifndef FPM_WORKER_POOL_H
6474 +#define FPM_WORKER_POOL_H 1
6476 +#include "fpm_conf.h"
6477 +#include "fpm_arrays.h"
6479 +struct fpm_worker_pool_s;
6480 +struct fpm_child_s;
6481 +struct fpm_child_stat_s;
6484 +enum fpm_address_domain {
6489 +struct fpm_worker_pool_s {
6490 + struct fpm_worker_pool_s *next;
6491 + struct fpm_worker_pool_config_s *config;
6492 + char *user, *home; /* for setting env USER and HOME */
6493 + enum fpm_address_domain listen_address_domain;
6494 + int listening_socket;
6495 + int set_uid, set_gid; /* config uid and gid */
6496 + unsigned is_template:1; /* just config template, no processes will be created */
6497 + int socket_uid, socket_gid, socket_mode;
6499 + struct fpm_shm_s *shm_list;
6500 + struct fpm_array_s slots_used;
6501 + struct fpm_array_s slots_free;
6504 + struct fpm_child_s *children;
6505 + int running_children;
6508 +struct fpm_worker_pool_s *fpm_worker_pool_alloc();
6509 +int fpm_worker_pool_init_main();
6511 +extern struct fpm_worker_pool_s *fpm_worker_all_pools;
6515 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/init.d/php-fpm.in php-5.2.17/sapi/cgi/fpm/init.d/php-fpm.in
6516 --- php-5.2.17.org/sapi/cgi/fpm/init.d/php-fpm.in 1970-01-01 01:00:00.000000000 +0100
6517 +++ php-5.2.17/sapi/cgi/fpm/init.d/php-fpm.in 2021-10-23 19:09:19.833125073 +0200
6521 +php_fpm_BIN=@prefix@/bin/php-cgi
6522 +php_fpm_CONF=@php_fpm_conf_path@
6523 +php_fpm_PID=@php_fpm_pid_path@
6526 +php_opts="--fpm-config $php_fpm_CONF"
6532 + while test $try -lt 35 ; do
6536 + if [ -f "$2" ] ; then
6543 + if [ ! -f "$2" ] ; then
6551 + try=`expr $try + 1`
6560 + echo -n "Starting php_fpm "
6562 + $php_fpm_BIN --fpm $php_opts
6564 + if [ "$?" != 0 ] ; then
6569 + wait_for_pid created $php_fpm_PID
6571 + if [ -n "$try" ] ; then
6580 + echo -n "Shutting down php_fpm "
6582 + if [ ! -r $php_fpm_PID ] ; then
6583 + echo "warning, no pid file found - php-fpm is not running ?"
6587 + kill -TERM `cat $php_fpm_PID`
6589 + wait_for_pid removed $php_fpm_PID
6591 + if [ -n "$try" ] ; then
6600 + echo -n "Gracefully shutting down php_fpm "
6602 + if [ ! -r $php_fpm_PID ] ; then
6603 + echo "warning, no pid file found - php-fpm is not running ?"
6607 + kill -QUIT `cat $php_fpm_PID`
6609 + wait_for_pid removed $php_fpm_PID
6611 + if [ -n "$try" ] ; then
6626 + echo -n "Reload service php-fpm "
6628 + if [ ! -r $php_fpm_PID ] ; then
6629 + echo "warning, no pid file found - php-fpm is not running ?"
6633 + kill -USR2 `cat $php_fpm_PID`
6640 + echo -n "Re-opening php-fpm log file "
6642 + if [ ! -r $php_fpm_PID ] ; then
6643 + echo "warning, no pid file found - php-fpm is not running ?"
6647 + kill -USR1 `cat $php_fpm_PID`
6653 + echo "Usage: $0 {start|stop|quit|restart|reload|logrotate}"
6658 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/xml_config.c php-5.2.17/sapi/cgi/fpm/xml_config.c
6659 --- php-5.2.17.org/sapi/cgi/fpm/xml_config.c 1970-01-01 01:00:00.000000000 +0100
6660 +++ php-5.2.17/sapi/cgi/fpm/xml_config.c 2021-10-23 19:09:19.833125073 +0200
6664 + /* (c) 2004-2007 Andrei Nigmatulin */
6666 +#include "fpm_config.h"
6668 +#ifdef HAVE_ALLOCA_H
6669 +#include <alloca.h>
6671 +#include <string.h>
6673 +#include <stddef.h>
6674 +#include <stdlib.h>
6676 +#include <libxml/parser.h>
6677 +#include <libxml/tree.h>
6679 +#include "xml_config.h"
6681 +static struct xml_conf_section **xml_conf_sections = 0;
6682 +static int xml_conf_sections_allocated = 0;
6683 +static int xml_conf_sections_used = 0;
6685 +char *xml_conf_set_slot_boolean(void **conf, char *name, void *vv, intptr_t offset)
6688 + long value_y = !strcasecmp(value, "yes") || !strcmp(value, "1") || !strcasecmp(value, "on");
6689 + long value_n = !strcasecmp(value, "no") || !strcmp(value, "0") || !strcasecmp(value, "off");
6691 + if (!value_y && !value_n) {
6692 + return "xml_conf_set_slot(): invalid boolean value";
6695 +#ifdef XML_CONF_DEBUG
6696 + fprintf(stderr, "setting boolean '%s' => %s\n", name, value_y ? "TRUE" : "FALSE");
6699 + * (int *) ((char *) *conf + offset) = value_y ? 1 : 0;
6704 +char *xml_conf_set_slot_string(void **conf, char *name, void *vv, intptr_t offset)
6707 + char *v = strdup(value);
6709 + if (!v) return "xml_conf_set_slot_string(): strdup() failed";
6711 +#ifdef XML_CONF_DEBUG
6712 + fprintf(stderr, "setting string '%s' => '%s'\n", name, v);
6715 + * (char **) ((char *) *conf + offset) = v;
6720 +char *xml_conf_set_slot_integer(void **conf, char *name, void *vv, intptr_t offset)
6723 + int v = atoi(value);
6725 + * (int *) ((char *) *conf + offset) = v;
6727 +#ifdef XML_CONF_DEBUG
6728 + fprintf(stderr, "setting integer '%s' => %d\n", name, v);
6734 +char *xml_conf_set_slot_time(void **conf, char *name, void *vv, intptr_t offset)
6737 + int len = strlen(value);
6741 + if (!len) return "xml_conf_set_slot_timeval(): invalid timeval value";
6743 + suffix = value[len-1];
6745 + value[len-1] = '\0';
6749 + seconds = atoi(value);
6752 + seconds = 60 * atoi(value);
6755 + seconds = 60 * 60 * atoi(value);
6758 + seconds = 24 * 60 * 60 * atoi(value);
6761 + return "xml_conf_set_slot_timeval(): unknown suffix used in timeval value";
6764 + * (int *) ((char *) *conf + offset) = seconds;
6766 +#ifdef XML_CONF_DEBUG
6767 + fprintf(stderr, "setting time '%s' => %d:%02d:%02d:%02d\n", name, expand_dhms(seconds));
6773 +char *xml_conf_parse_section(void **conf, struct xml_conf_section *section, void *xml_node)
6775 + xmlNode *element = xml_node;
6778 +#ifdef XML_CONF_DEBUG
6779 + fprintf(stderr, "processing a section %s\n", section->path);
6782 + for ( ; element; element = element->next) {
6783 + if (element->type == XML_ELEMENT_NODE && !strcmp((const char *) element->name, "value") && element->children) {
6784 + xmlChar *name = xmlGetProp(element, (unsigned char *) "name");
6789 +#ifdef XML_CONF_DEBUG
6790 + fprintf(stderr, "found a value: %s\n", name);
6792 + for (i = 0; section->parsers[i].parser; i++) {
6793 + if (!section->parsers[i].name || !strcmp(section->parsers[i].name, (char *) name)) {
6798 + if (section->parsers[i].parser) {
6799 + if (section->parsers[i].type == XML_CONF_SCALAR) {
6800 + if (element->children->type == XML_TEXT_NODE) {
6801 + ret = section->parsers[i].parser(conf, (char *) name, element->children->content, section->parsers[i].offset);
6804 + ret = "XML_TEXT_NODE is expected, something different is given";
6808 + ret = section->parsers[i].parser(conf, (char *) name, element->children, section->parsers[i].offset);
6812 + if (ret) return ret;
6816 + fprintf(stderr, "Warning, unknown setting '%s' in section '%s'\n", (char *) name, section->path);
6826 +static char *xml_conf_parse_file(xmlNode *element)
6830 + for ( ; element; element = element->next) {
6832 + if (element->parent && element->type == XML_ELEMENT_NODE && !strcmp((const char *) element->name, "section")) {
6833 + xmlChar *name = xmlGetProp(element, (unsigned char *) "name");
6836 + char *parent_name = (char *) xmlGetNodePath(element->parent);
6839 + struct xml_conf_section *section = NULL;
6841 +#ifdef XML_CONF_DEBUG
6842 + fprintf(stderr, "got a section: %s/%s\n", parent_name, name);
6844 + full_name = alloca(strlen(parent_name) + strlen((char *) name) + 1 + 1);
6846 + sprintf(full_name, "%s/%s", parent_name, (char *) name);
6848 + xmlFree(parent_name);
6851 + for (i = 0; i < xml_conf_sections_used; i++) {
6852 + if (!strcmp(xml_conf_sections[i]->path, full_name)) {
6853 + section = xml_conf_sections[i];
6857 + if (section) { /* found a registered section */
6858 + void *conf = section->conf();
6859 + ret = xml_conf_parse_section(&conf, section, element->children);
6866 + if (element->children) {
6867 + ret = xml_conf_parse_file(element->children);
6875 +char *xml_conf_load_file(char *file)
6880 + LIBXML_TEST_VERSION
6882 + doc = xmlParseFile(file);
6885 + ret = xml_conf_parse_file(doc->children);
6889 + ret = "failed to parse conf file";
6892 + xmlCleanupParser();
6896 +int xml_conf_init()
6901 +void xml_conf_clean()
6903 + if (xml_conf_sections) {
6904 + free(xml_conf_sections);
6908 +int xml_conf_section_register(struct xml_conf_section *section)
6910 + if (xml_conf_sections_allocated == xml_conf_sections_used) {
6911 + int new_size = xml_conf_sections_used + 10;
6912 + void *new_ptr = realloc(xml_conf_sections, sizeof(struct xml_conf_section *) * new_size);
6915 + xml_conf_sections = new_ptr;
6916 + xml_conf_sections_allocated = new_size;
6919 + fprintf(stderr, "xml_conf_section_register(): out of memory\n");
6924 + xml_conf_sections[xml_conf_sections_used++] = section;
6929 +int xml_conf_sections_register(struct xml_conf_section *sections[])
6931 + for ( ; sections && *sections; sections++) {
6932 + if (0 > xml_conf_section_register(*sections)) {
6940 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/xml_config.h php-5.2.17/sapi/cgi/fpm/xml_config.h
6941 --- php-5.2.17.org/sapi/cgi/fpm/xml_config.h 1970-01-01 01:00:00.000000000 +0100
6942 +++ php-5.2.17/sapi/cgi/fpm/xml_config.h 2021-10-23 19:09:19.833125073 +0200
6946 + /* (c) 2004-2007 Andrei Nigmatulin */
6948 +#ifndef XML_CONFIG_H
6949 +#define XML_CONFIG_H 1
6951 +#include <stdint.h>
6953 +struct xml_value_parser;
6955 +struct xml_value_parser {
6958 + char *(*parser)(void **, char *, void *, intptr_t offset);
6962 +struct xml_conf_section {
6965 + struct xml_value_parser *parsers;
6968 +char *xml_conf_set_slot_boolean(void **conf, char *name, void *value, intptr_t offset);
6969 +char *xml_conf_set_slot_string(void **conf, char *name, void *value, intptr_t offset);
6970 +char *xml_conf_set_slot_integer(void **conf, char *name, void *value, intptr_t offset);
6971 +char *xml_conf_set_slot_time(void **conf, char *name, void *value, intptr_t offset);
6973 +int xml_conf_init();
6974 +void xml_conf_clean();
6975 +char *xml_conf_load_file(char *file);
6976 +char *xml_conf_parse_section(void **conf, struct xml_conf_section *section, void *ve);
6977 +int xml_conf_section_register(struct xml_conf_section *section);
6978 +int xml_conf_sections_register(struct xml_conf_section *sections[]);
6980 +#define expand_hms(value) (value) / 3600, ((value) % 3600) / 60, (value) % 60
6982 +#define expand_dhms(value) (value) / 86400, ((value) % 86400) / 3600, ((value) % 3600) / 60, (value) % 60
6984 +enum { XML_CONF_SCALAR = 1, XML_CONF_SUBSECTION = 2 };
6987 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/zlog.c php-5.2.17/sapi/cgi/fpm/zlog.c
6988 --- php-5.2.17.org/sapi/cgi/fpm/zlog.c 1970-01-01 01:00:00.000000000 +0100
6989 +++ php-5.2.17/sapi/cgi/fpm/zlog.c 2021-10-23 19:09:19.833125073 +0200
6993 + /* (c) 2004-2007 Andrei Nigmatulin */
6995 +#include "fpm_config.h"
6998 +#include <unistd.h>
7000 +#include <string.h>
7001 +#include <stdarg.h>
7002 +#include <sys/time.h>
7007 +#define MAX_LINE_LENGTH 1024
7009 +static int zlog_fd = -1;
7010 +static int zlog_level = ZLOG_NOTICE;
7012 +static const char *level_names[] = {
7013 + [ZLOG_DEBUG] = "DEBUG",
7014 + [ZLOG_NOTICE] = "NOTICE",
7015 + [ZLOG_WARNING] = "WARNING",
7016 + [ZLOG_ERROR] = "ERROR",
7017 + [ZLOG_ALERT] = "ALERT",
7020 +size_t zlog_print_time(struct timeval *tv, char *timebuf, size_t timebuf_len)
7025 + len = strftime(timebuf, timebuf_len, "%b %d %H:%M:%S", localtime_r((const time_t *) &tv->tv_sec, &t));
7026 + len += snprintf(timebuf + len, timebuf_len - len, ".%06d", (int) tv->tv_usec);
7031 +int zlog_set_fd(int new_fd)
7033 + int old_fd = zlog_fd;
7039 +int zlog_set_level(int new_value)
7041 + int old_value = zlog_level;
7043 + zlog_level = new_value;
7048 +void zlog(const char *function, int line, int flags, const char *fmt, ...)
7050 + struct timeval tv;
7051 + char buf[MAX_LINE_LENGTH];
7052 + const size_t buf_size = MAX_LINE_LENGTH;
7055 + int truncated = 0;
7058 + if ((flags & ZLOG_LEVEL_MASK) < zlog_level) {
7062 + saved_errno = errno;
7064 + gettimeofday(&tv, 0);
7066 + len = zlog_print_time(&tv, buf, buf_size);
7068 + len += snprintf(buf + len, buf_size - len, " [%s] %s(), line %d: ", level_names[flags & ZLOG_LEVEL_MASK], function, line);
7070 + if (len > buf_size - 1) {
7075 + va_start(args, fmt);
7077 + len += vsnprintf(buf + len, buf_size - len, fmt, args);
7081 + if (len >= buf_size) {
7087 + if (flags & ZLOG_HAVE_ERRNO) {
7088 + len += snprintf(buf + len, buf_size - len, ": %s (%d)", strerror(saved_errno), saved_errno);
7089 + if (len >= buf_size) {
7096 + memcpy(buf + buf_size - sizeof("..."), "...", sizeof("...") - 1);
7097 + len = buf_size - 1;
7100 + buf[len++] = '\n';
7102 + write(zlog_fd > -1 ? zlog_fd : STDERR_FILENO, buf, len);
7104 diff -urNp -x '*.orig' php-5.2.17.org/sapi/cgi/fpm/zlog.h php-5.2.17/sapi/cgi/fpm/zlog.h
7105 --- php-5.2.17.org/sapi/cgi/fpm/zlog.h 1970-01-01 01:00:00.000000000 +0100
7106 +++ php-5.2.17/sapi/cgi/fpm/zlog.h 2021-10-23 19:09:19.833125073 +0200
7110 + /* (c) 2004-2007 Andrei Nigmatulin */
7115 +#define ZLOG_STUFF __func__, __LINE__
7119 +int zlog_set_fd(int new_fd);
7120 +int zlog_set_level(int new_value);
7122 +size_t zlog_print_time(struct timeval *tv, char *timebuf, size_t timebuf_len);
7124 +void zlog(const char *function, int line, int flags, const char *fmt, ...)
7125 + __attribute__ ((format(printf,4,5)));
7135 +#define ZLOG_LEVEL_MASK 7
7137 +#define ZLOG_HAVE_ERRNO 0x100
7139 +#define ZLOG_SYSERROR (ZLOG_ERROR | ZLOG_HAVE_ERRNO)