STM32F(ARM内核)中断返回地址查询及问题咨询
STM32F(ARMv6-M架构)中断返回地址问题解析
先明确:中断时LR的0xFFFFFFF9不是返回地址
普通函数调用时,返回地址确实存在Link Register(LR/R14),但中断触发后LR被设置为异常返回标记值,0xFFFFFFF9就是其中一种——它用来告诉CPU返回时的模式:回到线程模式,使用主栈指针(MSP)作为当前栈指针。这类特殊值不是实际的内存地址,执行BX LR时CPU会自动识别并触发栈帧恢复流程。
中断返回地址的实际存储位置
ARMv6-M架构(STM32F0/F1等系列基于此)触发中断时,会自动将8个寄存器压入栈中(满递减栈,SP自动减去32字节),压栈顺序为:
- R0 → R1 → R2 → R3 → R12 → 线程LR → PC(中断返回地址) → xPSR
也就是说,你要找的返回地址,是栈中偏移#24的位置(从SP当前值算起,每个寄存器占4字节:24 = 6×4,对应第7个压入的PC)。
你检查[SP,#24]不对的可能原因
- 栈指针选错了:中断默认使用主栈指针(MSP),如果你的线程代码用的是进程栈指针(PSP),要确认读取的是MSP而非PSP;
- 栈帧已被修改:中断服务函数开头如果手动压入了其他寄存器,会导致栈偏移变化;
- 对返回地址的理解偏差:中断返回地址是中断发生时CPU正要执行的下一条指令地址,不是当前函数的返回地址——两者不是同一个概念。
快速验证方法
在中断服务函数开头添加代码,直接读取MSP指向的栈帧中的PC值:
uint32_t *stack_frame = (uint32_t*)__get_MSP(); uint32_t interrupt_return_addr = stack_frame[6]; // stack_frame[0]是R0,索引6对应PC
内容的提问来源于stack exchange,提问作者MarooNarae
相关产品推荐
相关产品推荐

