new states added and _Rate_monotonic_Set_State removed.

This commit is contained in:
Joel Sherrill
1995-12-05 15:27:51 +00:00
parent 8d0b7d9643
commit 11ab74ef98
5 changed files with 127 additions and 205 deletions

View File

@@ -39,9 +39,13 @@ extern "C" {
*/
typedef enum {
RATE_MONOTONIC_INACTIVE, /* off chain, never initialized */
RATE_MONOTONIC_ACTIVE, /* on chain, running continuously */
RATE_MONOTONIC_EXPIRED /* off chain, will be reset by next rm_period */
RATE_MONOTONIC_INACTIVE, /* off chain, never initialized */
RATE_MONOTONIC_OWNER_IS_BLOCKING, /* on chain, owner is blocking on it */
RATE_MONOTONIC_ACTIVE, /* on chain, running continuously */
RATE_MONOTONIC_EXPIRED_WHILE_BLOCKING, /* on chain, expired while owner was */
/* was blocking on it */
RATE_MONOTONIC_EXPIRED /* off chain, will be reset by next */
/* rtems_rate_monotonic_period */
} Rate_Monotonic_Period_states;
/*
@@ -192,20 +196,6 @@ STATIC INLINE Rate_monotonic_Control *_Rate_monotonic_Get (
Objects_Locations *location
);
/*
* _Rate_monotonic_Set_state
*
* DESCRIPTION:
*
* This function blocks the calling task so that it is waiting for
* a period to expire. It returns TRUE if the task was successfully
* blocked, and FALSE otherwise.
*/
boolean _Rate_monotonic_Set_state(
Rate_monotonic_Control *the_period
);
/*
* _Rate_monotonic_Timeout
*

View File

@@ -39,9 +39,13 @@ extern "C" {
*/
typedef enum {
RATE_MONOTONIC_INACTIVE, /* off chain, never initialized */
RATE_MONOTONIC_ACTIVE, /* on chain, running continuously */
RATE_MONOTONIC_EXPIRED /* off chain, will be reset by next rm_period */
RATE_MONOTONIC_INACTIVE, /* off chain, never initialized */
RATE_MONOTONIC_OWNER_IS_BLOCKING, /* on chain, owner is blocking on it */
RATE_MONOTONIC_ACTIVE, /* on chain, running continuously */
RATE_MONOTONIC_EXPIRED_WHILE_BLOCKING, /* on chain, expired while owner was */
/* was blocking on it */
RATE_MONOTONIC_EXPIRED /* off chain, will be reset by next */
/* rtems_rate_monotonic_period */
} Rate_Monotonic_Period_states;
/*
@@ -192,20 +196,6 @@ STATIC INLINE Rate_monotonic_Control *_Rate_monotonic_Get (
Objects_Locations *location
);
/*
* _Rate_monotonic_Set_state
*
* DESCRIPTION:
*
* This function blocks the calling task so that it is waiting for
* a period to expire. It returns TRUE if the task was successfully
* blocked, and FALSE otherwise.
*/
boolean _Rate_monotonic_Set_state(
Rate_monotonic_Control *the_period
);
/*
* _Rate_monotonic_Timeout
*

View File

@@ -233,9 +233,11 @@ rtems_status_code rtems_rate_monotonic_period(
rtems_interval length
)
{
Rate_monotonic_Control *the_period;
Objects_Locations location;
rtems_status_code return_value;
Rate_monotonic_Control *the_period;
Objects_Locations location;
rtems_status_code return_value;
Rate_Monotonic_Period_states local_state;
ISR_Level level;
the_period = _Rate_monotonic_Get( id, &location );
switch ( location ) {
@@ -268,8 +270,10 @@ rtems_status_code rtems_rate_monotonic_period(
return( return_value );
}
_ISR_Disable( level );
switch ( the_period->state ) {
case RATE_MONOTONIC_INACTIVE:
_ISR_Enable( level );
the_period->state = RATE_MONOTONIC_ACTIVE;
_Watchdog_Initialize(
&the_period->Timer,
@@ -282,88 +286,58 @@ rtems_status_code rtems_rate_monotonic_period(
return RTEMS_SUCCESSFUL;
case RATE_MONOTONIC_ACTIVE:
/* following is and could be a critical section problem */
_Thread_Executing->Wait.id = the_period->Object.id;
if ( _Rate_monotonic_Set_state( the_period ) ) {
_Thread_Enable_dispatch();
return RTEMS_SUCCESSFUL;
}
/* has expired -- fall into next case */
/*
* This tells the _Rate_monotonic_Timeout that this task is
* in the process of blocking on the period.
*/
the_period->state = RATE_MONOTONIC_OWNER_IS_BLOCKING;
_ISR_Enable( level );
_Thread_Executing->Wait.id = the_period->Object.id;
_Thread_Set_state( _Thread_Executing, STATES_WAITING_FOR_PERIOD );
/*
* Did the watchdog timer expire while we were actually blocking
* on it?
*/
_ISR_Disable( level );
local_state = the_period->state;
the_period->state = RATE_MONOTONIC_ACTIVE;
_ISR_Enable( level );
/*
* If it did, then we want to unblock ourself and continue as
* if nothing happen. The period was reset in the timeout routine.
*/
if ( local_state == RATE_MONOTONIC_EXPIRED_WHILE_BLOCKING )
_Thread_Clear_state( _Thread_Executing, STATES_WAITING_FOR_PERIOD );
_Thread_Enable_dispatch();
return RTEMS_SUCCESSFUL;
break;
case RATE_MONOTONIC_EXPIRED:
_ISR_Enable( level );
the_period->state = RATE_MONOTONIC_ACTIVE;
_Watchdog_Insert_ticks( &the_period->Timer, length );
_Thread_Enable_dispatch();
return RTEMS_TIMEOUT;
case RATE_MONOTONIC_OWNER_IS_BLOCKING:
case RATE_MONOTONIC_EXPIRED_WHILE_BLOCKING:
/*
* These should never happen.
*/
break;
}
}
return RTEMS_INTERNAL_ERROR; /* unreached - only to remove warnings */
}
/*PAGE
*
* _Rate_monotonic_Set_state
*
* This kernel routine sets the STATES_WAITING_FOR_PERIOD state in
* the running thread's tcb if the specified period has not expired.
* The ready chain is adjusted if necessary.
*
* Input parameters:
* the_period - pointer to period control block
*
* Output parameters:
* TRUE - if blocked successfully for period
* FALSE - if period has expired
*
* INTERRUPT LATENCY:
* delete node
* priority map
* select heir
*/
boolean _Rate_monotonic_Set_state(
Rate_monotonic_Control *the_period
)
{
Thread_Control *executing;
Chain_Control *ready;
ISR_Level level;
States_Control old_state;
executing = _Thread_Executing;
ready = executing->ready;
_ISR_Disable( level );
old_state = executing->current_state;
if ( _Rate_monotonic_Is_expired( the_period ) ) {
_ISR_Enable( level );
return( FALSE );
}
executing->current_state =
_States_Set( STATES_WAITING_FOR_PERIOD, old_state );
if ( _States_Is_ready( old_state ) ) {
if ( _Chain_Has_only_one_node( ready ) ) {
_Chain_Initialize_empty( ready );
_Priority_Remove_from_bit_map( &executing->Priority_map );
_ISR_Flash( level );
} else {
_Chain_Extract_unprotected( &executing->Object.Node );
_ISR_Flash( level );
}
if ( _Thread_Is_heir( executing ) )
_Thread_Calculate_heir();
_Context_Switch_necessary = TRUE;
}
_ISR_Enable( level );
return( TRUE );
}
/*PAGE
*
* _Rate_monotonic_Timeout
@@ -385,7 +359,7 @@ void _Rate_monotonic_Timeout(
)
{
Rate_monotonic_Control *the_period;
Objects_Locations location;
Objects_Locations location;
Thread_Control *the_thread;
the_period = _Rate_monotonic_Get( id, &location );
@@ -399,8 +373,10 @@ void _Rate_monotonic_Timeout(
the_thread->Wait.id == the_period->Object.id ) {
_Thread_Unblock( the_thread );
_Watchdog_Reset( &the_period->Timer );
}
else
} else if ( the_period->state == RATE_MONOTONIC_OWNER_IS_BLOCKING ) {
the_period->state = RATE_MONOTONIC_EXPIRED_WHILE_BLOCKING;
_Watchdog_Reset( &the_period->Timer );
} else
the_period->state = RATE_MONOTONIC_EXPIRED;
_Thread_Unnest_dispatch();
break;