Deleted Added
full compact
kern_lock.c (28569) kern_lock.c (29653)
1/*
2 * Copyright (c) 1995
3 * The Regents of the University of California. All rights reserved.
4 *
5 * Copyright (C) 1997
6 * John S. Dyson. All rights reserved.
7 *
8 * This code contains ideas from software contributed to Berkeley by

--- 24 unchanged lines hidden (view full) ---

33 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
34 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
35 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
36 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
37 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
38 * SUCH DAMAGE.
39 *
40 * @(#)kern_lock.c 8.18 (Berkeley) 5/21/95
1/*
2 * Copyright (c) 1995
3 * The Regents of the University of California. All rights reserved.
4 *
5 * Copyright (C) 1997
6 * John S. Dyson. All rights reserved.
7 *
8 * This code contains ideas from software contributed to Berkeley by

--- 24 unchanged lines hidden (view full) ---

33 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
34 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
35 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
36 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
37 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
38 * SUCH DAMAGE.
39 *
40 * @(#)kern_lock.c 8.18 (Berkeley) 5/21/95
41 * $Id: kern_lock.c,v 1.10 1997/08/19 00:27:07 dyson Exp $
41 * $Id: kern_lock.c,v 1.11 1997/08/22 07:16:46 phk Exp $
42 */
43
44#include <sys/param.h>
45#include <sys/proc.h>
46#include <sys/lock.h>
47#include <sys/systm.h>
48
49#ifdef SMP

--- 15 unchanged lines hidden (view full) ---

65#define LOCK_SAMPLE_WAIT 7
66
67#if defined(DIAGNOSTIC)
68#define LOCK_INLINE
69#else
70#define LOCK_INLINE inline
71#endif
72
42 */
43
44#include <sys/param.h>
45#include <sys/proc.h>
46#include <sys/lock.h>
47#include <sys/systm.h>
48
49#ifdef SMP

--- 15 unchanged lines hidden (view full) ---

65#define LOCK_SAMPLE_WAIT 7
66
67#if defined(DIAGNOSTIC)
68#define LOCK_INLINE
69#else
70#define LOCK_INLINE inline
71#endif
72
73#define LK_ALL (LK_HAVE_EXCL | LK_WANT_EXCL | LK_WANT_UPGRADE | \
74 LK_SHARE_NONZERO | LK_WAIT_NONZERO)
75
73static int acquire(struct lock *lkp, int extflags, int wanted);
76static int acquire(struct lock *lkp, int extflags, int wanted);
77static int apause(struct lock *lkp, int flags);
78static int acquiredrain(struct lock *lkp, int extflags) ;
74
75static LOCK_INLINE void
76sharelock(struct lock *lkp, int incr) {
77 lkp->lk_flags |= LK_SHARE_NONZERO;
78 lkp->lk_sharecount += incr;
79}
80
81static LOCK_INLINE void

--- 7 unchanged lines hidden (view full) ---

89#endif
90#endif
91
92 lkp->lk_sharecount -= decr;
93 if (lkp->lk_sharecount == 0)
94 lkp->lk_flags &= ~LK_SHARE_NONZERO;
95}
96
79
80static LOCK_INLINE void
81sharelock(struct lock *lkp, int incr) {
82 lkp->lk_flags |= LK_SHARE_NONZERO;
83 lkp->lk_sharecount += incr;
84}
85
86static LOCK_INLINE void

--- 7 unchanged lines hidden (view full) ---

