On Sun, Jan 12, 2020 at 01:42:44PM +0100, Martin Pieuchot wrote:
> The consensus is now to switch syscall doing sleeps to use tsleep_nsec(9).
> Our direct goal is to stop expressing time as ticks, more might come
> later.
>
> Diff below introduces the previously discussed TIMESPEC_TO_NSEC(9) macro
> and makes use of it in 3 syscalls.
>
> Comments?  Oks?

OK bluhm@

> Index: kern/kern_sig.c
> ===================================================================
> RCS file: /cvs/src/sys/kern/kern_sig.c,v
> retrieving revision 1.240
> diff -u -p -r1.240 kern_sig.c
> --- kern/kern_sig.c   8 Jan 2020 16:27:41 -0000       1.240
> +++ kern/kern_sig.c   12 Jan 2020 12:36:40 -0000
> @@ -1699,7 +1699,7 @@ sys___thrsigdivert(struct proc *p, void
>       sigset_t *m;
>       sigset_t mask = SCARG(uap, sigmask) &~ sigcantmask;
>       siginfo_t si;
> -     uint64_t to_ticks = 0;
> +     uint64_t nsecs = INFSLP;
>       int timeinvalid = 0;
>       int error = 0;
>
> @@ -1715,14 +1715,8 @@ sys___thrsigdivert(struct proc *p, void
>  #endif
>               if (!timespecisvalid(&ts))
>                       timeinvalid = 1;
> -             else {
> -                     to_ticks = (uint64_t)hz * ts.tv_sec +
> -                         ts.tv_nsec / (tick * 1000);
> -                     if (to_ticks > INT_MAX)
> -                             to_ticks = INT_MAX;
> -                     if (to_ticks == 0 && ts.tv_nsec)
> -                             to_ticks = 1;
> -             }
> +             else
> +                     nsecs = TIMESPEC_TO_NSEC(&ts);
>       }
>
>       dosigsuspend(p, p->p_sigmask &~ mask);
> @@ -1749,14 +1743,14 @@ sys___thrsigdivert(struct proc *p, void
>               if (timeinvalid)
>                       error = EINVAL;
>
> -             if (SCARG(uap, timeout) != NULL && to_ticks == 0)
> +             if (SCARG(uap, timeout) != NULL && nsecs == INFSLP)
>                       error = EAGAIN;
>
>               if (error != 0)
>                       break;
>
> -             error = tsleep(&sigwaitsleep, PPAUSE|PCATCH, "sigwait",
> -                 (int)to_ticks);
> +             error = tsleep_nsec(&sigwaitsleep, PPAUSE|PCATCH, "sigwait",
> +                 nsecs);
>       }
>
>       if (error == 0) {
> Index: kern/sys_futex.c
> ===================================================================
> RCS file: /cvs/src/sys/kern/sys_futex.c,v
> retrieving revision 1.13
> diff -u -p -r1.13 sys_futex.c
> --- kern/sys_futex.c  10 Jul 2019 15:52:17 -0000      1.13
> +++ kern/sys_futex.c  31 Dec 2019 10:19:49 -0000
> @@ -213,7 +213,7 @@ futex_wait(uint32_t *uaddr, uint32_t val
>  {
>       struct proc *p = curproc;
>       struct futex *f;
> -     uint64_t to_ticks = 0;
> +     uint64_t nsecs = INFSLP;
>       uint32_t cval;
>       int error;
>
> @@ -244,17 +244,14 @@ futex_wait(uint32_t *uaddr, uint32_t val
>  #endif
>               if (ts.tv_sec < 0 || !timespecisvalid(&ts))
>                       return EINVAL;
> -             to_ticks = (uint64_t)hz * ts.tv_sec +
> -                 (ts.tv_nsec + tick * 1000 - 1) / (tick * 1000) + 1;
> -             if (to_ticks > INT_MAX)
> -                     to_ticks = INT_MAX;
> +             nsecs = TIMESPEC_TO_NSEC(&ts);
>       }
>
>       f = futex_get(uaddr, flags | FT_CREATE);
>       TAILQ_INSERT_TAIL(&f->ft_threads, p, p_fut_link);
>       p->p_futex = f;
>
> -     error = rwsleep(p, &ftlock, PWAIT|PCATCH, "fsleep", (int)to_ticks);
> +     error = rwsleep_nsec(p, &ftlock, PWAIT|PCATCH, "fsleep", nsecs);
>       if (error == ERESTART)
>               error = ECANCELED;
>       else if (error == EWOULDBLOCK) {
> Index: kern/kern_synch.c
> ===================================================================
> RCS file: /cvs/src/sys/kern/kern_synch.c,v
> retrieving revision 1.156
> diff -u -p -r1.156 kern_synch.c
> --- kern/kern_synch.c 12 Jan 2020 00:01:12 -0000      1.156
> +++ kern/kern_synch.c 12 Jan 2020 11:42:20 -0000
> @@ -641,7 +641,7 @@ thrsleep(struct proc *p, struct sys___th
>       long ident = (long)SCARG(uap, ident);
>       struct timespec *tsp = (struct timespec *)SCARG(uap, tp);
>       void *lock = SCARG(uap, lock);
> -     uint64_t to_ticks = 0;
> +     uint64_t nsecs = INFSLP;
>       int abort, error;
>       clockid_t clock_id = SCARG(uap, clock_id);
>
> @@ -665,10 +665,7 @@ thrsleep(struct proc *p, struct sys___th
>               }
>
>               timespecsub(tsp, &now, tsp);
> -             to_ticks = (uint64_t)hz * tsp->tv_sec +
> -                 (tsp->tv_nsec + tick * 1000 - 1) / (tick * 1000) + 1;
> -             if (to_ticks > INT_MAX)
> -                     to_ticks = INT_MAX;
> +             nsecs = TIMESPEC_TO_NSEC(tsp);
>       }
>
>       p->p_thrslpid = ident;
> @@ -692,8 +689,7 @@ thrsleep(struct proc *p, struct sys___th
>               void *sleepaddr = &p->p_thrslpid;
>               if (ident == -1)
>                       sleepaddr = &globalsleepaddr;
> -             error = tsleep(sleepaddr, PWAIT|PCATCH, "thrsleep",
> -                 (int)to_ticks);
> +             error = tsleep_nsec(sleepaddr, PWAIT|PCATCH, "thrsleep", nsecs);
>       }
>
>  out:
> Index: sys/time.h
> ===================================================================
> RCS file: /cvs/src/sys/sys/time.h,v
> retrieving revision 1.48
> diff -u -p -r1.48 time.h
> --- sys/time.h        1 Jan 2020 14:09:59 -0000       1.48
> +++ sys/time.h        12 Jan 2020 12:21:33 -0000
> @@ -370,6 +383,14 @@ USEC_TO_NSEC(uint64_t microseconds)
>       if (microseconds > UINT64_MAX / 1000ULL)
>               return UINT64_MAX;
>       return microseconds * 1000ULL;
> +}
> +
> +static inline uint64_t
> +TIMESPEC_TO_NSEC(const struct timespec *ts)
> +{
> +     if (ts->tv_sec > (UINT64_MAX - ts->tv_nsec) / 1000000000ULL)
> +             return UINT64_MAX;
> +     return ts->tv_sec * 1000000000ULL + ts->tv_nsec;
>  }
>
>  #else /* !_KERNEL */

Reply via email to