STM32(HAL库)中设置中断优先级函数__NVIC_SetPriority(IRQn_Type IRQn, uint32_t priority)详解

__STATIC_INLINE void __NVIC_SetPriority(IRQn_Type IRQn, uint32_t priority)
{
  //当外设号大于0时设置外设中断优先级
  //原理为priority << (8U - __NVIC_PRIO_BITS左移, __NVIC_PRIO_BITS在F103系列中为4,因为在优先 
   级寄存器中(Interrupt priority registers (NVIC_IPRx))只有高四位有用,故需要将设定优先级 
   priority的值左移四位;
  if ((int32_t)(IRQn) >= 0)
  {
    NVIC->IP[((uint32_t)IRQn)]               = (uint8_t)((priority << (8U - __NVIC_PRIO_BITS)) & (uint32_t)0xFFUL);
  }
   
  //当IRQn号小于0时执行下方指令
  else
  {
    SCB->SHP[(((uint32_t)IRQn) & 0xFUL)-4UL] = (uint8_t)((priority << (8U - __NVIC_PRIO_BITS)) & (uint32_t)0xFFUL);
  }
}

本文主要说明IRQn小于0时,代码运行原理:


  MemoryManagement_IRQn       = -12,    /*!< 4 Cortex-M3 Memory Management Interrupt              */
  BusFault_IRQn               = -11,    /*!< 5 Cortex-M3 Bus Fault Interrupt                      */
  UsageFault_IRQn             = -10,    /*!< 6 Cortex-M3 Usage Fault Interrupt                    */
  SVCall_IRQn                 = -5,     /*!< 11 Cortex-M3 SV Call Interrupt                       */
  PendSV_IRQn                 = -2,     /*!< 14 Cortex-M3 Pend SV Interrupt                       */
  SysTick_IRQn                = -1,     /*!< 15 Cortex-M3 System Tick Interrupt                   */

上述代码为系统硬件的IRQn,可以发现均小于0,

在第一部分代码中有一个强制转换(uint32_t)IRQn,因为中断号为负数,在计算机中负数用补码存储,以-5为例,8位二进制表示为1000 0101  ,反码为1111 1010 ,补码为1111  1011,将其转为无符号32位其为11111111        11111111       11111111        11111011;

(((uint32_t)IRQn) & 0xFUL)-4UL 表示将IRQn的末四位取出并且减去4,当IRQn=-5时,该代码运行结果为1011即为11减去4,最终结果为7;该处8代表了 SCB->SHP[8]中此处的数组中的元素,表明SHP中的第9个元素为SVCall的优先级。

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值