summaryrefslogtreecommitdiff
path: root/networking
diff options
context:
space:
mode:
Diffstat (limited to 'networking')
-rw-r--r--networking/Config.src16
-rw-r--r--networking/wget.c24
2 files changed, 30 insertions, 10 deletions
diff --git a/networking/Config.src b/networking/Config.src
index e1ae0c9..ca0ddcd 100644
--- a/networking/Config.src
+++ b/networking/Config.src
@@ -970,16 +970,18 @@ config FEATURE_WGET_LONG_OPTIONS
Support long options for the wget applet.
config FEATURE_WGET_TIMEOUT
- bool "Enable read timeout option -T SEC"
+ bool "Enable timeout option -T SEC"
default y
depends on WGET
help
- Supports network read timeout for wget, so that wget will give
- up and timeout when reading network data, through the -T command
- line option. Currently only network data read timeout is
- supported (i.e., timeout is not applied to the DNS nor TCP
- connection initialization). When FEATURE_WGET_LONG_OPTIONS is
- also enabled, the --timeout option will work in addition to -T.
+ Supports network read and connect timeouts for wget,
+ so that wget will give up and timeout, through the -T
+ command line option.
+
+ Currently only connect and network data read timeout are
+ supported (i.e., timeout is not applied to the DNS query). When
+ FEATURE_WGET_LONG_OPTIONS is also enabled, the --timeout option
+ will work in addition to -T.
config ZCIP
bool "zcip"
diff --git a/networking/wget.c b/networking/wget.c
index 5dac2b5..a32f852 100644
--- a/networking/wget.c
+++ b/networking/wget.c
@@ -72,6 +72,7 @@ struct globals {
const char *user_agent; /* "User-Agent" header field */
#if ENABLE_FEATURE_WGET_TIMEOUT
unsigned timeout_seconds;
+ bool connecting;
#endif
int output_fd;
int o_flags;
@@ -87,7 +88,6 @@ struct globals {
#define G (*ptr_to_globals)
#define INIT_G() do { \
SET_PTR_TO_GLOBALS(xzalloc(sizeof(G))); \
- IF_FEATURE_WGET_TIMEOUT(G.timeout_seconds = 900;) \
} while (0)
@@ -195,13 +195,27 @@ static char* sanitize_string(char *s)
return s;
}
+#if ENABLE_FEATURE_WGET_TIMEOUT
+static void alarm_handler(int sig UNUSED_PARAM)
+{
+ /* This is theoretically unsafe (uses stdio and malloc in signal handler) */
+ if (G.connecting)
+ bb_error_msg_and_die("download timed out");
+}
+#endif
+
static FILE *open_socket(len_and_sockaddr *lsa)
{
+ int fd;
FILE *fp;
+ IF_FEATURE_WGET_TIMEOUT(alarm(G.timeout_seconds); G.connecting = 1;)
+ fd = xconnect_stream(lsa);
+ IF_FEATURE_WGET_TIMEOUT(G.connecting = 0;)
+
/* glibc 2.4 seems to try seeking on it - ??! */
/* hopefully it understands what ESPIPE means... */
- fp = fdopen(xconnect_stream(lsa), "r+");
+ fp = fdopen(fd, "r+");
if (fp == NULL)
bb_perror_msg_and_die(bb_msg_memory_exhausted);
@@ -209,6 +223,7 @@ static FILE *open_socket(len_and_sockaddr *lsa)
}
/* Returns '\n' if it was seen, else '\0'. Trims at first '\r' or '\n' */
+/* FIXME: does not respect FEATURE_WGET_TIMEOUT and -T N: */
static char fgets_and_trim(FILE *fp)
{
char c;
@@ -944,7 +959,10 @@ int wget_main(int argc UNUSED_PARAM, char **argv)
INIT_G();
- IF_FEATURE_WGET_TIMEOUT(G.timeout_seconds = 900;)
+#if ENABLE_FEATURE_WGET_TIMEOUT
+ G.timeout_seconds = 900;
+ signal(SIGALRM, alarm_handler);
+#endif
G.proxy_flag = "on"; /* use proxies if env vars are set */
G.user_agent = "Wget"; /* "User-Agent" header field */