@@ -69,6 +69,8 @@ ngx_http_read_client_request_body(ngx_http_request_t *r,
69
69
* rb->busy = NULL;
70
70
* rb->chunked = NULL;
71
71
* rb->received = 0;
72
+ * rb->filter_need_buffering = 0;
73
+ * rb->last_sent = 0;
72
74
* rb->last_saved = 0;
73
75
*/
74
76
@@ -147,7 +149,7 @@ ngx_http_read_client_request_body(ngx_http_request_t *r,
147
149
}
148
150
}
149
151
150
- if (rb -> rest == 0 ) {
152
+ if (rb -> rest == 0 && rb -> last_saved ) {
151
153
/* the whole request body was pre-read */
152
154
r -> request_body_no_buffering = 0 ;
153
155
post_handler (r );
@@ -175,6 +177,10 @@ ngx_http_read_client_request_body(ngx_http_request_t *r,
175
177
size += preread ;
176
178
}
177
179
180
+ if (size == 0 ) {
181
+ size ++ ;
182
+ }
183
+
178
184
} else {
179
185
size = clcf -> client_body_buffer_size ;
180
186
}
@@ -273,19 +279,25 @@ ngx_http_do_read_client_request_body(ngx_http_request_t *r)
273
279
size_t size ;
274
280
ssize_t n ;
275
281
ngx_int_t rc ;
282
+ ngx_uint_t flush ;
276
283
ngx_chain_t out ;
277
284
ngx_connection_t * c ;
278
285
ngx_http_request_body_t * rb ;
279
286
ngx_http_core_loc_conf_t * clcf ;
280
287
281
288
c = r -> connection ;
282
289
rb = r -> request_body ;
290
+ flush = 1 ;
283
291
284
292
ngx_log_debug0 (NGX_LOG_DEBUG_HTTP , c -> log , 0 ,
285
293
"http read client request body" );
286
294
287
295
for ( ;; ) {
288
296
for ( ;; ) {
297
+ if (rb -> rest == 0 ) {
298
+ break ;
299
+ }
300
+
289
301
if (rb -> buf -> last == rb -> buf -> end ) {
290
302
291
303
/* update chains */
@@ -309,12 +321,25 @@ ngx_http_do_read_client_request_body(ngx_http_request_t *r)
309
321
return NGX_AGAIN ;
310
322
}
311
323
324
+ if (rb -> filter_need_buffering ) {
325
+ clcf = ngx_http_get_module_loc_conf (r ,
326
+ ngx_http_core_module );
327
+ ngx_add_timer (c -> read , clcf -> client_body_timeout );
328
+
329
+ if (ngx_handle_read_event (c -> read , 0 ) != NGX_OK ) {
330
+ return NGX_HTTP_INTERNAL_SERVER_ERROR ;
331
+ }
332
+
333
+ return NGX_AGAIN ;
334
+ }
335
+
312
336
ngx_log_error (NGX_LOG_ALERT , c -> log , 0 ,
313
337
"busy buffers after request body flush" );
314
338
315
339
return NGX_HTTP_INTERNAL_SERVER_ERROR ;
316
340
}
317
341
342
+ flush = 0 ;
318
343
rb -> buf -> pos = rb -> buf -> start ;
319
344
rb -> buf -> last = rb -> buf -> start ;
320
345
}
@@ -326,6 +351,10 @@ ngx_http_do_read_client_request_body(ngx_http_request_t *r)
326
351
size = (size_t ) rest ;
327
352
}
328
353
354
+ if (size == 0 ) {
355
+ break ;
356
+ }
357
+
329
358
n = c -> recv (c , rb -> buf -> last , size );
330
359
331
360
ngx_log_debug1 (NGX_LOG_DEBUG_HTTP , c -> log , 0 ,
@@ -350,6 +379,7 @@ ngx_http_do_read_client_request_body(ngx_http_request_t *r)
350
379
351
380
/* pass buffer to request body filter chain */
352
381
382
+ flush = 0 ;
353
383
out .buf = rb -> buf ;
354
384
out .next = NULL ;
355
385
@@ -371,11 +401,19 @@ ngx_http_do_read_client_request_body(ngx_http_request_t *r)
371
401
ngx_log_debug1 (NGX_LOG_DEBUG_HTTP , c -> log , 0 ,
372
402
"http client request body rest %O" , rb -> rest );
373
403
374
- if (rb -> rest == 0 ) {
404
+ if (flush ) {
405
+ rc = ngx_http_request_body_filter (r , NULL );
406
+
407
+ if (rc != NGX_OK ) {
408
+ return rc ;
409
+ }
410
+ }
411
+
412
+ if (rb -> rest == 0 && rb -> last_saved ) {
375
413
break ;
376
414
}
377
415
378
- if (!c -> read -> ready ) {
416
+ if (!c -> read -> ready || rb -> rest == 0 ) {
379
417
380
418
clcf = ngx_http_get_module_loc_conf (r , ngx_http_core_module );
381
419
ngx_add_timer (c -> read , clcf -> client_body_timeout );
@@ -1280,7 +1318,9 @@ ngx_http_request_body_save_filter(ngx_http_request_t *r, ngx_chain_t *in)
1280
1318
return NGX_OK ;
1281
1319
}
1282
1320
1283
- /* rb->rest == 0 */
1321
+ if (!rb -> last_saved ) {
1322
+ return NGX_OK ;
1323
+ }
1284
1324
1285
1325
if (rb -> temp_file || r -> request_body_in_file_only ) {
1286
1326
0 commit comments