I am developing a body filter which transforms outgoing stream. As part
of the function, the incoming stream is copied in new buffer and sent.
This in some cases results in a condition where my filter has busy
buffers but the upper layers don’t have any busy buffer. In our case the
data is generated by upstream module. Since upstream module does not pay
attention to connection->buffered, the output_filter is never called
again to flush my busy buffers and the transfer just hangs.
Adding r->connection->buffered to the or condition solves the hang.
if (u->out_bufs || u->busy_bufs) {
rc = ngx_http_output_filter(r, u->out_bufs);
if (rc == NGX_ERROR) {
ngx_http_upstream_finalize_request(r, u, 0);
return;
}
ngx_chain_update_chains(&u->free_bufs, &u->busy_bufs,
&u->out_bufs, u->output.tag);
}
Is this nginx bug or am I missing something?
-Umesh
Any help on this will be greatly appreciated.
Thank you!
-Umesh
I am developing a body filter which transforms outgoing stream. As part
of the function, the incoming stream is copied in new buffer and sent.
This in some cases results in a condition where my filter has busy
buffers but the upper layers don’t have any busy buffer. In our case the
data is generated by upstream module. Since upstream module does not pay
attention to connection->buffered, the output_filter is never called
again to flush my busy buffers and the transfer just hangs.
Adding r->connection->buffered to the or condition solves the hang.
if (u->out_bufs || u->busy_bufs) {
rc = ngx_http_output_filter(r, u->out_bufs);
if (rc == NGX_ERROR) {
ngx_http_upstream_finalize_request(r, u, 0);
return;
}
ngx_chain_update_chains(&u->free_bufs, &u->busy_bufs,
&u->out_bufs, u->output.tag);
}
Is this nginx bug or am I missing something?
-Umesh
Hello!
On Mon, Nov 28, 2011 at 11:52:38AM -0500, Umesh Sirsiwal wrote:
}
Is this nginx bug or am I missing something?
I tend to think this is a bug, and it should probably manifest
itself with e.g. gzip filter as well.
(Well, as far as I see transfer shouldn’t hang completely, but it
will be only resumed as soon as upstream sends some more data or
closes connection.)
It would be superb if you’ll be able to provide test case which
catches this for our test suite (nginx-tests: log).
I’ll look into this more closely as time permits.
Maxim D.
Hello!
On Fri, Dec 02, 2011 at 11:13:15AM -0500, Umesh Sirsiwal wrote:
Hey Maxim,
I spent some time yesterday and today trying to reproduce this issue
with standard gzip module. But, unfortunately I could not. May be I
am doing something wrong in my module.
My configuration looked like the following. I was using nginx
version 1.1.10.
[…]
proxy_buffering on;
The code in question isn’t executed with proxy_buffering set to
on, it’s only in “proxy_buffering off” codepath.
Maxim D.
On 12/02/2011 12:02 PM, Maxim D. wrote:
version 1.1.10.
[…]
proxy_buffering on;
The code in question isn’t executed with proxy_buffering set to
on, it’s only in “proxy_buffering off” codepath.
Ouch! I changed it to “proxy_buffering off” and retrieved 10MB file in a
loop over and over again. Still can’t reproduce it. Looking at netstat
output I can see lots of data sitting in the socket buffer.
I did notice that the limit_rate directive does not work with
proxy_buffering off.
-Umesh
Hey Maxim,
I spent some time yesterday and today trying to reproduce this issue
with standard gzip module. But, unfortunately I could not. May be I am
doing something wrong in my module.
My configuration looked like the following. I was using nginx version
1.1.10.
-Umesh
worker_processes 1;
daemon off;
http {
default_type application/octet-stream;
sendfile on;
keepalive_timeout 65;
upstream http_backend {
server 127.0.0.1:8080;
keepalive 1;
}
server {
listen 8080 sndbuf=10k;
server_name localhost;
proxy_buffering on;
proxy_buffers 10000 4k;
gzip on;
gzip_proxied any;
location / {
proxy_pass http://http_backend/local/;
proxy_http_version 1.1;
proxy_set_header Connection "";
#limit_rate 100K;
}
location /local/ {
alias /tmp/nginx-test-dL3kfZazKJ/;
}
}
}