1 /* 2 * Copyright (c) 2001 Daniel Eischen <deischen@FreeBSD.org>. 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 14 * THIS SOFTWARE IS PROVIDED BY DANIEL EISCHEN AND CONTRIBUTORS ``AS IS'' 15 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 18 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24 * SUCH DAMAGE. 25 */ 26 27 #include <sys/cdefs.h> 28 __FBSDID("$FreeBSD$"); 29 30 #include <signal.h> 31 #include <pthread.h> 32 #include <pthread_np.h> 33 34 void *_pthread_getspecific(pthread_key_t key); 35 pthread_t _pthread_self(void); 36 37 /* 38 * Weak symbols: All libc internal usage of these functions should 39 * use the weak symbol versions (_pthread_XXX). If libpthread is 40 * linked, it will override these functions with (non-weak) routines. 41 * The _pthread_XXX functions are provided solely for internal libc 42 * usage to avoid unwanted cancellation points and to differentiate 43 * between application locks and libc locks (threads holding the 44 * latter can't be allowed to exit/terminate). 45 * 46 * We also provide weak pthread_XXX stubs which call their 47 * _pthread_XXX counterparts. These stubs may be used be other 48 * libraries for ensuring thread-safety without requiring the presence 49 * of a thread library. 50 */ 51 __weak_reference(_pthread_cond_init_stub, _pthread_cond_init); 52 __weak_reference(_pthread_cond_signal_stub, _pthread_cond_signal); 53 __weak_reference(_pthread_cond_broadcast_stub, _pthread_cond_broadcast); 54 __weak_reference(_pthread_cond_wait_stub, _pthread_cond_wait); 55 __weak_reference(_pthread_cond_destroy_stub, _pthread_cond_destroy); 56 __weak_reference(_pthread_getspecific_stub, _pthread_getspecific); 57 __weak_reference(_pthread_key_create_stub, _pthread_key_create); 58 __weak_reference(_pthread_key_delete_stub, _pthread_key_delete); 59 __weak_reference(_pthread_main_np_stub, _pthread_main_np); 60 __weak_reference(_pthread_mutex_destroy_stub, _pthread_mutex_destroy); 61 __weak_reference(_pthread_mutex_init_stub, _pthread_mutex_init); 62 __weak_reference(_pthread_mutex_lock_stub, _pthread_mutex_lock); 63 __weak_reference(_pthread_mutex_trylock_stub, _pthread_mutex_trylock); 64 __weak_reference(_pthread_mutex_unlock_stub, _pthread_mutex_unlock); 65 __weak_reference(_pthread_mutexattr_init_stub, _pthread_mutexattr_init); 66 __weak_reference(_pthread_mutexattr_destroy_stub, _pthread_mutexattr_destroy); 67 __weak_reference(_pthread_mutexattr_settype_stub, _pthread_mutexattr_settype); 68 __weak_reference(_pthread_once_stub, _pthread_once); 69 __weak_reference(_pthread_self_stub, _pthread_self); 70 __weak_reference(_pthread_rwlock_init_stub, _pthread_rwlock_init); 71 __weak_reference(_pthread_rwlock_destroy_stub, _pthread_rwlock_destroy); 72 __weak_reference(_pthread_rwlock_rdlock_stub, _pthread_rwlock_rdlock); 73 __weak_reference(_pthread_rwlock_tryrdlock_stub, _pthread_rwlock_tryrdlock); 74 __weak_reference(_pthread_rwlock_trywrlock_stub, _pthread_rwlock_trywrlock); 75 __weak_reference(_pthread_rwlock_unlock_stub, _pthread_rwlock_unlock); 76 __weak_reference(_pthread_rwlock_wrlock_stub, _pthread_rwlock_wrlock); 77 __weak_reference(_pthread_setspecific_stub, _pthread_setspecific); 78 __weak_reference(_pthread_sigmask_stub, _pthread_sigmask); 79 80 __weak_reference(pthread_cond_init_stub, pthread_cond_init); 81 __weak_reference(pthread_cond_signal_stub, pthread_cond_signal); 82 __weak_reference(pthread_cond_broadcast_stub, pthread_cond_broadcast); 83 __weak_reference(pthread_cond_wait_stub, pthread_cond_wait); 84 __weak_reference(pthread_cond_destroy_stub, pthread_cond_destroy); 85 __weak_reference(pthread_getspecific_stub, pthread_getspecific); 86 __weak_reference(pthread_key_create_stub, pthread_key_create); 87 __weak_reference(pthread_key_delete_stub, pthread_key_delete); 88 __weak_reference(pthread_main_np_stub, pthread_main_np); 89 __weak_reference(pthread_mutex_destroy_stub, pthread_mutex_destroy); 90 __weak_reference(pthread_mutex_init_stub, pthread_mutex_init); 91 __weak_reference(pthread_mutex_lock_stub, pthread_mutex_lock); 92 __weak_reference(pthread_mutex_trylock_stub, pthread_mutex_trylock); 93 __weak_reference(pthread_mutex_unlock_stub, pthread_mutex_unlock); 94 __weak_reference(pthread_mutexattr_init_stub, pthread_mutexattr_init); 95 __weak_reference(pthread_mutexattr_destroy_stub, pthread_mutexattr_destroy); 96 __weak_reference(pthread_mutexattr_settype_stub, pthread_mutexattr_settype); 97 __weak_reference(pthread_once_stub, pthread_once); 98 __weak_reference(pthread_self_stub, pthread_self); 99 __weak_reference(pthread_rwlock_init_stub, pthread_rwlock_init); 100 __weak_reference(pthread_rwlock_destroy_stub, pthread_rwlock_destroy); 101 __weak_reference(pthread_rwlock_rdlock_stub, pthread_rwlock_rdlock); 102 __weak_reference(pthread_rwlock_tryrdlock_stub, pthread_rwlock_tryrdlock); 103 __weak_reference(pthread_rwlock_trywrlock_stub, pthread_rwlock_trywrlock); 104 __weak_reference(pthread_rwlock_unlock_stub, pthread_rwlock_unlock); 105 __weak_reference(pthread_rwlock_wrlock_stub, pthread_rwlock_wrlock); 106 __weak_reference(pthread_setspecific_stub, pthread_setspecific); 107 __weak_reference(pthread_sigmask_stub, pthread_sigmask); 108 109 /* Define a null pthread structure just to satisfy _pthread_self. */ 110 struct pthread { 111 }; 112 113 static struct pthread main_thread; 114 115 static int 116 _pthread_cond_init_stub(pthread_cond_t *cond, 117 const pthread_condattr_t *cond_attr) 118 { 119 return (0); 120 } 121 122 static int 123 _pthread_cond_signal_stub(pthread_cond_t *cond) 124 { 125 return (0); 126 } 127 128 static int 129 _pthread_cond_broadcast_stub(pthread_cond_t *cond) 130 { 131 return (0); 132 } 133 134 static int 135 _pthread_cond_wait_stub(pthread_cond_t *cond, pthread_mutex_t *mutex) 136 { 137 return (0); 138 } 139 140 static int 141 _pthread_cond_destroy_stub(pthread_cond_t *cond) 142 { 143 return (0); 144 } 145 146 static void * 147 _pthread_getspecific_stub(pthread_key_t key) 148 { 149 return (NULL); 150 } 151 152 static int 153 _pthread_key_create_stub(pthread_key_t *key, void (*destructor) (void *)) 154 { 155 return (0); 156 } 157 158 static int 159 _pthread_key_delete_stub(pthread_key_t key) 160 { 161 return (0); 162 } 163 164 static int 165 _pthread_main_np_stub() 166 { 167 return (-1); 168 } 169 170 static int 171 _pthread_mutex_destroy_stub(pthread_mutex_t *mattr) 172 { 173 return (0); 174 } 175 176 static int 177 _pthread_mutex_init_stub(pthread_mutex_t *mutex, const pthread_mutexattr_t *mattr) 178 { 179 return (0); 180 } 181 182 static int 183 _pthread_mutex_lock_stub(pthread_mutex_t *mutex) 184 { 185 return (0); 186 } 187 188 static int 189 _pthread_mutex_trylock_stub(pthread_mutex_t *mutex) 190 { 191 return (0); 192 } 193 194 static int 195 _pthread_mutex_unlock_stub(pthread_mutex_t *mutex) 196 { 197 return (0); 198 } 199 200 static int 201 _pthread_mutexattr_init_stub(pthread_mutexattr_t *mattr) 202 { 203 return (0); 204 } 205 206 static int 207 _pthread_mutexattr_destroy_stub(pthread_mutexattr_t *mattr) 208 { 209 return (0); 210 } 211 212 static int 213 _pthread_mutexattr_settype_stub(pthread_mutexattr_t *mattr, int type) 214 { 215 return (0); 216 } 217 218 static int 219 _pthread_once_stub(pthread_once_t *once_control, void (*init_routine) (void)) 220 { 221 return (0); 222 } 223 224 static int 225 _pthread_rwlock_init_stub(pthread_rwlock_t *rwlock, 226 const pthread_rwlockattr_t *attr) 227 { 228 return (0); 229 } 230 231 static int 232 _pthread_rwlock_destroy_stub(pthread_rwlock_t *rwlock) 233 { 234 return (0); 235 } 236 237 static int 238 _pthread_rwlock_rdlock_stub(pthread_rwlock_t *rwlock) 239 { 240 return (0); 241 } 242 243 static int 244 _pthread_rwlock_tryrdlock_stub(pthread_rwlock_t *rwlock) 245 { 246 return (0); 247 } 248 249 static int 250 _pthread_rwlock_trywrlock_stub(pthread_rwlock_t *rwlock) 251 { 252 return (0); 253 } 254 255 static int 256 _pthread_rwlock_unlock_stub(pthread_rwlock_t *rwlock) 257 { 258 return (0); 259 } 260 261 static int 262 _pthread_rwlock_wrlock_stub(pthread_rwlock_t *rwlock) 263 { 264 return (0); 265 } 266 267 static pthread_t 268 _pthread_self_stub(void) 269 { 270 return (&main_thread); 271 } 272 273 static int 274 _pthread_setspecific_stub(pthread_key_t key, const void *value) 275 { 276 return (0); 277 } 278 279 static int 280 _pthread_sigmask_stub(int how, const sigset_t *set, sigset_t *oset) 281 { 282 return (0); 283 } 284 285 static int 286 pthread_cond_init_stub(pthread_cond_t *cond, 287 const pthread_condattr_t *cond_attr) 288 { 289 return (_pthread_cond_init(cond, cond_attr)); 290 } 291 292 static int 293 pthread_cond_signal_stub(pthread_cond_t *cond) 294 { 295 return (_pthread_cond_signal(cond)); 296 } 297 298 static int 299 pthread_cond_broadcast_stub(pthread_cond_t *cond) 300 { 301 return (_pthread_cond_broadcast(cond)); 302 } 303 304 static int 305 pthread_cond_wait_stub(pthread_cond_t *cond, pthread_mutex_t *mutex) 306 { 307 return (_pthread_cond_wait(cond, mutex)); 308 } 309 310 static int 311 pthread_cond_destroy_stub(pthread_cond_t *cond) 312 { 313 return (_pthread_cond_destroy(cond)); 314 } 315 316 static void * 317 pthread_getspecific_stub(pthread_key_t key) 318 { 319 return (_pthread_getspecific(key)); 320 } 321 322 static int 323 pthread_key_create_stub(pthread_key_t *key, void (*destructor) (void *)) 324 { 325 return (_pthread_key_create(key, destructor)); 326 } 327 328 static int 329 pthread_key_delete_stub(pthread_key_t key) 330 { 331 return (_pthread_key_delete(key)); 332 } 333 334 static int 335 pthread_main_np_stub() 336 { 337 return (_pthread_main_np()); 338 } 339 340 static int 341 pthread_mutex_destroy_stub(pthread_mutex_t *mattr) 342 { 343 return (_pthread_mutex_destroy(mattr)); 344 } 345 346 static int 347 pthread_mutex_init_stub(pthread_mutex_t *mutex, const pthread_mutexattr_t *mattr) 348 { 349 return (_pthread_mutex_init(mutex, mattr)); 350 } 351 352 static int 353 pthread_mutex_lock_stub(pthread_mutex_t *mutex) 354 { 355 return (_pthread_mutex_lock(mutex)); 356 } 357 358 static int 359 pthread_mutex_trylock_stub(pthread_mutex_t *mutex) 360 { 361 return (_pthread_mutex_trylock(mutex)); 362 } 363 364 static int 365 pthread_mutex_unlock_stub(pthread_mutex_t *mutex) 366 { 367 return (_pthread_mutex_unlock(mutex)); 368 } 369 370 static int 371 pthread_mutexattr_init_stub(pthread_mutexattr_t *mattr) 372 { 373 return (_pthread_mutexattr_init(mattr)); 374 } 375 376 static int 377 pthread_mutexattr_destroy_stub(pthread_mutexattr_t *mattr) 378 { 379 return (_pthread_mutexattr_destroy(mattr)); 380 } 381 382 static int 383 pthread_mutexattr_settype_stub(pthread_mutexattr_t *mattr, int type) 384 { 385 return (_pthread_mutexattr_settype(mattr, type)); 386 } 387 388 static int 389 pthread_once_stub(pthread_once_t *once_control, void (*init_routine) (void)) 390 { 391 return (_pthread_once(once_control, init_routine)); 392 } 393 394 static int 395 pthread_rwlock_init_stub(pthread_rwlock_t *rwlock, 396 const pthread_rwlockattr_t *attr) 397 { 398 return (_pthread_rwlock_init(rwlock, attr)); 399 } 400 401 static int 402 pthread_rwlock_destroy_stub(pthread_rwlock_t *rwlock) 403 { 404 return (_pthread_rwlock_destroy(rwlock)); 405 } 406 407 static int 408 pthread_rwlock_rdlock_stub(pthread_rwlock_t *rwlock) 409 { 410 return (_pthread_rwlock_rdlock(rwlock)); 411 } 412 413 static int 414 pthread_rwlock_tryrdlock_stub(pthread_rwlock_t *rwlock) 415 { 416 return (_pthread_rwlock_tryrdlock(rwlock)); 417 } 418 419 static int 420 pthread_rwlock_trywrlock_stub(pthread_rwlock_t *rwlock) 421 { 422 return (_pthread_rwlock_trywrlock(rwlock)); 423 } 424 425 static int 426 pthread_rwlock_unlock_stub(pthread_rwlock_t *rwlock) 427 { 428 return (_pthread_rwlock_unlock(rwlock)); 429 } 430 431 static int 432 pthread_rwlock_wrlock_stub(pthread_rwlock_t *rwlock) 433 { 434 return (_pthread_rwlock_wrlock(rwlock)); 435 } 436 437 static pthread_t 438 pthread_self_stub(void) 439 { 440 return (_pthread_self()); 441 } 442 443 static int 444 pthread_setspecific_stub(pthread_key_t key, const void *value) 445 { 446 return (_pthread_setspecific(key, value)); 447 } 448 449 static int 450 pthread_sigmask_stub(int how, const sigset_t *set, sigset_t *oset) 451 { 452 return (_pthread_sigmask(how, set, oset)); 453 } 454