Changeset 409 for trunk/kernel/syscalls/sys_thread_join.c
- Timestamp:
- Dec 20, 2017, 4:51:09 PM (7 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/kernel/syscalls/sys_thread_join.c
r408 r409 40 40 cxy_t target_cxy; 41 41 ltid_t target_ltid; 42 uint32_t flags; // target thread flags 43 intptr_t value; // value returned by target thread44 paddr_t paddr; // required for vmm_v2p_translate()42 uint32_t target_blocked; // target thread blocked bit-vector 43 uint32_t target_flags; // target thread flags bit-bector 44 paddr_t paddr; // required for vmm_v2p_translate() 45 45 46 thread_t * this = CURRENT_THREAD;47 process_t * process = this->process;46 thread_t * this = CURRENT_THREAD; 47 process_t * process = this->process; 48 48 49 49 // get target thread ltid and cxy … … 89 89 90 90 // check target thread joinable 91 flags = hal_remote_lw( XPTR( target_cxy , &target_ptr->flags ) );92 if( flags & THREAD_FLAG_DETACHED )91 target_flags = hal_remote_lw( XPTR( target_cxy , &target_ptr->flags ) ); 92 if( target_flags & THREAD_FLAG_DETACHED ) 93 93 { 94 94 printk("\n[ERROR] in %s : target thread not joinable\n", __FUNCTION__ ); … … 100 100 if( target_ptr->signature != THREAD_SIGNATURE ) 101 101 { 102 printk("\n[PANIC] in %s : kernel stack overflow\n", __FUNCTION__ ); 103 hal_core_sleep(); 102 panic("\n[PANIC] in %s : kernel stack overflow\n", __FUNCTION__ ); 104 103 } 105 104 106 // wait target thread exit 107 while( 1 ) 105 // get the lock protecting the join in target thread 106 remote_spinlock_lock( XPTR( target_cxy , &target_ptr->join_lock ) ); 107 108 // get the blocked bit_vector from the target thread 109 target_blocked = hal_remote_lw( XPTR( target_cxy , &target_ptr->blocked ) ); 110 111 if( target_blocked & THREAD_BLOCKED_JOIN ) // target thread arrived first 108 112 { 109 // take the target thread lock protecting flags110 remote_spinlock_lock( XPTR( target_cxy , &target_ptr->flags_lock ));113 // unblock the target thread 114 thread_unblock( target_xp , THREAD_BLOCKED_JOIN ); 111 115 112 // get the remote thread flags113 flags = hal_remote_lw( XPTR( target_cxy , &target_ptr->flags) );116 // release the lock protecting flags 117 remote_spinlock_unlock( XPTR( target_cxy , &target_ptr->join_lock ) ); 114 118 115 // check the EXIT flag 116 if( flags & THREAD_FLAG_EXIT ) // target made an exit 117 { 118 // unblock the target thread 119 thread_unblock( target_xp , THREAD_BLOCKED_EXIT ); 119 // get the exit value from target thread 120 *exit_value = hal_remote_lpt( XPTR( target_cxy , &target_ptr->join_value ) ); 121 } 122 else // this thread arrived first 123 { 124 // register this thread extended pointer in target thread 125 hal_remote_swd( XPTR( target_cxy , &target_ptr->join_xp ) , 126 XPTR( local_cxy , this ) ); 120 127 121 // release the target thread lock protecting flags 122 remote_spinlock_unlock( XPTR( target_cxy , &target_ptr->flags_lock ) ); 128 // set the JOIN_DONE flag in target thread 129 hal_remote_atomic_or( XPTR( target_cxy , &target_ptr->flags ) , 130 THREAD_FLAG_JOIN_DONE ); 123 131 124 // exit while 125 break; 126 } 127 else // no exit done by target thread 128 { 129 // set the JOIN flag in target thread 130 hal_remote_atomic_or( XPTR( target_xp , &target_ptr->flags ) , 131 THREAD_BLOCKED_JOIN ); 132 // block this thread on BLOCKED_EXIT 133 thread_block( this , THREAD_BLOCKED_EXIT ); 132 134 133 // block this thread134 thread_block( this , THREAD_BLOCKED_JOIN);135 // release the lock protecting flags 136 remote_spinlock_unlock( XPTR( target_cxy , &target_ptr->join_lock ) ); 135 137 136 // release the target thread lock protecting flags 137 remote_spinlock_unlock( XPTR( target_cxy , &target_ptr->flags_lock ) ); 138 139 // deschedule 140 sched_yield("waiting child exit"); 141 } 138 // deschedule 139 sched_yield( "WAITING_EXIT" ); 140 141 // get the exit value from target thread when resume 142 *exit_value = hal_remote_lpt( XPTR( target_cxy , &target_ptr->join_value ) ); 142 143 } 143 144 144 // return exit_value from target thread descriptor145 value = (intptr_t)hal_remote_lpt( XPTR( target_cxy , &target_ptr->exit_value ) );146 *exit_value = (void *)value;147 145 return 0; 148 146
Note: See TracChangeset
for help on using the changeset viewer.