lock.h revision 115080
1193326Sed/* 2193326Sed * Copyright (c) 2001, 2003 Daniel Eischen <deischen@freebsd.org>. 3193326Sed * All rights reserved. 4193326Sed * 5193326Sed * Redistribution and use in source and binary forms, with or without 6193326Sed * modification, are permitted provided that the following conditions 7193326Sed * are met: 8193326Sed * 1. Redistributions of source code must retain the above copyright 9193326Sed * notice, this list of conditions and the following disclaimer. 10198092Srdivacky * 2. Redistributions in binary form must reproduce the above copyright 11193326Sed * notice, this list of conditions and the following disclaimer in the 12193326Sed * documentation and/or other materials provided with the distribution. 13193326Sed * 14193326Sed * THIS SOFTWARE IS PROVIDED BY THE AUTHORS AND CONTRIBUTORS ``AS IS'' AND 15193326Sed * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16193326Sed * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17198092Srdivacky * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 18193326Sed * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19193326Sed * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20193326Sed * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21193326Sed * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22193326Sed * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23203955Srdivacky * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24193326Sed * SUCH DAMAGE. 25193326Sed * 26193326Sed * $FreeBSD: head/lib/libkse/sys/lock.h 115080 2003-05-16 19:58:30Z deischen $ 27193326Sed */ 28193326Sed 29193326Sed#ifndef _LOCK_H_ 30193326Sed#define _LOCK_H_ 31193326Sed 32198092Srdivackystruct lockreq; 33193326Sedstruct lockuser; 34193326Sedstruct lock; 35193326Sed 36193326Sedenum lock_type { 37193326Sed LCK_DEFAULT = 0x0000, /* default is FIFO spin locks */ 38204643Srdivacky LCK_PRIORITY = 0x0001, 39199990Srdivacky LCK_ADAPTIVE = 0x0002 /* call user-supplied handlers */ 40199990Srdivacky}; 41193326Sed 42193326Sedtypedef void lock_handler_t(struct lock *, struct lockuser *); 43193326Sed 44193326Sedstruct lock { 45193326Sed struct lockreq *l_head; 46193326Sed struct lockreq *l_tail; /* only used for priority locks */ 47193326Sed enum lock_type l_type; 48193326Sed lock_handler_t *l_wait; /* only used for adaptive locks */ 49193326Sed lock_handler_t *l_wakeup; /* only used for adaptive locks */ 50193326Sed}; 51193326Sed 52204643Srdivacky/* Try to make this >= CACHELINESIZE */ 53193326Sedstruct lockreq { 54193326Sed volatile long lr_locked; /* lock granted = 0, busy otherwise */ 55193326Sed struct lockuser *lr_watcher; /* only used for priority locks */ 56193326Sed struct lockuser *lr_owner; /* only used for priority locks */ 57198092Srdivacky long lr_waiting; /* non-zero when wakeup needed */ 58193326Sed volatile int lr_active; /* non-zero if the lock is last lock for thread */ 59193326Sed}; 60193326Sed 61198092Srdivackystruct lockuser { 62198092Srdivacky struct lockreq *lu_myreq; /* request to give up/trade */ 63198092Srdivacky struct lockreq *lu_watchreq; /* watch this request */ 64198092Srdivacky int lu_priority; /* only used for priority locks */ 65203955Srdivacky void *lu_private1; /* private{1,2} are initialized to */ 66203955Srdivacky void *lu_private2; /* NULL and can be used by caller */ 67203955Srdivacky#define lu_private lu_private1 68203955Srdivacky}; 69198092Srdivacky 70193326Sed#define _LCK_INITIALIZER(lck_req) { &lck_req, NULL, LCK_DEFAULT, \ 71203955Srdivacky NULL, NULL } 72203955Srdivacky#define _LCK_REQUEST_INITIALIZER { 0, NULL, NULL, 0 } 73193326Sed 74193326Sed#define _LCK_BUSY(lu) ((lu)->lu_watchreq->lr_locked != 0) 75198092Srdivacky#define _LCK_ACTIVE(lu) ((lu)->lu_watchreq->lr_active != 0) 76198092Srdivacky#define _LCK_GRANTED(lu) ((lu)->lu_watchreq->lr_locked == 0) 77193326Sed 78193326Sed#define _LCK_SET_PRIVATE(lu, p) (lu)->lu_private = (void *)(p) 79203955Srdivacky#define _LCK_GET_PRIVATE(lu) (lu)->lu_private 80203955Srdivacky#define _LCK_SET_PRIVATE2(lu, p) (lu)->lu_private2 = (void *)(p) 81203955Srdivacky#define _LCK_GET_PRIVATE2(lu) (lu)->lu_private2 82203955Srdivacky 83193326Sedvoid _lock_destroy(struct lock *); 84198092Srdivackyint _lock_init(struct lock *, enum lock_type, 85193326Sed lock_handler_t *, lock_handler_t *); 86193326Sedint _lockuser_init(struct lockuser *lu, void *priv); 87193326Sedvoid _lockuser_destroy(struct lockuser *lu); 88193326Sedvoid _lockuser_setactive(struct lockuser *lu, int active); 89193326Sedvoid _lock_acquire(struct lock *, struct lockuser *, int); 90199482Srdivackyvoid _lock_release(struct lock *, struct lockuser *); 91193326Sedvoid _lock_grant(struct lock *, struct lockuser *); 92193326Sed 93202379Srdivacky#endif 94198092Srdivacky