thr_private.h revision 138129
1/* 2 * Copyright (c) 1995-1998 John Birrell <jb@cimlogic.com.au>. 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 * 3. All advertising materials mentioning features or use of this software 14 * must display the following acknowledgement: 15 * This product includes software developed by John Birrell. 16 * 4. Neither the name of the author nor the names of any co-contributors 17 * may be used to endorse or promote products derived from this software 18 * without specific prior written permission. 19 * 20 * THIS SOFTWARE IS PROVIDED BY JOHN BIRRELL AND CONTRIBUTORS ``AS IS'' AND 21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 23 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 30 * SUCH DAMAGE. 31 * 32 * Private thread definitions for the uthread kernel. 33 * 34 * $FreeBSD: head/lib/libthr/thread/thr_private.h 138129 2004-11-27 06:51:39Z das $ 35 */ 36 37#ifndef _THR_PRIVATE_H 38#define _THR_PRIVATE_H 39 40/* 41 * Evaluate the storage class specifier. 42 */ 43#ifdef GLOBAL_PTHREAD_PRIVATE 44#define SCLASS 45#else 46#define SCLASS extern 47#endif 48 49/* 50 * Include files. 51 */ 52#include <sys/types.h> 53#include <sys/cdefs.h> 54#include <sys/errno.h> 55#include <sys/msg.h> 56#include <sys/time.h> 57#include <sys/param.h> 58#include <sys/queue.h> 59#include <pthread_np.h> 60#include <sched.h> 61#include <signal.h> 62#include <spinlock.h> 63#include <stdio.h> 64#include <ucontext.h> 65#include <unistd.h> 66#if defined(_PTHREADS_INVARIANTS) 67#include <assert.h> 68#endif 69 70#include <machine/atomic.h> 71#include <sys/thr.h> 72#include <sys/umtx.h> 73#include <vm/vm.h> 74#include <vm/vm_param.h> 75#include <vm/pmap.h> 76#include <vm/vm_map.h> 77 78#if defined(_PTHREADS_INVARIANTS) 79/* 80 * Kernel fatal error handler macro. 81 */ 82#define PANIC(string) \ 83 do { \ 84 _thread_printf(STDOUT_FILENO, (string)); \ 85 _thread_printf(STDOUT_FILENO, \ 86 "\nAbnormal termination, file: %s, line: %d\n", \ 87 __FILE__, __LINE__); \ 88 abort(); \ 89 } while (0) 90 91#define PTHREAD_ASSERT(cond, msg) do { \ 92 if (!(cond)) \ 93 PANIC(msg); \ 94} while (0) 95 96#define PTHREAD_ASSERT_NOT_IN_SYNCQ(thrd) \ 97 PTHREAD_ASSERT((((thrd)->flags & PTHREAD_FLAGS_IN_SYNCQ) == 0), \ 98 "Illegal call from signal handler"); 99 100#else /* !_PTHREADS_INVARIANTS */ 101#define PANIC(string) _thread_exit(__FILE__, __LINE__, (string)) 102#define PTHREAD_ASSERT(cond, msg) 103#define PTHREAD_ASSERT_NOT_IN_SYNCQ(thrd) 104#endif /* _PTHREADS_INVARIANTS */ 105 106/* Output debug messages like this: */ 107#define stdout_debug(args...) _thread_printf(STDOUT_FILENO, args) 108#define stderr_debug(args...) _thread_printf(STDOUT_FILENO, args) 109 110/* 111 * Currently executing thread. 112 */ 113#define curthread _get_curthread() 114 115/* 116 * Locking macros 117 */ 118#define UMTX_LOCK(m) \ 119 do { \ 120 if (umtx_lock((m), curthread->thr_id) != 0) \ 121 abort(); \ 122 } while (0) 123 124#define UMTX_TRYLOCK(m, r) \ 125 do { \ 126 (r) = umtx_trylock((m), curthread->thr_id); \ 127 if ((r) != 0 && (r) != EBUSY) \ 128 abort(); \ 129 } while (0) 130 131#define UMTX_UNLOCK(m) \ 132 do { \ 133 if (umtx_unlock((m), curthread->thr_id) != 0) \ 134 abort(); \ 135 } while (0) 136 137#define PTHREAD_LOCK(p) UMTX_LOCK(&(p)->lock) 138#define PTHREAD_UNLOCK(p) UMTX_UNLOCK(&(p)->lock) 139 140#define PTHREAD_WAKE(ptd) thr_wake((ptd)->thr_id) 141 142/* 143 * TailQ initialization values. 144 */ 145#define TAILQ_INITIALIZER { NULL, NULL } 146 147#define UMTX_INITIALIZER { NULL } 148 149struct pthread_mutex_attr { 150 enum pthread_mutextype m_type; 151 int m_protocol; 152 int m_ceiling; 153 long m_flags; 154}; 155 156/* 157 * Static mutex initialization values. 158 */ 159 160#define PTHREAD_MUTEXATTR_STATIC_INITIALIZER \ 161 { PTHREAD_MUTEX_DEFAULT, PTHREAD_PRIO_NONE, 0, MUTEX_FLAGS_PRIVATE } 162 163#define PTHREAD_MUTEX_STATIC_INITIALIZER \ 164 { PTHREAD_MUTEXATTR_STATIC_INITIALIZER, UMTX_INITIALIZER, NULL, \ 165 0, 0, TAILQ_INITIALIZER } 166 167union pthread_mutex_data { 168 void *m_ptr; 169 int m_count; 170}; 171 172struct pthread_mutex { 173 enum pthread_mutextype m_type; 174 int m_protocol; 175 TAILQ_HEAD(mutex_head, pthread) m_queue; 176 struct pthread *m_owner; 177 union pthread_mutex_data m_data; 178 long m_flags; 179 int m_refcount; 180 181 /* 182 * Used for priority inheritence and protection. 183 * 184 * m_prio - For priority inheritence, the highest active 185 * priority (threads locking the mutex inherit 186 * this priority). For priority protection, the 187 * ceiling priority of this mutex. 188 * m_saved_prio - mutex owners inherited priority before 189 * taking the mutex, restored when the owner 190 * unlocks the mutex. 191 */ 192 int m_prio; 193 int m_saved_prio; 194 195 /* 196 * Link for list of all mutexes a thread currently owns. 197 */ 198 TAILQ_ENTRY(pthread_mutex) m_qe; 199 200 /* 201 * Lock for accesses to this structure. 202 */ 203 spinlock_t lock; 204}; 205 206struct pthread_spinlock { 207 void *s_owner; 208 unsigned int s_magic; 209}; 210 211/* 212 * Flags for mutexes. 213 */ 214#define MUTEX_FLAGS_PRIVATE 0x01 215#define MUTEX_FLAGS_INITED 0x02 216#define MUTEX_FLAGS_BUSY 0x04 217 218/* 219 * Condition variable definitions. 220 */ 221enum pthread_cond_type { 222 COND_TYPE_FAST, 223 COND_TYPE_MAX 224}; 225 226struct pthread_cond { 227 enum pthread_cond_type c_type; 228 TAILQ_HEAD(cond_head, pthread) c_queue; 229 pthread_mutex_t c_mutex; 230 void *c_data; 231 long c_flags; 232 int c_seqno; 233 234 /* 235 * Lock for accesses to this structure. 236 */ 237 struct umtx c_lock; 238}; 239 240struct pthread_cond_attr { 241 enum pthread_cond_type c_type; 242 long c_flags; 243}; 244 245/* 246 * Flags for condition variables. 247 */ 248#define COND_FLAGS_INITED 0x01 249 250/* 251 * Static cond initialization values. 252 */ 253#define PTHREAD_COND_STATIC_INITIALIZER \ 254 { COND_TYPE_FAST, TAILQ_INITIALIZER, NULL, NULL, \ 255 0, 0, UMTX_INITIALIZER } 256 257/* 258 * Semaphore definitions. 259 */ 260struct sem { 261#define SEM_MAGIC ((u_int32_t) 0x09fa4012) 262 u_int32_t magic; 263 pthread_mutex_t lock; 264 pthread_cond_t gtzero; 265 u_int32_t count; 266 u_int32_t nwaiters; 267}; 268 269/* 270 * Cleanup definitions. 271 */ 272struct pthread_cleanup { 273 struct pthread_cleanup *next; 274 void (*routine) (); 275 void *routine_arg; 276}; 277 278struct pthread_atfork { 279 TAILQ_ENTRY(pthread_atfork) qe; 280 void (*prepare)(void); 281 void (*parent)(void); 282 void (*child)(void); 283}; 284 285struct pthread_attr { 286 int sched_policy; 287 int sched_inherit; 288 int sched_interval; 289 int prio; 290 int suspend; 291 int flags; 292 void *arg_attr; 293 void (*cleanup_attr) (); 294 void *stackaddr_attr; 295 size_t stacksize_attr; 296 size_t guardsize_attr; 297}; 298 299/* 300 * Thread creation state attributes. 301 */ 302#define PTHREAD_CREATE_RUNNING 0 303#define PTHREAD_CREATE_SUSPENDED 1 304 305/* 306 * Miscellaneous definitions. 307 */ 308#define PTHREAD_STACK_DEFAULT 65536 309/* 310 * Size of default red zone at the end of each stack. In actuality, this "red 311 * zone" is merely an unmapped region, except in the case of the initial stack. 312 * Since mmap() makes it possible to specify the maximum growth of a MAP_STACK 313 * region, an unmapped gap between thread stacks achieves the same effect as 314 * explicitly mapped red zones. 315 * This is declared and initialized in uthread_init.c. 316 */ 317extern int _pthread_guard_default; 318 319extern int _pthread_page_size; 320 321/* 322 * Maximum size of initial thread's stack. This perhaps deserves to be larger 323 * than the stacks of other threads, since many applications are likely to run 324 * almost entirely on this stack. 325 */ 326#define PTHREAD_STACK_INITIAL 0x100000 327 328/* 329 * Define the different priority ranges. All applications have thread 330 * priorities constrained within 0-31. The threads library raises the 331 * priority when delivering signals in order to ensure that signal 332 * delivery happens (from the POSIX spec) "as soon as possible". 333 * In the future, the threads library will also be able to map specific 334 * threads into real-time (cooperating) processes or kernel threads. 335 * The RT and SIGNAL priorities will be used internally and added to 336 * thread base priorities so that the scheduling queue can handle both 337 * normal and RT priority threads with and without signal handling. 338 * 339 * The approach taken is that, within each class, signal delivery 340 * always has priority over thread execution. 341 */ 342#define PTHREAD_DEFAULT_PRIORITY 15 343#define PTHREAD_MIN_PRIORITY 0 344#define PTHREAD_MAX_PRIORITY 31 /* 0x1F */ 345#define PTHREAD_SIGNAL_PRIORITY 32 /* 0x20 */ 346#define PTHREAD_RT_PRIORITY 64 /* 0x40 */ 347#define PTHREAD_FIRST_PRIORITY PTHREAD_MIN_PRIORITY 348#define PTHREAD_LAST_PRIORITY \ 349 (PTHREAD_MAX_PRIORITY + PTHREAD_SIGNAL_PRIORITY + PTHREAD_RT_PRIORITY) 350#define PTHREAD_BASE_PRIORITY(prio) ((prio) & PTHREAD_MAX_PRIORITY) 351 352/* 353 * Clock resolution in microseconds. 354 */ 355#define CLOCK_RES_USEC 10000 356#define CLOCK_RES_USEC_MIN 1000 357 358/* 359 * Time slice period in microseconds. 360 */ 361#define TIMESLICE_USEC 20000 362 363/* 364 * XXX Define a thread-safe macro to get the current time of day 365 * which is updated at regular intervals by the scheduling signal 366 * handler. 367 */ 368#define GET_CURRENT_TOD(tv) gettimeofday(&(tv), NULL) 369 370struct pthread_barrierattr { 371 int ba_pshared; 372}; 373 374/* 375 * POSIX Threads barrier object. 376 * Lock order: 377 * 1. pthread_barrier 378 * 2. pthread 379 */ 380struct pthread_barrier { 381 TAILQ_HEAD(barrq_head, pthread) b_barrq; 382 struct umtx b_lock; 383 int b_total; 384 int b_subtotal; 385}; 386 387struct pthread_rwlockattr { 388 int pshared; 389}; 390 391struct pthread_rwlock { 392 pthread_mutex_t lock; /* monitor lock */ 393 int state; /* 0 = idle >0 = # of readers -1 = writer */ 394 pthread_cond_t read_signal; 395 pthread_cond_t write_signal; 396 int blocked_writers; 397}; 398 399/* 400 * Thread states. 401 */ 402enum pthread_state { 403 PS_RUNNING, 404 PS_MUTEX_WAIT, 405 PS_COND_WAIT, 406 PS_BARRIER_WAIT, 407 PS_SLEEP_WAIT, /* XXX We need to wrap syscalls to set this state */ 408 PS_WAIT_WAIT, 409 PS_JOIN, 410 PS_DEAD, 411 PS_DEADLOCK, 412 PS_STATE_MAX 413}; 414 415 416/* 417 * File descriptor locking definitions. 418 */ 419#define FD_READ 0x1 420#define FD_WRITE 0x2 421#define FD_RDWR (FD_READ | FD_WRITE) 422 423union pthread_wait_data { 424 pthread_mutex_t mutex; 425 pthread_cond_t cond; 426 spinlock_t *spinlock; 427 struct pthread *thread; 428}; 429 430struct join_status { 431 struct pthread *thread; 432 void *ret; 433 int error; 434}; 435 436struct pthread_state_data { 437 union pthread_wait_data psd_wait_data; 438 enum pthread_state psd_state; 439 int psd_flags; 440}; 441 442struct pthread_specific_elem { 443 const void *data; 444 int seqno; 445}; 446 447struct rwlock_held { 448 LIST_ENTRY(rwlock_held) rh_link; 449 struct pthread_rwlock *rh_rwlock; 450 int rh_rdcount; 451 int rh_wrcount; 452}; 453 454LIST_HEAD(rwlock_listhead, rwlock_held); 455 456/* 457 * The cancel mode a thread is in is determined by the 458 * the cancel type and state it is set in. The two values 459 * are combined into one mode: 460 * Mode State Type 461 * ---- ----- ---- 462 * off disabled deferred 463 * off disabled async 464 * deferred enabled deferred 465 * async enabled async 466 */ 467enum cancel_mode { M_OFF, M_DEFERRED, M_ASYNC }; 468 469/* 470 * A thread's cancellation is pending until the cancel 471 * mode has been tested to determine if the thread can be 472 * cancelled immediately. 473 */ 474enum cancellation_state { CS_NULL, CS_PENDING, CS_SET }; 475 476/* 477 * Thread structure. 478 */ 479struct pthread { 480 /* 481 * Magic value to help recognize a valid thread structure 482 * from an invalid one: 483 */ 484#define PTHREAD_MAGIC ((u_int32_t) 0xd09ba115) 485 u_int32_t magic; 486 char *name; 487 long thr_id; 488 sigset_t savedsig; 489 int signest; /* blocked signal netsting level */ 490 int ptdflags; /* used by other other threads 491 to signal this thread */ 492 int isdead; 493 int isdeadlocked; 494 int exiting; 495 int cancellationpoint; 496 497 /* 498 * Lock for accesses to this thread structure. 499 */ 500 struct umtx lock; 501 502 /* Queue entry for list of all threads: */ 503 TAILQ_ENTRY(pthread) tle; 504 505 /* Queue entry for list of dead threads: */ 506 TAILQ_ENTRY(pthread) dle; 507 508 /* 509 * Thread start routine, argument, stack pointer and thread 510 * attributes. 511 */ 512 void *(*start_routine)(void *); 513 void *arg; 514 void *stack; 515 struct pthread_attr attr; 516 517 /* 518 * Machine context, including signal state. 519 */ 520 ucontext_t ctx; 521 522 /* 523 * The primary method of obtaining a thread's cancel state 524 * and type is through cancelmode. The cancelstate field is 525 * only so we don't loose the cancel state when the mode is 526 * turned off. 527 */ 528 enum cancel_mode cancelmode; 529 enum cancel_mode cancelstate; 530 531 /* Specifies if cancellation is pending, acted upon, or neither. */ 532 enum cancellation_state cancellation; 533 534 /* 535 * Error variable used instead of errno. The function __error() 536 * returns a pointer to this. 537 */ 538 int error; 539 540 /* 541 * The joiner is the thread that is joining to this thread. The 542 * join status keeps track of a join operation to another thread. 543 */ 544 struct pthread *joiner; 545 struct join_status join_status; 546 547 /* 548 * A thread can belong to: 549 * 550 * o A queue of threads waiting for a mutex 551 * o A queue of threads waiting for a condition variable 552 * 553 * A thread can also be joining a thread (the joiner field above). 554 * 555 * Use sqe for synchronization (mutex and condition variable) queue 556 * links. 557 */ 558 TAILQ_ENTRY(pthread) sqe; /* synchronization queue link */ 559 560 /* Wait data. */ 561 union pthread_wait_data data; 562 563 /* Miscellaneous flags; only set with signals deferred. */ 564 int flags; 565#define PTHREAD_FLAGS_PRIVATE 0x0001 566#define PTHREAD_FLAGS_BARR_REL 0x0004 /* has been released from barrier */ 567#define PTHREAD_FLAGS_IN_BARRQ 0x0008 /* in barrier queue using sqe link */ 568#define PTHREAD_FLAGS_IN_CONDQ 0x0080 /* in condition queue using sqe link*/ 569#define PTHREAD_FLAGS_IN_MUTEXQ 0x0100 /* in mutex queue using sqe link */ 570#define PTHREAD_FLAGS_SUSPENDED 0x0200 /* thread is suspended */ 571#define PTHREAD_FLAGS_TRACE 0x0400 /* for debugging purposes */ 572#define PTHREAD_FLAGS_IN_SYNCQ \ 573 (PTHREAD_FLAGS_IN_CONDQ | PTHREAD_FLAGS_IN_MUTEXQ | PTHREAD_FLAGS_IN_BARRQ) 574#define PTHREAD_FLAGS_NOT_RUNNING \ 575 (PTHREAD_FLAGS_IN_SYNCQ | PTHREAD_FLAGS_SUSPENDED) 576 577 /* 578 * Base priority is the user setable and retrievable priority 579 * of the thread. It is only affected by explicit calls to 580 * set thread priority and upon thread creation via a thread 581 * attribute or default priority. 582 */ 583 char base_priority; 584 585 /* 586 * Inherited priority is the priority a thread inherits by 587 * taking a priority inheritence or protection mutex. It 588 * is not affected by base priority changes. Inherited 589 * priority defaults to and remains 0 until a mutex is taken 590 * that is being waited on by any other thread whose priority 591 * is non-zero. 592 */ 593 char inherited_priority; 594 595 /* 596 * Active priority is always the maximum of the threads base 597 * priority and inherited priority. When there is a change 598 * in either the base or inherited priority, the active 599 * priority must be recalculated. 600 */ 601 char active_priority; 602 603 /* Number of priority ceiling or protection mutexes owned. */ 604 int prio_inherit_count; 605 int prio_protect_count; 606 607 /* 608 * Queue of currently owned mutexes. 609 */ 610 TAILQ_HEAD(, pthread_mutex) mutexq; 611 612 /* 613 * List of read-write locks owned for reading _OR_ writing. 614 * This is accessed only by the current thread, so there's 615 * no need for mutual exclusion. 616 */ 617 struct rwlock_listhead *rwlockList; 618 619 void *ret; 620 struct pthread_specific_elem *specific; 621 int specific_data_count; 622 623 /* 624 * Architecture specific id field used for _{get, set}_curthread() 625 * interface. 626 */ 627 void *arch_id; 628 629 /* Cleanup handlers Link List */ 630 struct pthread_cleanup *cleanup; 631 char *fname; /* Ptr to source file name */ 632 int lineno; /* Source line number. */ 633}; 634 635/* 636 * Global variables for the uthread kernel. 637 */ 638 639SCLASS void *_usrstack 640#ifdef GLOBAL_PTHREAD_PRIVATE 641= (void *) USRSTACK; 642#else 643; 644#endif 645 646SCLASS spinlock_t stack_lock 647#ifdef GLOBAL_PTHREAD_PRIVATE 648= _SPINLOCK_INITIALIZER 649#endif 650; 651#define STACK_LOCK _SPINLOCK(&stack_lock); 652#define STACK_UNLOCK _SPINUNLOCK(&stack_lock); 653 654/* List of all threads: */ 655SCLASS TAILQ_HEAD(, pthread) _thread_list 656#ifdef GLOBAL_PTHREAD_PRIVATE 657= TAILQ_HEAD_INITIALIZER(_thread_list); 658#else 659; 660#endif 661 662/* Dead threads: */ 663SCLASS TAILQ_HEAD(, pthread) _dead_list 664#ifdef GLOBAL_PTHREAD_PRIVATE 665= TAILQ_HEAD_INITIALIZER(_dead_list); 666#else 667; 668#endif 669 670/* 671 * These two locks protect the global active threads list and 672 * the global dead threads list, respectively. Combining these 673 * into one lock for both lists doesn't seem wise, since it 674 * would likely increase contention during busy thread creation 675 * and destruction for very little savings in space. 676 * 677 * The lock for the "dead threads list" must be a pthread mutex 678 * because it is used with condition variables to synchronize 679 * the gc thread with active threads in the process of exiting or 680 * dead threads who have just been joined. 681 */ 682SCLASS spinlock_t thread_list_lock 683#ifdef GLOBAL_PTHREAD_PRIVATE 684= _SPINLOCK_INITIALIZER 685#endif 686; 687SCLASS pthread_mutex_t dead_list_lock 688#ifdef GLOBAL_PTHREAD_PRIVATE 689= NULL 690#endif 691; 692 693#define THREAD_LIST_LOCK _SPINLOCK(&thread_list_lock) 694#define THREAD_LIST_UNLOCK _SPINUNLOCK(&thread_list_lock) 695#define DEAD_LIST_LOCK _pthread_mutex_lock(&dead_list_lock) 696#define DEAD_LIST_UNLOCK _pthread_mutex_unlock(&dead_list_lock) 697 698/* Initial thread: */ 699SCLASS struct pthread *_thread_initial 700#ifdef GLOBAL_PTHREAD_PRIVATE 701= NULL; 702#else 703; 704#endif 705 706SCLASS TAILQ_HEAD(atfork_head, pthread_atfork) _atfork_list; 707SCLASS pthread_mutex_t _atfork_mutex; 708 709/* Default thread attributes: */ 710SCLASS struct pthread_attr pthread_attr_default 711#ifdef GLOBAL_PTHREAD_PRIVATE 712= { SCHED_RR, 0, TIMESLICE_USEC, PTHREAD_DEFAULT_PRIORITY, 713 PTHREAD_CREATE_RUNNING, PTHREAD_CREATE_JOINABLE, NULL, NULL, NULL, 714 PTHREAD_STACK_DEFAULT, -1 }; 715#else 716; 717#endif 718 719/* Default mutex attributes: */ 720SCLASS struct pthread_mutex_attr pthread_mutexattr_default 721#ifdef GLOBAL_PTHREAD_PRIVATE 722= { PTHREAD_MUTEX_DEFAULT, PTHREAD_PRIO_NONE, 0, 0 }; 723#else 724; 725#endif 726 727/* Default condition variable attributes: */ 728SCLASS struct pthread_cond_attr pthread_condattr_default 729#ifdef GLOBAL_PTHREAD_PRIVATE 730= { COND_TYPE_FAST, 0 }; 731#else 732; 733#endif 734 735/* 736 * Array of signal actions for this process. 737 */ 738SCLASS struct sigaction _thread_sigact[NSIG]; 739 740/* Precomputed signal set for _thread_suspend. */ 741SCLASS sigset_t _thread_suspend_sigset; 742 743/* Tracks the number of threads blocked while waiting for a spinlock. */ 744SCLASS volatile int _spinblock_count 745#ifdef GLOBAL_PTHREAD_PRIVATE 746= 0 747#endif 748; 749 750/* 751 * libthread_db.so support. 752 */ 753SCLASS int _libthr_debug 754#ifdef GLOBAL_PTHREAD_PRIVATE 755= 0 756#endif 757; 758 759/* Undefine the storage class specifier: */ 760#undef SCLASS 761 762/* 763 * Function prototype definitions. 764 */ 765__BEGIN_DECLS 766char *__ttyname_basic(int); 767char *__ttyname_r_basic(int, char *, size_t); 768char *ttyname_r(int, char *, size_t); 769void _cond_wait_backout(pthread_t); 770int _find_thread(pthread_t); 771pthread_t _get_curthread(void); 772void *_set_curthread(ucontext_t *, struct pthread *, int *); 773void _retire_thread(void *arch_id); 774void *_thread_stack_alloc(size_t, size_t); 775void _thread_stack_free(void *, size_t, size_t); 776int _thread_create(pthread_t *,const pthread_attr_t *,void *(*start_routine)(void *),void *,pthread_t); 777int _mutex_cv_lock(pthread_mutex_t *); 778int _mutex_cv_unlock(pthread_mutex_t *); 779void _mutex_lock_backout(pthread_t); 780void _mutex_notify_priochange(pthread_t); 781int _mutex_reinit(pthread_mutex_t *); 782void _mutex_unlock_private(pthread_t); 783int _cond_reinit(pthread_cond_t *); 784void *_pthread_getspecific(pthread_key_t); 785int _pthread_key_create(pthread_key_t *, void (*) (void *)); 786int _pthread_key_delete(pthread_key_t); 787int _pthread_mutex_destroy(pthread_mutex_t *); 788int _pthread_mutex_init(pthread_mutex_t *, const pthread_mutexattr_t *); 789int _pthread_mutex_lock(pthread_mutex_t *); 790int _pthread_mutex_trylock(pthread_mutex_t *); 791int _pthread_mutex_unlock(pthread_mutex_t *); 792int _pthread_mutexattr_init(pthread_mutexattr_t *); 793int _pthread_mutexattr_destroy(pthread_mutexattr_t *); 794int _pthread_mutexattr_settype(pthread_mutexattr_t *, int); 795int _pthread_once(pthread_once_t *, void (*) (void)); 796pthread_t _pthread_self(void); 797int _pthread_setspecific(pthread_key_t, const void *); 798int _spintrylock(spinlock_t *); 799void _thread_exit(char *, int, char *); 800void _thread_exit_cleanup(void); 801void *_thread_cleanup(pthread_t); 802void _thread_cleanupspecific(void); 803void _thread_dump_info(void); 804void _thread_init(void); 805void _thread_printf(int fd, const char *, ...); 806void _thread_start(pthread_t td); 807void _thread_seterrno(pthread_t, int); 808void _thread_enter_cancellation_point(void); 809void _thread_leave_cancellation_point(void); 810void _thread_cancellation_point(void); 811int _thread_suspend(pthread_t thread, const struct timespec *abstime); 812void _thread_critical_enter(pthread_t); 813void _thread_critical_exit(pthread_t); 814void _thread_sigblock(); 815void _thread_sigunblock(); 816void adjust_prio_inheritance(struct pthread *); 817void adjust_prio_protection(struct pthread *); 818void deadlist_free_onethread(struct pthread *); 819void init_td_common(struct pthread *, struct pthread_attr *, int); 820void init_tdlist(struct pthread *, int); 821void proc_sigact_copyin(int, const struct sigaction *); 822void proc_sigact_copyout(int, struct sigaction *); 823void readjust_priorities(struct pthread *, struct pthread_mutex *); 824struct sigaction *proc_sigact_sigaction(int); 825 826/* #include <sys/aio.h> */ 827#ifdef _SYS_AIO_H_ 828int __sys_aio_suspend(const struct aiocb * const[], int, const struct timespec *); 829#endif 830 831/* #include <sys/event.h> */ 832#ifdef _SYS_EVENT_H_ 833int __sys_kevent(int, const struct kevent *, int, struct kevent *, 834 int, const struct timespec *); 835#endif 836 837/* #include <sys/ioctl.h> */ 838#ifdef _SYS_IOCTL_H_ 839int __sys_ioctl(int, unsigned long, ...); 840#endif 841 842/* #include <sys/msg.h> */ 843#ifdef _SYS_MSG_H_ 844int __sys_msgrcv(int, void *, size_t, long, int); 845int __sys_msgsnd(int, const void *, size_t, int); 846#endif 847 848/* #include <sys/mman.h> */ 849#ifdef _SYS_MMAN_H_ 850int __sys_msync(void *, size_t, int); 851#endif 852 853/* #include <sys/mount.h> */ 854#ifdef _SYS_MOUNT_H_ 855int __sys_fstatfs(int, struct statfs *); 856#endif 857 858/* #include <sys/socket.h> */ 859#ifdef _SYS_SOCKET_H_ 860int __sys_accept(int, struct sockaddr *, socklen_t *); 861int __sys_bind(int, const struct sockaddr *, socklen_t); 862int __sys_connect(int, const struct sockaddr *, socklen_t); 863int __sys_getpeername(int, struct sockaddr *, socklen_t *); 864int __sys_getsockname(int, struct sockaddr *, socklen_t *); 865int __sys_getsockopt(int, int, int, void *, socklen_t *); 866int __sys_listen(int, int); 867ssize_t __sys_recv(int, void *, size_t, int); 868ssize_t __sys_recvfrom(int, void *, size_t, int, struct sockaddr *, socklen_t *); 869ssize_t __sys_recvmsg(int, struct msghdr *, int); 870int __sys_sendfile(int, int, off_t, size_t, struct sf_hdtr *, off_t *, int); 871ssize_t __sys_sendmsg(int, const struct msghdr *, int); 872ssize_t __sys_sendto(int, const void *,size_t, int, const struct sockaddr *, socklen_t); 873int __sys_setsockopt(int, int, int, const void *, socklen_t); 874int __sys_shutdown(int, int); 875int __sys_socket(int, int, int); 876int __sys_socketpair(int, int, int, int *); 877#endif 878 879/* #include <sys/stat.h> */ 880#ifdef _SYS_STAT_H_ 881int __sys_fchflags(int, u_long); 882int __sys_fchmod(int, mode_t); 883int __sys_fstat(int, struct stat *); 884#endif 885 886/* #include <sys/uio.h> */ 887#ifdef _SYS_UIO_H_ 888ssize_t __sys_readv(int, const struct iovec *, int); 889ssize_t __sys_writev(int, const struct iovec *, int); 890#endif 891 892/* #include <sys/wait.h> */ 893#ifdef WNOHANG 894pid_t __sys_wait4(pid_t, int *, int, struct rusage *); 895#endif 896 897/* #include <dirent.h> */ 898#ifdef _DIRENT_H_ 899int __sys_getdirentries(int, char *, int, long *); 900#endif 901 902/* #include <fcntl.h> */ 903#ifdef _SYS_FCNTL_H_ 904int __sys_fcntl(int, int, ...); 905int __sys_flock(int, int); 906int __sys_open(const char *, int, ...); 907#endif 908 909/* #include <poll.h> */ 910#ifdef _SYS_POLL_H_ 911int __sys_poll(struct pollfd *, unsigned, int); 912#endif 913 914/* #include <semaphore.h> */ 915#ifdef _SEMAPHORE_H_ 916int __sem_timedwait(sem_t * __restrict, const struct timespec * __restrict); 917int __sem_wait(sem_t *); 918#endif 919 920/* #include <signal.h> */ 921#ifdef _SIGNAL_H_ 922int __sys_sigaction(int, const struct sigaction *, struct sigaction *); 923int __sys_sigaltstack(const struct sigaltstack *, struct sigaltstack *); 924int __sys_sigprocmask(int, const sigset_t *, sigset_t *); 925int __sys_sigreturn(ucontext_t *); 926int __sys_sigsuspend(const sigset_t *); 927int __sys_sigtimedwait(const sigset_t * __restrict, siginfo_t * __restrict, 928 const struct timespec * __restrict); 929int __sys_sigwait(const sigset_t * __restrict, int * __restrict); 930int __sys_sigwaitinfo(const sigset_t * __restrict, siginfo_t * __restrict); 931#endif 932 933/* #include <unistd.h> */ 934#ifdef _UNISTD_H_ 935int __sys_close(int); 936int __sys_dup(int); 937int __sys_dup2(int, int); 938int __sys_execve(const char *, char * const *, char * const *); 939void __sys_exit(int); 940int __sys_fchown(int, uid_t, gid_t); 941pid_t __sys_fork(void); 942long __sys_fpathconf(int, int); 943int __sys_fsync(int); 944int __sys_pipe(int *); 945ssize_t __sys_pread(int, void *, size_t, off_t); 946ssize_t __sys_pwrite(int, const void *, size_t, off_t); 947ssize_t __sys_read(int, void *, size_t); 948ssize_t __sys_write(int, const void *, size_t); 949#endif 950 951__END_DECLS 952 953#endif /* !_PTHREAD_PRIVATE_H */ 954