代码之家  ›  专栏  ›  技术社区  ›  LOSnel

干扰irq将我从睡眠模式唤醒

  •  0
  • LOSnel  · 技术社区  · 7 年前

    我的系统在睡眠模式下有问题。

    目前,我的MCU正在驱动一个通过无线电定期发送消息的无线电芯片,当无线电芯片发送消息时,我将MCU设置为睡眠模式。

    但有时,当无线芯片发送数据时,我会收到一个中断,这会唤醒我的MCU并中止数据发送。 我不知道如何找到哪个irq正在唤醒我,因为我的系统当前运行着许多任务,这些任务可以“随机”运行irq,但当无线芯片发送消息时,没有一个“随机”irq应该触发。

    当我尝试在睡眠模式中使用的_uwfi()后中断时,调用堆栈已经用新数据刷新,我看不到最后执行的指令是什么。

    你知道一种方法来确定哪个irq唤醒了我一个睡眠系统吗?

    谢谢你的帮助。

    1 回复  |  直到 7 年前
        1
  •  1
  •   followed Monica to Codidact    7 年前

    检查 NVIC->ISPR[x] SCB->ICSR 唤醒后立即注册。如果在处理程序运行之前无法中断,请替换 __WFI() 使用此宏(如果不使用gcc,则使用等效的东西)

    uint32_t ispr0, ispr1, ispr2, icsr;
    #define __WFI() ({ \
        uint32_t primask = __get_PRIMASK(); \
        __disable_irq(); \
        asm volatile("wfi");    \
        ispr0 = NVIC->ISPR[0];  \
        ispr1 = NVIC->ISPR[1];  \
        ispr2 = NVIC->ISPR[2];  \
        icsr = SCB->ICSR;       \
        __set_PRIMASK(primask); \
    })
    

    之后能够轻松地检查内容。我从ST Cortex-M3编程手册中获取了寄存器名称,其他内核的过程应该类似。