目录
前面,我们完成了点灯案例,但是我们当时都是翻阅技术手册然后找到寄存器的基地址和偏移地址来给寄存器的数据赋值的,然后在代码中还得反复地强转指针,这未免麻烦了点。
一旦到后期,我们会学习到很多很多模块,各个模块都会用到不同的寄存器,那要是像这样去一个个找那将非常麻烦。所以我们接下来,要对点灯代码进行一个优化,主要在于寄存器寻址部分。使用宏定义的方式定义寄存器的名称。
一、探索宏定义文件
前面我们加过一些启动文件和相关的核心文件,其中有一个文件中充满了宏定义,即stm32f10x.h
现在,我们进去看看
我们顺势找一下,看看有没有我们开启时钟用的寄存器RCC
这里,我们找到了一个RCC定义宏,但似乎不是我们想要的。
那我们继续往下翻看看,这里,我们找到了RCC基地址的宏定义,发现这里还包含一个基地址以及一个地址值的和,即0x1000+AHBPERIPH_BASE
一探究竟,那么我们继续找这个宏定义看看
找到以后,我们发现,这又是一个宏加上地址值,即0x2000+PERIPH_BASE
我们继续找,发现这也是一个地址值,但没有其他宏了
此时,我们将这些宏全部按照RCC_BASE的意思全部加起来,这样就是表达的RCC基地址的地址值了,我们加起来看看 0x40000000+0x20000+ 0x1000 = 0x40021000
对照技术手册上给的RCC基地址一看,发现这俩一模一样!那么这也说明,这个文件里面确实有用宏定义寄存器名,这样更便于找到寄存器了
我们找到的是他的基地址,那么要知道RCC_APB2ER是不是也有相应的宏定义呢?我们继续探索,再次找找RCC
这里我们发现,这个基地址指针用RCC进行了宏定义,我们可以直接通过RCC去找到相应的寄存器。至于RCC寄存器这么多,他是怎么确定偏移地址的呢?实际上在定义宏的时候他是按照寄存器顺序每四个字节地按顺序排列定义的,因为结构体中访问时顺序访问的,所以这样就可以避免再次定义有关偏移地址值的宏了。
二、宏定义名称替换
因此我们现在可以直接通过宏定义的方式去找到我们想要的的各种寄存器。现在我们来修改代码:
就以第一次点灯案例为例吧
首先我们既然用的是stm32f10x.h中的宏定义,那么我们这里就要包含以下头文件先
同理
修改完后的代码
三、测试运行
修改完毕后,现在我们来编译运行并下载程序
编译没有问题
现在运行,下载程序,我们看现象
对比之前的代码
相对来说还是简洁了不少的。
四、结语
这次利用宏定义寄存器名称对点灯代码的优化,我们更加方便的找到寄存器,大大节约了开发效率。
也认识到了宏定义的使用