Takashi Ishihara wrote:
> I wrote a http server using pth, but it has a problem when the
> request rate is high (say 200 request per second), and the client
> closes the socket. (or bad connection). For debugging purpose,
> I made it w/o spawning thread. i.e. the server handles the request
> in main thread. Only other thread is the pth scheduler.
> (the original version of the server spawns a thread per request or
>  use pre-spawned thread for handling the request).
> Followings are the problem and possible solutions. Any fix?
> 
> 1. the server is writing to a socket, say fd.
>    fd is default (or equivalently BLOCKING mode).
> 2. in the middle of writing to fd,
>    the client closed the connection.
> 3. When write to socket,
> ---------------------+-----------
> fd  \ func :  write  | pth_write(or pth_send)
> ...........----------+-----------
> BLOCK      :   works | BAD(i.e. stops)
> NONBLOCK   :   works | works
> ---------------------+-----------
> 
> in pthlib,
> pth_write calls
> pth_write_ev calls
>   for(;;) { // polling mode
>   ...
>     ev = pth_event(PTH_EVENT_FD|PTH_UNTIL_FD_WRITEABLE|PTH_MODE_STATIC, &ev_key, fd);
>     pth_wait(ev);
>   ...
>   }
> pth_wait first initialze ev_ring, then calls pth_yield(NULL);
> pth_yield calls
>     pth_mctx_switch(&pth_current->mctx, &pth_sched->mctx);
> ...
> // here pth_p.h says "#define cpp 0", so pth_mctx_switch in
> // "if cpp" block is not used? if so, where it's defined?
> // Anyhow, gdb bt showed
> (gdb) bt
> #0  0x4010690e in __select () from /lib/i686/libc.so.6
> #1  0x08072c3c in ?? ()
> #2  0x08052475 in __pth_scheduler ()
> #3  0x080508d3 in pth_spawn_trampoline ()
> #4  0x08051545 in pth_mctx_set_bootstrap ()
> #5  <signal handler called>
> #6  0x400538a5 in __sigsuspend (set=0xbfffc210)
>     at ../sysdeps/unix/sysv/linux/sigsuspend.c:45
> #7  0x400d6233 in __tzfile_read (file=0x0, extra=0, extrap=0x0) at tzfile.c:309
> (gdb)
> ---------------
> In short, pth_event(PTH_EVENT_FD|PTH_UNTIL_FD_WRITEABLE, .. will never
> happen. Then pthlib stops at select(). Forever.

Are you checking the return value of every call to pth_write() ?
If it returns -1 and you miss that, then this could happen.

This may be O/S dependent.. which are you using?

FYI, on FreeBSD I've never seen this happen. An open socket descriptor
for which the peer has closed it's side of the connection will always
report writable, and then when you write to it you will get an error.

-Archie

__________________________________________________________________________
Archie Cobbs     *     Packet Design     *     http://www.packetdesign.com
______________________________________________________________________
GNU Portable Threads (Pth)            http://www.gnu.org/software/pth/
User Support Mailing List                            [EMAIL PROTECTED]
Automated List Manager (Majordomo)           [EMAIL PROTECTED]

Reply via email to