[PATCH] os/unix: don't stop old workers if reload failed
kasei at kasei.im
kasei at kasei.im
Fri Dec 4 04:15:53 UTC 2020
Hello, We found sometimes nginx might failed to start new worker
processes
during reconfiguring, (the number of processes exceeds
NGX_MAX_PROCESSES for
example). In that case, the master process still send QUIT signal to
old
workers, leads to the situation that there is no worker processes
accept socket
from listening sockets.
And we found actually there is a return code in os/win32's
ngx_start_worker_processes funcation. It skip quiting workers if there
is no
worker processes be spawned. So I written this patch followed win32's
implementation and tested it. Cloud you please check this patch to see
if there
is anything missed? Thanks very much.
# HG changeset patch
# User Kasei Wang <kasei at kasei.im>
# Date 1607052987 -28800
# Fri Dec 04 11:36:27 2020 +0800
# Node ID 0711cc5f95b5fc2aad0b51328b382b5cfe08f8bb
# Parent 90cc7194e993f8d722347e9f46a00f65dffc3935
os/unix: don't stop old workers if start new worker processes
failed during reconfiguring.
diff -r 90cc7194e993 -r 0711cc5f95b5 src/os/unix/ngx_process_cycle.c
--- a/src/os/unix/ngx_process_cycle.c Fri Nov 27 00:01:20 2020 +0300
+++ b/src/os/unix/ngx_process_cycle.c Fri Dec 04 11:36:27 2020 +0800
@@ -11,7 +11,7 @@
#include <ngx_channel.h>
-static void ngx_start_worker_processes(ngx_cycle_t *cycle, ngx_int_t
n,
+static ngx_int_t ngx_start_worker_processes(ngx_cycle_t *cycle,
ngx_int_t n,
ngx_int_t type);
static void ngx_start_cache_manager_processes(ngx_cycle_t *cycle,
ngx_uint_t respawn);
@@ -127,8 +127,13 @@
ccf = (ngx_core_conf_t *) ngx_get_conf(cycle->conf_ctx,
ngx_core_module);
- ngx_start_worker_processes(cycle, ccf->worker_processes,
- NGX_PROCESS_RESPAWN);
+ if (ngx_start_worker_processes(cycle, ccf->worker_processes,
+ NGX_PROCESS_RESPAWN) == 0)
+ {
+ ngx_log_error(NGX_LOG_EMERG, cycle->log, 0,
+ "start worker processes failed");
+ exit(2);
+ }
ngx_start_cache_manager_processes(cycle, 0);
ngx_new_binary = 0;
@@ -231,8 +236,14 @@
ngx_cycle = cycle;
ccf = (ngx_core_conf_t *) ngx_get_conf(cycle->conf_ctx,
ngx_core_module);
- ngx_start_worker_processes(cycle, ccf->worker_processes,
- NGX_PROCESS_JUST_RESPAWN);
+ /* TODO: close reuseport listening sockets not handled by
worker */
+ if (ngx_start_worker_processes(cycle, ccf-
>worker_processes,
+ NGX_PROCESS_JUST_RESPAWN) == 0)
+ {
+ ngx_log_error(NGX_LOG_WARN, cycle->log, 0,
+ "start worker processes failed during reconfiguring");
+ continue;
+ }
ngx_start_cache_manager_processes(cycle, 1);
/* allow new processes to start */
@@ -332,7 +343,7 @@
}
-static void
+static ngx_int_t
ngx_start_worker_processes(ngx_cycle_t *cycle, ngx_int_t n, ngx_int_t
type)
{
ngx_int_t i;
@@ -346,8 +357,12 @@
for (i = 0; i < n; i++) {
- ngx_spawn_process(cycle, ngx_worker_process_cycle,
- (void *) (intptr_t) i, "worker process",
type);
+ if (ngx_spawn_process(cycle, ngx_worker_process_cycle,
+ (void *) (intptr_t) i, "worker process",
type)
+ == NGX_INVALID_PID)
+ {
+ break;
+ }
ch.pid = ngx_processes[ngx_process_slot].pid;
ch.slot = ngx_process_slot;
@@ -355,6 +370,8 @@
ngx_pass_open_channel(cycle, &ch);
}
+
+ return i;
}
More information about the nginx-devel
mailing list