aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMaxim Dounin <mdounin@mdounin.ru>2023-07-19 05:09:23 +0300
committerMaxim Dounin <mdounin@mdounin.ru>2023-07-19 05:09:23 +0300
commit9e1a000f2bb5d32d0fa8ff804ce8a0f7539694d7 (patch)
treea4842e77f90d1ee77f779f3fc127dbb1431e1382 /src
parent4d3a9cc11fb883a7fa8b4f1859047acc121741d3 (diff)
downloadnginx-9e1a000f2bb5d32d0fa8ff804ce8a0f7539694d7.tar.gz
nginx-9e1a000f2bb5d32d0fa8ff804ce8a0f7539694d7.zip
Core: fixed environment variables on exit.
Similarly to 6822:c045b4926b2c, environment variables introduced with the "env" directive (and "NGINX_BPF_MAPS" added by QUIC) are now allocated via ngx_alloc(), and explicitly freed by a cleanup handler if no longer used. In collaboration with Sergey Kandaurov.
Diffstat (limited to 'src')
-rw-r--r--src/core/nginx.c53
1 files changed, 51 insertions, 2 deletions
diff --git a/src/core/nginx.c b/src/core/nginx.c
index 062ab0898..0deb27b7f 100644
--- a/src/core/nginx.c
+++ b/src/core/nginx.c
@@ -13,6 +13,7 @@
static void ngx_show_version_info(void);
static ngx_int_t ngx_add_inherited_sockets(ngx_cycle_t *cycle);
static void ngx_cleanup_environment(void *data);
+static void ngx_cleanup_environment_variable(void *data);
static ngx_int_t ngx_get_options(int argc, char *const *argv);
static ngx_int_t ngx_process_options(ngx_cycle_t *cycle);
static ngx_int_t ngx_save_argv(ngx_cycle_t *cycle, int argc, char *const *argv);
@@ -518,7 +519,8 @@ ngx_add_inherited_sockets(ngx_cycle_t *cycle)
char **
ngx_set_environment(ngx_cycle_t *cycle, ngx_uint_t *last)
{
- char **p, **env;
+ char **p, **env, *str;
+ size_t len;
ngx_str_t *var;
ngx_uint_t i, n;
ngx_core_conf_t *ccf;
@@ -600,7 +602,31 @@ tz_found:
for (i = 0; i < ccf->env.nelts; i++) {
if (var[i].data[var[i].len] == '=') {
- env[n++] = (char *) var[i].data;
+
+ if (last) {
+ env[n++] = (char *) var[i].data;
+ continue;
+ }
+
+ cln = ngx_pool_cleanup_add(cycle->pool, 0);
+ if (cln == NULL) {
+ return NULL;
+ }
+
+ len = ngx_strlen(var[i].data) + 1;
+
+ str = ngx_alloc(len, cycle->log);
+ if (str == NULL) {
+ return NULL;
+ }
+
+ ngx_memcpy(str, var[i].data, len);
+
+ cln->handler = ngx_cleanup_environment_variable;
+ cln->data = str;
+
+ env[n++] = str;
+
continue;
}
@@ -645,6 +671,29 @@ ngx_cleanup_environment(void *data)
}
+static void
+ngx_cleanup_environment_variable(void *data)
+{
+ char *var = data;
+
+ char **p;
+
+ for (p = environ; *p; p++) {
+
+ /*
+ * if an environment variable is still used, as it happens on exit,
+ * the only option is to leak it
+ */
+
+ if (*p == var) {
+ return;
+ }
+ }
+
+ ngx_free(var);
+}
+
+
ngx_pid_t
ngx_exec_new_binary(ngx_cycle_t *cycle, char *const *argv)
{