94#endif
95#endif
96
97 lkp->lk_sharecount -= decr;
98 if (lkp->lk_sharecount == 0)
99 lkp->lk_flags &= ~LK_SHARE_NONZERO;
100}
101
102/*
103 * This is the waitloop optimization, and note for this to work
104 * simple_lock and simple_unlock should be subroutines to avoid
105 * optimization troubles.
106 */
97static int
98apause(struct lock *lkp, int flags) {
99 int lock_wait;
100 lock_wait = LOCK_WAIT_TIME;
101 for (; lock_wait > 0; lock_wait--) {
102 int i;
103 if ((lkp->lk_flags & flags) == 0)
104 return 0;

--- 5 unchanged lines hidden (view full) ---

110 return 0;
111 break;
112 }
113 }
114 }
115 return 1;
116}
117
107static int
108apause(struct lock *lkp, int flags) {
109 int lock_wait;
110 lock_wait = LOCK_WAIT_TIME;
111 for (; lock_wait > 0; lock_wait--) {
112 int i;
113 if ((lkp->lk_flags & flags) == 0)
114 return 0;

--- 5 unchanged lines hidden (view full) ---

120 return 0;
121 break;
122 }
123 }
124 }
125 return 1;
126}
127
118
119static int
120acquire(struct lock *lkp, int extflags, int wanted) {
121 int error;
122 int lock_wait;
123
124 if ((extflags & LK_NOWAIT) && (lkp->lk_flags & wanted)) {
125 return EBUSY;
126 }
127
128static int
129acquire(struct lock *lkp, int extflags, int wanted) {
130 int error;
131 int lock_wait;
132
133 if ((extflags & LK_NOWAIT) && (lkp->lk_flags & wanted)) {
134 return EBUSY;
135 }
136
128 error = apause(lkp, wanted);
129 if (error == 0)
130 return 0;
137 if (((lkp->lk_flags | extflags) & LK_NOPAUSE) == 0) {
138 error = apause(lkp, wanted);
139 if (error == 0)
140 return 0;
141 }
131
132 while ((lkp->lk_flags & wanted) != 0) {
133 lkp->lk_flags |= LK_WAIT_NONZERO;
134 lkp->lk_waitcount++;
135 simple_unlock(&lkp->lk_interlock);
136 error = tsleep(lkp, lkp->lk_prio, lkp->lk_wmesg, lkp->lk_timo);
137 simple_lock(&lkp->lk_interlock);
138 lkp->lk_waitcount--;
139 if (lkp->lk_waitcount == 0)
140 lkp->lk_flags &= ~LK_WAIT_NONZERO;
141 if (error)
142 return error;
143 if (extflags & LK_SLEEPFAIL) {
144 return ENOLCK;
145 }
146 }
147 return 0;
148}
149
142
143 while ((lkp->lk_flags & wanted) != 0) {
144 lkp->lk_flags |= LK_WAIT_NONZERO;
145 lkp->lk_waitcount++;
146 simple_unlock(&lkp->lk_interlock);
147 error = tsleep(lkp, lkp->lk_prio, lkp->lk_wmesg, lkp->lk_timo);
148 simple_lock(&lkp->lk_interlock);
149 lkp->lk_waitcount--;
150 if (lkp->lk_waitcount == 0)
151 lkp->lk_flags &= ~LK_WAIT_NONZERO;
152 if (error)
153 return error;
154 if (extflags & LK_SLEEPFAIL) {
155 return ENOLCK;
156 }
157 }
158 return 0;
159}
160
150#define LK_ALL (LK_HAVE_EXCL | LK_WANT_EXCL | LK_WANT_UPGRADE | \
151 LK_SHARE_NONZERO | LK_WAIT_NONZERO)
152
153static int
154acquiredrain(struct lock *lkp, int extflags) {
155 int error;
156 int lock_wait;
157
158 if ((extflags & LK_NOWAIT) && (lkp->lk_flags & LK_ALL)) {
159 return EBUSY;
160 }
161
162 error = apause(lkp, LK_ALL);
163 if (error == 0)
164 return 0;
165
166 while (lkp->lk_flags & LK_ALL) {
167 lkp->lk_flags |= LK_WAITDRAIN;
168 simple_unlock(&lkp->lk_interlock);
169 error = tsleep(&lkp->lk_flags, lkp->lk_prio,
170 lkp->lk_wmesg, lkp->lk_timo);
171 simple_lock(&lkp->lk_interlock);
172 if (error)
173 return error;
174 if (extflags & LK_SLEEPFAIL) {
175 return ENOLCK;
176 }
177 }
178 return 0;
179}
180
181/*
161/*
182 * Initialize a lock; required before use.
183 */
184void
185lockinit(lkp, prio, wmesg, timo, flags)
186 struct lock *lkp;
187 int prio;
188 char *wmesg;
189 int timo;
190 int flags;
191{
192
193 simple_lock_init(&lkp->lk_interlock);
194 lkp->lk_flags = (flags & LK_EXTFLG_MASK);
195 lkp->lk_sharecount = 0;
196 lkp->lk_waitcount = 0;
197 lkp->lk_exclusivecount = 0;
198 lkp->lk_prio = prio;
199 lkp->lk_wmesg = wmesg;
200 lkp->lk_timo = timo;
201 lkp->lk_lockholder = LK_NOPROC;
202}
203
204/*
205 * Determine the status of a lock.
206 */
207int
208lockstatus(lkp)
209 struct lock *lkp;
210{
211 int lock_type = 0;
212
213 simple_lock(&lkp->lk_interlock);
214 if (lkp->lk_exclusivecount != 0)
215 lock_type = LK_EXCLUSIVE;
216 else if (lkp->lk_sharecount != 0)
217 lock_type = LK_SHARED;
218 simple_unlock(&lkp->lk_interlock);
219 return (lock_type);
220}
221
222/*
223 * Set, change, or release a lock.
224 *
225 * Shared requests increment the shared count. Exclusive requests set the
226 * LK_WANT_EXCL flag (preventing further shared locks), and wait for already
227 * accepted shared locks and shared-to-exclusive upgrades to go away.
228 */
229int
230lockmgr(lkp, flags, interlkp, p)

