netwerk/sctp/src/netinet/sctp_process_lock.h

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/netwerk/sctp/src/netinet/sctp_process_lock.h	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,642 @@
     1.4 +/*-
     1.5 + * Copyright (c) 2001-2007, by Cisco Systems, Inc. All rights reserved.
     1.6 + * Copyright (c) 2008-2011, by Randall Stewart. All rights reserved.
     1.7 + * Copyright (c) 2008-2011, by Michael Tuexen. All rights reserved.
     1.8 + *
     1.9 + * Redistribution and use in source and binary forms, with or without
    1.10 + * modification, are permitted provided that the following conditions are met:
    1.11 + *
    1.12 + * a) Redistributions of source code must retain the above copyright notice,
    1.13 + *   this list of conditions and the following disclaimer.
    1.14 + *
    1.15 + * b) Redistributions in binary form must reproduce the above copyright
    1.16 + *    notice, this list of conditions and the following disclaimer in
    1.17 + *   the documentation and/or other materials provided with the distribution.
    1.18 + *
    1.19 + * c) Neither the name of Cisco Systems, Inc. nor the names of its
    1.20 + *    contributors may be used to endorse or promote products derived
    1.21 + *    from this software without specific prior written permission.
    1.22 + *
    1.23 + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
    1.24 + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
    1.25 + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
    1.26 + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
    1.27 + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
    1.28 + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
    1.29 + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
    1.30 + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
    1.31 + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
    1.32 + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
    1.33 + * THE POSSIBILITY OF SUCH DAMAGE.
    1.34 + */
    1.35 +#ifndef __sctp_process_lock_h__
    1.36 +#define __sctp_process_lock_h__
    1.37 +
    1.38 +/*
    1.39 + * Need to yet define five atomic fuctions or
    1.40 + * their equivalant.
    1.41 + * - atomic_add_int(&foo, val) - add atomically the value
    1.42 + * - atomic_fetchadd_int(&foo, val) - does same as atomic_add_int
    1.43 + *				      but value it was is returned.
    1.44 + * - atomic_subtract_int(&foo, val) - can be made from atomic_add_int()
    1.45 + *
    1.46 + * - atomic_cmpset_int(&foo, value, newvalue) - Does a set of newvalue
    1.47 + *					        in foo if and only if
    1.48 + *					        foo is value. Returns 0
    1.49 + *					        on success.
    1.50 + */
    1.51 +
    1.52 +#ifdef SCTP_PER_SOCKET_LOCKING
    1.53 +/*
    1.54 + * per socket level locking
    1.55 + */
    1.56 +
    1.57 +#if defined(__Userspace_os_Windows)
    1.58 +/* Lock for INFO stuff */
    1.59 +#define SCTP_INP_INFO_LOCK_INIT()
    1.60 +#define SCTP_INP_INFO_RLOCK()
    1.61 +#define SCTP_INP_INFO_RUNLOCK()
    1.62 +#define SCTP_INP_INFO_WLOCK()
    1.63 +#define SCTP_INP_INFO_WUNLOCK()
    1.64 +#define SCTP_INP_INFO_LOCK_DESTROY()
    1.65 +#define SCTP_IPI_COUNT_INIT()
    1.66 +#define SCTP_IPI_COUNT_DESTROY()
    1.67 +#else
    1.68 +#define SCTP_INP_INFO_LOCK_INIT()
    1.69 +#define SCTP_INP_INFO_RLOCK()
    1.70 +#define SCTP_INP_INFO_RUNLOCK()
    1.71 +#define SCTP_INP_INFO_WLOCK()
    1.72 +#define SCTP_INP_INFO_WUNLOCK()
    1.73 +#define SCTP_INP_INFO_LOCK_DESTROY()
    1.74 +#define SCTP_IPI_COUNT_INIT()
    1.75 +#define SCTP_IPI_COUNT_DESTROY()
    1.76 +#endif
    1.77 +
    1.78 +#define SCTP_TCB_SEND_LOCK_INIT(_tcb)
    1.79 +#define SCTP_TCB_SEND_LOCK_DESTROY(_tcb)
    1.80 +#define SCTP_TCB_SEND_LOCK(_tcb)
    1.81 +#define SCTP_TCB_SEND_UNLOCK(_tcb)
    1.82 +
    1.83 +/* Lock for INP */
    1.84 +#define SCTP_INP_LOCK_INIT(_inp)
    1.85 +#define SCTP_INP_LOCK_DESTROY(_inp)
    1.86 +
    1.87 +#define SCTP_INP_RLOCK(_inp)
    1.88 +#define SCTP_INP_RUNLOCK(_inp)
    1.89 +#define SCTP_INP_WLOCK(_inp)
    1.90 +#define SCTP_INP_WUNLOCK(_inep)
    1.91 +#define SCTP_INP_INCR_REF(_inp)
    1.92 +#define SCTP_INP_DECR_REF(_inp)
    1.93 +
    1.94 +#define SCTP_ASOC_CREATE_LOCK_INIT(_inp)
    1.95 +#define SCTP_ASOC_CREATE_LOCK_DESTROY(_inp)
    1.96 +#define SCTP_ASOC_CREATE_LOCK(_inp)
    1.97 +#define SCTP_ASOC_CREATE_UNLOCK(_inp)
    1.98 +
    1.99 +#define SCTP_INP_READ_INIT(_inp)
   1.100 +#define SCTP_INP_READ_DESTROY(_inp)
   1.101 +#define SCTP_INP_READ_LOCK(_inp)
   1.102 +#define SCTP_INP_READ_UNLOCK(_inp)
   1.103 +
   1.104 +/* Lock for TCB */
   1.105 +#define SCTP_TCB_LOCK_INIT(_tcb)
   1.106 +#define SCTP_TCB_LOCK_DESTROY(_tcb)
   1.107 +#define SCTP_TCB_LOCK(_tcb)
   1.108 +#define SCTP_TCB_TRYLOCK(_tcb) 1
   1.109 +#define SCTP_TCB_UNLOCK(_tcb)
   1.110 +#define SCTP_TCB_UNLOCK_IFOWNED(_tcb)
   1.111 +#define SCTP_TCB_LOCK_ASSERT(_tcb)
   1.112 +
   1.113 +#else
   1.114 +/*
   1.115 + * per tcb level locking
   1.116 + */
   1.117 +#define SCTP_IPI_COUNT_INIT()
   1.118 +
   1.119 +#if defined(__Userspace_os_Windows)
   1.120 +#define SCTP_WQ_ADDR_INIT() \
   1.121 +        InitializeCriticalSection(&SCTP_BASE_INFO(wq_addr_mtx))
   1.122 +#define SCTP_WQ_ADDR_DESTROY() \
   1.123 +	DeleteCriticalSection(&SCTP_BASE_INFO(wq_addr_mtx))
   1.124 +#define SCTP_WQ_ADDR_LOCK() \
   1.125 +        EnterCriticalSection(&SCTP_BASE_INFO(wq_addr_mtx))
   1.126 +#define SCTP_WQ_ADDR_UNLOCK() \
   1.127 +        LeaveCriticalSection(&SCTP_BASE_INFO(wq_addr_mtx))
   1.128 +
   1.129 +
   1.130 +#define SCTP_INP_INFO_LOCK_INIT() \
   1.131 +	InitializeCriticalSection(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.132 +#define SCTP_INP_INFO_LOCK_DESTROY() \
   1.133 +	DeleteCriticalSection(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.134 +#define SCTP_INP_INFO_RLOCK() \
   1.135 +	EnterCriticalSection(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.136 +#define SCTP_INP_INFO_TRYLOCK()	\
   1.137 +        TryEnterCriticalSection(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.138 +#define SCTP_INP_INFO_WLOCK() \
   1.139 +	EnterCriticalSection(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.140 +#define SCTP_INP_INFO_RUNLOCK() \
   1.141 + 	LeaveCriticalSection(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.142 +#define SCTP_INP_INFO_WUNLOCK()	\
   1.143 +	LeaveCriticalSection(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.144 +
   1.145 +#define SCTP_IP_PKTLOG_INIT() \
   1.146 +        InitializeCriticalSection(&SCTP_BASE_INFO(ipi_pktlog_mtx))
   1.147 +#define SCTP_IP_PKTLOG_DESTROY () \
   1.148 +	DeleteCriticalSection(&SCTP_BASE_INFO(ipi_pktlog_mtx))
   1.149 +#define SCTP_IP_PKTLOG_LOCK() \
   1.150 +    	EnterCriticalSection(&SCTP_BASE_INFO(ipi_pktlog_mtx))
   1.151 +#define SCTP_IP_PKTLOG_UNLOCK() \
   1.152 +	LeaveCriticalSection(&SCTP_BASE_INFO(ipi_pktlog_mtx))
   1.153 +
   1.154 +/*
   1.155 + * The INP locks we will use for locking an SCTP endpoint, so for example if
   1.156 + * we want to change something at the endpoint level for example random_store
   1.157 + * or cookie secrets we lock the INP level.
   1.158 + */
   1.159 +#define SCTP_INP_READ_INIT(_inp) \
   1.160 +	InitializeCriticalSection(&(_inp)->inp_rdata_mtx)
   1.161 +#define SCTP_INP_READ_DESTROY(_inp) \
   1.162 +	DeleteCriticalSection(&(_inp)->inp_rdata_mtx)
   1.163 +#define SCTP_INP_READ_LOCK(_inp) \
   1.164 +	EnterCriticalSection(&(_inp)->inp_rdata_mtx)
   1.165 +#define SCTP_INP_READ_UNLOCK(_inp) \
   1.166 +	LeaveCriticalSection(&(_inp)->inp_rdata_mtx)
   1.167 +
   1.168 +#define SCTP_INP_LOCK_INIT(_inp) \
   1.169 +	InitializeCriticalSection(&(_inp)->inp_mtx)
   1.170 +
   1.171 +#define SCTP_ASOC_CREATE_LOCK_INIT(_inp) \
   1.172 +	InitializeCriticalSection(&(_inp)->inp_create_mtx)
   1.173 +
   1.174 +#define SCTP_INP_LOCK_DESTROY(_inp) \
   1.175 +	DeleteCriticalSection(&(_inp)->inp_mtx)
   1.176 +
   1.177 +#define SCTP_ASOC_CREATE_LOCK_DESTROY(_inp) \
   1.178 +	DeleteCriticalSection(&(_inp)->inp_create_mtx)
   1.179 +
   1.180 +#ifdef SCTP_LOCK_LOGGING
   1.181 +#define SCTP_INP_RLOCK(_inp)	do { 					\
   1.182 +	if(SCTP_BASE_SYSCTL(sctp_logging_level) & SCTP_LOCK_LOGGING_ENABLE) sctp_log_lock(_inp, (struct sctp_tcb *)NULL, SCTP_LOG_LOCK_INP);\
   1.183 +	EnterCriticalSection(&(_inp)->inp_mtx);			\
   1.184 +} while (0)
   1.185 +
   1.186 +#define SCTP_INP_WLOCK(_inp)	do { 					\
   1.187 +	sctp_log_lock(_inp, (struct sctp_tcb *)NULL, SCTP_LOG_LOCK_INP);\
   1.188 +	EnterCriticalSection(&(_inp)->inp_mtx);			\
   1.189 +} while (0)
   1.190 +#else
   1.191 +
   1.192 +#define SCTP_INP_RLOCK(_inp)	do { 					\
   1.193 +	EnterCriticalSection(&(_inp)->inp_mtx);			\
   1.194 +} while (0)
   1.195 +
   1.196 +#define SCTP_INP_WLOCK(_inp)	do { 					\
   1.197 +	EnterCriticalSection(&(_inp)->inp_mtx);			\
   1.198 +} while (0)
   1.199 +#endif
   1.200 +
   1.201 +
   1.202 +#define SCTP_TCB_SEND_LOCK_INIT(_tcb) \
   1.203 +	InitializeCriticalSection(&(_tcb)->tcb_send_mtx)
   1.204 +
   1.205 +#define SCTP_TCB_SEND_LOCK_DESTROY(_tcb) \
   1.206 +	DeleteCriticalSection(&(_tcb)->tcb_send_mtx)
   1.207 +
   1.208 +#define SCTP_TCB_SEND_LOCK(_tcb) do { \
   1.209 +	EnterCriticalSection(&(_tcb)->tcb_send_mtx); \
   1.210 +} while (0)
   1.211 +
   1.212 +#define SCTP_TCB_SEND_UNLOCK(_tcb) \
   1.213 +	LeaveCriticalSection(&(_tcb)->tcb_send_mtx)
   1.214 +
   1.215 +#define SCTP_INP_INCR_REF(_inp) atomic_add_int(&((_inp)->refcount), 1)
   1.216 +#define SCTP_INP_DECR_REF(_inp) atomic_add_int(&((_inp)->refcount), -1)
   1.217 +
   1.218 +#ifdef SCTP_LOCK_LOGGING
   1.219 +#define SCTP_ASOC_CREATE_LOCK(_inp) do {				\
   1.220 +	if(SCTP_BASE_SYSCTL(sctp_logging_level) & SCTP_LOCK_LOGGING_ENABLE) sctp_log_lock(_inp, (struct sctp_tcb *)NULL, SCTP_LOG_LOCK_CREATE); \
   1.221 +	EnterCriticalSection(&(_inp)->inp_create_mtx);		\
   1.222 +} while (0)
   1.223 +#else
   1.224 +#define SCTP_ASOC_CREATE_LOCK(_inp) do {				\
   1.225 +	EnterCriticalSection(&(_inp)->inp_create_mtx);		\
   1.226 +} while (0)
   1.227 +#endif
   1.228 +
   1.229 +#define SCTP_INP_RUNLOCK(_inp) \
   1.230 +	LeaveCriticalSection(&(_inp)->inp_mtx)
   1.231 +#define SCTP_INP_WUNLOCK(_inp) \
   1.232 +	LeaveCriticalSection(&(_inp)->inp_mtx)
   1.233 +#define SCTP_ASOC_CREATE_UNLOCK(_inp) \
   1.234 +	LeaveCriticalSection(&(_inp)->inp_create_mtx)
   1.235 +
   1.236 +/*
   1.237 + * For the majority of things (once we have found the association) we will
   1.238 + * lock the actual association mutex. This will protect all the assoiciation
   1.239 + * level queues and streams and such. We will need to lock the socket layer
   1.240 + * when we stuff data up into the receiving sb_mb. I.e. we will need to do an
   1.241 + * extra SOCKBUF_LOCK(&so->so_rcv) even though the association is locked.
   1.242 + */
   1.243 +
   1.244 +#define SCTP_TCB_LOCK_INIT(_tcb) \
   1.245 +	InitializeCriticalSection(&(_tcb)->tcb_mtx)
   1.246 +
   1.247 +#define SCTP_TCB_LOCK_DESTROY(_tcb) \
   1.248 +	DeleteCriticalSection(&(_tcb)->tcb_mtx)
   1.249 +
   1.250 +#ifdef SCTP_LOCK_LOGGING
   1.251 +#define SCTP_TCB_LOCK(_tcb)  do {					\
   1.252 +	if(SCTP_BASE_SYSCTL(sctp_logging_level) & SCTP_LOCK_LOGGING_ENABLE) sctp_log_lock(_tcb->sctp_ep, _tcb, SCTP_LOG_LOCK_TCB);		\
   1.253 +	EnterCriticalSection(&(_tcb)->tcb_mtx);			\
   1.254 +} while (0)
   1.255 +
   1.256 +#else
   1.257 +#define SCTP_TCB_LOCK(_tcb)  do {					\
   1.258 +	EnterCriticalSection(&(_tcb)->tcb_mtx);			\
   1.259 +} while (0)
   1.260 +#endif
   1.261 +
   1.262 +#define SCTP_TCB_TRYLOCK(_tcb) 	((TryEnterCriticalSection(&(_tcb)->tcb_mtx)))
   1.263 +
   1.264 +#define SCTP_TCB_UNLOCK(_tcb)	do {  \
   1.265 +	LeaveCriticalSection(&(_tcb)->tcb_mtx);  \
   1.266 +} while (0)
   1.267 +
   1.268 +#define SCTP_TCB_LOCK_ASSERT(_tcb)
   1.269 +
   1.270 +#else /* all Userspaces except Windows */
   1.271 +#define SCTP_WQ_ADDR_INIT() \
   1.272 +        (void)pthread_mutex_init(&SCTP_BASE_INFO(wq_addr_mtx), NULL)
   1.273 +#define SCTP_WQ_ADDR_DESTROY() \
   1.274 +	(void)pthread_mutex_destroy(&SCTP_BASE_INFO(wq_addr_mtx))
   1.275 +#define SCTP_WQ_ADDR_LOCK() \
   1.276 +        (void)pthread_mutex_lock(&SCTP_BASE_INFO(wq_addr_mtx))
   1.277 +#define SCTP_WQ_ADDR_UNLOCK() \
   1.278 +        (void)pthread_mutex_unlock(&SCTP_BASE_INFO(wq_addr_mtx))
   1.279 +
   1.280 +
   1.281 +#define SCTP_INP_INFO_LOCK_INIT() \
   1.282 +	(void)pthread_mutex_init(&SCTP_BASE_INFO(ipi_ep_mtx), NULL)
   1.283 +#define SCTP_INP_INFO_LOCK_DESTROY() \
   1.284 +	(void)pthread_mutex_destroy(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.285 +#define SCTP_INP_INFO_RLOCK() \
   1.286 +	(void)pthread_mutex_lock(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.287 +#define SCTP_INP_INFO_TRYLOCK()	\
   1.288 +        (!(pthread_mutex_trylock(&SCTP_BASE_INFO(ipi_ep_mtx))))
   1.289 +#define SCTP_INP_INFO_WLOCK() \
   1.290 +	(void)pthread_mutex_lock(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.291 +#define SCTP_INP_INFO_RUNLOCK()	\
   1.292 +	(void)pthread_mutex_unlock(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.293 +#define SCTP_INP_INFO_WUNLOCK()	\
   1.294 +	(void)pthread_mutex_unlock(&SCTP_BASE_INFO(ipi_ep_mtx))
   1.295 +
   1.296 +#define SCTP_IP_PKTLOG_INIT() \
   1.297 +        (void)pthread_mutex_init(&SCTP_BASE_INFO(ipi_pktlog_mtx), NULL)
   1.298 +#define SCTP_IP_PKTLOG_DESTROY() \
   1.299 +	(void)pthread_mutex_destroy(&SCTP_BASE_INFO(ipi_pktlog_mtx))
   1.300 +#define SCTP_IP_PKTLOG_LOCK() \
   1.301 +        (void)pthread_mutex_lock(&SCTP_BASE_INFO(ipi_pktlog_mtx))
   1.302 +#define SCTP_IP_PKTLOG_UNLOCK()	\
   1.303 +        (void)pthread_mutex_unlock(&SCTP_BASE_INFO(ipi_pktlog_mtx))
   1.304 +
   1.305 +
   1.306 +
   1.307 +/*
   1.308 + * The INP locks we will use for locking an SCTP endpoint, so for example if
   1.309 + * we want to change something at the endpoint level for example random_store
   1.310 + * or cookie secrets we lock the INP level.
   1.311 + */
   1.312 +#define SCTP_INP_READ_INIT(_inp) \
   1.313 +	(void)pthread_mutex_init(&(_inp)->inp_rdata_mtx, NULL)
   1.314 +
   1.315 +#define SCTP_INP_READ_DESTROY(_inp) \
   1.316 +	(void)pthread_mutex_destroy(&(_inp)->inp_rdata_mtx)
   1.317 +
   1.318 +#define SCTP_INP_READ_LOCK(_inp)	do { \
   1.319 +	(void)pthread_mutex_lock(&(_inp)->inp_rdata_mtx);    \
   1.320 +} while (0)
   1.321 +
   1.322 +
   1.323 +#define SCTP_INP_READ_UNLOCK(_inp) \
   1.324 +	(void)pthread_mutex_unlock(&(_inp)->inp_rdata_mtx)
   1.325 +
   1.326 +#define SCTP_INP_LOCK_INIT(_inp) \
   1.327 +	(void)pthread_mutex_init(&(_inp)->inp_mtx, NULL)
   1.328 +
   1.329 +#define SCTP_ASOC_CREATE_LOCK_INIT(_inp) \
   1.330 +	(void)pthread_mutex_init(&(_inp)->inp_create_mtx, NULL)
   1.331 +
   1.332 +#define SCTP_INP_LOCK_DESTROY(_inp) \
   1.333 +	(void)pthread_mutex_destroy(&(_inp)->inp_mtx)
   1.334 +
   1.335 +#define SCTP_ASOC_CREATE_LOCK_DESTROY(_inp) \
   1.336 +	(void)pthread_mutex_destroy(&(_inp)->inp_create_mtx)
   1.337 +
   1.338 +#ifdef SCTP_LOCK_LOGGING
   1.339 +#define SCTP_INP_RLOCK(_inp)	do { 					\
   1.340 +	if(SCTP_BASE_SYSCTL(sctp_logging_level) & SCTP_LOCK_LOGGING_ENABLE) sctp_log_lock(_inp, (struct sctp_tcb *)NULL, SCTP_LOG_LOCK_INP);\
   1.341 +	(void)pthread_mutex_lock(&(_inp)->inp_mtx);			\
   1.342 +} while (0)
   1.343 +
   1.344 +#define SCTP_INP_WLOCK(_inp)	do { 					\
   1.345 +	sctp_log_lock(_inp, (struct sctp_tcb *)NULL, SCTP_LOG_LOCK_INP);\
   1.346 +	(void)pthread_mutex_lock(&(_inp)->inp_mtx);			\
   1.347 +} while (0)
   1.348 +
   1.349 +#else
   1.350 +
   1.351 +#define SCTP_INP_RLOCK(_inp)	do { 					\
   1.352 +	(void)pthread_mutex_lock(&(_inp)->inp_mtx);			\
   1.353 +} while (0)
   1.354 +
   1.355 +#define SCTP_INP_WLOCK(_inp)	do { 					\
   1.356 +	(void)pthread_mutex_lock(&(_inp)->inp_mtx);			\
   1.357 +} while (0)
   1.358 +#endif
   1.359 +
   1.360 +
   1.361 +#define SCTP_TCB_SEND_LOCK_INIT(_tcb) \
   1.362 +	(void)pthread_mutex_init(&(_tcb)->tcb_send_mtx, NULL)
   1.363 +
   1.364 +#define SCTP_TCB_SEND_LOCK_DESTROY(_tcb) \
   1.365 +	(void)pthread_mutex_destroy(&(_tcb)->tcb_send_mtx)
   1.366 +
   1.367 +#define SCTP_TCB_SEND_LOCK(_tcb) do { \
   1.368 +	(void)pthread_mutex_lock(&(_tcb)->tcb_send_mtx); \
   1.369 +} while (0)
   1.370 +
   1.371 +#define SCTP_TCB_SEND_UNLOCK(_tcb) \
   1.372 +	(void)pthread_mutex_unlock(&(_tcb)->tcb_send_mtx)
   1.373 +
   1.374 +#define SCTP_INP_INCR_REF(_inp) atomic_add_int(&((_inp)->refcount), 1)
   1.375 +#define SCTP_INP_DECR_REF(_inp) atomic_add_int(&((_inp)->refcount), -1)
   1.376 +
   1.377 +#ifdef SCTP_LOCK_LOGGING
   1.378 +#define SCTP_ASOC_CREATE_LOCK(_inp) do {				\
   1.379 +	if(SCTP_BASE_SYSCTL(sctp_logging_level) & SCTP_LOCK_LOGGING_ENABLE) sctp_log_lock(_inp, (struct sctp_tcb *)NULL, SCTP_LOG_LOCK_CREATE); \
   1.380 +	(void)pthread_mutex_lock(&(_inp)->inp_create_mtx);		\
   1.381 +} while (0)
   1.382 +#else
   1.383 +#define SCTP_ASOC_CREATE_LOCK(_inp) do {				\
   1.384 +	(void)pthread_mutex_lock(&(_inp)->inp_create_mtx);		\
   1.385 +} while (0)
   1.386 +#endif
   1.387 +
   1.388 +#define SCTP_INP_RUNLOCK(_inp) \
   1.389 +	(void)pthread_mutex_unlock(&(_inp)->inp_mtx)
   1.390 +#define SCTP_INP_WUNLOCK(_inp) \
   1.391 +	(void)pthread_mutex_unlock(&(_inp)->inp_mtx)
   1.392 +#define SCTP_ASOC_CREATE_UNLOCK(_inp) \
   1.393 +	(void)pthread_mutex_unlock(&(_inp)->inp_create_mtx)
   1.394 +
   1.395 +/*
   1.396 + * For the majority of things (once we have found the association) we will
   1.397 + * lock the actual association mutex. This will protect all the assoiciation
   1.398 + * level queues and streams and such. We will need to lock the socket layer
   1.399 + * when we stuff data up into the receiving sb_mb. I.e. we will need to do an
   1.400 + * extra SOCKBUF_LOCK(&so->so_rcv) even though the association is locked.
   1.401 + */
   1.402 +
   1.403 +#define SCTP_TCB_LOCK_INIT(_tcb) \
   1.404 +	(void)pthread_mutex_init(&(_tcb)->tcb_mtx, NULL)
   1.405 +
   1.406 +#define SCTP_TCB_LOCK_DESTROY(_tcb) \
   1.407 +	(void)pthread_mutex_destroy(&(_tcb)->tcb_mtx)
   1.408 +
   1.409 +#ifdef SCTP_LOCK_LOGGING
   1.410 +#define SCTP_TCB_LOCK(_tcb)  do {					\
   1.411 +	if(SCTP_BASE_SYSCTL(sctp_logging_level) & SCTP_LOCK_LOGGING_ENABLE) sctp_log_lock(_tcb->sctp_ep, _tcb, SCTP_LOG_LOCK_TCB);		\
   1.412 +	(void)pthread_mutex_lock(&(_tcb)->tcb_mtx);			\
   1.413 +} while (0)
   1.414 +
   1.415 +#else
   1.416 +#define SCTP_TCB_LOCK(_tcb)  do {					\
   1.417 +	(void)pthread_mutex_lock(&(_tcb)->tcb_mtx);			\
   1.418 +} while (0)
   1.419 +#endif
   1.420 +
   1.421 +#define SCTP_TCB_TRYLOCK(_tcb) 	(!(pthread_mutex_trylock(&(_tcb)->tcb_mtx)))
   1.422 +
   1.423 +#define SCTP_TCB_UNLOCK(_tcb)	(void)pthread_mutex_unlock(&(_tcb)->tcb_mtx)
   1.424 +
   1.425 +#define SCTP_TCB_LOCK_ASSERT(_tcb)
   1.426 +#endif
   1.427 +
   1.428 +#endif /* SCTP_PER_SOCKET_LOCKING */
   1.429 +
   1.430 +
   1.431 +/*
   1.432 + * common locks
   1.433 + */
   1.434 +
   1.435 +/* copied over to compile */
   1.436 +#define SCTP_INP_LOCK_CONTENDED(_inp) (0) /* Don't know if this is possible */
   1.437 +#define SCTP_INP_READ_CONTENDED(_inp) (0) /* Don't know if this is possible */
   1.438 +#define SCTP_ASOC_CREATE_LOCK_CONTENDED(_inp) (0) /* Don't know if this is possible */
   1.439 +
   1.440 +
   1.441 +/* socket locks */
   1.442 +
   1.443 +#if defined(__Userspace__)
   1.444 +#if defined(__Userspace_os_Windows)
   1.445 +#define SOCKBUF_LOCK_ASSERT(_so_buf)
   1.446 +#define SOCKBUF_LOCK(_so_buf) EnterCriticalSection(&(_so_buf)->sb_mtx)
   1.447 +#define SOCKBUF_UNLOCK(_so_buf) LeaveCriticalSection(&(_so_buf)->sb_mtx)
   1.448 +#define SOCK_LOCK(_so)  SOCKBUF_LOCK(&(_so)->so_rcv)
   1.449 +#define SOCK_UNLOCK(_so)  SOCKBUF_UNLOCK(&(_so)->so_rcv)
   1.450 +#else
   1.451 +#define SOCKBUF_LOCK_ASSERT(_so_buf) KASSERT(pthread_mutex_trylock(SOCKBUF_MTX(_so_buf)) == EBUSY, ("%s: socket buffer not locked", __func__))
   1.452 +#define SOCKBUF_LOCK(_so_buf)   pthread_mutex_lock(SOCKBUF_MTX(_so_buf))
   1.453 +#define SOCKBUF_UNLOCK(_so_buf) pthread_mutex_unlock(SOCKBUF_MTX(_so_buf))
   1.454 +#define	SOCK_LOCK(_so)		SOCKBUF_LOCK(&(_so)->so_rcv)
   1.455 +#define	SOCK_UNLOCK(_so)	SOCKBUF_UNLOCK(&(_so)->so_rcv)
   1.456 +#endif
   1.457 +#else
   1.458 +#define SOCK_LOCK(_so)
   1.459 +#define SOCK_UNLOCK(_so)
   1.460 +#define SOCKBUF_LOCK(_so_buf)
   1.461 +#define SOCKBUF_UNLOCK(_so_buf)
   1.462 +#define SOCKBUF_LOCK_ASSERT(_so_buf)
   1.463 +#endif
   1.464 +
   1.465 +#define SCTP_STATLOG_INIT_LOCK()
   1.466 +#define SCTP_STATLOG_LOCK()
   1.467 +#define SCTP_STATLOG_UNLOCK()
   1.468 +#define SCTP_STATLOG_DESTROY()
   1.469 +
   1.470 +#if defined(__Userspace_os_Windows)
   1.471 +/* address list locks */
   1.472 +#define SCTP_IPI_ADDR_INIT() \
   1.473 +	InitializeCriticalSection(&SCTP_BASE_INFO(ipi_addr_mtx))
   1.474 +#define SCTP_IPI_ADDR_DESTROY() \
   1.475 +	DeleteCriticalSection(&SCTP_BASE_INFO(ipi_addr_mtx))
   1.476 +
   1.477 +#define SCTP_IPI_ADDR_RLOCK() 						\
   1.478 +	do { 								\
   1.479 +		EnterCriticalSection(&SCTP_BASE_INFO(ipi_addr_mtx));	\
   1.480 +	} while (0)
   1.481 +#define SCTP_IPI_ADDR_RUNLOCK() \
   1.482 +	LeaveCriticalSection(&SCTP_BASE_INFO(ipi_addr_mtx))
   1.483 +
   1.484 +#define SCTP_IPI_ADDR_WLOCK() 						\
   1.485 +	do { 								\
   1.486 +		EnterCriticalSection(&SCTP_BASE_INFO(ipi_addr_mtx));	\
   1.487 +	} while (0)
   1.488 +#define SCTP_IPI_ADDR_WUNLOCK() \
   1.489 +	LeaveCriticalSection(&SCTP_BASE_INFO(ipi_addr_mtx))
   1.490 +
   1.491 +
   1.492 +/* iterator locks */
   1.493 +#define SCTP_ITERATOR_LOCK_INIT() \
   1.494 +	InitializeCriticalSection(&sctp_it_ctl.it_mtx)
   1.495 +
   1.496 +#define SCTP_ITERATOR_LOCK() 						\
   1.497 +	do {								\
   1.498 +		EnterCriticalSection(&sctp_it_ctl.it_mtx);		\
   1.499 +	} while (0)
   1.500 +
   1.501 +#define SCTP_ITERATOR_UNLOCK() \
   1.502 +	LeaveCriticalSection(&sctp_it_ctl.it_mtx)
   1.503 +
   1.504 +#define SCTP_ITERATOR_LOCK_DESTROY() \
   1.505 +	DeleteCriticalSection(&sctp_it_ctl.it_mtx)
   1.506 +
   1.507 +
   1.508 +#define SCTP_IPI_ITERATOR_WQ_INIT() \
   1.509 +	InitializeCriticalSection(&sctp_it_ctl.ipi_iterator_wq_mtx)
   1.510 +
   1.511 +#define SCTP_IPI_ITERATOR_WQ_DESTROY() \
   1.512 +	DeleteCriticalSection(&sctp_it_ctl.ipi_iterator_wq_mtx)
   1.513 +
   1.514 +#define SCTP_IPI_ITERATOR_WQ_LOCK() \
   1.515 +	do { \
   1.516 +		EnterCriticalSection(&sctp_it_ctl.ipi_iterator_wq_mtx); \
   1.517 +	} while (0)
   1.518 +
   1.519 +#define SCTP_IPI_ITERATOR_WQ_UNLOCK() \
   1.520 +	LeaveCriticalSection(&sctp_it_ctl.ipi_iterator_wq_mtx)
   1.521 +
   1.522 +#else /* end of __Userspace_os_Windows */
   1.523 +/* address list locks */
   1.524 +#define SCTP_IPI_ADDR_INIT() \
   1.525 +	(void)pthread_mutex_init(&SCTP_BASE_INFO(ipi_addr_mtx), NULL)
   1.526 +#define SCTP_IPI_ADDR_DESTROY() \
   1.527 +	(void)pthread_mutex_destroy(&SCTP_BASE_INFO(ipi_addr_mtx))
   1.528 +
   1.529 +#define SCTP_IPI_ADDR_RLOCK() 						\
   1.530 +	do { 								\
   1.531 +		(void)pthread_mutex_lock(&SCTP_BASE_INFO(ipi_addr_mtx));	\
   1.532 +	} while (0)
   1.533 +#define SCTP_IPI_ADDR_RUNLOCK() \
   1.534 +	(void)pthread_mutex_unlock(&SCTP_BASE_INFO(ipi_addr_mtx))
   1.535 +
   1.536 +#define SCTP_IPI_ADDR_WLOCK() 						\
   1.537 +	do { 								\
   1.538 +		(void)pthread_mutex_lock(&SCTP_BASE_INFO(ipi_addr_mtx));	\
   1.539 +	} while (0)
   1.540 +#define SCTP_IPI_ADDR_WUNLOCK() \
   1.541 +	(void)pthread_mutex_unlock(&SCTP_BASE_INFO(ipi_addr_mtx))
   1.542 +
   1.543 +
   1.544 +/* iterator locks */
   1.545 +#define SCTP_ITERATOR_LOCK_INIT() \
   1.546 +	(void)pthread_mutex_init(&sctp_it_ctl.it_mtx, NULL)
   1.547 +
   1.548 +#define SCTP_ITERATOR_LOCK() 						\
   1.549 +	do {								\
   1.550 +		(void)pthread_mutex_lock(&sctp_it_ctl.it_mtx);		\
   1.551 +	} while (0)
   1.552 +
   1.553 +#define SCTP_ITERATOR_UNLOCK() \
   1.554 +	(void)pthread_mutex_unlock(&sctp_it_ctl.it_mtx)
   1.555 +
   1.556 +#define SCTP_ITERATOR_LOCK_DESTROY() \
   1.557 +	(void)pthread_mutex_destroy(&sctp_it_ctl.it_mtx)
   1.558 +
   1.559 +
   1.560 +#define SCTP_IPI_ITERATOR_WQ_INIT() \
   1.561 +	(void)pthread_mutex_init(&sctp_it_ctl.ipi_iterator_wq_mtx, NULL)
   1.562 +
   1.563 +#define SCTP_IPI_ITERATOR_WQ_DESTROY() \
   1.564 +	(void)pthread_mutex_destroy(&sctp_it_ctl.ipi_iterator_wq_mtx)
   1.565 +
   1.566 +#define SCTP_IPI_ITERATOR_WQ_LOCK() \
   1.567 +	do { \
   1.568 +		(void)pthread_mutex_lock(&sctp_it_ctl.ipi_iterator_wq_mtx); \
   1.569 +	} while (0)
   1.570 +
   1.571 +#define SCTP_IPI_ITERATOR_WQ_UNLOCK() \
   1.572 +	(void)pthread_mutex_unlock(&sctp_it_ctl.ipi_iterator_wq_mtx)
   1.573 +#endif
   1.574 +
   1.575 +#define SCTP_INCR_EP_COUNT() \
   1.576 +	do { \
   1.577 +		atomic_add_int(&SCTP_BASE_INFO(ipi_count_ep), 1); \
   1.578 +	} while (0)
   1.579 +
   1.580 +#define SCTP_DECR_EP_COUNT() \
   1.581 +	do { \
   1.582 +	       atomic_subtract_int(&SCTP_BASE_INFO(ipi_count_ep), 1); \
   1.583 +	} while (0)
   1.584 +
   1.585 +#define SCTP_INCR_ASOC_COUNT() \
   1.586 +	do { \
   1.587 +	       atomic_add_int(&SCTP_BASE_INFO(ipi_count_asoc), 1); \
   1.588 +	} while (0)
   1.589 +
   1.590 +#define SCTP_DECR_ASOC_COUNT() \
   1.591 +	do { \
   1.592 +	       atomic_subtract_int(&SCTP_BASE_INFO(ipi_count_asoc), 1); \
   1.593 +	} while (0)
   1.594 +
   1.595 +#define SCTP_INCR_LADDR_COUNT() \
   1.596 +	do { \
   1.597 +	       atomic_add_int(&SCTP_BASE_INFO(ipi_count_laddr), 1); \
   1.598 +	} while (0)
   1.599 +
   1.600 +#define SCTP_DECR_LADDR_COUNT() \
   1.601 +	do { \
   1.602 +	       atomic_subtract_int(&SCTP_BASE_INFO(ipi_count_laddr), 1); \
   1.603 +	} while (0)
   1.604 +
   1.605 +#define SCTP_INCR_RADDR_COUNT() \
   1.606 +	do { \
   1.607 + 	       atomic_add_int(&SCTP_BASE_INFO(ipi_count_raddr), 1); \
   1.608 +	} while (0)
   1.609 +
   1.610 +#define SCTP_DECR_RADDR_COUNT() \
   1.611 +	do { \
   1.612 + 	       atomic_subtract_int(&SCTP_BASE_INFO(ipi_count_raddr), 1); \
   1.613 +	} while (0)
   1.614 +
   1.615 +#define SCTP_INCR_CHK_COUNT() \
   1.616 +	do { \
   1.617 +  	       atomic_add_int(&SCTP_BASE_INFO(ipi_count_chunk), 1); \
   1.618 +	} while (0)
   1.619 +
   1.620 +#define SCTP_DECR_CHK_COUNT() \
   1.621 +	do { \
   1.622 +  	       atomic_subtract_int(&SCTP_BASE_INFO(ipi_count_chunk), 1); \
   1.623 +	} while (0)
   1.624 +
   1.625 +#define SCTP_INCR_READQ_COUNT() \
   1.626 +	do { \
   1.627 +	       atomic_add_int(&SCTP_BASE_INFO(ipi_count_readq), 1); \
   1.628 +	} while (0)
   1.629 +
   1.630 +#define SCTP_DECR_READQ_COUNT() \
   1.631 +	do { \
   1.632 +	       atomic_subtract_int(&SCTP_BASE_INFO(ipi_count_readq), 1); \
   1.633 +	} while (0)
   1.634 +
   1.635 +#define SCTP_INCR_STRMOQ_COUNT() \
   1.636 +	do { \
   1.637 +	       atomic_add_int(&SCTP_BASE_INFO(ipi_count_strmoq), 1); \
   1.638 +	} while (0)
   1.639 +
   1.640 +#define SCTP_DECR_STRMOQ_COUNT() \
   1.641 +	do { \
   1.642 +	       atomic_subtract_int(&SCTP_BASE_INFO(ipi_count_strmoq), 1); \
   1.643 +	} while (0)
   1.644 +
   1.645 +#endif

mercurial