kern_timeout.c revision 163246
11541Srgrimes/*-
21541Srgrimes * Copyright (c) 1982, 1986, 1991, 1993
31541Srgrimes *	The Regents of the University of California.  All rights reserved.
41541Srgrimes * (c) UNIX System Laboratories, Inc.
51541Srgrimes * All or some portions of this file are derived from material licensed
61541Srgrimes * to the University of California by American Telephone and Telegraph
71541Srgrimes * Co. or Unix System Laboratories, Inc. and are reproduced herein with
81541Srgrimes * the permission of UNIX System Laboratories, Inc.
91541Srgrimes *
101541Srgrimes * Redistribution and use in source and binary forms, with or without
111541Srgrimes * modification, are permitted provided that the following conditions
121541Srgrimes * are met:
131541Srgrimes * 1. Redistributions of source code must retain the above copyright
141541Srgrimes *    notice, this list of conditions and the following disclaimer.
151541Srgrimes * 2. Redistributions in binary form must reproduce the above copyright
161541Srgrimes *    notice, this list of conditions and the following disclaimer in the
171541Srgrimes *    documentation and/or other materials provided with the distribution.
181541Srgrimes * 4. Neither the name of the University nor the names of its contributors
191541Srgrimes *    may be used to endorse or promote products derived from this software
201541Srgrimes *    without specific prior written permission.
211541Srgrimes *
221541Srgrimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
231541Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
241541Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
251541Srgrimes * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
261541Srgrimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
271541Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
281541Srgrimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
291541Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
301541Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
311541Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
321541Srgrimes * SUCH DAMAGE.
331541Srgrimes *
3444510Swollman *	From: @(#)kern_clock.c	8.5 (Berkeley) 1/21/94
351541Srgrimes */
361541Srgrimes
37116182Sobrien#include <sys/cdefs.h>
38116182Sobrien__FBSDID("$FreeBSD: head/sys/kern/kern_timeout.c 163246 2006-10-11 14:57:03Z glebius $");
39116182Sobrien
401541Srgrimes#include <sys/param.h>
411541Srgrimes#include <sys/systm.h>
4233392Sphk#include <sys/callout.h>
43127969Scperciva#include <sys/condvar.h>
441541Srgrimes#include <sys/kernel.h>
45133229Srwatson#include <sys/ktr.h>
4674914Sjhb#include <sys/lock.h>
4768840Sjhb#include <sys/mutex.h>
48150188Sjhb#include <sys/proc.h>
49115810Sphk#include <sys/sysctl.h>
501541Srgrimes
51115810Sphkstatic int avg_depth;
52115810SphkSYSCTL_INT(_debug, OID_AUTO, to_avg_depth, CTLFLAG_RD, &avg_depth, 0,
53115810Sphk    "Average number of items examined per softclock call. Units = 1/1000");
54115810Sphkstatic int avg_gcalls;
55115810SphkSYSCTL_INT(_debug, OID_AUTO, to_avg_gcalls, CTLFLAG_RD, &avg_gcalls, 0,
56115810Sphk    "Average number of Giant callouts made per softclock call. Units = 1/1000");
57141428Siedowsestatic int avg_mtxcalls;
58141428SiedowseSYSCTL_INT(_debug, OID_AUTO, to_avg_mtxcalls, CTLFLAG_RD, &avg_mtxcalls, 0,
59141428Siedowse    "Average number of mtx callouts made per softclock call. Units = 1/1000");
60115810Sphkstatic int avg_mpcalls;
61115810SphkSYSCTL_INT(_debug, OID_AUTO, to_avg_mpcalls, CTLFLAG_RD, &avg_mpcalls, 0,
62115810Sphk    "Average number of MP callouts made per softclock call. Units = 1/1000");
6333392Sphk/*
6433392Sphk * TODO:
6533392Sphk *	allocate more timeout table slots when table overflows.
6633392Sphk */
6733392Sphk
6833392Sphk/* Exported to machdep.c and/or kern_clock.c.  */
6929680Sgibbsstruct callout *callout;
7029680Sgibbsstruct callout_list callfree;
7129680Sgibbsint callwheelsize, callwheelbits, callwheelmask;
7229680Sgibbsstruct callout_tailq *callwheel;
7333392Sphkint softticks;			/* Like ticks, but for softclock(). */
74116606Sphkstruct mtx callout_lock;
752112Swollman
7629680Sgibbsstatic struct callout *nextsoftcheck;	/* Next callout to be checked. */
77128024Scperciva
78139831Scperciva/**
79127969Scperciva * Locked by callout_lock:
80127969Scperciva *   curr_callout    - If a callout is in progress, it is curr_callout.
81155957Sjhb *                     If curr_callout is non-NULL, threads waiting in
82155957Sjhb *                     callout_drain() will be woken up as soon as the
83127969Scperciva *                     relevant callout completes.
84141428Siedowse *   curr_cancelled  - Changing to 1 with both callout_lock and c_mtx held
85141428Siedowse *                     guarantees that the current callout will not run.
86141428Siedowse *                     The softclock() function sets this to 0 before it
87141428Siedowse *                     drops callout_lock to acquire c_mtx, and it calls
88155957Sjhb *                     the handler only if curr_cancelled is still 0 after
89141428Siedowse *                     c_mtx is successfully acquired.
90155957Sjhb *   callout_wait    - If a thread is waiting in callout_drain(), then
91155957Sjhb *                     callout_wait is nonzero.  Set only when
92128024Scperciva *                     curr_callout is non-NULL.
93127969Scperciva */
94127969Scpercivastatic struct callout *curr_callout;
95141428Siedowsestatic int curr_cancelled;
96155957Sjhbstatic int callout_wait;
97128024Scperciva
981541Srgrimes/*
9982127Sdillon * kern_timeout_callwheel_alloc() - kernel low level callwheel initialization
10082127Sdillon *
10182127Sdillon *	This code is called very early in the kernel initialization sequence,
10282127Sdillon *	and may be called more then once.
10382127Sdillon */
10482127Sdilloncaddr_t
10582127Sdillonkern_timeout_callwheel_alloc(caddr_t v)
10682127Sdillon{
10782127Sdillon	/*
10882127Sdillon	 * Calculate callout wheel size
10982127Sdillon	 */
11082127Sdillon	for (callwheelsize = 1, callwheelbits = 0;
11182127Sdillon	     callwheelsize < ncallout;
11282127Sdillon	     callwheelsize <<= 1, ++callwheelbits)
11382127Sdillon		;
11482127Sdillon	callwheelmask = callwheelsize - 1;
11582127Sdillon
11682127Sdillon	callout = (struct callout *)v;
11782127Sdillon	v = (caddr_t)(callout + ncallout);
11882127Sdillon	callwheel = (struct callout_tailq *)v;
11982127Sdillon	v = (caddr_t)(callwheel + callwheelsize);
12082127Sdillon	return(v);
12182127Sdillon}
12282127Sdillon
12382127Sdillon/*
12482127Sdillon * kern_timeout_callwheel_init() - initialize previously reserved callwheel
12582127Sdillon *				   space.
12682127Sdillon *
12782127Sdillon *	This code is called just once, after the space reserved for the
12882127Sdillon *	callout wheel has been finalized.
12982127Sdillon */
13082127Sdillonvoid
13182127Sdillonkern_timeout_callwheel_init(void)
13282127Sdillon{
13382127Sdillon	int i;
13482127Sdillon
13582127Sdillon	SLIST_INIT(&callfree);
13682127Sdillon	for (i = 0; i < ncallout; i++) {
13782127Sdillon		callout_init(&callout[i], 0);
13882127Sdillon		callout[i].c_flags = CALLOUT_LOCAL_ALLOC;
13982127Sdillon		SLIST_INSERT_HEAD(&callfree, &callout[i], c_links.sle);
14082127Sdillon	}
14182127Sdillon	for (i = 0; i < callwheelsize; i++) {
14282127Sdillon		TAILQ_INIT(&callwheel[i]);
14382127Sdillon	}
14493818Sjhb	mtx_init(&callout_lock, "callout", NULL, MTX_SPIN | MTX_RECURSE);
14582127Sdillon}
14682127Sdillon
14782127Sdillon/*
14829680Sgibbs * The callout mechanism is based on the work of Adam M. Costello and
14929680Sgibbs * George Varghese, published in a technical report entitled "Redesigning
15029680Sgibbs * the BSD Callout and Timer Facilities" and modified slightly for inclusion
15129680Sgibbs * in FreeBSD by Justin T. Gibbs.  The original work on the data structures
152128630Shmp * used in this implementation was published by G. Varghese and T. Lauck in
15329680Sgibbs * the paper "Hashed and Hierarchical Timing Wheels: Data Structures for
15429680Sgibbs * the Efficient Implementation of a Timer Facility" in the Proceedings of
15529680Sgibbs * the 11th ACM Annual Symposium on Operating Systems Principles,
15629680Sgibbs * Austin, Texas Nov 1987.
15729680Sgibbs */
15832388Sphk
15929680Sgibbs/*
1601541Srgrimes * Software (low priority) clock interrupt.
1611541Srgrimes * Run periodic events from timeout queue.
1621541Srgrimes */
1631541Srgrimesvoid
16467551Sjhbsoftclock(void *dummy)
1651541Srgrimes{
166102936Sphk	struct callout *c;
167102936Sphk	struct callout_tailq *bucket;
168102936Sphk	int curticks;
169102936Sphk	int steps;	/* #steps since we last allowed interrupts */
170115810Sphk	int depth;
171115810Sphk	int mpcalls;
172141428Siedowse	int mtxcalls;
173115810Sphk	int gcalls;
174122585Smckusick#ifdef DIAGNOSTIC
175122585Smckusick	struct bintime bt1, bt2;
176122585Smckusick	struct timespec ts2;
177122585Smckusick	static uint64_t maxdt = 36893488147419102LL;	/* 2 msec */
178123254Sphk	static timeout_t *lastfunc;
179122585Smckusick#endif
1801541Srgrimes
18133392Sphk#ifndef MAX_SOFTCLOCK_STEPS
18233392Sphk#define MAX_SOFTCLOCK_STEPS 100 /* Maximum allowed value of steps. */
18333392Sphk#endif /* MAX_SOFTCLOCK_STEPS */
18429680Sgibbs
185115810Sphk	mpcalls = 0;
186141428Siedowse	mtxcalls = 0;
187115810Sphk	gcalls = 0;
188115810Sphk	depth = 0;
18929680Sgibbs	steps = 0;
19072200Sbmilekic	mtx_lock_spin(&callout_lock);
19129680Sgibbs	while (softticks != ticks) {
19229805Sgibbs		softticks++;
19329805Sgibbs		/*
19429805Sgibbs		 * softticks may be modified by hard clock, so cache
19529805Sgibbs		 * it while we work on a given bucket.
19629805Sgibbs		 */
19729805Sgibbs		curticks = softticks;
19829805Sgibbs		bucket = &callwheel[curticks & callwheelmask];
19929805Sgibbs		c = TAILQ_FIRST(bucket);
20029680Sgibbs		while (c) {
201115810Sphk			depth++;
20229805Sgibbs			if (c->c_time != curticks) {
20329680Sgibbs				c = TAILQ_NEXT(c, c_links.tqe);
20429680Sgibbs				++steps;
20529680Sgibbs				if (steps >= MAX_SOFTCLOCK_STEPS) {
20629680Sgibbs					nextsoftcheck = c;
20729805Sgibbs					/* Give interrupts a chance. */
20872200Sbmilekic					mtx_unlock_spin(&callout_lock);
20981370Sjhb					;	/* nothing */
21072200Sbmilekic					mtx_lock_spin(&callout_lock);
21129680Sgibbs					c = nextsoftcheck;
21229680Sgibbs					steps = 0;
21329680Sgibbs				}
21429680Sgibbs			} else {
21529680Sgibbs				void (*c_func)(void *);
21629680Sgibbs				void *c_arg;
217141428Siedowse				struct mtx *c_mtx;
21868889Sjake				int c_flags;
21929680Sgibbs
22029680Sgibbs				nextsoftcheck = TAILQ_NEXT(c, c_links.tqe);
22129805Sgibbs				TAILQ_REMOVE(bucket, c, c_links.tqe);
22229680Sgibbs				c_func = c->c_func;
22329680Sgibbs				c_arg = c->c_arg;
224141428Siedowse				c_mtx = c->c_mtx;
22568889Sjake				c_flags = c->c_flags;
22644510Swollman				if (c->c_flags & CALLOUT_LOCAL_ALLOC) {
227140489Scperciva					c->c_func = NULL;
22844510Swollman					c->c_flags = CALLOUT_LOCAL_ALLOC;
22944510Swollman					SLIST_INSERT_HEAD(&callfree, c,
23044510Swollman							  c_links.sle);
231141674Siedowse					curr_callout = NULL;
23244510Swollman				} else {
23344510Swollman					c->c_flags =
23450673Sjlemon					    (c->c_flags & ~CALLOUT_PENDING);
235141674Siedowse					curr_callout = c;
23644510Swollman				}
237141428Siedowse				curr_cancelled = 0;
23872200Sbmilekic				mtx_unlock_spin(&callout_lock);
239141428Siedowse				if (c_mtx != NULL) {
240141428Siedowse					mtx_lock(c_mtx);
241141428Siedowse					/*
242141428Siedowse					 * The callout may have been cancelled
243141428Siedowse					 * while we switched locks.
244141428Siedowse					 */
245141428Siedowse					if (curr_cancelled) {
246141428Siedowse						mtx_unlock(c_mtx);
247155957Sjhb						goto skip;
248141428Siedowse					}
249141428Siedowse					/* The callout cannot be stopped now. */
250141428Siedowse					curr_cancelled = 1;
251141428Siedowse
252141428Siedowse					if (c_mtx == &Giant) {
253141428Siedowse						gcalls++;
254163246Sglebius						CTR3(KTR_CALLOUT,
255163246Sglebius						    "callout %p func %p arg %p",
256163246Sglebius						    c, c_func, c_arg);
257141428Siedowse					} else {
258141428Siedowse						mtxcalls++;
259163246Sglebius						CTR3(KTR_CALLOUT, "callout mtx"
260163246Sglebius						    " %p func %p arg %p",
261163246Sglebius						    c, c_func, c_arg);
262141428Siedowse					}
263115810Sphk				} else {
264115810Sphk					mpcalls++;
265163246Sglebius					CTR3(KTR_CALLOUT,
266163246Sglebius					    "callout mpsafe %p func %p arg %p",
267163246Sglebius					    c, c_func, c_arg);
268115810Sphk				}
269122585Smckusick#ifdef DIAGNOSTIC
270122585Smckusick				binuptime(&bt1);
271122585Smckusick#endif
272150187Sjhb				THREAD_NO_SLEEPING();
27329680Sgibbs				c_func(c_arg);
274150187Sjhb				THREAD_SLEEPING_OK();
275122585Smckusick#ifdef DIAGNOSTIC
276122585Smckusick				binuptime(&bt2);
277122585Smckusick				bintime_sub(&bt2, &bt1);
278122585Smckusick				if (bt2.frac > maxdt) {
279123254Sphk					if (lastfunc != c_func ||
280123254Sphk					    bt2.frac > maxdt * 2) {
281123254Sphk						bintime2timespec(&bt2, &ts2);
282123254Sphk						printf(
283123254Sphk			"Expensive timeout(9) function: %p(%p) %jd.%09ld s\n",
284123254Sphk						    c_func, c_arg,
285123254Sphk						    (intmax_t)ts2.tv_sec,
286123254Sphk						    ts2.tv_nsec);
287123254Sphk					}
288122585Smckusick					maxdt = bt2.frac;
289123254Sphk					lastfunc = c_func;
290122585Smckusick				}
291122585Smckusick#endif
292141428Siedowse				if ((c_flags & CALLOUT_RETURNUNLOCKED) == 0)
293141428Siedowse					mtx_unlock(c_mtx);
294155957Sjhb			skip:
29572200Sbmilekic				mtx_lock_spin(&callout_lock);
296127969Scperciva				curr_callout = NULL;
297155957Sjhb				if (callout_wait) {
298127969Scperciva					/*
299155957Sjhb					 * There is someone waiting
300127969Scperciva					 * for the callout to complete.
301127969Scperciva					 */
302155957Sjhb					wakeup(&callout_wait);
303155957Sjhb					callout_wait = 0;
304128024Scperciva				}
30529680Sgibbs				steps = 0;
30629680Sgibbs				c = nextsoftcheck;
30729680Sgibbs			}
30829680Sgibbs		}
3091541Srgrimes	}
310115810Sphk	avg_depth += (depth * 1000 - avg_depth) >> 8;
311115810Sphk	avg_mpcalls += (mpcalls * 1000 - avg_mpcalls) >> 8;
312141428Siedowse	avg_mtxcalls += (mtxcalls * 1000 - avg_mtxcalls) >> 8;
313115810Sphk	avg_gcalls += (gcalls * 1000 - avg_gcalls) >> 8;
31429680Sgibbs	nextsoftcheck = NULL;
31572200Sbmilekic	mtx_unlock_spin(&callout_lock);
3161541Srgrimes}
3171541Srgrimes
3181541Srgrimes/*
3191541Srgrimes * timeout --
3201541Srgrimes *	Execute a function after a specified length of time.
3211541Srgrimes *
3221541Srgrimes * untimeout --
3231541Srgrimes *	Cancel previous timeout function call.
3241541Srgrimes *
32529680Sgibbs * callout_handle_init --
32629680Sgibbs *	Initialize a handle so that using it with untimeout is benign.
32729680Sgibbs *
3281541Srgrimes *	See AT&T BCI Driver Reference Manual for specification.  This
32929680Sgibbs *	implementation differs from that one in that although an
33029680Sgibbs *	identification value is returned from timeout, the original
33129680Sgibbs *	arguments to timeout as well as the identifier are used to
33229680Sgibbs *	identify entries for untimeout.
3331541Srgrimes */
33429680Sgibbsstruct callout_handle
33529680Sgibbstimeout(ftn, arg, to_ticks)
33633824Sbde	timeout_t *ftn;
3371541Srgrimes	void *arg;
33869147Sjlemon	int to_ticks;
3391541Srgrimes{
34029680Sgibbs	struct callout *new;
34129680Sgibbs	struct callout_handle handle;
3421541Srgrimes
34372200Sbmilekic	mtx_lock_spin(&callout_lock);
3441541Srgrimes
3451541Srgrimes	/* Fill in the next free callout structure. */
34629680Sgibbs	new = SLIST_FIRST(&callfree);
34729680Sgibbs	if (new == NULL)
34829680Sgibbs		/* XXX Attempt to malloc first */
3491541Srgrimes		panic("timeout table full");
35029680Sgibbs	SLIST_REMOVE_HEAD(&callfree, c_links.sle);
35144510Swollman
35244510Swollman	callout_reset(new, to_ticks, ftn, arg);
3531541Srgrimes
35444510Swollman	handle.callout = new;
35572200Sbmilekic	mtx_unlock_spin(&callout_lock);
35629680Sgibbs	return (handle);
3571541Srgrimes}
3581541Srgrimes
3591541Srgrimesvoid
36029680Sgibbsuntimeout(ftn, arg, handle)
36133824Sbde	timeout_t *ftn;
3621541Srgrimes	void *arg;
36329680Sgibbs	struct callout_handle handle;
3641541Srgrimes{
3651541Srgrimes
36629680Sgibbs	/*
36729680Sgibbs	 * Check for a handle that was initialized
36829680Sgibbs	 * by callout_handle_init, but never used
36929680Sgibbs	 * for a real timeout.
37029680Sgibbs	 */
37129680Sgibbs	if (handle.callout == NULL)
37229680Sgibbs		return;
37329680Sgibbs
37472200Sbmilekic	mtx_lock_spin(&callout_lock);
37544510Swollman	if (handle.callout->c_func == ftn && handle.callout->c_arg == arg)
37644510Swollman		callout_stop(handle.callout);
37772200Sbmilekic	mtx_unlock_spin(&callout_lock);
3781541Srgrimes}
3791541Srgrimes
38024101Sbdevoid
38129680Sgibbscallout_handle_init(struct callout_handle *handle)
38229680Sgibbs{
38329680Sgibbs	handle->callout = NULL;
38429680Sgibbs}
38529680Sgibbs
38644510Swollman/*
38744510Swollman * New interface; clients allocate their own callout structures.
38844510Swollman *
38944510Swollman * callout_reset() - establish or change a timeout
39044510Swollman * callout_stop() - disestablish a timeout
39144510Swollman * callout_init() - initialize a callout structure so that it can
39244510Swollman *	safely be passed to callout_reset() and callout_stop()
39344510Swollman *
39450673Sjlemon * <sys/callout.h> defines three convenience macros:
39544510Swollman *
396140487Scperciva * callout_active() - returns truth if callout has not been stopped,
397140487Scperciva *	drained, or deactivated since the last time the callout was
398140487Scperciva *	reset.
39950673Sjlemon * callout_pending() - returns truth if callout is still waiting for timeout
40050673Sjlemon * callout_deactivate() - marks the callout as having been serviced
40144510Swollman */
402149879Sglebiusint
40369147Sjlemoncallout_reset(c, to_ticks, ftn, arg)
40444510Swollman	struct	callout *c;
40544510Swollman	int	to_ticks;
40692723Salfred	void	(*ftn)(void *);
40744510Swollman	void	*arg;
40844510Swollman{
409149879Sglebius	int cancelled = 0;
41044510Swollman
411141428Siedowse#ifdef notyet /* Some callers of timeout() do not hold Giant. */
412141428Siedowse	if (c->c_mtx != NULL)
413141428Siedowse		mtx_assert(c->c_mtx, MA_OWNED);
414141428Siedowse#endif
415141428Siedowse
41672200Sbmilekic	mtx_lock_spin(&callout_lock);
417141428Siedowse	if (c == curr_callout) {
418127969Scperciva		/*
419127969Scperciva		 * We're being asked to reschedule a callout which is
420141428Siedowse		 * currently in progress.  If there is a mutex then we
421141428Siedowse		 * can cancel the callout if it has not really started.
422127969Scperciva		 */
423141428Siedowse		if (c->c_mtx != NULL && !curr_cancelled)
424149879Sglebius			cancelled = curr_cancelled = 1;
425155957Sjhb		if (callout_wait) {
426141428Siedowse			/*
427141428Siedowse			 * Someone has called callout_drain to kill this
428141428Siedowse			 * callout.  Don't reschedule.
429141428Siedowse			 */
430163246Sglebius			CTR4(KTR_CALLOUT, "%s %p func %p arg %p",
431163246Sglebius			    cancelled ? "cancelled" : "failed to cancel",
432163246Sglebius			    c, c->c_func, c->c_arg);
433141428Siedowse			mtx_unlock_spin(&callout_lock);
434149879Sglebius			return (cancelled);
435141428Siedowse		}
436128024Scperciva	}
437133190Scperciva	if (c->c_flags & CALLOUT_PENDING) {
438133190Scperciva		if (nextsoftcheck == c) {
439133190Scperciva			nextsoftcheck = TAILQ_NEXT(c, c_links.tqe);
440133190Scperciva		}
441133190Scperciva		TAILQ_REMOVE(&callwheel[c->c_time & callwheelmask], c,
442133190Scperciva		    c_links.tqe);
44344510Swollman
444149879Sglebius		cancelled = 1;
445149879Sglebius
446133190Scperciva		/*
447133190Scperciva		 * Part of the normal "stop a pending callout" process
448133190Scperciva		 * is to clear the CALLOUT_ACTIVE and CALLOUT_PENDING
449133190Scperciva		 * flags.  We're not going to bother doing that here,
450133190Scperciva		 * because we're going to be setting those flags ten lines
451133190Scperciva		 * after this point, and we're holding callout_lock
452133190Scperciva		 * between now and then.
453133190Scperciva		 */
454133190Scperciva	}
455133190Scperciva
45644510Swollman	/*
45781370Sjhb	 * We could unlock callout_lock here and lock it again before the
45881370Sjhb	 * TAILQ_INSERT_TAIL, but there's no point since doing this setup
45981370Sjhb	 * doesn't take much time.
46044510Swollman	 */
46144510Swollman	if (to_ticks <= 0)
46244510Swollman		to_ticks = 1;
46344510Swollman
46444510Swollman	c->c_arg = arg;
46569147Sjlemon	c->c_flags |= (CALLOUT_ACTIVE | CALLOUT_PENDING);
46644510Swollman	c->c_func = ftn;
46744510Swollman	c->c_time = ticks + to_ticks;
46844510Swollman	TAILQ_INSERT_TAIL(&callwheel[c->c_time & callwheelmask],
46944510Swollman			  c, c_links.tqe);
470163246Sglebius	CTR5(KTR_CALLOUT, "%sscheduled %p func %p arg %p in %d",
471163246Sglebius	    cancelled ? "re" : "", c, c->c_func, c->c_arg, to_ticks);
47272200Sbmilekic	mtx_unlock_spin(&callout_lock);
473149879Sglebius
474149879Sglebius	return (cancelled);
47544510Swollman}
47644510Swollman
47781481Sjhbint
478127969Scperciva_callout_stop_safe(c, safe)
479127969Scperciva	struct	callout *c;
480127969Scperciva	int	safe;
481127969Scperciva{
482155957Sjhb	int use_mtx;
483127969Scperciva
484141428Siedowse	if (!safe && c->c_mtx != NULL) {
485141428Siedowse#ifdef notyet /* Some callers do not hold Giant for Giant-locked callouts. */
486141428Siedowse		mtx_assert(c->c_mtx, MA_OWNED);
487141428Siedowse		use_mtx = 1;
488141428Siedowse#else
489141428Siedowse		use_mtx = mtx_owned(c->c_mtx);
490141428Siedowse#endif
491141428Siedowse	} else {
492141428Siedowse		use_mtx = 0;
493141428Siedowse	}
494141428Siedowse
49572200Sbmilekic	mtx_lock_spin(&callout_lock);
49644510Swollman	/*
497155957Sjhb	 * If the callout isn't pending, it's not on the queue, so
498155957Sjhb	 * don't attempt to remove it from the queue.  We can try to
499155957Sjhb	 * stop it by other means however.
50044510Swollman	 */
50144510Swollman	if (!(c->c_flags & CALLOUT_PENDING)) {
50250673Sjlemon		c->c_flags &= ~CALLOUT_ACTIVE;
503155957Sjhb
504155957Sjhb		/*
505155957Sjhb		 * If it wasn't on the queue and it isn't the current
506155957Sjhb		 * callout, then we can't stop it, so just bail.
507155957Sjhb		 */
508141428Siedowse		if (c != curr_callout) {
509163246Sglebius			CTR3(KTR_CALLOUT, "failed to stop %p func %p arg %p",
510163246Sglebius			    c, c->c_func, c->c_arg);
511141428Siedowse			mtx_unlock_spin(&callout_lock);
512141428Siedowse			return (0);
513141428Siedowse		}
514155957Sjhb
515141428Siedowse		if (safe) {
516127969Scperciva			/*
517155957Sjhb			 * The current callout is running (or just
518155957Sjhb			 * about to run) and blocking is allowed, so
519155957Sjhb			 * just wait for the current invocation to
520155957Sjhb			 * finish.
521127969Scperciva			 */
522155957Sjhb			while (c == curr_callout) {
523155957Sjhb				callout_wait = 1;
524155957Sjhb				msleep_spin(&callout_wait, &callout_lock,
525155957Sjhb				    "codrain", 0);
526155957Sjhb			}
527141428Siedowse		} else if (use_mtx && !curr_cancelled) {
528155957Sjhb			/*
529155957Sjhb			 * The current callout is waiting for it's
530155957Sjhb			 * mutex which we hold.  Cancel the callout
531155957Sjhb			 * and return.  After our caller drops the
532155957Sjhb			 * mutex, the callout will be skipped in
533155957Sjhb			 * softclock().
534155957Sjhb			 */
535141428Siedowse			curr_cancelled = 1;
536163246Sglebius			CTR3(KTR_CALLOUT, "cancelled %p func %p arg %p",
537163246Sglebius			    c, c->c_func, c->c_arg);
538141428Siedowse			mtx_unlock_spin(&callout_lock);
539141428Siedowse			return (1);
540155957Sjhb		}
541163246Sglebius		CTR3(KTR_CALLOUT, "failed to stop %p func %p arg %p",
542163246Sglebius		    c, c->c_func, c->c_arg);
543155957Sjhb		mtx_unlock_spin(&callout_lock);
54481481Sjhb		return (0);
54544510Swollman	}
54650673Sjlemon	c->c_flags &= ~(CALLOUT_ACTIVE | CALLOUT_PENDING);
54744510Swollman
54844510Swollman	if (nextsoftcheck == c) {
54944510Swollman		nextsoftcheck = TAILQ_NEXT(c, c_links.tqe);
55044510Swollman	}
55144510Swollman	TAILQ_REMOVE(&callwheel[c->c_time & callwheelmask], c, c_links.tqe);
55244510Swollman
553163246Sglebius	CTR3(KTR_CALLOUT, "cancelled %p func %p arg %p",
554163246Sglebius	    c, c->c_func, c->c_arg);
555163246Sglebius
55644510Swollman	if (c->c_flags & CALLOUT_LOCAL_ALLOC) {
557140492Scperciva		c->c_func = NULL;
55844510Swollman		SLIST_INSERT_HEAD(&callfree, c, c_links.sle);
55944510Swollman	}
56072200Sbmilekic	mtx_unlock_spin(&callout_lock);
56181481Sjhb	return (1);
56244510Swollman}
56344510Swollman
56444510Swollmanvoid
56569147Sjlemoncallout_init(c, mpsafe)
56644510Swollman	struct	callout *c;
56769147Sjlemon	int mpsafe;
56844510Swollman{
56944527Swollman	bzero(c, sizeof *c);
570141428Siedowse	if (mpsafe) {
571141428Siedowse		c->c_mtx = NULL;
572141428Siedowse		c->c_flags = CALLOUT_RETURNUNLOCKED;
573141428Siedowse	} else {
574141428Siedowse		c->c_mtx = &Giant;
575141428Siedowse		c->c_flags = 0;
576141428Siedowse	}
57744510Swollman}
57844510Swollman
579141428Siedowsevoid
580141428Siedowsecallout_init_mtx(c, mtx, flags)
581141428Siedowse	struct	callout *c;
582141428Siedowse	struct	mtx *mtx;
583141428Siedowse	int flags;
584141428Siedowse{
585141428Siedowse	bzero(c, sizeof *c);
586141428Siedowse	c->c_mtx = mtx;
587141428Siedowse	KASSERT((flags & ~CALLOUT_RETURNUNLOCKED) == 0,
588141428Siedowse	    ("callout_init_mtx: bad flags %d", flags));
589141428Siedowse	/* CALLOUT_RETURNUNLOCKED makes no sense without a mutex. */
590141428Siedowse	KASSERT(mtx != NULL || (flags & CALLOUT_RETURNUNLOCKED) == 0,
591141428Siedowse	    ("callout_init_mtx: CALLOUT_RETURNUNLOCKED with no mutex"));
592141428Siedowse	c->c_flags = flags & CALLOUT_RETURNUNLOCKED;
593141428Siedowse}
594141428Siedowse
59531950Snate#ifdef APM_FIXUP_CALLTODO
59631950Snate/*
59731950Snate * Adjust the kernel calltodo timeout list.  This routine is used after
59831950Snate * an APM resume to recalculate the calltodo timer list values with the
59931950Snate * number of hz's we have been sleeping.  The next hardclock() will detect
60031950Snate * that there are fired timers and run softclock() to execute them.
60131950Snate *
60231950Snate * Please note, I have not done an exhaustive analysis of what code this
60331950Snate * might break.  I am motivated to have my select()'s and alarm()'s that
60431950Snate * have expired during suspend firing upon resume so that the applications
60531950Snate * which set the timer can do the maintanence the timer was for as close
60631950Snate * as possible to the originally intended time.  Testing this code for a
60731950Snate * week showed that resuming from a suspend resulted in 22 to 25 timers
60831950Snate * firing, which seemed independant on whether the suspend was 2 hours or
60931950Snate * 2 days.  Your milage may vary.   - Ken Key <key@cs.utk.edu>
61031950Snate */
61131950Snatevoid
61231950Snateadjust_timeout_calltodo(time_change)
61331950Snate    struct timeval *time_change;
61431950Snate{
61531950Snate	register struct callout *p;
61631950Snate	unsigned long delta_ticks;
61731950Snate
61831950Snate	/*
61931950Snate	 * How many ticks were we asleep?
62036127Sbde	 * (stolen from tvtohz()).
62131950Snate	 */
62231950Snate
62331950Snate	/* Don't do anything */
62431950Snate	if (time_change->tv_sec < 0)
62531950Snate		return;
62631950Snate	else if (time_change->tv_sec <= LONG_MAX / 1000000)
62731950Snate		delta_ticks = (time_change->tv_sec * 1000000 +
62831950Snate			       time_change->tv_usec + (tick - 1)) / tick + 1;
62931950Snate	else if (time_change->tv_sec <= LONG_MAX / hz)
63031950Snate		delta_ticks = time_change->tv_sec * hz +
63131950Snate			      (time_change->tv_usec + (tick - 1)) / tick + 1;
63231950Snate	else
63331950Snate		delta_ticks = LONG_MAX;
63431950Snate
63531950Snate	if (delta_ticks > INT_MAX)
63631950Snate		delta_ticks = INT_MAX;
63731950Snate
63831950Snate	/*
63931950Snate	 * Now rip through the timer calltodo list looking for timers
64031950Snate	 * to expire.
64131950Snate	 */
64231950Snate
64331950Snate	/* don't collide with softclock() */
64472200Sbmilekic	mtx_lock_spin(&callout_lock);
64531950Snate	for (p = calltodo.c_next; p != NULL; p = p->c_next) {
64631950Snate		p->c_time -= delta_ticks;
64731950Snate
64831950Snate		/* Break if the timer had more time on it than delta_ticks */
64931950Snate		if (p->c_time > 0)
65031950Snate			break;
65131950Snate
65231950Snate		/* take back the ticks the timer didn't use (p->c_time <= 0) */
65331950Snate		delta_ticks = -p->c_time;
65431950Snate	}
65572200Sbmilekic	mtx_unlock_spin(&callout_lock);
65631950Snate
65731950Snate	return;
65831950Snate}
65931950Snate#endif /* APM_FIXUP_CALLTODO */
660