嵌入式中变量被意外修改的调试方法
发布日期:2021-05-10 10:31:55 浏览次数:13 分类:精选文章

本文共 716 字,大约阅读时间需要 2 分钟。

题目在移植实时操作系统到国产RISC-V架构芯片时遇到了一个奇怪的现象。测试发现、中断ISR(中断服务函数)中增加了一个静态变量i一,但之后再次进入同一ISR时,该变量值变为了0。调试发现汇编代码没有问题,但多次执行后效果一致。问题可以复现。这里将详细分析和解决这个问题。

调试过程中,发现本想通过“观察”该变量地址在发生非法修改时定位问题,但在此款芯片上这种方法效果不好,执行 programs 变得很慢,无法及时定位问题。于是想到了另一种巧妙的方法,将该变量设置为常量,存储在代码段(Flash)中。由于访问Flash的一般代码段需要特定的访问权限(如Read/Write),而普通访存操作可能会出现异常。

实际测试中,当该加一操作执行时,程序试图修改代码段中的常量,导致触发内存异常。记录异常发生的位置即可定位到问题所在。然而,调试发现异常位置指向用户程序区域之外,这可能意味着系统栈被破坏。

进一步分析:该ISR切换了系统栈的栈指针,将当前的现场(如寄存器和程序计数器)保存到系统栈环境中。当该处理完成,恢复现场时,系统栈中的环境指针指向了错误的程序区。这可能是因为中断处理和任务调度共享同一个系统栈,由中断切换栈指针是正确的,但在特定情况下可能导致栈帧不正确。

解决这个问题需要确保在非任务环境下测试完整,并确认实时操作系统中的任务调度是否稳定。系统栈切换满足要求,只要暂时环境下的己处理正确就不会出错。

最终发现问题是由于在中断处理中切到已经存在的系统栈,导致用户程序的栈帧被破坏。解决办法是在任务环境启动前确认切换栈指针的正确性,使其不会导致已保存的系统栈问题。通过验证中断处理和任务调度的兼容性,即可发现并解决问题。

上一篇:移植实时操作系统到 risc-v 架构芯片时上下文切换的实现
下一篇:awtk 中统一接口的实例

发表评论

最新留言

感谢大佬
[***.8.128.20]2025年04月16日 08时39分25秒