Everything

CHAPTER 3 TASK MANAGEMENT FUNCTIONS


This chapter describes the task management functions performed by the RI78V4.
3.1 Outline
The task control functions provided by the RI78V4 include a function to reference task statuses, in addition to a function to manipulate task statuses.
3.2 Tasks
A task is processing program that is not executed unless it is explicitly manipulated via service calls provided by the RI78V4, unlike other processing programs (cyclic handler and interrupt handler), and is called from the scheduler.
Note The execution environment information required for a task's execution is called "task context". During task execution switching, the task context of the task currently under execution by the RI78V4 is saved and the task context of the next task to be executed is loaded.
3.2.1 Task state
Tasks enter various states according to the acquisition status for the OS resources required for task execution and the occurrence/non-occurrence of various events. In this process, the current state of each task must be checked and managed by the RI78V4.
The RI78V4 classifies task states into the following six types.
Figure 3-1 Task State
- DORMANT state
State of a task that is not active, or the state entered by a task whose processing has ended.
A task in the DORMANT state, while being under management of the RI78V4, is not subject to the RI78V4 scheduling.
- READY state
State of a task for which the preparations required for processing execution have been completed, but since another task with a higher priority level or a task with the same priority level is currently being processed, the task is waiting to be given the CPU's use right.
- RUNNING state
State of a task that has acquired the CPU use right and is currently being processed.
Only one task can be in the running state at one time in the entire system.
- WAITING state
State in which processing execution has been suspended because conditions required for execution are not satisfied.
Resumption of processing from the WAITING state starts from the point where the processing execution was suspended. The value of information required for resumption (such as task context) immediately before suspension is therefore restored.
In the RI78V4, the WAITING state is classified into the following six types according to their required conditions and managed.
Table 3-1 Waiting States
Waiting States
Description
Sleeping state
A task enters this state if the counter for the task (registering the number of times the wakeup request has been issued) indicates 0x0 upon the issuance of a slp_tsk or tslp_tsk.
Delayed state
A task enters this state upon the issuance of a dly_tsk.
Waiting state for a semaphore resource
A task enters this state if it cannot acquire a resource from the relevant semaphore upon the issuance of a wai_sem or twai_sem.
Waiting state for an eventflag
A task enters this state if a relevant eventflag does not satisfy a predetermined condition upon the issuance of a wai_flg or twai_flg.
Sending WAITING state for a data queue
A task enters this state if cannot send a data to the relevant data queue upon the issuance of a snd_dtq or .tsnd_dtq
Receiving WAITING state for a data queue
A task enters this state if cannot receive a data from the relevant data queue upon the issuance of a rcv_dtq or trcv_dtq.
Receiving waiting state for a mailbox
A task enters this state if cannot receive a message from the relevant mailbox upon the issuance of a rcv_mbx or trcv_mbx.
Waiting state for a fixed-sized memory block
A task enters this state if it cannot acquire a fxed-sized memory block from the relevant memory pool upon the issuance of a get_mpf or tget_mpf.

