lighttpd 1.4.x https://www.lighttpd.net/
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1635 lines
42 KiB

#include "first.h"
#include "base.h"
#include "buffer.h"
#include "network.h"
#include "log.h"
#include "rand.h"
#include "chunk.h"
#include "http_auth.h" /* http_auth_dumbdata_reset() */
#include "http_vhostdb.h" /* http_vhostdb_dumbdata_reset() */
#include "fdevent.h"
#include "connections.h"
#include "sock_addr.h"
#include "stat_cache.h"
#include "plugin.h"
#include "network_write.h" /* network_write_show_handlers() */
#include "response.h" /* strftime_cache_reset() */
#ifdef HAVE_VERSIONSTAMP_H
# include "versionstamp.h"
#else
# define REPO_VERSION ""
#endif
#define PACKAGE_DESC PACKAGE_NAME "/" PACKAGE_VERSION REPO_VERSION
static const buffer default_server_tag = { CONST_STR_LEN(PACKAGE_DESC), 0 };
#include <sys/types.h>
#include <sys/time.h>
#include <sys/stat.h>
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
#include <sys/wait.h>
#include <string.h>
#include <errno.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdlib.h>
#include <time.h>
#include <signal.h>
#include <locale.h>
#include <stdio.h>
#ifdef HAVE_GETOPT_H
# include <getopt.h>
#endif
#ifdef HAVE_VALGRIND_VALGRIND_H
# include <valgrind/valgrind.h>
#endif
#ifdef HAVE_SYS_WAIT_H
# include <sys/wait.h>
#endif
#ifdef HAVE_PWD_H
# include <grp.h>
# include <pwd.h>
#endif
#ifdef HAVE_SYS_LOADAVG_H
# include <sys/loadavg.h>
#endif
#ifdef HAVE_SYS_RESOURCE_H
# include <sys/resource.h>
#endif
#ifdef HAVE_SYS_PRCTL_H
# include <sys/prctl.h>
#endif
#include "sys-crypto.h"
#if defined(USE_OPENSSL_CRYPTO) \
|| defined(USE_MBEDTLS_CRYPTO) \
|| defined(USE_NSS_CRYPTO) \
|| defined(USE_GNUTLS_CRYPTO) \
|| defined(USE_WOLFTLS_CRYPTO)
#define TEXT_SSL " (ssl)"
#else
#define TEXT_SSL
#endif
#ifndef __sgi
/* IRIX doesn't like the alarm based time() optimization */
/* #define USE_ALARM */
#endif
static int oneshot_fd = 0;
static volatile int pid_fd = -2;
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static server_socket_array graceful_sockets;
static server_socket_array inherited_sockets;
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static volatile sig_atomic_t graceful_restart = 0;
static volatile sig_atomic_t graceful_shutdown = 0;
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static volatile sig_atomic_t srv_shutdown = 0;
static volatile sig_atomic_t handle_sig_child = 0;
static volatile sig_atomic_t handle_sig_alarm = 1;
static volatile sig_atomic_t handle_sig_hup = 0;
static time_t idle_limit = 0;
#if defined(HAVE_SIGACTION) && defined(SA_SIGINFO)
static volatile siginfo_t last_sigterm_info;
static volatile siginfo_t last_sighup_info;
static void sigaction_handler(int sig, siginfo_t *si, void *context) {
static const siginfo_t empty_siginfo;
UNUSED(context);
if (!si) *(const siginfo_t **)&si = &empty_siginfo;
switch (sig) {
case SIGTERM:
srv_shutdown = 1;
last_sigterm_info = *si;
break;
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
case SIGUSR1:
if (!graceful_shutdown) {
graceful_restart = 1;
graceful_shutdown = 1;
last_sigterm_info = *si;
}
break;
case SIGINT:
if (graceful_shutdown) {
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
if (2 == graceful_restart)
graceful_restart = 1;
else
srv_shutdown = 1;
} else {
graceful_shutdown = 1;
}
last_sigterm_info = *si;
break;
case SIGALRM:
handle_sig_alarm = 1;
break;
case SIGHUP:
handle_sig_hup = 1;
last_sighup_info = *si;
break;
case SIGCHLD:
handle_sig_child = 1;
break;
}
}
#elif defined(HAVE_SIGNAL) || defined(HAVE_SIGACTION)
static void signal_handler(int sig) {
switch (sig) {
case SIGTERM: srv_shutdown = 1; break;
case SIGUSR1:
if (!graceful_shutdown) {
graceful_restart = 1;
graceful_shutdown = 1;
}
break;
case SIGINT:
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
if (graceful_shutdown) {
if (2 == graceful_restart)
graceful_restart = 1;
else
srv_shutdown = 1;
} else {
graceful_shutdown = 1;
}
break;
case SIGALRM: handle_sig_alarm = 1; break;
case SIGHUP: handle_sig_hup = 1; break;
case SIGCHLD: handle_sig_child = 1; break;
}
}
#endif
#ifdef HAVE_FORK
static int daemonize(void) {
int pipefd[2];
pid_t pid;
#ifdef SIGTTOU
signal(SIGTTOU, SIG_IGN);
#endif
#ifdef SIGTTIN
signal(SIGTTIN, SIG_IGN);
#endif
#ifdef SIGTSTP
signal(SIGTSTP, SIG_IGN);
#endif
if (pipe(pipefd) < 0) exit(-1);
if (0 > (pid = fork())) exit(-1);
if (0 < pid) {
char buf;
ssize_t bytes;
close(pipefd[1]);
/* parent waits for grandchild to be ready */
do {
bytes = read(pipefd[0], &buf, sizeof(buf));
} while (bytes < 0 && EINTR == errno);
close(pipefd[0]);
if (bytes <= 0) {
/* closed fd (without writing) == failure in grandchild */
fputs("daemonized server failed to start; check error log for details\n", stderr);
exit(-1);
}
exit(0);
}
close(pipefd[0]);
if (-1 == setsid()) exit(0);
signal(SIGHUP, SIG_IGN);
if (0 != fork()) exit(0);
if (0 != chdir("/")) exit(0);
fdevent_setfd_cloexec(pipefd[1]);
return pipefd[1];
}
#endif
__attribute_cold__
static server *server_init(void) {
server *srv = calloc(1, sizeof(*srv));
force_assert(srv);
#define CLEAN(x) \
srv->x = buffer_init();
CLEAN(tmp_buf);
#undef CLEAN
strftime_cache_reset();
li_rand_reseed();
srv->startup_ts = log_epoch_secs = time(NULL);
srv->errh = log_error_st_init();
config_init(srv);
srv->request_env = plugins_call_handle_request_env;
srv->loadavg[0] = 0.0;
srv->loadavg[1] = 0.0;
srv->loadavg[2] = 0.0;
srv->stdin_fd = -1;
return srv;
}
__attribute_cold__
static void server_free(server *srv) {
if (oneshot_fd > 0) {
close(oneshot_fd);
}
if (srv->stdin_fd >= 0) {
close(srv->stdin_fd);
}
#define CLEAN(x) \
buffer_free(srv->x);
CLEAN(tmp_buf);
#undef CLEAN
fdevent_free(srv->ev);
config_free(srv);
free(srv->joblist.ptr);
free(srv->fdwaitqueue.ptr);
stat_cache_free();
li_rand_cleanup();
chunkqueue_chunk_pool_free();
log_error_st_free(srv->errh);
free(srv);
}
__attribute_cold__
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static void remove_pid_file(server *srv) {
if (pid_fd <= -2) return;
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
if (!buffer_string_is_empty(srv->srvconf.pid_file) && 0 <= pid_fd) {
if (0 != ftruncate(pid_fd, 0)) {
log_perror(srv->errh, __FILE__, __LINE__,
"ftruncate failed for: %s", srv->srvconf.pid_file->ptr);
}
}
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
if (0 <= pid_fd) {
close(pid_fd);
pid_fd = -1;
}
if (!buffer_string_is_empty(srv->srvconf.pid_file) &&
buffer_string_is_empty(srv->srvconf.changeroot)) {
if (0 != unlink(srv->srvconf.pid_file->ptr)) {
if (errno != EACCES && errno != EPERM) {
log_perror(srv->errh, __FILE__, __LINE__,
"unlink failed for: %s", srv->srvconf.pid_file->ptr);
}
}
}
}
__attribute_cold__
static server_socket * server_oneshot_getsock(server *srv, sock_addr *cnt_addr) {
server_socket *srv_socket, *srv_socket_wild = NULL;
for (uint32_t i = 0; i < srv->srv_sockets.used; ++i) {
srv_socket = srv->srv_sockets.ptr[i];
if (!sock_addr_is_port_eq(&srv_socket->addr,cnt_addr)) continue;
if (sock_addr_is_addr_eq(&srv_socket->addr,cnt_addr)) return srv_socket;
if (NULL != srv_socket_wild) continue;
if (sock_addr_is_addr_wildcard(&srv_socket->addr)) {
srv_socket_wild = srv_socket;
}
}
if (NULL != srv_socket_wild) {
return srv_socket_wild;
} else if (srv->srv_sockets.used) {
return srv->srv_sockets.ptr[0];
} else {
log_error(srv->errh, __FILE__, __LINE__, "no sockets configured");
return NULL;
}
}
__attribute_cold__
static int server_oneshot_init(server *srv, int fd) {
/* Note: does not work with netcat due to requirement that fd be socket.
* STDOUT_FILENO was not saved earlier in startup, and that is to where
* netcat expects output to be sent. Since lighttpd expects connections
* to be sockets, con->fd is where output is sent; separate fds are not
* stored for input and output, but netcat has different fds for stdin
* and * stdout. To support netcat, would additionally need to avoid
* S_ISSOCK(), getsockname(), and getpeername() below, reconstructing
* addresses from environment variables:
* NCAT_LOCAL_ADDR NCAT_LOCAL_PORT
* NCAT_REMOTE_ADDR NCAT_REMOTE_PORT
* NCAT_PROTO
*/
connection *con;
server_socket *srv_socket;
sock_addr cnt_addr;
socklen_t cnt_len;
struct stat st;
if (0 != fstat(fd, &st)) {
log_perror(srv->errh, __FILE__, __LINE__, "fstat()");
return 0;
}
if (!S_ISSOCK(st.st_mode)) {
/* require that fd is a socket
* (modules might expect STDIN_FILENO and STDOUT_FILENO opened to /dev/null) */
log_error(srv->errh, __FILE__, __LINE__,
"lighttpd -1 stdin is not a socket");
return 0;
}
cnt_len = sizeof(cnt_addr);
if (0 != getsockname(fd, (struct sockaddr *)&cnt_addr, &cnt_len)) {
log_perror(srv->errh, __FILE__, __LINE__, "getsockname()");
return 0;
}
srv_socket = server_oneshot_getsock(srv, &cnt_addr);
if (NULL == srv_socket) return 0;
#ifdef __clang_analyzer__
memset(&cnt_addr, 0, sizeof(cnt_addr));
#endif
cnt_len = sizeof(cnt_addr);
if (0 != getpeername(fd, (struct sockaddr *)&cnt_addr, &cnt_len)) {
log_perror(srv->errh, __FILE__, __LINE__, "getpeername()");
return 0;
}
/*(must set flags; fd did not pass through fdevent accept() logic)*/
if (-1 == fdevent_fcntl_set_nb_cloexec(fd)) {
log_perror(srv->errh, __FILE__, __LINE__, "fcntl()");
return 0;
}
if (sock_addr_get_family(&cnt_addr) != AF_UNIX) {
network_accept_tcp_nagle_disable(fd);
}
con = connection_accepted(srv, srv_socket, &cnt_addr, fd);
if (NULL == con) return 0;
connection_state_machine(con);
return 1;
}
__attribute_cold__
static void show_version (void) {
char *b = PACKAGE_DESC TEXT_SSL \
" - a light and fast webserver\n"
#ifdef NONREPRODUCIBLE_BUILD
"Build-Date: " __DATE__ " " __TIME__ "\n";
#endif
;
write_all(STDOUT_FILENO, b, strlen(b));
}
__attribute_cold__
static void show_features (void) {
static const char features[] =
"\nFeatures:\n\n"
#ifdef HAVE_IPV6
"\t+ IPv6 support\n"
#else
"\t- IPv6 support\n"
#endif
#if defined HAVE_ZLIB_H && defined HAVE_LIBZ
"\t+ zlib support\n"
#else
"\t- zlib support\n"
#endif
#if defined HAVE_BZLIB_H && defined HAVE_LIBBZ2
"\t+ bzip2 support\n"
#else
"\t- bzip2 support\n"
#endif
#if defined HAVE_BROTLI_ENCODE_H && defined HAVE_BROTLI
"\t+ brotli support\n"
#else
"\t- brotli support\n"
#endif
#if defined(HAVE_CRYPT) || defined(HAVE_CRYPT_R) || defined(HAVE_LIBCRYPT)
"\t+ crypt support\n"
#else
"\t- crypt support\n"
#endif
#ifdef USE_OPENSSL_CRYPTO
"\t+ OpenSSL support\n"
#else
"\t- OpenSSL support\n"
#endif
#ifdef USE_MBEDTLS_CRYPTO
"\t+ mbedTLS support\n"
#else
"\t- mbedTLS support\n"
#endif
#ifdef USE_NSS_CRYPTO
"\t+ NSS crypto support\n"
#else
"\t- NSS crypto support\n"
#endif
#ifdef USE_GNUTLS_CRYPTO
"\t+ GnuTLS support\n"
#else
"\t- GnuTLS support\n"
#endif
#ifdef USE_WOLFSSL_CRYPTO
"\t+ WolfSSL support\n"
#else
"\t- WolfSSL support\n"
#endif
#ifdef USE_NETTLE_CRYPTO
"\t+ Nettle support\n"
#else
"\t- Nettle support\n"
#endif
#ifdef HAVE_LIBPCRE
"\t+ PCRE support\n"
#else
"\t- PCRE support\n"
#endif
#ifdef HAVE_MYSQL
"\t+ MySQL support\n"
#else
"\t- MySQL support\n"
#endif
#ifdef HAVE_PGSQL
"\t+ PgSQL support\n"
#else
"\t- PgSQL support\n"
#endif
#ifdef HAVE_DBI
"\t+ DBI support\n"
#else
"\t- DBI support\n"
#endif
#ifdef HAVE_KRB5
"\t+ Kerberos support\n"
#else
"\t- Kerberos support\n"
#endif
#if defined(HAVE_LDAP_H) && defined(HAVE_LBER_H) && defined(HAVE_LIBLDAP) && defined(HAVE_LIBLBER)
"\t+ LDAP support\n"
#else
"\t- LDAP support\n"
#endif
#ifdef HAVE_PAM
"\t+ PAM support\n"
#else
"\t- PAM support\n"
#endif
#ifdef USE_MEMCACHED
"\t+ memcached support\n"
#else
"\t- memcached support\n"
#endif
#ifdef HAVE_FAM_H
"\t+ FAM support\n"
#else
"\t- FAM support\n"
#endif
#ifdef HAVE_LUA_H
"\t+ LUA support\n"
#else
"\t- LUA support\n"
#endif
#ifdef HAVE_LIBXML_H
"\t+ xml support\n"
#else
"\t- xml support\n"
#endif
#ifdef HAVE_SQLITE3_H
"\t+ SQLite support\n"
#else
"\t- SQLite support\n"
#endif
#ifdef HAVE_GDBM_H
"\t+ GDBM support\n"
#else
"\t- GDBM support\n"
#endif
;
show_version();
printf("%s%s%s\n", fdevent_show_event_handlers(), network_write_show_handlers(), features);
}
__attribute_cold__
static void show_help (void) {
char *b = PACKAGE_DESC TEXT_SSL
#ifdef NONREPRODUCIBLE_BUILD
" ("__DATE__ " " __TIME__ ")"
#endif
" - a light and fast webserver\n" \
"usage:\n" \
" -f <name> filename of the config-file\n" \
" -m <name> module directory (default: "LIBRARY_DIR")\n" \
" -i <secs> graceful shutdown after <secs> of inactivity\n" \
" -1 process single (one) request on stdin socket, then exit\n" \
" -p print the parsed config-file in internal form, and exit\n" \
" -t test config-file syntax, then exit\n" \
" -tt test config-file syntax, load and init modules, then exit\n" \
" -D don't go to background (default: go to background)\n" \
" -v show version\n" \
" -V show compile-time features\n" \
" -h show this help\n" \
"\n"
;
write_all(STDOUT_FILENO, b, strlen(b));
}
__attribute_cold__
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static void server_sockets_save (server *srv) { /* graceful_restart */
memcpy(&graceful_sockets, &srv->srv_sockets, sizeof(server_socket_array));
memset(&srv->srv_sockets, 0, sizeof(server_socket_array));
memcpy(&inherited_sockets, &srv->srv_sockets_inherited, sizeof(server_socket_array));
memset(&srv->srv_sockets_inherited, 0, sizeof(server_socket_array));
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
}
__attribute_cold__
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static void server_sockets_restore (server *srv) { /* graceful_restart */
memcpy(&srv->srv_sockets, &graceful_sockets, sizeof(server_socket_array));
memset(&graceful_sockets, 0, sizeof(server_socket_array));
memcpy(&srv->srv_sockets_inherited, &inherited_sockets, sizeof(server_socket_array));
memset(&inherited_sockets, 0, sizeof(server_socket_array));
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
}
__attribute_cold__
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static int server_sockets_set_nb_cloexec (server *srv) {
if (srv->sockets_disabled) return 0; /* lighttpd -1 (one-shot mode) */
for (uint32_t i = 0; i < srv->srv_sockets.used; ++i) {
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
server_socket *srv_socket = srv->srv_sockets.ptr[i];
if (-1 == fdevent_fcntl_set_nb_cloexec_sock(srv_socket->fd)) {
log_perror(srv->errh, __FILE__, __LINE__, "fcntl()");
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
return -1;
}
}
return 0;
}
__attribute_cold__
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static void server_sockets_set_event (server *srv, int event) {
for (uint32_t i = 0; i < srv->srv_sockets.used; ++i) {
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
server_socket *srv_socket = srv->srv_sockets.ptr[i];
fdevent_fdnode_event_set(srv->ev, srv_socket->fdn, event);
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
}
}
__attribute_cold__
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static void server_sockets_unregister (server *srv) {
if (2 == srv->sockets_disabled) return;
srv->sockets_disabled = 2;
for (uint32_t i = 0; i < srv->srv_sockets.used; ++i)
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
network_unregister_sock(srv, srv->srv_sockets.ptr[i]);
}
__attribute_cold__
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
static void server_sockets_close (server *srv) {
/* closing socket right away will make it possible for the next lighttpd
* to take over (old-style graceful restart), but only if backends
* (e.g. fastcgi, scgi, etc) are independent from lighttpd, rather
* than started by lighttpd via "bin-path")
*/
if (3 == srv->sockets_disabled) return;
for (uint32_t i = 0; i < srv->srv_sockets.used; ++i) {
[core] graceful restart with SIGUSR1 (fixes #2785) more consistent cleanup of resources at shutdown (e.g. upon error conditions) Notes: graceful restart with SIGUSR1 - not available if chroot()ed, oneshot mode, or if idle timeout occurs - preserve process id (pid) - preserve existing listen sockets - i.e. does not close old listen sockets from prior configs (even if old listen sockets no longer in the new config) (sockets may have been bound w/ root privileges no longer available) - will fail to add listen sockets from new config if privileges lighttpd configured to drop privileges to non-root user, and new listen socket attempts to bind to low-numbered port requiring root privileges. - will fail if listen sockets in new config conflict with any previous old listen sockets - These failure modes will result in lighttpd shutting down instead of graceful restart. These failure modes are not detectable with preflight checks (&#39;lighttpd -tt -f lighttpd.conf&#39;) because the new instance of lighttpd running the preflight check does not known config state of n prior graceful restarts, or even the config state of the currently running lighttpd server. - due to lighttpd feature of optionally managing backends (e.g. fastcgi and scgi via &#34;bin-path&#34;), lighttpd must wait for all child processes to exit prior to restarting. Restarting new workers while old workers (and old backends) were still running would result in failure of restarted lighttpd process to be able to bind to sockets already in use by old backends (e.g. unix &#34;socket&#34; path) x-ref: &#34;graceful restart with SIGUSR1&#34; https://redmine.lighttpd.net/issues/2785
5 years ago
server_socket *srv_socket = srv->srv_sockets.ptr[i];
if (-1 == srv_socket->fd) continue;
if (2 != srv->sockets_disabled) network_unregister_sock(srv,srv_socket);