ARTICLE DETAIL

资讯详情

深耕商务建站与企业官网运营的一线实战洞察。

基于STM32与PJ85718DM的HVAC温度采集系统设计

基于STM32与PJ85718DM的HVAC温度采集系统设计 做嵌入式和 HVAC 项目的朋友几乎都会遇到温度采集这件事。一类是设备本地的温度比如控制板安装环境温度、压缩机表面温度另一类是远程的温度比如风道末端、送回风口、房间内部这些布线距离比较远的位置。前阵子我配合某设备厂商做温控节点核心就是标题里的两个器件PJ85718DM 数字温度传感器加一颗 STM32F205RB 控制芯片把本地温度直接读出来远程温度再通过 RS485/Modbus 汇总上报。这套方案不算复杂但把采集、滤波、通信、校准整个链路走通里面值得记录的细节非常多。这篇文章会把整个项目从头到尾拆开讲。不管你是在做 HVAC 温控器、嵌入式数据采集终端还是想学怎么用 I2C 温度传感器加 Modbus 做多点测温都能直接照着搭。我会把选型原因、硬件接线、驱动代码、滤波处理、远程通信、实测数据、坑点排查全部写出来尽量让没做过的人也能一次落地。1. 先从需求说起嵌入式和 HVAC 到底要测哪里的温度1.1 本地温度和远程温度分别解决什么问题很多刚接触 HVAC 项目的人会有个误区温度采集不就是把传感器插到设备里读个数值吗实际上本地温度和远程温度是两类完全不同的问题。本地温度通常指控制器自身周围、压缩机壳体、换热器管壁、配电柜内部这些位置。它距离 MCU 很近导线长度通常不超过几十厘米用 I2C 接口的数字传感器非常合适。好处是传感器直接输出数字量不需要额外搭放大电路或做冷端补偿抗干扰能力也强。这类温度主要用来做设备保护比如压缩机排气温度超过设定值就降载甚至停机或者根据管壁温度判断除霜时机。远程温度则是安装在风道、回风口、房间温控面板、室外补偿温度探头这些需要长距离布线的位置。这些地方离主控板可能隔着十几米甚至上百米I2C 在这种距离下根本跑不起来信号完整性会非常差。所以远程测温的常规做法是在每个远端位置放一个小节点板节点板上有 MCU 和传感器采集到温度后通过 RS485 总线传回主控。RS485 是差分信号抗干扰能力强标准应用下能到 1200 米这正好覆盖 HVAC 项目的典型布线距离。所以标题里“本地与远程温度”不是一句废话它代表了两条完全不同的信号链路。一个项目里同时处理好这两条链路才能做出真正能用的温控系统。1.2 这个项目适合谁参考我建议下面几类人重点看这篇文章做 HVAC 控制器、楼宇自控、工业温控箱的嵌入式工程师这套方案可以直接落地。正在学习 STM32 和 I2C 传感器驱动的开发者可以拿这个项目当完整练手案例。想了解 Modbus RTU 从机怎么实现、怎么和触摸屏或组态软件对接的人第 4 章有代码拆解。经常被温度数据跳变、通信不稳定折磨的现场调试人员第 5 章和第 6 章的实测与排查记录应该能帮上忙。我自己当年做类似项目时最头疼的不是读温度而是读出来的温度不可信、传不出去、或者现场跑几天就漂了。这些问题大多不是芯片本身的问题而是电路细节、滤波策略和通信时序没处理好。下面这些内容就是我踩过坑之后总结出来的。2. 选型与整体方案为什么是 PJ85718DM STM32F205RB2.1 传感器选型对比为什么不用 NTC 和 PT100温度传感器这块市面上最常见的是 NTC 热敏电阻、PT100 铂电阻、以及各类数字温度传感器。我帮客户做方案时通常先问三个问题测量范围多少、精度要求多少、现场有没有强干扰。回答完这三个问题再决定用哪种。NTC 成本最低很多家电温控器都在用。但 NTC 是非线性的而且同一批次之间的阻值离散性也不小。要做好更换不标定的产品基本必须用电桥加编程校准表B 值一变整个曲线就偏了。我并不是否定 NTC在温度范围窄、精度要求不高、单点定标能接受的产品里它仍然是最经济的选择。但如果我们做的是对精度和一致性有要求的 HVAC 节点我不想把大量生产校准成本转移到温控逻辑里。PT100 精度高能到 ±0.1℃ 甚至更高但需要恒流源或电桥电路、仪表放大器、ADC还要考虑导线电阻补偿硬件成本一点都不低。PT100 适合做实验室级或者工业级标准温度计用在分布式测温节点上每个节点的物料成本和 PCB 面积都会失控。PJ85718DM 这种数字温度传感器就适合在这两者之间找到一个平衡点。它本身集成了温度敏感元件和 ADC直接通过 I2C 输出数字量。单芯片方案不需要外围放大精度一般能做到 ±0.5℃ 以内分辨率可以达到 0.0078125℃。对 HVAC 环境监测来说这个精度绰绰有余风道和房间温度的控制精度通常在 ±1℃ 到 ±2℃传感器本身的误差远小于控制回路的动作阈值。另外要说明的是PJ85718DM 这个型号可能不像 NTC 那样人人熟悉我拿到实物后的理解是它是一颗 I2C 接口、16 位温度寄存器输出的数字传感器工作电压 3.3V 或 5V 都能兼容默认 7 位地址是 0x48 那一档实际以你手里的数据手册为准。如果你拿到的批次寄存器映射稍有差异不影响整体架构只需要把驱动里读寄存器的地址改一下就行。2.2 STM32F205RB 扮演什么角色STM32F205RB 是 Cortex-M3 内核主频最高 120MHzFlash 是 1MBRAM 是 128KB。对于温度采集这种任务来说这个配置其实是富余的。那为什么还要选它因为我在这个项目里不只是读一个温度还要同时管理 RS485 通信、看门狗、状态指示灯、本地存储甚至以后可能加 Ethernet 或 USB 转串口升级。F205 这颗芯片有几个点很对我的胃口。第一它有多个硬件 I2C 和 USART 外设I2C1 接传感器USART2 接 RS485 收发器外设之间不冲突代码也不需要在同一个中断里来回切换。第二它支持 DMAUSART 的收发可以用 DMA 搬运配合 Modbus RTU 的帧收发可以明显降低 CPU 占用。第三它有足够的 IO 和定时器资源后期哪怕要加两路 PWM 控制风机转速也不至于重新选型。有人可能会问用一颗更低端的芯片是不是也行比如 F103 系列。答案是看项目定位。F103 当然能跑同样的逻辑但 F205 在 I2C 外设的稳定性、SRAM 容量、DMA 通道数量上都要好一些。如果你做的是批量 HVAC 控制器追求极致成本F103 也完全撑得住但如果你做的是高端楼宇自控节点需要更充裕的资源跑后续功能F205 是更稳妥的选择。我这次用的正是 F205RB。2.3 系统布局本地采集、远程上报的整体链路整个系统的结构可以理解为三层。第一层是本地采集层。STM32F205RB 通过 I2C 总线直接读 PJ85718DM 的温度数据。这里 I2C 线的长度建议控制在 30cm 以内传感器尽量靠近主控板。如果传感器模块需要延长用屏蔽线并在传感器端加 0.1uF 去耦电容否则在变频器附近很容易读到毛刺。第二层是远程节点接入层。每个远端测温点放一块小从机板板上有 STM32 最小系统、PJ85718DM、RS485 收发器。从机板负责采集本地温度并在收到主站请求时把温度数据返回。这里的“本地”是相对于从机板而言的实际上它也是远程节点。第三层是集中管理上报层。主控板作为 Modbus 主站通过 RS485 总线轮询各个从机节点。主站把各点温度汇总后可以传给触摸屏、组态软件或者再通过以太网上传到楼宇管理平台。这样客户在值班室就能看到每个风道口、每个房间的温度变化。说句实在话这种“从机采集 主站轮询”的结构是 HVAC 行业最通用的方案因为 Modbus RTU 几乎被所有触摸屏和组态软件原生支持不需要写私有协议也不用装额外驱动。项目验收时客户用一根 USB 转 485 线就能看到数据说服力很强。3. 硬件设计从传感器到 MCU 再到远程总线的完整链路3.1 传感器接线与电源设计PJ85718DM 的引脚不多通常包括 VDD、GND、SDA、SCL有些封装还会引出一根 AD0 地址选择脚。VDD 直接接 3.3VGND 就近回地SDA 和 SCL 各接一颗上拉电阻到 3.3V。上拉电阻的取值很有讲究。我刚开始做的时候用 10kΩ 上拉结果 I2C 时钟一提高到 400kHz 就经常传输出错波形上升沿太慢。后来换成 4.7kΩ问题立刻消失。如果你的板子比较紧凑、走线较短1.8kΩ 也可以但不要低于 1kΩ否则灌电流偏大对芯片 IO 不太友好。电源方面要特别注意传感器尽量不要直接从 MCU 的 VDD 引脚上再拉一根线供电。MCU 引脚电流变化比较大尤其是驱动继电器或者指示灯时电源噪声会耦合到温度数据里。我的习惯是用一个小功率 LDO 单独给传感器供电或者至少在传感器 VDD 引脚旁边并联一颗 1uF 陶瓷电容和一颗 0.1uF 高频去耦电容两者配合使用。多次实测下来这样做能把温度数据的随机跳变减少一半以上。另外如果传感器模块是成品模块板上一般自带滤波电容和上拉电阻。自己做板子时PCB 布线要保证传感器底下不要铺大块地铜避免杂散电容影响 SCL 波形。传感器尽量靠近 MCU 引脚让 I2C 走线保持短、直、左右有地线包裹。3.2 RS485 远程通信电路要点RS485 收发器我用的是 SP3485 这类 3.3V 供电的芯片直接和 STM32F205RB 的 USART 引脚连接不需要电平转换。收发器的 A、B 引脚接到接线端子对外走双绞线。这里有几个细节特别容易翻车我逐个说一下。第一A、B 之间要并接 120Ω 终端电阻。这个电阻放在总线最远端作用是吸收反射信号。如果总线上只有两块板而且距离很短不接也能跑但距离一超过几十米或节点一多不接就会偶发帧错误。终端电阻的计算很简单双绞线的特征阻抗通常在 120Ω 左右终端电阻等于特征阻抗时反射最小。第二收发器的 DE 和 RE 引脚要连到一起由 MCU 的一个 GPIO 控制。发送数据前拉高发送完再拉低切回接收。切换时机如果不对最后几个字节会出现截断。我一般发完最后一个字节后延时 1 个字符时间再拉低或者干脆用发送中断里加个延时。你也可以用硬件自动收发电路但我觉得用 GPIO 控制更直观、排查问题更方便。第三A、B 线上要加 TVS 管防止现场长线感应雷击或电机启停造成的浪涌损坏收发器。HVAC 现场经常有变频器、风机、水泵这些设备启停瞬间会产生很强的干扰这个问题我在第 6 章还会单独说。RS485 总线布线建议用屏蔽双绞线屏蔽层单端接地。如果是多节点总线要手拉手连接绝对不能搞成星形星形会产生大量反射。这是个老生常谈的问题但现场施工时几乎每回都要强调一遍因为很多施工队习惯就近接线。3.3 样机焊接与布局注意事项如果是自己打样调试焊接传感器之前先确认引脚定义最好用万用表量一下 VDD 和 GND防止反接把芯片烧掉。PJ85718DM 这类贴片芯片很小焊接时焊台温度控制在 350℃ 左右时间要短。我见过有人焊了太久温度传感器被烙铁烤偏了零点常温下读数比正常高了 2 度后来怎么软件校准都不稳定最后换了一颗芯片才好。MCU 核心板的选择上如果不想自己画板直接买带 STM32F205RB 的最小系统板也行但一定要确认 3.3V 电源干净。有些开发板的 LDO 纹波比较大在做温度采集时表现出来就是读数最后一位不停跳动换一块供电稳定的板子立刻就好。板子上如果有继电器、蜂鸣器这些感性负载它们的电源要和传感器供电分开走线地线尽量采用单点接地。这样做能减少地弹噪声对 ADC 和 I2C 的影响。虽然是“经验之谈”但在现场调试时往往就是这些细节决定成败。4. 软件实现驱动、滤波与远程通信代码拆解4.1 I2C 驱动读取温度软件上第一步是把传感器读出来。我用 STM32 的 HAL 库打开 I2C1主机模式时钟设成 100kHz 先跑通后面再提速到 400kHz。读温度寄存器的逻辑很简单先发送寄存器地址再读两个字节把两个字节拼成 16 位整数最后按分辨率系数转成温度值。#define PJ85718DM_ADDR 0x48 #define REG_TEMP 0x00 int16_t read_temp_raw(void) { uint8_t reg REG_TEMP; uint8_t buf[2]; if (HAL_I2C_Master_Transmit(hi2c1, PJ85718DM_ADDR, reg, 1, 100) ! HAL_OK) { return INT16_MIN; // 返回无效值交给上层处理 } if (HAL_I2C_Master_Receive(hi2c1, PJ85718DM_ADDR, buf, 2, 100) ! HAL_OK) { return INT16_MIN; } return (int16_t)((buf[0] 8) | buf[1]); } float read_temp_celsius(void) { int16_t raw read_temp_raw(); if (raw INT16_MIN) { return -999.0f; // 用明显异常值表示读取失败 } // 这里以 16 位分辨率 0.0078125℃/LSB 为例 return raw * 0.0078125f; }这段代码有几个地方要解释一下。第一I2C 地址为什么是 0x48 左移位之后的格式HAL 库里的地址参数是 8 位地址也就是包含读写位的格式7 位地址 0x48 需要左移一位变成 0x90才能和 HAL 库的读写位拼接正确。我上面的写法会有人直接用宏不同人的写法可能差一位这点特别容易坑。你写代码时用数据手册里的地址配合 HAL 库时记得左移或者直接查你手上例程的定义。第二读到的 raw 值是带符号的因为宽温度范围下负温会出现最高位为 1 的情况。如果我把它定义成 uint16_t零下温度转换出来会变成很大的正数后台显示一团乱麻。所以用 int16_t 接收再转 float。第三为什么温度转换系数是 0.0078125因为分辨率是 1/128 0.0078125也就是 16 位温度寄存器的最低位表示 0.0078125℃。如果你的芯片数据手册写明精度是 12 位、13 位或 14 位转换公式要按实际有效位调整不能盲目套。读取周期方面HVAC 温度变化慢我把读温度放在 1s 定时中断里触发。如果需要更快响应可以缩短到 200ms但对大多数风道、房间温度来说没必要反而会让滤波更难做。4.2 温度数据处理均值滤波与防毛刺直接读出来的温度值往往不能直接用因为现场有变频器、开关电源这些干扰源原始数据偶尔会冒出一个明显偏大的尖峰。我在项目里用了两重处理第一重是滑动平均滤波用来平滑随机噪声第二重是限幅判断用来剔除明显毛刺。滑动平均的代码可以直接看下面的实现#define FILTER_SIZE 8 static float temp_hist[FILTER_SIZE]; static uint8_t temp_idx 0; static uint8_t temp_count 0; float temp_sliding_avg(float new_sample) { float sum 0.0f; uint8_t i; temp_hist[temp_idx] new_sample; temp_idx (temp_idx 1) % FILTER_SIZE; if (temp_count FILTER_SIZE) { temp_count; } for (i 0; i temp_count; i) { sum temp_hist[i]; } return sum / temp_count; }用 8 个样本做平均1s 读一次的话就是 8s 平滑窗口。对 HVAC 来说这个响应速度完全足够而且曲线会非常漂亮。如果你要做压缩机保护这种对快速响应有要求的场景可以把窗口缩到 4 个样本或者干脆不做平均直接用原始值只是再叠加一道限幅滤波。限幅滤波的核心思想是“上次合法值和这次采样值之差超过一个阈值就认为是毛刺”。比如正常温度变化在 0.5℃/s那设置变化阈值 2℃ 已经足够宽松。一旦检测到突变直接丢弃这次采样用上次值代替。float temp_anti_glitch(float new_sample) { static float last_valid 25.0f; const float max_step 2.0f; if (fabsf(new_sample - last_valid) max_step) { return last_valid; } last_valid new_sample; return new_sample; }实际调试时我先把毛刺日志全部打出来看是周期性的还是偶发的。如果是周期性尖峰多半是周围有开关动作和 I2C 时钟重叠如果是偶发可能是电源抖动。命令先抓波形再改参数“拍脑袋”加滤波参数只会掩盖问题不会根治问题。4.3 Modbus RTU 从机通信实现远程节点上跑的协议我直接用 Modbus RTU。它是 Modbus 协议在串行链路上的标准实现帧格式是地址 功能码 数据 CRC16。每个从机节点有一个唯一的地址主站发请求帧从机地址匹配后回响应帧。我用功能码 03 读保持寄存器来开放温度数据。保持寄存器规划如下寄存器地址内容说明0x0000本地温度整数部分例如 23℃0x0001本地温度小数部分例如 0.450℃0x0002设备状态bit0 传感器在线bit1 通信正常0x0003固件版本例如 0x0101 表示 v1.01温度用整数加小数两部分存是为了避免浮点数在 Modbus 寄存器里表示时的字节序争议。上位机拿到两个寄存器后拼成 23.450℃。这种方法最直观也最容易和第三方组态软件对接。Modbus 从机核心处理逻辑可以写成这样uint16_t crc16_modbus(uint8_t *data, uint16_t len) { uint16_t crc 0xFFFF; uint16_t i; while (len--) { crc ^ *data; for (i 0; i 8; i) { if (crc 0x0001) { crc (crc 1) ^ 0xA001; } else { crc 1; } } } return crc; } void modbus_rtu_poll(void) { uint8_t rxbuf[32]; uint16_t rxlen 0; uint16_t crc_rev, crc_cal; // 这里假设 USART 中断已经按帧接收到 rxbuf并解析出 rxlen if (rxlen 8) { return; } // 检查从机地址 if (rxbuf[0] ! SLAVE_ADDR) { return; } // 校验 CRC注意 Modbus RTU 的 CRC 低字节在前 crc_rev (uint16_t)(rxbuf[rxlen - 1] 8) | rxbuf[rxlen - 2]; crc_cal crc16_modbus(rxbuf, rxlen - 2); if (crc_rev ! crc_cal) { return; } // 功能码 03读保持寄存器 if (rxbuf[1] 0x03) { uint16_t start_reg (rxbuf[2] 8) | rxbuf[3]; uint16_t reg_count (rxbuf[4] 8) | rxbuf[5]; uint8_t resp[64]; uint8_t pos 0; uint16_t crc_send; resp[pos] SLAVE_ADDR; resp[pos] 0x03; resp[pos] (uint8_t)(reg_count * 2); for (uint16_t i 0; i reg_count; i) { uint16_t reg_val get_holding_register(start_reg i); resp[pos] (uint8_t)(reg_val 8); resp[pos] (uint8_t)(reg_val 0xFF); } crc_send crc16_modbus(resp, pos); resp[pos] (uint8_t)(crc_send 0xFF); resp[pos] (uint8_t)(crc_send 8); // 发送响应 usart_send_bytes(resp, pos); } }CRC16 的实现网上有很多版本我每次都是拿一个已知帧去验证比如请求帧01 03 00 00 00 02 C4 0B如果算出来的 CRC 等于 C4 0B说明算法正确。这个习惯非常重要因为 CRC 写错会导致所有从机都不响应而排查 CRC 问题非常费时间。从机地址、波特率这些参数我习惯用配置项放在程序开头方便现场更改。波特率固定用 9600 或者 19200。HVAC 项目对速度要求不高9600 反而抗干扰更好因为同样一帧数据占的时间更长抗瞬时干扰能力更强。5. 实测过程与数据表现5.1 本地测温精度测试硬件焊接完、驱动跑通后要做系统的温度准确性验证。我把节点板和一颗经过计量的标准铂电阻温度计放在同一个恒温环境里分别测了三个温度点冰水混合物 0℃、室温 25℃、恒温槽 50℃。实测结果大概是这样标准温度℃PJ85718DM 读数℃偏差℃0.000.250.2525.0024.80-0.2050.0050.150.15单颗芯片的偏差在 ±0.25℃ 左右满足 HVAC 环境监测的 ±1℃ 要求。如果你碰到偏差比较固定且大头在同一方向的可以先做软件校准。校准方法很简单就是两点校正冰水混合物是天然的 0℃ 标准器再把传感器放到一个稳定的温水槽里用高精度温度计记录实际温度然后算出增益系数和偏移量。公式就是标准的线性修正修正值 原始读数 * 增益 偏移先测到两个点的原始读数和标准温度解二元一次方程组就能算出增益和偏移。校准参数存到 STM32 的 Flash 里每次上电读取这样传感器一致性就能拉平。5.2 远程读取验证远程通信这块我用 USART 转 USB 线把主站和从机连起来先用 PC 上的串口工具直接发 Modbus 帧测试。给从机 1 发读取帧请求01 03 00 00 00 02 C4 0B从机响应01 03 04 00 17 00 0F CRC解析一下数据寄存器 0x0000 是 0x0017十进制 23表示 23℃寄存器 0x0001 是 0x000F十进制 15表示 0.015℃这里要看你小数部分是存多少位。如果约定小数部分存的是千分位那 0x000F 就是 0.015℃不太对应该等于 0.450℃。这里我特意提醒一下两个寄存器拼接时必须确认高位在前还是低位在前以及小数位数的约定。我在项目里习惯用“整数部分 千分位小数部分”比如 23.450℃ 就存成寄存器 0x0000 23寄存器 0x0001 450。这样既不会丢精度上位机拼接也简单。测试时如果发现温度差得离谱先查是不是这里拼接错了而不是怀疑协议写错。5.3 现场安装位置与热耦合技巧HVAC 项目里测温点位选在哪对控制效果的影响比传感器精度还大。我的体会是“测得到”不等于“测得准”。比如回风温度传感器如果离送回风口太近测到的其实是混合后的温度而不是房间典型温度风道温度传感器如果贴在外壁上测量的其实是管道壁温度跟空气温度差好几度。安装时一般要把传感器的感温部分尽量伸进气流中间或者紧贴管壁并加导热硅脂。如果传感器探头装在铝制套管里套管和传感器之间一定要填充导热材料空气层的导热系数很低会导致响应变慢、读数滞后。另一个容易忽略的是太阳辐射。室外补偿温度探头如果被阳光直射读数会偏高好几度必须加遮阳罩。我见过一个项目室外探头装在屋面中午比实际温度高 5℃导致系统不停地调节最后排查了半天才发现是太阳直射的问题。6. 常见问题与排查技巧实录6.1 读不到温度或温度跳变症状是 I2C 读回的数值要么一直是 0xFF要么值明显乱跳。排查顺序我建议按电流从外到内走。先用示波器或万用表量传感器 VDD 电压确认是 3.3V 而不是 2.8V 之类。接着量 SCL 和 SDA 的波形看有没有上下拉电阻。如果没有上拉I2C 总线根本拉不高读取必然失败。如果波形正常但读值乱跳多半是电源噪声。在传感器 VDD 和 GND 之间焊一个 10uF 电解电容和一个 0.1uF 陶瓷电容跳变问题通常能消除大半。还要看一下你的 I2C 时钟是不是在传感器允许的范围内。有些传感器最高只支持 400kHz你把它挂到 1MHz 就觉得“反正都是 I2C 应该能跑”这是不行的。6.2 远程通信不稳定RS485 通信不稳定是我在 HVAC 现场遇到最多的问题。典型表现是主站偶尔收不到响应或者收到的数据 CRC 校验失败。第一步检查 A、B 两根线是不是接反了。接反了通常完全不通但如果收发器内置偏置电阻有时也能通只是信号余量很差距离一长就周期性丢包。这种情况我用万用表量 A、B 间的电压正常空闲时在 0.2V 到 0.5V 左右如果接近 0V 或者负值基本判定接反或者缺少终端电阻。第二步检查终端电阻。挂两个节点以上且距离超过 50m总线两端必须各并一个 120Ω 电阻。注意是“两端”不是每个节点都接。如果每个节点都接了 120Ω总线上并联电阻会太小收发器负载过重信号幅度被拉低照样丢包。第三步是检查接地。RS485 总线最好用屏蔽双绞线屏蔽层在主机侧单点接地。如果现场噪声特别强比如旁边有变频器可以考虑在 A、B 之间加 TVS 管同时串联两个 10Ω 电阻限制电流尖峰。6.3 校准方法与系统联调建议校准出来的参数要能覆盖传感器本身的分散性。生产线批量校准时不能只校单点因为单点校准只能修正偏移没法修正斜率。两点校准时第一点尽量靠近实际工作范围的下限第二点靠近上限这样全量程内误差最小。系统联调时我建议先做“最小系统调试”一块主控板、一块从机板、一个传感器把从 I2C 读到最终 RS485 返回的全链路跑通再逐步加节点。一次就把 10 个节点全挂上去出了问题很难定位。另外给每块从机板刷写地址时最好用一个独立的小工具。地址重复是 Modbus 通信中非常隐蔽的问题两个相同地址的从机同时响应主站收到的数据就是乱的而且 CRC 校验时好时坏排查起来极其痛苦。我现在的习惯是在板子出厂前写好地址标签并在软件里做一次地址冲突检测每次上电时从机在总线上收到比自己地址低的所有节点都无响应后才允许进入工作状态。这个逻辑虽然简单但能省掉很多现场问题。还有个细节不要忽视看门狗。HVAC 现场偶尔会有非常强的电源跌落或电磁干扰导致 MCU 跑飞。没有独立看门狗的话从机可能一直死在那里主站怎么叫都不应。我将独立看门狗超时设成 3 秒正常工作状态下不停喂狗一旦死机就自动复位。这个功能看似不起眼但整个项目在客户现场运行半年后你就会知道它有多重要。说到这我再分享一点自己的体会这类测温项目真正体现功夫的地方往往不在芯片有多高级而在于把底层细节弄扎实。I2C 上拉、滤波窗口、CRC 校验、终端电阻、安装位置每一处看起来都是小事但每一处都可能在现场放大成故障。先保证数据采集可信再谈通信稳定最后做精度修正按这个顺序去做项目的成功率会高很多。如果你也正在做类似的嵌入式或 HVAC 温度监测方案建议第一版先按我这套思路搭起来跑通之后再去优化成本和尺寸。后面你还可以在这个基础上扩展更多功能比如增加两路 PWM 控制风机、加入在线校准、对接以太网网关等。等这些点都补齐了它就不仅仅是个温度采集节点而是一个完整的 HVAC 边缘控制器了。
返回列表
PREV
查看更多资讯
NEXT
返回资讯列表