如何根据死机时的栈空间数据分析推导调用栈的情况
通过死机时刻的寄存器查看是最容易入手的;
R13是当前栈顶;R14是LinkLR;
于是就知道程序是在运行0x8055C6A的这条指令出现了问题;
这条指令是将R3的值给到PC就出错了。从前面可以看到R3是0xAA8AAAB,将这个值给到PC,考虑到是thumb指令,于是给的就是0xAA8AAAA,这确实和当前死掉的时候PC的值一样;
结果查看0xAA8AAAAA处都不是指令,都是全零的东西,怪不得会造成系统死机;
从如下可知R3值从R6得到的。
从如下查到R6的来源,那么就是g_mp3_context的位置被踩坏了;
通过linkLR知道当前执行的接口是lightduer_mp3_codec_callback;
该接口的开始会进行压栈的操作,即将R0~R6、R14压进去,由此可以知道上一步的LinkLR是指向哪里的;
根据SP的位置mp3_codec_decoder_hisr_handler的调用者是mp3_codec_request_data_to_share_buffer;
接下来mp3_codec_request_data_to_share_buffer接口也有压栈操作;
根据SP的位置mp3_codec_request_data_to_share_buffer的调用者是mp3_codec_decoder_hisr_handler;
同样的方法,检查mp3_codec_decoder_hisr_handler的压栈操作;
很明显现在LR不对了;
这是因为在mp3_codec_decoder_hisr_handler里面还有对SP的减数操作,减去了0x14;
根据SP的位置mp3_codec_decoder_hisr_handler的调用者是mp3_codec_task_main;
接下来mp3_codec_task_main接口也有压栈操作;
根据SP的位置mp3_codec_task_main的LinkLR是prvTaskExitError;
prvTaskExitError正常是不会运行到的;
于是就推算完成整个调用栈:
mp3_codec_task_main
---》mp3_codec_decoder_hisr_handler
---》mp3_codec_request_data_to_share_buffer
---》lightduer_mp3_codec_callback
----》因为pc指向不对引发死机;