From eb02f47b126b56091ffaeaad470a48e2ac6d57b5 Mon Sep 17 00:00:00 2001 From: Joel Sherrill Date: Wed, 10 Nov 1999 13:48:27 +0000 Subject: Committed modifications from ITRON Task and Task Dependendent Synchronization Working Group. Included are tests. --- c/src/exec/itron/include/itronsys/types.h | 2 - c/src/exec/itron/include/rtems/itron/object.h | 2 +- c/src/exec/itron/include/rtems/itron/task.h | 11 ++ c/src/exec/itron/inline/rtems/itron/task.inl | 28 ++++- c/src/exec/itron/src/can_wup.c | 21 +++- c/src/exec/itron/src/chg_pri.c | 40 +++++- c/src/exec/itron/src/cre_tsk.c | 79 +++++------- c/src/exec/itron/src/del_tsk.c | 15 ++- c/src/exec/itron/src/exd_tsk.c | 4 +- c/src/exec/itron/src/ext_tsk.c | 5 + c/src/exec/itron/src/frsm_tsk.c | 27 +++- c/src/exec/itron/src/get_tid.c | 6 + c/src/exec/itron/src/ref_tsk.c | 55 +++++++- c/src/exec/itron/src/rel_wai.c | 25 +++- c/src/exec/itron/src/rot_rdq.c | 20 +++ c/src/exec/itron/src/rsm_tsk.c | 27 +++- c/src/exec/itron/src/slp_tsk.c | 2 +- c/src/exec/itron/src/sta_tsk.c | 36 ++---- c/src/exec/itron/src/sus_tsk.c | 29 ++++- c/src/exec/itron/src/task.c | 4 +- c/src/exec/itron/src/ter_tsk.c | 26 +++- c/src/exec/rtems/src/taskresume.c | 2 +- c/src/exec/rtems/src/tasksuspend.c | 2 +- c/src/exec/score/include/rtems/score/Makefile.in | 5 +- c/src/exec/score/include/rtems/score/thread.h | 48 ++++++- c/src/exec/score/inline/rtems/score/thread.inl | 18 --- c/src/exec/score/macros/rtems/score/thread.inl | 9 -- c/src/exec/score/src/Makefile.in | 8 +- c/src/exec/score/src/threadinitialize.c | 1 + c/src/exec/score/src/threadrestart.c | 3 +- c/src/exec/score/src/threadresume.c | 95 ++++++++++++++ c/src/exec/score/src/threadrotatequeue.c | 93 ++++++++++++++ c/src/exec/score/src/threadsuspend.c | 83 +++++++++++++ c/src/tests/itrontests/itrontask03/Makefile.in | 2 +- c/src/tests/itrontests/itrontask03/spinit.c | 152 ----------------------- 35 files changed, 696 insertions(+), 289 deletions(-) create mode 100644 c/src/exec/score/src/threadresume.c create mode 100644 c/src/exec/score/src/threadrotatequeue.c create mode 100644 c/src/exec/score/src/threadsuspend.c delete mode 100644 c/src/tests/itrontests/itrontask03/spinit.c (limited to 'c/src') diff --git a/c/src/exec/itron/include/itronsys/types.h b/c/src/exec/itron/include/itronsys/types.h index c9dc8db40e..80cb31f3b8 100644 --- a/c/src/exec/itron/include/itronsys/types.h +++ b/c/src/exec/itron/include/itronsys/types.h @@ -19,14 +19,12 @@ extern "C" { * off the shell programs including paranoia. */ -#if 0 typedef signed8 B; /* signed 8-bit integer */ typedef signed16 H; /* signed 16-bit integer */ typedef signed32 W; /* signed 32-bit integer */ typedef unsigned8 UB; /* unsigned 8-bit integer */ typedef unsigned16 UH; /* unsigned 16-bit integer */ typedef unsigned32 UW; /* unsigned 32-bit integer */ -#endif typedef unsigned32 VW; /* unpredictable data type (32-bit size) */ typedef unsigned16 VH; /* unpredictable data type (16-bit size) */ diff --git a/c/src/exec/itron/include/rtems/itron/object.h b/c/src/exec/itron/include/rtems/itron/object.h index 71bc9ed6d1..919baffd9e 100644 --- a/c/src/exec/itron/include/rtems/itron/object.h +++ b/c/src/exec/itron/include/rtems/itron/object.h @@ -80,7 +80,7 @@ typedef Objects_Control ITRON_Objects_Control; #define _ITRON_Objects_Clarify_get_id_error( _the_information, _id ) \ (((_id) < -4) ? E_OACV : /* attempt to access a "system object" */ \ ((_id) <= 0) ? E_ID : /* bogus index of 0 - -3 */ \ - ((_id) <= (_the_information)->maximum) ? E_OBJ : /* object is in use */ \ + ((_id) <= (_the_information)->maximum) ? E_NOEXS : /* does not exist */ \ E_ID) /* simply a bad id */ diff --git a/c/src/exec/itron/include/rtems/itron/task.h b/c/src/exec/itron/include/rtems/itron/task.h index fffcc16d82..5d52d632f5 100644 --- a/c/src/exec/itron/include/rtems/itron/task.h +++ b/c/src/exec/itron/include/rtems/itron/task.h @@ -77,7 +77,18 @@ ER _ITRON_Delete_task( Thread_Control *the_thread ); +/* XXX remove the need for this. Enable dispatch should not be hidden */ + +#define _ITRON_return_errorno( _errno ) \ +do { \ + _Thread_Enable_dispatch(); \ + return _errno; \ +} while (0); + + +#ifndef __RTEMS_APPLICATION__ #include +#endif #ifdef __cplusplus } diff --git a/c/src/exec/itron/inline/rtems/itron/task.inl b/c/src/exec/itron/inline/rtems/itron/task.inl index 1833fee84a..834e47b0c9 100644 --- a/c/src/exec/itron/inline/rtems/itron/task.inl +++ b/c/src/exec/itron/inline/rtems/itron/task.inl @@ -109,7 +109,13 @@ RTEMS_INLINE_ROUTINE Thread_Control *_ITRON_Task_Get ( ID id, Objects_Locations *location ) -{ +{ + if ( id == 0 ) { + _Thread_Disable_dispatch(); + *location = OBJECTS_LOCAL; + return _Thread_Executing; + } + return (Thread_Control *) _ITRON_Objects_Get( &_ITRON_Task_Information, id, location ); } @@ -144,17 +150,29 @@ RTEMS_INLINE_ROUTINE boolean _ITRON_Task_Is_null ( * _ITRON_tasks_Priority_to_Core */ -RTEMS_INLINE_ROUTINE Priority_Control _ITRON_Task_Priority_to_Core( - PRI _priority +RTEMS_INLINE_ROUTINE _ITRON_Task_Priority_to_Core( + PRI ITRON_priority +) +{ + return (Priority_Control) ITRON_priority; +} + +/*PAGE + * + * _ITRON_tasks_Core_to_Priority + */ + +RTEMS_INLINE_ROUTINE _ITRON_Task_Core_to_Priority( + Priority_Control core_priority ) { - return ((Priority_Control) (_priority)); + return (PRI) core_priority; } + #ifdef __cplusplus } #endif #endif /* end of include file */ - diff --git a/c/src/exec/itron/src/can_wup.c b/c/src/exec/itron/src/can_wup.c index d75d379de9..b7442d1392 100644 --- a/c/src/exec/itron/src/can_wup.c +++ b/c/src/exec/itron/src/can_wup.c @@ -25,6 +25,25 @@ ER can_wup( ID tskid ) { - return E_OK; + register Thread_Control *the_thread; + Objects_Locations location; + + the_thread = _ITRON_Task_Get( tskid, &location ); + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + switch ( location ) { + case OBJECTS_REMOTE: + case OBJECTS_ERROR: + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + case OBJECTS_LOCAL: + /* + * XXX - FILL ME IN. + */ + return E_OK; + } + + return E_OBJ; /* XXX - Should never get here */ } diff --git a/c/src/exec/itron/src/chg_pri.c b/c/src/exec/itron/src/chg_pri.c index b2d42905e5..412bab054e 100644 --- a/c/src/exec/itron/src/chg_pri.c +++ b/c/src/exec/itron/src/chg_pri.c @@ -25,6 +25,44 @@ ER chg_pri( PRI tskpri ) { - return E_OK; + register Thread_Control *the_thread; + Objects_Locations location; + Priority_Control new_priority; + + the_thread = _ITRON_Task_Get( tskid, &location ); + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + if (_States_Is_dormant( the_thread->current_state )) + return -1; + + if (( tskpri <= 0 ) || ( tskpri >= 256 )) + _ITRON_return_errorno( E_PAR ); + + switch ( location ) { + case OBJECTS_REMOTE: + case OBJECTS_ERROR: + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid )); + + case OBJECTS_LOCAL: + new_priority = _ITRON_Task_Priority_to_Core( tskpri ); + the_thread->real_priority = new_priority; + + /* + * XXX This is from the rtems side and I'm not sure what this is for. + * XXX Is this check right or should change priority be called + * regardless? + */ + + if ( the_thread->resource_count == 0 || + the_thread->current_priority > new_priority ) + _Thread_Change_priority( the_thread, new_priority, FALSE ); + + _Thread_Enable_dispatch(); + return E_OK; + } + + return E_OBJ; /* XXX - Should never get here */ } + diff --git a/c/src/exec/itron/src/cre_tsk.c b/c/src/exec/itron/src/cre_tsk.c index 76bcd75eda..f4e8e605fc 100644 --- a/c/src/exec/itron/src/cre_tsk.c +++ b/c/src/exec/itron/src/cre_tsk.c @@ -21,28 +21,6 @@ * cre_tsk - Create Task */ -/* - * XXX - How do I return these errors ??? Do I have to validate the ID - prior to calling the ID routine ?? - E_NOMEM Insufficient memory (Memory for control block and/or user stack - cannot be allocated) - E_ID Invalid ID Number (tskid was invalid or could not be used) - E_RSATR Reserved attribute (tskatr was invalid or could not be used) - E_OBJ Invalid object state (a task of the same ID already exists) - E_OACV Object access violation (A tskid less than -4 was specified from - a user task. This is implementation dependent.) - E_PAR Parameter error (pk_ctsk, task, itskpri and/or stksz is invalid) - EN_OBJNO An object number which could not be accessed on the target node - is specified. - EN_CTXID Specified an object on another node when the system call was - issued from a task in dispatch disabled state or from a task- - independent portion - EN_PAR A value outside the range supported by the target node and/or - transmission packet format was specified as a parameter (a value - outside supported range was specified for exinf, tskatr, task, - itskpri and/or stksz) - */ - ER cre_tsk( ID tskid, T_CTSK *pk_ctsk @@ -59,19 +37,40 @@ ER cre_tsk( _Thread_Disable_dispatch(); + /* + * Validate Parameters. + */ + + if ( pk_ctsk == NULL ) + _ITRON_return_errorno( E_PAR ); + + if ((pk_ctsk->tskatr != TA_ASM ) && + (pk_ctsk->tskatr != TA_HLNG) && + (pk_ctsk->tskatr != TA_COP0) && + (pk_ctsk->tskatr != TA_COP1) && + (pk_ctsk->tskatr != TA_COP2) && + (pk_ctsk->tskatr != TA_COP3) && + (pk_ctsk->tskatr != TA_COP4) && + (pk_ctsk->tskatr != TA_COP5) && + (pk_ctsk->tskatr != TA_COP6) && + (pk_ctsk->tskatr != TA_COP7)) + _ITRON_return_errorno( E_RSATR ); + + if (( pk_ctsk->itskpri <= 0 ) || ( pk_ctsk->itskpri >= 256 )) + if ( pk_ctsk->itskpri <= 0 ) + _ITRON_return_errorno( E_PAR ); + if ( pk_ctsk->task == NULL ) + _ITRON_return_errorno( E_PAR ); + if ( pk_ctsk->stksz < 0 ) + _ITRON_return_errorno( E_PAR ); + /* * allocate the thread. */ the_thread = _ITRON_Task_Allocate( tskid ); - if ( !the_thread ) { - ena_dsp(); - return _ITRON_Task_Clarify_allocation_id_error( tskid ); - } - - /* - * XXX - FIX THE VARIABLES TO THE CORRECT VALUES!!! - */ + if ( !the_thread ) + _ITRON_return_errorno( _ITRON_Task_Clarify_allocation_id_error( tskid ) ); /* * Initialize the core thread for this task. @@ -83,7 +82,7 @@ ER cre_tsk( the_thread, NULL, pk_ctsk->stksz, - TRUE, /* XXX - All tasks FP ??? */ + TRUE, /* XXX - All tasks FP for now */ core_priority, TRUE, THREAD_CPU_BUDGET_ALGORITHM_EXHAUST_TIMESLICE, @@ -94,22 +93,9 @@ ER cre_tsk( if ( !status ) { _ITRON_Task_Free( the_thread ); - _Thread_Enable_dispatch(); - return -1; -#if (0) -/* XXX */ -#endif + _ITRON_return_errorno( E_NOMEM ); } -#if (0) /* XXX We have any thing else to set per API structure? */ - api = the_thread->API_Extensions[ THREAD_API_ITRON ]; - asr = &api->Signal; - - asr->is_enabled = FALSE; - - *id = the_thread->Object.id; -#endif - /* * This insures we evaluate the process-wide signals pending when we * first run. @@ -125,3 +111,6 @@ ER cre_tsk( return E_OK; } + + + diff --git a/c/src/exec/itron/src/del_tsk.c b/c/src/exec/itron/src/del_tsk.c index 5230acddca..4514eb6348 100644 --- a/c/src/exec/itron/src/del_tsk.c +++ b/c/src/exec/itron/src/del_tsk.c @@ -29,16 +29,21 @@ ER del_tsk( Objects_Locations location; ER result; - /* XXX - Fix Documentation and error checking for this error on self */ - the_thread = _ITRON_Task_Get( tskid, &location ); - _Thread_Disable_dispatch(); + + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + if ( the_thread == _Thread_Executing ) + _ITRON_return_errorno( E_OBJ ); + + if ( !_States_Is_dormant( the_thread->current_state ) ) + _ITRON_return_errorno( E_OBJ ); switch ( location ) { case OBJECTS_REMOTE: case OBJECTS_ERROR: - _Thread_Enable_dispatch(); - return _ITRON_Task_Clarify_get_id_error( tskid ); + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); case OBJECTS_LOCAL: result = _ITRON_Delete_task( the_thread ); diff --git a/c/src/exec/itron/src/exd_tsk.c b/c/src/exec/itron/src/exd_tsk.c index c2b86f3126..51c0eb04c5 100644 --- a/c/src/exec/itron/src/exd_tsk.c +++ b/c/src/exec/itron/src/exd_tsk.c @@ -25,13 +25,13 @@ void exd_tsk( void ) { Objects_Information *the_information; + _Thread_Disable_dispatch(); + the_information = _Objects_Get_information( _Thread_Executing->Object.id ); /* This should never happen if _Thread_Get() works right */ assert( the_information ); - _Thread_Disable_dispatch(); - _Thread_Set_state( _Thread_Executing, STATES_DORMANT ); _ITRON_Delete_task( _Thread_Executing ); diff --git a/c/src/exec/itron/src/ext_tsk.c b/c/src/exec/itron/src/ext_tsk.c index a8a3b0ec23..d3f13939f1 100644 --- a/c/src/exec/itron/src/ext_tsk.c +++ b/c/src/exec/itron/src/ext_tsk.c @@ -23,5 +23,10 @@ void ext_tsk( void ) { + _Thread_Disable_dispatch(); + + _Thread_Restart( _Thread_Executing, NULL, 0 ); _Thread_Set_state( _Thread_Executing, STATES_DORMANT ); + + _Thread_Enable_dispatch(); } diff --git a/c/src/exec/itron/src/frsm_tsk.c b/c/src/exec/itron/src/frsm_tsk.c index 8fe5e9e6fc..2840061dd6 100644 --- a/c/src/exec/itron/src/frsm_tsk.c +++ b/c/src/exec/itron/src/frsm_tsk.c @@ -25,7 +25,32 @@ ER frsm_tsk( ID tskid ) { - return E_OK; + register Thread_Control *the_thread; + Objects_Locations location; + + the_thread = _ITRON_Task_Get( tskid, &location ); + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + if ( the_thread == _Thread_Executing ) + _ITRON_return_errorno( E_OBJ ); + + if (_States_Is_dormant( the_thread->current_state )) + _ITRON_return_errorno( E_OBJ ); + + switch ( location ) { + case OBJECTS_REMOTE: + case OBJECTS_ERROR: + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + case OBJECTS_LOCAL: + _Thread_Resume( the_thread, TRUE ); + _Thread_Enable_dispatch(); + return E_OK; + } + + return E_OBJ; /* XXX - Should never get here */ + } diff --git a/c/src/exec/itron/src/get_tid.c b/c/src/exec/itron/src/get_tid.c index 1c5175052a..7904e3e167 100644 --- a/c/src/exec/itron/src/get_tid.c +++ b/c/src/exec/itron/src/get_tid.c @@ -24,6 +24,12 @@ ER get_tid( ID *p_tskid ) { + /* + * This does not support multiprocessing. The id handling will have + * to be enhanced to support multiprocessing. + */ + + *p_tskid = _Objects_Get_index( _Thread_Executing->Object.id ); return E_OK; } diff --git a/c/src/exec/itron/src/ref_tsk.c b/c/src/exec/itron/src/ref_tsk.c index 50ce76e8ed..2c6ad11709 100644 --- a/c/src/exec/itron/src/ref_tsk.c +++ b/c/src/exec/itron/src/ref_tsk.c @@ -26,6 +26,59 @@ ER ref_tsk( ID tskid ) { - return E_OK; + register Thread_Control *the_thread; + Objects_Locations location; + Priority_Control core_priority; + + the_thread = _ITRON_Task_Get( tskid, &location ); + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + if (!pk_rtsk) + _ITRON_return_errorno( E_PAR ); + + /* + * The following are extended functions [level X ]. + * XXX - tskwait, wid, wupcnt, and tskatr are presently not implemented. + */ + + pk_rtsk->tskwait = 0; + pk_rtsk->wid = 0; + pk_rtsk->wupcnt = 0; + pk_rtsk->suscnt = the_thread->suspend_count; + pk_rtsk->tskatr = 0; + pk_rtsk->task = the_thread->Start.entry_point; + core_priority = the_thread->Start.initial_priority; + pk_rtsk->itskpri = _ITRON_Task_Core_to_Priority( core_priority ); + pk_rtsk->stksz = the_thread->Start.Initial_stack.size; + + /* + * The following are required. + */ + + pk_rtsk->exinf = NULL; /* extended information */ + pk_rtsk->tskpri = _ITRON_Task_Core_to_Priority(the_thread->current_priority); + pk_rtsk->tskstat = 0; + + /* + * Mask in the tskstat information + * Convert the task state XXX double check this + */ + + if ( the_thread == _Thread_Executing ) + pk_rtsk->tskstat |= TTS_RUN; + if ((the_thread->current_state & STATES_READY) != 0) + pk_rtsk->tskstat = TTS_RDY; + if (_States_Is_dormant( the_thread->current_state )) + pk_rtsk->tskstat = TTS_DMT; + if ((the_thread->current_state & STATES_SUSPENDED) != 0) + pk_rtsk->tskstat = TTS_SUS; + if ((the_thread->current_state & STATES_BLOCKED) != 0) + pk_rtsk->tskstat = TTS_WAI; + + return E_OK; /* XXX - Should never get here */ } + + + diff --git a/c/src/exec/itron/src/rel_wai.c b/c/src/exec/itron/src/rel_wai.c index 390433ec0c..81d7e6dc94 100644 --- a/c/src/exec/itron/src/rel_wai.c +++ b/c/src/exec/itron/src/rel_wai.c @@ -24,7 +24,30 @@ ER rel_wai( ID tskid ) { - return E_OK; + register Thread_Control *the_thread; + Objects_Locations location; + + the_thread = _ITRON_Task_Get( tskid, &location ); + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + _Thread_Disable_dispatch(); + + switch ( location ) { + case OBJECTS_REMOTE: + case OBJECTS_ERROR: + _Thread_Enable_dispatch(); + return _ITRON_Task_Clarify_get_id_error( tskid ); + + case OBJECTS_LOCAL: + /* + * XXX - FILL ME IN. + */ + return E_OK; + } + + return E_OBJ; /* XXX - Should never get here */ } + diff --git a/c/src/exec/itron/src/rot_rdq.c b/c/src/exec/itron/src/rot_rdq.c index b329313946..ac6d89d55f 100644 --- a/c/src/exec/itron/src/rot_rdq.c +++ b/c/src/exec/itron/src/rot_rdq.c @@ -24,6 +24,26 @@ ER rot_rdq( PRI tskpri ) { + PRI priority; + + + _Thread_Disable_dispatch(); + + /* + * Yield of processor will rotate the queue for this processor. + */ + + if (( tskpri <= 0 ) || ( tskpri >= 256 )) + _ITRON_return_errorno( E_PAR ); + + priority = _ITRON_Task_Core_to_Priority(_Thread_Executing->current_priority); + if ( priority == tskpri ) + _Thread_Yield_processor(); + else { + _Thread_Rotate_Ready_Queue( _ITRON_Task_Core_to_Priority( tskpri ) ); + } + _Thread_Enable_dispatch(); + return E_OK; } diff --git a/c/src/exec/itron/src/rsm_tsk.c b/c/src/exec/itron/src/rsm_tsk.c index a19842f8da..81be3446eb 100644 --- a/c/src/exec/itron/src/rsm_tsk.c +++ b/c/src/exec/itron/src/rsm_tsk.c @@ -25,6 +25,31 @@ ER rsm_tsk( ID tskid ) { - return E_OK; + register Thread_Control *the_thread; + Objects_Locations location; + + the_thread = _ITRON_Task_Get( tskid, &location ); + + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + if ( the_thread == _Thread_Executing ) + _ITRON_return_errorno( E_OBJ ); + + if (_States_Is_dormant( the_thread->current_state )) + _ITRON_return_errorno( E_OBJ ); + + switch ( location ) { + case OBJECTS_REMOTE: + case OBJECTS_ERROR: + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + case OBJECTS_LOCAL: + _Thread_Resume( the_thread, FALSE ); + _Thread_Enable_dispatch(); + return E_OK; + } + + return E_OBJ; /* XXX - Should never get here */ } diff --git a/c/src/exec/itron/src/slp_tsk.c b/c/src/exec/itron/src/slp_tsk.c index 00562dda92..b8c84c9808 100644 --- a/c/src/exec/itron/src/slp_tsk.c +++ b/c/src/exec/itron/src/slp_tsk.c @@ -19,7 +19,7 @@ /* - * slp_tsk - Sleep Task Sleep Task with Timeout + * slp_tsk - Sleep Task */ ER slp_tsk( void ) diff --git a/c/src/exec/itron/src/sta_tsk.c b/c/src/exec/itron/src/sta_tsk.c index 91a6586c0e..73cc49e36b 100644 --- a/c/src/exec/itron/src/sta_tsk.c +++ b/c/src/exec/itron/src/sta_tsk.c @@ -21,24 +21,6 @@ * sta_tsk - Start Task */ -/* - * XXX - How Do I know when these happen ??? - E_NOEXS Object does not exist (the task specified by tskid does not exist) - E_OACV Object access violation (A tskid less than -4 was specified from - a user task. This is implementation dependent.) - E_OBJ Invalid object state (the target task is not in DORMANT state) - EN_OBJNO An object number which could not be accessed on the target node - is specified. XXX Should never get on a single processor?? - EN_CTXID Specified an object on another node when the system call was - issued from a task in dispatch disabled state or from a task- - independent portionXXX Should never get on a single processor?? - EN_PAR A value outside the range supported by the target node and/or - transmission packet format was specified as a parameter (a value - outside supported range was specified for stacd) -XXX- What does _ITRON_Task_Get return on an invalid id and how do you know - if it is E_ID, E_NOEXS, E_OACV -*/ - ER sta_tsk( ID tskid, INT stacd @@ -49,10 +31,16 @@ ER sta_tsk( boolean status; the_thread = _ITRON_Task_Get( tskid, &location ); + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + if ( !_States_Is_dormant( the_thread->current_state ) ) + _ITRON_return_errorno( E_OBJ ); + switch ( location ) { case OBJECTS_REMOTE: case OBJECTS_ERROR: - return E_ID; /* XXX */ + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); case OBJECTS_LOCAL: status = _Thread_Start( @@ -63,14 +51,8 @@ ER sta_tsk( 0 /* unused */ ); - /* - * Wrong state XXX - */ - - if ( !status ) { - _Thread_Enable_dispatch(); - return E_OBJ; - } + if ( !status ) + _ITRON_return_errorno( E_OBJ ); _Thread_Enable_dispatch(); return E_OK; diff --git a/c/src/exec/itron/src/sus_tsk.c b/c/src/exec/itron/src/sus_tsk.c index f4a5d5b851..12ef07ff7b 100644 --- a/c/src/exec/itron/src/sus_tsk.c +++ b/c/src/exec/itron/src/sus_tsk.c @@ -29,6 +29,33 @@ ER sus_tsk( ID tskid ) { - return E_OK; + register Thread_Control *the_thread; + Objects_Locations location; + + the_thread = _ITRON_Task_Get( tskid, &location ); + if (!the_thread) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + if ( the_thread == _Thread_Executing ) + _ITRON_return_errorno( E_OBJ ); + + switch ( location ) { + case OBJECTS_REMOTE: + case OBJECTS_ERROR: + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + case OBJECTS_LOCAL: + _Thread_Suspend( the_thread ); + _Thread_Enable_dispatch(); + return E_OK; + } + + return E_OBJ; /* XXX - Should never get here */ } + + + + + + diff --git a/c/src/exec/itron/src/task.c b/c/src/exec/itron/src/task.c index f646b29d49..c4e785a4bb 100644 --- a/c/src/exec/itron/src/task.c +++ b/c/src/exec/itron/src/task.c @@ -117,10 +117,8 @@ ER _ITRON_Delete_task( Objects_Information *the_information; the_information = _Objects_Get_information( the_thread->Object.id ); - if ( !the_information ) { - return -1; /* XXX */ - /* This should never happen if _Thread_Get() works right */ + return E_OBJ; /* XXX - should never happen */ } _Thread_Close( the_information, the_thread ); diff --git a/c/src/exec/itron/src/ter_tsk.c b/c/src/exec/itron/src/ter_tsk.c index c0d05c1fec..070cfcee25 100644 --- a/c/src/exec/itron/src/ter_tsk.c +++ b/c/src/exec/itron/src/ter_tsk.c @@ -18,13 +18,37 @@ /* - * ter_tsk - Terminate Other Task + * ter_tsk - Terminate Other Task - Set State to DORMANT */ ER ter_tsk( ID tskid ) { + register Thread_Control *the_thread; + Objects_Locations location; + + the_thread = _ITRON_Task_Get( tskid, &location ); + + if ( !the_thread ) + _ITRON_return_errorno( _ITRON_Task_Clarify_get_id_error( tskid ) ); + + if ( the_thread == _Thread_Executing ) + _ITRON_return_errorno( E_OBJ ); + + if ( _States_Is_dormant( the_thread->current_state ) ) + _ITRON_return_errorno( E_OBJ ); + + _Thread_Restart( the_thread, NULL, 0 ); + _Thread_Set_state( the_thread, STATES_DORMANT ); + + _Thread_Enable_dispatch(); return E_OK; } + + + + + + diff --git a/c/src/exec/rtems/src/taskresume.c b/c/src/exec/rtems/src/taskresume.c index 70c2051eaf..92360db43b 100644 --- a/c/src/exec/rtems/src/taskresume.c +++ b/c/src/exec/rtems/src/taskresume.c @@ -70,7 +70,7 @@ rtems_status_code rtems_task_resume( case OBJECTS_LOCAL: if ( _States_Is_suspended( the_thread->current_state ) ) { - _Thread_Resume( the_thread ); + _Thread_Resume( the_thread, TRUE ); _Thread_Enable_dispatch(); return RTEMS_SUCCESSFUL; } diff --git a/c/src/exec/rtems/src/tasksuspend.c b/c/src/exec/rtems/src/tasksuspend.c index c9635b0ff3..04fafcbea9 100644 --- a/c/src/exec/rtems/src/tasksuspend.c +++ b/c/src/exec/rtems/src/tasksuspend.c @@ -71,7 +71,7 @@ rtems_status_code rtems_task_suspend( case OBJECTS_LOCAL: if ( !_States_Is_suspended( the_thread->current_state ) ) { - _Thread_Set_state( the_thread, STATES_SUSPENDED ); + _Thread_Suspend( the_thread ); _Thread_Enable_dispatch(); return RTEMS_SUCCESSFUL; } diff --git a/c/src/exec/score/include/rtems/score/Makefile.in b/c/src/exec/score/include/rtems/score/Makefile.in index 7dc33b70a7..42e8a8a055 100644 --- a/c/src/exec/score/include/rtems/score/Makefile.in +++ b/c/src/exec/score/include/rtems/score/Makefile.in @@ -11,6 +11,8 @@ subdir = score/include/rtems/score RTEMS_ROOT = @RTEMS_ROOT@ PROJECT_ROOT = @PROJECT_ROOT@ +HAS_ITRON_API = @HAS_ITRON_API@ + VPATH = @srcdir@ include $(RTEMS_ROOT)/make/custom/@RTEMS_BSP@.cfg @@ -93,8 +95,7 @@ $(TARGOPTS): @if test "$(HAS_POSIX_API)" = "yes"; then \ echo "#define RTEMS_POSIX_API 1" >>$@; \ fi - echo "SHOULD BE HAS_ITRON_API not RTEMS_HAS_ITRON_API XXX " - @if test "$(RTEMS_HAS_ITRON_API)" = "yes"; then \ + @if test "$(HAS_ITRON_API)" = "yes"; then \ echo "#define RTEMS_ITRON_API 1" >>$@; \ fi @if test "$(RTEMS_USE_NEWLIB)" = "yes"; then \ diff --git a/c/src/exec/score/include/rtems/score/thread.h b/c/src/exec/score/include/rtems/score/thread.h index 26452bffbe..bfc42b6fad 100644 --- a/c/src/exec/score/include/rtems/score/thread.h +++ b/c/src/exec/score/include/rtems/score/thread.h @@ -185,6 +185,7 @@ struct Thread_Control_struct { MP_packet_Prefix *receive_packet; #endif /****************** end of common block ********************/ + unsigned32 suspend_count; boolean is_global; boolean do_post_task_switch_extension; @@ -552,6 +553,20 @@ void _Thread_Tickle_timeslice( void ); void _Thread_Yield_processor( void ); +/* + * _Thread_Rotate_Ready_Queue + * + * DESCRIPTION: + * + * This routine is invoked to rotate the ready queue for the + * given priority. It can be used to yeild the processor + * by rotating the executing threads ready queue. + */ + +void _Thread_Rotate_Ready_Queue( + Priority_Control priority +); + /* * _Thread_Load_environment * @@ -623,12 +638,43 @@ void _Thread_Set_priority( Priority_Control new_priority ); +/* + * _Thread_Suspend + * + * DESCRIPTION: + * + * This routine updates the related suspend fields in the_thread + * control block to indicate the current nested level. + */ + +void _Thread_Suspend( + Thread_Control *the_thread +); + +/* + * _Thread_Resume + * + * DESCRIPTION: + * + * This routine updates the related suspend fields in the_thread + * control block to indicate the current nested level. A force + * parameter of TRUE will force a resume and clear the suspend count. + */ + +void _Thread_Resume( + Thread_Control *the_thread, + boolean force +); + /* * _Thread_Evaluate_mode * * DESCRIPTION: * - * This routine XXX + * This routine evaluates the current scheduling information for the + * system and determines if a context switch is required. This + * is usually called after changing an execution mode such as preemptability + * for a thread. */ boolean _Thread_Evaluate_mode( void ); diff --git a/c/src/exec/score/inline/rtems/score/thread.inl b/c/src/exec/score/inline/rtems/score/thread.inl index eef4532c07..650439e8e6 100644 --- a/c/src/exec/score/inline/rtems/score/thread.inl +++ b/c/src/exec/score/inline/rtems/score/thread.inl @@ -82,24 +82,6 @@ RTEMS_INLINE_ROUTINE boolean _Thread_Is_executing_also_the_heir( void ) return ( _Thread_Executing == _Thread_Heir ); } -/*PAGE - * - * _Thread_Resume - * - * DESCRIPTION: - * - * This routine clears the SUSPENDED state for the_thread. It performs - * any necessary scheduling operations including the selection of - * a new heir thread. - */ - -RTEMS_INLINE_ROUTINE void _Thread_Resume ( - Thread_Control *the_thread -) -{ - _Thread_Clear_state( the_thread, STATES_SUSPENDED ); -} - /*PAGE * * _Thread_Unblock diff --git a/c/src/exec/score/macros/rtems/score/thread.inl b/c/src/exec/score/macros/rtems/score/thread.inl index 96761143b8..415bb0fb8d 100644 --- a/c/src/exec/score/macros/rtems/score/thread.inl +++ b/c/src/exec/score/macros/rtems/score/thread.inl @@ -53,15 +53,6 @@ #define _Thread_Is_executing_also_the_heir() \ ( _Thread_Executing == _Thread_Heir ) -/*PAGE - * - * _Thread_Resume - * - */ - -#define _Thread_Resume( _the_thread ) \ - _Thread_Clear_state( (_the_thread), STATES_SUSPENDED ) - /*PAGE * * _Thread_Unblock diff --git a/c/src/exec/score/src/Makefile.in b/c/src/exec/score/src/Makefile.in index 28ad2ef6a3..99cce9fa76 100644 --- a/c/src/exec/score/src/Makefile.in +++ b/c/src/exec/score/src/Makefile.in @@ -42,10 +42,10 @@ OBJECT_C_PIECES = object objectallocate objectallocatebyindex \ THREAD_C_PIECES = thread threadchangepriority threadclearstate threadclose \ threadcreateidle threaddelayended threaddispatch threadevaluatemode \ threadget threadhandler threadidlebody threadinitialize threadloadenv \ - threadready threadresettimeslice threadrestart threadsetpriority \ - threadsetstate threadsettransient threadstackallocate threadstackfree \ - threadstart threadstartmultitasking threadtickletimeslice \ - threadyieldprocessor + threadready threadresettimeslice threadrestart threadresume \ + threadrotatequeue threadsetpriority threadsetstate threadsettransient \ + threadstackallocate threadstackfree threadstart threadstartmultitasking \ + threadsuspend threadtickletimeslice threadyieldprocessor THREADQ_C_PIECES= threadq threadqdequeue threadqdequeuefifo \ threadqdequeuepriority threadqenqueue threadqenqueuefifo \ diff --git a/c/src/exec/score/src/threadinitialize.c b/c/src/exec/score/src/threadinitialize.c index 28cfa324bc..f294d865bf 100644 --- a/c/src/exec/score/src/threadinitialize.c +++ b/c/src/exec/score/src/threadinitialize.c @@ -153,6 +153,7 @@ boolean _Thread_Initialize( the_thread->current_state = STATES_DORMANT; the_thread->resource_count = 0; + the_thread->suspend_count = 0; the_thread->real_priority = priority; the_thread->Start.initial_priority = priority; the_thread->ticks_executed = 0; diff --git a/c/src/exec/score/src/threadrestart.c b/c/src/exec/score/src/threadrestart.c index 7419514a4f..229dbe2d94 100644 --- a/c/src/exec/score/src/threadrestart.c +++ b/c/src/exec/score/src/threadrestart.c @@ -44,7 +44,8 @@ boolean _Thread_Restart( if ( !_States_Is_dormant( the_thread->current_state ) ) { _Thread_Set_transient( the_thread ); - the_thread->resource_count = 0; + the_thread->resource_count = 0; + the_thread->suspend_count = 0; the_thread->is_preemptible = the_thread->Start.is_preemptible; the_thread->budget_algorithm = the_thread->Start.budget_algorithm; the_thread->budget_callout = the_thread->Start.budget_callout; diff --git a/c/src/exec/score/src/threadresume.c b/c/src/exec/score/src/threadresume.c new file mode 100644 index 0000000000..067dc59610 --- /dev/null +++ b/c/src/exec/score/src/threadresume.c @@ -0,0 +1,95 @@ +/* + * Thread Handler + * + * + * COPYRIGHT (c) 1989-1998. + * On-Line Applications Research Corporation (OAR). + * Copyright assigned to U.S. Government, 1994. + * + * The license and distribution terms for this file may be + * found in found in the file LICENSE in this distribution or at + * http://www.OARcorp.com/rtems/license.html. + * + * $Id$ + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/*PAGE + * + * _Thread_Resume + * + * This kernel routine clears the SUSPEND state if the suspend_count + * drops below one. If the force parameter is set the suspend_count + * is forced back to zero. The thread ready chain is adjusted if + * necessary and the Heir thread is set accordingly. + * + * Input parameters: + * the_thread - pointer to thread control block + * force - force the suspend count back to 0 + * + * Output parameters: NONE + * + * INTERRUPT LATENCY: + * priority map + * select heir + */ + + +void _Thread_Resume( + Thread_Control *the_thread, + boolean force +) +{ + + ISR_Level level; + States_Control current_state; + + _ISR_Disable( level ); + + if ( force == TRUE ) + the_thread->suspend_count = 0; + else + the_thread->suspend_count--; + + if ( the_thread->suspend_count > 0 ) { + _ISR_Enable( level ); + return; + } + + current_state = the_thread->current_state; + if ( current_state & STATES_SUSPENDED ) { + current_state = + the_thread->current_state = _States_Clear(STATES_SUSPENDED, current_state); + + if ( _States_Is_ready( current_state ) ) { + + _Priority_Add_to_bit_map( &the_thread->Priority_map ); + + _Chain_Append_unprotected(the_thread->ready, &the_thread->Object.Node); + + _ISR_Flash( level ); + + if ( the_thread->current_priority < _Thread_Heir->current_priority ) { + _Thread_Heir = the_thread; + if ( _Thread_Executing->is_preemptible || + the_thread->current_priority == 0 ) + _Context_Switch_necessary = TRUE; + } + } + } + + _ISR_Enable( level ); +} diff --git a/c/src/exec/score/src/threadrotatequeue.c b/c/src/exec/score/src/threadrotatequeue.c new file mode 100644 index 0000000000..f7ee9c12f5 --- /dev/null +++ b/c/src/exec/score/src/threadrotatequeue.c @@ -0,0 +1,93 @@ +/* + * Thread Handler + * + * + * COPYRIGHT (c) 1989-1998. + * On-Line Applications Research Corporation (OAR). + * Copyright assigned to U.S. Government, 1994. + * + * The license and distribution terms for this file may be + * found in found in the file LICENSE in this distribution or at + * http://www.OARcorp.com/rtems/license.html. + * + * $Id$ + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/*PAGE + * + * _Thread_Rotate_Ready_Queue + * + * This kernel routine will rotate the ready queue. + * remove the running THREAD from the ready chain + * and place it immediatly at the rear of this chain. Reset timeslice + * and yield the processor functions both use this routine, therefore if + * reset is TRUE and this is the only thread on the chain then the + * timeslice counter is reset. The heir THREAD will be updated if the + * running is also the currently the heir. + * + * Input parameters: + * Priority of the queue we wish to modify. + * + * Output parameters: NONE + * + * INTERRUPT LATENCY: + * ready chain + * select heir + */ + +void _Thread_Rotate_Ready_Queue( + Priority_Control priority +) +{ + ISR_Level level; + Thread_Control *executing; + Chain_Control *ready; + Chain_Node *node; + + ready = &_Thread_Ready_chain[ priority ]; + executing = _Thread_Executing; + + if ( ready == executing->ready ) { + _Thread_Yield_processor(); + return; + } + + _ISR_Disable( level ); + + if ( !_Chain_Is_empty( ready ) ) { + if (!_Chain_Has_only_one_node( ready ) ) { + node = _Chain_Get_first_unprotected( ready ); + _Chain_Append_unprotected( ready, node ); + } + } + + _ISR_Flash( level ); + + if ( _Thread_Heir->ready == ready ) + _Thread_Heir = (Thread_Control *) ready->first; + + if ( executing != _Thread_Heir ) + _Context_Switch_necessary = TRUE; + + _ISR_Enable( level ); +} + + + + + + diff --git a/c/src/exec/score/src/threadsuspend.c b/c/src/exec/score/src/threadsuspend.c new file mode 100644 index 0000000000..82363054e5 --- /dev/null +++ b/c/src/exec/score/src/threadsuspend.c @@ -0,0 +1,83 @@ +/* + * Thread Handler + * + * + * COPYRIGHT (c) 1989-1998. + * On-Line Applications Research Corporation (OAR). + * Copyright assigned to U.S. Government, 1994. + * + * The license and distribution terms for this file may be + * found in found in the file LICENSE in this distribution or at + * http://www.OARcorp.com/rtems/license.html. + * + * $Id$ + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/*PAGE + * + * _Thread_Suspend + * + * This kernel routine sets the SUSPEND state in the THREAD. The + * THREAD chain and suspend count are adjusted if necessary. + * + * Input parameters: + * the_thread - pointer to thread control block + * + * Output parameters: NONE + * + * INTERRUPT LATENCY: + * ready chain + * select map + */ + +void _Thread_Suspend( + Thread_Control *the_thread +) +{ + ISR_Level level; + Chain_Control *ready; + + ready = the_thread->ready; + _ISR_Disable( level ); + the_thread->suspend_count++; + if ( !_States_Is_ready( the_thread->current_state ) ) { + the_thread->current_state = + _States_Set( STATES_SUSPENDED, the_thread->current_state ); + _ISR_Enable( level ); + return; + } + + the_thread->current_state = STATES_SUSPENDED; + + if ( _Chain_Has_only_one_node( ready ) ) { + + _Chain_Initialize_empty( ready ); + _Priority_Remove_from_bit_map( &the_thread->Priority_map ); + + } else + _Chain_Extract_unprotected( &the_thread->Object.Node ); + + _ISR_Flash( level ); + + if ( _Thread_Is_heir( the_thread ) ) + _Thread_Calculate_heir(); + + if ( _Thread_Is_executing( the_thread ) ) + _Context_Switch_necessary = TRUE; + + _ISR_Enable( level ); +} diff --git a/c/src/tests/itrontests/itrontask03/Makefile.in b/c/src/tests/itrontests/itrontask03/Makefile.in index 0435f04407..71c674f002 100644 --- a/c/src/tests/itrontests/itrontask03/Makefile.in +++ b/c/src/tests/itrontests/itrontask03/Makefile.in @@ -19,7 +19,7 @@ PGM = ${ARCH}/$(TEST).exe MANAGERS = all # C source names, if any, go here -- minus the .c -C_PIECES = init preempt spinit task1 task2 task3 +C_PIECES = init preempt task1 task2 task3 C_FILES = $(C_PIECES:%=%.c) C_O_FILES = $(C_PIECES:%=${ARCH}/%.o) diff --git a/c/src/tests/itrontests/itrontask03/spinit.c b/c/src/tests/itrontests/itrontask03/spinit.c deleted file mode 100644 index dda2f9661c..0000000000 --- a/c/src/tests/itrontests/itrontask03/spinit.c +++ /dev/null @@ -1,152 +0,0 @@ -/* Init - * - * This routine is the initialization task for this test program. - * It is a user initialization task and has the responsibility for creating - * and starting the tasks that make up the test. If the time of day - * clock is required for the test, it should also be set to a known - * value by this function. - * - * Input parameters: - * argument - task argument - * - * Output parameters: NONE - * - * COPYRIGHT (c) 1989-1998. - * On-Line Applications Research Corporation (OAR). - * Copyright assigned to U.S. Government, 1994. - * - * The license and distribution terms for this file may be - * found in the file LICENSE in this distribution or at - * http://www.OARcorp.com/rtems/license.html. - * - * $Id$ - */ - -#define TEST_INIT -#include "system.h" - -rtems_task Init( - rtems_task_argument argument -) -{ - rtems_status_code status; - - puts( "\n\n*** TEST 2 ***" ); - - Preempt_task_name = rtems_build_name( 'P', 'R', 'M', 'T' ); - - status = rtems_task_create( - Preempt_task_name, - 1, - RTEMS_MINIMUM_STACK_SIZE, - RTEMS_DEFAULT_MODES, - RTEMS_DEFAULT_ATTRIBUTES, - &Preempt_task_id - ); - directive_failed( status, "rtems_task_create of RTEMS_PREEMPT" ); - - status = rtems_task_start( Preempt_task_id, Preempt_task, 0 ); - directive_failed( status, "rtems_task_start of RTEMS_PREEMPT" ); - - puts( "INIT - rtems_task_wake_after - yielding processor" ); - status = rtems_task_wake_after( RTEMS_YIELD_PROCESSOR ); - directive_failed( status, "rtems_task_wake_after" ); - - Task_name[ 1 ] = rtems_build_name( 'T', 'A', '1', ' ' ); - Task_name[ 2 ] = rtems_build_name( 'T', 'A', '2', ' ' ); - Task_name[ 3 ] = rtems_build_name( 'T', 'A', '3', ' ' ); - - status = rtems_task_create( - Task_name[ 1 ], - 3, - RTEMS_MINIMUM_STACK_SIZE, - RTEMS_DEFAULT_MODES, - RTEMS_DEFAULT_ATTRIBUTES, - &Task_id[ 1 ] - ); - directive_failed( status, "rtems_task_create of TA1" ); - - status = rtems_task_create( - Task_name[ 2 ], - 3, - RTEMS_MINIMUM_STACK_SIZE, - RTEMS_DEFAULT_MODES, - RTEMS_DEFAULT_ATTRIBUTES, - &Task_id[ 2 ] - ); - directive_failed( status, "rtems_task_create of TA2" ); - - status = rtems_task_create( - Task_name[ 3 ], - 3, - RTEMS_MINIMUM_STACK_SIZE, - RTEMS_DEFAULT_MODES, - RTEMS_DEFAULT_ATTRIBUTES, - &Task_id[ 3 ] - ); - directive_failed( status, "rtems_task_create of TA3" ); - - status = rtems_task_start( Task_id[ 1 ], Task_1, 0 ); - directive_failed( status, "rtems_task_start of TA1" ); - - status = rtems_task_start( Task_id[ 2 ], Task_2, 0 ); - directive_failed( status, "rtems_task_start of TA2" ); - - status = rtems_task_start( Task_id[ 3 ], Task_3, 0 ); - directive_failed( status, "rtems_task_start of TA3" ); - - puts( "INIT - suspending TA2 while middle task on a ready chain" ); - status = rtems_task_suspend( Task_id[ 2 ] ); - directive_failed( status, "rtems_task_suspend of TA2" ); - - status = rtems_task_delete( Task_id[ 1 ] ); - directive_failed( status, "rtems_task_delete of TA1" ); - - status = rtems_task_delete( Task_id[ 2 ] ); - directive_failed( status, "rtems_task_delete of TA2" ); - - status = rtems_task_delete( Task_id[ 3 ] ); - directive_failed( status, "rtems_task_delete of TA3" ); - - status = rtems_task_create( - Task_name[ 1 ], - 1, - RTEMS_MINIMUM_STACK_SIZE, - RTEMS_DEFAULT_MODES, - RTEMS_DEFAULT_ATTRIBUTES, - &Task_id[ 1 ] - ); - directive_failed( status, "rtems_task_create of TA1" ); - - status = rtems_task_create( - Task_name[ 2 ], - 3, - RTEMS_MINIMUM_STACK_SIZE, - RTEMS_DEFAULT_MODES, - RTEMS_DEFAULT_ATTRIBUTES, - &Task_id[ 2 ] - ); - directive_failed( status, "rtems_task_create of TA2" ); - - status = rtems_task_create( - Task_name[ 3 ], - 3, - RTEMS_MINIMUM_STACK_SIZE, - RTEMS_DEFAULT_MODES, - RTEMS_DEFAULT_ATTRIBUTES, - &Task_id[ 3 ] - ); - directive_failed( status, "rtems_task_create of TA3" ); - - status = rtems_task_start( Task_id[ 1 ], Task_1, 0 ); - directive_failed( status, "rtems_task_start of TA1" ); - - status = rtems_task_start( Task_id[ 2 ], Task_2, 0 ); - directive_failed( status, "rtems_task_start of TA2" ); - - status = rtems_task_start( Task_id[ 3 ], Task_3, 0 ); - directive_failed( status, "rtems_task_start of TA3" ); - - status = rtems_task_delete( RTEMS_SELF ); - directive_failed( status, "rtems_task_delete of RTEMS_SELF" ); -} -- cgit v1.2.3