mirror of
https://github.com/mirror/wget.git
synced 2024-12-29 14:30:48 +08:00
[svn] New function xsleep that resumes sleeps interrupted by signals
on systems that support nanosleep.
This commit is contained in:
parent
2f2939d23e
commit
8cd9b4cd8a
@ -1,3 +1,7 @@
|
||||
2003-11-03 Hrvoje Niksic <hniksic@xemacs.org>
|
||||
|
||||
* configure.in: Check for nanosleep.
|
||||
|
||||
2003-03-09 Nicolas Schodet <contact@ni.fr.eu.org>
|
||||
|
||||
* Makefile.in: Fixed bad configure.bat scrdir.
|
||||
|
@ -194,7 +194,7 @@ AC_FUNC_MMAP
|
||||
AC_CHECK_FUNCS(strdup strstr strcasecmp strncasecmp strpbrk memmove)
|
||||
AC_CHECK_FUNCS(gettimeofday mktime strptime strerror snprintf vsnprintf)
|
||||
AC_CHECK_FUNCS(select sigblock sigsetjmp signal symlink access isatty)
|
||||
AC_CHECK_FUNCS(uname gethostname usleep)
|
||||
AC_CHECK_FUNCS(uname gethostname nanosleep usleep)
|
||||
|
||||
dnl
|
||||
dnl Check if we need to compile in getopt.c.
|
||||
|
@ -1,3 +1,9 @@
|
||||
2003-11-03 Hrvoje Niksic <hniksic@xemacs.org>
|
||||
|
||||
* utils.c (xsleep): New function. Uses nanosleep where available,
|
||||
resuming sleeps interrupted by signals. Updated callers of sleep
|
||||
and usleep to use xsleep.
|
||||
|
||||
2003-11-03 Hrvoje Niksic <hniksic@xemacs.org>
|
||||
|
||||
* ftp-basic.c (ftp_login): Remove shadowing (and bogus)
|
||||
|
20
src/cmpt.c
20
src/cmpt.c
@ -1431,26 +1431,6 @@ const unsigned short int __mon_yday[2][13] =
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_USLEEP
|
||||
#ifndef WINDOWS
|
||||
|
||||
/* A simple usleep implementation based on select(). For Unix and
|
||||
Unix-like systems. */
|
||||
|
||||
int
|
||||
usleep (unsigned long usec)
|
||||
{
|
||||
struct timeval tm;
|
||||
tm.tv_sec = 0;
|
||||
tm.tv_usec = usec;
|
||||
select (0, NULL, NULL, NULL, &tm);
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif /* not WINDOWS */
|
||||
#endif /* not HAVE_USLEEP */
|
||||
|
||||
|
||||
/* Currently unused in Wget. Uncomment if we start using memmove
|
||||
again. */
|
||||
#if 0
|
||||
|
@ -191,6 +191,9 @@ char *alloca ();
|
||||
/* Define if you have the usleep function. */
|
||||
#undef HAVE_USLEEP
|
||||
|
||||
/* Define if you have the nanosleep function. */
|
||||
#undef HAVE_NANOSLEEP
|
||||
|
||||
/* Define if you have the <string.h> header file. */
|
||||
#undef HAVE_STRING_H
|
||||
|
||||
|
@ -74,35 +74,23 @@ static DWORD set_sleep_mode (DWORD mode);
|
||||
static DWORD pwr_mode = 0;
|
||||
static int windows_nt_p;
|
||||
|
||||
#ifndef HAVE_SLEEP
|
||||
/* Windows version of xsleep in utils.c. */
|
||||
|
||||
/* Emulation of Unix sleep. */
|
||||
|
||||
unsigned int
|
||||
sleep (unsigned seconds)
|
||||
void
|
||||
xsleep (double seconds)
|
||||
{
|
||||
return SleepEx (1000 * seconds, TRUE) ? 0U : 1000 * seconds;
|
||||
#ifdef HAVE_USLEEP
|
||||
if (seconds > 1000)
|
||||
{
|
||||
/* Explained in utils.c. */
|
||||
sleep (seconds);
|
||||
seconds -= (long) seconds;
|
||||
}
|
||||
usleep (seconds * 1000000L);
|
||||
#else /* not HAVE_USLEEP */
|
||||
SleepEx (seconds * 1000, FALSE);
|
||||
#endif /* not HAVE_USLEEP */
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_USLEEP
|
||||
/* Emulation of Unix usleep(). This has a granularity of
|
||||
milliseconds, but that's ok because:
|
||||
|
||||
a) Wget is only using it with milliseconds [not anymore, but b)
|
||||
still applies];
|
||||
|
||||
b) You can't rely on usleep's granularity anyway. If a caller
|
||||
expects usleep to respect every microsecond, he's in for a
|
||||
surprise. */
|
||||
|
||||
int
|
||||
usleep (unsigned long usec)
|
||||
{
|
||||
SleepEx (usec / 1000, TRUE);
|
||||
return 0;
|
||||
}
|
||||
#endif /* HAVE_USLEEP */
|
||||
|
||||
void
|
||||
windows_main_junk (int *argc, char **argv, char **exec_name)
|
||||
|
10
src/retr.c
10
src/retr.c
@ -114,7 +114,7 @@ limit_bandwidth (long bytes, double *dltime, struct wget_timer *timer)
|
||||
slp, limit_data.chunk_bytes, limit_data.sleep_adjust));
|
||||
|
||||
t0 = *dltime;
|
||||
usleep ((unsigned long) (1000 * slp));
|
||||
xsleep (slp / 1000);
|
||||
t1 = wtimer_elapsed (timer);
|
||||
|
||||
/* Due to scheduling, we probably slept slightly longer (or
|
||||
@ -642,9 +642,9 @@ sleep_between_retrievals (int count)
|
||||
/* If opt.waitretry is specified and this is a retry, wait for
|
||||
COUNT-1 number of seconds, or for opt.waitretry seconds. */
|
||||
if (count <= opt.waitretry)
|
||||
sleep (count - 1);
|
||||
xsleep (count - 1);
|
||||
else
|
||||
usleep (1000000L * opt.waitretry);
|
||||
xsleep (opt.waitretry);
|
||||
}
|
||||
else if (opt.wait)
|
||||
{
|
||||
@ -652,7 +652,7 @@ sleep_between_retrievals (int count)
|
||||
/* If random-wait is not specified, or if we are sleeping
|
||||
between retries of the same download, sleep the fixed
|
||||
interval. */
|
||||
usleep (1000000L * opt.wait);
|
||||
xsleep (opt.wait);
|
||||
else
|
||||
{
|
||||
/* Sleep a random amount of time averaging in opt.wait
|
||||
@ -661,7 +661,7 @@ sleep_between_retrievals (int count)
|
||||
double waitsecs = 2 * opt.wait * random_float ();
|
||||
DEBUGP (("sleep_between_retrievals: avg=%f,sleep=%f\n",
|
||||
opt.wait, waitsecs));
|
||||
usleep (1000000L * waitsecs);
|
||||
xsleep (waitsecs);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -183,9 +183,6 @@ int snprintf ();
|
||||
#ifndef HAVE_VSNPRINTF
|
||||
int vsnprintf ();
|
||||
#endif
|
||||
#ifndef HAVE_USLEEP
|
||||
int usleep PARAMS ((unsigned long));
|
||||
#endif
|
||||
#ifndef HAVE_MEMMOVE
|
||||
void *memmove ();
|
||||
#endif
|
||||
|
52
src/utils.c
52
src/utils.c
@ -1851,3 +1851,55 @@ run_with_timeout (double timeout, void (*fun) (void *), void *arg)
|
||||
}
|
||||
#endif /* not WINDOWS */
|
||||
#endif /* not USE_SIGNAL_TIMEOUT */
|
||||
|
||||
#ifndef WINDOWS
|
||||
|
||||
/* Sleep the specified amount of seconds. On machines without
|
||||
nanosleep(), this may sleep shorter if interrupted by signals. */
|
||||
|
||||
void
|
||||
xsleep (double seconds)
|
||||
{
|
||||
#ifdef HAVE_NANOSLEEP
|
||||
/* nanosleep is the preferred interface because it offers high
|
||||
accuracy and, more importantly, because it allows us to reliably
|
||||
restart after having been interrupted by a signal such as
|
||||
SIGWINCH. */
|
||||
struct timespec sleep, remaining;
|
||||
sleep.tv_sec = (long) seconds;
|
||||
sleep.tv_nsec = 1000000000L * (seconds - (long) seconds);
|
||||
while (nanosleep (&sleep, &remaining) < 0 && errno == EINTR)
|
||||
/* If nanosleep has been interrupted by a signal, adjust the
|
||||
sleeping period and return to sleep. */
|
||||
sleep = remaining;
|
||||
#else /* not HAVE_NANOSLEEP */
|
||||
#ifdef HAVE_USLEEP
|
||||
/* If usleep is available, use it in preference to select. */
|
||||
if (seconds > 1000)
|
||||
{
|
||||
/* usleep apparently accepts unsigned long, which means it can't
|
||||
sleep longer than ~70 min (35min if signed). If the period
|
||||
is larger than what usleep can safely handle, use sleep
|
||||
first, then add usleep for subsecond accuracy. */
|
||||
sleep (seconds);
|
||||
seconds -= (long) seconds;
|
||||
}
|
||||
usleep (seconds * 1000000L);
|
||||
#else /* not HAVE_USLEEP */
|
||||
#ifdef HAVE_SELECT
|
||||
struct timeval sleep;
|
||||
sleep.tv_sec = (long) seconds;
|
||||
sleep.tv_usec = 1000000L * (seconds - (long) seconds);
|
||||
select (0, NULL, NULL, NULL, &sleep);
|
||||
/* If select returns -1 and errno is EINTR, it means we were
|
||||
interrupted by a signal. But without knowing how long we've
|
||||
actually slept, we can't return to sleep. Using gettimeofday to
|
||||
track sleeps is slow and unreliable due to clock skew. */
|
||||
#else /* not HAVE_SELECT */
|
||||
sleep (seconds);
|
||||
#endif /* not HAVE_SELECT */
|
||||
#endif /* not HAVE_USLEEP */
|
||||
#endif /* not HAVE_NANOSLEEP */
|
||||
}
|
||||
|
||||
#endif /* not WINDOWS */
|
||||
|
@ -121,5 +121,6 @@ int random_number PARAMS ((int));
|
||||
double random_float PARAMS ((void));
|
||||
|
||||
int run_with_timeout PARAMS ((double, void (*) (void *), void *));
|
||||
void xsleep PARAMS ((double));
|
||||
|
||||
#endif /* UTILS_H */
|
||||
|
Loading…
Reference in New Issue
Block a user