![wKgaomXb5PyAJi8cAAr3J2Otupw085.png](https://file1.elecfans.com/web2/M00/C1/DD/wKgaomXb5PyAJi8cAAr3J2Otupw085.png)
![wKgZomXb5QKAECMPAAkQGcyy6b4811.png](https://file1.elecfans.com/web2/M00/C0/EF/wKgZomXb5QKAECMPAAkQGcyy6b4811.png)
在郭天祥老师视频里有一个问题分享,是EXMC初始化里的一个变量定义和初始化位置不同会导致程序死机,最终定位到程序是进入hardfault死机,但暂时没有后续分析了,这里我们来继续分析一下。
死机的程序是这样的:
![wKgZomXb5QiAO5QpAABAwKR0WCs524.png](https://file1.elecfans.com/web2/M00/C0/EF/wKgZomXb5QiAO5QpAABAwKR0WCs524.png)
这段代码是定义和初始化exmc的结构体参数,我们来详细看下结构体中的定义,其中有一个关键是这里有两个指针成员,分别是读和写的结构体参数指针。
![wKgZomXb5Q2AeC0OAABR9iP3hUk323.png](https://file1.elecfans.com/web2/M00/C0/EF/wKgZomXb5Q2AeC0OAABR9iP3hUk323.png)
那我们看下结构体成员初始化函数,其中除了对成员变量赋值了默认参数外,还对读写时序参数结构体指针的成员也赋值了默认参数:
![wKgaomXb5ROAOfffAABluphjhp0417.png](https://file1.elecfans.com/web2/M00/C1/DD/wKgaomXb5ROAOfffAABluphjhp0417.png)
所以这里就是重点,此时这个结构体刚定义完成,因为是局部变量是定义在栈里的,所以初值都是随机值,这个随机值实际可以解释为栈空间上次释放的局部变量值。
当对一个随机值的指针进行赋值会发生什么?三个结果:
1、随机值是非法地址,立刻触发hardfault;
2、随机值是程序实际RAM地址范围外的可写地址,意外操作了寄存器或者无效地址,一次无效操作或开启意外功能;
3、随机值是程序已使用的RAM地址,破坏了这段内存,程序不会立刻触发hardfault,会在CPU使用到该区域时才出现异常。
那我们应该如何调用这个EXMC的结构体初始化呢?其实这里有定义三个结构图,另外两个就是读写的时序结构体的实体,我们定义后先将这两个结构体变量赋值到exmc模式结构体成员的两个指针,此时指针才有了正确地址,调用结构图初始化后就可以把这两个结构体一起完成初始化。
![wKgZomXb5RiAH0HrAAATjr3T7fk244.png](https://file1.elecfans.com/web2/M00/C0/EF/wKgZomXb5RiAH0HrAAATjr3T7fk244.png)
这里的分析很考验大家C语音指针、CPU内存的理解功底,还有什么疑难杂症欢迎大家提供素材。上面分析的正确初始化顺序在红枫派开发板例程中应用,欢迎大家应用到项目中使用。
-
单片机
+关注
关注
6019文章
44323浏览量
627740 -
嵌入式
+关注
关注
5039文章
18775浏览量
297800 -
GD32
+关注
关注
7文章
398浏览量
23945 -
EXMC
+关注
关注
0文章
7浏览量
5167
发布评论请先 登录
相关推荐
![](https://file1.elecfans.com/web2/M00/C0/F0/wKgZomXb5yqAV_deAAvmPu3NNZU588.png)
评论