Subject: ftpd jobs hanging [1079]

From: Russel Kipp Jones <[email-masked]>
Date: Tue, 10 Jan 1995 22:14:31 -0500

Hello all,

We are running wu-ftpd-2.4 on a SunOS 4.1.3_U1.  Lately, we've
been seeing a lot of tasks hanging and never going away.

It appears that these (at least some of them) are being generated
by the new Netscape browser (v1.0N) which opens an ftp session
and tends to leave it open  [I've heard that this was done for
performance reasons...].  But it also appears that the sessions
are not always being terminated correctly, thus leaving the ftpd
hanging.

I've got some of the details of where it's hanging, and I can
repeatedly re-create this.  See below if you are interested.

Has anybody experienced this?  Does anyone know of a patch?

Thanks,

kipp
p.s. I sent this off to Netscape Communications Corporation as well.
-----------
debug info....

Looks like in ftpdcmd.y, line 992
getline(s = 0x23510 "CWD /pub/ai/www\n", n = 511), line 992 in "ftpcmd.y
Came from ftpd.c, line 555
*`ftpd`main`argv = 0xf7ffffcb "ulst.ac.uk: anonymous/Netscape@: IDLE         "
....

-----------------------------------------------------------------------------
Kipp Jones ([email-masked])(http://www.cc.gatech.edu/grads/j/Kipp.Jones/)
Graduate Research Assistant                 Computing and Networking Services 
College of Computing, Room 212,  Georgia Institute of Technology, Atlanta, GA 
"Every thirty minutes, another network connects"    Anthony-Michael Rutkowski

---

From: Donn Cave <[email-masked]>
Date: Wed, 11 Jan 1995 13:43:09 -0800 (PST)

| We are running wu-ftpd-2.4 on a SunOS 4.1.3_U1.  Lately, we've
| been seeing a lot of tasks hanging and never going away.
| 
| It appears that these (at least some of them) are being generated
| by the new Netscape browser (v1.0N) which opens an ftp session
| and tends to leave it open  [I've heard that this was done for
| performance reasons...].  But it also appears that the sessions
| are not always being terminated correctly, thus leaving the ftpd
| hanging.

An alert reader gave me a patch that addresses this problem.  Our
ftp service had been losing really badly on this, I'd guess a 2-day
system crash interval, from attrition in kernel resources.  After
application of the patch, we don't have the lingering connections,
and network memory allocation is now pretty stable.

The patch doesn't go to exactly the place you indicate, but since its
author (Caspar Dik) relates it to the same Netscape phenomenon,
it seems like a pretty safe bet.  I'm going to post the patch as I
received it - but is there a better way to handle a patch like this,
than periodic reposts?

	Donn Cave, University Computing Services, University of Washington
	[email-masked]
-------------------------------
Date: Fri, 25 Nov 1994 15:00:18 +0100
From: Casper Dik <[email-masked]>
Subject: [772] hanging ftpds fix for wu-ftpd 2.4

The following patch works around a problem with wu-ftpd.
Recently we've seen an increasing number of ftpd's sticking around.

This scenario has become increasingly common since netscape was released
and from our logs it does look like web-browser connections caused this
problem.

After some investigation it turned out that ftpd hung in accept.
(thanks to lsof and truss).  

Problem scenario:

	client sends "PASV"
	client sends "RETR file"
	client doesn't open a connection, instead the client aborts.

This fix may not be portable, but works for me on Solaris 2.x and probably
works on SunOS 4.1.x and BSD derivatives with fd_set typedef'ed as well.
Some systes may need to include extra files.

The fix is a timeout on accept with select().  The timeout is set to 120
seconds, but I have no idea whether that is sufficient.

Please include me in any replies, as I'm not on this list.

Casper

*** ftpd.c.org	Thu Apr 14 22:05:35 1994
--- ftpd.c	Mon Nov 21 19:40:59 1994
***************
*** 1710,1717 ****
--- 1710,1731 ----
          int s,
            fromlen = sizeof(from);
  
+ #ifdef FD_ZERO
+ 	struct timeval timeout;
+ 	fd_set set;
+ 
+ 	FD_ZERO(&set);
+ 	FD_SET(pdata, &set);
+ 
+ 	timeout.tv_usec = 0;
+ 	timeout.tv_sec = 120;
+ 
+ 	if (select(pdata+1, &set, (fd_set *) 0, (fd_set *) 0, &timeout) == 0 ||
+ 	    (s = accept(pdata, (struct sockaddr *) &from, &fromlen)) < 0) {
+ #else
          s = accept(pdata, (struct sockaddr *) &from, &fromlen);
          if (s < 0) {
+ #endif
              reply(425, "Can't open data connection.");
              (void) close(pdata);
              pdata = -1;