xref: /onnv-gate/usr/src/uts/common/sys/condvar_impl.h (revision 9876:fd1599e394c8)
10Sstevel@tonic-gate /*
20Sstevel@tonic-gate  * CDDL HEADER START
30Sstevel@tonic-gate  *
40Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
52958Sdr146992  * Common Development and Distribution License (the "License").
62958Sdr146992  * You may not use this file except in compliance with the License.
70Sstevel@tonic-gate  *
80Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
90Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
100Sstevel@tonic-gate  * See the License for the specific language governing permissions
110Sstevel@tonic-gate  * and limitations under the License.
120Sstevel@tonic-gate  *
130Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
140Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
150Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
160Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
170Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
180Sstevel@tonic-gate  *
190Sstevel@tonic-gate  * CDDL HEADER END
200Sstevel@tonic-gate  */
212958Sdr146992 
220Sstevel@tonic-gate /*
23*9876SDarren.Reed@Sun.COM  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
242958Sdr146992  * Use is subject to license terms.
250Sstevel@tonic-gate  */
260Sstevel@tonic-gate 
270Sstevel@tonic-gate #ifndef _SYS_CONDVAR_IMPL_H
280Sstevel@tonic-gate #define	_SYS_CONDVAR_IMPL_H
290Sstevel@tonic-gate 
300Sstevel@tonic-gate /*
310Sstevel@tonic-gate  * Implementation-private definitions for condition variables
320Sstevel@tonic-gate  */
330Sstevel@tonic-gate 
340Sstevel@tonic-gate #ifndef	_ASM
350Sstevel@tonic-gate #include <sys/types.h>
360Sstevel@tonic-gate #include <sys/thread.h>
370Sstevel@tonic-gate #endif	/* _ASM */
380Sstevel@tonic-gate 
390Sstevel@tonic-gate #ifdef	__cplusplus
400Sstevel@tonic-gate extern "C" {
410Sstevel@tonic-gate #endif
420Sstevel@tonic-gate 
430Sstevel@tonic-gate #ifndef	_ASM
440Sstevel@tonic-gate 
450Sstevel@tonic-gate /*
460Sstevel@tonic-gate  * Condtion variables.
470Sstevel@tonic-gate  */
480Sstevel@tonic-gate 
490Sstevel@tonic-gate typedef struct _condvar_impl {
500Sstevel@tonic-gate 	ushort_t	cv_waiters;
510Sstevel@tonic-gate } condvar_impl_t;
520Sstevel@tonic-gate 
530Sstevel@tonic-gate #define	CV_HAS_WAITERS(cvp)	(((condvar_impl_t *)(cvp))->cv_waiters != 0)
540Sstevel@tonic-gate 
550Sstevel@tonic-gate #endif	/* _ASM */
560Sstevel@tonic-gate 
572958Sdr146992 
58*9876SDarren.Reed@Sun.COM /*
59*9876SDarren.Reed@Sun.COM  * The cvwaitlock_t structure and associated macros provide an implementation
60*9876SDarren.Reed@Sun.COM  * of a locking mechanism that allows recursion on the reader lock without
61*9876SDarren.Reed@Sun.COM  * danger of a pending write lock elsewhere being able to cause a deadlock.
62*9876SDarren.Reed@Sun.COM  * The provision for supporting recursion is necessary for use with the
63*9876SDarren.Reed@Sun.COM  * netinfo (neti) kernel module when processing network data.
64*9876SDarren.Reed@Sun.COM  *
65*9876SDarren.Reed@Sun.COM  * Support for recursion (giving precedence to readers and allowing them
66*9876SDarren.Reed@Sun.COM  * to enter even when a write is blocked) can result in write starvation.
67*9876SDarren.Reed@Sun.COM  * There is no priority inheritence for this locking interface.
68*9876SDarren.Reed@Sun.COM  */
692958Sdr146992 typedef	struct	cvwaitlock_s	{
702958Sdr146992 	kmutex_t	cvw_lock;
712958Sdr146992 	kcondvar_t	cvw_waiter;
722958Sdr146992 	int		cvw_refcnt;
732958Sdr146992 } cvwaitlock_t;
742958Sdr146992 
752958Sdr146992 
762958Sdr146992 #define	CVW_INIT(_c)		{				\
772958Sdr146992 	mutex_init(&(_c)->cvw_lock, NULL, MUTEX_DRIVER, NULL);	\
782958Sdr146992 	cv_init(&(_c)->cvw_waiter, NULL, CV_DRIVER, NULL);	\
792958Sdr146992 	(_c)->cvw_refcnt = 0;					\
802958Sdr146992 }
812958Sdr146992 
822958Sdr146992 #define	CVW_ENTER_READ(_c)	{				\
832958Sdr146992 	mutex_enter(&(_c)->cvw_lock);				\
842958Sdr146992 	while ((_c)->cvw_refcnt < 0)				\
852958Sdr146992 		cv_wait(&((_c)->cvw_waiter), &(_c)->cvw_lock);	\
862958Sdr146992 	(_c)->cvw_refcnt++;					\
872958Sdr146992 	mutex_exit(&(_c)->cvw_lock);				\
882958Sdr146992 }
892958Sdr146992 
902958Sdr146992 #define	CVW_ENTER_WRITE(_c)	{				\
912958Sdr146992 	mutex_enter(&(_c)->cvw_lock);				\
922958Sdr146992 	while ((_c)->cvw_refcnt != 0)				\
932958Sdr146992 		cv_wait(&((_c)->cvw_waiter), &(_c)->cvw_lock);	\
942958Sdr146992 	(_c)->cvw_refcnt = -1;					\
952958Sdr146992 	mutex_exit(&(_c)->cvw_lock);				\
962958Sdr146992 }
972958Sdr146992 
982958Sdr146992 #define	CVW_EXIT_READ(_c)	{			\
992958Sdr146992 	mutex_enter(&(_c)->cvw_lock);			\
1002958Sdr146992 	ASSERT((_c)->cvw_refcnt > 0);			\
1012958Sdr146992 	if ((--((_c)->cvw_refcnt)) == 0)		\
1022958Sdr146992 		cv_broadcast(&(_c)->cvw_waiter);	\
1032958Sdr146992 	mutex_exit(&(_c)->cvw_lock);			\
1042958Sdr146992 }
1052958Sdr146992 
1062958Sdr146992 #define	CVW_EXIT_WRITE(_c)	{			\
1072958Sdr146992 	mutex_enter(&(_c)->cvw_lock);			\
1082958Sdr146992 	ASSERT((_c)->cvw_refcnt == -1);			\
1092958Sdr146992 	(_c)->cvw_refcnt = 0;				\
1102958Sdr146992 	cv_broadcast(&(_c)->cvw_waiter);		\
1112958Sdr146992 	mutex_exit(&(_c)->cvw_lock);			\
1122958Sdr146992 }
1132958Sdr146992 
1147513SDarren.Reed@Sun.COM #define	CVW_WRITE_TO_READ(_c)	{			\
1157513SDarren.Reed@Sun.COM 	mutex_enter(&(_c)->cvw_lock);			\
1167513SDarren.Reed@Sun.COM 	ASSERT((_c)->cvw_refcnt == -1);			\
1177513SDarren.Reed@Sun.COM 	(_c)->cvw_refcnt = 1;				\
1187513SDarren.Reed@Sun.COM 	cv_broadcast(&(_c)->cvw_waiter);		\
1197513SDarren.Reed@Sun.COM 	mutex_exit(&(_c)->cvw_lock);			\
1207513SDarren.Reed@Sun.COM }
1217513SDarren.Reed@Sun.COM 
1223448Sdh155122 #define	CVW_DESTROY(_c)	{				\
1233448Sdh155122 	mutex_destroy(&(_c)->cvw_lock);			\
1243448Sdh155122 	cv_destroy(&(_c)->cvw_waiter);			\
1253448Sdh155122 }
1263448Sdh155122 
1270Sstevel@tonic-gate #ifdef	__cplusplus
1280Sstevel@tonic-gate }
1290Sstevel@tonic-gate #endif
1300Sstevel@tonic-gate 
1310Sstevel@tonic-gate #endif	/* _SYS_CONDVAR_IMPL_H */
132