13182fc7bSGleb Smirnoff.\" Copyright (c) 2006 Gleb Smirnoff <glebius@FreeBSD.org> 23182fc7bSGleb Smirnoff.\" All rights reserved. 33182fc7bSGleb Smirnoff.\" 43182fc7bSGleb Smirnoff.\" Redistribution and use in source and binary forms, with or without 53182fc7bSGleb Smirnoff.\" modification, are permitted provided that the following conditions 63182fc7bSGleb Smirnoff.\" are met: 73182fc7bSGleb Smirnoff.\" 1. Redistributions of source code must retain the above copyright 83182fc7bSGleb Smirnoff.\" notice, this list of conditions and the following disclaimer. 93182fc7bSGleb Smirnoff.\" 2. Redistributions in binary form must reproduce the above copyright 103182fc7bSGleb Smirnoff.\" notice, this list of conditions and the following disclaimer in the 113182fc7bSGleb Smirnoff.\" documentation and/or other materials provided with the distribution. 123182fc7bSGleb Smirnoff.\" 133182fc7bSGleb Smirnoff.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 143182fc7bSGleb Smirnoff.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 153182fc7bSGleb Smirnoff.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 163182fc7bSGleb Smirnoff.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 173182fc7bSGleb Smirnoff.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 183182fc7bSGleb Smirnoff.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 193182fc7bSGleb Smirnoff.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 203182fc7bSGleb Smirnoff.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 213182fc7bSGleb Smirnoff.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 223182fc7bSGleb Smirnoff.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 233182fc7bSGleb Smirnoff.\" SUCH DAMAGE. 243182fc7bSGleb Smirnoff.\" 253182fc7bSGleb Smirnoff.\" $FreeBSD$ 263182fc7bSGleb Smirnoff.\" 270b79fedbSJohn Baldwin.Dd April 19, 2006 283182fc7bSGleb Smirnoff.Dt RWLOCK 9 293182fc7bSGleb Smirnoff.Os 303182fc7bSGleb Smirnoff.Sh NAME 310b79fedbSJohn Baldwin.Nm rwlock , 323182fc7bSGleb Smirnoff.Nm rw_init , 333182fc7bSGleb Smirnoff.Nm rw_rlock , 343182fc7bSGleb Smirnoff.Nm rw_wlock , 353182fc7bSGleb Smirnoff.Nm rw_assert , 363182fc7bSGleb Smirnoff.Nm rw_runlock , 373182fc7bSGleb Smirnoff.Nm rw_wunlock , 383182fc7bSGleb Smirnoff.Nm rw_initialized , 393182fc7bSGleb Smirnoff.Nm rw_destroy , 40bd84dd2fSRuslan Ermilov.Nm RW_SYSINIT 410b79fedbSJohn Baldwin.Nd kernel reader/writer lock 423182fc7bSGleb Smirnoff.Sh SYNOPSIS 433182fc7bSGleb Smirnoff.In sys/param.h 443182fc7bSGleb Smirnoff.In sys/lock.h 453182fc7bSGleb Smirnoff.In sys/rwlock.h 463182fc7bSGleb Smirnoff.Ft void 470b79fedbSJohn Baldwin.Fn rw_init "struct rwlock *rw" "const char *name" 483182fc7bSGleb Smirnoff.Ft void 490b79fedbSJohn Baldwin.Fn rw_rlock "struct rwlock *rw" 503182fc7bSGleb Smirnoff.Ft void 510b79fedbSJohn Baldwin.Fn rw_wlock "struct rwlock *rw" 523182fc7bSGleb Smirnoff.Ft void 530b79fedbSJohn Baldwin.Fn rw_runlock "struct rwlock *rw" 543182fc7bSGleb Smirnoff.Ft void 550b79fedbSJohn Baldwin.Fn rw_wunlock "struct rwlock *rw" 563182fc7bSGleb Smirnoff.Ft int 5796cb5f99SJohn Baldwin.Fn rw_try_upgrade "struct rwlock *rw" 5896cb5f99SJohn Baldwin.Ft void 5996cb5f99SJohn Baldwin.Fn rw_downgrade "struct rwlock *rw" 6096cb5f99SJohn Baldwin.Ft int 610b79fedbSJohn Baldwin.Fn rw_initialized "struct rwlock *rw" 623182fc7bSGleb Smirnoff.Ft void 630b79fedbSJohn Baldwin.Fn rw_destroy "struct rwlock *rw" 64dd348217SRobert Watson.Ft int 65dd348217SRobert Watson.Fn rw_wowned "struct rwlock *rw" 663182fc7bSGleb Smirnoff.Pp 673182fc7bSGleb Smirnoff.Cd "options INVARIANTS" 683182fc7bSGleb Smirnoff.Cd "options INVARIANT_SUPPORT" 693182fc7bSGleb Smirnoff.Ft void 700b79fedbSJohn Baldwin.Fn rw_assert "struct rwlock *rw" "int what" 713182fc7bSGleb Smirnoff.In sys/kernel.h 720b79fedbSJohn Baldwin.Fn RW_SYSINIT "name" "struct rwlock *rw" "const char *desc" 733182fc7bSGleb Smirnoff.Sh DESCRIPTION 740b79fedbSJohn BaldwinReader/writer locks allow shared access to protected data by multiple threads, 750b79fedbSJohn Baldwinor exclusive access by a single thread. 760b79fedbSJohn BaldwinThe threads with shared access are known as 773182fc7bSGleb Smirnoff.Em readers 780b79fedbSJohn Baldwinsince they only read the protected data. 790b79fedbSJohn BaldwinA thread with exclusive access is known as a 803182fc7bSGleb Smirnoff.Em writer 813182fc7bSGleb Smirnoffsince it can modify protected data. 823182fc7bSGleb Smirnoff.Pp 83f1acac21SFlorent ThoumieAlthough reader/writer locks look very similar to 843182fc7bSGleb Smirnoff.Xr sx 9 853182fc7bSGleb Smirnofflocks, their usage pattern is different. 860b79fedbSJohn BaldwinReader/writer locks can be treated as mutexes (see 873182fc7bSGleb Smirnoff.Xr mutex 9 ) 883182fc7bSGleb Smirnoffwith shared/exclusive semantics. 893182fc7bSGleb SmirnoffUnlike 903182fc7bSGleb Smirnoff.Xr sx 9 , 913182fc7bSGleb Smirnoffan 923182fc7bSGleb Smirnoff.Nm 930b79fedbSJohn Baldwincan be locked while holding a non-spin mutex, and an 943182fc7bSGleb Smirnoff.Nm 953182fc7bSGleb Smirnoffcannot be held while sleeping. 963182fc7bSGleb SmirnoffThe 973182fc7bSGleb Smirnoff.Nm 983182fc7bSGleb Smirnofflocks have priority propagation like mutexes, but priority 990b79fedbSJohn Baldwincan be propagated only to an exclusive holder. 1003182fc7bSGleb SmirnoffThis limitation comes from the fact that shared owners 1013182fc7bSGleb Smirnoffare anonymous. 1020b79fedbSJohn BaldwinAnother important property is that shared holders of 1033182fc7bSGleb Smirnoff.Nm 1040b79fedbSJohn Baldwincan recurse, 1050b79fedbSJohn Baldwinbut exclusive locks are not allowed to recurse. 1063182fc7bSGleb Smirnoff.Ss Macros and Functions 1073182fc7bSGleb Smirnoff.Bl -tag -width indent 1080b79fedbSJohn Baldwin.It Fn rw_init "struct rwlock *rw" "const char *name" 1093182fc7bSGleb SmirnoffInitialize structure located at 1100b79fedbSJohn Baldwin.Fa rw 1110b79fedbSJohn Baldwinas reader/writer lock, described by name 1123182fc7bSGleb Smirnoff.Fa name . 1133182fc7bSGleb SmirnoffThe description is used solely for debugging purposes. 1140b79fedbSJohn BaldwinThis function must be called before any other operations 1150b79fedbSJohn Baldwinon the lock. 1160b79fedbSJohn Baldwin.It Fn rw_rlock "struct rwlock *rw" 1170b79fedbSJohn BaldwinLock 1180b79fedbSJohn Baldwin.Fa rw 1190b79fedbSJohn Baldwinas a reader. 1203182fc7bSGleb SmirnoffIf any thread holds this lock exclusively, the current thread blocks, 1210b79fedbSJohn Baldwinand its priority is propagated to the exclusive holder. 1223182fc7bSGleb SmirnoffThe 1233182fc7bSGleb Smirnoff.Fn rw_rlock 1243182fc7bSGleb Smirnofffunction can be called when the thread has already acquired reader 1253182fc7bSGleb Smirnoffaccess on 1260b79fedbSJohn Baldwin.Fa rw . 1273182fc7bSGleb SmirnoffThis is called 1283182fc7bSGleb Smirnoff.Dq "recursing on a lock" . 1290b79fedbSJohn Baldwin.It Fn rw_wlock "struct rwlock *rw" 1300b79fedbSJohn BaldwinLock 1310b79fedbSJohn Baldwin.Fa rw 1320b79fedbSJohn Baldwinas a writer. 1333182fc7bSGleb SmirnoffIf there are any shared owners of the lock, the current thread blocks. 1343182fc7bSGleb SmirnoffThe 1353182fc7bSGleb Smirnoff.Fn rw_wlock 1363182fc7bSGleb Smirnofffunction cannot be called recursively. 1370b79fedbSJohn Baldwin.It Fn rw_runlock "struct rwlock *rw" 1380b79fedbSJohn BaldwinThis function releases a shared lock previously acquired by 1393182fc7bSGleb Smirnoff.Fn rw_rlock . 1400b79fedbSJohn Baldwin.It Fn rw_wunlock "struct rwlock *rw" 1410b79fedbSJohn BaldwinThis function releases an exclusive lock previously acquired by 1423182fc7bSGleb Smirnoff.Fn rw_wlock . 14396cb5f99SJohn Baldwin.It Fn rw_try_upgrade "struct rwlock *rw" 14496cb5f99SJohn BaldwinAttempt to upgrade a single shared lock to an exclusive lock. 14596cb5f99SJohn BaldwinThe current thread must hold a shared lock of 14696cb5f99SJohn Baldwin.Fa rw . 14796cb5f99SJohn BaldwinThis will only succeed if the current thread holds the only shared lock on 14896cb5f99SJohn Baldwin.Fa rw , 14996cb5f99SJohn Baldwinand it only holds a single shared lock. 15096cb5f99SJohn BaldwinIf the attempt succeeds 15196cb5f99SJohn Baldwin.Fn rw_try_upgrade 15296cb5f99SJohn Baldwinwill return a non-zero value, 15396cb5f99SJohn Baldwinand the current thread will hold an exclusive lock. 15496cb5f99SJohn BaldwinIf the attempt fails 15596cb5f99SJohn Baldwin.Fn rw_try_upgrade 15696cb5f99SJohn Baldwinwill return zero, 15796cb5f99SJohn Baldwinand the current thread will still hold a shared lock. 15896cb5f99SJohn Baldwin.It Fn rw_downgrade "struct rwlock *rw" 15996cb5f99SJohn BaldwinConvert an exclusive lock into a single shared lock. 16096cb5f99SJohn BaldwinThe current thread must hold an exclusive lock of 16196cb5f99SJohn Baldwin.Fa rw . 1620b79fedbSJohn Baldwin.It Fn rw_initialized "struct rwlock *rw" 1630b79fedbSJohn BaldwinThis function returns non-zero if 1640b79fedbSJohn Baldwin.Fa rw 1653182fc7bSGleb Smirnoffhas been initialized, and zero otherwise. 1660b79fedbSJohn Baldwin.It Fn rw_destroy "struct rwlock *rw" 1673182fc7bSGleb SmirnoffThis functions destroys a lock previously initialized with 1683182fc7bSGleb Smirnoff.Fn rw_init . 1693182fc7bSGleb SmirnoffThe 1700b79fedbSJohn Baldwin.Fa rw 1710b79fedbSJohn Baldwinlock must be unlocked. 172dd348217SRobert Watson.It Fn rw_wowned "struct rwlock *rw" 173dd348217SRobert WatsonThis function returns a non-zero value if the current thread owns an 174dd348217SRobert Watsonexclusive lock on 175dd348217SRobert Watson.Fa rw . 1760b79fedbSJohn Baldwin.It Fn rw_assert "struct rwlock *rw" "int what" 1773182fc7bSGleb SmirnoffThis function allows assertions specified in 1783182fc7bSGleb Smirnoff.Fa what 1793182fc7bSGleb Smirnoffto be made about 1800b79fedbSJohn Baldwin.Fa rw . 1813182fc7bSGleb SmirnoffIf the assertions are not true and the kernel is compiled 1823182fc7bSGleb Smirnoffwith 1833182fc7bSGleb Smirnoff.Cd "options INVARIANTS" 1843182fc7bSGleb Smirnoffand 1853182fc7bSGleb Smirnoff.Cd "options INVARIANT_SUPPORT" , 1863182fc7bSGleb Smirnoffthe kernel will panic. 1873182fc7bSGleb SmirnoffCurrently the following assertions are supported: 1883182fc7bSGleb Smirnoff.Bl -tag -width ".Dv RA_UNLOCKED" 1893182fc7bSGleb Smirnoff.It Dv RA_LOCKED 1900b79fedbSJohn BaldwinAssert that current thread holds either a shared or exclusive lock 1910b79fedbSJohn Baldwinof 1920b79fedbSJohn Baldwin.Fa rw . 1933182fc7bSGleb Smirnoff.It Dv RA_RLOCKED 1940b79fedbSJohn BaldwinAssert that current thread holds a shared lock of 1950b79fedbSJohn Baldwin.Fa rw . 1963182fc7bSGleb Smirnoff.It Dv RA_WLOCKED 1970b79fedbSJohn BaldwinAssert that current thread holds an exclusive lock of 1980b79fedbSJohn Baldwin.Fa rw . 1993182fc7bSGleb Smirnoff.It Dv RA_UNLOCKED 2000b79fedbSJohn BaldwinAssert that current thread holds neither a shared nor exclusive lock of 2010b79fedbSJohn Baldwin.Fa rw . 2023182fc7bSGleb Smirnoff.El 2033182fc7bSGleb Smirnoff.El 2043182fc7bSGleb Smirnoff.Sh SEE ALSO 2053182fc7bSGleb Smirnoff.Xr mutex 9 , 2063182fc7bSGleb Smirnoff.Xr panic 9 , 2073182fc7bSGleb Smirnoff.Xr sema 9 , 2083182fc7bSGleb Smirnoff.Xr sx 9 2093182fc7bSGleb Smirnoff.Sh HISTORY 2103182fc7bSGleb SmirnoffThese 2113182fc7bSGleb Smirnofffunctions appeared in 2123182fc7bSGleb Smirnoff.Fx 7.0 . 2133182fc7bSGleb Smirnoff.Sh AUTHORS 2143182fc7bSGleb Smirnoff.An -nosplit 2153182fc7bSGleb SmirnoffThe 2163182fc7bSGleb Smirnoff.Nm 2173182fc7bSGleb Smirnofffacility was written by 2183182fc7bSGleb Smirnoff.An "John Baldwin" . 2193182fc7bSGleb SmirnoffThis manual page was written by 2203182fc7bSGleb Smirnoff.An "Gleb Smirnoff" . 2210b79fedbSJohn Baldwin.Sh BUGS 2220b79fedbSJohn BaldwinIf 2230b79fedbSJohn Baldwin.Dv WITNESS 2240b79fedbSJohn Baldwinis not included in the kernel, 2250b79fedbSJohn Baldwinthen it is impossible to assert that the current thread does or does not 2260b79fedbSJohn Baldwinhold a shared lock. 2270b79fedbSJohn BaldwinIn the 228bd84dd2fSRuslan Ermilov.Pf non- Dv WITNESS 2290b79fedbSJohn Baldwincase, the 2300b79fedbSJohn Baldwin.Dv RA_LOCKED 2310b79fedbSJohn Baldwinand 2320b79fedbSJohn Baldwin.Dv RA_RLOCKED 2330b79fedbSJohn Baldwinassertions merely check that some thread holds a shared lock. 2340b79fedbSJohn Baldwin.Pp 2350b79fedbSJohn BaldwinReader/writer is a bit of an awkward name. 2360b79fedbSJohn BaldwinAn 2370b79fedbSJohn Baldwin.Nm 2380b79fedbSJohn Baldwincan also be called a 2390b79fedbSJohn Baldwin.Dq Robert Watson 2400b79fedbSJohn Baldwinlock if desired. 241