Skip to content

Commit 7598007

Browse files
author
Jérôme Loyet
committed
status and ping online feature
1 parent 2d79ec1 commit 7598007

14 files changed

+412
-4
lines changed

sapi/fpm/config.m4

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -585,6 +585,7 @@ if test "$PHP_FPM" != "no"; then
585585
fpm/fpm_shm_slots.c \
586586
fpm/fpm_signals.c \
587587
fpm/fpm_sockets.c \
588+
fpm/fpm_status.c \
588589
fpm/fpm_stdio.c \
589590
fpm/fpm_unix.c \
590591
fpm/fpm_worker_pool.c \

sapi/fpm/fpm/fpm_children.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
#include "fpm_unix.h"
2727
#include "fpm_env.h"
2828
#include "fpm_shm_slots.h"
29+
#include "fpm_status.h"
2930

3031
#include "zlog.h"
3132

@@ -145,6 +146,7 @@ static void fpm_child_init(struct fpm_worker_pool_s *wp) /* {{{ */
145146
fpm_globals.max_requests = wp->config->max_requests;
146147

147148
if (0 > fpm_stdio_init_child(wp) ||
149+
0 > fpm_status_init_child(wp) ||
148150
0 > fpm_unix_init_child(wp) ||
149151
0 > fpm_signals_init_child() ||
150152
0 > fpm_env_init_child(wp) ||

sapi/fpm/fpm/fpm_conf.c

Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
#include <string.h>
1111
#include <stdlib.h>
1212
#include <stddef.h>
13+
#include <string.h>
1314
#if HAVE_INTTYPES_H
1415
# include <inttypes.h>
1516
#else
@@ -26,6 +27,8 @@
2627
#include "fpm_cleanup.h"
2728
#include "fpm_php.h"
2829
#include "fpm_sockets.h"
30+
#include "fpm_shm.h"
31+
#include "fpm_status.h"
2932
#include "xml_config.h"
3033
#include "zlog.h"
3134

@@ -190,6 +193,9 @@ static struct xml_conf_section fpm_conf_set_pm_subsection_conf = {
190193
.parsers = (struct xml_value_parser []) {
191194
{ XML_CONF_SCALAR, "style", &fpm_conf_set_pm_style, 0 },
192195
{ XML_CONF_SCALAR, "max_children", &xml_conf_set_slot_integer, offsetof(struct fpm_pm_s, max_children) },
196+
{ XML_CONF_SCALAR, "status", &xml_conf_set_slot_string, offsetof(struct fpm_pm_s, status) },
197+
{ XML_CONF_SCALAR, "ping", &xml_conf_set_slot_string, offsetof(struct fpm_pm_s, ping) },
198+
{ XML_CONF_SCALAR, "pong", &xml_conf_set_slot_string, offsetof(struct fpm_pm_s, pong) },
193199
{ XML_CONF_SUBSECTION, "dynamic", &fpm_conf_set_dynamic_subsection, offsetof(struct fpm_pm_s, dynamic) },
194200
{ 0, 0, 0, 0 }
195201
}
@@ -288,6 +294,9 @@ int fpm_worker_pool_config_free(struct fpm_worker_pool_config_s *wpc) /* {{{ */
288294

289295
free(wpc->name);
290296
free(wpc->listen_address);
297+
free(wpc->pm->status);
298+
free(wpc->pm->ping);
299+
free(wpc->pm->pong);
291300
if (wpc->listen_options) {
292301
free(wpc->listen_options->owner);
293302
free(wpc->listen_options->group);
@@ -466,6 +475,74 @@ static int fpm_conf_process_all_pools() /* {{{ */
466475
close(fd);
467476
}
468477
}
478+
479+
if (wp->config->pm->ping && *wp->config->pm->ping) {
480+
char *ping = wp->config->pm->ping;
481+
int i;
482+
483+
if (*ping != '/') {
484+
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] the ping page '%s' must start with a '/'", wp->config->name, ping);
485+
return(-1);
486+
}
487+
488+
if (strlen(ping) < 2) {
489+
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] the ping page '%s' is not long enough", wp->config->name, ping);
490+
return(-1);
491+
}
492+
493+
for (i=0; i<strlen(ping); i++) {
494+
if (!isalnum(ping[i]) && ping[i] != '/' && ping[i] != '-' && ping[i] != '_' && ping[i] != '.') {
495+
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] the ping page '%s' must containt only the following characters '[alphanum]/_-.'", wp->config->name, ping);
496+
return(-1);
497+
}
498+
}
499+
500+
if (!wp->config->pm->pong) {
501+
wp->config->pm->pong = strdup("pong");
502+
} else {
503+
if (strlen(wp->config->pm->pong) < 1) {
504+
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] the ping response page '%s' is not long enough", wp->config->name, wp->config->pm->pong);
505+
return(-1);
506+
}
507+
}
508+
} else {
509+
if (wp->config->pm->pong) {
510+
free(wp->config->pm->pong);
511+
wp->config->pm->pong = NULL;
512+
}
513+
}
514+
515+
if (wp->config->pm->status && *wp->config->pm->status) {
516+
int i;
517+
char *status = wp->config->pm->status;
518+
struct fpm_status_s fpm_status;
519+
520+
if (*status != '/') {
521+
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] the status page '%s' must start with a '/'", wp->config->name, status);
522+
return(-1);
523+
}
524+
525+
if (strlen(status) < 2) {
526+
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] the status page '%s' is not long enough", wp->config->name, status);
527+
return(-1);
528+
}
529+
530+
for (i=0; i<strlen(status); i++) {
531+
if (!isalnum(status[i]) && status[i] != '/' && status[i] != '-' && status[i] != '_' && status[i] != '.') {
532+
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] the status page '%s' must containt only the following characters '[alphanum]/_-.'", wp->config->name, status);
533+
return(-1);
534+
}
535+
}
536+
wp->shm_status = fpm_shm_alloc(sizeof(struct fpm_status_s));
537+
if (!wp->shm_status) {
538+
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] unable to allocate shared memory for status page '%s'", wp->config->name, status);
539+
return(-1);
540+
}
541+
fpm_status_update_accepted_conn(wp->shm_status, 0);
542+
fpm_status_update_activity(wp->shm_status, -1, -1, -1, 1);
543+
fpm_status_set_pm(wp->shm_status, wp->config->pm->style);
544+
//memset(&fpm_status.last_update, 0, sizeof(fpm_status.last_update));
545+
}
469546
}
470547
return 0;
471548
}

