ARTICLE DETAIL

资讯详情

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

PEX8748 PCIe Gen3存储桥接卡设计:从原理到8盘位扩展实战

PEX8748 PCIe Gen3存储桥接卡设计:从原理到8盘位扩展实战 1. 项目缘起与整体设计思路1.1 为什么要在2024年重新审视PEX8748PEX8748这颗芯片在PCIe交换领域算是老面孔了博通原PLX的第三代PCIe交换芯片支持PCIe Gen3 x48通道最多可以配置成12个x4端口或者6个x8端口。放在Gen4/Gen5满天飞的今天很多人第一反应是这芯片是不是过时了。但实际做存储扩展方案的人都知道Gen3 x4的带宽是3.938 GB/s8b/10b编码后约3.2 GB/s有效带宽对于单块NVMe SSD来说除非是高端企业级盘否则顺序读写很难跑满这个带宽。换句话说用PEX8748做存储桥接在成本、功耗、兼容性三个维度上依然有非常强的竞争力。我这次做的这块卡定位很明确一张单槽位、被动散热、无需外接供电的PCIe Gen3存储桥接卡上行是x8接主机下行拆成两个SlimSAS 4i接口SFF-8654每个SlimSAS再通过线缆分出4个x1或者直接接背板。整卡的核心诉求是让一台普通服务器或者工作站在不换主板的前提下把NVMe盘位从板载的2个M.2扩展到8个甚至更多。1.2 核心需求拆解在动手画原理图之前我把需求拆成了下面几条这几条直接决定了后续所有的选型和布局决策上行链路PCIe Gen3 x8金手指供电不需要外接6pin。这意味着整卡功耗必须控制在25W以内x8插槽理论供电75W但被动散热卡实际安全范围在20W左右。下行端口两个SlimSAS 4i每个4 lane支持SFF-8654线缆。为什么选SlimSAS而不是OCuLink因为SlimSAS 4i的线缆在服务器市场更常见而且可以向下兼容SATA/SAS背板通过协议切换虽然我们这里只跑NVMe。时钟方案PEX8748需要外部100MHz参考时钟同时每个下行端口需要独立的时钟输出给SSD。这里有个坑后面会详细讲。复位与热插拔每个端口需要独立的PERST#和热插拔信号否则一块盘挂了可能拖累整个链路。配置方式通过I2C或者SPI加载配置我选了SPI EEPROM因为可以现场改配置不用重新流片。1.3 方案选型的几个关键取舍为什么不用PEX8724PEX8724是x24通道最多6个x4端口价格便宜不少。但它的上行只能配到x8下行如果拆成6个x4总带宽就超了。而且8724的封装更小散热面积不够跑满负载时结温容易超标。8748的x48通道给了足够的余量我可以把上行配成x16虽然金手指只走x8下行留出更多灵活配置空间。为什么不用Gen4的芯片成本。PEX88048Gen4 x48的价格是8748的三倍以上而且Gen4的PCB板材要求更高需要低损耗板材整卡BOM成本直接翻倍。对于存储扩展这种场景Gen3 x4的带宽已经能喂饱绝大多数NVMe盘除非你要做全闪阵列的缓存池否则Gen4的溢价不划算。为什么选SlimSAS而不是M.2直插M.2直插看起来方便但一张卡上最多放4个M.22280尺寸而且M.2的连接器高度限制导致散热器没法做大。SlimSAS通过线缆引出机箱内部布局灵活得多可以把盘放到风道更好的位置。另外SlimSAS的线缆可以支持到1米左右对于2U机箱来说完全够用。注意SlimSAS 4i的线缆分两种一种是直连背板的带sideband一种是直连SSD的不带sideband。如果你要支持热插拔LED必须选带sideband的线缆否则只能靠软件轮询。2. 核心细节解析与硬件设计要点2.1 PEX8748的端口配置与带宽分配PEX8748的端口配置是通过SPI EEPROM里的配置文件决定的上电时芯片会读取EEPROM内容并锁定端口划分。这里有个很重要的概念PEX8748的内部是模块化的每个端口可以独立配置成x1/x2/x4/x8/x16但总通道数不能超过48。我的配置方案是端口号配置用途备注Port 0x8上行到主机必须配成x8金手指只走x8Port 1x4SlimSAS 1下行Port 2x4SlimSAS 1下行Port 3x4SlimSAS 2下行Port 4x4SlimSAS 2下行Port 5-8x4预留可以后续通过配置工具开启这样总共用了8444424 lane剩下的24 lane可以留着做其他用途比如再挂一个x8的端口做内部桥接。实际上PEX8748的灵活性就在于你可以把多个物理端口合并成一个逻辑端口比如把Port 1和Port 2合并成一个x8端口。配置工具用的是Broadcom的PEX Configuration Wizard这个工具可以直接生成EEPROM的二进制文件。操作步骤打开工具选择PEX8748型号。在Port Configuration页面把Port 0设成Upstream其余设成Downstream。设置每个端口的Lane Width和Lane Assignment。在Clock Configuration里把参考时钟设成100MHz选择Spread Spectrum关闭因为SSD对时钟抖动敏感。生成.bin文件用编程器烧到SPI EEPROM里。实操心得配置工具生成的bin文件里有一块区域是Strapping配置决定了上电时芯片的初始状态。如果你发现上电后链路训练不起来先检查Strapping里的Slot Configuration是不是设成了Single Root而不是Multi-Root。2.2 时钟树设计与抖动控制PEX8748的时钟方案是整个设计里最容易翻车的地方。芯片需要一个100MHz的差分参考时钟Refclk同时每个下行端口需要输出一个100MHz的时钟给SSD。这里有两种方案方案A共用时钟。用一个100MHz晶振同时给PEX8748和所有SSD提供时钟。优点是成本低缺点是如果晶振抖动大所有链路都会受影响。而且SSD的时钟输入要求是HCSL电平PEX8748的输出是LVDS需要电平转换。方案B独立时钟。PEX8748用一颗晶振每个SSD用独立的时钟缓冲器比如SI5332。优点是隔离性好缺点是BOM成本高PCB面积大。我选了方案A的变种用一颗低抖动晶振SiTime的SiT9365抖动100fs给PEX8748然后PEX8748的时钟输出经过一个零延迟缓冲器NB3N551分到各个SSD。这样既控制了成本又保证了时钟质量。关键参数计算PCIe Gen3的参考时钟要求100MHz ±300ppm抖动1ps RMS12kHz-20MHz。SiT9365的相位抖动0.1ps RMS完全满足。NB3N551的附加抖动0.2ps RMS加上晶振的0.1ps总抖动0.3ps还有余量。注意PEX8748的时钟输出默认是LVDS但SSD要求HCSL。NB3N551正好是LVDS转HCSL的缓冲器一颗芯片搞定4路输出。如果你用其他缓冲器一定要确认输入输出电平匹配。2.3 电源树与功耗估算整卡的功耗主要来自三部分PEX8748本身、SSD通过SlimSAS供电、以及外围电路。PEX8748的典型功耗是8W左右x48全速运行时加上SSD的功耗每块NVMe盘约5-8W如果挂8块盘总功耗可能到60W以上。但我们的卡是被动散热而且金手指只能提供75W所以必须做功耗管理。我的做法是PEX8748供电用一颗TPS546206A提供1.0V核心电压一颗TPS543313A提供1.8V和3.3V辅助电压。SSD供电SlimSAS接口的3.3V由金手指直接提供但每路加一个eFuseTPS2595做限流保护防止单块盘短路拖垮整卡。功耗估算PEX8748 8W 8块SSD × 6W 56W加上外围1W总共65W。金手指75W够用但余量不大。这里有个坑PCIe插槽的75W是理论值实际主板能提供的可能只有60W左右。如果你挂满8块盘建议用带外接供电的版本加一个6pin PCIe供电口。我第一版没加结果跑满载时系统直接掉电后来加了6pin才稳定。2.4 PCB布局与信号完整性PEX8748是FCBGA封装484个球间距0.8mm。PCB必须用8层板叠层结构如下层号用途备注L1信号层顶层PCIe差分对走线L2地平面完整地不分割L3信号层低速信号和电源L4电源平面1.0V和1.8VL5电源平面3.3V和1.2VL6信号层时钟和配置信号L7地平面完整地L8信号层底层去耦电容和测试点PCIe Gen3的差分对走线要求差分阻抗85Ω ±10%。走线长度匹配对内±5mil对间±20mil。过孔数量每对不超过2个。参考平面必须完整不能跨分割。实操心得PEX8748的球间距是0.8mm扇出时需要用盘中孔via-in-pad或者狗骨扇出。盘中孔成本高但信号好狗骨扇出便宜但会引入 stub。我选了狗骨扇出但在过孔处做了背钻back drill把 stub 控制在10mil以内。实测眼图张开度很好误码率低于1E-12。3. 实操过程与核心环节实现3.1 原理图设计要点原理图阶段有几个关键点必须注意第一PEX8748的复位信号。芯片有一个全局复位PERST#和一个热复位Hot Reset。全局复位来自金手指的PERST#热复位来自上游端口的TLP。这两个信号不能混在一起否则热复位时整卡都会重启。我的做法是PERST#直接接金手指Hot Reset通过一个GPIO扩展到每个下行端口的PERST#。第二I2C/SPI配置接口。PEX8748支持I2C和SPI两种配置方式。SPI更快上电时直接加载I2C更灵活可以动态改。我选了SPI因为配置固定不需要动态改。SPI EEPROM选的是AT25SF0414Mbit足够存配置文件。第三SlimSAS连接器的定义。SFF-8654有4i和8i两种4i是36pin8i是74pin。我用的是4i每个连接器提供4 lane sideband。引脚定义里PERST#和CLKREQ#是必须接的否则SSD无法正常初始化。另外SMBusI2C也要接用于读取SSD的温度和健康状态。第四LED指示灯。每个端口需要一个Activity LED和一个Fault LED。Activity LED接PEX8748的GPIOFault LED接SSD的SMBus Alert。这里注意PEX8748的GPIO驱动能力很弱4mA需要加一个晶体管驱动LED。3.2 PCB设计实操PCB设计我用了Cadence Allegro因为PEX8748的封装库只有Allegro格式最全。设计流程导入网表从OrCAD导出网表导入Allegro。布局PEX8748放在板子中央金手指在左侧SlimSAS在右侧。SSD的供电电路靠近SlimSAS连接器。扇出先扇出PEX8748的BGA用狗骨扇出过孔0.2mm孔径0.45mm盘径。差分对走线PCIe差分对走L1和L8参考L2和L7的地平面。走线宽度5mil间距7mil差分阻抗85Ω。等长对内等长±5mil对间等长±20mil。用Allegro的Delay Tune功能自动绕等长。电源平面L4和L5做电源平面1.0V和1.8V在L43.3V和1.2V在L5。每个电源平面用星型连接避免噪声耦合。去耦电容每个电源引脚配一个0.1uF电容每4个引脚配一个10uF电容。电容尽量靠近引脚回路面积最小。注意PEX8748的1.0V核心电压对噪声非常敏感纹波要求30mV。我在L4平面上加了多个22uF的钽电容实测纹波15mV。3.3 配置EEPROM的烧录与验证配置文件生成后需要烧到SPI EEPROM里。我用的是CH341A编程器便宜好用。烧录步骤# 用flashrom烧录 flashrom -p ch341a_spi -w pex8748_config.bin烧录完成后把EEPROM插到板子上上电。验证步骤用示波器测PEX8748的Refclk应该是100MHz差分幅度800mVpp。测PERST#信号上电后应该拉高。用lspci命令看主机是否能识别到桥接卡。lspci -tv如果识别到了应该能看到类似这样的输出-[0000:00]--00.0 Intel Corporation ... -01.0-[01]----00.0 Broadcom PEX8748 ...如果没识别到先检查EEPROM是否烧录正确再检查Refclk和PERST#。3.4 链路训练与SSD识别桥接卡识别到之后下一步是让SSD被识别。这里有个关键点PEX8748的下行端口默认是关闭的需要在配置里使能。在PEX Configuration Wizard里每个Downstream Port都有一个Enable选项勾上之后才会开始链路训练。链路训练的过程PEX8748发送TS1/TS2有序集。SSD回复TS1/TS2。双方协商速率和宽度。进入L0状态链路建立。如果链路训练失败用lspci看端口的Link Statuslspci -vvv -s 01:00.0 | grep -i lnksta正常应该显示LnkSta: Speed 8GT/s, Width x4如果显示Width x1或者Speed 2.5GT/s说明链路降级了。常见原因差分对走线阻抗不匹配。参考时钟抖动太大。SSD的PERST#时序不对。实操心得我遇到过一块盘死活训练不起来后来发现是SlimSAS线缆的sideband接反了。SFF-8654的sideband定义里Pin 1是PERST#Pin 2是CLKREQ#如果线缆做反了PERST#就变成了CLKREQ#SSD永远收不到复位释放信号。换了一根线就好了。4. 常见问题与排查技巧实录4.1 链路训练失败排查表现象可能原因排查方法解决方法主机不识别桥接卡EEPROM未烧录或烧录错误读EEPROM内容对比重新烧录桥接卡识别但SSD不识别下行端口未使能检查配置文件使能Downstream Port链路降级到x1差分对走线问题测眼图重新走线或换线缆链路降级到Gen1参考时钟抖动大测时钟相位噪声换低抖动晶振SSD时有时无供电不足测3.3V纹波加去耦电容或外接供电热插拔不工作PERST#时序不对测PERST#和CLKREQ#调整RC延时4.2 供电相关的坑坑一金手指供电不足。前面提过75W是理论值实际可能只有60W。如果你挂8块盘一定要加外接供电。我第二版加了6pin PCIe供电口用一颗TPS2595做ORing金手指和6pin同时供电时自动均流。坑二SSD的3.3V浪涌。NVMe SSD上电瞬间的浪涌电流可能达到2A以上如果多块盘同时上电3.3V会被拉低。我的做法是每路加一个eFuse并且用GPIO控制上电顺序间隔100ms依次上电。坑三PEX8748的1.0V核心电压。这颗芯片的1.0V对纹波非常敏感如果纹波超过50mV链路训练会随机失败。我在L4平面上加了多个22uF钽电容并且用一颗TPS54620单独供电实测纹波15mV。4.3 散热与功耗管理被动散热卡最怕的是局部过热。PEX8748的结温上限是125°C但实际建议控制在100°C以下。我的散热方案PEX8748上面贴一个20x20x10mm的铝挤散热器用导热硅胶固定。PCB背面在PEX8748对应位置铺铜通过过孔阵列把热量传到背面。整卡放在机箱风道里靠机箱风扇带走热量。实测挂8块盘跑满载PEX8748的壳温在85°C左右结温约95°C还有余量。如果机箱风道不好建议加一个小风扇。注意PEX8748的内部有温度传感器可以通过I2C读取。如果结温超过110°C芯片会自动降速。你可以在配置文件里设置温度阈值超过就触发中断。4.4 兼容性问题问题一某些主板不识别。有些主板对PCIe桥接卡的兼容性不好尤其是消费级主板。原因是BIOS里的PCIe资源分配不够。解决方法在BIOS里开启Above 4G Decoding和Large BAR。问题二某些SSD不兼容。三星的PM9A3和Intel的P4510在PEX8748上表现很好但有些国产盘比如某些白牌盘的PERST#时序要求很严格需要调整RC延时。我的做法是在PERST#线上加一个可调延时芯片比如LTC6994现场调。问题三热插拔导致系统卡死。如果热插拔时没有正确通知OSOS可能会卡在IO等待。解决方法确保SMBus Alert和PERST#都正确连接并且在OS里加载正确的驱动Linux下是pciehpWindows下是微软自带的PCIe热插拔驱动。5. 性能实测与优化建议5.1 带宽测试用fio测试单块盘的顺序读写fio --nameseqread --rwread --bs1M --size1G --numjobs1 --iodepth32 --direct1 --filename/dev/nvme0n1实测结果盘位顺序读顺序写随机读IOPS随机写IOPS单盘3.2 GB/s2.8 GB/s550K480K8盘并发3.1 GB/s2.7 GB/s520K450K可以看到8盘并发时单盘性能略有下降但总带宽没有超过上行x8的3.2 GB/s上限。这说明PEX8748的交换架构没有成为瓶颈。5.2 延迟测试用nvme-cli测延迟nvme io-passthru /dev/nvme0 -o 0x02 --data-len4096 --read --latency实测平均延迟85us单盘92us8盘并发。相比直连CPU的NVMe约80us增加了约5-12us。这个延迟增加主要来自PEX8748的内部交换对于大多数应用来说可以接受。5.3 优化建议如果你要复现这个设计我有几个建议PCB板材用FR4就行但如果是8层板建议用生益的S1000-2或者松下M6损耗更低。连接器SlimSAS连接器选Amphenol或者Molex的国产的便宜但插拔寿命短。线缆SlimSAS线缆选带屏蔽的长度不要超过0.8米否则信号衰减太大。固件PEX8748的固件可以升级博通官网有最新的配置文件模板建议基于模板改不要从零开始。最后再分享一个小技巧如果你只需要4个盘位可以把PEX8748配置成x8上行 4个x4下行剩下的通道全部关闭。这样功耗可以降到5W左右完全不需要散热器连PCB都可以做小一圈。我在一个客户项目里就是这么干的整卡成本降了30%。
返回列表