--- 205 unchanged lines hidden (view full) ---

436 LK_SHARE_NONZERO | LK_WAIT_NONZERO)) == 0) {
437 lkp->lk_flags &= ~LK_WAITDRAIN;
438 wakeup((void *)&lkp->lk_flags);
439 }
440 simple_unlock(&lkp->lk_interlock);
441 return (error);
442}
443
162 * Set, change, or release a lock.
163 *
164 * Shared requests increment the shared count. Exclusive requests set the
165 * LK_WANT_EXCL flag (preventing further shared locks), and wait for already
166 * accepted shared locks and shared-to-exclusive upgrades to go away.
167 */
168int
169lockmgr(lkp, flags, interlkp, p)

--- 205 unchanged lines hidden (view full) ---

375 LK_SHARE_NONZERO | LK_WAIT_NONZERO)) == 0) {
376 lkp->lk_flags &= ~LK_WAITDRAIN;
377 wakeup((void *)&lkp->lk_flags);
378 }
379 simple_unlock(&lkp->lk_interlock);
380 return (error);
381}
382
383static int
384acquiredrain(struct lock *lkp, int extflags) {
385 int error;
386 int lock_wait;
387
388 if ((extflags & LK_NOWAIT) && (lkp->lk_flags & LK_ALL)) {
389 return EBUSY;
390 }
391
392 error = apause(lkp, LK_ALL);
393 if (error == 0)
394 return 0;
395
396 while (lkp->lk_flags & LK_ALL) {
397 lkp->lk_flags |= LK_WAITDRAIN;
398 simple_unlock(&lkp->lk_interlock);
399 error = tsleep(&lkp->lk_flags, lkp->lk_prio,
400 lkp->lk_wmesg, lkp->lk_timo);
401 simple_lock(&lkp->lk_interlock);
402 if (error)
403 return error;
404 if (extflags & LK_SLEEPFAIL) {
405 return ENOLCK;
406 }
407 }
408 return 0;
409}
410
444/*
411/*
412 * Initialize a lock; required before use.
413 */
414void
415lockinit(lkp, prio, wmesg, timo, flags)
416 struct lock *lkp;
417 int prio;
418 char *wmesg;
419 int timo;
420 int flags;
421{
422
423 simple_lock_init(&lkp->lk_interlock);
424 lkp->lk_flags = (flags & LK_EXTFLG_MASK);
425 lkp->lk_sharecount = 0;
426 lkp->lk_waitcount = 0;
427 lkp->lk_exclusivecount = 0;
428 lkp->lk_prio = prio;
429 lkp->lk_wmesg = wmesg;
430 lkp->lk_timo = timo;
431 lkp->lk_lockholder = LK_NOPROC;
432}
433
434/*
435 * Determine the status of a lock.
436 */
437int
438lockstatus(lkp)
439 struct lock *lkp;
440{
441 int lock_type = 0;
442
443 simple_lock(&lkp->lk_interlock);
444 if (lkp->lk_exclusivecount != 0)
445 lock_type = LK_EXCLUSIVE;
446 else if (lkp->lk_sharecount != 0)
447 lock_type = LK_SHARED;
448 simple_unlock(&lkp->lk_interlock);
449 return (lock_type);
450}
451
452/*
445 * Print out information about state of a lock. Used by VOP_PRINT
446 * routines to display status about contained locks.
447 */
448void
449lockmgr_printinfo(lkp)
450 struct lock *lkp;
451{
452

--- 104 unchanged lines hidden ---
453 * Print out information about state of a lock. Used by VOP_PRINT
454 * routines to display status about contained locks.
455 */
456void
457lockmgr_printinfo(lkp)
458 struct lock *lkp;
459{
460

--- 104 unchanged lines hidden ---