凌晨两点半接到值班电话是种什么体验?我印象最深的一次,是电话那头说“全网都断了”,远程登上一台汇聚交换机,CPU占用99%,所有端口指示灯都在疯狂闪烁,敲一条命令要等十几秒才有响应。查到最后,原因让人哭笑不得——机房整理线缆时,有人觉得“多加一根线更保险”,随手用一根跳线把两台交换机又连了一道。就是这一根多余的线,让整个二层网络直接瘫痪。
这类事故,干网络的迟早会遇到。而解决它的核心机制,就是标题里这个必须吃透的名字:生成树协议(STP)。
这篇是“0基础入门网络工程师必学知识”系列的第12篇。我把STP和它的加强版RSTP从头到尾梳理了一遍,内容包括:二层环路为什么致命、STP的四个选举步骤、端口状态机与收敛时间、软考和面试的常见考点、以及一次环路事故的完整排查复盘。准备入行网络、备考软考、或者面试网络工程师岗位的朋友,这篇可以当复习提纲直接看。
1. 环路怎么毁掉一个二层网络:先理解STP存在的理由
很多初学者学STP时容易犯一个毛病——上来就背“选根桥、选根端口、选指定端口”,背了一堆概念,却不知道这东西到底是干什么的。所以我先不聊协议本身,先聊一个更根本的问题:没有STP的二层网络,一旦出现物理环路,会发生什么。
1.1 二层网络为什么比三层网络更怕环路
三层网络(IP层)也有环路风险,但IP报文头部有个TTL字段,每经过一台路由器就减1,减到0直接丢弃。哪怕路由表出了环路,报文转几圈就会被丢掉,网络最多是部分不通,不会形成无限循环。
二层以太网帧没有TTL。交换机转发数据帧,靠的是MAC地址表,查不到目的MAC就向所有端口泛洪。这个“泛洪”机制在正常拓扑下没问题,但一旦拓扑里出现物理环路,问题就来了:一个广播帧会从交换机的一个端口进来,再从其他所有端口发出去,绕一圈又从另一个端口收到同一份副本,然后继续转发。每一轮都是一次指数级复制。
这就是广播风暴。可以想象成在一个密闭房间里放了两个对着喊的喇叭,声音不会自己消除,只会来回震荡,越来越大,直到把房间彻底淹没。广播风暴的结果是:链路带宽被占满、交换机CPU耗尽、终端设备因为处理海量广播帧而死机或网卡狂转,整个网络陷入瘫痪。
1.2 环路引发的三大问题,不只是“卡”那么简单
除了广播风暴,环路还会带来另外两个同样致命的问题。
第一个是MAC地址漂移。交换机学习MAC地址,靠的是接收帧的源MAC和接收端口。正常情况下,一个MAC地址只会稳定出现在一个端口上。可一旦有环路,同一台PC发出的帧会从A、B两条路径到达同一台交换机,交换机一会儿在端口1学到这个MAC,一会儿又在端口2学到,MAC表项被反复刷新。结果就是发往这台PC的数据帧不知道该从哪个端口出,转发逻辑完全混乱。
第二个是多帧副本。单播帧在环路拓扑下,也会沿着多条路径到达目的地。接收方网卡可能会收到同一份数据的多个副本,轻则触发网络协议栈的重复帧处理,重则导致上层应用异常。对于依赖以太网的存储、语音、视频业务,这种重复帧带来的链路抖动非常明显。
正因为这几个后果都是灾难级的,网络架构上我们又不能完全不要冗余链路——毕竟只有一条线的话,线断了网络就单点故障了。于是STP的出现就很自然了:**允许你物理上多接线,但逻辑上自动阻塞掉其中一条,让它做备用。正常时只用一条活跃路径,链路出问题时再把备用路径启用起来。**这也是生成树这名字的由来,物理拓扑有环没关系,它把逻辑拓扑修整成一棵没有环的树。
2. 生成树协议的核心机制:四个选举步骤彻底讲透
STP的原理绕不开BPDU(Bridge Protocol Data Unit,桥协议数据单元),这是交换机之间互相通信的“投票信”。每台启用了STP的交换机都会周期性地发送BPDU,里面携带的关键信息包括:根桥ID(Root ID)、根路径开销(Root Path Cost)、发送者桥ID(Transmitter Bridge ID)、发送者端口ID(Port ID)等。
搞清楚BPDU里这几个字段,后面的选举就都好理解了。
2.1 BPDU里藏着什么,决定了谁说了算
BPDU里最重要的字段主要有以下几个,这也是考试里很喜欢挖的细节:
| 字段 | 作用 | 比较规则 |
|---|---|---|
| 根桥ID | 声明当前根桥是谁 | 数值最小者更优 |
| 根路径开销 | 发送者到达根桥的开销 | 数值最小者更优 |
| 发送者桥ID | 声称自己是谁 | 数值最小者更优 |
| 发送者端口ID | 从哪个端口发出的 | 数值最小者更优 |
桥ID(Bridge ID)由两部分组成:优先级 + MAC地址。优先级默认是32768,取值范围0到65535,且必须是4096的倍数。优先级数值越小越有优势;如果优先级相同,就比MAC地址,MAC地址越小越有优势。
2.2 第一步:选举根桥
整个STP网络的“最高领导”是根桥(Root Bridge)。选举规则一句话概括:桥ID最小的交换机成为根桥。
每台交换机开机时都认为自己是根桥,会向外发送携带自己桥ID的BPDU。当一台交换机收到邻居发来的BPDU,发现对方的桥ID比自己更小,就会停止声称自己是根桥,转而认可对方,后续BPDU里的根桥ID就改为对方。这个过程持续一段时间后,全网会收敛出唯一一台根桥。
我举个例子。假设有三台交换机A、B、C,优先级都是默认的32768:
- 交换机A MAC地址:0000.0000.0001
- 交换机B MAC地址:0000.0000.0002
- 交换机C MAC地址:0000.0000.0003
三台交换机两两互联,形成一个三角形拓扑。因为优先级相同,直接比MAC地址,A的MAC最小,所以A成为根桥。整个过程不用人工干预,全网自己协商出来。
2.3 第二步和第三步:根端口与指定端口的选举规则
根桥选出来之后,接下来要为每台非根桥选一个根端口(Root Port),也就是这台交换机去往根桥的最优路径出口。
根端口的选举顺序是:
- 比较端口到达根桥的路径开销,开销最小者成为根端口;
- 如果路径开销相同,就比较对端(发送者)的桥ID,桥ID小的优先;
- 如果还相同,就比较对端的端口ID,端口ID小的优先;
- 如果仍然相同,比较本机的端口ID,端口ID小的优先。
继续上面那个三角形拓扑。假设链路都是千兆,路径开销都是4。交换机B有两个途径到达根桥A:直连A的链路,开销4;经C再到A,开销4+4=8。所以B连接A的那个端口成为根端口。交换机C同理,连接A的端口成为根端口。
每个网段/链路上还要再选一个指定端口(Designated Port)。指定端口的任务是负责在该网段上转发BPDU和用户数据。选举规则也是先比根路径开销,再比桥ID,最后比端口ID。根桥上的所有端口默认都是指定端口,因为根桥到达自己的根路径开销是0,其他交换机怎么比都比不过。
2.4 第四步:剩下的端口进入阻塞状态
根端口和指定端口都定下来之后,剩下的端口既不是根端口也不是指定端口,就会被置为阻塞状态(Blocking)。
回到三角形拓扑:A-B链路上,A的端口是指定端口;A-C链路上,A的端口是指定端口;B-C链路上,B的根路径开销是4,C的根路径开销也是4,这时候就比较桥ID,B的MAC地址0000.0000.0002比C的0000.0000.0003更小,所以B连接C的端口是指定端口,C连接B的端口既不是根端口也不是指定端口,进入阻塞。
最终逻辑拓扑变成:A直接连B,A直接连C,B和C之间的链路虽然物理上是通的,但逻辑上被切断作为备用。整个网络变成一棵以A为根的树,所有数据都沿着树的枝干走,环路被消除。
这个四步选举过程是STP最核心的逻辑,建议0基础的朋友拿笔画一遍拓扑,手动算一遍每个端口的角色,比背十遍概念都管用。
3. 端口状态机与收敛时间:为什么STP被叫“慢协议”
STP经常被吐槽“慢”,这个慢不是指BPDU传输慢,而是指从链路故障到备用路径启用,往往需要几十秒时间。这几十秒的来源,就是端口状态机的设计。
3.1 五种端口状态,一次看明白
传统STP中端口有五种状态:
| 状态 | 能否收发BPDU | 能否学习MAC | 能否转发数据 |
|---|---|---|---|
| Disabled | 否 | 否 | 否 |
| Blocking | 只收不发 | 否 | 否 |
| Listening | 能收能发 | 否 | 否 |
| Learning | 能收能发 | 是 | 否 |
| Forwarding | 能收能发 | 是 | 是 |
端口刚启动时,如果它在选举中被确定为根端口或指定端口,会按顺序经历Blocking → Listening → Learning → Forwarding。如果选举结果是要阻塞,就会停在Blocking状态。
为什么要设计Listening和Learning两个过渡状态,而不是直接从Blocking跳到Forwarding?因为端口一旦进入转发,就需要参与数据转发和MAC学习。如果它还没把网络拓扑彻底搞清楚就仓促转发,很可能会把数据帧从错误端口转发出去,甚至再次形成短期环路。所以留出两个15秒的缓冲时间:Listening阶段只跑BPDU,确认自己是根端口或指定端口;Learning阶段开始学习MAC地址,但还不转发数据,这样转发表准备好了再上阵。
3.2 30秒和50秒是怎么算出来的
这里有一个高频考点:STP收敛时间到底是多少?
先看两个关键计时器:
- Max Age(最大老化时间):默认20秒。阻塞端口在这段时间内如果一直没收到更优的BPDU,就会认为上游拓扑发生变化,开始进入Listening。
- Forward Delay(转发延迟):默认15秒。Listening持续15秒,Learning再持续15秒。
如果是最坏情况——根桥发生故障,备用端口等Max Age超时后才开始迁移,那么总时间是:
20秒(Max Age)+ 15秒(Listening)+ 15秒(Learning)= 50秒
如果是端口直接从Down变成Up,不需要等Max Age超时,那么是:
15秒(Listening)+ 15秒(Learning)= 30秒
这50秒在网络世界里简直是天文数字。终端用户的感觉就是:断网之后,等快一分钟才恢复。这也是后来RSTP快速生成树要解决的核心问题。考试如果问“STP收敛最慢多久”,默认答50秒基本不会错。
3.3 拓扑变更通知:链路变化后交换机如何联动
还有一个考点是拓扑变更机制(Topology Change Notification,TCN)。
当某台交换机检测到拓扑发生变化——比如有端口从Blocking进入Forwarding,或者从Forwarding进入Blocking——它不会默默更新自己的转发表,而是会向根桥方向发送TCN BPDU。根桥收到后,会向全网发送设置了TC标志的配置BPDU,通知所有交换机“拓扑变了”。
交换机收到TC标志后,会把MAC地址表的老化时间从默认的300秒(思科默认值)缩短到Forward Delay,也就是15秒。这样做的目的是让所有交换机快速清除旧的MAC表项,重新学习新的转发路径,避免把数据帧一直发往旧的、已经不通的端口。
注意这个细节:**TCN机制缩短的是MAC地址表老化时间,不是让STP收敛变快。**收敛速度和状态机的计时器有关,别把两个概念混在一起。
4. RSTP快速生成树:现代网络的主力协议
STP虽好,但慢是硬伤。50秒的恢复时间放到今天很多业务都受不了。于是IEEE在802.1w标准里定义了快速生成树协议RSTP(Rapid Spanning Tree Protocol)。现在主流交换机的默认模式基本都兼容RSTP或直接在RSTP基础上发展出MSTP,纯传统STP已经很少单独部署了。
4.1 RSTP改了什么:端口角色与端口状态的重构
传统STP的端口角色只有三种:根端口、指定端口、阻塞端口。RSTP把“阻塞”拆得更细,变成四种角色:
- 根端口(Root Port):到根桥的最优路径出口。
- 指定端口(Designated Port):每段链路/网段上的转发端口。
- 替代端口(Alternate Port):收到来自其他交换机更优BPDU的端口,是根端口的备份。根端口挂了,替代端口可以立刻顶上。
- 备份端口(Backup Port):收到自己这台交换机发出来的更优BPDU的端口,是指定端口的备份,通常出现在同一交换机双连同一个网段的场景。
端口状态也从五种精简为三种:Discarding(丢弃)、Learning(学习)、Forwarding(转发)。原来传统STP的Disabled、Blocking、Listening都被合并到Discarding里去了。状态少了,理解起来也更直观。
RSTP还有一个很关键的变化:所有端口都会周期性地发送BPDU,而不是像传统STP那样只有根端口和指定端口才发。同时,一台交换机如果连续3个Hello Time(默认每个Hello Time是2秒,3个就是6秒)没收到邻居的BPDU,就认为邻居失效,不再傻等20秒的Max Age。这直接省掉了一大段等待时间。
4.2 P/A机制:从“等待计时”变成“协商握手”
RSTP最核心的快速收敛机制叫P/A(Proposal/Agreement)机制,中文常叫“提议/同意”。
简单描述一下这个过程:链路上某台交换机的端口想成为指定端口,会先发送一个Proposal(提议)消息,表示“我想在这个网段上转发”。对端收到后,会检查自己有没有更好的路径到根桥。如果没有,对端就会把自己这边的非边缘端口阻塞掉,然后回复一个Agreement(同意)消息。发送方收到Agreement后,立即进入Forwarding状态,不需要等一个又一个15秒。
这个过程有点像两个人过独木桥:一个人先说“我先走”,另一个人看看情况说“行,你走,我停着”,第一个人直接跑过去。整个过程在几个BPDU交互内完成,收敛时间从秒级直接降到毫秒级。
注意,P/A机制有个前提条件:链路类型必须是点到点(Point-to-Point),也就是交换机之间是直连的。如果中间挂着集线器(共享链路),RSTP会退化为传统STP那种慢收敛方式。所以在实际交换机配置里,确认互联端口是否被识别为point-to-point链路挺重要,全双工模式通常都能被自动识别,但如果是半双工或共享端口就得检查了。
4.3 边缘端口:接PC的口别再傻等30秒
RSTP里另一个非常实用的概念是边缘端口(Edge Port)。
接入层交换机那些连接PC、打印机、IP电话的端口,下面根本不会再接交换机,按理说没必要参与生成树计算。如果不管它,每次电脑开机网口up,端口都要经历Listening和Learning,大概30秒才能上网。用户会觉得“这交换机是不是坏了”。
如果把端口设置为边缘端口,端口一up就直接进入Forwarding状态,秒开。这是所有接入交换机上都应该做的配置。
但“边缘端口”有个隐含风险:如果有人把一台交换机插到了这个口上,就会形成环路。所以边缘端口必须配合另一个保护机制,BPDU Guard,下面会细说。
配置方面,思科和华为略有差异。思科接口模式下:
interface GigabitEthernet0/1 spanning-tree portfast spanning-tree bpduguard enable华为交换机接口模式下:
interface GigabitEthernet0/0/1 stp edged-port enable华为的BPDU保护是全局配置:
stp bpdu-protection配置了edged-port的端口一旦收到BPDU,就会被shutdown进入error-down状态,从物理上避免从一个“看似安全的接入端口”长出环路来。
5. 软考和面试里的STP考题,实际上都围绕这几个点
5.1 选择题最爱考的桥ID与开销
软考网络工程师里STP题目非常稳定,基本围绕着桥ID、路径开销和端口状态出题。
常见考法一:给你几台交换机的优先级和MAC地址,问谁是根桥。这种题只要抓住“先比优先级,再比MAC,越小越优”就不会错。
常见考法二:给你一条链路带宽,问路径开销是多少。802.1D标准下:10Mbps开销100,100Mbps开销19,1Gbps开销4,10Gbps开销2。这个表最好背下来。
常见考法三:问某台非根交换机的根端口怎么确定。记住那四个比较步骤:路径开销、发送者桥ID、发送者端口ID、本机端口ID。
我统一整理在一张表里,方便复习:
| 考点 | 规则 | 细节 |
|---|---|---|
| 根桥选举 | 桥ID最小者 | 优先级数值小优先,再比MAC小 |
| 根端口选举 | 到达根桥最优路径 | 路径开销 → 对端桥ID → 对端端口ID → 本机端口ID |
| 指定端口选举 | 每个网段最优 | 根路径开销 → 桥ID → 端口ID |
| 路径开销 | 带宽越大开销越小 | 10M=100,100M=19,1G=4,10G=2 |
| 端口状态迁移 | 阻塞→监听→学习→转发 | 最终阻塞的是既非根又非指定的端口 |
| 收敛时间 | 50秒最坏 | 20秒Max Age + 15秒监听 + 15秒学习 |
5.2 面试官更爱问的“为什么”和“怎么办”
面试题和笔试不太一样,不会让你背表格,而是会换个场景问理解。
比如:“如果网络里出现环路,你作为网络工程师怎么排查?”回答思路应该是:先看现象(广播风暴、MAC漂移、端口流量异常),再用命令找阻塞端口、看日志里的MAC地址漂移记录,最后物理上逐段拔线定位。不要只回答“用STP”,而是要展现出你有实际排查链路的能力。
再比如:“RSTP为什么比STP快?”光答“P/A机制”还不够,最好能顺带说出RSTP所有端口都发BPDU、6秒超时、替代端口/备份端口角色这些细节,显得你是真懂,而不是背了概念。
还有一个高频追问:“如果新接入一台优先级更低的交换机,网络会发生什么?”很多人会答“它会成为新根桥”,这只是第一步。面试官真正想听的是后果,新根桥位置如果不在核心层,会导致整个网络的流量路径发生大调整,可能出现次优路径甚至短时中断。问到这一步,你就可以顺势说出Root Guard保护机制:在核心交换机面向接入侧的端口上启用根保护,一旦收到更优的BPDU,端口会被置为阻塞状态,防止新设备抢根桥角色。
5.3 厂商差异:思科和华为的默认模式与配置命令
国内网络环境里,思科和华为的设备最常见,两家在STP上的默认行为有一点不同,需要留意。
思科交换机默认运行的是PVST+(Per-VLAN Spanning Tree Plus),也就是每个VLAN单独跑一棵生成树,不同VLAN可以有不同的根桥,实现负载均衡。思科新一些的设备可以配置为Rapid PVST+:
spanning-tree mode rapid-pvst指定根桥的常用命令:
spanning-tree vlan 10 root primary spanning-tree vlan 10 root secondary查看生成树状态:
show spanning-tree show spanning-tree summary show spanning-tree blockedports华为交换机默认运行的是MSTP(Multiple Spanning Tree Protocol,多生成树协议),它可以把多个VLAN映射到同一个生成树实例上,既保留VLAN负载均衡能力,又比PVST+节省资源。MSTP向下兼容RSTP和STP。
华为指定根桥:
stp mode rstp stp root primary stp root secondary stp priority 4096查看生成树状态:
display stp brief display stp root display stp interface GigabitEthernet0/0/1配置这种东西死记硬背容易混,最好手里有模拟器(比如华为eNSP、思科Packet Tracer),把拓扑搭出来实际敲一遍命令,看状态输出,比背十遍都管用。
6. 真实网络里STP故障排查:一次环路事故的完整复盘
最后一章,回到开头那个深夜故障。我用一次实际环路的排查过程,把命令、现象和思路串起来。这不是虚构的教学案例,而是很多网络工程师都经历过的真实场景。
6.1 事故现象与第一反应
那天晚上的现象非常典型:
- 核心交换机CPU占用率接近100%,远程登录延迟极大;
- 所有交换机端口流量异常,哪怕没有业务的VLAN也有大量报文;
- 日志里不断出现MAC地址漂移记录,同一个MAC在两个端口之间反复跳变;
- 全网终端上网卡顿,部分业务直接不可用。
遇到这种情况,第一反应应该是判断“大概率是二层环路”,而不是去重启设备。重启核心交换机只会让情况更糟——启动过程中STP重新收敛,又是几十秒,而且环路根源不排除的话,起来之后还会再被打垮。
我当时的第一件事是尝试登录交换机,用命令确认环路。虽然远程很卡,但show命令还是能慢慢敲出来:
show spanning-tree blockedports正常网络里,这台核心交换机上应该有若干个阻塞端口。但那个时刻,几乎看不到被阻塞的端口,说明原本该被切断的备份路径全部处于转发状态。这是环路的最直接证据。
6.2 用命令和抓包定位环路
确认环路后,接下来定位端口。我的排查顺序是:
- 看MAC地址漂移日志。日志里如果反复出现某个MAC地址在端口Gi0/1和Gi0/2之间漂移,说明这两个端口之间大概率存在环路路径。
- 查看端口流量统计。用show interface看每个端口的输入输出速率,找到流量异常飙高的端口。环路报文会集中在环路路径上,流量激增的端口往往就是环路两端。
- 拔线验证。如果平台允许短时操作,把怀疑是环路新增链路的那根线拔掉,观察交换机CPU和端口流量是否立刻下降。注意,拔线之前最好有变更窗口,否则这种操作本身也可能引发一次STP收敛。
那晚的逻辑链很清楚:新增的那根跳线,把两台汇聚交换机直接连通,而这两台交换机之间本来就已经通过核心交换机形成了另一条路径。一根线制造了一个物理环路,STP理论上应该能挡住它,可为什么没挡住?
顺着这个疑问查下去,发现新接入的那台交换机虽然是默认开启了STP,但因为这台交换机之前可能被手动改过优先级,导致它成了新的根桥。新根桥位置不在核心层,整个网络的STP拓扑被打乱,加上BPDU在经过一段光纤链路传输时出现了延迟,部分交换机还在等待旧BPDU老化,结果备用端口抢先进入了Forwarding状态,环路就这样形成了。
6.3 防止环路再次发生的四个手段
踩过坑之后,我给你分享几条真实有效的防护组合,可按顺序打在设备上。
**第一,接入端口全部开启PortFast + BPDU Guard。**这是成本最低、效果最好的一招。终端口不需要参与STP计算,直接转发;一旦有设备往这个口发BPDU,端口立刻error-down,从物理上阻止“有人把交换机插到办公桌网口上”引发的环路。
**第二,合理规划根桥并启用Root Guard。**核心层交换机应该手动指定为根桥和备用根桥,避免接入层设备因为MAC地址小、优先级配置失误而抢占根桥。在核心交换机朝向接入交换机的端口上,开启根保护,防止新的更优BPDU改变根桥位置。
**第三,在可能出现阻塞的端口上启用Loop Guard。**RSTP有个隐患:如果单向链路故障(光纤收发光异常、网线坏芯),阻塞端口收不到BPDU,等待超时后会进入转发状态,造成环路。Loop Guard会持续监测端口是否收到BPDU,如果发现应该收到却没有收到,会强制端口保持阻塞,而不是放行。
**第四,能用链路聚合就别用STP兜底。**两根线冗余,最优雅的方案是把它们绑成一个Eth-Trunk(华为)或Port-Channel(思科),这样物理上有两条链路,逻辑上是一个端口,天然无环路,负载还能均衡。STP是兜底机制,不是最优解。
那次事故之后,我把所有接入端口统一配置了PortFast和BPDU Guard,核心设备上手工指定了根桥,并开启了Root Guard,同时在关键链路上配了Loop Guard。后面再没出过类似的环路问题。
最后补充几句个人经验
STP这章内容不少,但它本质上就三件事:为什么要防环、怎么选举、收敛有多快。把这三件事的逻辑链条理顺,再去看命令行和厂商差异就很容易了。
我自己的建议是,零基础的朋友不用急着背命令,第一遍先把第2章的选举过程按照三台交换机的例子手动推演一遍,第二遍再用模拟器实际搭拓扑,看看端口角色和状态怎么变化。两遍下来,STP基本就焊死在脑子里了。
做了这么多年网络,我最大的体会是:很多看起来无解的网络故障,根源往往就是“环路”两个字。而STP这套机制,就是网络工程师手里最基础、也最不能丢的防身工具。