优先级位图算法

教材:嵌入式系统及应用,罗蕾、李允、陈丽蓉等,电子工业出版社

优先级位图算法

主要的数据结构

都是从0开始算

优先级就绪表 OSRdyTbl

  • char OSRdyTbl[8];

  • 优先级位图算法_第1张图片

  • 每个数组元素对应64个优先级中的8个

  • 若对应优先级存在就绪任务,相应的二进制位置1

优先级就绪组 OSRdyGrp

  • char OSRdyGrp;

  • OSRdyGrp 的每个二进制位对应一个 OSRdyTbl 的数组元素,第 i 位对应 OSRdyTbl[i]

  • 若 OSRdyTbl[i] 对应的8个优先级中有就绪的任务,则 OSRdyGrp 的第 i 位置1,不然为0

  • 优先级位图算法_第2张图片

任务优先级与 OSRdyTbl、OSRdyGrp 的关系

  • 优先级数目为64时,对应6个二进制位

  • 优先级位图算法_第3张图片

  • 表示优先级的6个二进制位中

    • 高3位为优先级在 OSRdyGrp 中二进制位的位置,亦对应OSRdyTbl 的数组下标
    • 低3位对应 OSRdyTbl 的数组元素的值
  • 例如优先级36,二进制表示为为00100101

    • 高3位为100,则 OSRdyGrp 中位序为4的是1,对应 OSRdyTbl [4]
    • 低3位为101,对应 OSRdyTbl [4] 中的位序5,即优先级36
  • OSRdyGrp = 0x011; //0b00010001 
    OSRdyTbl[0] = 0x0a;   //0b00001010 
    OSRdyTbl[4] = 0x01;//0b00000001 

    存在的几个优先级为 0×8+1=1,0×8+3=3,4×8+0=32

优先级映射表 OSMapTbl

  • char OSMapTbl[8] = {0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80};

  • 优先级位图算法_第4张图片

  • 数组元素的下标与任务优先级的高3位对应时,数组元素对应的二进制值中,位为1的位表示 OSRdyGrp 的对应位也为1

  • 数组元素的下标与任务优先级的低3位对应时,数组元素对应的二进制值中,位为1的位表示 OSRdyTbl[] 的对应位也为1

优先级判定表 OSUnMapTbl

  • char OSUnMapTbl[256]

  • INT8U  const  OSUnMapTbl[256] = { 
      0, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x00 to 0x0F                             */
      4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x10 to 0x1F                             */
      5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x20 to 0x2F                             */
      4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x30 to 0x3F                             */
      6, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x40 to 0x4F                             */
      4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x50 to 0x5F                             */
      5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x60 to 0x6F                             */
      4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x70 to 0x7F                             */
      7, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x80 to 0x8F                             */
      4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0x90 to 0x9F                             */
      5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0xA0 to 0xAF                             */
      4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0xB0 to 0xBF                             */
      6, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0xC0 to 0xCF                             */
      4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0xD0 to 0xDF                             */
      5, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0,       /* 0xE0 to 0xEF                             */
      4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0        /* 0xF0 to 0xFF                             */
    };
  • 以 OSRdyGrp 或是 OSRdyTbl[] 数组元素的值为索引,获取该值对应二进制表示中1出现的最低二进制位的序号(0-7)

  • 数组中元素 OSUnMapTbl[n] 表示一个任意的8位无符号数n对应的最低位为1的那个位序

  • 例如二进制数 00000001B 最低位为1的是 bit0,OSUnMapTbl[1] = 0;1000000B最低位为1的是bit7,所以OSUnMapTbl[128] = 7

  • n为奇数时 OSUnMapTbl[n] = 0

相关操作

任务进入就绪态

  • OSRdyGrp |= OSMapTbl[priority >> 3];  //进行二进制或运算
    OSRdyTbl[priority >> 3] |= OSMapTbl[priority & 0x07]; //进行二进制或运算
  • priority >> 3获取优先级的高3位

  • 就绪任务的优先级为 priority,右移3位后找到在 OSMapTbl 中的对应值,再与 OSRdyGrp 做或运算,将对应位置1

  • priority & 0x07获取优先级的低3位

任务退出就绪态

  • if((OSRdyTbl[priority >> 3] &= ~OSMapTbl[priority & 0x07]) == 0)
    OSRdyGrp &= ~OSMapTbl[priority >> 3]; 
  • 把相应的二进制位清除

  • 优先级组中不存在就绪任务时清对应的 OSRdyGrp

获取进入就绪态的最高优先级

  • high3Bit = OSUnMapTbl[OSRdyGrp];
    low3Bit = OSUnMapTbl[OSRdyTbl[high3Bit]];
        priority = (high3Bit << 3) + low3Bit; 
  • 通过优先级判定表 OSUnMapTbl 操作

  • 数字越小,优先级越大

你可能感兴趣的:(嵌入式系统及应用,问题与算法)