Add to git.
[pthrlib.git] / src / pthr_rwlock.h
1 /* Multiple reader / single writer locks for pthrlib.
2  * by Richard W.M. Jones <rich@annexia.org>
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Library General Public
6  * License as published by the Free Software Foundation; either
7  * version 2 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Library General Public License for more details.
13  *
14  * You should have received a copy of the GNU Library General Public
15  * License along with this library; if not, write to the Free
16  * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17  *
18  * $Id: pthr_rwlock.h,v 1.3 2002/12/01 14:29:30 rich Exp $
19  */
20
21 #ifndef PTHR_RWLOCK_H
22 #define PTHR_RWLOCK_H
23
24 #include <pool.h>
25 #include <hash.h>
26
27 #include "pthr_pseudothread.h"
28 #include "pthr_wait_queue.h"
29
30 struct rwlock;
31 typedef struct rwlock *rwlock;
32
33 /* Function: new_rwlock - multiple reader / single writer locks (rwlocks)
34  * Function: rwlock_writers_have_priority
35  * Function: rwlock_readers_have_priority
36  * Function: rwlock_enter_read
37  * Function: rwlock_enter_write
38  * Function: rwlock_try_enter_read
39  * Function: rwlock_try_enter_write
40  * Function: rwlock_leave
41  *
42  * Multiple reader / single writer locks (rwlocks) do what they
43  * say. They allow either many readers to access a critical section
44  * or a single writer (but not both). If instead you require simple
45  * mutex semantics, then please see <pthr_mutex.h>.
46  *
47  * RWlocks are automatically released if they are being held when
48  * the thread exits.
49  *
50  * RWlocks are not ``upgradable''. The implementation is too
51  * complex to justify that.
52  *
53  * Note that there are possible deadlocks when using locks. To
54  * avoid deadlocks, always ensure every thread acquires locks
55  * in the same order.
56  *
57  * @code{new_rwlock} creates a new rwlock object.
58  *
59  * @code{rwlock_writers_have_priority} changes the nature of the lock so that
60  * writers have priority over readers. If this is the case then
61  * new readers will not be able to enter a critical section if
62  * there are writers waiting to enter.
63  * [NB: This is the default.]
64  *
65  * @code{rwlock_readers_have_priority} changes the nature of the lock so that
66  * readers have priority over writers. Note that if this is the case
67  * then writers are likely to be starved if the lock is frequently
68  * read.
69  *
70  * @code{rwlock_enter_read} enters the critical section as a reader.
71  * Any number of readers are allowed to enter a critical section at
72  * the same time. This function may block.
73  *
74  * @code{rwlock_enter_write} enters the critical section as a writer.
75  * Only a single writer is allowed to enter a critical section, and
76  * then only if there are no readers. This function may block.
77  *
78  * @code{rwlock_try_enter_read} is identical to
79  * @code{rwlock_enter_read}, but it
80  * does not block. It returns true if the lock was successfully
81  * acquired, or false if the operation would block.
82  *
83  * @code{rwlock_try_enter_write} is identical to
84  * @code{rwlock_enter_write}, but it
85  * does not block. It returns true if the lock was successfully
86  * acquired, or false if the operation would block.
87  *
88  * @code{rwlock_leave} leaves the critical section.
89  *
90  * Bugs: A common mistake is to accidentally call @code{rwlock_leave}
91  * when you are not holding the lock. This generally causes the
92  * library to crash.
93  */
94 extern rwlock new_rwlock (pool);
95 extern void rwlock_writers_have_priority (rwlock);
96 extern void rwlock_readers_have_priority (rwlock);
97 extern void rwlock_enter_read (rwlock);
98 extern void rwlock_enter_write (rwlock);
99 extern int rwlock_try_enter_read (rwlock);
100 extern int rwlock_try_enter_write (rwlock);
101 extern void rwlock_leave (rwlock);
102
103 #endif /* PTHR_RWLOCK_H */