wget: use FEATURE_COPYBUF_KB-sized buffer. Much faster for local transfers
function old new delta base64enc - 53 +53 gethdr 190 200 +10 ftpcmd 129 133 +4 progress_meter 160 122 -38 retrieve_file_data 431 392 -39 base64enc_512 46 - -46 wget_main 2456 2220 -236 ------------------------------------------------------------------------------ (add/remove: 1/1 grow/shrink: 2/3 up/down: 67/-359) Total: -292 bytes Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
This commit is contained in:
parent
77350aa933
commit
df4e16c9af
@ -156,7 +156,7 @@ config FEATURE_COPYBUF_KB
|
|||||||
range 1 1024
|
range 1 1024
|
||||||
default 4
|
default 4
|
||||||
help
|
help
|
||||||
Size of buffer used by cp, mv, install etc.
|
Size of buffer used by cp, mv, install, wget etc.
|
||||||
Buffers which are 4 kb or less will be allocated on stack.
|
Buffers which are 4 kb or less will be allocated on stack.
|
||||||
Bigger buffers will be allocated with mmap, with fallback to 4 kb
|
Bigger buffers will be allocated with mmap, with fallback to 4 kb
|
||||||
stack buffer if mmap fails.
|
stack buffer if mmap fails.
|
||||||
|
@ -35,12 +35,16 @@ struct globals {
|
|||||||
#endif
|
#endif
|
||||||
smallint chunked; /* chunked transfer encoding */
|
smallint chunked; /* chunked transfer encoding */
|
||||||
smallint got_clen; /* got content-length: from server */
|
smallint got_clen; /* got content-length: from server */
|
||||||
|
/* Local downloads do benefit from big buffer.
|
||||||
|
* With 512 byte buffer, it was measured to be
|
||||||
|
* an order of magnitude slower than with big one.
|
||||||
|
*/
|
||||||
|
uint64_t just_to_align_next_member;
|
||||||
|
char wget_buf[CONFIG_FEATURE_COPYBUF_KB*1024];
|
||||||
} FIX_ALIASING;
|
} FIX_ALIASING;
|
||||||
#define G (*(struct globals*)&bb_common_bufsiz1)
|
#define G (*ptr_to_globals)
|
||||||
struct BUG_G_too_big {
|
|
||||||
char BUG_G_too_big[sizeof(G) <= COMMON_BUFSIZE ? 1 : -1];
|
|
||||||
};
|
|
||||||
#define INIT_G() do { \
|
#define INIT_G() do { \
|
||||||
|
SET_PTR_TO_GLOBALS(xzalloc(sizeof(G))); \
|
||||||
IF_FEATURE_WGET_TIMEOUT(G.timeout_seconds = 900;) \
|
IF_FEATURE_WGET_TIMEOUT(G.timeout_seconds = 900;) \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
@ -158,14 +162,14 @@ static char *safe_fgets(char *s, int size, FILE *stream)
|
|||||||
}
|
}
|
||||||
|
|
||||||
#if ENABLE_FEATURE_WGET_AUTHENTICATION
|
#if ENABLE_FEATURE_WGET_AUTHENTICATION
|
||||||
/* Base64-encode character string. buf is assumed to be char buf[512]. */
|
/* Base64-encode character string. */
|
||||||
static char *base64enc_512(char buf[512], const char *str)
|
static char *base64enc(const char *str)
|
||||||
{
|
{
|
||||||
unsigned len = strlen(str);
|
unsigned len = strlen(str);
|
||||||
if (len > 512/4*3 - 10) /* paranoia */
|
if (len > sizeof(G.wget_buf)/4*3 - 10) /* paranoia */
|
||||||
len = 512/4*3 - 10;
|
len = sizeof(G.wget_buf)/4*3 - 10;
|
||||||
bb_uuencode(buf, str, len, bb_uuenc_tbl_base64);
|
bb_uuencode(G.wget_buf, str, len, bb_uuenc_tbl_base64);
|
||||||
return buf;
|
return G.wget_buf;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -191,7 +195,7 @@ static FILE *open_socket(len_and_sockaddr *lsa)
|
|||||||
return fp;
|
return fp;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int ftpcmd(const char *s1, const char *s2, FILE *fp, char *buf)
|
static int ftpcmd(const char *s1, const char *s2, FILE *fp)
|
||||||
{
|
{
|
||||||
int result;
|
int result;
|
||||||
if (s1) {
|
if (s1) {
|
||||||
@ -203,18 +207,18 @@ static int ftpcmd(const char *s1, const char *s2, FILE *fp, char *buf)
|
|||||||
do {
|
do {
|
||||||
char *buf_ptr;
|
char *buf_ptr;
|
||||||
|
|
||||||
if (fgets(buf, 510, fp) == NULL) {
|
if (fgets(G.wget_buf, sizeof(G.wget_buf)-2, fp) == NULL) {
|
||||||
bb_perror_msg_and_die("error getting response");
|
bb_perror_msg_and_die("error getting response");
|
||||||
}
|
}
|
||||||
buf_ptr = strstr(buf, "\r\n");
|
buf_ptr = strstr(G.wget_buf, "\r\n");
|
||||||
if (buf_ptr) {
|
if (buf_ptr) {
|
||||||
*buf_ptr = '\0';
|
*buf_ptr = '\0';
|
||||||
}
|
}
|
||||||
} while (!isdigit(buf[0]) || buf[3] != ' ');
|
} while (!isdigit(G.wget_buf[0]) || G.wget_buf[3] != ' ');
|
||||||
|
|
||||||
buf[3] = '\0';
|
G.wget_buf[3] = '\0';
|
||||||
result = xatoi_positive(buf);
|
result = xatoi_positive(G.wget_buf);
|
||||||
buf[3] = ' ';
|
G.wget_buf[3] = ' ';
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -278,7 +282,7 @@ static void parse_url(char *src_url, struct host_info *h)
|
|||||||
sp = h->host;
|
sp = h->host;
|
||||||
}
|
}
|
||||||
|
|
||||||
static char *gethdr(char *buf, size_t bufsiz, FILE *fp /*, int *istrunc*/)
|
static char *gethdr(FILE *fp /*, int *istrunc*/)
|
||||||
{
|
{
|
||||||
char *s, *hdrval;
|
char *s, *hdrval;
|
||||||
int c;
|
int c;
|
||||||
@ -286,24 +290,24 @@ static char *gethdr(char *buf, size_t bufsiz, FILE *fp /*, int *istrunc*/)
|
|||||||
/* *istrunc = 0; */
|
/* *istrunc = 0; */
|
||||||
|
|
||||||
/* retrieve header line */
|
/* retrieve header line */
|
||||||
if (fgets(buf, bufsiz, fp) == NULL)
|
if (fgets(G.wget_buf, sizeof(G.wget_buf), fp) == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
/* see if we are at the end of the headers */
|
/* see if we are at the end of the headers */
|
||||||
for (s = buf; *s == '\r'; ++s)
|
for (s = G.wget_buf; *s == '\r'; ++s)
|
||||||
continue;
|
continue;
|
||||||
if (*s == '\n')
|
if (*s == '\n')
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
/* convert the header name to lower case */
|
/* convert the header name to lower case */
|
||||||
for (s = buf; isalnum(*s) || *s == '-' || *s == '.'; ++s) {
|
for (s = G.wget_buf; isalnum(*s) || *s == '-' || *s == '.'; ++s) {
|
||||||
/* tolower for "A-Z", no-op for "0-9a-z-." */
|
/* tolower for "A-Z", no-op for "0-9a-z-." */
|
||||||
*s = (*s | 0x20);
|
*s = (*s | 0x20);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* verify we are at the end of the header name */
|
/* verify we are at the end of the header name */
|
||||||
if (*s != ':')
|
if (*s != ':')
|
||||||
bb_error_msg_and_die("bad header line: %s", sanitize_string(buf));
|
bb_error_msg_and_die("bad header line: %s", sanitize_string(G.wget_buf));
|
||||||
|
|
||||||
/* locate the start of the header value */
|
/* locate the start of the header value */
|
||||||
*s++ = '\0';
|
*s++ = '\0';
|
||||||
@ -366,7 +370,6 @@ static char *URL_escape(const char *str)
|
|||||||
|
|
||||||
static FILE* prepare_ftp_session(FILE **dfpp, struct host_info *target, len_and_sockaddr *lsa)
|
static FILE* prepare_ftp_session(FILE **dfpp, struct host_info *target, len_and_sockaddr *lsa)
|
||||||
{
|
{
|
||||||
char buf[512];
|
|
||||||
FILE *sfp;
|
FILE *sfp;
|
||||||
char *str;
|
char *str;
|
||||||
int port;
|
int port;
|
||||||
@ -375,8 +378,8 @@ static FILE* prepare_ftp_session(FILE **dfpp, struct host_info *target, len_and_
|
|||||||
target->user = xstrdup("anonymous:busybox@");
|
target->user = xstrdup("anonymous:busybox@");
|
||||||
|
|
||||||
sfp = open_socket(lsa);
|
sfp = open_socket(lsa);
|
||||||
if (ftpcmd(NULL, NULL, sfp, buf) != 220)
|
if (ftpcmd(NULL, NULL, sfp) != 220)
|
||||||
bb_error_msg_and_die("%s", sanitize_string(buf+4));
|
bb_error_msg_and_die("%s", sanitize_string(G.wget_buf + 4));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Splitting username:password pair,
|
* Splitting username:password pair,
|
||||||
@ -385,24 +388,24 @@ static FILE* prepare_ftp_session(FILE **dfpp, struct host_info *target, len_and_
|
|||||||
str = strchr(target->user, ':');
|
str = strchr(target->user, ':');
|
||||||
if (str)
|
if (str)
|
||||||
*str++ = '\0';
|
*str++ = '\0';
|
||||||
switch (ftpcmd("USER ", target->user, sfp, buf)) {
|
switch (ftpcmd("USER ", target->user, sfp)) {
|
||||||
case 230:
|
case 230:
|
||||||
break;
|
break;
|
||||||
case 331:
|
case 331:
|
||||||
if (ftpcmd("PASS ", str, sfp, buf) == 230)
|
if (ftpcmd("PASS ", str, sfp) == 230)
|
||||||
break;
|
break;
|
||||||
/* fall through (failed login) */
|
/* fall through (failed login) */
|
||||||
default:
|
default:
|
||||||
bb_error_msg_and_die("ftp login: %s", sanitize_string(buf+4));
|
bb_error_msg_and_die("ftp login: %s", sanitize_string(G.wget_buf + 4));
|
||||||
}
|
}
|
||||||
|
|
||||||
ftpcmd("TYPE I", NULL, sfp, buf);
|
ftpcmd("TYPE I", NULL, sfp);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Querying file size
|
* Querying file size
|
||||||
*/
|
*/
|
||||||
if (ftpcmd("SIZE ", target->path, sfp, buf) == 213) {
|
if (ftpcmd("SIZE ", target->path, sfp) == 213) {
|
||||||
G.content_len = BB_STRTOOFF(buf+4, NULL, 10);
|
G.content_len = BB_STRTOOFF(G.wget_buf + 4, NULL, 10);
|
||||||
if (G.content_len < 0 || errno) {
|
if (G.content_len < 0 || errno) {
|
||||||
bb_error_msg_and_die("SIZE value is garbage");
|
bb_error_msg_and_die("SIZE value is garbage");
|
||||||
}
|
}
|
||||||
@ -412,20 +415,20 @@ static FILE* prepare_ftp_session(FILE **dfpp, struct host_info *target, len_and_
|
|||||||
/*
|
/*
|
||||||
* Entering passive mode
|
* Entering passive mode
|
||||||
*/
|
*/
|
||||||
if (ftpcmd("PASV", NULL, sfp, buf) != 227) {
|
if (ftpcmd("PASV", NULL, sfp) != 227) {
|
||||||
pasv_error:
|
pasv_error:
|
||||||
bb_error_msg_and_die("bad response to %s: %s", "PASV", sanitize_string(buf));
|
bb_error_msg_and_die("bad response to %s: %s", "PASV", sanitize_string(G.wget_buf));
|
||||||
}
|
}
|
||||||
// Response is "227 garbageN1,N2,N3,N4,P1,P2[)garbage]
|
// Response is "227 garbageN1,N2,N3,N4,P1,P2[)garbage]
|
||||||
// Server's IP is N1.N2.N3.N4 (we ignore it)
|
// Server's IP is N1.N2.N3.N4 (we ignore it)
|
||||||
// Server's port for data connection is P1*256+P2
|
// Server's port for data connection is P1*256+P2
|
||||||
str = strrchr(buf, ')');
|
str = strrchr(G.wget_buf, ')');
|
||||||
if (str) str[0] = '\0';
|
if (str) str[0] = '\0';
|
||||||
str = strrchr(buf, ',');
|
str = strrchr(G.wget_buf, ',');
|
||||||
if (!str) goto pasv_error;
|
if (!str) goto pasv_error;
|
||||||
port = xatou_range(str+1, 0, 255);
|
port = xatou_range(str+1, 0, 255);
|
||||||
*str = '\0';
|
*str = '\0';
|
||||||
str = strrchr(buf, ',');
|
str = strrchr(G.wget_buf, ',');
|
||||||
if (!str) goto pasv_error;
|
if (!str) goto pasv_error;
|
||||||
port += xatou_range(str+1, 0, 255) * 256;
|
port += xatou_range(str+1, 0, 255) * 256;
|
||||||
set_nport(lsa, htons(port));
|
set_nport(lsa, htons(port));
|
||||||
@ -433,20 +436,19 @@ static FILE* prepare_ftp_session(FILE **dfpp, struct host_info *target, len_and_
|
|||||||
*dfpp = open_socket(lsa);
|
*dfpp = open_socket(lsa);
|
||||||
|
|
||||||
if (G.beg_range) {
|
if (G.beg_range) {
|
||||||
sprintf(buf, "REST %"OFF_FMT"u", G.beg_range);
|
sprintf(G.wget_buf, "REST %"OFF_FMT"u", G.beg_range);
|
||||||
if (ftpcmd(buf, NULL, sfp, buf) == 350)
|
if (ftpcmd(G.wget_buf, NULL, sfp) == 350)
|
||||||
G.content_len -= G.beg_range;
|
G.content_len -= G.beg_range;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ftpcmd("RETR ", target->path, sfp, buf) > 150)
|
if (ftpcmd("RETR ", target->path, sfp) > 150)
|
||||||
bb_error_msg_and_die("bad response to %s: %s", "RETR", sanitize_string(buf));
|
bb_error_msg_and_die("bad response to %s: %s", "RETR", sanitize_string(G.wget_buf));
|
||||||
|
|
||||||
return sfp;
|
return sfp;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void NOINLINE retrieve_file_data(FILE *dfp, int output_fd)
|
static void NOINLINE retrieve_file_data(FILE *dfp, int output_fd)
|
||||||
{
|
{
|
||||||
char buf[512];
|
|
||||||
#if ENABLE_FEATURE_WGET_STATUSBAR || ENABLE_FEATURE_WGET_TIMEOUT
|
#if ENABLE_FEATURE_WGET_STATUSBAR || ENABLE_FEATURE_WGET_TIMEOUT
|
||||||
# if ENABLE_FEATURE_WGET_TIMEOUT
|
# if ENABLE_FEATURE_WGET_TIMEOUT
|
||||||
unsigned second_cnt;
|
unsigned second_cnt;
|
||||||
@ -468,9 +470,9 @@ static void NOINLINE retrieve_file_data(FILE *dfp, int output_fd)
|
|||||||
int n;
|
int n;
|
||||||
unsigned rdsz;
|
unsigned rdsz;
|
||||||
|
|
||||||
rdsz = sizeof(buf);
|
rdsz = sizeof(G.wget_buf);
|
||||||
if (G.got_clen) {
|
if (G.got_clen) {
|
||||||
if (G.content_len < (off_t)sizeof(buf)) {
|
if (G.content_len < (off_t)sizeof(G.wget_buf)) {
|
||||||
if ((int)G.content_len <= 0)
|
if ((int)G.content_len <= 0)
|
||||||
break;
|
break;
|
||||||
rdsz = (unsigned)G.content_len;
|
rdsz = (unsigned)G.content_len;
|
||||||
@ -493,7 +495,7 @@ static void NOINLINE retrieve_file_data(FILE *dfp, int output_fd)
|
|||||||
progress_meter(PROGRESS_BUMP);
|
progress_meter(PROGRESS_BUMP);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
n = safe_fread(buf, rdsz, dfp);
|
n = safe_fread(G.wget_buf, rdsz, dfp);
|
||||||
if (n <= 0) {
|
if (n <= 0) {
|
||||||
if (ferror(dfp)) {
|
if (ferror(dfp)) {
|
||||||
/* perror will not work: ferror doesn't set errno */
|
/* perror will not work: ferror doesn't set errno */
|
||||||
@ -501,7 +503,7 @@ static void NOINLINE retrieve_file_data(FILE *dfp, int output_fd)
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
xwrite(output_fd, buf, n);
|
xwrite(output_fd, G.wget_buf, n);
|
||||||
#if ENABLE_FEATURE_WGET_STATUSBAR
|
#if ENABLE_FEATURE_WGET_STATUSBAR
|
||||||
G.transferred += n;
|
G.transferred += n;
|
||||||
progress_meter(PROGRESS_BUMP);
|
progress_meter(PROGRESS_BUMP);
|
||||||
@ -513,10 +515,10 @@ static void NOINLINE retrieve_file_data(FILE *dfp, int output_fd)
|
|||||||
if (!G.chunked)
|
if (!G.chunked)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
safe_fgets(buf, sizeof(buf), dfp); /* This is a newline */
|
safe_fgets(G.wget_buf, sizeof(G.wget_buf), dfp); /* This is a newline */
|
||||||
get_clen:
|
get_clen:
|
||||||
safe_fgets(buf, sizeof(buf), dfp);
|
safe_fgets(G.wget_buf, sizeof(G.wget_buf), dfp);
|
||||||
G.content_len = STRTOOFF(buf, NULL, 16);
|
G.content_len = STRTOOFF(G.wget_buf, NULL, 16);
|
||||||
/* FIXME: error check? */
|
/* FIXME: error check? */
|
||||||
if (G.content_len == 0)
|
if (G.content_len == 0)
|
||||||
break; /* all done! */
|
break; /* all done! */
|
||||||
@ -529,7 +531,6 @@ static void NOINLINE retrieve_file_data(FILE *dfp, int output_fd)
|
|||||||
int wget_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
|
int wget_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
|
||||||
int wget_main(int argc UNUSED_PARAM, char **argv)
|
int wget_main(int argc UNUSED_PARAM, char **argv)
|
||||||
{
|
{
|
||||||
char buf[512];
|
|
||||||
struct host_info server, target;
|
struct host_info server, target;
|
||||||
len_and_sockaddr *lsa;
|
len_and_sockaddr *lsa;
|
||||||
unsigned opt;
|
unsigned opt;
|
||||||
@ -709,11 +710,11 @@ int wget_main(int argc UNUSED_PARAM, char **argv)
|
|||||||
#if ENABLE_FEATURE_WGET_AUTHENTICATION
|
#if ENABLE_FEATURE_WGET_AUTHENTICATION
|
||||||
if (target.user) {
|
if (target.user) {
|
||||||
fprintf(sfp, "Proxy-Authorization: Basic %s\r\n"+6,
|
fprintf(sfp, "Proxy-Authorization: Basic %s\r\n"+6,
|
||||||
base64enc_512(buf, target.user));
|
base64enc(target.user));
|
||||||
}
|
}
|
||||||
if (use_proxy && server.user) {
|
if (use_proxy && server.user) {
|
||||||
fprintf(sfp, "Proxy-Authorization: Basic %s\r\n",
|
fprintf(sfp, "Proxy-Authorization: Basic %s\r\n",
|
||||||
base64enc_512(buf, server.user));
|
base64enc(server.user));
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -743,10 +744,10 @@ int wget_main(int argc UNUSED_PARAM, char **argv)
|
|||||||
* Retrieve HTTP response line and check for "200" status code.
|
* Retrieve HTTP response line and check for "200" status code.
|
||||||
*/
|
*/
|
||||||
read_response:
|
read_response:
|
||||||
if (fgets(buf, sizeof(buf), sfp) == NULL)
|
if (fgets(G.wget_buf, sizeof(G.wget_buf), sfp) == NULL)
|
||||||
bb_error_msg_and_die("no response from server");
|
bb_error_msg_and_die("no response from server");
|
||||||
|
|
||||||
str = buf;
|
str = G.wget_buf;
|
||||||
str = skip_non_whitespace(str);
|
str = skip_non_whitespace(str);
|
||||||
str = skip_whitespace(str);
|
str = skip_whitespace(str);
|
||||||
// FIXME: no error check
|
// FIXME: no error check
|
||||||
@ -755,7 +756,7 @@ int wget_main(int argc UNUSED_PARAM, char **argv)
|
|||||||
switch (status) {
|
switch (status) {
|
||||||
case 0:
|
case 0:
|
||||||
case 100:
|
case 100:
|
||||||
while (gethdr(buf, sizeof(buf), sfp /*, &n*/) != NULL)
|
while (gethdr(sfp /*, &n*/) != NULL)
|
||||||
/* eat all remaining headers */;
|
/* eat all remaining headers */;
|
||||||
goto read_response;
|
goto read_response;
|
||||||
case 200:
|
case 200:
|
||||||
@ -795,13 +796,13 @@ However, in real world it was observed that some web servers
|
|||||||
break;
|
break;
|
||||||
/* fall through */
|
/* fall through */
|
||||||
default:
|
default:
|
||||||
bb_error_msg_and_die("server returned error: %s", sanitize_string(buf));
|
bb_error_msg_and_die("server returned error: %s", sanitize_string(G.wget_buf));
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Retrieve HTTP headers.
|
* Retrieve HTTP headers.
|
||||||
*/
|
*/
|
||||||
while ((str = gethdr(buf, sizeof(buf), sfp /*, &n*/)) != NULL) {
|
while ((str = gethdr(sfp /*, &n*/)) != NULL) {
|
||||||
/* gethdr converted "FOO:" string to lowercase */
|
/* gethdr converted "FOO:" string to lowercase */
|
||||||
smalluint key;
|
smalluint key;
|
||||||
/* strip trailing whitespace */
|
/* strip trailing whitespace */
|
||||||
@ -810,7 +811,7 @@ However, in real world it was observed that some web servers
|
|||||||
*s = '\0';
|
*s = '\0';
|
||||||
s--;
|
s--;
|
||||||
}
|
}
|
||||||
key = index_in_strings(keywords, buf) + 1;
|
key = index_in_strings(keywords, G.wget_buf) + 1;
|
||||||
if (key == KEY_content_length) {
|
if (key == KEY_content_length) {
|
||||||
G.content_len = BB_STRTOOFF(str, NULL, 10);
|
G.content_len = BB_STRTOOFF(str, NULL, 10);
|
||||||
if (G.content_len < 0 || errno) {
|
if (G.content_len < 0 || errno) {
|
||||||
@ -881,9 +882,9 @@ However, in real world it was observed that some web servers
|
|||||||
if (dfp != sfp) {
|
if (dfp != sfp) {
|
||||||
/* It's ftp. Close it properly */
|
/* It's ftp. Close it properly */
|
||||||
fclose(dfp);
|
fclose(dfp);
|
||||||
if (ftpcmd(NULL, NULL, sfp, buf) != 226)
|
if (ftpcmd(NULL, NULL, sfp) != 226)
|
||||||
bb_error_msg_and_die("ftp error: %s", sanitize_string(buf+4));
|
bb_error_msg_and_die("ftp error: %s", sanitize_string(G.wget_buf + 4));
|
||||||
/* ftpcmd("QUIT", NULL, sfp, buf); - why bother? */
|
/* ftpcmd("QUIT", NULL, sfp); - why bother? */
|
||||||
}
|
}
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
|
Loading…
Reference in New Issue
Block a user