嵌入式设备Lwip协议栈实现功能
LWIP 协议栈与以太网硬件层对接
本节说明嵌入式系统中协议栈(如 LWIP)与以太网硬件的职责划分、常见芯片(W5500、PHY)及接口要点,便于理解协议栈实现和移植。
1. 分层职责回顾
- 硬件通常完成:物理层(PHY) + 链路层(MAC)的收发与部分解析工作。
- 上层(网络层、传输层、应用层)由软件协议栈负责(如 LWIP)。
- 特殊芯片(例如 W5500)把更多功能集成到硬件中:W5500 通过 SPI 提供一个“硬件 TCP/IP”接口,芯片内部实现从链路层到传输层的一些功能,主控只需通过寄存器/缓冲区读写数据即可。
2. 常见以太网接口:MII / RMII / RGMII(简介)
- MII(Media Independent Interface)
- 传统接口,数据宽度较大(4-bit),有独立 TX/RX 时钟与数据线。
- 引脚较多,常用于 10/100 Mbps。
- RMII(Reduced MII)
- 精简版 MII,数据线由 4 -> 2(双半字节复用),参考时钟统一(通常 50 MHz)。
- 引脚更少,常用于资源受限 MCU。
- RGMII(Reduced Gigabit MII)
- 支持千兆速度(Gbps),采用 4-bit 双向数据,但时序更严格,通常需要 125 MHz 时钟。
3. MCU(MAC)与 PHY 的常用引脚说明(要点)
以下是常见信号与功能的简要说明(以 MCU 侧 ENET_* 命名为例):
- ENET_MDC / ENET_MDIO:用于 MDIO 总线,MCU(MAC)通过该总线配置和读取 PHY 寄存器(管理/控制)。
- ENET_TX_DATA[0…3]:发送数据线(MII 下为 4-bit 串行输出)。
- ENET_TX_EN:发送有效指示(当为 1 时,TX_DATA 上的数据有效)。
- ENET_TX_CLK:发送时钟(MII 模式下由 PHY 提供或由 MAC 提供,取决于配置)。
- ENET_RX_DATA[0…3]:接收数据线(PHY 到 MAC)。
- ENET_RX_EN:接收数据有效指示。
- ENET_RX_CLK:接收时钟。
- ENET_CRS / ENET_COL:载波感应与冲突指示(半双工相关,现代全双工下较少使用)。
- ENET_REF_CLK:RMII 模式下的参考时钟(通常 50 MHz),可由 PHY 提供给 MAC。
注意:不同 MCU/PHY 的命名与功能细节可能略有差异,具体参考芯片手册。
4. W5500 简要说明(硬件 TCP/IP 芯片)
- W5500 是硬件实现的网络控制器,通过 SPI 与 MCU 通信。
- 特点:
- 内置以太网协议处理、内置 socket-like 接口(读写寄存器/缓冲区实现 TCP/UDP/RAW)。
- 适合没有内置以太网 MAC/PHY 的 MCU,或需要减轻 MCU 协议栈负担的场景。
- 使用要点:
- MCU 通过 SPI 命令访问 W5500 的 TX/RX 缓冲区、状态寄存器和 socket 控制寄存器。
- 不需要在 MCU 上运行完整 LWIP(但也可以做混合方案:W5500 做链路+传输,MCU 只做应用逻辑)。
5. 常用 PHY:LAN8720A(与 MCU 的协作)
- LAN8720A 是常见的 10/100M PHY 芯片,通常与 MCU 的 MAC 通过 RMII(或 MII)接口连接。
- PHY 职责:
- 物理层(编码/解码、链路检测、速度/双工协商)
- 提供 MDIO 接口以供 MAC/MCU 配置(读取 link 状态、PHY 寄存器等)
- 使用建议:
- 在板级设计中,注意 RMII 时钟源(PHY 是否输出 REFCLK),以及外部晶振/时钟走线。
- 在驱动层初始化时,使用 MDIO 读取 PHY ID 与 PHY 状态,确认链路已建立再开启 MAC 收发与 LWIP netif。
5.1 LAN8720A 常用引脚说明
-
MODE[2:0]
- 用于选择 LAN8720A 的工作速率与模式(10/100 Mbps、半/全双工)以及是否启用自动协商/自动翻转(Auto-MDIX)。
- 一般建议将 MODE 引脚拉为 1(高)以启用自动协商与 Auto-MDIX,让芯片自动选择最佳工作方式。
- 注意:MODE[0] 与 RXD0 共用、MODE[1] 与 RXD1 共用、MODE[2] 与 CRS_DV 共用,布线时需考虑复用。
-
nINT / REFCLKO
- 复用功能:在 RMII 应用中可作为 50 MHz 的参考时钟输出(REFCLK)或作为中断输入(nINT)。
- nINTSEL = 低(通常接地)时:nINT/REFCLKO 输出 50MHz 时钟(由内部 PLL 生成),此时中断功能不可用。此模式下要求提供 25MHz 到 XTAL1/CLKIN 或在 XTAL1/CLKIN 之间输入一个 25MHz 源。
- nINTSEL = 高(通常上拉)时:nINT/REFCLKO 作为中断输出,PHY 由外部提供 50MHz 时钟(外部时钟到 REF_CLK/CLKIN);此时可使用中断功能。
- 在 STM32 等 MCU 与 LAN8720 协作时,常见做法:将 PHY 输出的 50MHz REFCLK 直接连到 MCU 的 ENET_REF_CLK(若支持),或让 MCU 提供时钟并把 nINT/REFCLKO 作为中断线使用。
-
REGOFF
- 用于选择 LAN8720A 内部 1.2V 参考供电来源。
- REGOFF = 低:使用芯片内部的 +1.2V 稳压器(推荐板上简化设计)。
- REGOFF = 高:外部通过 VDDCR 引脚提供 +1.2V 电源(用于对噪声或电源有特殊要求的设计)。
- 注意:REGOFF 与 LED1 共用,设计时需兼顾复用影响。
-
SMI / MDIO 寄存器访问
- LAN8720A 的 SMI (Serial Management Interface,MDIO/MDC) 支持最多 32 个寄存器寻址,常用寄存器约 14 个,含 PHY ID、状态寄存器、控制寄存器等。
- MCU 通过 ENET_MDC(时钟)与 ENET_MDIO(双向数据)读写 PHY 寄存器,用于:
- 读取 PHY ID(确认芯片)
- 读取链路状态与速度/双工信息
- 控制复位、节能、自动协商等功能
- 在驱动初始化序列中应:
- 通过 MDIO 读取 PHY ID,确认存在并识别型号;
- 触发/等待自动协商完成并检查链路状态;
- 在链路建立后启用 MAC 的收发与 DMA。
-
MODE 与复用注意事项
- 因 MODE 与若干 RMII 信号复用,若需要在运行时通过 RXD/CRS_DV 使用这些信号,须在硬件或启动配置上保证复用逻辑一致。
- 推荐在硬件设计阶段将 MODE 固定为所需配置,避免运行时冲突。
示意与应用要点:
- 若板上没有外部 50MHz 时钟源,且 MCU 支持从 PHY 接收 REFCLK:可将 nINT/REFCLKO 配为 50MHz 输出,让 MCU 使用该时钟并把 nINT 功能弃用。
- 若需要使用 PHY 中断(链路变化通知等),应把 nINTSEL 设置为高电平并由系统提供稳定的 50MHz 时钟输入。
- 在固件中实现 PHY 初始化流程(MDIO 读 ID -> 启动自动协商 -> 等待链路 up -> 启动 netif)可以显著提升稳定性。
5.2 示例:STM32 + LAN8720 初始化(简要流程)
- 配置 RMII 引脚复用与 ENET_REF_CLK(取决于是否使用 PHY 输出时钟)。
- 初始化 MAC(设置 MAC 地址、MTU、DMA 描述符、Rx/Tx 缓冲区,启用中断/回调)。
- 通过 MDIO 读取 LAN8720 PHY ID,确认通信。
- 启动 PHY 自动协商(或根据 MODE 固定速率/双工),轮询 PHY 状态直至 LINK UP。
- netif 上报接口已就绪,启动 LWIP 的 netif 输入处理线程或回调。
6. MCU 端驱动与 LWIP 交互要点
- 网络接口驱动(ethernetif)应该完成:
- MAC、DMA 的初始化(设置 MAC 地址、MTU、DMA 描述符、中断/回调)。
- low_level_output:将 pbuf 链复制到 DMA 发送缓冲区并触发发送。
- low_level_input:从 DMA 接收缓冲区取出帧,封装为 pbuf 并交给 netif->input(通常是 ethernet_input)。
- 异步与中断策略:
- 推荐使用中断或 DMA 完成回调,将收到的包放入队列或信号量,由专门的 lwIP 处理线程调用 netif->input。
- 避免在中断上下文直接调用 LWIP API(除非使用 NO_SYS 或特殊移植)。
- 缓冲区布局:
- 以太网帧通常由 DMA 描述符指向外部/内部缓冲区,注意对齐与缓存一致性(DCache)处理。
- pbuf_pool 与 PBUF_RAM/PBUF_POOL 的选择影响性能与内存使用。
7. 实践建议与排错要点
- PHY link 不起作用时:
- 检查 MDIO 是否能读到 PHY ID 和状态寄存器;
- 检查 REFCLK 是否稳定、RMII 引脚是否正确复用;
- 检查交换机/网线/对端设备。
- 收到非法帧或 CRC 错误:
- 检查 PHY 与 MAC 时钟相位、接口模式(MII vs RMII)是否匹配;
- 检查 PCB 布线与地线。
- 性能优化:
- 使用 DMA 与 pbuf_pool 减少内存拷贝;
- 调整 LWIP 的 pbuf、TCP 缓冲配置以匹配实际流量模式。
8. 小结
- 常见嵌入式方案分为两类:
- MCU + MAC + PHY:MCU 运行完整 LWIP,MAC/PHY 负责链路层与物理层;
- MCU + 硬件 TCP/IP(如 W5500):硬件完成大部分协议栈功能,MCU 通过寄存器/缓冲区交互。
- 选择方案时考虑硬件资源、开发复杂度与性能需求。
- 在移植 LWIP 时,关注 ethernetif 驱动、MDIO/PHY 管理、DMA 与缓存一致性,以及正确的中断/线程模型。