diff options
author | jhb <jhb@FreeBSD.org> | 2007-03-09 22:41:01 +0000 |
---|---|---|
committer | jhb <jhb@FreeBSD.org> | 2007-03-09 22:41:01 +0000 |
commit | f5e396934025920e30b32a3eef21d05548f16898 (patch) | |
tree | 343c44631b470578282dfd1c1d3fb73ed2833f3c /share/man | |
parent | b470e17165153afeed8259afb043250b76f64e76 (diff) | |
download | FreeBSD-src-f5e396934025920e30b32a3eef21d05548f16898.zip FreeBSD-src-f5e396934025920e30b32a3eef21d05548f16898.tar.gz |
Allow threads to atomically release rw and sx locks while waiting for an
event. Locking primitives that support this (mtx, rw, and sx) now each
include their own foo_sleep() routine.
- Rename msleep() to _sleep() and change it's 'struct mtx' object to a
'struct lock_object' pointer. _sleep() uses the recently added
lc_unlock() and lc_lock() function pointers for the lock class of the
specified lock to release the lock while the thread is suspended.
- Add wrappers around _sleep() for mutexes (mtx_sleep()), rw locks
(rw_sleep()), and sx locks (sx_sleep()). msleep() still exists and
is now identical to mtx_sleep(), but it is deprecated.
- Rename SLEEPQ_MSLEEP to SLEEPQ_SLEEP.
- Rewrite much of sleep.9 to not be msleep(9) centric.
- Flesh out the 'RETURN VALUES' section in sleep.9 and add an 'ERRORS'
section.
- Add __nonnull(1) to _sleep() and msleep_spin() so that the compiler will
warn if you try to pass a NULL wait channel. The functions already have
a KASSERT to that effect.
Diffstat (limited to 'share/man')
-rw-r--r-- | share/man/man9/Makefile | 3 | ||||
-rw-r--r-- | share/man/man9/condvar.9 | 2 | ||||
-rw-r--r-- | share/man/man9/lock.9 | 8 | ||||
-rw-r--r-- | share/man/man9/mi_switch.9 | 13 | ||||
-rw-r--r-- | share/man/man9/mtx_pool.9 | 5 | ||||
-rw-r--r-- | share/man/man9/mutex.9 | 14 | ||||
-rw-r--r-- | share/man/man9/rwlock.9 | 10 | ||||
-rw-r--r-- | share/man/man9/sleep.9 | 179 | ||||
-rw-r--r-- | share/man/man9/sleepqueue.9 | 10 | ||||
-rw-r--r-- | share/man/man9/sx.9 | 12 | ||||
-rw-r--r-- | share/man/man9/thread_exit.9 | 4 |
11 files changed, 169 insertions, 91 deletions
diff --git a/share/man/man9/Makefile b/share/man/man9/Makefile index 64793de..970430f 100644 --- a/share/man/man9/Makefile +++ b/share/man/man9/Makefile @@ -835,6 +835,7 @@ MLINKS+=mutex.9 mtx_assert.9 \ mutex.9 mtx_lock_spin_flags.9 \ mutex.9 mtx_owned.9 \ mutex.9 mtx_recursed.9 \ + mutex.9 mtx_sleep.9 \ mutex.9 MTX_SYSINIT.9 \ mutex.9 mtx_trylock.9 \ mutex.9 mtx_trylock_flags.9 \ @@ -925,6 +926,7 @@ MLINKS+=rwlock.9 rw_assert.9 \ rwlock.9 rw_initialized.9 \ rwlock.9 rw_rlock.9 \ rwlock.9 rw_runlock.9 \ + rwlock.9 rw_sleep.9 \ rwlock.9 RW_SYSINIT.9 \ rwlock.9 rw_try_upgrade.9 \ rwlock.9 rw_wlock.9 \ @@ -1059,6 +1061,7 @@ MLINKS+=sx.9 sx_assert.9 \ sx.9 sx_try_slock.9 \ sx.9 sx_try_upgrade.9 \ sx.9 sx_try_xlock.9 \ + sx.9 sx_sleep.9 \ sx.9 sx_unlock.9 \ sx.9 sx_xlock.9 \ sx.9 sx_xlocked.9 \ diff --git a/share/man/man9/condvar.9 b/share/man/man9/condvar.9 index dbb2cce..1976504 100644 --- a/share/man/man9/condvar.9 +++ b/share/man/man9/condvar.9 @@ -192,9 +192,9 @@ will fail if: Timeout expired. .El .Sh SEE ALSO -.Xr msleep 9 , .Xr mtx_pool 9 , .Xr mutex 9 , .Xr rwlock 9 , .Xr sema 9 , +.Xr sleep 9 , .Xr sx 9 diff --git a/share/man/man9/lock.9 b/share/man/man9/lock.9 index fbbced9..94e03dd 100644 --- a/share/man/man9/lock.9 +++ b/share/man/man9/lock.9 @@ -63,14 +63,14 @@ Its arguments are: A pointer to the lock to initialize. .It Fa prio The priority passed to -.Xr msleep 9 . +.Xr sleep 9 . .It Fa wmesg The lock message. This is used for both debugging output and -.Xr msleep 9 . +.Xr sleep 9 . .It Fa timo The timeout value passed to -.Xr msleep 9 . +.Xr sleep 9 . .It Fa flags The flags the lock is to be initialized with. .Bl -tag -width ".Dv LG_CANRECURSE" @@ -272,7 +272,7 @@ exclusive lock, and a .Xr panic 9 will be the result of trying. .Sh SEE ALSO -.Xr msleep 9 , +.Xr sleep 9 , .Xr mtx_assert 9 , .Xr panic 9 , .Xr VOP_PRINT 9 diff --git a/share/man/man9/mi_switch.9 b/share/man/man9/mi_switch.9 index a602936..fe97bc5 100644 --- a/share/man/man9/mi_switch.9 +++ b/share/man/man9/mi_switch.9 @@ -65,13 +65,13 @@ The various major uses of can be enumerated as follows: .Bl -enum -offset indent .It -From within -.Xr sleep 9 , -.Xr tsleep 9 -and -.Xr msleep 9 +From within a function such as +.Xr cv_wait 9 , +.Xr mtx_lock , +or +.Xr tsleep 9 when the current thread -voluntarily relinquishes the CPU to wait for some resource to become +voluntarily relinquishes the CPU to wait for some resource or lock to become available. .It After handling a trap @@ -157,6 +157,7 @@ all of these functions must be called with the .Va sched_lock mutex held. .Sh SEE ALSO +.Xr cv_wait 9 , .Xr issignal 9 , .Xr mutex 9 , .Xr runqueue 9 , diff --git a/share/man/man9/mtx_pool.9 b/share/man/man9/mtx_pool.9 index 0084bb5..0d6af1c 100644 --- a/share/man/man9/mtx_pool.9 +++ b/share/man/man9/mtx_pool.9 @@ -64,7 +64,7 @@ .Sh DESCRIPTION Mutex pools are designed to be used as short term leaf mutexes; i.e., the last mutex one might acquire before calling -.Xr msleep 9 . +.Xr mtx_sleep 9 . They operate using a shared pool of mutexes. A mutex may be chosen from the pool based on a supplied pointer, which may or may not point to anything valid, @@ -110,7 +110,7 @@ mutexes to interlock destructor operations. No initialization or destruction overhead. .It Can be used with -.Xr msleep 9 . +.Xr mtx_sleep 9 . .El .Pp And the following disadvantages: @@ -177,7 +177,6 @@ on each mutex in the specified pool, deallocates the memory associated with the pool, and assigns NULL to the pool pointer. .Sh SEE ALSO -.Xr msleep 9 , .Xr mutex 9 .Sh HISTORY These routines first appeared in diff --git a/share/man/man9/mutex.9 b/share/man/man9/mutex.9 index cf89175..c73dfee 100644 --- a/share/man/man9/mutex.9 +++ b/share/man/man9/mutex.9 @@ -45,6 +45,7 @@ .Nm mtx_unlock_spin , .Nm mtx_unlock_flags , .Nm mtx_unlock_spin_flags , +.Nm mtx_sleep , .Nm mtx_initialized , .Nm mtx_owned , .Nm mtx_recursed , @@ -80,6 +81,8 @@ .Ft void .Fn mtx_unlock_spin_flags "struct mtx *mutex" "int flags" .Ft int +.Fn mtx_sleep "void *chan" "struct mtx *mtx" "int priority" "const char *wmesg" "int timo" +.Ft int .Fn mtx_initialized "struct mtx *mutex" .Ft int .Fn mtx_owned "struct mtx *mutex" @@ -305,6 +308,15 @@ or have another thread blocked on the mutex when it is destroyed. .Pp The +.Fn mtx_sleep +function is used to atomically release +.Fa mtx +while waiting for an event. +For more details on the parameters to this function, +see +.Xr sleep 9 . +.Pp +The .Fn mtx_initialized function returns non-zero if .Fa mutex @@ -498,11 +510,11 @@ No locks are needed when calling these functions. .Sh SEE ALSO .Xr condvar 9 , .Xr LOCK_PROFILING 9 , -.Xr msleep 9 , .Xr mtx_pool 9 , .Xr panic 9 , .Xr rwlock 9 , .Xr sema 9 , +.Xr sleep 9 , .Xr sx 9 .Sh HISTORY These diff --git a/share/man/man9/rwlock.9 b/share/man/man9/rwlock.9 index 73bd1ae..7f1a431 100644 --- a/share/man/man9/rwlock.9 +++ b/share/man/man9/rwlock.9 @@ -37,6 +37,7 @@ .Nm rw_wunlock , .Nm rw_try_upgrade , .Nm rw_downgrade , +.Nm rw_sleep , .Nm rw_initialized , .Nm rw_wowned , .Nm rw_assert , @@ -63,6 +64,8 @@ .Ft void .Fn rw_downgrade "struct rwlock *rw" .Ft int +.Fn rw_sleep "void *chan" "struct rwlock *rw" "int priority" "const char *wmesg" "int timo" +.Ft int .Fn rw_initialized "struct rwlock *rw" .Ft int .Fn rw_wowned "struct rwlock *rw" @@ -162,6 +165,13 @@ and the current thread will still hold a shared lock. Convert an exclusive lock into a single shared lock. The current thread must hold an exclusive lock of .Fa rw . +.It Fn rw_sleep "void *chan" "struct rwlock *rw" "int priority" "const char *wmesg" "int timo" +Atomically release +.Fa rw +while waiting for an event. +For more details on the parameters to this function, +see +.Xr sleep 9 . .It Fn rw_initialized "struct rwlock *rw" This function returns non-zero if .Fa rw diff --git a/share/man/man9/sleep.9 b/share/man/man9/sleep.9 index eafa150..67fba57 100644 --- a/share/man/man9/sleep.9 +++ b/share/man/man9/sleep.9 @@ -68,6 +68,12 @@ external event, it is put to sleep by .Fn msleep_spin , or .Fn pause . +Threads may also wait using one of the locking primitive sleep routines +.Xr mtx_sleep 9 , +.Xr rw_sleep 9 , +or +.Xr sx_sleep 9 . +.Pp The parameter .Fa chan is an arbitrary address that uniquely identifies the event on which @@ -80,66 +86,19 @@ often called from inside an interrupt routine, to indicate that the resource the thread was blocking on is available now. .Pp The parameter -.Fa wmesg -is a string describing the sleep condition for tools like -.Xr ps 1 . -Due to the limited space of those programs to display arbitrary strings, -this message should not be longer than 6 characters. -.Pp -The -.Fn msleep -function is the general sleep call. -It suspends the current thread until a wakeup is -performed on the specified identifier. -The -.Fa mtx -parameter is a mutex which will be released before sleeping and reacquired -before -.Fn msleep -returns. -If -.Fa priority -includes the -.Dv PDROP -flag, the -.Fa mtx -parameter will not be reacquired before returning. -The mutex is used to ensure that a condition can be checked atomically, -and that the current thread can be suspended without missing a -change to the condition, or an associated wakeup. -If .Fa priority -is not 0, +specifies a new priority for the thread as well as some optional flags. +If the new priority is not 0, then the thread will be made runnable with the specified .Fa priority when it resumes. If -.Fa timo -is not 0, -then the thread will sleep for at most -.Fa timo No / Va hz -seconds. -If the -.Va Giant -lock is not held and -.Fa mtx -is -.Dv NULL , -then -.Fa timo -must be non-zero. -If .Fa priority includes the .Dv PCATCH flag, signals are checked before and after sleeping, otherwise signals are not checked. -The -.Fn msleep -function returns 0 if awakened, -.Er EWOULDBLOCK -if the timeout expires. If .Dv PCATCH is set and a signal needs to be delivered, @@ -151,33 +110,86 @@ is returned if the system call should be interrupted by the signal (return .Er EINTR ) . .Pp -The +The parameter +.Fa wmesg +is a string describing the sleep condition for tools like +.Xr ps 1 . +Due to the limited space of those programs to display arbitrary strings, +this message should not be longer than 6 characters. +.Pp +The parameter +.Fa timo +specifies a timeout for the sleep. +If +.Fa timo +is not 0, +then the thread will sleep for at most +.Fa timo No / Va hz +seconds. +If the timeout expires, +then the sleep function will return +.Er EWOULDBLOCK . +.Pp +Several of the sleep functions including +.Fn msleep , +.Fn msleep_spin , +and the locking primitive sleep routines specify an additional lock +parameter. +The lock will be released before sleeping and reacquired +before the sleep routine returns. +If +.Fa priority +includes the +.Dv PDROP +flag, then +the lock will not be reacquired before returning. +The lock is used to ensure that a condition can be checked atomically, +and that the current thread can be suspended without missing a +change to the condition, or an associated wakeup. +In addition, all of the sleep routines will fully drop the +.Va Giant +mutex +(even if recursed) +while the thread is suspended and will reacquire the +.Va Giant +mutex before the function returns. +.Pp +To avoid lost wakeups, +either a lock should be used to protect against races, +or a timeout should be specified to place an upper bound on the delay due +to a lost wakeup. +As a result, +the .Fn tsleep -function is a variation on -.Fn msleep . -It is identical to invoking +function should only be invoked with a timeout of 0 when the +.Va Giant +mutex is held. +.Pp +The .Fn msleep -with a -.Dv NULL +function requires that .Fa mtx -parameter. +reference a default, i.e. non-spin, mutex. +It's use is deprecated in favor of +.Xr mtx_sleep 9 +which provides identical behavior. .Pp The .Fn msleep_spin -function is another variation on -.Fn msleep . -This function accepts a spin mutex rather than a default mutex for its +function requires that .Fa mtx -parameter. -It is also more limited in that it does not accept a +reference a spin mutex. +The +.Fn msleep_spin +function does not accept a .Fa priority -parameter. -Thus, it will not change the priority of a sleeping thread, -and it does not support the +parameter and thus does not support changing the current thread's priority, +the .Dv PDROP -and +flag, +or catching signals via the .Dv PCATCH -flags. +flag. .Pp The .Fn pause @@ -221,11 +233,42 @@ pay particular attention to ensure that no other threads wait on the same .Fa chan . .Sh RETURN VALUES -See above. +If the thread is awakened by a call to +.Fn wakeup +or +.Fn wakeup_one , +the +.Fn msleep , +.Fn msleep_spin , +.Fn tsleep , +and locking primitive sleep functions return 0. +Otherwise, a non-zero error code is returned. +.Sh ERRORS +.Fn msleep , +.Fn msleep_spin , +.Fn tsleep , +and the locking primitive sleep functions will fail if: +.Bl -tag -width Er +.It Bq Er EINTR +The +.Dv PCATCH +flag was specified, a signal was caught, and the system call should be +interrupted. +.It Bq Er ERESTART +The +.Dv PCATCH +flag was specified, a signal was caught, and the system call should be +restarted. +.It Bq Er EWOULDBLOCK +A non-zero timeout was specified and the timeout expired. +.El .Sh SEE ALSO .Xr ps 1 , .Xr malloc 9 , -.Xr mi_switch 9 +.Xr mi_switch 9 , +.Xr mtx_sleep 9 , +.Xr rw_sleep 9 , +.Xr sx_sleep 9 .Sh HISTORY The functions .Fn sleep diff --git a/share/man/man9/sleepqueue.9 b/share/man/man9/sleepqueue.9 index 882a3aa..c381539 100644 --- a/share/man/man9/sleepqueue.9 +++ b/share/man/man9/sleepqueue.9 @@ -178,9 +178,9 @@ There are currently three types of sleep queues: .Bl -tag -width ".Dv SLEEPQ_CONDVAR" -compact .It Dv SLEEPQ_CONDVAR A sleep queue used to implement condition variables. -.It Dv SLEEPQ_MSLEEP +.It Dv SLEEPQ_SLEEP A sleep queue used to implement -.Xr msleep 9 , +.Xr sleep 9 , .Xr wakeup 9 and .Xr wakeup_one 9 . @@ -339,7 +339,7 @@ One possible use is waking up a specific thread from a widely shared sleep channel. .Pp The sleep queue interface is currently used to implement the -.Xr msleep 9 +.Xr sleep 9 and .Xr condvar 9 interfaces. @@ -347,6 +347,6 @@ Almost all other code in the kernel should use one of those interfaces rather than manipulating sleep queues directly. .Sh SEE ALSO .Xr condvar 9 , -.Xr msleep 9 , .Xr runqueue 9 , -.Xr scheduler 9 +.Xr scheduler 9 , +.Xr sleep 9 diff --git a/share/man/man9/sx.9 b/share/man/man9/sx.9 index a204ad5..50c0bc4 100644 --- a/share/man/man9/sx.9 +++ b/share/man/man9/sx.9 @@ -42,6 +42,7 @@ .Nm sx_unlock , .Nm sx_try_upgrade , .Nm sx_downgrade , +.Nm sx_sleep , .Nm sx_xlocked , .Nm sx_assert , .Nm SX_SYSINIT @@ -73,6 +74,8 @@ .Ft void .Fn sx_downgrade "struct sx *sx" .Ft int +.Fn sx_sleep "void *chan" "struct sx *sx" "int priority" "const char *wmesg" "int timo" +.Ft int .Fn sx_xlocked "struct sx *sx" .Pp .Cd "options INVARIANTS" @@ -134,6 +137,13 @@ will return 0 if the shared lock cannot be upgraded to an exclusive lock immediately; otherwise the exclusive lock will be acquired and a non-zero value will be returned. .Pp +A thread can atomically release a shared/exclusive lock while waiting for an +event by calling +.Fn sx_sleep . +For more details on the parameters to this function, +see +.Xr sleep 9 . +.Pp When compiled with .Cd "options INVARIANTS" and @@ -169,7 +179,7 @@ by the first argument. .El .Pp .Fn sx_xlocked -will return non-zero if the current process holds the exclusive lock; +will return non-zero if the current thread holds the exclusive lock; otherwise, it will return zero. .Pp For ease of programming, diff --git a/share/man/man9/thread_exit.9 b/share/man/man9/thread_exit.9 index 9dc8acb..6a06433 100644 --- a/share/man/man9/thread_exit.9 +++ b/share/man/man9/thread_exit.9 @@ -58,6 +58,6 @@ must be called with the mutex held. .Sh SEE ALSO .Xr mi_switch 9 , -.Xr msleep 9 , .Xr mutex 9 , -.Xr runqueue 9 +.Xr runqueue 9 , +.Xr sleep 9 |