Mercurial > hg > nginx
comparison src/http/modules/ngx_http_slice_filter_module.c @ 6962:a97ad1663ef4
Slice filter: allowed at most one subrequest at a time.
Previously, if slice main request write handler was called while a slice
subrequest was running, a new subrequest for the same slice was started.
author | Roman Arutyunyan <arut@nginx.com> |
---|---|
date | Tue, 28 Mar 2017 14:03:57 +0300 |
parents | d16ba0ea3434 |
children | 3ff293cfdab8 |
comparison
equal
deleted
inserted
replaced
6961:903fb1ddc07f | 6962:a97ad1663ef4 |
---|---|
9 #include <ngx_core.h> | 9 #include <ngx_core.h> |
10 #include <ngx_http.h> | 10 #include <ngx_http.h> |
11 | 11 |
12 | 12 |
13 typedef struct { | 13 typedef struct { |
14 size_t size; | 14 size_t size; |
15 } ngx_http_slice_loc_conf_t; | 15 } ngx_http_slice_loc_conf_t; |
16 | 16 |
17 | 17 |
18 typedef struct { | 18 typedef struct { |
19 off_t start; | 19 off_t start; |
20 off_t end; | 20 off_t end; |
21 ngx_str_t range; | 21 ngx_str_t range; |
22 ngx_str_t etag; | 22 ngx_str_t etag; |
23 ngx_uint_t last; /* unsigned last:1; */ | 23 ngx_uint_t last; /* unsigned last:1; */ |
24 ngx_http_request_t *sr; | |
24 } ngx_http_slice_ctx_t; | 25 } ngx_http_slice_ctx_t; |
25 | 26 |
26 | 27 |
27 typedef struct { | 28 typedef struct { |
28 off_t start; | 29 off_t start; |
29 off_t end; | 30 off_t end; |
30 off_t complete_length; | 31 off_t complete_length; |
31 } ngx_http_slice_content_range_t; | 32 } ngx_http_slice_content_range_t; |
32 | 33 |
33 | 34 |
34 static ngx_int_t ngx_http_slice_header_filter(ngx_http_request_t *r); | 35 static ngx_int_t ngx_http_slice_header_filter(ngx_http_request_t *r); |
35 static ngx_int_t ngx_http_slice_body_filter(ngx_http_request_t *r, | 36 static ngx_int_t ngx_http_slice_body_filter(ngx_http_request_t *r, |
207 static ngx_int_t | 208 static ngx_int_t |
208 ngx_http_slice_body_filter(ngx_http_request_t *r, ngx_chain_t *in) | 209 ngx_http_slice_body_filter(ngx_http_request_t *r, ngx_chain_t *in) |
209 { | 210 { |
210 ngx_int_t rc; | 211 ngx_int_t rc; |
211 ngx_chain_t *cl; | 212 ngx_chain_t *cl; |
212 ngx_http_request_t *sr; | |
213 ngx_http_slice_ctx_t *ctx; | 213 ngx_http_slice_ctx_t *ctx; |
214 ngx_http_slice_loc_conf_t *slcf; | 214 ngx_http_slice_loc_conf_t *slcf; |
215 | 215 |
216 ctx = ngx_http_get_module_ctx(r, ngx_http_slice_filter_module); | 216 ctx = ngx_http_get_module_ctx(r, ngx_http_slice_filter_module); |
217 | 217 |
232 | 232 |
233 if (rc == NGX_ERROR || !ctx->last) { | 233 if (rc == NGX_ERROR || !ctx->last) { |
234 return rc; | 234 return rc; |
235 } | 235 } |
236 | 236 |
237 if (ctx->sr && !ctx->sr->done) { | |
238 return rc; | |
239 } | |
240 | |
237 if (ctx->start >= ctx->end) { | 241 if (ctx->start >= ctx->end) { |
238 ngx_http_set_ctx(r, NULL, ngx_http_slice_filter_module); | 242 ngx_http_set_ctx(r, NULL, ngx_http_slice_filter_module); |
239 ngx_http_send_special(r, NGX_HTTP_LAST); | 243 ngx_http_send_special(r, NGX_HTTP_LAST); |
240 return rc; | 244 return rc; |
241 } | 245 } |
242 | 246 |
243 if (r->buffered) { | 247 if (r->buffered) { |
244 return rc; | 248 return rc; |
245 } | 249 } |
246 | 250 |
247 if (ngx_http_subrequest(r, &r->uri, &r->args, &sr, NULL, | 251 if (ngx_http_subrequest(r, &r->uri, &r->args, &ctx->sr, NULL, |
248 NGX_HTTP_SUBREQUEST_CLONE) | 252 NGX_HTTP_SUBREQUEST_CLONE) |
249 != NGX_OK) | 253 != NGX_OK) |
250 { | 254 { |
251 return NGX_ERROR; | 255 return NGX_ERROR; |
252 } | 256 } |
253 | 257 |
254 ngx_http_set_ctx(sr, ctx, ngx_http_slice_filter_module); | 258 ngx_http_set_ctx(ctx->sr, ctx, ngx_http_slice_filter_module); |
255 | 259 |
256 slcf = ngx_http_get_module_loc_conf(r, ngx_http_slice_filter_module); | 260 slcf = ngx_http_get_module_loc_conf(r, ngx_http_slice_filter_module); |
257 | 261 |
258 ctx->range.len = ngx_sprintf(ctx->range.data, "bytes=%O-%O", ctx->start, | 262 ctx->range.len = ngx_sprintf(ctx->range.data, "bytes=%O-%O", ctx->start, |
259 ctx->start + (off_t) slcf->size - 1) | 263 ctx->start + (off_t) slcf->size - 1) |