位带操作详解

一、位带操作的原理

1.1 位带操作的基本概念

位操作就是可以单独的对一个比特位读和写,在51 单片机中通过关键字 sbit 来实现位定义,STM32 没有这样的关键字,而是通过访问位带别名区来实现位定义
在这里插入图片描述

1.2 为什么需要位带操作

在引脚初始化后,控制引脚输入/输出是通过操作寄存器ODR/IDR的值来进行,例如让PA0输出高电平程序入下:

GPIOA->ODR |= 1 << 0;

这个操作包含了三个隐含的操作:

  1. 读取整个ODR寄存器值到内存中的寄存器
  2. 改写内存中寄存器第0位值
  3. 改写后值写入ODR寄存器

相比之下位带操作通过专门的硬件支持,直接对特定的位进行操作,省去了读取寄存器,修改和再写回的过程。这样做主要有以下两点优势:

  1. 当我们需要频繁操作IO口的时候,位带操作效率更高
  2. 多任务中实现共享资源在任务间互斥操作(将读-改-写做成一个硬件级别支持的原子操作)

1.3 具体实现

位带区的一个比特位经过膨胀之后,变大到 4 个字节,由于STM32 的系统总线是 32 位的,按照 4 个字节访问的时候是最快的,如下图:
在这里插入图片描述

地址转换:AliasAddr = 0x42000000 + (A - 0x40000000) * 32 + n * 4
A是片上外设所在字节地址,序号为n
代码实现:这里使用volatile修饰避免被编辑器优化,确保每次读取的都是内存地址的值

#define BITBAND(addr, bitnum) ((addr & 0xF0000000)+0x2000000+((addr &0xFFFFF)<<5)+(bitnum<<2)) 
#define MEM_ADDR(addr)  *((volatile unsigned long  *)(addr)) 
#define BIT_ADDR(addr, bitnum)   MEM_ADDR(BITBAND(addr, bitnum)) 

二、参考资料

  • 1 <<CM3权威指南>>第五章(87页~92页).
  • 2 野火零死角玩转 STM32
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值