- SUSPENDED state
State in which processing execution has been suspended forcibly.
Resumption of processing from the SUSPENDED state starts from the point where the processing execution was suspended. The value of information required for resumption (such as task context) immediately before suspension is therefore restored.
- WAITING-SUSPENDED state
State in which the WAITING and SUSPENDED states are combined.
A task enters the SUSPENDED state when the WAITING state is cancelled, or enters the WAITING state when the SUSPENDED state is cancelled.
3.2.2 Task priority
A priority level that determines the order in which that task will be processed in relation to the other tasks is assigned to each task.
As a result, in the RI78V4, the task that has the highest priority level of all the tasks that have entered an executable state (RUNNING state or READY state) is selected and given the CPU use right.
In the RI78V4, the following two types of priorities are used for management purposes.
- Task initial priority
Priority set when a task is created.
- Task current priority
This is the general term used to describe the priority level of a task from the time it enters the READY state from the DORMANT state until it returns to the DORMANT state.
Therefore, the current priority level of a task that enters the READY state from the DORMANT state has the same value as the "initial priority level," and the current priority level when the priority level is changed by issuing chg_pri or ichg_pri is the same value as the "priority level after change".
Note 1 In the RI78V4, a task having a smaller priority number is given a higher priority.
Note 2 The priority that can be specified in a system is in the priority range specified in Task priority information.
3.2.3 Create task
In the RI78V4, the method of creating a task is limited to "static creation by the Kernel Initialization Module".
Tasks therefore cannot be created dynamically using a method such as issuing a service call from a processing program.
- Static create
Static task creation is realized by defining Task information in the system configuration file.
The RI78V4 executes task creation processing based on data stored in information files, using the Kernel Initialization Module, and handles the created tasks as management targets.
3.2.4 Delete task
In the RI78V4, tasks created statically by the Kernel Initialization Module cannot be deleted dynamically using a method such as issuing a service call from a processing program.
3.2.5 Basic form of tasks
When coding a task, use a void function with one VP_INT argument (any function name is fine) .
The extended information specified with Task information, or the start code specified when sta_tsk or ista_tsk is issued, is set for the exinf argument.
The following shows the basic form of tasks.
[ C Language ]
 #include    <kernel.h>          /*Standard header file definition*/
 #include    <kernel_id.h>       /*System information header file definition*/
 
 void
 func_task ( VP_INT exinf )
 {
     /* ............ */          /*Main processing*/
 
     ext_tsk ( );                /*Terminate invoking task*/
 }

Note The the #pragma rtos_task directive is defined in the file "kernel_id.h" (CF78V4 outputs automatically). Therefore please the file "kernel_id.h" be sure to do include.
Assembly Language ]
 $INCLUDE    (kernel.inc)        ;Standard header file definition
 $INCLUDE    (kernel_id.inc)     ;System information header file definition
 
     .PUBLIC  _func_task
     .SECTION .text, TEXT
 _func_task:
     PUSH    BC          ;Stores the higher 2 bytes of argument exinf into stack
     PUSH    AX          ;Stores the lower 2 bytes of argument exinf into stack
 
     ; ............              ;Main processing
 
     BR      !!_ext_tsk          ;Terminate invoking task

3.2.6 Internal processing of task
In the RI78V4, original dispatch processing (task scheduling) is executed during task switching.
Therefore, note the following points when coding tasks.
- Coding method
Code tasks using C or assembly language in the format shown in "3.2.5 Basic form of tasks".
- Stack switching
In the RI78V4, switching to the stack for the switching destination task (task stack) is executed during task switching.
The user is therefore not required to code processing related to stack switching in tasks.
- Interrupt status
In the RI78V4, the initial interrupt state specified in Task information when a task is switched from the READY state to the RUNNING state.
To change (disable or enable) the interrupt status in the task, calling of the __DI or __EI function are therefore required.
- Service call issuance
Service calls that can be issued in tasks are limited to the service calls that can be issued from tasks.
Note For details on the valid issuance range of each service call, refer to Table 12-8 to Table 12-17.
3.3 Activate Task
The RI78V4 provides two types of interfaces for task activation: queuing an activation request queuing and not queuing an activation request.
3.3.1 Queuing an activation request
A task (queuing an activation request) is activated by issuing the following service call from the processing program.
- act_tsk, iact_tsk
These service calls move a task specified by parameter tskid from the DORMANT state to the READY state.
As a result, the target task is queued at the end on the ready queue corresponding to the initial priority and becomes subject to scheduling by the RI78V4.
If the target task has been moved to a state other than the DORMANT state when this service call is issued, this service call does not move the state but increments the activation request counter (by added 0x1 to the wakeup request counter).
The following describes an example for coding this service call.
 #include    <kernel.h>          /*Standard header file definition*/
 #include    <kernel_id.h>       /*System information header file definition*/
 
 void
 func_task ( VP_INT exinf )
 {
     ID      tskid = ID_tskA;    /*Declares and initializes variable*/
 
     /* ............ */
 
     act_tsk ( tskid );          /*Activate task (queues an activation request)*/
 
     /* ............ */
 }

