Changeset fe19611 in mainline
- Timestamp:
- 2006-06-04T17:15:27Z (18 years ago)
- Branches:
- lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
- Children:
- c4e4507
- Parents:
- 8adafa0
- Location:
- generic
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
generic/include/proc/thread.h
r8adafa0 rfe19611 52 52 Ready, /**< State of threads in a run queue. */ 53 53 Entering, /**< Threads are in this state before they are first readied. */ 54 Exiting /**< After a thread calls thread_exit(), it is put into Exiting state. */ 54 Exiting, /**< After a thread calls thread_exit(), it is put into Exiting state. */ 55 Undead /**< Threads that were not detached but exited are in the Undead state. */ 55 56 }; 56 57 … … 98 99 bool in_copy_to_uspace; 99 100 101 bool detached; /**< If true, thread_join_timeout() cannot be used on this thread. */ 102 waitq_t join_wq; /**< Waitq for thread_join_timeout(). */ 100 103 101 104 fpu_context_t *saved_fpu_context; … … 152 155 extern void thread_usleep(__u32 usec); 153 156 157 extern int thread_join_timeout(thread_t *t, __u32 usec, int flags); 158 extern void thread_detach(thread_t *t); 159 154 160 extern void thread_register_call_me(void (* call_me)(void *), void *call_me_with); 155 161 extern void thread_print_list(void); -
generic/src/proc/scheduler.c
r8adafa0 rfe19611 41 41 #include <mm/page.h> 42 42 #include <mm/as.h> 43 #include <time/delay.h> 43 44 #include <arch/asm.h> 44 45 #include <arch/faddr.h> … … 375 376 376 377 case Exiting: 377 thread_destroy(THREAD); 378 repeat: 379 if (THREAD->detached) { 380 thread_destroy(THREAD); 381 } else { 382 /* 383 * The thread structure is kept allocated until somebody 384 * calls thread_detach() on it. 385 */ 386 if (!spinlock_trylock(&THREAD->join_wq.lock)) { 387 /* 388 * Avoid deadlock. 389 */ 390 spinlock_unlock(&THREAD->lock); 391 delay(10); 392 spinlock_lock(&THREAD->lock); 393 goto repeat; 394 } 395 _waitq_wakeup_unsafe(&THREAD->join_wq, false); 396 spinlock_unlock(&THREAD->join_wq.lock); 397 398 THREAD->state = Undead; 399 spinlock_unlock(&THREAD->lock); 400 } 378 401 break; 379 402 -
generic/src/proc/thread.c
r8adafa0 rfe19611 64 64 #include <errno.h> 65 65 66 char *thread_states[] = {"Invalid", "Running", "Sleeping", "Ready", "Entering", "Exiting"}; /**< Thread states */ 66 67 /** Thread states */ 68 char *thread_states[] = { 69 "Invalid", 70 "Running", 71 "Sleeping", 72 "Ready", 73 "Entering", 74 "Exiting", 75 "Undead" 76 }; 67 77 68 78 /** Lock protecting threads_head list. For locking rules, see declaration thereof. */ … … 311 321 t->in_copy_to_uspace = false; 312 322 323 t->detached = false; 324 waitq_initialize(&t->join_wq); 325 313 326 t->rwlock_holder_type = RWLOCK_NONE; 314 327 … … 372 385 { 373 386 thread_usleep(sec*1000000); 387 } 388 389 /** Wait for another thread to exit. 390 * 391 * @param t Thread to join on exit. 392 * @param usec Timeout in microseconds. 393 * @param flags Mode of operation. 394 * 395 * @return An error code from errno.h or an error code from synch.h. 396 */ 397 int thread_join_timeout(thread_t *t, __u32 usec, int flags) 398 { 399 ipl_t ipl; 400 int rc; 401 402 if (t == THREAD) 403 return EINVAL; 404 405 /* 406 * Since thread join can only be called once on an undetached thread, 407 * the thread pointer is guaranteed to be still valid. 408 */ 409 410 ipl = interrupts_disable(); 411 spinlock_lock(&t->lock); 412 413 ASSERT(!t->detached); 414 415 (void) waitq_sleep_prepare(&t->join_wq); 416 spinlock_unlock(&t->lock); 417 418 rc = waitq_sleep_timeout_unsafe(&t->join_wq, usec, flags); 419 420 waitq_sleep_finish(&t->join_wq, rc, ipl); 421 422 return rc; 423 } 424 425 /** Detach thread. 426 * 427 * Mark the thread as detached, if the thread is already in the Undead state, 428 * deallocate its resources. 429 * 430 * @param t Thread to be detached. 431 */ 432 void thread_detach(thread_t *t) 433 { 434 ipl_t ipl; 435 436 /* 437 * Since the thread is expected to not be already detached, 438 * pointer to it must be still valid. 439 */ 440 441 ipl = interrupts_disable(); 442 spinlock_lock(&t->lock); 443 ASSERT(!t->detached); 444 if (t->state == Undead) { 445 thread_destroy(t); /* unlocks &t->lock */ 446 interrupts_restore(ipl); 447 return; 448 } else { 449 t->detached = true; 450 } 451 spinlock_unlock(&t->lock); 452 interrupts_restore(ipl); 374 453 } 375 454
Note:
See TracChangeset
for help on using the changeset viewer.