首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >将STM32寄存器封装为库函数.上

将STM32寄存器封装为库函数.上

作者头像
云深无际
发布2022-02-09 11:33:57
发布2022-02-09 11:33:57
5400
举报
文章被收录于专栏:云深之无迹云深之无迹

点了个灯开心不?开心个锤子。。。至于吗?Ctrl+F都摁坏了,而且这位运算,不好玩。。。

我们接下来升级

我觉得性能敏感可以寄存器,如果不敏感就库函数,你全用寄存器操作,我也不会说你一个牛逼。

F4,F7的片子怎么办?哭吧,卫生纸也挺缺的,我用完了。

在操作寄存器的时候,操作的是都寄存器的绝对地址,如果每个外设寄存器都这样操作,那将非常麻烦。我们考虑到外设寄存器的地址都是基于外设基地址的偏移地址,都是在外设基地址上逐个连续递增的,每个寄存器占32 个字节,这种方式跟结构体里面的成员类似。所以我们可以定义一种外设结构体,结构体的地址等于外设的基地址,结构体的成员等于寄存器,成员的排列顺序跟寄存器的顺序一样。这样我们操作寄存器的时候就不用每次都找到绝对地址,只要知道外设的基地址就可以操作外设的全部寄存器,即操作结构体的成员即可。

寄存器的值常常是芯片外设自动更改的,即使CPU 没有执行程序,也有可能发生变化,编译器有可能会对没有执行程序的变量进行优化。

这就是我们的库函数的样子。

这段代码在每个结构体成员前增加了一个“__IO”前缀,它的原型在这段代码的第一行,代表了C 语言中的关键字“volatile”,在C 语言中该关键字用于表示变量是易变的,要求编译器不要优化。这些结构体内的成员,都代表着寄存器,而寄存器很多时候是由外设或STM32 芯片状态修改的,也就是说即使CPU 不执行代码修改这些变量,变量的值也有可能被外设修改、更新,所以每次使用这些变量的时候,我们都要求CPU 去该变量的地址重新访问。若没有这个关键字修饰,在某些情况下,编译器认为没有代码修改该变量,就直接从CPU 的某个缓存获取该变量值,这时可以加快执行速度,但该缓存中的是陈旧数据,与我们要求的寄存器最新状态可能会有出入。

还有个事情,就是我们还没有和我们的地址产生联系,外设寄存器结构体定义仅仅是一个定义,要想实现给这个结构体赋值就达到操作寄存器的效果,我们还需要找到该寄存器的地址,就把寄存器地址跟结构体的地址对应起来。所以我们要再找到外设的地址,我们可以把这些外设的地址定义成一个个宏,实现外设存储器的映射。

不装逼了,就是这样的一点东西。

定义好外设寄存器结构体,实现完外设存储器映射后,我们再把外设的基址强制类型转换成相应的外设寄存器结构体指针,然后再把该指针声明成外设名,这样一来,外设名就跟外设的地址对应起来了,而且该外设名还是一个该外设类型的寄存器结构体指针,通过该指针可以直接操作该外设的全部寄存器。

哎,真理就是这样的朴实无华。

首先通过强制类型转换把外设的基地址转换成GPIO_TypeDef 类型的结构体指针,然后通过宏定义把GPIOA、GPIOB 等定义成外设的结构体指针,通过外设的结构体指针我们就可以达到访问外设的寄存器的目的。

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2022-02-06,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 云深之无迹 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档