ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

服务器机柜RJ45以太网温湿度变送器开发实战

服务器机柜RJ45以太网温湿度变送器开发实战 这次做服务器机柜内部监测的小型RJ45以太网温湿度变送器最初的动机是被一次凌晨的告警电话给逼出来的。机房空调回风温度显示正常可某台服务器的进风口温度已经飙到38度风扇转速长期拉满。查了一圈发现是机柜背部气流被线缆堵了大半形成了局部热点。这件事让我意识到机柜级温湿度监测应该是小设备能干的事不一定非要上大而全的动环系统。把温湿度传感器、MCU、以太网接口和防护电路做进一块不到四厘米见方的PCB插在机柜内部空闲位置通过RJ45网口用标准以太网协议把数据送进监控平台这就是整个项目的核心。这篇笔记记录我从硬件选型、EMC防护、小型化layout到固件协议的全过程也把过程中踩过的坑一并写出来给正在做同类嵌入式联网设备的工程师当个参考。1. 项目缘起机柜空间里的局部热点与测量盲区1.1 一个“假报警”背后的真实故障先说那次告警。客户机房报告某机柜温度异常动环平台上显示的是空调回风温度26度完全正常。但现场运维人员用手背贴着服务器前面板一摸明显烫手赶紧打开机柜门用红外测温枪扫了一遍——前门中上部进风口已经到38.2度而后背板出风口只有31度。这种“空调显示正常、机柜内局部超温”的情况比整个机房过热还难排查因为动环系统测量的是环境的平均状态机柜内部的空气流动、线缆阻挡、服务器散热风道互相影响某个缝隙里就是能闷出一个热点。后来我们把机柜里的线缆重新理了一遍热点才消失。但这件事说明一个问题服务器机柜内部的环境参数不能靠机房级的传感器去推测。机柜是一个半封闭的小空间前门进风、后门排风气流路径稍微被堵一点局部温度就能差到十度以上。服务器的风扇转速、CPU负载、电源转换效率都会叠加到这个局部环境里任何一个环节出状况最先被影响的就是邻近服务器的进风口温度。所以这个项目的需求非常明确做一个体积尽量小的温湿度监测设备部署位置直接放进机柜内部——可以贴在机柜前门内侧的立柱上也可以塞在服务器之间的空隙里甚至挂在理线架上。数量多、体积小、成本低、组网方便这四个条件同时满足才是这个项目真正的难点。1.2 为什么是RJ45以太网而不是RS485、WiFi或ZigBee先说RS485。工业现场测点用RS485很成熟一条总线挂几十个节点布线简单。但缺点也直接每个测点需要单独拉一条信号线到采集器还要考虑终端电阻、地址分配在机柜环境里布线就是给自己找麻烦。而且RS485是半双工轮询机制采集器需要不断轮询每个节点节点一多实时性就下降还要额外配一个协议转换网关才能上网络平台。WiFi方案我也考虑过。机柜密集的机房2.4GHz频段干扰严重本身WiFi连接的稳定性就不如有线。另一个问题是功耗和认证——WiFi模块入网要做一堆配置嵌入式设备一旦部署到现场没人愿意对着模块搞配网。ZigBee、LoRa这类无线方案要额外搭建网关对单机柜几十个测点来说性价比不高而且无线信号在金属机柜里的衰减非常厉害实测隔着两层服务器机箱信号强度能掉一半以上。反而以太网是最自然的方案。机房本来就有大量空闲的网口和交换机资源RJ45接口随处可得插上就能通不需要额外网关不需要配网PoE还能顺便解决供电。只要把温湿度数据封装成标准协议Modbus TCP或简单的私有TCP协议监控平台直接通过网络读取就行。更重要的是以太网变送器在机房这种环境里可以用现成的网线布线和服务器共享交换机网络拓扑天然就是星型故障点隔离清晰一个测点断线不影响其他测点。于是方案定了RJ45以太网接口 以太网协议栈芯片 低功耗MCU 温湿度传感器做一台插网线即用的机柜内部温湿度变送器。2. 嵌入式硬件选型把传感器和网络接口压缩进一枚RJ45的空间2.1 温湿度传感器SHT30与候选方案的取舍温湿度传感器看起来是小问题实际上对长期运行稳定性影响最大。我对比过几款常见型号型号接口精度典型特点SHT30I2C±0.3°C / ±2%RH内置加热器带CRC校验功耗低HTU21DI2C±0.3°C / ±2%RH老牌校准系数烧录在内部AHT20I2C±0.3°C / ±2%RH国产价格低但供货波动大SHT40I2C±0.2°C / ±1.8%RH封装更小价格略高最终选了SHT30。原因有三个一是它内部带CRC数据校验I2C读回来的每个数据字都有校验字节长期使用出现单bit错误能被识别出来这对监测设备很重要毕竟谁也不想看到监控平台上一个突兀的-40度假告警二是它的测量命令可以直接读到温度、湿度两个值不需要额外的转换计算也支持周期测量模式固件写起来省事三是SHT30的工作电压范围宽2.4V-5.5V配合低功耗MCU可以直接3.3V供电省掉一路LDO。SHT30的I2C地址默认是0x44ADDR引脚接地如果ADDR接高就是0x45。一个I2C总线上最多挂两个对单点温湿度变送器来说完全够用。后面我会详细讲驱动和CRC校验的实现。2.2 以太网接入为什么选中W5500而不是内置MAC外接PHY把以太网功能加进嵌入式设备有几种主流做法。第一种是单片机内置MAC外接PHY芯片比如STM32F407加LAN8720A。这种方案灵活性能上限高还能跑轻量级TCP/IP协议栈lwIP、FreeRTOSTCP但坏处也很清楚协议栈运行在MCU上要占用大量RAM和Flash调试起来链路长——MAC、DMA描述符、PHY寄存器、链路状态轮询任何一个环节出问题都够查一天。对一台只跑一个TCP连接的温湿度变送器来说这种复杂度不值得。第二种是用串口转以太网模块比如用ESP8266的AT固件或者专门的串口转以太网模块。这种方案开发最快但问题在于体积和稳定性模块本身不小而且AT指令交互方式在长时间运行时偶尔会出现响应卡顿需要额外做超时重发。对于工业监测设备我不太信任这种“黑盒”方案。第三种就是W5500这颗芯片。它把TCP/IP协议栈用硬件实现了MCU通过SPI接口直接读写socket寄存器就能完成TCP连接。MCU这边的负载非常轻不需要跑协议栈RAM占用只有几十KB。W5500的SPI时钟可以跑到40MHz以上实际传输一个温湿度数据包几十字节毫无压力。W5500还自带8个独立socket这意味着同一个芯片上可以同时开多个TCP连接比如一个连接给Modbus TCP轮询另一个连接给主动上报通道互不干扰。这个特性在后续做断线重连和主动告警时非常有用。选型对比汇总一下方案MCU负载开发成本体积稳定性MCU内置MAC 外部PHY高复杂小依赖软件协议栈串口转以太网模块低简单大一般W5500低中等小高硬件协议栈最终方案MCU用STM32L051低功耗内置IWDG工作电流低以太网用W5500传感器SHT30RJ45用集成变压器的连接器。2.3 RJ45连接器与变压器集成式还是分离式RJ45接口和网络变压器有两种组合方式一种是分离式RJ45座子加独立的网络变压器比如20F001N、HX1188NL另一种是集成式RJ45座子内部自带变压器和共模电感比如HR911105A、J0011D21B等。从EMC和设计便利性角度看集成式明显更适合这种小型化项目。分离式变压器虽然在某些高端设备里提供了更大的设计自由度但会增加主板面积和接线复杂度。集成式RJ45把变压器、共模电感和LED指示灯都封装在连接器内部PCB外围只需要加TVS和Bob Smith终端电阻而且连接器后部就是安装螺丝孔位正好用来固定整块板卡。选集成式RJ45还有一个隐性好处变压器内部隔离了差分信号和PHY之间的共模通路抗共模干扰能力强很多对EMC测试有很大帮助。我选的是带金属屏蔽壳的型号塑料壳体的RJ45在高频噪声环境下表现不如金属屏蔽壳稳定。金属屏蔽壳的接地脚一定要处理好这个我放到EMC那一节细说。2.4 电源部分的小心思板卡供电我一开始想得很简单5V进来一片AMS1117-3.3就够了。实际上这个方案在实验室没问题到了机房就暴露问题机柜里经常有服务器电源、UPS等强干扰源市电线缆和信号线缆交织5V电源线上会耦合进不少毛刺。AMS1117这种线性稳压器的电源抑制比在高频段并不理想毛刺会直接穿到3.3V上导致W5500偶发丢包。后面改成了两级滤波第一级是磁珠加钽电容吸收高频噪声第二级才是LDO并在输出端并联0.1uF和10uF电容。实测在同一个机柜里丢包率从改造前的0.3%降到0.01%以下。这个细节看起来不起眼但对长期稳定性影响非常大。3. RJ45接口EMC防护电路设计与实测3.1 干扰从哪里来一场雷雨天的顿悟第一次打样回来我在办公室桌子上测试一切正常就把板子拿到机房去放。结果一场雷雨过后三块板子里有两块W5500的寄存器读取出错再重启就恢复不了。排查了一整天才定位到RJ45接口上雷击和静电虽然没有直接把芯片打坏但通过网线耦合进来的共模浪涌电压把W5500的PHY引脚打出了不可恢复的内部闩锁。这个教训告诉我EMC防护不能只靠实验室的想象。机柜内部的网线虽然是短距离布线但这些网线最终都会连到交换机的对端——连接部署在建筑物不同位置的设备等效于把整栋楼的感应雷击能量引到了你的板子上。此外机房运维人员插拔网线时会产生静电人体静电放电ESD的电压可以高达几千伏直接打在外露的RJ45金属屏蔽壳上。3.2 防护电路设计三级防御的具体参数RJ45以太网口的防护电路标准做法是三级防御结构。第一级是共模电感CM Choke第二级是TVS瞬态抑制二极管阵列第三级是网络变压器内部的隔离和Bob Smith终端匹配。我实际采用的电路如下。先说TVS选型。以太网线对的耐受电压不只是看击穿电压还要看钳位电压和结电容。我选的是PESD5V0S1UB或者SM712这类专用于以太网的TVS阵列单芯片集成两对差分线的保护结电容低于5pF不会明显损伤100M以太网的信号眼图。TVS的位置要尽量靠近RJ45连接器走线越短越好否则引线电感会削弱钳位效果。然后是共模电感。共模电感选和W5500匹配的型号感值在100uH左右额定电流大于100mA。它在正常工作状态对差分信号几乎没有影响差分电流产生的磁通相互抵消但对共模干扰呈现高阻抗能挡住相当一部分共模浪涌。第三是Bob Smith终端网络。变压器中心抽头通过一组电阻电容接到一个公共点这个网络上并接一个高压电容到机壳地。具体做法是每个变压器的4根中心抽头对应两对差分线各接一个75欧姆电阻到一个公共节点公共节点再串一个1000pF/2kV高压电容电容另一端接机壳地RJ45金属屏蔽壳。这个网络的目的是给共模噪声一个低阻抗泄放路径同时让差分信号的回流路径更干净。下面是防护电路的关键参数表防护器件参数放置位置作用共模电感100uH / 100mA变压器LAN侧之后抑制共模噪声TVS阵列击穿电压5V结电容5pF最靠近RJ45引脚钳位浪涌电压Bob Smith电阻75Ω x4变压器中心抽头共模泄放高压电容1000pF / 2kV公共节点到机壳地隔离直流泄放高频共模3.3 机壳地、信号地和PCB布局金属RJ45的屏蔽壳接地问题我最初直接把屏蔽壳连接到PCB的GND结果EMC测试时辐射发射超标。原因是机壳地和信号地直接相连网线上的共模噪声会通过PCB地平面直接耦合进W5500的芯片地等于把外部干扰引入了内部。正确做法是把RJ45金属壳地用一颗1MΩ电阻并联1000pF/2kV电容接到信号地。高压电容负责把高频共模噪声旁路到信号地泄放高阻电阻则防止低频地环路电流的形成。同时PCB layout上还要保证防护器件、变压器和W5500之间的走线尽可能短差分对走线控制在100Ω±10%的阻抗并在W5500的差分对附近加一个2.2uF的去耦电容。改造完防护电路我把板子送去做静电放电和浪涌测试接触放电±6kV、空气放电±8kV、浪涌±1kV都能通过。这块板子在雷雨天再也没出现过掉线问题。4. 小型化PCB设计与结构实现4.1 把板卡压缩到60mm x 35mm的规划思路小型化是这个项目的核心诉求之一。机柜内部的可用空间其实很紧张前立柱附近的空隙通常只有几十毫米宽。我最终把PCB尺寸定在60mm x 35mm厚度1.6mm正好可以贴着机柜立柱安装。板级规划的思路是RJ45集成连接器放在板子的一端占掉大约25mm x 16mm的面积另一端放MCU和传感器中间夹着W5500、电源和防护电路。元器件封装尽量用0402和0603排布时把模拟部分SHT30、数字部分STM32、W5500和接口部分RJ45、防护电路三个区域严格分开避免数字高频信号串扰到传感器信号上。这里有一个经验教训第一版我把SHT30贴在了板子中央被W5500的走线包围实测湿度读数在板卡运行一小时之后明显偏高3-4%RH——板上自发热和数字器件散的热直接加热了传感器。后面我把传感器挪到了板子边缘下面架空处理读数才恢复正常。4.2 传感器探头的放置远离发热源才是关键温湿度变送器最大的坑是传感器受自身板卡热量干扰。MCU和W5500工作时会有几十毫瓦甚至上百毫瓦的功耗如果传感器离这些器件太近测出来的温度永远是“板卡温度”而不是“环境温度”。解决方案有三个组合一是传感器放在板子的最远端远离MCU和W5500二是在传感器底下开一个散热窗PCB镂空让空气可以直接流过传感器背面的通风孔三是如果结构允许用一根软排线把传感器外置成探头形态但会增加体积和成本不适合“小体积”这个定位。我实测过不同位置的温升差异把传感器放在板子中央时温度读数比环境温度高了1.8度放到板子边缘且架空之后误差降到0.3度以内。这个0.3度基本就是传感器自身精度和气流对流导致的可以接受。4.3 供电方案外部DC还是PoE机柜内部要解决供电最常见的路径是PoE以太网供电。W5500本身不带PoE功能需要额外加PoE PD控制器和隔离DC-DC比如Si3402加一颗反激或者非隔离Buck。这会让板卡面积增大很多和“小型化”的目标冲突。这个项目的定位是贴装式小变送器我更倾向于用外部DC供电即板端留一个DC接口或者两线接线端子支持6-24V宽压输入。宽压输入的逻辑是机柜里各种电压都有能用现成的直流电源直接带。内部用降压芯片MP2451或SY2109这种宽压Buck把6-24V转成3.3V效率比线性稳压高发热小。PoE方案我也在评估第二版。如果后期客户需求明确要求“只用网线供电”我会选用一颗低成本的PD控制器搭配非隔离Buck尽量把PoE供电部分做在RJ45连接器之后、防护电路之间。这不是一个轻松的活儿因为PoE供电的隔离和EMC处理比普通直流更严格需要专门的变压器和布局。5. 固件与协议实现从I2C读温湿度到Modbus TCP上报5.1 SHT30驱动、CRC校验与数据滤波SHT30的驱动很简单I2C发送命令0x2C 0x06高重复性测量之后读取6字节数据2字节温度、1字节CRC2字节湿度、1字节CRC。温度计算公式是-45 175 * raw/65535湿度公式是100 * raw/65535。说一个容易踩的坑SHT30在华氏温度模式下和摄氏温度模式下输出的系数不一样出厂默认是摄氏模式但如果你之前用其他传感器项目的代码改过来很容易把寄存器配置设成华氏模式导致温度整体偏差很大。我在固件初始化时强制写入摄氏模式配置0x60 0x00实际是周期测量模式配置确保每次上电都是稳定状态。CRC校验的多项式是0x31初值0xFF算法是CRC-8。我写过一段很小的CRC校验函数读回来的数据先校验校验不过直接丢弃这一帧不参与后续平均uint8_t sht30_crc8(uint8_t *data, uint8_t len) { uint8_t crc 0xFF; for (uint8_t i 0; i len; i) { crc ^ data[i]; for (uint8_t j 0; j 8; j) { crc (crc 0x80) ? (crc 1) ^ 0x31 : crc 1; } } return crc; }这个校验在温度突变时特别有用——我曾见过一次机房电源浪涌导致SHT30读回一个明显非法的温度值正是CRC把它拦了下来。数据滤波用的是滑动平均取最近10次有效读数做中值滤波加平均。对于机柜这种温度变化缓慢的场景10次采样每次间隔2秒的滤波足够平滑又能保留灵敏性。湿度数据相对波动大滤波窗口可以适当加大到15次。5.2 寄存器映射与Modbus TCP协议实现监测设备要接入监控平台协议必须选市场上通用的。Modbus TCP是最保险的选择几乎所有动环监控平台和网络管理软件都支持。Modbus TCP基于TCP 502端口报文开头是6字节的MBAP头然后是功能码和数据区。我给变送器定义的寄存器映射如下寄存器地址类型内容说明0x0000保持寄存器温度值有符号16位单位0.1度0x0001保持寄存器湿度值无符号16位单位0.1%RH0x0002保持寄存器设备状态bit0-在线, bit1-传感器故障0x0003保持寄存器累计重启次数用于故障诊断Modbus TCP的从站实现我用的是W5500的socket0监听502端口。W5500硬件协议栈会自动处理TCP的握手和拆包MCU只需要循环检查socket0接收缓冲区里是否有完整报文读出来解析MBAP头然后按功能码处理请求、回写响应。实现过程中要注意两点一是W5500的接收缓冲区要开够大至少2KB否则Modbus报文几十字节没问题但如果有其他TCP连接同时通信缓冲区不足会导致丢包二是要注意Modbus报文里的寄存器地址是大端序而MCU处理时如果用了小端结构体会在解析时把字节序颠倒这个错误第一次调试时花了整个下午才定位。5.3 断线重连、看门狗与长时间稳定性以太网设备最怕的就是“假在线”——TCP连接还挂着但对端已经不理你了。W5500硬件协议栈虽然稳定但网络环境不是自己能控制的对端服务器重启、交换机端口被重新配置、网线被误拔任何一种情况都可能导致socket状态异常。我在固件里做了三个层次的可靠性保障。第一层是链路层检测周期读取W5500的PHY链路状态寄存器如果检测到网线断开立即关闭socket0等链路恢复后再重新监听。这一层的反应速度最快50ms内就能感知。第二层是应用层超时每5秒向对端服务器发送一个心跳报文如果连续3次没有收到响应主动关闭socket0并重新建立连接。这比TCP半开连接的超时机制要快得多也容易控制。第三层是硬件看门狗STM32L051内置的IWDG超时时间设为4秒主循环每2秒喂狗一次。万一固件中有任何一次死循环看门狗会在4秒内复位MCU复位后重新初始化W5500设备自动恢复在线。这个机制的代价是重启后传感器的平均滤波数据需要重新积累所以我在状态寄存器里记录了重启次数方便运维人员判断是否发生了多次自动复位。6. 实测校准与机柜部署经验6.1 温湿度校准不能只信出厂值SHT30出厂校准精度在±0.3度/±2%RH对大多数场景够用但如果你想做到更高置信度或者传感器焊接过程中的热量导致参数漂移就需要做二次校准。我搭了个简单的校准环境一个恒温恒湿箱一台参考级的温湿度计精度±0.1度/±0.8%RH把变送器和参考计同时放进箱内分别在25度/50%RH、40度/80%RH两个点做对比。用两点线性校准的方式修正读数的offset校准后的温度 实测温度 * 斜率 偏移。实际校准中发现湿度在中高湿度段的非线性比低湿度段明显因此除了两点线性校准还要在湿度60%-80%区间加一个补偿表。这个补偿表可以提前烧录在EEPROM里单片机每次上电读出来应用。6.2 机柜内实测同一机柜不同位置的温度差我把几台变送器分别部署在一个标准42U机柜的前门、中部和后门位置连续采集了48小时。实测数据显示前门进风区24.5度左右中部27度左右后门排气区32度左右。同一个机柜内垂直方向的温差超过7度如果要精确掌握某台服务器的进风温度传感器的位置就得贴到服务器前部。另外一个发现是湿度波动机柜内的相对湿度一天内的波动幅度可以达到15%RH。这主要是因为空调除湿的启停周期以及服务器散热水汽的叠加。如果监控平台只设置了一个笼统的湿度阈值比如40%-60%会频繁触发误告警建议把湿度告警做成短时平均值判断。6.3 几个真实踩坑记录这里整理几个调试过程中印象最深的坑都是常规文档里不会写的。第一个是W5500的芯片版本问题。不同批次的W5500在PHY寄存器的默认值上有细微差异有个版本的link状态寄存器默认值是0x00导致我读状态判断“link is down”然后主动断开socket实际网线是通的表现为每10分钟掉线一次。这个问题排查了很久最后通过对比不同芯片的规格书寄存映射才定位。第二个是SHT30在I2C开始信号前必须留出足够的上电稳定时间。SHT30在VDD上电后至少需要1ms的稳定时间才能响应I2C命令否则第一个ACK会不返回MCU如果没做重试机制就会永久卡在I2C等待处。我在固件里加了一个上电延迟和最多3次的重试之后再没出现过初始化失败。第三个是RJ45集成变压器中心的Bob Smith网络不能用模拟地AGND连接要用信号地。第一版原理图我把公共节点接到了AGND导致网线插拔时偶尔会出现PHY芯片的电压跌落。改成信号地之后问题消失这其实也印证了前面EMC一节讲的机壳地、信号地、模拟地要严格分开的原则。还有一个关于部署的细节变送器的网口建议用质量好的成品网线不要自己手打水晶头。手打水晶头的线序或者压接质量不好会造成对绞线的回波损耗增大虽然短距离通信不会出错但对EMC性能和长期稳定性有潜在影响。经过这几轮迭代这台变送器已在我的一个实验机柜里连续运行了三个月没有出现过一次掉线也没有一次因传感器故障导致的误报。目前的固件已经加入了远程升级功能通过简单的TCP文件传输协议后续可以把校准参数和滤波算法都做成在线可调这样运维人员就不用爬到机柜里改参数了。在最开始的那次“假报警”机柜里同样装了这种变送器现在监控平台上能直接看到进风、出风两个测点的实时温差曲线哪台服务器的散热风道出问题一眼就能看出来。这类小玩意不是高难度的黑科技但把传感器选型、EMC防护、小型化布局和协议对接每一环都做扎实了它就能在机柜里安安静静地跑上一整年。
RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进