realip module broken?
Igor Sysoev
is at rambler-co.ru
Wed Aug 13 20:18:35 MSD 2008
On Wed, Aug 13, 2008 at 10:23:27AM +0200, Spil Games wrote:
> Igor Sysoev wrote:
> > I will look how to resolve the issue. Right now you may disable
> > keepalive on nginx side.
>
> I'll keep it at 0.0.0.0/0 for now. The 'set_real_ip_from' directive
> doesn't add much security anyway:
>
> a) The loadbalancer overwrites any existing X-Real-IP headers.
>
> b) Even if a) would not be done, the header would be accepted because
> all requests come from the loadbalancer IP.
>
> It would be nice if the realip module could be fixed though. It's a
> matter of semantics, but I believe an X-Real-IP (or X-Forwarded-For)
> header should only influence the request, not the entire connection.
The attached patch should fix the issue.
--
Igor Sysoev
http://sysoev.ru/en/
-------------- next part --------------
Index: src/http/ngx_http_request.h
===================================================================
--- src/http/ngx_http_request.h (revision 1494)
+++ src/http/ngx_http_request.h (working copy)
@@ -436,17 +436,7 @@
unsigned bypass_cache:1;
unsigned no_cache:1;
-#if (NGX_HTTP_REALIP)
-
/*
- * instead of using the request context data in ngx_http_realip_module
- * we use the single bit in the request structure
- */
- unsigned realip_set:1;
-
-#endif
-
- /*
* instead of using the request context data in ngx_http_limit_zone_module
* we use the single bit in the request structure
*/
Index: src/http/modules/ngx_http_realip_module.c
===================================================================
--- src/http/modules/ngx_http_realip_module.c (revision 1494)
+++ src/http/modules/ngx_http_realip_module.c (working copy)
@@ -12,19 +12,26 @@
/* AF_INET only */
typedef struct {
- in_addr_t mask;
- in_addr_t addr;
+ in_addr_t mask;
+ in_addr_t addr;
} ngx_http_realip_from_t;
typedef struct {
- ngx_array_t *from; /* array of ngx_http_realip_from_t */
-
- ngx_uint_t xfwd;
+ ngx_array_t *from; /* array of ngx_http_realip_from_t */
+ ngx_uint_t xfwd;
} ngx_http_realip_loc_conf_t;
+typedef struct {
+ ngx_connection_t *connection;
+ in_addr_t addr;
+ ngx_str_t addr_text;
+} ngx_http_realip_ctx_t;
+
+
static ngx_int_t ngx_http_realip_handler(ngx_http_request_t *r);
+static void ngx_http_realip_cleanup(void *data);
static char *ngx_http_realip_from(ngx_conf_t *cf, ngx_command_t *cmd,
void *conf);
static void *ngx_http_realip_create_loc_conf(ngx_conf_t *cf);
@@ -100,13 +107,23 @@
in_addr_t addr;
ngx_uint_t i;
struct sockaddr_in *sin;
+ ngx_connection_t *c;
+ ngx_pool_cleanup_t *cln;
+ ngx_http_realip_ctx_t *ctx;
ngx_http_realip_from_t *from;
ngx_http_realip_loc_conf_t *rlcf;
- if (r->realip_set) {
+ ctx = ngx_http_get_module_ctx(r, ngx_http_realip_module);
+
+ if (ctx) {
return NGX_DECLINED;
}
+ cln = ngx_pool_cleanup_add(r->pool, sizeof(ngx_http_realip_ctx_t));
+ if (cln == NULL) {
+ return NGX_HTTP_INTERNAL_SERVER_ERROR;
+ }
+
rlcf = ngx_http_get_module_loc_conf(r, ngx_http_realip_module);
if (rlcf->from == NULL) {
@@ -139,41 +156,50 @@
}
}
- ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
- "realip: \"%s\"", ip);
+ c = r->connection;
+ ngx_log_debug1(NGX_LOG_DEBUG_HTTP, c->log, 0, "realip: \"%s\"", ip);
+
/* AF_INET only */
- sin = (struct sockaddr_in *) r->connection->sockaddr;
+ sin = (struct sockaddr_in *) c->sockaddr;
from = rlcf->from->elts;
for (i = 0; i < rlcf->from->nelts; i++) {
- ngx_log_debug3(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
+ ngx_log_debug3(NGX_LOG_DEBUG_HTTP, c->log, 0,
"realip: %08XD %08XD %08XD",
sin->sin_addr.s_addr, from[i].mask, from[i].addr);
if ((sin->sin_addr.s_addr & from[i].mask) == from[i].addr) {
- r->realip_set = 1;
+ ctx = cln->data;
+ ngx_http_set_ctx(r, ctx, ngx_http_realip_module);
+
addr = inet_addr((char *) ip);
if (addr == INADDR_NONE) {
return NGX_DECLINED;
}
- p = ngx_pnalloc(r->connection->pool, len);
+ p = ngx_pnalloc(c->pool, len);
if (p == NULL) {
return NGX_HTTP_INTERNAL_SERVER_ERROR;
}
ngx_memcpy(p, ip, len);
+ cln->handler = ngx_http_realip_cleanup;
+
+ ctx->connection = c;
+ ctx->addr = sin->sin_addr.s_addr;
+ ctx->addr_text = c->addr_text;
+
sin->sin_addr.s_addr = addr;
- r->connection->addr_text.len = len;
- r->connection->addr_text.data = p;
+ c->addr_text.len = len;
+ c->addr_text.data = p;
return NGX_DECLINED;
}
@@ -183,6 +209,23 @@
}
+static void
+ngx_http_realip_cleanup(void *data)
+{
+ ngx_http_realip_ctx_t *ctx = data;
+
+ ngx_connection_t *c;
+ struct sockaddr_in *sin;
+
+ c = ctx->connection;
+
+ sin = (struct sockaddr_in *) c->sockaddr;
+ sin->sin_addr.s_addr = ctx->addr;
+
+ c->addr_text = ctx->addr_text;
+}
+
+
static char *
ngx_http_realip_from(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
{
More information about the nginx
mailing list