Skip to content

Commit 8e58f7f

Browse files
committed
better implementation of protection against X-Accel-Redirect headers
1 parent 2e0db57 commit 8e58f7f

File tree

3 files changed

+43
-32
lines changed

3 files changed

+43
-32
lines changed

src/ngx_http_combined_upstreams_module.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ typedef struct {
2929

3030
typedef struct {
3131
ngx_array_t dyn_upstrands;
32+
ngx_uint_t upstrand_gw_modules_checked;
3233
} ngx_http_combined_upstreams_loc_conf_t;
3334

3435

src/ngx_http_combined_upstreams_upstrand.c

Lines changed: 40 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -38,25 +38,6 @@ typedef struct {
3838
typedef void (*upstream_finalize_request_pt)(ngx_http_request_t *, ngx_int_t);
3939

4040

41-
static const ngx_str_t upstream_vars[] =
42-
{
43-
ngx_string("upstream_addr"),
44-
ngx_string("upstream_cache_status"),
45-
ngx_string("upstream_connect_time"),
46-
ngx_string("upstream_header_time"),
47-
ngx_string("upstream_response_length"),
48-
ngx_string("upstream_response_time"),
49-
ngx_string("upstream_status")
50-
};
51-
52-
53-
typedef struct {
54-
ngx_http_request_t *r;
55-
ngx_str_t upstream;
56-
ngx_str_t data[UPSTREAM_VARS_SIZE];
57-
} ngx_http_upstrand_status_data_t;
58-
59-
6041
typedef struct {
6142
upstream_finalize_request_pt upstream_finalize_request;
6243
ngx_uint_t last:1;
@@ -93,11 +74,30 @@ typedef struct {
9374

9475

9576
typedef struct {
96-
ngx_str_t key;
97-
ngx_int_t index;
77+
ngx_str_t key;
78+
ngx_int_t index;
9879
} ngx_http_upstrand_var_handle_t;
9980

10081

82+
static const ngx_str_t upstream_vars[] =
83+
{
84+
ngx_string("upstream_addr"),
85+
ngx_string("upstream_cache_status"),
86+
ngx_string("upstream_connect_time"),
87+
ngx_string("upstream_header_time"),
88+
ngx_string("upstream_response_length"),
89+
ngx_string("upstream_response_time"),
90+
ngx_string("upstream_status")
91+
};
92+
93+
94+
typedef struct {
95+
ngx_http_request_t *r;
96+
ngx_str_t upstream;
97+
ngx_str_t data[UPSTREAM_VARS_SIZE];
98+
} ngx_http_upstrand_status_data_t;
99+
100+
101101
static ngx_int_t ngx_http_upstrand_intercept_statuses(ngx_http_request_t *r,
102102
ngx_array_t *statuses, ngx_int_t status, ngx_str_t *uri);
103103
static ngx_int_t ngx_http_upstrand_response_header_filter(
@@ -131,8 +131,10 @@ extern ngx_module_t ngx_http_uwsgi_module;
131131
extern ngx_module_t ngx_http_fastcgi_module;
132132
extern ngx_module_t ngx_http_scgi_module;
133133

134+
#if (NGX_HTTP_V2)
134135
extern ngx_module_t ngx_http_grpc_module;
135136
#endif
137+
#endif
136138

137139
static ngx_uint_t ngx_http_upstrand_gw_modules[5];
138140

@@ -149,7 +151,9 @@ ngx_http_upstrand_init(ngx_conf_t *cf)
149151
ngx_http_upstrand_gw_modules[3] = ngx_http_fastcgi_module.ctx_index;
150152
ngx_http_upstrand_gw_modules[4] = ngx_http_scgi_module.ctx_index;
151153

154+
#if (NGX_HTTP_V2)
152155
ngx_http_upstrand_gw_modules[4] = ngx_http_grpc_module.ctx_index;
156+
#endif
153157
#endif
154158

155159
ngx_http_next_header_filter = ngx_http_top_header_filter;
@@ -512,6 +516,7 @@ ngx_http_upstrand_variable(ngx_http_request_t *r, ngx_http_variable_value_t *v,
512516
ngx_http_upstrand_conf_t *upstrand = (ngx_http_upstrand_conf_t *) data;
513517

514518
ngx_uint_t i;
519+
ngx_http_combined_upstreams_loc_conf_t *lcf;
515520
ngx_http_upstrand_request_ctx_t *ctx;
516521
ngx_http_upstrand_subrequest_ctx_t *sr_ctx;
517522
ngx_http_upstrand_request_common_ctx_t *common;
@@ -557,15 +562,20 @@ ngx_http_upstrand_variable(ngx_http_request_t *r, ngx_http_variable_value_t *v,
557562
* this is achieved by setting error_page flag for the request */
558563
r->error_page = 1;
559564

560-
for (i = 0; i < UPSTRAND_EFFECTIVE_GW_MODULES_SIZE; i++) {
561-
/* FIXME: this is a dirty hack: getting proxy module's location
562-
* configuration as an upstream configuration is safe only if the
563-
* upstream configuration is the first field of the location
564-
* configuration; fortunately, this is true for proxy, uwsgi, fastcgi,
565-
* scgi, and grpc modules */
566-
u = r->loc_conf[ngx_http_upstrand_gw_modules[i]];
567-
/* location must also be protected against X-Accel-Redirect headers */
568-
u->ignore_headers |= NGX_HTTP_UPSTREAM_IGN_XA_REDIRECT;
565+
lcf = ngx_http_get_module_loc_conf(r, ngx_http_combined_upstreams_module);
566+
567+
if (!lcf->upstrand_gw_modules_checked) {
568+
for (i = 0; i < UPSTRAND_EFFECTIVE_GW_MODULES_SIZE; i++) {
569+
/* FIXME: this is a dirty hack: getting proxy module's location
570+
* configuration as an upstream configuration is safe only if the
571+
* upstream configuration is the first field of the location
572+
* configuration; fortunately, this is true for proxy, uwsgi,
573+
* fastcgi, scgi, and grpc modules */
574+
u = r->loc_conf[ngx_http_upstrand_gw_modules[i]];
575+
/* location must be protected against X-Accel-Redirect headers */
576+
u->ignore_headers |= NGX_HTTP_UPSTREAM_IGN_XA_REDIRECT;
577+
}
578+
lcf->upstrand_gw_modules_checked = 1;
569579
}
570580

571581
if (ctx == NULL) {

src/ngx_http_combined_upstreams_upstrand.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -43,8 +43,8 @@ typedef struct {
4343

4444

4545
typedef struct {
46-
ngx_array_t data;
47-
ngx_int_t index;
46+
ngx_array_t data;
47+
ngx_int_t index;
4848
} ngx_http_upstrand_var_list_elem_t;
4949

5050

0 commit comments

Comments
 (0)