Note 1 The activation request counter managed by the RI78V4 is configured in 7-bit widths. If the number of activation requests exceeds the maximum count value 127 as a result of issuing this service call, the counter manipulation processing is therefore not performed but "E_QOVR" is returned.
Note 2 An extended information "Extended information: exinf" is passed to the task activated by issuing this service call.
3.3.2 Not queuing an activation request
A task (not queuing an activation request) is activated by issuing the following service call from the processing program.
- sta_tsk, ista_tsk
These service calls move a task specified by parameter tskid from the DORMANT state to the READY state.
As a result, the target task is queued at the end on the ready queue corresponding to the initial priority and becomes subject to scheduling by the RI78V4.
The following describes an example for coding this service call.
 #include    <kernel.h>          /*Standard header file definition*/
 #include    <kernel_id.h>       /*System information header file definition*/
 
 void
 func_task ( VP_INT exinf )
 {
     ID      tskid = ID_tskA;    /*Declares and initializes variable*/
     VP_INT  stacd = 1048575;    /*Declares and initializes variable*/
 
     /* ............ */
 
     sta_tsk ( tskid, stacd );   /*Activate task (does not queue an activation
                                   request)*/
 
     /* ............ */
 }

Note 1 This service call does not perform queuing of activation requests. If the target task is in a state other than the DORMANT state, the counter manipulation processing is therefore not performed but "E_OBJ" is returned.
Note 2 An start code "stacd" is passed to the task activated by issuing this service call.
3.4 Cancel Task Activation Requests
An activation request is cancelled by issuing the following service call from the processing program.
- can_act
This service call cancels all of the activation requests queued to the task specified by parameter tskid (sets the activation request counter to 0x0).
When this service call is terminated normally, the number of cancelled activation requests is returned.
The following describes an example for coding this service call.
 #include    <kernel.h>          /*Standard header file definition*/
 #include    <kernel_id.h>       /*System information header file definition*/
 
 void
 func_task ( VP_INT exinf )
 {
     ER_UINT ercd;               /*Declares variable*/
     ID      tskid = ID_tskA;    /*Declares and initializes variable*/
 
     /* ............ */
 
     ercd = can_act ( tskid );   /*Cancel task activation requests*/
 
     if ( ercd >= 0x0 ) {
         /* ............ */      /*Normal termination processing*/
     }
 
     /* ............ */
 }

3.5 Terminate Task
The RI78V4 provides two types of interfaces for task termination: termination of invoking task and forced termination of other tasks.
3.5.1 Terminate invoking task
An invoking task is terminated by issuing the following service call from the processing program.
- ext_tsk
This service call moves an invoking task from the RUNNING state to the DORMANT state.
As a result, the invoking task is unlinked from the ready queue and excluded from the RI78V4 scheduling subject.
If an activation request has been queued to the invoking task (the activation request counter is not set to 0x0) when this service call is issued, this service call moves the task from the RUNNING state to the DORMANT state, decrements the wakeup request counter (by subtracting 0x1 from the wakeup request counter), and then moves the task from the DORMANT state to the READY state.
The following describes an example for coding this service call.
 #include    <kernel.h>          /*Standard header file definition*/
 #include    <kernel_id.h>       /*System information header file definition*/
 
 void
 func_task ( VP_INT exinf )
 {
     /* ............ */
 
     ext_tsk ( );                /*Terminate invoking task*/
 }

