]> git.ipfire.org Git - thirdparty/squid.git/commitdiff
Bug #1194: FTP data connection fails on some FTP servers when requesting
authorserassio <>
Sun, 30 Jan 2005 02:14:08 +0000 (02:14 +0000)
committerserassio <>
Sun, 30 Jan 2005 02:14:08 +0000 (02:14 +0000)
directory without a trailing slash

This patch simplifies FTP data connection management to always reopen a
new connection after a failed FTP request.

Forward port of 2.5 patch.

src/ftp.cc

index a2c324f9975d50abcd4f70ee76e15fedd11c0e95..b3ac65d5d881f5a0ce1541523849d48aa909f203 100644 (file)
@@ -1,6 +1,6 @@
 
 /*
- * $Id: ftp.cc,v 1.358 2004/05/31 23:17:51 hno Exp $
+ * $Id: ftp.cc,v 1.359 2005/01/29 19:14:08 serassio Exp $
  *
  * DEBUG: section 9     File Transfer Protocol (FTP)
  * AUTHOR: Harvest Derived
@@ -125,9 +125,6 @@ unsigned int put_mkdir:
 
 unsigned int listformat_unknown:
     1;
-
-unsigned int datachannel_hack:
-    1;
 };
 
 class FtpStateData
@@ -1184,8 +1181,11 @@ ftpDataRead(int fd, char *buf, size_t len, comm_err_t errflag, int xerrno, void
         IOStats.Ftp.read_hist[bin]++;
     }
 
-    if (ftpState->flags.isdir && !ftpState->flags.html_header_sent && len >= 0) {
-        ftpListingStart(ftpState);
+    if (!ftpState->flags.http_header_sent && len >= 0) {
+        ftpAppendSuccessHeader(ftpState);
+
+        if (ftpState->flags.isdir)
+            ftpListingStart(ftpState);
     }
 
     if (errflag != COMM_OK || len < 0) {
@@ -1201,6 +1201,11 @@ ftpDataRead(int fd, char *buf, size_t len, comm_err_t errflag, int xerrno, void
 
             comm_read(fd, ftpState->data.buf + ftpState->data.offset, read_sz, ftpDataRead, data);
         } else {
+            if (!ftpState->flags.http_header_sent && !ftpState->fwd->flags.ftp_pasv_failed && ftpState->flags.pasv_supported) {
+                ftpState->fwd->flags.dont_retry = 0;   /* this is a retryable error */
+                ftpState->fwd->flags.ftp_pasv_failed = 1;
+            }
+
             ftpFailed(ftpState, ERR_READ_ERROR, 0);
             /* ftpFailed closes ctrl.fd and frees ftpState */
             return;
@@ -1371,11 +1376,7 @@ ftpStart(FwdState * fwd)
     ftpState->size = -1;
     ftpState->mdtm = -1;
 
-    if (!Config.Ftp.passive)
-        ftpState->flags.rest_supported = 0;
-    else if (fwd->flags.ftp_pasv_failed)
-        ftpState->flags.pasv_supported = 0;
-    else
+    if (Config.Ftp.passive && !fwd->flags.ftp_pasv_failed)
         ftpState->flags.pasv_supported = 1;
 
     ftpState->flags.rest_supported = 1;
@@ -2123,15 +2124,9 @@ ftpSendPasv(FtpStateData * ftpState)
     }
 
     if (ftpState->data.fd >= 0) {
-        if (!ftpState->flags.datachannel_hack) {
-            /* We are already connected, reuse this connection. */
-            ftpRestOrList(ftpState);
-            return;
-        } else {
-            /* Close old connection */
-            comm_close(ftpState->data.fd);
-            ftpState->data.fd = -1;
-        }
+        /* Close old connection */
+        comm_close(ftpState->data.fd);
+        ftpState->data.fd = -1;
     }
 
     if (!ftpState->flags.pasv_supported) {
@@ -2617,7 +2612,6 @@ ftpReadList(FtpStateData * ftpState)
 
     if (code == 125 || (code == 150 && ftpState->data.host)) {
         /* Begin data transfer */
-        ftpAppendSuccessHeader(ftpState);
         /* XXX what about Config.Timeout.read? */
         assert(ftpState->data.offset == 0);
         ftpState->entry->delayAwareRead(ftpState->data.fd, ftpState->data.buf, ftpState->data.size, ftpDataRead, ftpState);
@@ -2665,7 +2659,6 @@ ftpReadRetr(FtpStateData * ftpState)
     if (code == 125 || (code == 150 && ftpState->data.host)) {
         /* Begin data transfer */
         debug(9, 3) ("ftpReadRetr: reading data channel\n");
-        ftpAppendSuccessHeader(ftpState);
         /* XXX what about Config.Timeout.read? */
         size_t read_sz = ftpState->data.size - ftpState->data.offset;
 
@@ -2830,31 +2823,6 @@ ftpTrySlashHack(FtpStateData * ftpState)
     ftpGetFile(ftpState);
 }
 
-static void
-ftpTryDatachannelHack(FtpStateData * ftpState)
-{
-    ftpState->flags.datachannel_hack = 1;
-    /* we have to undo some of the slash hack... */
-
-    if (ftpState->old_filepath != NULL) {
-        ftpState->flags.try_slash_hack = 0;
-        safe_free(ftpState->filepath);
-        ftpState->filepath = ftpState->old_filepath;
-        ftpState->old_filepath = NULL;
-    }
-
-    ftpState->flags.tried_nlst = 0;
-    /* And off we go */
-
-    if (ftpState->flags.isdir) {
-        ftpListDir(ftpState);
-    } else {
-        ftpGetFile(ftpState);
-    }
-
-    return;
-}
-
 /* Forget hack status. Next error is shown to the user */
 static void
 ftpUnhack(FtpStateData * ftpState)
@@ -2912,25 +2880,6 @@ ftpFail(FtpStateData * ftpState)
         }
     }
 
-    /* Try to reopen datachannel */
-    if (!ftpState->flags.datachannel_hack &&
-            ftpState->pathcomps == NULL) {
-        switch (ftpState->state) {
-
-        case SENT_RETR:
-
-        case SENT_LIST:
-
-        case SENT_NLST:
-            /* Try to reopen datachannel */
-            ftpHackShortcut(ftpState, ftpTryDatachannelHack);
-            return;
-
-        default:
-            break;
-        }
-    }
-
     ftpFailed(ftpState, ERR_NONE, 0);
     /* ftpFailed closes ctrl.fd and frees ftpState */
 }