上一期的参考资料如下:
源码地址://download.csdn.net/download/Sure_gengjia/1253037
MC9S12G128数据手册: //download.csdn.net/download/Sure_gengjia/12530918
本期源码地址:待更新
以下操作代码和测试代码可以关注公众号“激活未来”,后台留言即可。
下载源码可以获得更多内容。
还可添加微信号:ActivateFuture进行交流。
1 overview
1.1 目的
本文档用于起点开发板的软件中位操作说明。
不局限于硬件功能的实现,着眼于实现高质量、优美的软件。
2 位操作
2.1 原因
很多对寄存器的操作需要位操作,包括很多数据也需要位操作,为了让位操作更加优美、增加可读性和支持更复杂的位操作,特把位操作单独成章,进行解析。
2.2 位操作的用处
2.2.1 寄存器操作
在该开发板driver层中可见到以下代码:
对drio_dir_reg中的寄存器进行位与操作。
2.2.2 数据处理
3 具体操作
3.1 或操作|
3.1.1 以unsignedchar类型数据为例
希望对unsigned char或者unsigned short或者unsigned long数据进行位与操作,如:
unsigned char u8_data = 0x55;
-
将u8_data的bit0置一,操作如下:
u8_data |= 0x01;
0x01二进制表示为(0000 0001)b
-
将u8_data的bit4置一,操作如下:
u8_data |= 0x10;
0x10二进制表示为(0001 0000)b
0x01和0x10都可以用1移位到期望的bit位,
所以可以改写为:
u8_data |= (unsigned char)((unsigned char)(1 << 0));
u8_data |= (unsigned char)((unsigned char)(1 << 4));
//1<<4 -> 0001 0000b = 0x10,
//(unsigned char)(1 << 4) = (0001 0000)b= 0x10
//u8_data & 0xef将bit4置一,其他位置不影响;
3.1.2 如何生成指定位为1的掩码
3.2 位与运算&
3.2.1 以unsigned char类型数据为例
希望对unsigned char或者unsigned short或者unsigned long数据进行位与操作,如:
unsigned char u8_data = 0x55;
-
将u8_data的bit0清零,操作如下:
u8_data &= 0xfe;
0xfe二进制表示为(11111110)b
-
将u8_data的bit4清零,操作如下:
u8_data &= 0xef;
0xef二进制表示为(11101111)b
0xfe和0xfe都可以用1移位到期望的bit位,然后取反,
所以可以改写为:
u8_data &= (unsigned char)(~(1 << 0))
u8_data &= (unsigned char)(~(1 << 4));
//1<<4 -> 0001 0000b = 0x10,
//(unsigned char)(~(1 << 4)) = 1110 1111b = 0xef
//u8_data & 0xef将bit4清零,其他位置不影响;
3.2.2 如何取0xef——如何生成与掩码
将bit4清零生成的,只需要将数据与0xEF相与,将bit0清零,只需要将数据与0xFE相与;
如何生成0xEF和0xFE?
只需要将‘1’左移至指定位置,然后取反即可,具体代码实现见第四章。
3.3 异或取反操作^
① 与1异或操作可以用于对变量指定位取反。
1 ^ 1 = 0;
0 ^ 1 = 1;
相同为0,不同为1。
② 与0异或,取原值
1 ^ 0 = 1;
0 ^ 0 = 0;
3.3.1 以unsigned char类型数据为例
希望对unsigned char或者unsigned short或者unsigned long数据进行位与操作,如:
unsigned char u8_data= 0x55;
-
将u8_data的bit0取反,操作如下:
u8_data ^= 0x01;
0x01二进制表示为(0000 0001)b
-
将u8_data的bit4取反,操作如下:
u8_data ^= 0x10;
0x10二进制表示为(0001 0000)b
0x01和0x10都可以用1移位到期望的bit位,
所以可以改写为:
u8_data ^= (unsignedchar)(1 << 0);
u8_data ^= (unsignedchar)(1 << 4);
//u8_data ^ 0x10将bit4取反,其他位置不影响;
4 软件实现
4.1 生成掩码
约定:
① byte指八位数据长度无符号数值
② WORD指十六位数据长度无符号数值
③ DWORD指三十二位数据长度无符号数值
4.1.1 生成指定位为1的掩码
生成一个“1”
生成多个“1”
4.1.2 生成指定位为0的掩码
只需将生成多个“1”的掩码取反:
4.2 指定位置一
4.2.1 基本或操作
① data为unsigned char型变量;
bitmask为指定位要置一的掩码,如bit0->bit2置一,掩码应为0x07
② data为unsigned short型变量;
bitmask为指定位要置一的掩码,如bit0->bit2置一,掩码应为0x0007
③ data为unsigned long型变量;
bitmask为指定位要置一的掩码,如bit0->bit2置一,掩码应为0x0000 0007
4.2.2 指定一个位置一
bitidx为指定位,0~31;
4.2.3 指定多个位置一
startbit为指定位,0~31;
bitcount为期望被置一的位长度;
4.3 指定位清零
4.3.1 基本与操作
① data为unsigned char型变量;
bitmask为指定位要清零的掩码,如bit0->bit2清零,掩码应为0xF8
② data为unsigned short型变量;
bitmask为指定位要清零的掩码,如bit0->bit2清零,掩码应为0xFFF8
③ data为unsigned long型变量;
bitmask为指定位要清零的掩码,如bit0->bit2清零,掩码应为0xFFFFFFF8
4.3.2 指定一个位清零
bitidx为指定位,0~31;
4.3.3 指定多个位清零
startbit为指定位,0~31;
bitcount为期望被置一的位长度;
4.4 读取指定位
读取变量指定位是0还是1。
bitidx为指定的位的索引,范围0~31
4.5 指定位写值
给变量的指定位置写入0或1。
4.5.1 写值基本操作
4.5.2 指定一个位写值
① 首先要将指定位清零
BYTEOP_GENERATE_MASK_BITS (bitidx,1)生成掩码;
② 再判断要写入的值是0还是1
((bitvalue) & 0x01U) << (bitidx))限制写入值为0或1;
4.5.3 指定多个位写值
4.5.3.1 分解
一byteop为例
① 生成掩码,将指定的多个位清零
BYTEOP_GENERATE_MASK_BITS(startbit,bitcount)
② 根据startbit和bitcount生成指定长度的掩码,与要写入的value相与,排除对变量其他位的影响
BYTEOP_GENERATE_BITS(0,bitcount)
③ 或上要写入的被修饰过的值
5 软件测试
5.1 “1”移位操作
5.1.1 测试代码
5.1.2 测试结果
5.2 生成多位为“1”的操作
用于对多个位置一操作,生成如0x07的数值;
5.2.1 测试代码
5.2.2 测试结果
5.3 生成掩码
生成如0xFE的掩码,用于屏蔽bit0;
5.3.1 测试代码
5.3.2 测试结果
5.4 置一操作
5.4.1 测试代码
5.4.2 测试结果
5.5 指定位清零操作
5.5.1 测试代码
5.5.2 测试结果
5.6 其他操作
其他操作:
① 指定多位置一
② 指定多位清零
③ 读指定位数值
④ 写指定位数值
⑤ 写指定多位数值
以上操作代码和测试代码可以关注公众号“激活未来”。后台留言即可。
下载源码可以获得更多内容。
还可添加微信号:ActivateFuture进行交流。