X-Git-Url: http://sjero.net/git/?a=blobdiff_plain;f=src%2Fftp.c;h=cba545002d9039a936bfd18da3dcb0852387374d;hb=b5c9573ad6396acf3e4e33d0ae0db65b413b0d66;hp=c5ac83032aa596ad659bd9fa3b384db5669618a7;hpb=6ef8c69c9d34bbb750ddcd2062e668fb0d941cff;p=wget diff --git a/src/ftp.c b/src/ftp.c index c5ac8303..cba54500 100644 --- a/src/ftp.c +++ b/src/ftp.c @@ -63,8 +63,6 @@ as that of the covered work. */ #define LIST_FILENAME ".listing" #endif -#define max(a, b) ((a > b) ? (a) : (b)) - typedef struct { int st; /* connection status */ @@ -254,6 +252,7 @@ getftp (struct url *u, wgint passed_expected_bytes, wgint *qtyread, int cmd = con->cmd; bool pasv_mode_open = false; wgint expected_bytes = 0; + bool got_expected_bytes = false; bool rest_failed = false; int flags; wgint rd_size; @@ -757,6 +756,7 @@ Error in server response, closing control connection.\n")); con->csock = -1; return err; case FTPOK: + got_expected_bytes = true; /* Everything is OK. */ break; default: @@ -767,6 +767,16 @@ Error in server response, closing control connection.\n")); number_to_static_string (expected_bytes)); } + if (cmd & DO_RETR && restval > 0 && restval == expected_bytes) + { + /* Server confirms that file has length restval. We should stop now. + Some servers (f.e. NcFTPd) return error when receive REST 0 */ + logputs (LOG_VERBOSE, _("File has already been retrieved.\n")); + fd_close (csock); + con->csock = -1; + return RETRFINISHED; + } + /* If anything is to be retrieved, PORT (or PASV) must be sent. */ if (cmd & (DO_LIST | DO_RETR)) { @@ -1022,8 +1032,8 @@ Error in server response, closing control connection.\n")); if (!opt.server_response) logputs (LOG_VERBOSE, _("done.\n")); - expected_bytes = max (ftp_expected_bytes (ftp_last_respline), - expected_bytes); + if (! got_expected_bytes) + expected_bytes = ftp_expected_bytes (ftp_last_respline); } /* do retrieve */ if (cmd & DO_LIST) @@ -1069,8 +1079,9 @@ Error in server response, closing control connection.\n")); } if (!opt.server_response) logputs (LOG_VERBOSE, _("done.\n")); - expected_bytes = max (ftp_expected_bytes (ftp_last_respline), - expected_bytes); + + if (! got_expected_bytes) + expected_bytes = ftp_expected_bytes (ftp_last_respline); } /* cmd & DO_LIST */ if (!(cmd & (DO_LIST | DO_RETR)) || (opt.spider && !(cmd & DO_LIST))) @@ -1162,7 +1173,22 @@ Error in server response, closing control connection.\n")); } else if (opt.noclobber || opt.always_rest || opt.timestamping || opt.dirstruct || opt.output_document) - { + { + if (opt.unlink && file_exists_p (con->target)) + { + int res = unlink (con->target); + if (res < 0) + { + logprintf (LOG_NOTQUIET, "%s: %s\n", con->target, + strerror (errno)); + fd_close (csock); + con->csock = -1; + fd_close (dtsock); + fd_close (local_sock); + return UNLINKERR; + } + } + #ifdef __VMS int open_id; @@ -1371,7 +1397,7 @@ ftp_loop_internal (struct url *u, struct fileinfo *f, ccon *con, char **local_fi else { /* URL-derived file. Consider "-O file" name. */ - con->target = url_file_name (u); + con->target = url_file_name (u, NULL); if (!opt.output_document) locf = con->target; else @@ -1458,7 +1484,7 @@ ftp_loop_internal (struct url *u, struct fileinfo *f, ccon *con, char **local_fi xfree (hurl); } /* Send getftp the proper length, if fileinfo was provided. */ - if (f) + if (f && f->type != FT_SYMLINK) len = f->size; else len = 0; @@ -1473,6 +1499,7 @@ ftp_loop_internal (struct url *u, struct fileinfo *f, ccon *con, char **local_fi { case HOSTERR: case CONIMPOSSIBLE: case FWRITEERR: case FOPENERR: case FTPNSFOD: case FTPLOGINC: case FTPNOPASV: case CONTNOTSUPPORTED: + case UNLINKERR: /* Fatal errors, give up. */ return err; case CONSOCKERR: case CONERROR: case FTPSRVERR: case FTPRERR: @@ -1485,7 +1512,7 @@ ftp_loop_internal (struct url *u, struct fileinfo *f, ccon *con, char **local_fi { /* Re-determine the file name. */ xfree_null (con->target); - con->target = url_file_name (u); + con->target = url_file_name (u, NULL); locf = con->target; } continue; @@ -1613,7 +1640,7 @@ ftp_get_listing (struct url *u, ccon *con, struct fileinfo **f) /* Find the listing file name. We do it by taking the file name of the URL and replacing the last component with the listing file name. */ - uf = url_file_name (u); + uf = url_file_name (u, NULL); lf = file_merge (uf, LIST_FILENAME); xfree (uf); DEBUGP ((_("Using %s as listing tmp file.\n"), quote (lf))); @@ -1707,7 +1734,7 @@ ftp_retrieve_list (struct url *u, struct fileinfo *f, ccon *con) ofile = xstrdup (u->file); url_set_file (u, f->name); - con->target = url_file_name (u); + con->target = url_file_name (u, NULL); err = RETROK; dlthis = true; @@ -2126,7 +2153,7 @@ ftp_retrieve_glob (struct url *u, ccon *con, int action) of URL. Inherently, its capabilities are limited on what can be encoded into a URL. */ uerr_t -ftp_loop (struct url *u, char **local_file, int *dt, struct url *proxy, +ftp_loop (struct url *u, char **local_file, int *dt, struct url *proxy, bool recursive, bool glob) { ccon con; /* FTP connection */ @@ -2157,7 +2184,7 @@ ftp_loop (struct url *u, char **local_file, int *dt, struct url *proxy, char *filename = (opt.output_document ? xstrdup (opt.output_document) : (con.target ? xstrdup (con.target) - : url_file_name (u))); + : url_file_name (u, NULL))); res = ftp_index (filename, u, f); if (res == FTPOK && opt.verbose) {