static bool _Thread_queue_Make_ready_again( Thread_Control *the_thread ) { bool success; bool unblock; /* * We must update the wait flags under protection of the current thread lock, * otherwise a _Thread_Timeout() running on another processor may interfere. */ success = _Thread_Wait_flags_try_change_release( the_thread, THREAD_QUEUE_INTEND_TO_BLOCK, THREAD_QUEUE_READY_AGAIN ); if ( success ) { unblock = false; } else { _Assert( _Thread_Wait_flags_get( the_thread ) == THREAD_QUEUE_BLOCKED ); _Thread_Wait_flags_set( the_thread, THREAD_QUEUE_READY_AGAIN ); unblock = true; } _Thread_Wait_restore_default( the_thread ); return unblock; }
bool _Thread_queue_Do_extract_locked( Thread_queue_Queue *queue, const Thread_queue_Operations *operations, Thread_Control *the_thread #if defined(RTEMS_MULTIPROCESSING) , const Thread_queue_Context *queue_context #endif ) { bool success; bool unblock; #if defined(RTEMS_MULTIPROCESSING) if ( !_Objects_Is_local_id( the_thread->Object.id ) ) { Thread_Proxy_control *the_proxy; Thread_queue_MP_callout mp_callout; the_proxy = (Thread_Proxy_control *) the_thread; mp_callout = queue_context->mp_callout; _Assert( mp_callout != NULL ); the_proxy->thread_queue_callout = queue_context->mp_callout; } #endif ( *operations->extract )( queue, the_thread ); /* * We must update the wait flags under protection of the current thread lock, * otherwise a _Thread_Timeout() running on another processor may interfere. */ success = _Thread_Wait_flags_try_change_release( the_thread, THREAD_QUEUE_INTEND_TO_BLOCK, THREAD_QUEUE_READY_AGAIN ); if ( success ) { unblock = false; } else { _Assert( _Thread_Wait_flags_get( the_thread ) == THREAD_QUEUE_BLOCKED ); _Thread_Wait_flags_set( the_thread, THREAD_QUEUE_READY_AGAIN ); unblock = true; } _Thread_Wait_restore_default( the_thread ); return unblock; }
void _Rate_monotonic_Timeout( Watchdog_Control *the_watchdog ) { Rate_monotonic_Control *the_period; Thread_Control *owner; ISR_lock_Context lock_context; Thread_Wait_flags wait_flags; the_period = RTEMS_CONTAINER_OF( the_watchdog, Rate_monotonic_Control, Timer ); owner = the_period->owner; _ISR_lock_ISR_disable( &lock_context ); _Rate_monotonic_Acquire_critical( the_period, &lock_context ); wait_flags = _Thread_Wait_flags_get( owner ); if ( ( wait_flags & THREAD_WAIT_CLASS_PERIOD ) != 0 && owner->Wait.return_argument == the_period ) { bool unblock; bool success; owner->Wait.return_argument = NULL; success = _Thread_Wait_flags_try_change_release( owner, RATE_MONOTONIC_INTEND_TO_BLOCK, RATE_MONOTONIC_READY_AGAIN ); if ( success ) { unblock = false; } else { _Assert( _Thread_Wait_flags_get( owner ) == RATE_MONOTONIC_BLOCKED ); _Thread_Wait_flags_set( owner, RATE_MONOTONIC_READY_AGAIN ); unblock = true; } _Rate_monotonic_Restart( the_period, owner, &lock_context ); if ( unblock ) { _Thread_Unblock( owner ); } } else { _Rate_monotonic_Renew_deadline( the_period, &lock_context ); } }