ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

FPGA以太网SGMII接口设计:时钟同步、调试与工程实践

FPGA以太网SGMII接口设计:时钟同步、调试与工程实践 1. SGMII是谁从以太网链路聊起1.1 MAC和PHY之间为什么需要翻译官做FPGA以太网项目绕不开一个基础概念一块完整的以太网接口其实是由MAC媒体访问控制层和PHY物理层两大部分组成的。MAC负责组帧、解析、地址过滤、流控这些逻辑活PHY则负责把数据变成真正能在网线上跑的差分信号同时完成编码、解码、链路协商这些物理活。两块芯片之间需要一套标准的接口协议来传输数据和状态信息这就是MII系列接口存在的意义。早期最常见的接口是MII和RMII。MII用4位数据、两条控制线时钟25MHz百兆或2.5MHz十兆一根网线要拉十几根线RMII把数据线砍到2位时钟固定50MHz但代价是MAC侧和PHY侧必须共用同一个精确时钟源布线要求反而更苛刻。到了千兆时代GMII直接变成8位数据、125MHz时钟引脚数量暴涨PCB布线变得非常痛苦尤其对于高速信号来说走线等长、串扰、反射这些问题全都会冒出来。所以后来才有了RGMII和SGMII这两个主流方案。RGMII用DDR方式在上升沿和下降沿各采一次数据把引脚数压到12根左右至今仍大量用在低成本的ARMPHY方案里比如STM32F407搭配DP83848、ESP32搭配LAN8720都是这种接法。但在FPGA领域真正高端和通用的还是SGMII它的出现把MAC和PHY之间的连接从并行总线变成了高速串行差分信号只需要两对差分线传输距离和布线友好度都大幅提升。1.2 SGMII的技术底细SGMII全称是Serial Gigabit Media Independent Interface串行吉比特媒体独立接口。它工作在1.25Gbps的线速率上内部采用8B/10B编码也就是每8位有效数据编码成10位线数据扣掉编码开销后正好承载1Gbps的有效带宽。物理连接上包括一对发送差分线TX、一对接收差分线RX再加上一个125MHz的参考时钟。数据通路是独立双向的所以全双工模式下可以直接跑满千兆。如果只是把并行改成串行那SGMII还不算特别惊艳。它真正厉害的地方在于把整个物理编码子层PCS的工作集中到了接口内部包括自协商Auto-Negotiation功能。这就意味着PHY和MAC可以通过SGMII接口自协商链路速率支持10M、100M、1000M三档自适应。这部分逻辑都封装在SGMII IP核或PHY芯片内部对上层MAC来说是透明的。这里必须区分一个概念SGMII和1000BASE-X。很多人第一次用Xilinx或Intel的以太网IP核时都会在这两个选项之间犯迷糊。SGMII适用于MAC到PHY的短距离连接自协商内容是速率和双工模式1000BASE-X适用于光模块或两个MAC设备背靠背直连走的是另一种协议封装的8B/10B码流自协商内容也完全不同。如果选错格式最典型的故障现象就是链路永远无法建链。特性GMIIRGMIISGMII数据宽度8位4位DDR1位串行时钟频率125MHz125MHz1.25Gbps线速引脚数量不含MDIO约20根约12根4根差分1根时钟编码方式无无8B/10B是否含自协商能力否否是我从实际项目经验来看SGMII在FPGA端最大的优势不只是省引脚而是把MAC和PHY之间的时序约束大幅简化了。并行接口中最头疼的建立保持时间、偏斜skew问题到了串行接口上全都由收发器的CDR时钟数据恢复自动处理了。剩下的关键就是时钟同步这一件事。2. 时钟同步策略别让125MHz毁掉整条链路2.1 时钟架构一个125MHz引发的连锁反应SGMII所有收发器逻辑都建立在125MHz参考时钟的基础上。这个125MHz从哪来直接决定整条链路稳不稳。我见过的时钟方案大体有三种各有各的适用场景和隐患。第一种是独立晶振方案FPGA板卡和PHY板卡各自用自己的125MHz晶振。这种方案最简单硬件成本低但要求两边的125MHz必须足够接近。通常要求频率容差在±50ppm以内实际优质晶振能做到±25ppm甚至更好。但即使这样两边始终存在微小的频率偏差MAC和PHY之间的收发FIFO就会随时间慢慢溢出或下溢。对于千兆以太网这种连续数据流来说一旦FIFO错误帧就会周期性丢失或产生CRC错误非常难排查。这种方案在实验室验证低吞吐量时勉强能用但做产品级设计我不推荐。第二种是PHY回环时钟方案也是最符合SGMII设计预期的做法。PHY本身带有125MHz时钟输出引脚典型命名是CLK125_OUT或CLKOUT125它内部由晶振经过锁相环PLL锁定后输出频率稳定且与PHY内部时钟同源。FPGA把这根时钟作为SGMII收发器的参考时钟输入这样MAC和PHY就工作在完全同源的时钟域下收发FIFO不会因为频率偏差而累积误差。第二种方案是我在工程中的首选。第三种是FPGA主动提供时钟给PHY。Xilinx和Intel的参考设计里也允许FPGA输出一个125MHz参考时钟给PHY前提是FPGA端用高精度晶振加PLL生成。这个方案适合某些PHY必须由MAC侧统一提供低抖动时钟的场景但实现时要特别注意时钟有源端和无源端的信号完整性设计一旦走线过长或阻抗不连续时钟质量会直接影响PHY内部CDR的恢复效果。2.2 TX和RX时钟域处理GTX收发器内部到底发生了什么在FPGA内部SGMII一般通过GTX或GTH这类高速串行收发器来实现。收发器内部有独立的TX和RX时钟域TX方向使用本地的参考时钟分频产生串行时钟RX方向则通过CDR从接收数据流中恢复出时钟。这两个时钟域并不天然相等如果RX恢复时钟和本地时钟不一致数据跨时钟域就会出问题。好在SGMII协议本身具备异步缓存机制。在PCS层MAC发送的数据会先进入一个发送FIFO再按发送时钟读取PHY返回的数据则先进入接收FIFO再按本地读取时钟取出。这个FIFO本质上就是为了吸收两个时钟域的微小偏差。但注意FIFO的深度是有限的如果两侧时钟不同源偏差会不断累积最终不是读空就是写满表现为偶发性丢包或CRC错误而且很难通过提高容错来根治。所以我说时钟同步策略的核心不是怎么在FPGA里把时钟对齐而是怎么确保整个系统只有一个权威时钟源。对比一下三种时钟架构的稳定性结论就很直观了。时钟方案同源性发收FIFO风险适用场景独立晶振不同源高低速验证、低成本板卡PHY回环时钟同源低常规千兆设计FPGA主导时钟同源但依赖布局中低多PHY需统一时钟时2.3 多端口和跨板卡同步一个容易被忽视的深水区单路SGMII做好同源基本就够用了但一旦系统涉及多路以太网端口或者要求多块板卡之间的时间严格对齐时钟同步就上升到了另一个维度。多路端口的情况比如FPGA同时驱动4路千兆SGMII每路对应各自的PHY。理想状态下每个PHY的CLK125_OUT各自回环到对应的GTX通道。但很多参考设计为了省事会用同一个晶振或同一个PLL输出扇出给所有PHY和所有GTX通道。这会导致一个问题每个PHY和对应的GTX之间实际上还是不同源的因为PHY内部锁相环的输出和FPGA的PLL输出之间总有微小的相位差和频率跟踪差异。稳妥的做法是给每一路PHY单独回环时钟或者至少确保所有参与收发的时钟都锁定到同一个参考源上。跨板卡或跨芯片同步则更复杂比如车载以太网中多个ECU需要精确时间同步就要引入gPTPIEEE 802.1AS协议在软件协议栈层面对时间戳做精细校正硬件上则要求PHY支持时间戳功能能够精确标记帧的收发时刻。这里SGMII接口设计的重点就变成了为MAC提供高精度的TX和RX时间戳接口并且确保时间戳的采样时钟足够稳定一般是125MHz整数倍。如果只做普通数据透传不需要考虑这些但只要涉及工业控制或自动驾驶领域这一节就是必考的。3. 实操在FPGA上搭建SGMII接口的完整流程3.1 硬件连接与PHY配置速查先讲硬件。FPGA的GTX收发器引脚需要连接到PHY芯片的SGMII端。以常见的Marvell 88E1512为例它的SGMII端包括SIN接收串行差分输入、SOP发送串行差分输出两对差分线以及MDC/MDIO管理接口。连接时要注意FPGA的TXP/TXN要接到PHY的收端SINP/SINNFPGA的RXP/RXN要接到PHY的发端SOPP/SOPN这个交叉关系很多人第一次会接反接反的直接后果是PHY端完全收不到有效数据链路状态永远停留在没有信号。PHY的配置通常由硬件引脚和寄存器两部分共同决定。硬件引脚方面88E1512有芯片模式选择引脚和PHY地址引脚一般通过上下拉电阻配置为SGMII模式PHY地址常用0x00或0x1E这些值要和MDIO驱动代码里的地址完全一致。寄存器方面基本流程是复位PHY然后通过MDIO读取状态寄存器确认链路状态。读PHY ID是一个很好的自检手段88E1512的PHY ID是0x01410E90读出来不对的话大概率是MDIO时序或地址配置有问题。3.2 SGMII IP核配置要点在Xilinx Vivado环境中对应SGMII的IP核一般叫1G/2.5G Ethernet PCS/PMA or SGMII。创建IP核时有几个关键选项需要仔细确认。第一个是Physical Interface选择SGMII而不是1000BASE-X。第二个是Line Rate参数千兆对应1.25Gbps如果选成1000BASE-X或者错误速率后续调试非常被动。第三个是Shared Logic选项我强烈建议选择Include Shared Logic in core而不是Include Shared Logic in example design。第一个选项会把收发器、时钟管理、复位逻辑全部包含在IP核内部对外接口更简洁适配不同板卡时方便第二个选项适合需要定制化修改收发器参数的高级场景但配置起来复杂得多复用性也差。IP核配置完成之后还有一个容易忽视的点MAC侧接口。SGMII IP核对外通常提供GMII或XGMII类似的数据接口部分IP核也支持AXI Stream接口需要确认和你的MAC或协议栈一致。时间戳、流量控制这类可选功能在前期验证阶段建议全部关掉先把通路的畅通跑通再逐步打开。3.3 复位与初始化最容易翻车的环节复位是FPGA工程师的老朋友但SGMII的复位比想象中更讲究。PHY芯片需要在上电后保持至少10毫秒的复位低电平之后释放复位再等待芯片内部校准完成这个过程一般需要几十到几百毫秒期间不要读取PHY寄存器否则读到的都是默认值或者不稳定状态。FPGA内部的GTX收发器对复位时序要求也很高。收发器的TX和RX各自有复位信号且必须遵循先复位PLL再复位通道最后复位PCS的序列。很多SGMII初始化失败都是因为复位时序混乱。Xilinx官方提供了参考复位模块在Vivado中可以直接例化我建议第一次做项目时直接用官方模块不要自己写等调试熟练了再考虑自定义复位逻辑。另外FPGA的复位信号本身存在亚稳态风险。异步复位信号如果直接去复位逻辑单元在时钟沿附近变化时可能导致部分逻辑复位成功、部分失败这个状态在SGMII链路中尤其致命因为MAC和PCS的状态机会跑飞表现为链路偶发断连。解决办法很标准使用异步复位同步释放电路让复位信号经过两级或三级触发器同步后再使用。3.4 收发通路验证从环回测试到UDP收发链路搭建完成后的第一步验证我建议用PHY芯片自带的数字环回功能把PHY的接收数据直接环回到发送端。配置方法是通过MDIO把PHY的控制寄存器如0x00寄存器的环回位拉高然后用FPGA侧连续发送特定数据pattern再用ILA或SignalTap抓取接收数据确认数据一致。这个测试能验证FPGA到PHY芯片的物理通路、PCS层编解码、GTX收发器的TX和RX链路不涉及网络协议。环回测试通过后再切换到正常模式连接两台设备的PHY到交换机或直连电脑用Wireshark抓包验证。FPGA侧发送UDP广播帧电脑端如果能收到就说明MAC数据通路和PHY链路协作正常。有一点要注意SGMII在自动协商完成之前MAC侧发送的数据不会被PHY正确编码到线上所以一定要等到链路状态变成已连接之后再去测试。整个调试周期中UART是廉价但实用的辅助工具。在FPGA内部例化一个UART发送模块把PHY状态寄存器值和SGMII IP核的链路状态打印出来要比反复连接ILA看波形高效得多。QSPI配置FPGA也是一个建议从一开始就做好的环节每次上电都通过JTAG加载bit文件虽然方便但脱离电脑后无法独立运行调试SGMII链路时常常需要反复上下电QSPI配置能省下大量时间。4. 链接不上、丢包、CRC错问题排查实录4.1 链路协商失败先看灯再看寄存器调试SGMII时遇到最多的问题就是链路协商失败。我个人的经验是遇到问题先看三样东西板子上PHY芯片的LED指示灯、PHY状态寄存器、FPGA内部收发器状态。这三个位置由外到内能快速缩小问题范围。PHY的LED通常有Link和Activity两个指示灯Link常亮表示物理链路已建立。如果Link不亮优先检查PHY芯片供电和参考晶振是否起振。有些PHY支持通过寄存器读取当前协商模式和速率比如88E1512的状态寄存器0x11可以读取当前工作模式0x01寄存器可以读取链路状态。如果寄存器显示链路在反复上下电抖动多半是SGMII接口的时钟或数据线连接问题这时候用示波器看PHY侧SGMII差分线确认是否有信号在收发。时钟问题的典型点在于PHY芯片的125MHz参考时钟必须稳定、低抖动。早期我在一块自定义板卡上遇到链路永远协商不上的问题最后用频谱仪查出来是晶振负载电容选错导致实际振荡频率偏低PHY内部PLL无法锁定。这个调试过程非常痛苦所以后来我做硬件设计时都会在晶振旁边预留两个贴片电容位用来在出问题时调整负载电容。4.2 能通但丢包和CRC错误帧间隔与时钟抖动链路协商正常、数据能通但持续跑吞吐量测试时出现丢包或CRC错误这类问题往往和帧间隔IPG有关。IEEE 802.3规定以太网帧之间的最小间隔是96比特时间约9.6微秒。SGMII在PCS层进行8B/10B编解码和时钟恢复时如果帧间隔处理不合理特别是当MAC在环回或特殊模式下发送过快可能出现帧间隔被压缩的情况。解决办法通常需要在MAC侧配置帧间隔生成逻辑确保发送帧间间隔不低于96比特时间。另外RGMII转SGMII或者某些桥接芯片做格式转换时也会出现IPG被压缩的问题这些都是PHY和MAC之外的中间层容易埋雷的地方。还有一类丢包是因为时钟抖动过大引起的比特错误。GTX收发器和PHY芯片对参考时钟的抖动容限都有明确限值一般在数十皮秒到百皮秒级别。如果时钟走线经过过多过孔、跨越分割平面、或与其他高速信号距离过近都可能引入额外抖动。这种问题很难靠代码解决只能从PCB布局布线去修复比如保证125MHz走线走内层、保持阻抗连续、和其他高速信号保持至少3倍线宽的距离。4.3 不稳定、温漂和跨板卡不一致系统在常温下稳定运行但一进高低温箱或者长时间运行就出现偶发断链这类问题大概率指向时钟频率精度。晶振在不同温度下的频率漂移可能达到几十ppm两侧晶振各自漂移最终导致收发FIFO频繁溢出。要根治还是得回到时钟同源方案把PHY的CLK125_OUT回环作为FPGA收发器的参考时钟。我之前接手过一个客户遗留项目FPGA和PHY各用各的晶振常温下测不出问题但客户反馈在设备机房环境温度较高运行几个月后出现断续丢包改成同源时钟后问题彻底消失。跨板卡不一致的问题也很典型。比如两块相同设计的板卡一块链路很稳一块链路时好时坏。除了器件个体差异外最常见的原因是焊装环节导致差分线附近虚焊或者晶振焊接不良。这类问题建议先用IBERT集成误码率测试工具对GTX链路做误码率扫描IBERT能把收发器通道逐一测试定位到物理链路质量差异比盲目改逻辑高效得多。4.4 SGMII调试验证问题速查表现象可能原因排查方向Link灯不亮PHY不工作、晶振不起振检查供电、晶振波形、PHY复位链路一直协商不成功SGMII接口接反、模式配置错检查TX/RX交叉关系、PHY模式引脚能link但收不到数据PCS配置错、IPG问题确认SGMII/1000BASE-X选择、IPG设置偶尔丢包、CRC错误时钟不同源、FIFO溢出改用PHY回环时钟、检查收发FIFO状态传输时延抖动大参考时钟抖动超标优化PCB布局、检查电源纹波高低温环境断链晶振温漂、接触不良改用同源时钟、检查焊接质量5. 从SGMII出发扩展形态与设计演进5.1 速率升级从SGMII到USGMII、XAUI与10GSGMII本身是千兆时代的方案但当系统需要2.5G速率时传统SGMII就不够用了。这时有两个方向一是使用USGMIIUniversal SGMII或SGMII在同样的串行链路上通过提升线速率到3.125Gbps来承载2.5G数据二是直接升级到XAUI接口XAUI使用4条3.125Gbps的串行通道总共提供10Gbps带宽是万兆以太网MAC和PHY之间常见的接口形态。从工程实践角度看USGMII和SGMII在FPGA里的实现方式几乎完全一致区别主要在线速率和参考时钟分频比上。很多新款的PHY芯片同时支持SGMII和USGMII同一个引脚通过软件配置切换。而XAUI及以上速率则对PCB布线要求高得多差分对之间的等长约束、串扰控制、参考时钟抖动容限都以皮秒为单位计算。从SGMII入手学习再向更高频率演进是一条很平滑的技术成长路径。5.2 背靠背测试与链路质量评估PHY背靠背是评估PHY芯片或测试链路时常用的架构即两个PHY的SGMII接口直接互相连接不经过变压器和网线。这种接法在产线测试和实验室验证中非常实用能够在板级完成PHY到PHY的完整链路测试。需要注意的是背靠背模式下两个PHY通常需要配置为不同的工作模式一个作为主机master一个作为从机slave否则时钟参考会冲突导致链路不稳定。链路质量评估方面IBERT是FPGA工程师的得力工具。在Xilinx Vivado里可以直接例化IBERT IP核通过JTAG访问实时扫描GTX通道的误码率、眼图宽度和高度。我在验证一块多板卡系统的SGMII链路时就是先用IBERT把所有通道扫了一遍发现其中一个通道的眼图质量明显差于其他通道最终定位到是参考时钟扇出后的电源纹波过大。IBERT调通之后再做上层的SGMII协议验证整个调试过程会清晰很多。5.3 对FPGA系统工程师的几点实在建议把这几年做SGMII项目的经验压缩成几条建议供后来人参考。第一永远优先考虑时钟同源设计这是SGMII稳定性的基石。第二调试链路时用分层策略先物理层环回和IBERT再数据链路层PHY寄存器、MAC帧收发最后才做协议栈验证。第三多预留调试接口比如FPGA侧至少保留一组空闲GTX通道用于插入测试UART打印状态一定要从一开始就规划好。第四PCB设计时把PHY芯片的参考时钟、SGMII差分线、MDIO走线的规范检查到位这些硬件细节决定了后续软件调试的天花板。我在实际项目中还踩过一个老坑为了节省逻辑资源在SGMII IP核中关闭了某些状态监测信号后来链路出现偶发异常时完全拿不到有效状态。所以调通之后再精简资源可以但调试阶段务必把所有观测信号、状态计数器都拉出来宁可浪费一些BRAM和寄存器也不要让故障变成黑盒子。链路稳定运行之后再根据实际需要逐步裁剪。SGMII这套体系看起来简单一根差分线横跨MAC与PHY但真正吃透里面的时钟同步、PCS编解码、自协商细节需要踏踏实实做完一到两个完整项目。这篇内容算是我自己从一次次翻车中总结出来的路线图希望看完之后你能少走几步弯路直接踩在正确的节奏上把SGMII做成一个稳健、干净、可复用的接口设计模块。
返回列表