1
0
mirror of https://github.com/php/php-src.git synced 2026-04-28 02:33:17 +02:00

Fix bug #76003: FPM /status reports wrong number of active processe

The fix introduces early locking of scoreboard when it is updated
which prevents the race condition causing an incorrect number of
active processes being set.
This commit is contained in:
Jakub Zelenka
2022-04-09 13:20:07 +01:00
parent 07e91ca91c
commit 33bb201b3e
5 changed files with 66 additions and 20 deletions
+4
View File
@@ -6,6 +6,10 @@ PHP NEWS
. Fixed bug GH-8289 (Exceptions thrown within a yielded from iterator are
not rethrown into the generator). (Bob)
- FPM:
. Fixed bug #76003 (FPM /status reports wrong number of active processe).
(Jakub Zelenka)
- MySQLi:
. Fixed bug GH-8267 (MySQLi uses unsupported format specifier on Windows).
(cmb)
+19 -16
View File
@@ -324,21 +324,6 @@ static void fpm_pctl_perform_idle_server_maintenance(struct timeval *now) /* {{{
if (wp->config == NULL) continue;
for (child = wp->children; child; child = child->next) {
if (fpm_request_is_idle(child)) {
if (last_idle_child == NULL) {
last_idle_child = child;
} else {
if (timercmp(&child->started, &last_idle_child->started, <)) {
last_idle_child = child;
}
}
idle++;
} else {
active++;
}
}
/* update status structure for all PMs */
if (wp->listen_address_domain == FPM_AF_INET) {
if (0 > fpm_socket_get_listening_queue(wp->listening_socket, &cur_lq, NULL)) {
@@ -356,7 +341,25 @@ static void fpm_pctl_perform_idle_server_maintenance(struct timeval *now) /* {{{
#endif
}
}
fpm_scoreboard_update(idle, active, cur_lq, -1, -1, -1, 0, FPM_SCOREBOARD_ACTION_SET, wp->scoreboard);
fpm_scoreboard_update_begin(wp->scoreboard);
for (child = wp->children; child; child = child->next) {
if (fpm_request_is_idle(child)) {
if (last_idle_child == NULL) {
last_idle_child = child;
} else {
if (timercmp(&child->started, &last_idle_child->started, <)) {
last_idle_child = child;
}
}
idle++;
} else {
active++;
}
}
fpm_scoreboard_update_commit(idle, active, cur_lq, -1, -1, -1, 0, FPM_SCOREBOARD_ACTION_SET, wp->scoreboard);
/* this is specific to PM_STYLE_ONDEMAND */
if (wp->config->pm == PM_STYLE_ONDEMAND) {
+6 -2
View File
@@ -41,6 +41,8 @@ void fpm_request_accepting() /* {{{ */
fpm_clock_get(&now);
fpm_scoreboard_update_begin(NULL);
proc = fpm_scoreboard_proc_acquire(NULL, -1, 0);
if (proc == NULL) {
zlog(ZLOG_WARNING, "failed to acquire proc scoreboard");
@@ -52,7 +54,7 @@ void fpm_request_accepting() /* {{{ */
fpm_scoreboard_proc_release(proc);
/* idle++, active-- */
fpm_scoreboard_update(1, -1, 0, 0, 0, 0, 0, FPM_SCOREBOARD_ACTION_INC, NULL);
fpm_scoreboard_update_commit(1, -1, 0, 0, 0, 0, 0, FPM_SCOREBOARD_ACTION_INC, NULL);
}
/* }}} */
@@ -72,6 +74,8 @@ void fpm_request_reading_headers() /* {{{ */
times(&cpu);
#endif
fpm_scoreboard_update_begin(NULL);
proc = fpm_scoreboard_proc_acquire(NULL, -1, 0);
if (proc == NULL) {
zlog(ZLOG_WARNING, "failed to acquire proc scoreboard");
@@ -95,7 +99,7 @@ void fpm_request_reading_headers() /* {{{ */
fpm_scoreboard_proc_release(proc);
/* idle--, active++, request++ */
fpm_scoreboard_update(-1, 1, 0, 0, 1, 0, 0, FPM_SCOREBOARD_ACTION_INC, NULL);
fpm_scoreboard_update_commit(-1, 1, 0, 0, 1, 0, 0, FPM_SCOREBOARD_ACTION_INC, NULL);
}
/* }}} */
+34 -2
View File
@@ -74,18 +74,39 @@ int fpm_scoreboard_init_main() /* {{{ */
}
/* }}} */
void fpm_scoreboard_update(int idle, int active, int lq, int lq_len, int requests, int max_children_reached, int slow_rq, int action, struct fpm_scoreboard_s *scoreboard) /* {{{ */
static struct fpm_scoreboard_s *fpm_scoreboard_get_for_update(struct fpm_scoreboard_s *scoreboard) /* {{{ */
{
if (!scoreboard) {
scoreboard = fpm_scoreboard;
}
if (!scoreboard) {
zlog(ZLOG_WARNING, "Unable to update scoreboard: the SHM has not been found");
}
return scoreboard;
}
/* }}} */
void fpm_scoreboard_update_begin(struct fpm_scoreboard_s *scoreboard) /* {{{ */
{
scoreboard = fpm_scoreboard_get_for_update(scoreboard);
if (!scoreboard) {
return;
}
fpm_spinlock(&scoreboard->lock, 0);
}
/* }}} */
void fpm_scoreboard_update_commit(
int idle, int active, int lq, int lq_len, int requests, int max_children_reached,
int slow_rq, int action, struct fpm_scoreboard_s *scoreboard) /* {{{ */
{
scoreboard = fpm_scoreboard_get_for_update(scoreboard);
if (!scoreboard) {
return;
}
if (action == FPM_SCOREBOARD_ACTION_SET) {
if (idle >= 0) {
scoreboard->idle = idle;
@@ -154,6 +175,17 @@ void fpm_scoreboard_update(int idle, int active, int lq, int lq_len, int request
}
/* }}} */
void fpm_scoreboard_update(
int idle, int active, int lq, int lq_len, int requests, int max_children_reached,
int slow_rq, int action, struct fpm_scoreboard_s *scoreboard) /* {{{ */
{
fpm_scoreboard_update_begin(scoreboard);
fpm_scoreboard_update_commit(
idle, active, lq, lq_len, requests, max_children_reached, slow_rq, action, scoreboard);
}
/* }}} */
struct fpm_scoreboard_s *fpm_scoreboard_get() /* {{{*/
{
return fpm_scoreboard;
+3
View File
@@ -73,7 +73,10 @@ struct fpm_scoreboard_s {
int fpm_scoreboard_init_main();
int fpm_scoreboard_init_child(struct fpm_worker_pool_s *wp);
void fpm_scoreboard_update_begin(struct fpm_scoreboard_s *scoreboard);
void fpm_scoreboard_update_commit(int idle, int active, int lq, int lq_len, int requests, int max_children_reached, int slow_rq, int action, struct fpm_scoreboard_s *scoreboard);
void fpm_scoreboard_update(int idle, int active, int lq, int lq_len, int requests, int max_children_reached, int slow_rq, int action, struct fpm_scoreboard_s *scoreboard);
struct fpm_scoreboard_s *fpm_scoreboard_get();
struct fpm_scoreboard_proc_s *fpm_scoreboard_proc_get(struct fpm_scoreboard_s *scoreboard, int child_index);
struct fpm_scoreboard_proc_s *fpm_scoreboard_proc_get_from_child(struct fpm_child_s *child);