当前位置: 首页 > news >正文

在 STM32 上使用 register 关键字

在 STM32 上使用 register 关键字时,有一些特别需要注意的事项。虽然 register 是 C 语言中的一个标准关键字,它用于提示编译器将变量尽可能存放在寄存器中,以加速访问,但在 STM32 这样的嵌入式平台上,还是需要考虑几个方面:

1. STM32 的寄存器有限

STM32 的微控制器(MCU)拥有有限数量的寄存器(通常是 16 个通用寄存器)。因此,register 并不会将所有变量都放入寄存器,而是依赖于编译器的智能选择。

注意点:

  • 如果声明的局部变量比较多,编译器可能会选择不将所有变量都放入寄存器。
  • 在 STM32 系列中,尤其是小型型号(如 STM32F030,STM32F1 系列),寄存器资源非常紧张,过度使用 register 可能会导致寄存器分配冲突或性能下降。
  • 对于大多数情况下,编译器会自动优化局部变量,通常不需要显式使用 register

2. register 变量不能取地址

使用 register 声明的变量不能使用 & 操作符取其地址,因为它们是寄存器变量,不能被直接访问。如果你尝试取寄存器变量的地址,编译器会报错。

register int x = 10;
int *p = &x;  // 编译错误:无法取寄存器变量的地址

如果在代码中需要取变量的地址,那么应该避免使用 register

3. register 和优化设置

对于嵌入式开发,STM32 的编译器(如 Keil5)通常会做自动优化。尤其是在开启 -O3-Os 优化选项时,编译器会自动根据情况将局部变量存放到寄存器中,实际上很多时候你并不需要手动指定 register

  • -O3 优化: 该优化等级下,编译器会最大程度优化代码,包括变量寄存器分配,因此许多情况下,即使不使用 register,编译器也会将频繁使用的变量存储在寄存器中。
  • -Os 优化: 该选项关注代码的尺寸,编译器会尽可能减少代码大小,同时考虑将变量放入寄存器中,以提升性能。

在启用这些优化时,register 关键字的作用可能会显得不那么重要,因为编译器已经在做类似的优化。

4. 特殊寄存器

对于 STM32 微控制器,除了普通的通用寄存器外,还有一些专用寄存器(如 SFR, 特殊功能寄存器)。这些寄存器和通用寄存器有所不同,它们用于控制外设、系统设置等。使用 register 时,不能期望 STM32 编译器会将这些特殊寄存器存入普通的通用寄存器。

建议:

  • 如果操作的是硬件寄存器(如 GPIOUSART 等外设寄存器),应该直接使用该外设的寄存器地址,而不应依赖 register 关键字。

5. register 和 STM32 外设访问优化

在 STM32 中访问外设寄存器时,寄存器的值往往是需要直接映射到内存的。在这种情况下,编译器可能会将外设寄存器地址作为指针处理,而不是使用 register 来优化。对于外设的寄存器,手动优化(例如通过 DMA 或通过内存映射外设等)通常比使用 register 更为有效。

6. register 和 ARM 架构

STM32 微控制器基于 ARM Cortex-M 内核(如 Cortex-M3、M4、M7)。ARM 处理器本身有一套高效的寄存器管理和流水线机制,编译器在优化时会根据 ARM 的特点做相应优化。

注意:

  • ARM 处理器已经具有相对较多的寄存器(如 ARM Cortex-M4 有16个通用寄存器),如果使用 register,编译器会尽量选择合适的寄存器来存放变量。
  • 对于复杂的 ARM 指令集,编译器会在优化时选择合适的寄存器使用策略,因此即使不显式声明 register,编译器通常也能合理地优化寄存器的使用。

总结:

在 STM32 上使用 register 时,有以下几点需要特别注意:

  1. 有限的寄存器资源:STM32 的寄存器数量有限,过度使用 register 可能会导致寄存器分配冲突。
  2. 不能取地址:声明为 register 的变量不能取地址,因此如果需要传递指针或取地址,不能使用 register
  3. 编译器优化:Keil5 等编译器会自动进行优化,通常在开启高级优化(如 -O3)时,不需要显式使用 register,编译器会自动决定将局部变量放入寄存器中。
  4. 适用场景register 最适用于频繁访问的局部变量,但对于 STM32 外设寄存器操作,应直接操作地址,而不应使用 register

在 STM32 的开发过程中,很多时候依赖编译器的优化能力,特别是在 Keil5 环境下,编译器的优化已经非常强大,因此对 register 的使用可以保持谨慎,并根据实际情况决定。

相关文章:

  • 如何访问云相关的api
  • python数据分析常用的10个核心库
  • 题海拾贝:P1833 樱花
  • vue3项目创建-配置-elementPlus导入-路由自动导入
  • 滑动窗口——水果成篮
  • Java后端快速生成验证码
  • 【NextPilot日志移植】params.c解析
  • 携程酒店 phantom-token token1004 分析
  • 什么是原码和补码
  • python中的进程锁与线程锁
  • 关于索引的使用
  • pe文件二进制解析(用c/c++解析一个二进制pe文件)
  • HTTP协议解析:Session/Cookie机制与HTTPS加密体系的技术演进(二)
  • 基于STM32、HAL库的PCM3060PWR 音频接口芯片驱动程序设计
  • UDP协议详细讲解及C++代码实例
  • 转发多台px4仿真UDP数据到地面站
  • KIVI: A Tuning-Free Asymmetric 2bit Quantization for KV Cache
  • sqlserver免费版每天备份数据库
  • 【计算机网络】3数据链路层②
  • 数据结构(一) 绪论
  • A股午后拉升,沪指收复3400点:大金融发力,两市成交超1.3万亿元
  • “11+2”复式票,宝山购彩者领走大乐透1170万头奖
  • 中医的千年传承:网络科学描绘其演化之路|PNAS速递
  • 被流量绑架人生,《人生开门红》能戳破网络时代的幻象吗
  • 高培勇:中国资本市场的发展应将预期因素全面纳入分析和监测体系
  • 韩国前国务总理韩德洙加入国民力量党