mirror of
https://github.com/freebsd/freebsd-src
synced 2024-09-06 09:10:28 +00:00
bin/sleep: add support for multiple delay values
The sleep time is calculated as the sum of all arguments passed. This makes the FreeBSD version of sleep functionally compatible with the version in GNU coreutils. MFC after: 1 week
This commit is contained in:
parent
34978f7edd
commit
be038c3afc
|
@ -32,7 +32,7 @@
|
||||||
.\" @(#)sleep.1 8.3 (Berkeley) 4/18/94
|
.\" @(#)sleep.1 8.3 (Berkeley) 4/18/94
|
||||||
.\" $FreeBSD$
|
.\" $FreeBSD$
|
||||||
.\"
|
.\"
|
||||||
.Dd December 31, 2020
|
.Dd May 24, 2022
|
||||||
.Dt SLEEP 1
|
.Dt SLEEP 1
|
||||||
.Os
|
.Os
|
||||||
.Sh NAME
|
.Sh NAME
|
||||||
|
@ -40,21 +40,21 @@
|
||||||
.Nd suspend execution for an interval of time
|
.Nd suspend execution for an interval of time
|
||||||
.Sh SYNOPSIS
|
.Sh SYNOPSIS
|
||||||
.Nm
|
.Nm
|
||||||
.Ar number[unit]
|
.Ar number[unit] ...
|
||||||
.Sh DESCRIPTION
|
.Sh DESCRIPTION
|
||||||
The
|
The
|
||||||
.Nm
|
.Nm
|
||||||
command
|
command suspends execution for a minimum of
|
||||||
suspends execution for a minimum of
|
|
||||||
.Ar number
|
.Ar number
|
||||||
seconds (the default, or unit
|
seconds (the default, or unit
|
||||||
.Ar s ) ,
|
.Ar s ) ,
|
||||||
or minutes (unit
|
minutes (unit
|
||||||
.Ar m ) ,
|
.Ar m ) ,
|
||||||
hours (unit
|
hours (unit
|
||||||
.Ar h ) ,
|
.Ar h ) ,
|
||||||
or days (unit
|
or days (unit
|
||||||
.Ar d ) .
|
.Ar d ) .
|
||||||
|
If multiple arguments are passed, the delay will be the sum of all values.
|
||||||
.Pp
|
.Pp
|
||||||
If the
|
If the
|
||||||
.Nm
|
.Nm
|
||||||
|
@ -72,9 +72,9 @@ The
|
||||||
.Nm
|
.Nm
|
||||||
command allows and honors a non-integer number of seconds to sleep
|
command allows and honors a non-integer number of seconds to sleep
|
||||||
in any form acceptable by
|
in any form acceptable by
|
||||||
.Xr strtod 3 .
|
.Xr strtod 3 and it accepts more than one delay value.
|
||||||
This is a non-portable extension, but is also implemented in GNU sh-utils
|
These are non-portable extensions, but they have also been implemented
|
||||||
since version 2.0a (released in 2002).
|
in GNU sh-utils since version 2.0a (released in 2002).
|
||||||
.Sh EXIT STATUS
|
.Sh EXIT STATUS
|
||||||
.Ex -std
|
.Ex -std
|
||||||
.Sh EXAMPLES
|
.Sh EXAMPLES
|
||||||
|
|
|
@ -64,34 +64,48 @@ int
|
||||||
main(int argc, char *argv[])
|
main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
struct timespec time_to_sleep;
|
struct timespec time_to_sleep;
|
||||||
double d;
|
double d, seconds;
|
||||||
time_t original;
|
time_t original;
|
||||||
char unit;
|
char unit;
|
||||||
char buf[2];
|
char buf[2];
|
||||||
|
int i, matches;
|
||||||
|
|
||||||
if (caph_limit_stdio() < 0 || caph_enter() < 0)
|
if (caph_limit_stdio() < 0 || caph_enter() < 0)
|
||||||
err(1, "capsicum");
|
err(1, "capsicum");
|
||||||
|
|
||||||
if (argc != 2)
|
if (argc < 2)
|
||||||
usage();
|
usage();
|
||||||
|
|
||||||
if (sscanf(argv[1], "%lf%c%1s", &d, &unit, buf) == 2)
|
seconds = 0;
|
||||||
switch(unit) {
|
for (i = 1; i < argc; i++) {
|
||||||
case 'd': d *= 24;
|
matches = sscanf(argv[i], "%lf%c%1s", &d, &unit, buf);
|
||||||
case 'h': d *= 60;
|
if (matches == 2)
|
||||||
case 'm': d *= 60;
|
switch(unit) {
|
||||||
case 's': break;
|
case 'd':
|
||||||
default: usage();
|
d *= 24;
|
||||||
}
|
/* FALLTHROUGH */
|
||||||
else
|
case 'h':
|
||||||
if (sscanf(argv[1], "%lf%1s", &d, buf) != 1)
|
d *= 60;
|
||||||
usage();
|
/* FALLTHROUGH */
|
||||||
if (d > INT_MAX)
|
case 'm':
|
||||||
|
d *= 60;
|
||||||
|
/* FALLTHROUGH */
|
||||||
|
case 's':
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
usage();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
if (matches != 1)
|
||||||
|
usage();
|
||||||
|
seconds += d;
|
||||||
|
}
|
||||||
|
if (seconds > INT_MAX)
|
||||||
usage();
|
usage();
|
||||||
if (d <= 0)
|
if (seconds <= 0)
|
||||||
return (0);
|
return (0);
|
||||||
original = time_to_sleep.tv_sec = (time_t)d;
|
original = time_to_sleep.tv_sec = (time_t)seconds;
|
||||||
time_to_sleep.tv_nsec = 1e9 * (d - time_to_sleep.tv_sec);
|
time_to_sleep.tv_nsec = 1e9 * (seconds - time_to_sleep.tv_sec);
|
||||||
|
|
||||||
signal(SIGINFO, report_request);
|
signal(SIGINFO, report_request);
|
||||||
|
|
||||||
|
@ -116,7 +130,7 @@ static void
|
||||||
usage(void)
|
usage(void)
|
||||||
{
|
{
|
||||||
|
|
||||||
fprintf(stderr, "usage: sleep number[unit]\n");
|
fprintf(stderr, "usage: sleep number[unit] ...\n");
|
||||||
fprintf(stderr, "Unit can be 's' (seconds, the default), "
|
fprintf(stderr, "Unit can be 's' (seconds, the default), "
|
||||||
"m (minutes), h (hours), or d (days).\n");
|
"m (minutes), h (hours), or d (days).\n");
|
||||||
exit(1);
|
exit(1);
|
||||||
|
|
Loading…
Reference in a new issue