交换芯片架构解析:Slice、Flex Tile与智能缓冲转发机制 简介这份PDF整理自思科Live技术讲座BRKARC-3222面向数据中心网络工程师、思科认证备考者以及希望深入理解Nexus 9000硬件架构的技术人员重点解析最新一代模块化与Top-of-Rack交换机的芯片级设计。内容围绕云规模ASIC展开覆盖Nexus 9500模块化平台、Nexus 9300 TOR交换机及X9400、X9600-R等型号的交换结构、转发特性与硬件加速能力并对比商用硅片方案与思科自研芯片在功能、规模和成本上的取舍。讲座由思科杰出工程师Tim Stevenson主讲结合Packet Walks说明数据包在交换机内部的完整处理路径并涉及智能缓冲区、流遥测、隧道封装、QoS以及ACI策略模型等机制便于读者理解性能优化和故障定位思路。压缩包共1个PDF文件大小约3.56MB适合离线阅读、专题查阅和架构复盘。目前已有286人学习可作为数据中心网络选型、部署与排错时的参考资料。1. 6.4T 的交换芯片在硬件眼里其实是四台 1.6T 的交换机一块标称 6.4Tbps 的交换芯片端口面板上写着 64 个 100G很多人会默认它内部是一整块 6.4T 的转发引擎。实际上这 6.4T 是切出来的芯片内部被划成 4 个自包含的 slice每个 slice 负责 16 个 100G 端口各自有独立的入口查表流水线、独立的出口缓冲与调度器slice 之间靠一层 slice interconnect 做 any-to-any 互联。换句话说一颗芯片在硬件层面更像四台 1.6T 交换机拼在一起只是共享了封装和电源。这个事实决定了后面几乎所有容量数字的解读方式表项怎么分、缓存怎么分、加密模块放在哪一级、跨 slice 流量为什么可能比本地流量多一跳。2018 年那份芯片级讲义把这一层拆得极细值得顺着它的思路往下走一遍。2. Slice 互联与转发流水线一个包在芯片里到底走了几步把一个数据包从端口送进芯片到它从另一个端口出去中间发生的事比查表—转发四个字多得多。要讲清楚这条路径得先接受一个前提芯片不是一块均匀的逻辑而是若干结构相同的 slice 复制体每个复制体内部又是一条固定的流水线。2.1 每个 slice 都是自包含的转发复合体按讲义的定义slice 是一个控制单颗 ASIC 上某一部分端口的、自包含的转发复合体内部被切成 Ingress 和 Egress 两块功能域。Ingress 侧从前到后依次是包解析器Packet Parser、入口 MAC 处理、查表流水线Lookup Pipeline、入口分类、转发查表、TCAM、Flex Tile、流表Flow Table仅部分型号具备、负载均衡与 AFD/DPP 这类缓冲决策逻辑。Egress 侧则是出口缓冲、队列与调度、复制组播/广播、出口 MAC、报文重写、出口策略。这个切分的动机不难理解。交换机的转发决策是入口做一次、出口做一次的两段式模型入口关心的是这包该去哪出口关心的是这包怎么发出去、发不发得出去。把两段逻辑物理上放到独立的控制器里好处是入口侧的表项查找和出口侧的队列管理不会互相抢资源一个端口在拥塞不应该拖慢另一个端口的路由查找一个 slice 的查表流水线打满也不应该让别的 slice 的出口调度失速。提示讲每个 slice 有独立入口和出口控制器时容易漏掉的一点是——入口查表的结果要跨过 slice interconnect 才能到达目标 slice 的出口。这条跨片路径是理解后续所有本地转发 vs 跨片转发差异的根。再看 slice 之间的连接方式。讲义明确写了两条每个 slice 的 ingress 都连到所有 slice 的 egressslice interconnect 提供的是非阻塞的 any-to-any 互联。这句话的分量比它看起来重——它保证了任意端口到任意端口的流量在 fabric 内部不会因为跨片而被结构性阻塞。换句话说切片是一种组织结构不是一种带宽折损。但非阻塞不等于零代价。跨片流量比本地流量多走一段互联路径多占一份互联带宽。当流量模型是每个 slice 上都有若干服务器彼此全互联时互联上的负载会显著上升。这也是为什么在规划端口分布时同一条业务链路上的机器尽量落在同一个 slice 覆盖的端口组里——不是因为跨片不能通而是因为跨片会让互联层提前成为热点。2.2 一条流水线的六个站逐站拆开看把 Ingress 和 Egress 串起来一个单播包大致要经过这几站解析从以太头开始逐层解析识别出 MAC、VLAN、IP、L4 端口构造出后面查表要用的 key。入口 MAC 判断目的 MAC 是不是本设备的路由器 MAC如果是触发三层查表如果不是走二层桥接路径。这一步是路由还是交换的分叉点。查表硬件对 VRF 做精确匹配、对目的 IP 做最长匹配返回一个 adjacency 指针或者 ECMP 指针。ECMP 指针再进 ECMP 表选出具体下一跳。跨片把查表结果连同报文本体送到出方向的 slice。出口缓冲与调度进队列、按优先级和权重排队、被调度器选中发送。组播还要在这里做复制。重写与出口策略改 MAC、压/弹标签、做出口 ACL、打遥测标记然后从出口 MAC 发出。讲义里那张 IP 单播转发的图把第 2、3 步的依赖关系画得很清楚先用目的 MAC 命中路由器 MAC才触发三层查表三层查表返回的结果不是一个端口号而是一个指针——指向 MAC 表也就是邻接表的 ADJ_PTR或者指向 ECMP 组的 ECMP_PTR。MAC 表里存的才是出口 BD、重写后的目的 MAC 和出口端口。这个两级间接的设计是硬件转发的经典做法路由前缀的数量和邻接的数量解耦同一条路由可以指向多个邻接同一个邻接可以被多条路由共享表项利用率高。用一段 Python 把这条查表链模拟出来能更直观地看到指针是怎么走的# 用最小数据结构模拟硬件里的三级查表路由 - 邻接 / ECMP - 出口信息 ROUTER_MAC 00:1b:2c:00:00:01 # 第一级LPM 表key 是 (VRF, 目的IP)value 是邻接指针或 ECMP 指针 lpm_table { (vrf-blue, 10.10.0.0/16): {type: adj, ptr: 101}, (vrf-blue, 10.20.0.0/16): {type: ecmp, ptr: 7}, } # 第二级邻接表MAC 表存出口 BD、重写 MAC、出口端口 adj_table { 101: {bd: 200, rewrite_dmac: aa:bb:cc:00:00:11, port: Eth1/1}, 102: {bd: 200, rewrite_dmac: aa:bb:cc:00:00:12, port: Eth1/2}, } # 第二级ECMP 组成员是邻接指针 ecmp_table { 7: [101, 102], } def longest_prefix_match(vrf, dst_ip): 硬件做的是并行前缀匹配这里用线性扫描近似只表达语义 best, best_len None, -1 for (v, prefix), val in lpm_table.items(): if v ! vrf: continue net, length prefix.split(/) length int(length) if dst_ip.startswith(net.rsplit(., 1)[0]) and length best_len: best, best_len val, length return best def forward(dmac, vrf, dst_ip): # 第一步目的 MAC 是否是路由器 MAC决定走三层还是二层 if dmac ! ROUTER_MAC: return {path: L2-bridge} # 第二步LPM 查路由 route longest_prefix_match(vrf, dst_ip) if route is None: return {path: drop-no-route} # 第三步按指针类型解析到邻接 if route[type] adj: adj_ptr route[ptr] else: # ECMP 组内选一个成员硬件用哈希保证同流同路径 members ecmp_table[route[ptr]] adj_ptr members[hash((dst_ip, 12345)) % len(members)] adj adj_table[adj_ptr] return {path: L3, out_bd: adj[bd], rewrite_dmac: adj[rewrite_dmac], out_port: adj[port]} print(forward(ROUTER_MAC, vrf-blue, 10.10.5.9)) # {path: L3, out_bd: 200, rewrite_dmac: aa:bb:cc:00:00:11, out_port: Eth1/1}这段代码里最容易写错的是 ECMP 的哈希输入。硬件为了保证同一个流不出现乱序ECMP 选路必须对流的五元组做哈希而不是对目的 IP 单独哈希一旦你只哈希目的 IP同一对主机之间的多条并发连接就会被压到同一条成员链路上ECMP 形同虚设。上面的代码用(dst_ip, 12345)代替完整五元组只是为了演示语义真实实现里这个元组要包含源 IP、目的 IP、协议号、源端口、目的端口。这个细节在排障时非常关键ECMP 不均衡的问题八成出在哈希字段的配置上而不是链路本身。2.3 复制与组播为什么被放在出口侧讲义的流水线图把复制Replication放在了 Egress 控制器里位置在缓冲调度之后、出口 MAC 之前。这个位置不是随意安排的。如果把复制放在入口侧一个组播包在进入 fabric 之前就被复制成 N 份每份都要单独占用一份跨片带宽和一份出口队列入口侧的压力会随组播组规模线性膨胀。放在出口侧意味着复制发生在已经确定要从哪些端口出去之后入口只处理一份原始报文跨片也只传一份。代价是复制后的每一份都要单独排队、单独消耗出口缓冲所以组播规模大时出口缓冲的压力会更明显。这也解释了一个常见的现象同样的组播流量在单播压力不大的时候跑得好好的一旦出口侧有别的流量造成排队组播的丢包率会突然变高。原因不在组播路径本身而在它和单播共享同一份出口缓冲而复制后的多份报文会放大这份共享资源的竞争。排障时如果只盯着组播组的成员和 IGMP 表项看很容易漏掉这一层。3. Flex Tile把 LPM、主机路由和 ACL 塞进同一池表项如果说 slice 决定了芯片的物理形状那 Flex Tile 决定了它的逻辑形状。这是整套架构里最值得深挖的一层因为它解释了为什么同一颗芯片能同时被配置成互联网对等路由器和数据中心接入交换机这两种差别极大的形态。3.1 表项为什么必须是可拼接的池子传统交换芯片的表项是硬划分的MAC 表固定多少条、路由表固定多少条、ACL 固定多少条。这种划分在流量模型稳定的年代够用但在数据中心里很快就会失衡——做纯二层转发的场景路由表空着一大半MAC 表和 ACL 却打满了做三层边界路由的场景反过来。讲义里给出的解法是 Flex Tile一组数量固定的表项瓦片每片的条目数在芯片之间不同但这些瓦片本身是可互换用途的可以根据配置承担不同的查找功能——IPv4/IPv6 单播的最长前缀匹配、主机路由表、组播的 (*,G) 和 (S,G)、MAC 地址与邻接表、ECMP 表、策略表。这个设计的核心价值在于芯片出厂时并不知道自己要扮演什么角色角色是在系统初始化时通过模板烧进去的。这里有个容易忽略的工程后果因为瓦片的用途在初始化时就固定了改变用途必须重启。讲义里明确写了在系统初始化时定义改配置需要重启。这不是实现上的偷懒而是硬件表项的组织方式决定的——查表流水线的每一级在物理上就对应固定的瓦片组改用途等于改流水线的拓扑运行时改不了。3.2 HRT、LPM、TCAM三条查找路径各管一段讲义把 IP 前缀在硬件里的存储拆成了三种方法这个拆分是理解转发性能的关键。HRT主机路由表是一张哈希表专门存 IPv4 的 /32 和 IPv6 的 /128。主机路由的特点是前缀长度固定天然适合哈希——一次哈希、一次比较命中判定是 O(1)不需要逐级比对。数据中心里大量流量是主机到主机/32 和 /128 占了绝对多数所以把这类表项单独抽出来用哈希处理能让绝大部分查表都走最短路径。LPM处理其余长度的前缀实现上有两种手段要么是传统的前缀 掩码表项直接存要么用pivot trie的组合——先把前缀按某个中间长度切成几段每段用一张小表查的时候逐段收敛。不管哪种本质都是把任意长度的问题转换成若干个固定长度的问题因为硬件没法像软件那样任意地做位比较。TCAM的角色是兜底。哈希会冲突前缀表项会溢出这两类情况最终都落到 TCAM 上。TCAM 的优点是能表达任意掩码的匹配缺点众所周知贵、耗电、容量小。所以它在架构里的位置很明确——不是主力是溢出通道。讲义用front-ending这个词描述它意思是它挡在灵活查表的前面处理那些灵活查表装不下的条目。把这三者串起来看一次地址查找的实际路径是先看这个前缀长度是不是 /32 或 /128是就走 HRT 哈希不是就走 LPM 结构哪条路走不通或者发生冲突回退到 TCAM。这条链路的每一段都有独立的容量上限而这三个上限的配比正是由 Flex Tile 的模板决定的。注意表项溢出到 TCAM 不会导致转发中断但会导致查表延迟上升、TCAM 功耗上升并且在模板切换前这个状态会一直存在。看到 TCAM 利用率持续走高第一反应应该是检查路由模板和实际路由表的匹配度而不是直接扩容。3.3 路由模板一次重启换一种芯片形态讲义列出了当时可用的几套模板默认、双栈主机规模优先、互联网对等、LPM 优先、MPLS 优先、组播优先、组播 NBM。这些名字背后是不同场景下表项配比的经验值。举两个例子对比。双栈主机规模优先这套模板显然是把更多瓦片分配给 HRT让 /32 和 /128 的容量最大化——这是典型的虚拟化数据中心场景成千上万的虚机地址都是主机路由前缀路由相对少。而互联网对等模板反过来要的是 LPM 的容量和收敛速度因为对外通告的路由表是海量的变长前缀。这两套模板在同一种硬件上靠一次重启就互换了性格。配置形态大致如下不同版本语法略有差异参数名以实际系统为准# 查看当前生效的路由模板 show system routing template # 在全局配置下切换模板需要重启生效 configure terminal system routing template dual-stack-host-scale end # 重启后核对各表项的实际容量与占用 show hardware profile status show ip route summary show system internal forwarding table-usage命令的含义需要说清楚。第一条看的是当前芯片被烧成了什么形状第二条是写入期望形状写入后不会立即改变硬件只是把配置记下来第三条show hardware profile status才是关键——它告诉你重启之后模板到底有没有按预期生效以及各张表的实际条目上限。很多人栽在这里改完配置没重启以为生效了结果容量一直是旧的或者重启了但模板因为平台不支持而没有应用系统只在日志里留一行提示没人注意。show ip route summary和table-usage这两条要配合看。前者给你的是软件视角的路由数量后者给你的是硬件表项的真实占用。这两个数字对不上说明有路由没下到硬件或者硬件里有残留表项。这种软件看着有、硬件没下去的情况是路由不通类故障里最费时间的一类因为从控制面看不出任何异常。4. 智能缓冲与流表丢包策略为什么不能只看队列水位转发路径解决的是包该去哪缓冲解决的是包什么时候走、走不了怎么办。这部分在芯片里通常是最不透明的一块因为它不体现为任何一条 CLI 命令的输出只体现为拥塞时的丢包曲线。4.1 共享出口缓冲的两种失败模式现代交换芯片的出口缓冲是共享的所有出口队列从同一个缓冲池里按需取用而不是每个端口预分配固定份额。共享的好处是利用率高——空闲端口的缓冲可以被忙端口借走坏处是两种典型失败。第一种是队头拥堵扩散。某个出口端口拥塞它对应的队列开始堆积如果没有任何限制这个队列会持续吃缓冲池直到把池子吃干其他本来不拥塞的端口也拿不到缓冲于是丢包从一个端口扩散到所有端口。这在现象上非常迷惑明明只有一个端口在打满为什么全网都在丢包。第二种是突发吸收不足。共享池如果分配策略过于保守每个队列能用的份额很小那么即使总池子很空一个微突发microburst也能瞬间打穿某个队列的份额。微突发在监控上通常看不到——采样周期是秒级而微突发的持续时间是微秒级。4.2 AFD、DPP、DBP 各自解决哪一半讲义把智能缓冲归为三个缩写DBP、AFD、DPP。资料里没有展开每个缩写的完整定义按这类芯片的通行做法来理解它们分别对应三种不同层面的控制AFD近似公平丢弃解决的是第一种失败模式。它的思路不是等队列满了再丢而是在队列达到某个阈值之前就对占用资源过多的流做概率性丢弃让吃得多的流提前降速从而把缓冲留给吃得少的流。之所以叫近似公平是因为硬件里没有足够的资源做精确的每流计数只能用近似的数据结构估计每条流的占用。DPP动态包优先级解决的是第二种失败模式的一个侧面。它的思路是在缓冲紧张时优先保住小包和延迟敏感的包先丢大包。这个策略在存储和 AI 类流量里特别有用——大包丢一个的代价小重传一次就行小包往往是控制信令或者 RPC 响应丢了会导致上层超时重试代价远大于一个包的字节数。讲义里把 DPP 和 AFD 并列放在入口侧说明这个判断是在包进入缓冲之前就做掉的。DBP更接近缓冲池本身的动态阈值管理让每个队列能占用的份额随全局占用率浮动池子空的时候允许单队列占大头池子满的时候收紧每个队列的份额。这是防扩散的最后一道闸。用一小段代码模拟 AFD 的概率丢弃逻辑能看清为什么必须提前丢import random def afd_drop_prob(queue_len, threshold, max_p, alpha2.0): 近似公平丢弃的概率计算 queue_len : 当前队列长度字节 threshold : 开始介入的阈值 max_p : 队列打满时的最大丢弃概率 alpha : 曲线陡峭程度越大越晚丢、越接近满才丢 if queue_len threshold: return 0.0 if queue_len threshold * 2: return max_p # 在 [threshold, 2*threshold] 区间内按幂函数上升 ratio (queue_len - threshold) / threshold return max_p * (ratio ** alpha) # 对比两种队列状态下的实际丢弃行为 for qlen in (400, 800, 1200, 1600): p afd_drop_prob(qlen, threshold800, max_p0.1) drops sum(1 for _ in range(1000) if random.random() p) print(f队列 {qlen:5d} 字节 - 丢弃概率 {p:.3f}, 千包样本实际丢弃 {drops})这段代码的关键在alpha这个指数。当它等于 1 时丢弃概率随队列长度线性上升结果是队列刚过阈值就开始大量丢包吞吐掉得很快当它大于 1 时曲线是凸的队列在阈值附近时丢弃概率极低越接近打满才越激进。工程上调这个参数的方向通常是延迟敏感的业务希望曲线更凸晚丢、丢得集中吞吐敏感的业务希望曲线更平早丢、丢得分散让发送端平滑降速。这就是为什么同一个缓冲机制在不同业务下表现差异巨大也让配置一样但效果不一样成了常见的困惑来源。4.3 流表与遥测把芯片本身变成探针讲义里提到流表Flow Table只出现在部分型号上同时提到 SSX流式统计导出只出现在更大的那两颗芯片上。这两个特性的意义不在于转发而在于观测。传统交换机的统计是按端口计数、按秒采样你只能知道某个端口在这一秒发了多少字节不知道这些字节属于哪些流。流表把这个粒度降到了每条流芯片在转发的同时把五元组、字节数、时间戳记录下来通过流式接口实时导出。对排障来说这是质变——以前要定位是哪条流把链路打满得在两端抓包比对有了流表直接在导出数据里按字节数排序就行。代价是资源。流表要占表项采样要占带宽导出要占 CPU。所以它只在部分型号上提供而且通常需要显式开启。这也解释了为什么同一个系列的交换机转发性能看起来一样可观测性却差一个档次——差别不在转发流水线在旁路的观测通路。5. 常见问题与排查模板、表项和 slice 上的五个坑这一节是从实际踩过的坑里整理出来的。每条都按现象—原因—解决写因为排障时人最先拿到的是现象最缺的是原因。坑一改了路由模板容量没变现象把模板从默认切成主机规模优先重启后show ip route summary显示的主机路由上限还是老数字。原因模板写入的是期望配置真正烧进硬件发生在系统初始化阶段。如果重启过程中有配置回滚或者启动镜像不支持这个模板系统会静默回退到默认模板只在启动日志里打一行提示。解决重启后必须核对show hardware profile status看 active template 一栏是不是你期望的值而不是看 running-config。另外切换模板前先确认平台型号在支持列表里——模块化机箱和 TOR 的支持范围不一样。坑二双栈主机模板下组播不通现象为了提升主机路由容量切到双栈主机模板结果原本正常的组播业务大面积收不到流量。原因讲义在模板列表里用脚注标明了该模板不支持 IP 组播。主机规模优先意味着把瓦片几乎全部分给了 HRT没有余量再承载 (*,G) 和 (S,G) 表项。解决这类互斥要在规划阶段就确认。如果业务同时需要大主机表和组播要么选一个折中模板要么把组播功能放到另一台设备上承担。切换前用测试流量验证一遍组播别等上线后发现。坑三模板选错平台功能直接不可用现象在 TOR 上配置组播 NBM 模板命令能敲进去但功能不生效。原因讲义明确标注了某些模板不支持模块化机箱或不支持 TOR。这些限制来自硬件差异——模块化机箱的线卡和 TOR 的芯片虽然同属一个家族但瓦片数量和互联结构不同。解决选模板前先查该平台的支持矩阵不要假设同系列就同能力。命令能敲进去不等于硬件能实现这是网络设备里最常见的认知偏差之一。坑四/32 主机路由和前缀路由表现不一致现象同一个目的地址有时走直连、有时走默认路由转发路径飘忽。原因/32 走 HRT 哈希其他长度走 LPM两条路径是独立的表。如果某个 /32 没有正确下到 HRT它会回退到 LPM 里匹配到一条更短的前缀于是走了完全不同的下一跳。哈希冲突被挤到 TCAM 的条目也会出现类似的路径偏移。解决用show system internal forwarding table-usage看 HRT 的占用和冲突计数。如果冲突计数在持续增长说明哈希空间不够要么换模板要么把这类主机路由改成更短的前缀聚合。坑五MACsec 只在特定 slice 型号上有现象同系列的两款设备一台上能开链路加密另一台命令都没有。原因讲义在芯片家族列表里给某些型号标注了 with MACSEC给另一颗标注了 MACSEC CloudSec。加密模块是物理集成在 slice 里的不是软件许可开关。解决选型阶段就要把加密需求写进硬件规格不能按同系列应该都有来假设。这一条对合规场景尤其致命——设备到货了才发现不支持整个方案要重做。6. 自研 ASIC 与商用硅片的取舍什么时候该为可编程的表付钱把讲义里那张产品组合图摊开看会发现同一个系列里并存三条芯片路线自研的云规模 ASIC、商用的 XGS 系列走公开 SDK 的标准路线、商用的 DNX 系列多芯片、大表、深缓冲、基于信元的 fabric。这三条路线不是新旧替代关系而是三种不同的取舍。维度自研云规模 ASIC商用 XGS 路线商用 DNX 路线表项灵活性高瓦片可按模板重组中容量配比相对固定高但靠多芯片堆出来缓冲深度共享出口缓冲 智能丢弃常规共享缓冲深缓冲 VOQ抗突发强加密能力部分型号内置 MACsec/CloudSec通常需外置或选型视具体型号遥测粒度流表 流式统计导出依赖商用芯片能力依赖商用芯片能力典型定位数据中心接入与汇聚策略与遥测要求高通用场景生态成熟大表、大缓冲的边界与骨干这张表最值得琢磨的是第一行和第四行。自研路线的核心竞争力不在端口密度——商用芯片的端口密度从来不含糊——而在于表项可以按场景重组和转发通路旁边能挂一条观测通路。这两件事只有把芯片设计和软件策略模型放在同一个团队里做才可能对齐。讲义里提到的单次隧道封装、基于拥塞感知的流片级负载均衡、内置加密都属于同一类收益这些功能如果走商用芯片要么等厂商排期要么用外置器件补齐中间的性能损耗和集成复杂度都很可观。但自研的代价也很清楚。换代节奏由自己控制意味着每一代都要重新验证一遍所有转发路径表项模板这种重启才生效的机制在多租户环境里是运维负担芯片内部的诊断信息不公开出问题时能依靠的只有厂商自己的工具链。商用路线的优势恰恰在这——公开的 SDK、成熟的生态、广泛的第三方验证。所以你会看到同一个产品组合里两条路线并存不是摇摆是按场景分工。我从这份资料里学到的最有用的一件事是判断一个平台能力时不要看端口数字要看三个地方表项能不能重组、缓冲是不是共享并且有主动丢弃策略、转发通路旁边有没有独立的观测通路。这三个问题的答案决定了这台设备在拥塞、故障和安全事件面前是能自证还是只能猜。从那以后我每次评估交换平台都会先把这三项写成清单逐条确认不管厂商的宣传材料写得多漂亮——因为端口数字是最好写的而表项配比和观测粒度是藏不住的。希望帮到你。本文还有配套的精品资源点击获取