1 / 3

Nucleus 最多有 256 个优先级: 0~255, 0 表示最高优先级, 255 表示最低优先级, 我们用 P0~P255 来表示。

Nucleus 任务调度算法原理. Nucleus 最多有 256 个优先级: 0~255, 0 表示最高优先级, 255 表示最低优先级, 我们用 P0~P255 来表示。 我们在创建并运行一个任务时必须将该任务的优先级保存起来,以便我们在任务调度时可以知道当前就绪的任务的优先级, 从而找到一个最高优先级的任务, 那么我们如何来找到最高的优先级呢? Solution 1 : 我们可以用一个 256 个 BOOL 类型元素的数组来保存优先级 : unsigned long TCD_Priority [8] ;

hertz
Télécharger la présentation

Nucleus 最多有 256 个优先级: 0~255, 0 表示最高优先级, 255 表示最低优先级, 我们用 P0~P255 来表示。

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Nucleus任务调度算法原理 Nucleus最多有256个优先级:0~255, 0表示最高优先级,255表示最低优先级, 我们用P0~P255来表示。 我们在创建并运行一个任务时必须将该任务的优先级保存起来,以便我们在任务调度时可以知道当前就绪的任务的优先级, 从而找到一个最高优先级的任务, 那么我们如何来找到最高的优先级呢? Solution 1: 我们可以用一个256个BOOL类型元素的数组来保存优先级 :unsigned long TCD_Priority [8]; 该数组有32X8位,每一位对应一个有限级,当为1时,表示该优先级有任务就绪,为0时表示该优先级无任务就绪。 然后我们再来遍历每一位,看具体是哪个优先级。该方法的缺点是速度慢,因为我们要遍历8个32位数的每一位。 Solution 2: 将这256个优先级分组,Nucleus将其分成了32组(用一个32位数即可表示每组的状态),每组为8个, unsigned long TCD_Priority_Groups; P8~P15 bit31 bit30 bit1 bit0 P248 ~ P255 只要P0~P7的任务有一个就绪,那么该位将置1 P0~P7 那么我们如何快速确定究竟是哪一位为1呢?我们的原则是找到最高优先级,OK, 那么我们就应该从最低位开始找, 用遍历每一位的方式可以找到,但效率低!在Nucleus 中使用了一个256个元素的数组,我们通过这个数组可以快速找到最高优先级。 它的原理是什么呢? 我们先来看这样一个例子: unsigned char Prio; 加入用它的8位来表示8个优先级 P0 ~ P7 Prio = 0000 0101B , 那它表示P0 和 P3优先级有任务就绪。最高优先级当然是P0了 。 Prio = 5, Phigh = P0; Prio = 1000 0101B,那它表示P0 和 P7优先级有任务就绪。最高优先级当然还是P0了 。Prio = 0x85, Phigh = P0; Prio = 0000 0110B , 那它表示P1 和 P3优先级有任务就绪。最高优先级当然是P1了 。Prio = 6, Phigh = P1; Prio = 1000 0110B,那它表示P1 和 P7优先级有任务就绪。最高优先级当然还是P1了 。Prio = 0x86, Phigh = P1; 到这里我想大家应该发现这样一个规律:我们只需要找到最低位的1就可以确定我们想要的最高优先级了。于是我们就可以将这个8 位的数据的256(0~255)种可能做一个256个元素的表格,即当prio = 0, 1 ,2, 3, 4 ……………255时,最高优先级的值。 该表格的生成见:Nucleus_lookup_table.c

  2. bit7 bit6 bit5 bit4 bit3 bit2 bit1 bit0 • 这个表格只能查找一个8为数啊!我们上面使用了一个32位数啊,怎么查?有办法, 我们先判断一下这个32位数的哪8位不为零不就可以了。 • if(TCD_Priority_Groups > 0) • { • if(TCD_Priority_Groups & 0x00 00 00 FF) • index = 0; • else if (TCD_Priority_Groups & 0x00 00 FF 00) • index = 8; • else if (TCD_Priority_Groups & 0x00 FF 00 00) • index = 16; • else • index = 24; • } • 查 TCD_Lowest_Set_Bit[ (TCD_Priority_Groups >> index) & 0x 00 00 00 FF]; 就是我们要的值。 • 此时我们只是确定了哪8个优先级有任务就绪,具体是哪个优先级呢? • 一个优先级可以这样表示:组索引+偏移量。 • 例:85这个优先级可以表示为第10组(每组有8个)的第5个优先级, 如下图所示。 bit31 bit30 bit9 bit1 bit0 1 x x x 1 x x x x 于是我们在创建任务时,可以用如上的方式来保存我们创建的任务的优先级。我们有把任务分成32组,因此我们需要一个32个 元素的数据:unsgined char TCD_Sub_Priority_Groups[32];

  3. 我们在创建任务时: 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]); 执行任务时: 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; 任务调度时: if(TCD_Priority_Groups & TC_HIGHEST_MASK) index = 0; else if (TCD_Priority_Groups & TC_NEXT_HIGHEST_MASK) index = 8; else if (TCD_Priority_Groups & TC_NEXT_LOWEST_MASK) index = 16; else 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]; 具体代码请见文件Nucleus_task_dispatch.c

More Related