基于FPGA的DS18B20温度读取

1. 通信原理

  • DS18B20采用1-wire通信协议,只用一根线dq进行主从式半双工异步串行通信。一根线(DQ)之所以能实现双向读写,靠的是开漏输出(Open-Drain)+ 外部上拉电阻的物理结构,以及严格依赖时间的“时隙(Time Slot)”机制。用使能来控制总线,进而操控读取过程。

  • 手册里规定的通信步骤:初始化–ROM指令–RAM指令

  • 用使能来控制总线,进而操控读取过程,使能给1,则dq值由dq_out给出(dq_out基本为0,除了等待阶段),否则高阻态。

  • 读写时序(单个字节的读和写持续60us,间隔至少1us)

操作类型 0~2µs 主机动作 2µs后 主机动作 采样动作 最终总线电平(结果)
写 0 拉低总线 继续拉低至60µs 不采样 低电平
写 1 拉低总线 释放(z)让电阻拉高 不采样 高电平
读 0 拉低总线 释放(z)让给从机 在10µs采样(采到0) 从机强制拉低
读 1 拉低总线 释放(z)让给从机 在10µs采样(采到1) 电阻拉高(从机不拉低

2. 具体流程:

  1. 给出使能1持续500us,相当于拉低500us总线,发出复位脉冲
  2. 释放总线,再等待70us,读取dq_in得到总线当前采样值,如果采集到低电平,说明采集到从机响应脉冲了,初始化步骤完成。
  3. 依次写入ROM命令和功能命令。命令预先整合并保存为一个参数,0xcc是跳过ROM,0x44是温度转换,0xbe是温度读取
  4. 比方写温度读取命令0xCC时,用 bit_cnt 从 0 到 15 循环,依次取出 WR_CMD_DATA[bit_cnt]。先取 bit0(LSB)发送,最后取 bit15(MSB)。每发一个bit,等待一个完整的63µs时隙(多余3us用作间隔),再发下一个。
  5. 等待780ms温度转换完成
  6. 再次初始化
  7. 写RD_CMD_DATA进行温度读取
状态 动作 设计依据(数据手册)
INIT1 主机拉低总线500µs(复位脉冲),释放后在第570µs采样从机响应脉冲。 复位低电平≥480µs,存在脉冲出现在1560µs后,持续60240µs。
WR_CMD 依次写入16位数据:0x44CC(LSB first)。实际发送顺序:0xCC(跳过ROM)→ 0x44(启动温度转换)。 必须先发ROM命令(Skip ROM)再发功能命令(Convert T)。
WAIT 总线强制拉高(强上拉),延时780ms 12位分辨率最大转换时间为750ms,寄生电源模式下转换期间必须强上拉。
INIT2 再次执行复位/存在脉冲检测,为读取暂存器做准备。 每次访问DS18B20都必须以初始化序列开始。
RD_CMD 写入16位数据:0xBECC(LSB first),即0xCC(跳过ROM)→ 0xBE(读暂存器)。 读暂存器命令需在ROM命令之后发出。
RD_DATA 连续读取16个位(字节0和字节1,即温度寄存器的LSB和MSB)。 读时隙中,主机在2µs后释放总线,并在10µs处采样,符合“15µs内有效”的时序要求。

2.数据格式

对于12位分辨率(默认),低12位(bit110)为有效温度数据,高4位(bit1512)为符号扩展位(正数全0,负数全1)。输出数据到寄存器时可以先进行负温度处理(低12位取反+1)和正温度处理(直接取低11位),然后输出低11位为温度绝对值,最高位bit15作为温度符号。

3.调试

先下bit通过ila抓温度绝对值是否正常,然后在上位机软件里抓取寄存器值核对是否一致,最后通过上位机ui进行最后一步温度核对。