
做温控仪表这些年我越来越觉得温度测量本身并不玄但想把精度、稳定性和成本同时拿下细节一个都不能省。最近用ADS122U04IPWR搭配PIC18LF47K40搭了一套双通道温度采集单元目标很明确覆盖工业现场的 PT100/PT1000 和 HVAC 系统里常用的 K 型热电偶。整套方案做下来包括硬件电路、寄存器配置、温度换算、校准流程和现场排错都有不少值得记录的地方这里把完整思路写出来给正在做同类仪表的工程师当个参考。ADS122U04IPWR 是 TI 的 24 位 Δ-Σ ADC和常见的 ADS1220 相比它最大的不同是带 UART 接口对 MCU 的 IO 占用更少也方便做隔离或者远距离传输。PIC18LF47K40 则是 Microchip 的 8 位低功耗 MCU内置多个串口、EEPROM 和强大的休眠模式两者配合做温度采集模块硬件结构非常简洁。这篇博文涉及的内容适合三类读者准备做温控仪表或数据采集板的嵌入式工程师、做 HVAC 楼宇自控的集成商、以及想自己动手搭高精度测温电路的学习者。1. 方案选型为什么是 ADS122U04IPWR 和 PIC18LF47K401.1 模数转换前端的核心需求工业和 HVAC 的温度测量传感器类型基本就几种工业现场大量使用 PT100、PT1000 这类铂电阻HVAC 里除了铂电阻还常见 NTC 热敏电阻高温场合则用 K 型、J 型热电偶。它们的共同特点是输出信号都很微弱——PT100 在 0℃ 时只有 100Ω用 500µA 激励电流也只产生 50mV 电压热电偶更是只有几十毫伏的量级。MCU 自带的 12 位 ADC 在这种信号面前显得力不从心想做到 0.1℃ 分辨率前端就必须具备低噪声、可编程增益放大和稳定基准这几个能力。ADS122U04IPWR 正好把这些都集成在一个芯片里24 位 Δ-Σ 转换内核、可编程增益放大器、两个可编程激励电流源、内部基准和温度传感器都有。更关键的是它用 UART 通信四根线就能和 MCU 对接。我在早期项目里用 SPI 接口的 ADS1220虽然性能不错但 SPI 时序要求高走线一长就容易被干扰换成 UART 接口之后通信稳定性明显好处理特别是在模块化设计和隔离方案里UART 加数字隔离器是非常成熟的组合。1.2 MCU 选型的实际考量PIC18LF47K40 选择它不是因为性能有多炸裂而是在这个应用场景里非常合适。它有 32KB Flash、3.7KB SRAM 和 256B 数据 EEPROM存储温度校准系数、设备地址这些参数绰绰有余。内部振荡器精度在 ±1% 左右做传感器采集这种对时间精度不敏感的应用完全够用省掉一颗外部晶振成本和 PCB 面积都能压下来。而且它工作在 1.8V 到 3.6V 的电压范围和 ADS122U04IPWR 共用 3.3V 供电非常方便整板功耗可以做到很低。另外一个让我倾向它的原因是开发效率。PIC18LF47K40 支持 XC8 编译器内部外设丰富有两个 UART 模块一个和 ADC 通信另一个留给 RS485 或 Modbus 通讯主控芯片一颗搞定。对于 HVAC 这类需要组网的项目省掉额外通讯 MCU 的物料成本还是很可观的。当然了如果你更熟悉 STM32 或者 AVR思路完全一样UART 接口的 ADC 对 MCU 没有强烈绑定这一步按团队熟练度选型就好。1.3 整体系统框架整套采集模块可以拆成几个部分传感器接口、模拟前端、数字控制与算法、对外通讯。传感器接口部分要兼容 RTD 和热电偶RTD 走三线制接法热电偶走差分输入加冷端补偿。模拟前端由 ADS122U04IPWR 完成信号放大和模数转换。PIC18LF47K40 负责控制 ADC 的工作状态、读取转换结果、做温度线性化计算然后通过 RS485 或者 4-20mA 输出到上位机。电源部分用 3.3V 低噪声 LDO整个模块设计成可插拔端子结构方便现场更换传感器。这个架构最大的好处是模拟前端和数字处理彻底分离。ADC 芯片承担了所有与模拟信号打交道的工作MCU 只需处理数字结果就算传感器类型变了换一组寄存器配置就能适配硬件改动很小。RTD 和热电偶共用一个 ADC 前端也节省了不少 Bill of Materials 成本。2. 硬件设计细节与参数计算2.1 RTD 三线制比例式测量电路RTD 测温最怕的不是传感器自身精度而是导线电阻。施工现场的延长线经常有几十米铜导线每米电阻大约 0.01Ω20 米就是 0.2Ω对 PT100 来说这相当于约 0.5℃ 的误差绝对不能忽视。三线制接法配合 ADS122U04IPWR 的两个激励电流源可以把这个误差基本抵消。典型做法是RTD 的三根引线中两根分别接到 AIN0 和 AIN1另一根串联精密参考电阻 RREF 后接地。两个 IDAC 电流源分别从 RTD 的两端注入大小相等的电流这样两根长导线上的压降在差分测量中方向相反相互抵消。RREF 两端的电压同时作为 ADC 的参考电压这种比例式测量方式还有另一个好处——即使激励电流值存在漂移由于 RTD 电压和参考电压同比例变化最终转换结果不受影响。参数计算方面我的选择是激励电流 500µA参考电阻 RREF 取 1.8kΩPGA 增益设为 4。验证一下PT100 在 0℃ 时电压是 500µA×100Ω50mV在 400℃ 时约 500µA×257Ω128.5mV经过 4 倍放大后最大约 514mV。RREF 上的参考电压是 500µA×1.8kΩ900mV满足 PGA×V_RTD_max ≤ V_REF 的条件ADC 不会饱和。如果测温范围更大可以按公式 RREF ≥ PGA × R_RTD_max 核算增益降低或者把 RREF 加大都可以。需要特别注意的是 RREF 的温漂这个电阻直接决定参考电压的稳定性我选的是 0.1% 精度、温漂 5ppm/℃ 的金属箔电阻批量价格稍高但在工业现场值得投入。2.2 热电偶输入与冷端补偿设计热电偶和 RTD 不一样它输出的是毫伏级的热电动势K 型热电偶在 1000℃ 时也只有约 41mV。这种信号必须用高增益 PGA 放大我把热电偶通道配置成 PGA 增益 64接入差分输入 AIN2/AIN3满量程可以覆盖 K 型和 J 型热电偶的需求。冷端补偿是热电偶测量最容易翻车的地方。热电偶测到的是测量端与冷端的温差电动势要得到真实温度必须知道冷端也就是接线端子处的绝对温度。ADS122U04IPWR 内部自带温度传感器但实测精度大约 ±2℃折算到 K 型热电偶的补偿误差可能有 0.5℃ 到 1℃对于要求高的场景不够用。我的做法是在接线端子附近贴一个 PT1000用 ADC 的另一个通道单独测量精度可以做到 ±0.2℃ 以内。如果板子空间有限用 10kΩ NTC 加 Steinhart-Hart 公式也能接受但 NTC 的一致性不如铂电阻量产时需要在软件里逐个校准。输入端的滤波电路也不能随便省。我在 AIN2/AIN3 之前各串了一个 100Ω 电阻对地并联 0.1µF 电容组成低通滤波器截止频率大约 16kHz可以有效抑制高频辐射干扰。这个电阻值不宜太大否则会和热电偶内阻产生分压影响测量精度。热电偶屏蔽线的屏蔽层只在传感器一端接地另一端悬空避免形成地环路。2.3 电源、参考电压与 UART 接口电路ADS122U04IPWR 的模拟性能再高供电不干净等于白搭。整个采集板我用了一颗 LP5907 低压差线性稳压器输出 3.3V 给 ADC 模拟电源、参考电压、MCU 和 UART 接口供电。LP5907 的噪声典型值只有 6.5µVrms非常适合给高精度 ADC 供电。数字部分和模拟部分采用星形接地所有关键模拟信号的地都单独回到 LDO 输出电容的地端再接一个 0Ω 电阻连接到数字地平面避免数字开关噪声污染模拟地。PIC18LF47K40 和 ADS122U04IPWR 之间的 UART 接线我做了最简的四线连接TXD、RXD、DRDY、GND。ADS122U04IPWR 的 DRDY 引脚接到 PIC 的 RB0 外部中断引脚数据准备好之后 MCU 通过中断方式读取减少轮询对 CPU 的占用。需要注意的是两个芯片供电电压一致电平可以直接互连如果后续要做隔离方案可以在 UART 线上加一个 ISO7741 数字隔离器改成隔离电源供电这样模块就能直接用于高压工业现场了。3. 软件实现与温度换算算法3.1 ADS122U04IPWR 初始化与数据读取流程ADS122U04IPWR 的启动流程大致分为四步复位、写寄存器、启动转换、读数据。上电之后先延时 10ms 等待内部电路稳定然后发复位命令再延时 10ms。寄存器配置是整个初始化的核心主要设置输入多路选择、PGA 增益、激励电流源、基准电压和数据速率。我实测下来的配置思路是这样的RTD 模式差分输入 AIN0/AIN1PGA 增益 4激励电流 500µA基准选择外部 RREF 电压数据速率 20SPS。热电偶模式差分输入 AIN2/AIN3PGA 增益 64关闭激励电流基准选择内部基准数据速率 20SPS同时使能冷端 PT1000 通道。中断服务里读取数据时有一个很容易被忽略的细节必须在 DRDY 引脚拉低之后再读而且要先发读数命令紧接着连续接收三个字节顺序是高字节、中字节、低字节。三个字节拼成一个 24 位有符号数如果是负数还需要做符号扩展。下面这段代码是我在 XC8 环境里实际跑过的骨架寄存器值按你自己芯片的手册核对后再固化#include xc.h // 假设 DRDY 接到 RB0UART1 用于与 ADC 通信 #define ADS_DRDY PORTBbits.RB0 void ADS_WriteRegister(uint8_t reg, uint8_t val) { UART1_WriteByte(CMD_WREG); UART1_WriteByte(reg); UART1_WriteByte(1); // 写一个寄存器 UART1_WriteByte(val); } int32_t ADS_ReadRaw(void) { uint32_t raw 0; while (ADS_DRDY 1); // 等待数据就绪 UART1_WriteByte(CMD_RDATA); raw (uint32_t)UART1_ReadByte() 16; raw | (uint32_t)UART1_ReadByte() 8; raw | (uint32_t)UART1_ReadByte(); if (raw 0x800000UL) { raw | 0xFF000000UL; // 24 位负数符号扩展 } return (int32_t)raw; }实际项目里我不会在主循环里忙等 DRDY而是配置 RB0 下降沿中断DRDY 触发中断后置一个标志位主循环检测到标志位再调用 ADS_ReadRaw()这样 MCU 在等待转换期间可以去做显示刷新或者通讯处理不会造成资源浪费。3.2 RTD 原始码到温度的换算拿到 ADC 的原始码之后先要换算成电阻值。比例式测量的好处在这里就体现出来了公式非常简洁$$ R_{RTD} R_{REF} \times \frac{code}{0x7FFFFF \times PGA} $$其中 code 是经过符号扩展的 24 位 ADC 结果。以 0℃ 为例PT100 阻值 100ΩRREF 取 1800ΩPGA 取 4那么 code 100×0x7FFFFF×4/1800 ≈ 466033。反推回去就能得到电阻值。电阻值到温度的标准做法有两种。查表法最直接把 PT100 分度表按 10℃ 间隔做成常量数组运行时先定位到相邻两个温度点之间再做线性插值。10℃ 间隔下非线性误差大约 0.02℃ 以内绝大多数场景足够。如果要求更高或者想省 flash可以用 Callendar-Van Dusen 公式0℃ 以上用二次方程0℃ 以下加一个三次修正项然后用牛顿迭代法求解。我建议优先用查表法因为在 8 位 MCU 上浮点迭代计算时间较长查表加插值只需要几百字节 flash 和几个整数运算性价比高得多。还有一个小技巧RTD 计算不要直接在浮点数里反复做乘除可以先把系数缩放成整数再运算。比如把 RREF 1800Ω 放大 100 倍得到 180000电阻计算结果用定点数保存这样最终显示温度时只需要做一次浮点转换数值稳定性和速度都有提升。3.3 热电偶冷端补偿与反查温度热电偶的处理比 RTD 复杂一些核心在于冷端补偿。每次采样时先用 PT1000 通道测出冷端温度 T_cj然后查热电偶分度表得到 T_cj 对应的热电动势 E_cj把 E_cj 加上当前通道测得的 mV 值得到修正后的总电动势再用这个总值反查温度。这里的顺序不能反。很多人习惯先由热端电压直接查温度再把冷端温度加上去这在非线性较强的热电偶上会产生明显误差。K 型热电偶在低温段每度对应约 40µV高温段每度约 20µV线性化关系并非常数必须从电动势域做补偿再反查。具体实现上我用了 0℃ 到 1300℃ 每 10℃ 一个点的 K 型分度表把温度和对应电动势做成两个数组先查电动势插值定位区间再在温度区间做线性插值。实测在 400℃ 附近这种方法的非线性误差不超过 0.05℃。冷端 PT1000 的读数也需要滤波。热电偶端子位置靠近外壳容易受到环境温度波动影响我用移动平均滤波连续采 16 次取平均值再做一次一阶低通平滑。终端显示出来的冷端温度稳定在 ±0.1℃ 以内才能保证后面补偿的有效性。3.4 PIC18LF47K40 外围功能实现PIC18LF47K40 端除了和 ADC 通信还要负责对外通讯和参数存储。UART 初始化时我配置 9600bps、8 数据位、无校验、1 停止位波特率误差控制在 ±2% 以内就能稳定通信。如果使用内部振荡器建议先运行一次振荡器校准把 OSCTUNE 寄存器调整到最佳值否则 MCU 自身的时钟偏差叠加到 UART 采样上容易随机出错。存储方面校准系数、设备地址、通信参数都放在数据 EEPROM 里掉电不丢失。这里提醒一下PIC18LF47K40 的 EEPROM 写操作要关闭全局中断防止写入过程中被中断打断写完之后再打开中断。我在现场遇到过几次校准参数读到一半变成全 0xFF 的情况排查后发现就是写 EEPROM 过程中恰好来了串口中断把写周期中断了加上关中断操作之后问题消失。4. 校准流程与实测数据4.1 两点校准与多点校准实操任何高精度测温模块出厂前都必须校准。一套最简单的校准流程是先把模块和标准温度源同时放到恒温环境中等漂移稳定后记录 ADC 原始值和标准温度然后在另一个温度点做同样操作软件里算出斜率和截距写到 EEPROM。RTD 通道用精密电阻箱模拟传感器阻值比实际恒温槽更方便我常用 100Ω 和 300Ω 两个标准电阻分别模拟 0℃ 和约 176.9℃ 的 PT100 阻值两点校准后误差基本能控制在 ±0.05℃ 以内。热电偶通道校准则要用干井炉或冰点槽。0℃ 冰点槽做零点校准很简单把热电偶探头插进冰水混合物等待平衡后采集数据另一个点通常用干井炉设定 200℃ 或 500℃。校准系数同样保存为偏移量和增益调整因子。需要注意的是校准之后不要立刻关闭电源最好让模块继续通电一段时间观察数据是否稳定我遇到过某些样品在通电半小时后读数出现几十毫伏的漂移后来排查发现是板上某个电阻的热电动势在作祟这个问题下面细说。4.2 实验室与现场实测结果对比我这里放一组实验室实测数据环境温度 25℃模块连续上电 60 分钟后读数。PT100 通道使用精密电阻箱模拟传感器阻值K 型热电偶通道使用干井炉设定温度数据是 64 次采样的平均值设定温度/阻值实测读数绝对误差重复性(±)0℃ / 100.00Ω100.02Ω0.02℃0.008℃25℃ / 109.73Ω109.71Ω-0.02℃0.010℃100℃ / 138.51Ω138.55Ω0.04℃0.012℃K型 0℃0.12℃0.12℃0.10℃K型 200℃200.18℃0.18℃0.10℃K型 500℃499.82℃-0.18℃0.15℃RTD 通道的精度主要靠 RREF 和校准质量现场情况看只要延长线做好三线制连接100 米以内的误差增加不超过 0.05℃。热电偶通道误差来源比较复杂冷端补偿精度占了很大一块实测冷端温度误差在 ±0.2℃ 时总误差约增大 ±0.1℃。4.3 噪声指标与滤波策略ADS122U04IPWR 在 20SPS 数据速率下有效分辨率大概能做到 20 位以上但那是理想指标实际板子上的噪声主要来自 LDO 纹波、参考电阻热噪声和数字信号耦合。我实测 RTD 通道在 20SPS 时的峰峰值噪声大约 3 到 5 个 LSB对应温度约 ±0.01℃。这个水平已经能满足大多数工业过程控制要求但如果直接上 330SPS 高数据速率峰峰值噪声会明显增大需要软件滤波配合。我的经验是固定用 20SPS 采样软件里再做 16 次滑动平均等效时间常数大约 0.8 秒HVAC 和工业过程控制都等得起。热电偶通道因信号变化较慢滤波和中值同时用先做中值滤掉偶发毛刺再做滑动平均。如果现场有变频器或者大功率电机温度采集距离又近建议在输入端加共模电感或者在 ADC 的供电脚再并一个 10µF 钽电容能压掉不少高频干扰。5. 常见问题与现场排查经验5.1 问题速查表现场调试总会遇到各种奇奇怪怪的现象最有效的排查方式是先确认信号链路本身是否正常再逐步往两端找。我把两类传感器最常遇到的问题整理成了速查表现象可能原因解决措施RTD 读数整体偏高导线电阻未被补偿检查是否按三线制接线两线制需要软件补偿RTD 读数缓慢漂移IDAC 激励电流过大引起自热降低激励电流到 250µA 或 100µA热电偶读数严重偏低冷端补偿未生效或测错位置确认冷端传感器紧贴端子并已使能热电偶读数跳动大屏蔽层两端都接地形成地环路屏蔽层只在传感器端单点接地UART 偶尔收到乱码内部振荡器偏差过大校准 OSCTUNE 或改用外部晶振数据读出来全是 0xFFFFFFADC 配置错误或未启动转换重新复位 ADC核对寄存器配置同一块板子换传感器后误差增大校准系数还是旧的换传感器类型后重新校准并写 EEPROM5.2 热电动势对测量的隐形影响这个坑我花了好几天才排查出来。模块在恒温箱里测试时数据很漂亮但一到现场温度稍微变化RTD 读数就出现几十 mΩ 量级的漂移。后来用毫伏表测 ADC 输入引脚发现输入端和接线端子之间产生了微小的直流电压而且随温度变化。问题根源是 PCB 走线中使用了不同金属材料焊点处形成热电偶效应再加上板子本身存在温度梯度就会在采样瞬间引入工频不相关的缓慢漂移。解决方法是尽量让两个输入端走线对称、等长铜箔和焊盘材料保持一致同时对这些敏感走线做包地处理。硬件定型之后再在软件里加入周期性自动校准每次上电先短接内部输入端测一次零点把这个零点偏移存下来后续实时补偿掉大部分热电动势误差。5.3 批量生产和一致性控制建议如果这个设计要走向量产我建议在产线上加两个测试工位一个用标准电阻模拟 RTD一个用标准毫伏源模拟热电偶逐台写入校准系数而不只是抽检。另外ADS122U04IPWR 和 PIC18LF47K40 的批次差异也会影响最终精度换批次之后最好重新统计一下零点偏移的分布不要用旧的经验值直接套。我在这个项目里最大体会是高精度测量系统七分靠硬件三分靠软件。ADS122U04IPWR 把模拟前端的底子打好了但参考电阻、电源、布线和冷端补偿这些地方偷了懒最终精度一定打折扣。特别是 RREF 和冷端测温这两个点看起来不起眼实际对长期稳定性的影响比 ADC 本身大得多。所有关键位置的元件选型、走线长度、屏蔽接地都值得在设计阶段多花时间。以后做类似项目时我还会沿用这套架构只是把传感器通道从两路扩展到八路配上 Modbus 协议就能直接服务更多现场设备。