1. 从一堆热词里看LoRa自组网的真实需求
先把标题拆开看:LoRa 自组网设备原理深度分析。这里面有三个关键词——LoRa、自组网、设备原理。热词列表里还混进来一堆 RS485、IAP、嵌入式、STM32WLE5、HC32L136 之类的词,说明关注这个话题的人,大概率是搞嵌入式硬件或者做工业现场通信的工程师,而不是纯做应用层开发的人。
我先把结论摆在前面:LoRa 自组网设备的核心价值,不是"通信距离远"这一个点,而是在无运营商网络覆盖、无固定供电、节点数量多且分散的场景下,用极低的功耗和极低的维护成本,把数据从末端节点汇聚到网关。这句话听起来像废话,但你真正做过现场部署就知道,能同时满足"远距离+低功耗+多节点+免布线"这四个条件的无线方案,其实没几个。
LoRa 本身的物理层特性决定了它的定位。它用的是扩频调制(Chirp Spread Spectrum),在相同发射功率下,接收灵敏度比传统 FSK 高出 20dB 左右。这个 20dB 是什么概念?发射端功率不变,接收端能多收到大约 10 倍的信号强度余量,或者说通信距离理论上能拉到原来的 3 倍以上。代价是速率低,典型配置下 125kHz 带宽、SF7 到 SF12,空中速率从 5.5kbps 一路降到 0.3kbps 左右。所以 LoRa 从来不是用来传视频、传大文件的,它就是传几十字节的传感器数据。
那"自组网"又是什么意思?很多人一听到自组网就想到 Mesh,觉得节点之间要互相转发、动态路由。但 LoRa 自组网在工业场景里,绝大多数实现其实是星型拓扑 + 中继扩展,而不是真正意义上的多跳 Mesh。原因很现实:LoRa 的占空比限制、信道冲突、路由维护开销,都会让多跳 Mesh 的复杂度急剧上升。一个 100 节点的 LoRa Mesh,光是路由表的同步和冲突退避就能把工程师折腾到怀疑人生。所以市面上能落地的 LoRa 自组网设备,通常是"网关 + 若干节点 + 可选中继"的结构,节点自动入网、自动分配地址、自动上报,网关负责汇聚和转发。
这篇文章我打算按实际做项目的思路来写:先讲整体架构怎么设计,再拆核心细节,然后是实操流程,最后是踩坑记录。适合正在选型 LoRa 方案、或者已经拿到模块但不知道怎么组网的嵌入式工程师看。如果你只是想调通两个模块之间的点对点通信,那这篇文章可能有点"重",但如果你要做的是几十上百个节点的现场部署,那下面的内容应该能帮你少走不少弯路。
2. 整体架构设计与方案选型思路
2.1 为什么大多数LoRa自组网最终都做成了星型
先讲一个我自己的经历。早年做过一个农业大棚的项目,客户一开始要求"节点之间能互相转发,最远的节点离网关有 3 公里"。我们当时兴致勃勃地设计了一套三跳 Mesh 路由,结果现场一测,问题全出来了:节点之间的链路质量随天气、作物高度、大棚金属骨架变化剧烈,路由表一天要重建好几次;而且 LoRa 的空中速率本来就低,每多一跳,延迟就翻倍,一个数据从最远节点到网关要等好几秒。
后来我们改成了星型 + 一个固定中继的方案,反而稳定了。原因很简单:LoRa 的链路预算足够大,在大多数现场,单跳就能覆盖 1 到 3 公里,真正需要多跳的场景其实很少。与其花大力气做动态路由,不如把网关的天线架高一点、把节点的发射功率调到位、把扩频因子选对。
所以现在我做 LoRa 自组网,默认架构是这样的:
- 网关(Gateway):负责汇聚所有节点数据,通过 4G、以太网或者 RS485 上行到服务器或本地控制器。网关通常用性能强一点的 MCU,比如 STM32F4 或者带 Linux 的方案。
- 节点(Node):末端传感器节点,MCU 用低功耗系列,比如 STM32WLE5(内置 LoRa 射频)、HC32L136、GD32 等,负责采集数据并定时上报。
- 中继(Repeater):可选,放在链路质量差的位置,做一次转发。中继可以是独立设备,也可以让某个供电充足的节点兼任。
这个架构的好处是逻辑简单、维护成本低、故障定位容易。坏处是网关的覆盖半径有限,超出范围的节点需要中继。但对于大多数工业现场来说,这个取舍是划算的。
2.2 射频参数怎么选:SF、BW、CR 的取舍逻辑
LoRa 的射频参数直接决定了通信距离、速率和抗干扰能力。这三个参数是:
| 参数 | 含义 | 增大后的影响 |
|---|---|---|
| SF(扩频因子) | 每个符号携带的比特数,7~12 | 距离更远,速率更低,空中时间更长 |
| BW(带宽) | 信道带宽,常见 125/250/500kHz | 速率更高,灵敏度下降,距离变短 |
| CR(编码率) | 前向纠错比例,4/5~4/8 | 抗干扰更强,开销更大 |
我一般按这个顺序来定:先定距离需求,再定速率需求,最后定抗干扰需求。
如果节点离网关 1 公里以内,SF7、BW125 就够了,空中速率 5.5kbps,传 20 字节数据不到 50ms。如果距离 3 公里以上,或者中间有遮挡,就要上 SF10 到 SF12,速率降到 1kbps 以下,传同样的数据要几百毫秒甚至一秒多。
这里有个很多人忽略的点:SF 越大,空中时间越长,节点占用的信道时间就越多。如果一个网关下面挂了 100 个节点,每个节点都用 SF12,那信道会非常拥挤,碰撞概率急剧上升。所以实际项目中,我会根据节点到网关的距离,给不同节点分配不同的 SF,近的用 SF7,远的用 SF10,这叫自适应数据速率(ADR)。ADR 在 LoRaWAN 里是标准功能,但在私有协议里需要自己实现。
BW 的选择相对简单:国内 470MHz 频段一般用 125kHz,少数场景用 250kHz 换速率。500kHz 在国内用得少,因为占空比和法规限制。
CR 我通常用 4/5,也就是每 4 个有效比特加 1 个纠错比特。如果现场干扰特别严重,可以上 4/8,但速率会掉一半。实测下来,工业现场用 4/5 基本够用,除非旁边有大功率电机或者变频器。
2.3 自组网协议栈:私有协议还是LoRaWAN
这是选型时绕不开的问题。LoRaWAN 是标准协议,有完整的入网、加密、ADR、Class A/B/C 定义,生态成熟,网关和服务器都有现成方案。但它有几个"重"的地方:
- 入网流程需要 OTAA 或 ABP,OTAA 要多次交互,节点首次入网慢。
- 协议栈代码量大,对低端 MCU 不友好。
- 服务器端需要 Network Server、Join Server、Application Server,部署复杂。
- 在国内 470MHz 频段,LoRaWAN 的某些参数配置需要调整才能合规。
私有协议则完全相反:代码量小、入网快、参数随便调,但所有东西都要自己写,包括地址分配、确认重传、加密、固件升级。
我的经验是:如果节点数量在 50 个以内、场景固定、不需要跟第三方平台对接,私有协议更省事。如果节点上百、需要跟云平台对接、或者客户明确要求标准协议,那就上 LoRaWAN。
热词里出现了stm32wle5 lora smart tdma 完整协议栈工程实现,说明有人在做 TDMA 的私有协议。TDMA 在 LoRa 自组网里确实是个好思路:给每个节点分配固定的时隙,避免随机接入的碰撞。但 TDMA 需要全网时间同步,而 LoRa 的空中时间又长,同步开销不小。我见过做得好的 TDMA 方案,网关周期性发信标,节点根据信标对齐时隙,效果不错,但实现难度比纯 ALOHA 高一个量级。
3. 核心细节解析与实操要点
3.1 节点入网与地址分配:IAP和Flash的坑
热词里有个很有意思的词:iap boot里面定义的变量复位后会怎样。这个问题跟 LoRa 自组网设备关系很大,因为节点通常需要支持远程固件升级(OTA),而 OTA 的基础就是 IAP(In-Application Programming)。
先说 IAP 的基本结构:MCU 的 Flash 分成 Bootloader 区和 Application 区。Bootloader 负责接收新固件、校验、写入 Application 区,然后跳转。Application 区就是正常运行的业务代码。
这里有个经典坑:Bootloader 里定义的全局变量,在跳转到 Application 之后,如果发生复位,这些变量的值会怎样?答案是:取决于复位类型和变量存储位置。
- 如果变量在 RAM 里,普通复位(看门狗、软件复位)不会清 RAM,值可能保留;但上电复位会清 RAM,值丢失。
- 如果变量在 Flash 里(比如用
const或者指定到特定段),复位后值保留,但要注意 Flash 写入次数限制。 - 如果变量在备份寄存器(Backup Register)里,只要 VBAT 供电不断,复位后值保留。
我实际做 OTA 时,会在 Bootloader 里用一个备份寄存器存"升级标志"。Application 收到升级命令后,写标志、复位;Bootloader 启动时读标志,如果标志有效,就进入升级模式,否则跳转 Application。这样即使中途断电,标志也不会丢(只要 VBAT 有电)。
另一个坑是中断向量表的偏移。Application 区的起始地址不是 0x08000000,而是 Bootloader 之后,比如 0x08008000。这时候 Application 里必须设置SCB->VTOR = 0x08008000,否则中断会跳到 Bootloader 的向量表,直接跑飞。这个坑我踩过不止一次,尤其是用 HAL 库的时候,SystemInit里默认设的是 0x08000000,需要手动改。
对于 LoRa 节点来说,OTA 还有个特殊问题:LoRa 速率低,固件大。一个 100KB 的固件,用 SF10、BW125 传,空中速率大概 1kbps,理论上要 800 秒,实际加上协议开销和重传,可能要 20 分钟以上。所以 LoRa OTA 通常采用分片传输 + 断点续传,而且要在节点供电充足的时候做。我一般会把 OTA 设计成"网关主动推送 + 节点确认"的模式,而不是节点主动拉取,这样网关可以控制升级节奏,避免所有节点同时升级把信道占满。
3.2 RS485与LoRa的配合:为什么很多设备要带485接口
热词里 RS485 出现的频率极高,rs485组网、rs485电路、rs485自动换向电路、rs485与rs232协议详解及modbus通信指南,说明很多人关心的不是纯 LoRa,而是LoRa + RS485 的组合设备。
这个组合的逻辑很清晰:工业现场大量传感器、PLC、仪表都是 RS485 接口,走 Modbus RTU 协议。LoRa 自组网设备如果带一路 RS485,就可以直接接这些设备,把 Modbus 数据透传或者解析后通过 LoRa 发出去。这样既不用改原有设备,又能实现无线化。
RS485 电路设计有几个关键点:
- 收发切换:RS485 是半双工,发送和接收不能同时。传统方案用 MCU 的 GPIO 控制 DE/RE 引脚,但这样软件开销大,时序容易出错。现在常用自动换向电路,用三极管或者专用芯片,根据 TX 信号自动控制 DE,MCU 只管发数据就行。
- 保护电路:现场环境恶劣,RS485 总线容易受浪涌、静电、共模电压影响。TVS 管、共模电感、自恢复保险丝是标配。我见过没加保护的板子,雷雨天一打就烧一片。
- 终端电阻:RS485 总线两端要接 120 欧姆终端电阻,中间节点不接。很多人忘记这个,导致通信距离短、误码率高。
- AB 线极性:热词里有人问
rs485的ab波形哪种才是正确的。标准定义是 A 线比 B 线高时表示逻辑 1,但实际芯片标注可能相反,接线前一定要看手册或者用示波器确认。
LoRa 设备接 RS485 传感器时,典型流程是:MCU 通过 RS485 发 Modbus 查询帧,等传感器回复,解析数据,打包成 LoRa 帧发出去。这里要注意超时设置:Modbus 回复有延迟,如果超时设太短,会误判传感器离线;设太长,又影响 LoRa 上报周期。我一般设 200ms 到 500ms,根据传感器手册调整。
3.3 低功耗设计:节点怎么做到电池撑几年
LoRa 节点很多是电池供电,低功耗是核心指标。一个设计良好的节点,平均电流可以做到几十微安,用 2000mAh 的锂亚电池能撑 3 到 5 年。
低功耗的关键是让 MCU 和射频大部分时间都在睡。典型的工作周期是这样的:
- MCU 定时器唤醒(比如每 5 分钟一次)。
- 采集传感器数据(如果是 RS485 传感器,还要给传感器供电、等预热)。
- 打开 LoRa 射频,发送数据。
- 等待网关确认(如果需要确认)。
- 关闭射频和传感器电源,MCU 进入 STOP 或 STANDBY 模式。
这里面每个环节都有优化空间:
- 传感器供电:很多传感器静态电流不小,不能一直供电。用 MOS 管控制传感器电源,只在采集时打开。
- LoRa 发射功率:发射功率越大,电流越大。20dBm 发射时电流可能 120mA,而 14dBm 只有 40mA 左右。如果距离够,没必要用最大功率。
- 唤醒周期:这是最大的变量。5 分钟一次和 1 小时一次,平均电流差 10 倍以上。要根据实际需求定,不要盲目追求"实时"。
- STANDBY 模式:STM32 的 STANDBY 模式电流只有几微安,但唤醒后相当于复位,所有 RAM 丢失。STOP 模式电流几十微安,但 RAM 保留。我一般用 STOP 模式,因为唤醒后不用重新初始化。
实测数据:一个 STM32WLE5 节点,每 5 分钟采集一次 RS485 传感器并上报,发射功率 14dBm,平均电流大约 80 微安。2000mAh 电池理论寿命 2000/0.08 = 25000 小时,约 2.8 年。如果改成 15 分钟一次,平均电流降到 30 微安左右,寿命能到 7 年以上。
4. 实操过程与核心环节实现
4.1 硬件选型与最小系统搭建
先列一下我做 LoRa 自组网设备时的典型物料清单:
| 部件 | 选型 | 说明 |
|---|---|---|
| 主控+射频 | STM32WLE5JC | 内置 LoRa 射频,省一颗芯片,适合节点 |
| 网关主控 | STM32F407 或 Linux 方案 | 需要处理多节点数据,性能要够 |
| 射频前端 | SX1262 或内置 | 网关可用外置 PA 提升功率 |
| 电源 | 锂亚电池 + LDO | 节点用,注意 LDO 静态电流 |
| RS485 | SP3485 或 MAX3485 | 带自动换向 |
| 天线 | 470MHz 弹簧天线或外置 | 网关用高增益,节点用小型 |
最小系统搭建步骤:
- 供电检查:先用稳压电源给板子供电,测各路电压是否正常,尤其是射频部分的 3.3V 要干净。
- 晶振起振:STM32WLE5 需要 32MHz 和 32.768kHz 晶振,用示波器确认起振。
- SWD 连接:确认能下载程序,读到芯片 ID。
- 射频校准:用官方工具或者自己写代码,校准射频的频偏和功率。
- 点对点通信:先让两个节点互相发数据,确认射频链路通。
这一步最容易出问题的是射频部分。LoRa 的射频电路对布局很敏感,尤其是匹配网络。如果匹配没做好,发射功率上不去,接收灵敏度也差。我一般会先用频谱仪测发射频谱,确认功率和频偏正常,再测接收灵敏度。
4.2 私有协议帧格式设计
私有协议的核心是帧格式。我一般这样设计:
| 前导码 | 同步字 | 帧头 | 载荷 | CRC | | 8字节 | 2字节 | 4字节| N字节| 2字节|帧头里包含:
- 源地址(2字节):节点地址,入网时分配。
- 目的地址(2字节):网关地址通常是 0x0000。
- 帧类型(1字节):入网请求、数据上报、确认、升级等。
- 序列号(1字节):用于去重和确认。
载荷根据帧类型不同而不同。数据上报帧的载荷就是传感器数据,入网请求帧的载荷是节点唯一 ID(比如 MCU 的 UID)。
入网流程:
- 节点上电,发入网请求,载荷带 UID。
- 网关收到,检查 UID 是否已注册。如果已注册,回复入网成功,带分配的短地址;如果未注册,根据策略决定是否允许。
- 节点收到回复,保存短地址,进入正常上报模式。
- 如果节点没收到回复,随机延迟后重试,避免所有节点同时入网。
这里有个细节:入网请求要用较低的 SF 和较高的功率,因为节点还不知道自己离网关多远。入网成功后,网关可以根据收到的信号质量,指示节点调整 SF 和功率。
4.3 网关数据汇聚与上行
网关收到节点数据后,要做几件事:
- 去重:同一个序列号的数据只处理一次。
- 时间戳:给数据打上网关本地时间。
- 缓存:如果上行链路(4G/以太网)断了,数据要缓存,恢复后补传。
- 上行:通过 MQTT、Modbus TCP 或者自定义协议发给服务器。
网关的缓存策略很重要。我一般用环形缓冲区,存最近 10000 条数据。如果上行断了超过缓冲区容量,最老的数据会被覆盖。对于关键数据,可以加一个"重要标志",重要数据不覆盖。
网关的另一个功能是下行控制。服务器可以通过网关给节点发命令,比如修改上报周期、触发采集、启动 OTA。下行帧和上行帧用同样的格式,只是方向相反。
4.4 现场部署与信号测试
设备做好了,现场部署才是真正的考验。我的标准流程是:
- 现场勘测:先带一个网关和一个节点,到现场测信号。网关放在预定位置,节点拿到各个角落,记录 RSSI 和 SNR。
- 确定网关位置:网关尽量放高,避开金属遮挡。如果现场有多个建筑,可能需要多个网关或者中继。
- 节点安装:节点安装位置要避开金属、电机、变频器。天线尽量竖直,不要贴着墙面。
- 全网测试:所有节点装好后,观察一段时间的数据,看有没有丢包、延迟异常。
- 参数微调:根据实测数据,调整节点的 SF 和发射功率。
这里有个经验:RSSI 大于 -100dBm、SNR 大于 0dB 的链路,基本能稳定通信。如果 RSSI 在 -110 到 -120 之间,SNR 为负,就要考虑加中继或者调整天线。
5. 常见问题与排查技巧实录
5.1 通信距离不达标怎么排查
这是最常见的问题。排查顺序:
| 现象 | 可能原因 | 排查方法 |
|---|---|---|
| 近距离能通,远距离不通 | 天线匹配差、功率不足 | 频谱仪测发射功率 |
| 白天通,晚上不通 | 干扰源变化 | 扫频看背景噪声 |
| 晴天通,雨天不通 | 湿度影响、天线进水 | 检查天线密封 |
| 某些节点不通 | 遮挡、金属反射 | 换位置测试 |
| 全部不通 | 网关故障、频点错误 | 检查网关和频点配置 |
我遇到过一个案例:节点装在金属配电箱里,信号出不来。后来把天线用馈线引到箱外,问题解决。所以金属遮挡是 LoRa 最大的敌人,比距离本身影响还大。
5.2 丢包率高怎么办
丢包率高通常是信道冲突或者链路质量差。解决思路:
- 降低上报频率:如果所有节点都 1 分钟上报一次,信道肯定挤。改成 5 分钟或者 10 分钟。
- 错开上报时间:给每个节点加一个随机延迟,避免同时上报。
- 调整 SF:近的节点用低 SF,减少空中时间。
- 加确认重传:重要数据加 ACK,没收到就重传。但重传会增加信道负担,要权衡。
- 换频点:如果现场有同频干扰,换个频点试试。
5.3 节点功耗异常怎么查
功耗异常一般是某个环节没关干净。排查方法:
- 用高精度电流表(比如 uCurrent)测不同状态下的电流。
- 确认 MCU 进入了低功耗模式。
- 确认射频进入了 Sleep。
- 确认传感器电源被切断。
- 检查有没有悬空的 GPIO,悬空引脚会漏电。
我踩过一个坑:某个 GPIO 配置成输入但没上拉,浮空状态下电流多了几十微安。后来全部改成模拟输入或者输出低,功耗才降下来。
5.4 OTA升级失败怎么恢复
OTA 失败最怕的是节点变砖。我的做法是:
- Bootloader 永远不升级,只升级 Application。
- Application 升级前,先写一个"升级中"标志到备份寄存器。
- 升级完成后,清除标志。
- Bootloader 启动时,如果发现"升级中"标志还在,说明上次升级失败,回滚到旧固件或者重新进入升级模式。
这样即使升级中途断电,节点也能恢复。另外,Bootloader 要留一个串口或者 LoRa 的强制升级入口,万一标志逻辑出问题,还能手动救回来。
6. 一些实际项目中的经验体会
做 LoRa 自组网设备,最深的体会是:射频这东西,理论是一回事,现场是另一回事。你在实验室里调好的参数,到现场可能完全不是那么回事。所以我的习惯是,任何新方案,先做小批量现场测试,跑至少两周,看数据稳定性,再批量部署。
另一个体会是不要过度设计。我见过有人非要在 LoRa 上跑 Mesh,结果复杂度爆炸,维护成本极高。其实大多数场景,星型加中继就够了。把简单的事情做稳定,比把复杂的事情做出来更有价值。
最后分享一个小技巧:网关加一个 RSSI 日志功能。每个节点每次上报,网关都记录 RSSI 和 SNR。这样运行一段时间后,你就能看到哪些节点链路质量在下降,提前发现天线老化、遮挡物增加等问题。这个功能实现很简单,但运维价值很大。
这个内容后续还可以这样扩展:如果你要做的是带定位功能的 LoRa 设备,可以研究一下 LoRa 的到达时间差(TDOA)定位,虽然精度不如 GPS,但在室内或者 GPS 信号差的地方能派上用场。另外,LoRa 和蓝牙、WiFi 的共存问题也值得关注,尤其是网关同时带多种无线的时候,射频干扰要提前规划。