On Thu, Jan 25, 2018 at 09:35:33PM -0600, Scott Cheloha wrote:
> Hi,
> 
> This increases the range for sleep(1) from 100 million seconds up to
> 9223372036854775807.
> 
> POSIX.1-2001 added a stipulation (which POSIX.1-2008 retains) that sleep(1)
> support inputs of at least 2147483647 seconds.  This patch fulfills that
> requirement and brings us into alignment with POSIX.1-2008, which we already
> claim anyway.
> 
> FreeBSD supports up to INT_MAX and no further.  GNU sleep keeps seconds
> in a double, so they too ought to support at least this minimum... but
> they do something weird that I haven't quite figured out yet, so I'm
> actually not sure what they support.
> 
> But anyway I don't see a reason to cap user input (as FreeBSD does) at the
> positive 32-bit limit when we already carefully parse up to the limit of
> time_t and check for overflow.  If the end user wants to sleep that long,
> we can just let them.  I have a subsequent patch that tells the user that
> their input is too large in the event of overflow.  Currently we just exit
> with EINVAL and say nothing, which is both unusual and unhelpful.
> 
> Using a loop to extend the input range of the utility seems a bit unclean,
> but this case alone certainly doesn't warrant extending the input range for
> nanosleep(2).
> 
> I'm not sure whether the larger range is actually an extension to the
> standard, and if so whether we need to mention it in the manpage, but
> I've included a diff here anyway just in case.  If you have ideas about
> the wording I'd love to hear them.
> 
> Thoughts?  ok?

The diff for sleep.c is ok.

For the manpage part, I have no strong opinion, but I'm not so sure this
is needed/useful. That sleeping for fractions of a second isn't portable
definitely has practical relevance, sleeping longer than 68 years not so
much. I'll leave this for jmc to decide.

> 
> --
> Scott Cheloha
> 
> Index: bin/sleep/sleep.1
> ===================================================================
> RCS file: /cvs/src/bin/sleep/sleep.1,v
> retrieving revision 1.22
> diff -u -p -r1.22 sleep.1
> --- bin/sleep/sleep.1 16 Aug 2016 18:51:25 -0000      1.22
> +++ bin/sleep/sleep.1 26 Jan 2018 03:22:08 -0000
> @@ -108,8 +108,10 @@ utility is compliant with the
>  .St -p1003.1-2008
>  specification.
>  .Pp
> -The handling of fractional arguments is provided as an extension to that
> -specification.
> +The handling of fractional arguments and the support for values of
> +.Ar seconds
> +greater than 2147483647
> +are extensions to that specification.
>  .Sh HISTORY
>  A
>  .Nm
> Index: bin/sleep/sleep.c
> ===================================================================
> RCS file: /cvs/src/bin/sleep/sleep.c,v
> retrieving revision 1.24
> diff -u -p -r1.24 sleep.c
> --- bin/sleep/sleep.c 11 Oct 2015 20:17:49 -0000      1.24
> +++ bin/sleep/sleep.c 26 Jan 2018 03:22:08 -0000
> @@ -102,12 +102,24 @@ main(int argc, char *argv[])
>               }
>       }
>  
> -     rqtp.tv_sec = secs;
> -     rqtp.tv_nsec = nsecs;
> -
> -     if ((secs > 0) || (nsecs > 0))
> +     while (secs > 0 || nsecs > 0) {
> +             /*
> +              * nanosleep(2) supports a maximum of 100 million
> +              * seconds, so we break the nap up into multiple
> +              * calls if we have more than that.
> +              */
> +             if (secs > 100000000) {
> +                     rqtp.tv_sec = 100000000;
> +                     rqtp.tv_nsec = 0;
> +             } else {
> +                     rqtp.tv_sec = secs;
> +                     rqtp.tv_nsec = nsecs;
> +             }
>               if (nanosleep(&rqtp, NULL))
>                       err(1, NULL);
> +             secs -= rqtp.tv_sec;
> +             nsecs -= rqtp.tv_nsec;
> +     }
>       return (0);
>  }
>  
> 

Reply via email to