📝 Auto 语言设计文档:位操作与位域视图规范
1. 设计哲学
- 语义与物理分离:位操作不仅是算术,更是对物理空间的精准切片。
- 视图优先:推崇使用
bits()和bit()建立逻辑映射,而非原始的位移计算。 - 语法清晰:**位索引(位置/长度)**使用十进制数字,**位值(掩码/字面量)**推荐使用
0b二进制。
2. 基础位运算指令 (Bitwise Methods)
| 操作 | 语法示例 | 说明 |
|---|---|---|
| 与/或/异或 | val.and(0b1010), val.or(0b1), val.xor(0b1011) | 基础位逻辑运算。 |
| 取反 | val.not() | 按位取反(NOT) |
| 移位 | val.shl(2), val.shr(1) | 位索引使用十进制:逻辑左移/右移。 |
| 算术右移 | val.sar(1) | 算术右移,保留符号位。用于定点数运算和 DSP 算法。 |
| 循环移位 | val.rol(3), val.ror(1) | 循环左移/右移。 |
3. 位域视图 (Bitfield Views)
这是处理复杂寄存器的核心工具,将变量视为比特序列。
3.1 动态视图
val.bits(start, len): 返回切片视图。start: 起始位索引(十进制,0-31)。len: 位长度(十进制)。- 操作:
.read(),.write(0b1011)。
val.bit(index): 返回单比特视图。index: 位索引(十进制)。- 操作:
.on(),.off(),.flip(),.test() -> bool。
3.2 声明式位域 (Struct-Embedded)
在 type 定义中直接映射硬件手册字段。
auto
type CtrlReg u32 {
// 名称 = bits(起始位索引, 长度)
mode = bits(0, 4) // 位 0~3
rate = bits(4, 4) // 位 4~7
enable = bit(8) // 位 8
pending = bit(9) // 位 9
}4. 位特征扫描 (Bit-Scanning)
返回结果为十进制计数值,用于高性能算法。
.count_ones(): 返回1的总个数。.leading_zeros(): 从最高位开始的连续0个数(常用于查找最高优先级)。.trailing_zeros(): 从最低位开始的连续0个数。.flip(): 比特位镜像翻转(bit-reverse),将位序完全颠倒。
5. 综合代码示例 (S32G3 驱动场景)
auto
// 定义映射地址
pub shared var SYS_CTRL CtrlReg @ 0x4000_1000
fn configure_hardware() {
// 1. 写入位值:使用 0b 二进制,直观反映比特状态
SYS_CTRL.mode.write(0b1011)
// 2. 写入位值:十进制报错!编译器应当建议对应的二进制值。但是十六进制是允许的。
SYS_CTRL.rate.write(5)
// 3. 单比特操作
SYS_CTRL.enable.on()
// 4. 原子更新
atomic SYS_CTRL {
if SYS_CTRL.pending.test() {
SYS_CTRL.mode.write(0b0001)
SYS_CTRL.pending.off()
}
}
}6. 设计规约总结
- 端序一致性:
bits(0, 4)始终对应逻辑上的最低 4 位(LSB $2^0$ 到 $2^3$),不受内存端序影响。 - 安全约束:编译器会检查位操作。例如对
u32执行shl(32)或bit(35)会抛出编译错误。 - 零成本抽象:所有的视图操作(
.read(),.write(),.set())都会在编译时展开为最优的位掩码指令,不产生运行时对象。