From 3ecdd2c69c4864526c63b8e55df22ad1a86f3c72 Mon Sep 17 00:00:00 2001 From: Andrew Clayton Date: Fri, 18 Nov 2022 23:42:44 +0000 Subject: Isolation: Rename NXT_HAVE_CLONE -> NXT_HAVE_LINUX_NS. Due to the need to replace our use of clone/__NR_clone on Linux with fork(2)/unshare(2) for enabling Linux namespaces(7) to keep the pthreads(7) API working. Let's rename NXT_HAVE_CLONE to NXT_HAVE_LINUX_NS, i.e name it after the feature, not how it's implemented, then in future if we change how we do namespaces again we don't have to rename this. Reviewed-by: Alejandro Colomar Signed-off-by: Andrew Clayton --- src/nxt_main_process.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/nxt_main_process.c') diff --git a/src/nxt_main_process.c b/src/nxt_main_process.c index de41e8d7..4c89121e 100644 --- a/src/nxt_main_process.c +++ b/src/nxt_main_process.c @@ -556,7 +556,7 @@ nxt_main_process_created_handler(nxt_task_t *task, nxt_port_recv_msg_t *msg) nxt_assert(process != NULL); nxt_assert(process->state == NXT_PROCESS_STATE_CREATING); -#if (NXT_HAVE_CLONE && NXT_HAVE_CLONE_NEWUSER) +#if (NXT_HAVE_LINUX_NS && NXT_HAVE_CLONE_NEWUSER) if (nxt_is_clone_flag_set(process->isolation.clone.flags, NEWUSER)) { if (nxt_slow_path(nxt_clone_credential_map(task, process->pid, process->user_cred, -- cgit From ccaad38bc529897218a1e41c7e8704566695d1a9 Mon Sep 17 00:00:00 2001 From: Andrew Clayton Date: Sat, 25 Feb 2023 23:37:00 +0000 Subject: Socket: Remove Unix domain listen sockets at shutdown. If we don't remove the Unix domain listen socket file then when Unit restarts it get an error like 2023/02/25 23:10:11 [alert] 36388#36388 bind(\"unix:/tmp/unit.sock\") failed (98: Address already in use) This patch makes use of the listen_sockets array, that is already allocated in the main process but never populated, to place the Unix domain listen sockets into. At shutdown we can then loop through this array and unlink(2) any Unix domain sockets found therein. Closes: Reviewed-by: Alejandro Colomar Signed-off-by: Andrew Clayton --- src/nxt_main_process.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'src/nxt_main_process.c') diff --git a/src/nxt_main_process.c b/src/nxt_main_process.c index 4c89121e..7548be9a 100644 --- a/src/nxt_main_process.c +++ b/src/nxt_main_process.c @@ -1182,8 +1182,9 @@ nxt_main_listening_socket(nxt_sockaddr_t *sa, nxt_listening_socket_t *ls) if (sa->u.sockaddr.sa_family == AF_UNIX && sa->u.sockaddr_un.sun_path[0] != '\0') { - char *filename; - mode_t access; + char *filename; + mode_t access; + nxt_thread_t *thr; filename = sa->u.sockaddr_un.sun_path; access = (S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH); @@ -1194,6 +1195,9 @@ nxt_main_listening_socket(nxt_sockaddr_t *sa, nxt_listening_socket_t *ls) filename, nxt_errno); goto fail; } + + thr = nxt_thread(); + nxt_runtime_listen_socket_add(thr->runtime, sa); } #endif -- cgit From 2e3e1c7e7bd5ee177b2703fa3d261fe51164426f Mon Sep 17 00:00:00 2001 From: Andrew Clayton Date: Tue, 28 Feb 2023 01:59:04 +0000 Subject: Socket: Remove Unix domain listen sockets upon reconfigure. Currently when using Unix domain sockets for requests, if unit is reconfigured then it will fail if it tries to bind(2) again to a Unix domain socket with something like 2023/02/25 19:15:50 [alert] 35274#35274 bind(\"unix:/tmp/unit.sock\") failed (98: Address already in use) When closing such a socket we really need to unlink(2) it. However that presents a problem in that when running as root, while the main process runs as root and creates the socket, it's the router process, that runs as an unprivileged user, e.g nobody, that closes the socket and would thus remove it, but couldn't due to not having permission, even if the socket is mode 0666, you need write permissions on the containing directory to remove a file. There are several options to solve this, all with varying degrees of complexity and utility. 1) Give the user who the router process runs as write permission to the directory containing the listen sockets. These can then be unlink(2)'d from the router process. Simple and would work, but perhaps not the most elegant. 2) Using capabilities(7). The router process could temporarily attain the CAP_DAC_OVERRIDE capability, unlink(7) the socket, then relinquish the capability until required again. These are Linux specific (other systems may have similar mechanisms which would be extra work to support). There is also a, albeit small, window where the router process is running with elevated privileges. 3) Have the main process do the unlink(2), it is after all the process that created the socket. This is what this commit implements. We create a new port IPC message type of NXT_PORT_MSG_SOCKET_UNLINK, that is used by the router process to notify the main process about a Unix domain socket to unlink(2). Upon doing a reconfigure the router process will call nxt_router_listen_socket_release() which will close the socket, we extend this function in the case of non-abstract Unix domain sockets, so that it will send a message to the main process containing a copy of the nxt_sockaddr_t structure that will contain the filename of the socket. In the main process the handler that we have defined, nxt_main_port_socket_unlink_handler(), for this message type will run and allow us to look for the socket in question in the listen_sockets array and remove it and unlink(2) the socket. This then allows the reconfigure to work if it tries to bind(2) again to a socket that previously existed. Link: Link: Reviewed-by: Alejandro Colomar Signed-off-by: Andrew Clayton --- src/nxt_main_process.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 46 insertions(+) (limited to 'src/nxt_main_process.c') diff --git a/src/nxt_main_process.c b/src/nxt_main_process.c index 7548be9a..db1cfcb9 100644 --- a/src/nxt_main_process.c +++ b/src/nxt_main_process.c @@ -48,6 +48,8 @@ static void nxt_main_process_signal_handler(nxt_task_t *task, void *obj, static void nxt_main_process_cleanup(nxt_task_t *task, nxt_process_t *process); static void nxt_main_port_socket_handler(nxt_task_t *task, nxt_port_recv_msg_t *msg); +static void nxt_main_port_socket_unlink_handler(nxt_task_t *task, + nxt_port_recv_msg_t *msg); static nxt_int_t nxt_main_listening_socket(nxt_sockaddr_t *sa, nxt_listening_socket_t *ls); static void nxt_main_port_modules_handler(nxt_task_t *task, @@ -587,6 +589,7 @@ static nxt_port_handlers_t nxt_main_process_port_handlers = { .remove_pid = nxt_port_remove_pid_handler, .start_process = nxt_main_start_process_handler, .socket = nxt_main_port_socket_handler, + .socket_unlink = nxt_main_port_socket_unlink_handler, .modules = nxt_main_port_modules_handler, .conf_store = nxt_main_port_conf_store_handler, #if (NXT_TLS) @@ -1214,6 +1217,49 @@ fail: } +static void +nxt_main_port_socket_unlink_handler(nxt_task_t *task, nxt_port_recv_msg_t *msg) +{ +#if (NXT_HAVE_UNIX_DOMAIN) + size_t i; + nxt_buf_t *b; + const char *filename; + nxt_runtime_t *rt; + nxt_sockaddr_t *sa; + nxt_listen_socket_t *ls; + + b = msg->buf; + sa = (nxt_sockaddr_t *) b->mem.pos; + + filename = sa->u.sockaddr_un.sun_path; + unlink(filename); + + rt = task->thread->runtime; + + for (i = 0; i < rt->listen_sockets->nelts; i++) { + const char *name; + + ls = (nxt_listen_socket_t *) rt->listen_sockets->elts + i; + sa = ls->sockaddr; + + if (sa->u.sockaddr.sa_family != AF_UNIX + || sa->u.sockaddr_un.sun_path[0] == '\0') + { + continue; + } + + name = sa->u.sockaddr_un.sun_path; + if (strcmp(name, filename) != 0) { + continue; + } + + nxt_array_remove(rt->listen_sockets, ls); + break; + } +#endif +} + + static nxt_conf_map_t nxt_app_lang_module_map[] = { { nxt_string("type"), -- cgit From 45c45eaeb4443ff4af9cc49e716bbd9d65596b02 Mon Sep 17 00:00:00 2001 From: Andrew Clayton Date: Thu, 30 Mar 2023 05:53:13 +0100 Subject: Add per-application logging. Currently when running in the foreground, unit application processes will send stdout to the current TTY and stderr to the unit log file. That behaviour won't change. When running as a daemon, unit application processes will send stdout to /dev/null and stderr to the unit log file. This commit allows to alter the latter case of unit running as a daemon, by allowing applications to redirect stdout and/or stderr to specific log files. This is done via two new application options, 'stdout' & 'stderr', e.g "applications": { "myapp": { ... "stdout": "/path/to/log/unit/app/stdout.log", "stderr": "/path/to/log/unit/app/stderr.log" } } These log files are created by the application processes themselves and thus the log directories need to be writable by the user (and or group) of the application processes. E.g $ sudo mkdir -p /path/to/log/unit/app $ sudo chown APP_USER /path/to/log/unit/app These need to be setup before starting unit with the above config. Currently these log files do not participate in log-file rotation (SIGUSR1), that may change in a future commit. In the meantime these logs can be rotated using the traditional copy/truncate method. NOTE: You may or may not see stuff printed to stdout as stdout was traditionally used by CGI applications to communicate with the webserver. Closes: Closes: Reviewed-by: Alejandro Colomar Signed-off-by: Andrew Clayton --- src/nxt_main_process.c | 12 ++++++++++++ 1 file changed, 12 insertions(+) (limited to 'src/nxt_main_process.c') diff --git a/src/nxt_main_process.c b/src/nxt_main_process.c index db1cfcb9..ae62aff4 100644 --- a/src/nxt_main_process.c +++ b/src/nxt_main_process.c @@ -120,6 +120,18 @@ static nxt_conf_map_t nxt_common_app_conf[] = { offsetof(nxt_common_app_conf_t, group), }, + { + nxt_string("stdout"), + NXT_CONF_MAP_CSTRZ, + offsetof(nxt_common_app_conf_t, stdout_log), + }, + + { + nxt_string("stderr"), + NXT_CONF_MAP_CSTRZ, + offsetof(nxt_common_app_conf_t, stderr_log), + }, + { nxt_string("working_directory"), NXT_CONF_MAP_CSTRZ, -- cgit From a3c3a29493798873ad04922bb2a7180b2ce267d5 Mon Sep 17 00:00:00 2001 From: Zhidao HONG Date: Mon, 8 May 2023 16:00:25 +0800 Subject: NJS: supported loadable modules. --- src/nxt_main_process.c | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'src/nxt_main_process.c') diff --git a/src/nxt_main_process.c b/src/nxt_main_process.c index ae62aff4..7cba08d4 100644 --- a/src/nxt_main_process.c +++ b/src/nxt_main_process.c @@ -14,6 +14,9 @@ #if (NXT_TLS) #include #endif +#if (NXT_HAVE_NJS) +#include +#endif #include @@ -607,6 +610,10 @@ static nxt_port_handlers_t nxt_main_process_port_handlers = { #if (NXT_TLS) .cert_get = nxt_cert_store_get_handler, .cert_delete = nxt_cert_store_delete_handler, +#endif +#if (NXT_HAVE_NJS) + .script_get = nxt_script_store_get_handler, + .script_delete = nxt_script_store_delete_handler, #endif .access_log = nxt_main_port_access_log_handler, .rpc_ready = nxt_port_rpc_handler, -- cgit