mirror of
https://github.com/nginx/nginx.git
synced 2024-12-20 14:13:33 -06:00
implement "-s signal" option for Unix
This commit is contained in:
parent
80ce3d4dd1
commit
c8e9f26a57
@ -188,9 +188,7 @@ static ngx_uint_t ngx_show_version;
|
||||
static ngx_uint_t ngx_show_configure;
|
||||
static u_char *ngx_conf_file;
|
||||
static u_char *ngx_conf_params;
|
||||
#if (NGX_WIN32)
|
||||
static char *ngx_signal;
|
||||
#endif
|
||||
|
||||
|
||||
static char **ngx_os_environ;
|
||||
@ -213,20 +211,16 @@ main(int argc, char *const *argv)
|
||||
|
||||
if (ngx_show_help) {
|
||||
ngx_log_stderr(
|
||||
"Usage: nginx [-?hvVt]"
|
||||
#if (NGX_WIN32)
|
||||
" [-s signal]"
|
||||
#endif
|
||||
" [-c filename] [-g directives]" CRLF CRLF
|
||||
"Usage: nginx [-?hvVt] [-s signal] [-c filename] "
|
||||
"[-g directives]" CRLF CRLF
|
||||
"Options:" CRLF
|
||||
" -?,-h : this help" CRLF
|
||||
" -v : show version and exit" CRLF
|
||||
" -V : show version and configure options then exit"
|
||||
CRLF
|
||||
" -t : test configuration and exit" CRLF
|
||||
#if (NGX_WIN32)
|
||||
" -s signal : send signal to a master process" CRLF
|
||||
#endif
|
||||
" -s signal : send signal to a master process: "
|
||||
"stop, quit, reopen, reload" CRLF
|
||||
" -c filename : set configuration file (default: "
|
||||
NGX_CONF_PATH ")" CRLF
|
||||
" -g directives : set global directives out of configuration "
|
||||
@ -337,13 +331,11 @@ main(int argc, char *const *argv)
|
||||
ngx_process = NGX_PROCESS_MASTER;
|
||||
}
|
||||
|
||||
#if (NGX_WIN32)
|
||||
|
||||
if (ngx_signal) {
|
||||
return ngx_signal_process(cycle, ngx_signal);
|
||||
}
|
||||
|
||||
#else
|
||||
#if !(NGX_WIN32)
|
||||
|
||||
if (ngx_init_signals(cycle->log) != NGX_OK) {
|
||||
return 1;
|
||||
@ -685,7 +677,6 @@ ngx_get_options(int argc, char *const *argv)
|
||||
ngx_log_stderr("the option \"-g\" requires parameter");
|
||||
return NGX_ERROR;
|
||||
|
||||
#if (NGX_WIN32)
|
||||
case 's':
|
||||
if (*p) {
|
||||
ngx_signal = (char *) p;
|
||||
@ -709,7 +700,6 @@ ngx_get_options(int argc, char *const *argv)
|
||||
|
||||
ngx_log_stderr("invalid option: \"-s %s\"", ngx_signal);
|
||||
return NGX_ERROR;
|
||||
#endif
|
||||
|
||||
default:
|
||||
ngx_log_stderr("invalid option: \"%c\"", *(p - 1));
|
||||
|
@ -569,12 +569,14 @@ ngx_init_cycle(ngx_cycle_t *old_cycle)
|
||||
}
|
||||
}
|
||||
|
||||
if (ngx_open_listening_sockets(cycle) != NGX_OK) {
|
||||
goto failed;
|
||||
}
|
||||
if (ngx_process != NGX_PROCESS_SIGNALLER) {
|
||||
if (ngx_open_listening_sockets(cycle) != NGX_OK) {
|
||||
goto failed;
|
||||
}
|
||||
|
||||
if (!ngx_test_config) {
|
||||
ngx_configure_listening_socket(cycle);
|
||||
if (!ngx_test_config) {
|
||||
ngx_configure_listening_socket(cycle);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -986,6 +988,58 @@ ngx_delete_pidfile(ngx_cycle_t *cycle)
|
||||
}
|
||||
|
||||
|
||||
ngx_int_t
|
||||
ngx_signal_process(ngx_cycle_t *cycle, char *sig)
|
||||
{
|
||||
ssize_t n;
|
||||
ngx_int_t pid;
|
||||
ngx_file_t file;
|
||||
ngx_core_conf_t *ccf;
|
||||
u_char buf[NGX_INT64_LEN + 2];
|
||||
|
||||
ngx_log_error(NGX_LOG_NOTICE, cycle->log, 0, "signal process started");
|
||||
|
||||
ccf = (ngx_core_conf_t *) ngx_get_conf(cycle->conf_ctx, ngx_core_module);
|
||||
|
||||
file.name = ccf->pid;
|
||||
file.log = cycle->log;
|
||||
|
||||
file.fd = ngx_open_file(file.name.data, NGX_FILE_RDONLY,
|
||||
NGX_FILE_OPEN, NGX_FILE_DEFAULT_ACCESS);
|
||||
|
||||
if (file.fd == NGX_INVALID_FILE) {
|
||||
ngx_log_error(NGX_LOG_ERR, cycle->log, ngx_errno,
|
||||
ngx_open_file_n " \"%s\" failed", file.name.data);
|
||||
return 1;
|
||||
}
|
||||
|
||||
n = ngx_read_file(&file, buf, NGX_INT64_LEN + 2, 0);
|
||||
|
||||
if (ngx_close_file(file.fd) == NGX_FILE_ERROR) {
|
||||
ngx_log_error(NGX_LOG_ALERT, cycle->log, ngx_errno,
|
||||
ngx_close_file_n " \"%s\" failed", file.name.data);
|
||||
}
|
||||
|
||||
if (n == NGX_ERROR) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
while (n-- && (buf[n] == CR || buf[n] == LF)) { /* void */ }
|
||||
|
||||
pid = ngx_atoi(buf, ++n);
|
||||
|
||||
if (pid == NGX_ERROR) {
|
||||
ngx_log_error(NGX_LOG_ERR, cycle->log, 0,
|
||||
"invalid PID number \"%*s\" in \"%s\"",
|
||||
n, buf, file.name.data);
|
||||
return 1;
|
||||
}
|
||||
|
||||
return ngx_os_signal_process(cycle, sig, pid);
|
||||
|
||||
}
|
||||
|
||||
|
||||
static ngx_int_t
|
||||
ngx_test_lockfile(u_char *file, ngx_log_t *log)
|
||||
{
|
||||
|
@ -116,6 +116,7 @@ typedef struct {
|
||||
ngx_cycle_t *ngx_init_cycle(ngx_cycle_t *old_cycle);
|
||||
ngx_int_t ngx_create_pidfile(ngx_str_t *name, ngx_log_t *log);
|
||||
void ngx_delete_pidfile(ngx_cycle_t *cycle);
|
||||
ngx_int_t ngx_signal_process(ngx_cycle_t *cycle, char *sig);
|
||||
void ngx_reopen_files(ngx_cycle_t *cycle, ngx_uid_t user);
|
||||
char **ngx_set_environment(ngx_cycle_t *cycle, ngx_uint_t *last);
|
||||
ngx_pid_t ngx_exec_new_binary(ngx_cycle_t *cycle, char *const *argv);
|
||||
|
@ -37,6 +37,7 @@ void ngx_os_status(ngx_log_t *log);
|
||||
ngx_int_t ngx_os_specific_init(ngx_log_t *log);
|
||||
void ngx_os_specific_status(ngx_log_t *log);
|
||||
ngx_int_t ngx_daemon(ngx_log_t *log);
|
||||
ngx_int_t ngx_os_signal_process(ngx_cycle_t *cycle, char *sig, ngx_int_t pid);
|
||||
|
||||
|
||||
ssize_t ngx_unix_recv(ngx_connection_t *c, u_char *buf, size_t size);
|
||||
|
@ -13,6 +13,7 @@
|
||||
typedef struct {
|
||||
int signo;
|
||||
char *signame;
|
||||
char *name;
|
||||
void (*handler)(int signo);
|
||||
} ngx_signal_t;
|
||||
|
||||
@ -36,39 +37,45 @@ ngx_process_t ngx_processes[NGX_MAX_PROCESSES];
|
||||
ngx_signal_t signals[] = {
|
||||
{ ngx_signal_value(NGX_RECONFIGURE_SIGNAL),
|
||||
"SIG" ngx_value(NGX_RECONFIGURE_SIGNAL),
|
||||
"reload",
|
||||
ngx_signal_handler },
|
||||
|
||||
{ ngx_signal_value(NGX_REOPEN_SIGNAL),
|
||||
"SIG" ngx_value(NGX_REOPEN_SIGNAL),
|
||||
"reopen",
|
||||
ngx_signal_handler },
|
||||
|
||||
{ ngx_signal_value(NGX_NOACCEPT_SIGNAL),
|
||||
"SIG" ngx_value(NGX_NOACCEPT_SIGNAL),
|
||||
"",
|
||||
ngx_signal_handler },
|
||||
|
||||
{ ngx_signal_value(NGX_TERMINATE_SIGNAL),
|
||||
"SIG" ngx_value(NGX_TERMINATE_SIGNAL),
|
||||
"stop",
|
||||
ngx_signal_handler },
|
||||
|
||||
{ ngx_signal_value(NGX_SHUTDOWN_SIGNAL),
|
||||
"SIG" ngx_value(NGX_SHUTDOWN_SIGNAL),
|
||||
"quit",
|
||||
ngx_signal_handler },
|
||||
|
||||
{ ngx_signal_value(NGX_CHANGEBIN_SIGNAL),
|
||||
"SIG" ngx_value(NGX_CHANGEBIN_SIGNAL),
|
||||
"",
|
||||
ngx_signal_handler },
|
||||
|
||||
{ SIGALRM, "SIGALRM", ngx_signal_handler },
|
||||
{ SIGALRM, "SIGALRM", "", ngx_signal_handler },
|
||||
|
||||
{ SIGINT, "SIGINT", ngx_signal_handler },
|
||||
{ SIGINT, "SIGINT", "", ngx_signal_handler },
|
||||
|
||||
{ SIGIO, "SIGIO", ngx_signal_handler },
|
||||
{ SIGIO, "SIGIO", "", ngx_signal_handler },
|
||||
|
||||
{ SIGCHLD, "SIGCHLD", ngx_signal_handler },
|
||||
{ SIGCHLD, "SIGCHLD", "", ngx_signal_handler },
|
||||
|
||||
{ SIGPIPE, "SIGPIPE, SIG_IGN", SIG_IGN },
|
||||
{ SIGPIPE, "SIGPIPE, SIG_IGN", "", SIG_IGN },
|
||||
|
||||
{ 0, NULL, NULL }
|
||||
{ 0, NULL, "", NULL }
|
||||
};
|
||||
|
||||
|
||||
@ -540,3 +547,23 @@ ngx_debug_point(void)
|
||||
ngx_abort();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
ngx_int_t
|
||||
ngx_os_signal_process(ngx_cycle_t *cycle, char *name, ngx_int_t pid)
|
||||
{
|
||||
ngx_signal_t *sig;
|
||||
|
||||
for (sig = signals; sig->signo != 0; sig++) {
|
||||
if (ngx_strcmp(name, sig->name) == 0) {
|
||||
if (kill(pid, sig->signo) != -1) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
ngx_log_error(NGX_LOG_ALERT, cycle->log, ngx_errno,
|
||||
"kill(%P, %d) failed", pid, sig->signo);
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
@ -19,9 +19,10 @@
|
||||
#define NGX_CMD_REOPEN 5
|
||||
|
||||
|
||||
#define NGX_PROCESS_SINGLE 0
|
||||
#define NGX_PROCESS_MASTER 1
|
||||
#define NGX_PROCESS_WORKER 2
|
||||
#define NGX_PROCESS_SINGLE 0
|
||||
#define NGX_PROCESS_MASTER 1
|
||||
#define NGX_PROCESS_WORKER 2
|
||||
#define NGX_PROCESS_SIGNALLER 3
|
||||
|
||||
|
||||
void ngx_master_process_cycle(ngx_cycle_t *cycle);
|
||||
|
@ -11,6 +11,7 @@
|
||||
#include <ngx_config.h>
|
||||
#include <ngx_core.h>
|
||||
|
||||
|
||||
#define NGX_IO_SENDFILE 1
|
||||
|
||||
|
||||
@ -32,6 +33,7 @@ typedef struct {
|
||||
|
||||
ngx_int_t ngx_os_init(ngx_log_t *log);
|
||||
void ngx_os_status(ngx_log_t *log);
|
||||
ngx_int_t ngx_os_signal_process(ngx_cycle_t *cycle, char *sig, ngx_int_t pid);
|
||||
|
||||
ssize_t ngx_wsarecv(ngx_connection_t *c, u_char *buf, size_t size);
|
||||
ssize_t ngx_overlapped_wsarecv(ngx_connection_t *c, u_char *buf, size_t size);
|
||||
|
@ -1006,50 +1006,11 @@ ngx_single_process_cycle(ngx_cycle_t *cycle)
|
||||
|
||||
|
||||
ngx_int_t
|
||||
ngx_signal_process(ngx_cycle_t *cycle, char *sig)
|
||||
ngx_os_signal_process(ngx_cycle_t *cycle, char *sig, ngx_int_t pid)
|
||||
{
|
||||
size_t n;
|
||||
HANDLE ev;
|
||||
ngx_int_t rc, pid;
|
||||
ngx_file_t file;
|
||||
ngx_core_conf_t *ccf;
|
||||
u_char buf[NGX_INT64_LEN + 2];
|
||||
char evn[NGX_PROCESS_SYNC_NAME];
|
||||
|
||||
ngx_log_error(NGX_LOG_NOTICE, cycle->log, 0, "signal process started");
|
||||
|
||||
ccf = (ngx_core_conf_t *) ngx_get_conf(cycle->conf_ctx, ngx_core_module);
|
||||
|
||||
file.name = ccf->pid;
|
||||
file.log = cycle->log;
|
||||
|
||||
file.fd = ngx_open_file(file.name.data, NGX_FILE_RDONLY,
|
||||
NGX_FILE_OPEN, NGX_FILE_DEFAULT_ACCESS);
|
||||
|
||||
if (file.fd == NGX_INVALID_FILE) {
|
||||
ngx_log_error(NGX_LOG_ERR, cycle->log, ngx_errno,
|
||||
ngx_open_file_n " \"%s\" failed", file.name.data);
|
||||
return 1;
|
||||
}
|
||||
|
||||
rc = 1;
|
||||
|
||||
n = ngx_read_file(&file, buf, NGX_INT64_LEN + 2, 0);
|
||||
|
||||
if (n == NGX_ERROR) {
|
||||
goto failed;
|
||||
}
|
||||
|
||||
while (n-- && (buf[n] == CR || buf[n] == LF)) { /* void */ }
|
||||
|
||||
pid = ngx_atoi(buf, ++n);
|
||||
|
||||
if (pid == NGX_ERROR) {
|
||||
ngx_log_error(NGX_LOG_ERR, cycle->log, 0,
|
||||
"invalid PID number \"%*s\" in \"%s\"",
|
||||
n, buf, file.name.data);
|
||||
goto failed;
|
||||
}
|
||||
HANDLE ev;
|
||||
ngx_int_t rc;
|
||||
char evn[NGX_PROCESS_SYNC_NAME];
|
||||
|
||||
ngx_sprintf((u_char *) evn, "ngx_%s_%ul%Z", sig, pid);
|
||||
|
||||
@ -1057,25 +1018,20 @@ ngx_signal_process(ngx_cycle_t *cycle, char *sig)
|
||||
if (ev == NULL) {
|
||||
ngx_log_error(NGX_LOG_ERR, cycle->log, ngx_errno,
|
||||
"OpenEvent(\"%s\") failed", evn);
|
||||
goto failed;
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (SetEvent(ev) == 0) {
|
||||
ngx_log_error(NGX_LOG_ALERT, cycle->log, ngx_errno,
|
||||
"SetEvent(\"%s\") failed", evn);
|
||||
rc = 1;
|
||||
|
||||
} else {
|
||||
rc = 0;
|
||||
}
|
||||
|
||||
ngx_close_handle(ev);
|
||||
|
||||
failed:
|
||||
|
||||
if (ngx_close_file(file.fd) == NGX_FILE_ERROR) {
|
||||
ngx_log_error(NGX_LOG_ALERT, cycle->log, ngx_errno,
|
||||
ngx_close_file_n " \"%s\" failed", file.name.data);
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
@ -20,7 +20,6 @@
|
||||
|
||||
void ngx_master_process_cycle(ngx_cycle_t *cycle);
|
||||
void ngx_single_process_cycle(ngx_cycle_t *cycle);
|
||||
ngx_int_t ngx_signal_process(ngx_cycle_t *cycle, char *sig);
|
||||
void ngx_close_handle(HANDLE h);
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user