[nginx] Stream: got rid of pseudo variables.
Vladimir Homutov
vl at nginx.com
Mon Jul 4 14:50:23 UTC 2016
details: http://hg.nginx.org/nginx/rev/d5b5866c06c4
branches:
changeset: 6610:d5b5866c06c4
user: Vladimir Homutov <vl at nginx.com>
date: Wed Jun 29 12:46:12 2016 +0300
description:
Stream: got rid of pseudo variables.
Stream limit_conn, upstream_hash and proxy modules now use complex values.
diffstat:
src/stream/ngx_stream_limit_conn_module.c | 121 ++++++++++++++------------
src/stream/ngx_stream_proxy_module.c | 76 ++++++++++------
src/stream/ngx_stream_upstream_hash_module.c | 23 +++-
3 files changed, 126 insertions(+), 94 deletions(-)
diffs (381 lines):
diff -r 73543af69f14 -r d5b5866c06c4 src/stream/ngx_stream_limit_conn_module.c
--- a/src/stream/ngx_stream_limit_conn_module.c Wed Jun 29 12:46:12 2016 +0300
+++ b/src/stream/ngx_stream_limit_conn_module.c Wed Jun 29 12:46:12 2016 +0300
@@ -11,33 +11,34 @@
typedef struct {
- u_char color;
- u_char len;
- u_short conn;
- u_char data[1];
+ u_char color;
+ u_char len;
+ u_short conn;
+ u_char data[1];
} ngx_stream_limit_conn_node_t;
typedef struct {
- ngx_shm_zone_t *shm_zone;
- ngx_rbtree_node_t *node;
+ ngx_shm_zone_t *shm_zone;
+ ngx_rbtree_node_t *node;
} ngx_stream_limit_conn_cleanup_t;
typedef struct {
- ngx_rbtree_t *rbtree;
+ ngx_rbtree_t *rbtree;
+ ngx_stream_complex_value_t key;
} ngx_stream_limit_conn_ctx_t;
typedef struct {
- ngx_shm_zone_t *shm_zone;
- ngx_uint_t conn;
+ ngx_shm_zone_t *shm_zone;
+ ngx_uint_t conn;
} ngx_stream_limit_conn_limit_t;
typedef struct {
- ngx_array_t limits;
- ngx_uint_t log_level;
+ ngx_array_t limits;
+ ngx_uint_t log_level;
} ngx_stream_limit_conn_conf_t;
@@ -130,48 +131,36 @@ ngx_stream_limit_conn_handler(ngx_stream
ngx_slab_pool_t *shpool;
ngx_rbtree_node_t *node;
ngx_pool_cleanup_t *cln;
- struct sockaddr_in *sin;
-#if (NGX_HAVE_INET6)
- struct sockaddr_in6 *sin6;
-#endif
ngx_stream_limit_conn_ctx_t *ctx;
ngx_stream_limit_conn_node_t *lc;
ngx_stream_limit_conn_conf_t *lccf;
ngx_stream_limit_conn_limit_t *limits;
ngx_stream_limit_conn_cleanup_t *lccln;
- switch (s->connection->sockaddr->sa_family) {
-
- case AF_INET:
- sin = (struct sockaddr_in *) s->connection->sockaddr;
-
- key.len = sizeof(in_addr_t);
- key.data = (u_char *) &sin->sin_addr;
-
- break;
-
-#if (NGX_HAVE_INET6)
- case AF_INET6:
- sin6 = (struct sockaddr_in6 *) s->connection->sockaddr;
-
- key.len = sizeof(struct in6_addr);
- key.data = sin6->sin6_addr.s6_addr;
-
- break;
-#endif
-
- default:
- return NGX_DECLINED;
- }
-
- hash = ngx_crc32_short(key.data, key.len);
-
lccf = ngx_stream_get_module_srv_conf(s, ngx_stream_limit_conn_module);
limits = lccf->limits.elts;
for (i = 0; i < lccf->limits.nelts; i++) {
ctx = limits[i].shm_zone->data;
+ if (ngx_stream_complex_value(s, &ctx->key, &key) != NGX_OK) {
+ return NGX_ERROR;
+ }
+
+ if (key.len == 0) {
+ continue;
+ }
+
+ if (key.len > 255) {
+ ngx_log_error(NGX_LOG_ERR, s->connection->log, 0,
+ "the value of the \"%V\" key "
+ "is more than 255 bytes: \"%V\"",
+ &ctx->key.value, &key);
+ continue;
+ }
+
+ hash = ngx_crc32_short(key.data, key.len);
+
shpool = (ngx_slab_pool_t *) limits[i].shm_zone->shm.addr;
ngx_shmtx_lock(&shpool->mutex);
@@ -383,6 +372,19 @@ ngx_stream_limit_conn_init_zone(ngx_shm_
ctx = shm_zone->data;
if (octx) {
+ if (ctx->key.value.len != octx->key.value.len
+ || ngx_strncmp(ctx->key.value.data, octx->key.value.data,
+ ctx->key.value.len)
+ != 0)
+ {
+ ngx_log_error(NGX_LOG_EMERG, shm_zone->shm.log, 0,
+ "limit_conn_zone \"%V\" uses the \"%V\" key "
+ "while previously it used the \"%V\" key",
+ &shm_zone->shm.name, &ctx->key.value,
+ &octx->key.value);
+ return NGX_ERROR;
+ }
+
ctx->rbtree = octx->rbtree;
return NGX_OK;
@@ -466,12 +468,13 @@ ngx_stream_limit_conn_merge_conf(ngx_con
static char *
ngx_stream_limit_conn_zone(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
{
- u_char *p;
- ssize_t size;
- ngx_str_t *value, name, s;
- ngx_uint_t i;
- ngx_shm_zone_t *shm_zone;
- ngx_stream_limit_conn_ctx_t *ctx;
+ u_char *p;
+ ssize_t size;
+ ngx_str_t *value, name, s;
+ ngx_uint_t i;
+ ngx_shm_zone_t *shm_zone;
+ ngx_stream_limit_conn_ctx_t *ctx;
+ ngx_stream_compile_complex_value_t ccv;
value = cf->args->elts;
@@ -480,6 +483,16 @@ ngx_stream_limit_conn_zone(ngx_conf_t *c
return NGX_CONF_ERROR;
}
+ ngx_memzero(&ccv, sizeof(ngx_stream_compile_complex_value_t));
+
+ ccv.cf = cf;
+ ccv.value = &value[1];
+ ccv.complex_value = &ctx->key;
+
+ if (ngx_stream_compile_complex_value(&ccv) != NGX_OK) {
+ return NGX_CONF_ERROR;
+ }
+
size = 0;
name.len = 0;
@@ -538,17 +551,11 @@ ngx_stream_limit_conn_zone(ngx_conf_t *c
}
if (shm_zone->data) {
+ ctx = shm_zone->data;
+
ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
- "%V \"%V\" is already bound to key "
- "\"$binary_remote_addr\"",
- &cmd->name, &name);
- return NGX_CONF_ERROR;
- }
-
- if (ngx_strcmp(value[1].data, "$binary_remote_addr") != 0) {
- ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
- "unsupported key \"%V\", use "
- "$binary_remote_addr", &value[1]);
+ "%V \"%V\" is already bound to key \"%V\"",
+ &cmd->name, &name, &ctx->key.value);
return NGX_CONF_ERROR;
}
diff -r 73543af69f14 -r d5b5866c06c4 src/stream/ngx_stream_proxy_module.c
--- a/src/stream/ngx_stream_proxy_module.c Wed Jun 29 12:46:12 2016 +0300
+++ b/src/stream/ngx_stream_proxy_module.c Wed Jun 29 12:46:12 2016 +0300
@@ -12,10 +12,10 @@
typedef struct {
ngx_addr_t *addr;
+ ngx_stream_complex_value_t *value;
#if (NGX_HAVE_TRANSPARENT_PROXY)
- unsigned transparent:1;
+ ngx_uint_t transparent; /* unsigned transparent:1; */
#endif
- unsigned no_port:1;
} ngx_stream_upstream_local_t;
@@ -448,8 +448,9 @@ static ngx_int_t
ngx_stream_proxy_set_local(ngx_stream_session_t *s, ngx_stream_upstream_t *u,
ngx_stream_upstream_local_t *local)
{
- ngx_addr_t *addr;
- ngx_connection_t *c;
+ ngx_int_t rc;
+ ngx_str_t val;
+ ngx_addr_t *addr;
if (local == NULL) {
u->peer.local = NULL;
@@ -460,36 +461,36 @@ ngx_stream_proxy_set_local(ngx_stream_se
u->peer.transparent = local->transparent;
#endif
- if (local->addr) {
+ if (local->value == NULL) {
u->peer.local = local->addr;
return NGX_OK;
}
- /* $remote_addr, $remote_addr:$remote_port, [$remote_addr]:$remote_port */
+ if (ngx_stream_complex_value(s, local->value, &val) != NGX_OK) {
+ return NGX_ERROR;
+ }
- c = s->connection;
+ if (val.len == 0) {
+ return NGX_OK;
+ }
- addr = ngx_palloc(c->pool, sizeof(ngx_addr_t));
+ addr = ngx_palloc(s->connection->pool, sizeof(ngx_addr_t));
if (addr == NULL) {
return NGX_ERROR;
}
- addr->socklen = c->socklen;
-
- if (local->no_port) {
- addr->sockaddr = ngx_palloc(c->pool, addr->socklen);
- if (addr->sockaddr == NULL) {
- return NGX_ERROR;
- }
-
- ngx_memcpy(addr->sockaddr, c->sockaddr, c->socklen);
- ngx_inet_set_port(addr->sockaddr, 0);
-
- } else {
- addr->sockaddr = c->sockaddr;
+ rc = ngx_parse_addr_port(s->connection->pool, addr, val.data, val.len);
+ if (rc == NGX_ERROR) {
+ return NGX_ERROR;
}
- addr->name = c->addr_text;
+ if (rc != NGX_OK) {
+ ngx_log_error(NGX_LOG_ERR, s->connection->log, 0,
+ "invalid local address \"%V\"", &val);
+ return NGX_OK;
+ }
+
+ addr->name = val;
u->peer.local = addr;
return NGX_OK;
@@ -1699,9 +1700,11 @@ ngx_stream_proxy_bind(ngx_conf_t *cf, ng
{
ngx_stream_proxy_srv_conf_t *pscf = conf;
- ngx_int_t rc;
- ngx_str_t *value;
- ngx_stream_upstream_local_t *local;
+ ngx_int_t rc;
+ ngx_str_t *value;
+ ngx_stream_complex_value_t cv;
+ ngx_stream_upstream_local_t *local;
+ ngx_stream_compile_complex_value_t ccv;
if (pscf->local != NGX_CONF_UNSET_PTR) {
return "is duplicate";
@@ -1714,6 +1717,16 @@ ngx_stream_proxy_bind(ngx_conf_t *cf, ng
return NGX_CONF_OK;
}
+ ngx_memzero(&ccv, sizeof(ngx_stream_compile_complex_value_t));
+
+ ccv.cf = cf;
+ ccv.value = &value[1];
+ ccv.complex_value = &cv;
+
+ if (ngx_stream_compile_complex_value(&ccv) != NGX_OK) {
+ return NGX_CONF_ERROR;
+ }
+
local = ngx_pcalloc(cf->pool, sizeof(ngx_stream_upstream_local_t));
if (local == NULL) {
return NGX_CONF_ERROR;
@@ -1721,12 +1734,15 @@ ngx_stream_proxy_bind(ngx_conf_t *cf, ng
pscf->local = local;
- if (ngx_strcmp(value[1].data, "$remote_addr") == 0) {
- local->no_port = 1;
+ if (cv.lengths) {
+ local->value = ngx_palloc(cf->pool, sizeof(ngx_stream_complex_value_t));
+ if (local->value == NULL) {
+ return NGX_CONF_ERROR;
+ }
- } else if (ngx_strcmp(value[1].data, "$remote_addr:$remote_port") != 0
- && ngx_strcmp(value[1].data, "[$remote_addr]:$remote_port") != 0)
- {
+ *local->value = cv;
+
+ } else {
local->addr = ngx_palloc(cf->pool, sizeof(ngx_addr_t));
if (local->addr == NULL) {
return NGX_CONF_ERROR;
diff -r 73543af69f14 -r d5b5866c06c4 src/stream/ngx_stream_upstream_hash_module.c
--- a/src/stream/ngx_stream_upstream_hash_module.c Wed Jun 29 12:46:12 2016 +0300
+++ b/src/stream/ngx_stream_upstream_hash_module.c Wed Jun 29 12:46:12 2016 +0300
@@ -23,6 +23,7 @@ typedef struct {
typedef struct {
+ ngx_stream_complex_value_t key;
ngx_stream_upstream_chash_points_t *points;
} ngx_stream_upstream_hash_srv_conf_t;
@@ -141,7 +142,9 @@ ngx_stream_upstream_init_hash_peer(ngx_s
hcf = ngx_stream_conf_upstream_srv_conf(us,
ngx_stream_upstream_hash_module);
- hp->key = s->connection->addr_text;
+ if (ngx_stream_complex_value(s, &hcf->key, &hp->key) != NGX_OK) {
+ return NGX_ERROR;
+ }
ngx_log_debug1(NGX_LOG_DEBUG_STREAM, s->connection->log, 0,
"upstream hash key:\"%V\"", &hp->key);
@@ -616,15 +619,21 @@ ngx_stream_upstream_hash_create_conf(ngx
static char *
ngx_stream_upstream_hash(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
{
- ngx_str_t *value;
- ngx_stream_upstream_srv_conf_t *uscf;
+ ngx_stream_upstream_hash_srv_conf_t *hcf = conf;
+
+ ngx_str_t *value;
+ ngx_stream_upstream_srv_conf_t *uscf;
+ ngx_stream_compile_complex_value_t ccv;
value = cf->args->elts;
- if (ngx_strcmp(value[1].data, "$remote_addr")) {
- ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
- "unsupported hash key \"%V\", use $remote_addr",
- &value[1]);
+ ngx_memzero(&ccv, sizeof(ngx_stream_compile_complex_value_t));
+
+ ccv.cf = cf;
+ ccv.value = &value[1];
+ ccv.complex_value = &hcf->key;
+
+ if (ngx_stream_compile_complex_value(&ccv) != NGX_OK) {
return NGX_CONF_ERROR;
}
More information about the nginx-devel
mailing list