Note 1 This service call does not return the OS resource that the invoking task acquired by issuing a service call such as sig_sem or get_mpf. The OS resource have been acquired must therefore be returned before issuing this service call.
Note 2 When moving a task from the RUNNING state to the DORMANT state, this service call initializes the following information to values that are set during task creation.
- Priority (current priority)
- Wakeup request count
- Suspension count
- Interrupt status
Note 3 If the return instruction is written in a task, it executes the same operation as this service call.
Note 4 In the RI78V4, code efficiency is enhanced by coding the return instruction as a "Terminate invoking task".
3.5.2 Terminate task
Other tasks are forcibly terminated by issuing the following service call from the processing program.
- ter_tsk
This service call forcibly moves a task specified by parameter tskid to the DORMANT state.
As a result, the target task is excluded from the RI78V4 scheduling subject.
If an activation request has been queued to the target task (the activation request counter is not set to 0x0) when this service call is issued, this service call moves the task to the DORMANT state, decrements the wakeup request counter (by subtracting 0x1 from the wakeup request counter), and then moves the task from the DORMANT state to the READY state.
The following describes an example for coding this service call.
 #include    <kernel.h>          /*Standard header file definition*/
 #include    <kernel_id.h>       /*System information header file definition*/
 
 void
 func_task ( VP_INT exinf )
 {
     ID      tskid = ID_tskA;    /*Declares and initializes variable*/
 
     /* ............ */
 
     ter_tsk ( tskid );          /*Terminate task*/
 
     /* ............ */
 }

Note 1 This service call does not return the OS resource that the target task acquired by issuing a service call such as sig_sem or get_mpf. The OS resource have been acquired must therefore be returned before issuing this service call.
Note 2 When moving a task to the DORMANT state, this service call initializes the following information to values that are set during task creation.
- Priority (current priority)
- Wakeup request count
- Suspension count
- Interrupt status
3.6 Change Task Priority
The priority is changed by issuing the following service call from the processing program.
- chg_pri, ichg_pri
These service calls change the priority of the task specified by parameter tskid (current priority) to a value specified by parameter tskpri.
The following describes an example for coding this service call.
 #include    <kernel.h>          /*Standard header file definition*/
 #include    <kernel_id.h>       /*System information header file definition*/
 
 void
 func_task ( VP_INT exinf )
 {
     ID      tskid = ID_tskA;    /*Declares and initializes variable*/
     PRI     tskpri = 15;        /*Declares and initializes variable*/
 
     /* ............ */
 
     chg_pri ( tskid, tskpri );  /*Change task priority*/
 
     /* ............ */
 }

Note If the target task is in the RUNNING or READY state after this service call is issued, this service call re-queues the task at the end of the ready queue corresponding to the priority specified by parameter tskpri, following priority change processing.
3.7 Reference Task State
A task status is referenced by issuing the following service call from the processing program.
- ref_tsk
Stores task state packet (such as current status) of the task specified by parameter tskid in the area specified by parameter pk_rtsk.
The following describes an example for coding this service call.
 #include    <kernel.h>          /*Standard header file definition*/
 #include    <kernel_id.h>       /*System information header file definition*/
 
 void
 func_task ( VP_INT exinf )
 {
     ID      tskid = ID_tskA;    /*Declares and initializes variable*/
     T_RTSK  pk_rtsk;            /*Declares data structure*/
     STAT    tskstat;            /*Declares variable*/
     PRI     tskpri;             /*Declares variable*/
     STAT    tskwait;            /*Declares variable*/
     ID      wobjid;             /*Declares variable*/
     UINT    actcnt;             /*Declares variable*/
     UINT    wupcnt;             /*Declares variable*/
     UINT    suscnt;             /*Declares variable*/
 
     /* ............ */
 
     ref_tsk ( tskid, &pk_rtsk );/*Reference task state*/
 
     tskstat = pk_rtsk.tskstat;  /*Reference task current state*/
     tskpri = pk_rtsk.tskpri;    /*Reference task current priority*/
     tskwait = pk_rtsk.tskwait;  /*Reference reason for waiting*/
     wobjid = pk_rtsk.wobjid;    /*Reference object ID number for which the task is
                                   waiting*/
     actcnt = pk_rtsk.actcnt;    /*Reference activation request count*/
     wupcnt = pk_rtsk.wupcnt;    /*Reference wakeup request count*/
     suscnt = pk_rtsk.suscnt;    /*Reference suspension count*/
 
     /* ............ */
 }

Note For details about the task state packet, refer to "12.5.1 Task state packet".