📄 nucleus_task_dispatch.c
字号:
/********************************************************************************
* When nucleus task dispatching, how it get a highest priority
*
* File : Nucleus_priority_diapatch.c
* BY :
* Version :
* Date :
********************************************************************************/
#include <stdio.h>
typedef unsigned char DATA_ELEMENT;
typedef unsigned long UNSIGNED;
typedef unsigned char UNSIGNED_CHAR;
typedef int INT;
#define TC_PRIORITIES 256
#define TC_MAX_GROUPS (TC_PRIORITIES/8)
#define TC_HIGHEST_MASK 0x000000FFUL
#define TC_NEXT_HIGHEST_MASK 0x0000FF00UL
#define TC_NEXT_LOWEST_MASK 0x00FF0000UL
#define TC_LOWEST_MASK 0xFF000000UL
typedef struct nu_tcb
{
UNSIGNED tc_priority_group; /* Priority group mask bit*/
DATA_ELEMENT tc_priority; /* Task priority */
DATA_ELEMENT *tc_sub_priority_ptr; /* Pointer to sub-group */
DATA_ELEMENT tc_sub_priority; /* Mask of sub-group bit */
DATA_ELEMENT reserved;
}NU_TCB, *P_NU_TCB;
/********************************************************************************
* TCD_Priority_Groups is a 32-bit unsigned integer that is used as a bit map.
* Each bit corresponds to an 8-priority group. For example, if bit 0 is set,
* at least one task of priority 0 through 8 is ready for execution.
********************************************************************************/
UNSIGNED TCD_Priority_Groups;
/********************************************************************************
* TCD_Sub_Priority_Groups is an array of sub-priority groups. These are
* also used as bit maps. Index 0 of this array corresponds to priorities
* 0 through 8. Bit 0 of this element represents priority 0, while bit 7
* represents priority 7.
********************************************************************************/
DATA_ELEMENT TCD_Sub_Priority_Groups[TC_MAX_GROUPS];
/********************************************************************************
* TCD_Highest_Priority contains the highest priority task ready for execution.
* Note that this does not necessarily represent the priority of the currently
* executing task. This is true if the currently executing task has preemption
* disabled. If no tasks are executing, this variable is set to the maximum
* priority.
********************************************************************************/
INT TCD_Highest_Priority = TC_PRIORITIES;
/********************************************************************************
* TCD_Lowest_Set_Bit is nothing more than a standard lookup table. The
* table is indexed by values ranging from 1 to 255. The value at that
* position in the table indicates the number of the lowest set bit. This is
* used to determine the highest priority task represented in the previously
* defined bit maps.
********************************************************************************/
UNSIGNED_CHAR TCD_Lowest_Set_Bit[] =
{/* 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16*/
0, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //1
4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //2
5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //3
4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //4
6, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //5
4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //6
5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //7
4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //8
7, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //9
4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //10
5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //11
4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //12
6, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //13
4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //14
5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //15
4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0, //16
};
static void nu_printf_highest_priority()
{
printf("Now, The highest priority is : %d\n", TCD_Highest_Priority);
}
static void nu_create_task(NU_TCB *task_tcb, DATA_ELEMENT task_prio)
{
task_tcb->tc_priority = task_prio;
task_tcb->tc_sub_priority = (DATA_ELEMENT)(1<<(task_prio&7));
task_prio >>= 3;
task_tcb->tc_priority_group = ((UNSIGNED)1)<<task_prio;
task_tcb->tc_sub_priority_ptr = &(TCD_Sub_Priority_Groups[task_prio]);
}
static void nu_start_task(NU_TCB *task_tcb)
{
TCD_Priority_Groups |= task_tcb->tc_priority_group;
*(task_tcb->tc_sub_priority_ptr) |= task_tcb->tc_sub_priority;
if((INT)(task_tcb->tc_priority) < TCD_Highest_Priority)
TCD_Highest_Priority = (INT)task_tcb->tc_priority;
}
static void nu_find_highest_prio()
{
UNSIGNED_CHAR index, temp;
if(TCD_Priority_Groups & TC_HIGHEST_MASK)/* Base of sub-group is 0. */
index = 0;
else if (TCD_Priority_Groups & TC_NEXT_HIGHEST_MASK)/* Base of sub-group is 8. */
index = 8;
else if (TCD_Priority_Groups & TC_NEXT_LOWEST_MASK) /* Base of sub-group is 16. */
index = 16;
else/* Base of sub-group is 24. */
index = 24;
index += TCD_Lowest_Set_Bit[(INT)((TCD_Priority_Groups >> index) & TC_HIGHEST_MASK)];
temp = TCD_Sub_Priority_Groups[index];
TCD_Highest_Priority = (index << 3) + TCD_Lowest_Set_Bit[temp];
}
static void get_a_priority(INT *prio)
{
reinput:
printf("Please input a priority : ");
scanf("%d", prio);
if(*prio > 255 || *prio < 0)
{
printf("Unlogical priority!\n");
goto reinput;
}
printf("\n");
printf("The 1st priority you input is : %d\n", *prio);
}
static void execute_priority_test_routine(INT priority)
{
NU_TCB tcb;
nu_create_task(&tcb, priority);
nu_start_task(&tcb);
nu_find_highest_prio();
nu_printf_highest_priority();
}
int main(int argc, char *argv[])
{
NU_TCB my_tcb;
INT i, my_prio;
for(i=0;i<5;i++)
{
get_a_priority(&my_prio);
execute_priority_test_routine((UNSIGNED_CHAR)my_prio);
}
system("pause");
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -