Module Name: src
Committed By: riastradh
Date: Mon May 11 03:59:33 UTC 2020
Modified Files:
src/share/man/man9: condvar.9
src/sys/kern: kern_condvar.c subr_time.c
src/sys/sys: condvar.h timevar.h
Log Message:
Remove timedwaitclock.
This did not fix the bug I hoped it would fix in futex, and needs
more design thought. Might redo it somewhat differently later.
To generate a diff of this commit:
cvs rdiff -u -r1.27 -r1.28 src/share/man/man9/condvar.9
cvs rdiff -u -r1.51 -r1.52 src/sys/kern/kern_condvar.c
cvs rdiff -u -r1.23 -r1.24 src/sys/kern/subr_time.c
cvs rdiff -u -r1.16 -r1.17 src/sys/sys/condvar.h
cvs rdiff -u -r1.43 -r1.44 src/sys/sys/timevar.h
Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.
Modified files:
Index: src/share/man/man9/condvar.9
diff -u src/share/man/man9/condvar.9:1.27 src/share/man/man9/condvar.9:1.28
--- src/share/man/man9/condvar.9:1.27 Sun May 3 04:06:15 2020
+++ src/share/man/man9/condvar.9 Mon May 11 03:59:33 2020
@@ -1,4 +1,4 @@
-.\" $NetBSD: condvar.9,v 1.27 2020/05/03 04:06:15 riastradh Exp $
+.\" $NetBSD: condvar.9,v 1.28 2020/05/11 03:59:33 riastradh Exp $
.\"
.\" Copyright (c) 2006, 2007, 2008, 2020 The NetBSD Foundation, Inc.
.\" All rights reserved.
@@ -65,13 +65,6 @@
.Ft int
.Fn cv_timedwaitbt_sig "kcondvar_t *cv" "kmutex_t *mtx" "struct bintime *bt" \
"const struct bintime *epsilon"
-.Ft int
-.Fn cv_timedwaitclock "kcondvar_t *cv" "kmutex_t *mtx" \
-"struct timespec *timeout" "clockid_t clockid" "int flags" \
-"const struct bintime *epsilon"
-.Fn cv_timedwaitclock_sig "kcondvar_t *cv" "kmutex_t *mtx" \
-"struct timespec *timeout" "clockid_t clockid" "int flags" \
-"const struct bintime *epsilon"
.Ft void
.Fn cv_signal "kcondvar_t *cv"
.Ft void
@@ -264,47 +257,6 @@ However, the system is still limited by
resolution and by scheduling competition, which may delay the wakeup by
more than
.Fa bt Li "+" Fa epsilon .
-.It Fn cv_timedwaitclock "cv" "lock" "timeout" "clockid" "flags" "epsilon"
-.It Fn cv_timedwaitclock_sig "cv" "lock" "timeout" "clockid" "flags" "epsilon"
-As per
-.Fn cv_wait
-and
-.Fn cv_wait_sig ,
-but will return early in case of timeout.
-The timeout is measured by the clock
-.Fa clockid ;
-see
-.Xr clock_settime 2
-for the supported options.
-The
-.Fa flags
-may be
-.Dv TIMER_RELTIME
-for a relative duration or
-.Dv TIMER_ABSTIME
-for an absolute time on the clock.
-For relative timeouts,
-.Fn cv_timedwaitclock
-and
-.Fn cv_timedwaitclock_sig
-subtract the elapsed time from
-.Fa timeout
-in place, or set it to zero if there is no time remaining.
-The hint
-.Fa epsilon
-requests a maximum delay after the timeout before wakeup.
-.Pp
-It is safe to pass in values of
-.Fa clockid
-and
-.Fa flags
-from userland, and timeouts copied in from userland; if anything is
-wrong with them,
-.Fn cv_timedwaitclock
-or
-.Fn cv_timedwaitclock_sig
-will return
-.Er EINVAL .
.It Fn cv_signal "cv"
.Pp
Awaken one LWP waiting on the specified condition variable.
@@ -380,29 +332,6 @@ Consuming a resource:
consume(res);
.Ed
.Pp
-Consuming a resource using a timeout specified in a syscall by
-userland:
-.Bd -literal
- struct timespec timeout;
-
- error = copyin(SCARG(uap, timeout), &timeout, sizeof timeout);
- if (error)
- return error;
-
- mutex_enter(&res->mutex);
- while (res->state == BUSY) {
- error = cv_timedwaitclock_sig(&res->condvar,
- &res->mutex, &timeout, SCARG(uap, clock_id),
- SCARG(uap, flags), DEFAULT_TIMEOUT_EPSILON);
- if (error)
- break;
- }
- mutex_exit(&res->mutex);
- if (error)
- return error;
- consume(res);
-.Ed
-.Pp
Releasing a resource for the next consumer to use:
.Bd -literal
mutex_enter(&res->mutex);
@@ -442,9 +371,3 @@ and
.Fn cv_timedwaitbt_sig
primitives first appeared in
.Nx 9.0 .
-The
-.Fn cv_timedwaitclock
-and
-.Fn cv_timedwaitclock_sig
-primitives first appeared in
-.Nx 10.0 .
Index: src/sys/kern/kern_condvar.c
diff -u src/sys/kern/kern_condvar.c:1.51 src/sys/kern/kern_condvar.c:1.52
--- src/sys/kern/kern_condvar.c:1.51 Mon May 4 18:23:37 2020
+++ src/sys/kern/kern_condvar.c Mon May 11 03:59:33 2020
@@ -1,4 +1,4 @@
-/* $NetBSD: kern_condvar.c,v 1.51 2020/05/04 18:23:37 riastradh Exp $ */
+/* $NetBSD: kern_condvar.c,v 1.52 2020/05/11 03:59:33 riastradh Exp $ */
/*-
* Copyright (c) 2006, 2007, 2008, 2019, 2020 The NetBSD Foundation, Inc.
@@ -34,7 +34,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: kern_condvar.c,v 1.51 2020/05/04 18:23:37 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: kern_condvar.c,v 1.52 2020/05/11 03:59:33 riastradh Exp $");
#include <sys/param.h>
#include <sys/systm.h>
@@ -245,75 +245,6 @@ cv_timedwait_sig(kcondvar_t *cv, kmutex_
}
/*
- * cv_timedwaitclock:
- *
- * Wait on a condition variable until awoken normally, or the
- * specified timeout expires according to the provided clock.
- * Returns zero if awoken normally or EWOULDBLOCK if the timeout
- * expired. For relative timeouts ((flags & TIMER_ABSTIME) == 0),
- * updates timeout with the time left.
- *
- * timeout == NULL specifies an infinite timeout. epsilon is a
- * requested maximum error in timeout (excluding spurious
- * wakeups).
- */
-int
-cv_timedwaitclock(kcondvar_t *cv, kmutex_t *mtx, struct timespec *timeout,
- clockid_t clockid, int flags, const struct bintime *epsilon)
-{
- struct timedwaitclock T;
- int timo;
- int error;
-
- if (timeout == NULL) {
- cv_wait(cv, mtx);
- return 0;
- }
-
- timedwaitclock_setup(&T, timeout, clockid, flags, epsilon);
- error = timedwaitclock_begin(&T, &timo);
- if (error)
- return error;
- error = cv_timedwait(cv, mtx, timo);
- timedwaitclock_end(&T);
- return error;
-}
-
-/*
- * cv_timedwaitclock_sig:
- *
- * Wait on a condition variable until awoken normally, interrupted
- * by a signal, or the specified timeout expires according to the
- * provided clock. Returns zero if awoken normally,
- * EINTR/ERESTART if interrupted by a signal, or EWOULDBLOCK if
- * the timeout expired. For relative timeouts ((flags &
- * TIMER_ABSTIME) == 0), updates timeout with the time left.
- *
- * timeout == NULL specifies an infinite timeout. epsilon is a
- * requested maximum error in timeout (excluding spurious
- * wakeups).
- */
-int
-cv_timedwaitclock_sig(kcondvar_t *cv, kmutex_t *mtx, struct timespec *timeout,
- clockid_t clockid, int flags, const struct bintime *epsilon)
-{
- struct timedwaitclock T;
- int timo;
- int error;
-
- if (timeout == NULL)
- return cv_wait_sig(cv, mtx);
-
- timedwaitclock_setup(&T, timeout, clockid, flags, epsilon);
- error = timedwaitclock_begin(&T, &timo);
- if (error)
- return error;
- error = cv_timedwait_sig(cv, mtx, timo);
- timedwaitclock_end(&T);
- return error;
-}
-
-/*
* Given a number of seconds, sec, and 2^64ths of a second, frac, we
* want a number of ticks for a timeout:
*
Index: src/sys/kern/subr_time.c
diff -u src/sys/kern/subr_time.c:1.23 src/sys/kern/subr_time.c:1.24
--- src/sys/kern/subr_time.c:1.23 Mon May 4 18:23:37 2020
+++ src/sys/kern/subr_time.c Mon May 11 03:59:33 2020
@@ -1,4 +1,4 @@
-/* $NetBSD: subr_time.c,v 1.23 2020/05/04 18:23:37 riastradh Exp $ */
+/* $NetBSD: subr_time.c,v 1.24 2020/05/11 03:59:33 riastradh Exp $ */
/*
* Copyright (c) 1982, 1986, 1989, 1993
@@ -33,7 +33,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: subr_time.c,v 1.23 2020/05/04 18:23:37 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: subr_time.c,v 1.24 2020/05/11 03:59:33 riastradh Exp $");
#include <sys/param.h>
#include <sys/kernel.h>
@@ -354,141 +354,3 @@ ts2timo(clockid_t clock_id, int flags, s
return 0;
}
-
-/*
- * timedwaitclock_setup(T, timeout, clockid, flags, epsilon)
- *
- * Initialize state for a timedwaitclock, to be used subsequently
- * with timedwaitclock_begin/end, possibly many times in a row.
- *
- * No cleanup action required at the end; the caller-allocated
- * (typically stack-allocated) timedwaitclock just holds
- * parameters and a little state for timedwaitclock_begin/end.
- */
-void
-timedwaitclock_setup(struct timedwaitclock *T, struct timespec *timeout,
- clockid_t clockid, int flags, const struct bintime *epsilon)
-{
-
- memset(T, 0, sizeof(*T));
- T->timeout = timeout;
- T->clockid = clockid;
- T->flags = flags;
- T->epsilon = epsilon;
- T->starttime = (struct timespec){0,0};
-}
-
-/*
- * timedwaitclock_begin(T, timo)
- *
- * Decide how many ticks to wait for the timedwaitclock T and
- * store it in *timo. Keep state for timedwaitclock_end. May
- * fail with EINVAL if the specified timeout is invalid, or if the
- * specified clock fails. Fails with ETIMEDOUT if there is no
- * time left to wait.
- */
-int
-timedwaitclock_begin(struct timedwaitclock *T, int *timo)
-{
- struct timespec delta;
- const struct timespec *deltap;
- int error;
-
- /* Sanity-check timeout -- may have come from userland. */
- if (T->timeout->tv_nsec < 0 || T->timeout->tv_nsec >= 1000000000L)
- return EINVAL;
-
- /*
- * Compute the time delta.
- */
- if ((T->flags & TIMER_ABSTIME) == TIMER_ABSTIME) {
- /* Check our watch. */
- error = clock_gettime1(T->clockid, &T->starttime);
- if (error)
- return error;
-
- /* If the deadline has passed, we're done. */
- if (timespeccmp(T->timeout, &T->starttime, <=))
- return ETIMEDOUT;
-
- /* Count how much time is left. */
- timespecsub(T->timeout, &T->starttime, &delta);
- deltap = δ
- } else {
- /* The user specified how much time is left. */
- deltap = T->timeout;
-
- /* If there's none left, we've timed out. */
- if (deltap->tv_sec == 0 && deltap->tv_nsec == 0)
- return ETIMEDOUT;
- }
-
- /*
- * Convert to ticks, but clamp to be >=1.
- *
- * XXX In the tickless future, use a high-resolution timer if
- * timo would round to zero.
- */
- *timo = tstohz(deltap);
- KASSERTMSG(*timo >= 0, "negative ticks: %d", *timo);
- if (*timo == 0)
- *timo = 1;
-
- /* Success! */
- return 0;
-}
-
-/*
- * timedwaitclock_end(T)
- *
- * If the timedwaitclock T was relative, update the caller's
- * original timeout to reflect how much time is left, or zero if
- * there is no time left or if the clock has gone bad, so that the
- * next timedwaitclock_begin will immediately time out.
- */
-void
-timedwaitclock_end(struct timedwaitclock *T)
-{
- struct timespec endtime, delta;
-
- /* If the timeout is absolute, nothing to do. */
- if ((T->flags & TIMER_ABSTIME) == TIMER_ABSTIME)
- return;
-
- /*
- * Check our watch. If anything goes wrong with it, make sure
- * that the next time we immediately time out rather than fail
- * to deduct the time elapsed.
- */
- if (clock_gettime1(T->clockid, &endtime)) {
- T->timeout->tv_sec = 0;
- T->timeout->tv_nsec = 0;
- return;
- }
-
- /* Find how much time elapsed while we waited. */
- timespecsub(&endtime, &T->starttime, &delta);
-
- /*
- * Paranoia: If the clock went backwards, treat it as if no
- * time elapsed at all rather than adding anything.
- */
- if (delta.tv_sec < 0 ||
- (delta.tv_sec == 0 && delta.tv_nsec < 0)) {
- delta.tv_sec = 0;
- delta.tv_nsec = 0;
- }
-
- /*
- * Set it to the time left, or zero, whichever is larger. We
- * do not fail with EWOULDBLOCK here because this may have been
- * an explicit wakeup, so the caller needs to check before they
- * give up or else cv_signal would be lost.
- */
- if (timespeccmp(T->timeout, &delta, <=)) {
- T->timeout->tv_sec = 0;
- T->timeout->tv_nsec = 0;
- } else {
- timespecsub(T->timeout, &delta, T->timeout);
- }
-}
Index: src/sys/sys/condvar.h
diff -u src/sys/sys/condvar.h:1.16 src/sys/sys/condvar.h:1.17
--- src/sys/sys/condvar.h:1.16 Sun May 3 01:24:37 2020
+++ src/sys/sys/condvar.h Mon May 11 03:59:33 2020
@@ -1,4 +1,4 @@
-/* $NetBSD: condvar.h,v 1.16 2020/05/03 01:24:37 riastradh Exp $ */
+/* $NetBSD: condvar.h,v 1.17 2020/05/11 03:59:33 riastradh Exp $ */
/*-
* Copyright (c) 2006, 2007, 2008, 2020 The NetBSD Foundation, Inc.
@@ -49,10 +49,6 @@ void cv_wait(kcondvar_t *, struct kmutex
int cv_wait_sig(kcondvar_t *, struct kmutex *);
int cv_timedwait(kcondvar_t *, struct kmutex *, int);
int cv_timedwait_sig(kcondvar_t *, struct kmutex *, int);
-int cv_timedwaitclock(kcondvar_t *, struct kmutex *, struct timespec *,
- clockid_t, int, const struct bintime *);
-int cv_timedwaitclock_sig(kcondvar_t *, struct kmutex *, struct timespec *,
- clockid_t, int, const struct bintime *);
int cv_timedwaitbt(kcondvar_t *, struct kmutex *, struct bintime *,
const struct bintime *);
int cv_timedwaitbt_sig(kcondvar_t *, struct kmutex *, struct bintime *,
Index: src/sys/sys/timevar.h
diff -u src/sys/sys/timevar.h:1.43 src/sys/sys/timevar.h:1.44
--- src/sys/sys/timevar.h:1.43 Mon May 4 18:23:37 2020
+++ src/sys/sys/timevar.h Mon May 11 03:59:33 2020
@@ -1,4 +1,4 @@
-/* $NetBSD: timevar.h,v 1.43 2020/05/04 18:23:37 riastradh Exp $ */
+/* $NetBSD: timevar.h,v 1.44 2020/05/11 03:59:33 riastradh Exp $ */
/*
* Copyright (c) 2005, 2008, The NetBSD Foundation.
@@ -107,14 +107,6 @@ struct ptimers {
struct ptimer *pts_timers[TIMER_MAX];
};
-struct timedwaitclock {
- struct timespec *timeout;
- clockid_t clockid;
- int flags;
- const struct bintime *epsilon;
- struct timespec starttime;
-};
-
/*
* Functions for looking at our clock: [get]{bin,nano,micro}[up]time()
*
@@ -200,11 +192,6 @@ void time_init(void);
void time_init2(void);
bool time_wraps(struct timespec *, struct timespec *);
-void timedwaitclock_setup(struct timedwaitclock *, struct timespec *,
- clockid_t, int, const struct bintime *);
-int timedwaitclock_begin(struct timedwaitclock *, int *);
-void timedwaitclock_end(struct timedwaitclock *);
-
extern volatile time_t time_second; /* current second in the epoch */
extern volatile time_t time_uptime; /* system uptime in seconds */