sapi/fpm/fpm/fpm_conf.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@
55
#ifndef FPM_CONF_H
66
#define FPM_CONF_H 1
77

8+
#define FPM_CONF_MAX_PONG_LENGTH 64
9+
810
struct key_value_s;
911

1012
struct key_value_s {
@@ -27,6 +29,9 @@ extern struct fpm_global_config_s fpm_global_config;
2729
struct fpm_pm_s {
2830
int style;
2931
int max_children;
32+
char *status;
33+
char *ping;
34+
char *pong;
3035
struct {
3136
int start_servers;
3237
int min_spare_servers;

sapi/fpm/fpm/fpm_main.c

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,7 @@ int __riscosify_control = __RISCOSIFY_STRICT_UNIX_SPECS;
102102
#endif
103103
#include <fpm/fpm.h>
104104
#include <fpm/fpm_request.h>
105+
#include <fpm/fpm_status.h>
105106

106107
#ifndef PHP_WIN32
107108
/* XXX this will need to change later when threaded fastcgi is implemented. shane */
@@ -1764,6 +1765,7 @@ consult the installation file that came with this distribution, or visit \n\
17641765
SG(server_context) = (void *) &request;
17651766
init_request_info(TSRMLS_C);
17661767
CG(interactive) = 0;
1768+
char *status_buffer;
17671769

17681770
fpm_request_info();
17691771

@@ -1776,6 +1778,27 @@ consult the installation file that came with this distribution, or visit \n\
17761778
return FAILURE;
17771779
}
17781780

1781+
if (fpm_status_handle_status(SG(request_info).request_uri, &status_buffer)) {
1782+
sapi_add_header_ex(ZEND_STRL("Content-Type: text/plain"), 1, 1 TSRMLS_CC);
1783+
if (status_buffer) {
1784+
int i;
1785+
SG(sapi_headers).http_response_code = 200;
1786+
PUTS(status_buffer);
1787+
efree(status_buffer);
1788+
} else {
1789+
SG(sapi_headers).http_response_code = 500;
1790+
PUTS("Unable to retrieve status\n");
1791+
}
1792+
goto fastcgi_request_done;
1793+
}
1794+
1795+
if (status_buffer = fpm_status_handle_ping(SG(request_info).request_uri)) {
1796+
sapi_add_header_ex(ZEND_STRL("Content-Type: text/plain"), 1, 1 TSRMLS_CC);
1797+
SG(sapi_headers).http_response_code = 200;
1798+
PUTS(status_buffer);
1799+
goto fastcgi_request_done;
1800+
}
1801+
17791802
/* If path_translated is NULL, terminate here with a 404 */
17801803
if (!SG(request_info).path_translated) {
17811804
zend_try {

sapi/fpm/fpm/fpm_process_ctl.c

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
#include "fpm_cleanup.h"
1919
#include "fpm_request.h"
2020
#include "fpm_worker_pool.h"
21+
#include "fpm_status.h"
2122
#include "zlog.h"
2223

2324

@@ -322,7 +323,6 @@ static void fpm_pctl_perform_idle_server_maintenance(struct timeval *now) /* {{{
322323
int active = 0;
323324

324325
if (wp->config == NULL) continue;
325-
if (wp->config->pm->style != PM_STYLE_DYNAMIC) continue;
326326

327327
for (child = wp->children; child; child = child->next) {
328328
int ret = fpm_request_is_idle(child);
@@ -340,13 +340,19 @@ static void fpm_pctl_perform_idle_server_maintenance(struct timeval *now) /* {{{
340340
}
341341
}
342342

343-
zlog(ZLOG_STUFF, ZLOG_DEBUG, "[pool %s] currently %d active children, %d spare children, %d running children. Spawning rate %d", wp->config->name, active, idle, wp->running_children, wp->idle_spawn_rate);
344-
345343
if ((active + idle) != wp->running_children) {
346344
zlog(ZLOG_STUFF, ZLOG_ERROR, "[pool %s] unable to retrieve process activiry of one or more child(ren). Will try again later.", wp->config->name);
347345
continue;
348346
}
349347

348+
/* update status structure for all PMs */
349+
fpm_status_update_activity(wp->shm_status, idle, active, idle + active, 0);
350+
351+
/* the rest is only used by PM_STYLE_DYNAMIC */
352+
if (wp->config->pm->style != PM_STYLE_DYNAMIC) continue;
353+
354+
zlog(ZLOG_STUFF, ZLOG_DEBUG, "[pool %s] currently %d active children, %d spare children, %d running children. Spawning rate %d", wp->config->name, active, idle, wp->running_children, wp->idle_spawn_rate);
355+
350356
if (idle > wp->config->pm->dynamic.max_spare_servers && last_idle_child) {
351357
last_idle_child->idle_kill = 1;
352358
fpm_pctl_kill(last_idle_child->pid, FPM_PCTL_TERM);

sapi/fpm/fpm/fpm_request.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
#include "fpm_process_ctl.h"
1414
#include "fpm_children.h"
1515
#include "fpm_shm_slots.h"
16+
#include "fpm_status.h"
1617
#include "fpm_request.h"
1718

1819
#include "zlog.h"
@@ -40,6 +41,8 @@ void fpm_request_reading_headers() /* {{{ */
4041
fpm_clock_get(&slot->tv);
4142
slot->accepted = slot->tv;
4243
fpm_shm_slots_release(slot);
44+
45+
fpm_status_increment_accepted_conn(fpm_status_shm);
4346
}
4447
/* }}} */
4548

sapi/fpm/fpm/fpm_shm.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ struct fpm_shm_s *fpm_shm_alloc(size_t sz) /* {{{ */
4141
}
4242
/* }}} */
4343

44-
static void fpm_shm_free(struct fpm_shm_s *shm, int do_unmap) /* {{{ */
44+
void fpm_shm_free(struct fpm_shm_s *shm, int do_unmap) /* {{{ */
4545
{
4646
if (do_unmap) {
4747
munmap(shm->mem, shm->sz);

sapi/fpm/fpm/fpm_shm.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ struct fpm_shm_s {
1515
};
1616

1717
struct fpm_shm_s *fpm_shm_alloc(size_t sz);
18+
void fpm_shm_free(struct fpm_shm_s *shm, int do_unmap);
1819
void fpm_shm_free_list(struct fpm_shm_s *, void *);
1920
void *fpm_shm_alloc_chunk(struct fpm_shm_s **head, size_t sz, void **mem);
2021

0 commit comments

Comments
 (0)