Client abort detection w/ upstream broken on anything but kqueue ()?
Marcello Barnaba
marcello.barnaba at gmail.com
Wed Nov 3 14:21:47 MSK 2010
Hello,
On Nov 3, 2010, at 1:11 AM, Maxim Dounin wrote:
> Looking into errno without getting error from function is
> meaningless[1].
>
> [1] http://www.opengroup.org/onlinepubs/9699919799/functions/errno.html
Right
>> I've tried to change the condition at line 1016 from n > 0 to
>> (n > 0 && err != NGX_EAGAIN && err != NGX_EWOULDBLOCK) but I'm
>> sure it doesn't make much sense.
>> Is this a known issue? From where should I start to solve it?
>
> As long as recv() returned 1 - it means that you have outstanding
> data in connection (e.g. some pipelined request) and it's
> impossible to detect if connection was closed or not without
> reading this data or writing something to connection (or some
> out-of-band hint from OS as kqueue provides).
I've tried reading the whole data while in GDB, and this is the
result (Darwin/poll()):
(gdb) l
989
990 #endif
991
992 ngx_debug_point();
993
994 n = recv(c->fd, buf, 1, MSG_PEEK);
995
996 err = ngx_socket_errno;
997
998 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, ev->log, err,
(gdb) p buf = malloc(10000)
$2 = ""
(gdb) p (int)recv(c->fd, buf, 10000, 0)
$3 = 37
(gdb) x/37b buf
0x7fff5fbff06f: 0x15 0x03 0x01 0x00 0x20 0x5f 0x01 0x61
0x7fff5fbff077: 0x9d 0x83 0xa8 0x74 0xaa 0xcc 0xf6 0x78
0x7fff5fbff07f: 0x81 0x42 0x98 0x20 0x08 0xe3 0x66 0x21
0x7fff5fbff087: 0x52 0x3a 0xca 0xe2 0x08 0xac 0x98 0xcf
0x7fff5fbff08f: 0x74 0x5c 0xa4 0x06 0xd5
do this binary data make any sense?
> At the point in question it's not possible to read all data or
> write something, so basically premature connection close by client
> with outstanding data is undetectable with classic socket
> interface.
>
> This shouldn't be a major issue though:
>
> a) normally connections doesn't have outstanding data when user
> cancels request (closes browser window, hits "stop" and so on) and
> the detection works well even without kqueue;
> b) this is only optimization anyway.
In my case, the client connection is initiated by XHR and it's a
long-polling request towards an Erlang server that implements a
web-based chat system: the recv () return value is very strange,
because there's really no outstanding data to receive from the
client. From the nginx logs I see that the only data sent by the
browser is forwarded to the upstream.
Moreover, I'm using proxy_read_timeout 300, to reduce the number
of long-polling requests, and I need to know when a connection
is closed to kick off users from chat rooms after a timeout has
passed. But:
* nginx maintains duplicate open connections to the server even
when the client has closed the browser window or navigated to
a page without the client javascript;
* my 'client disconnection code' in the server doesn't work at all
until the nginx read timeout expires;
* javascript-initiated "logoff" commands on e.g. window.onUnload
aren't portable and reliable as (I thought) socket events :-)
Thank you for your answer,
~Marcello
--
~ marcello.barnaba at gmail.com
~ http://www.linkedin.com/in/marcellobarnaba
~ http://sindro.me/
More information about the nginx
mailing list