华为H3C实战 | 第4章 STP / RSTP / MSTP 生成树
📚 本系列共 43 篇(第 4 / 43 篇) · 第一卷 基础篇 —— 交换机的骨架
← 上一篇:第 3 章 VLAN 与二层转发 下一篇:第 5 章 链路聚合与堆叠 →
本章导读:为防一根线断了就多拉一根,结果拉出一个环——以太网帧没有 TTL,进环就出不来,几十秒打满全网。STP 要做的,就是在有环的物理拓扑上自动算出一棵无环的树,把多余的链路堵上待命。
本章结构:
- 4.1 功能原理与业务场景 —— 三层架构下的冗余拓扑、STP/RSTP/MSTP 三代对比(30~50 秒 vs 秒级 vs 按实例负载均衡)
- 4.2 华为设备配置详解 ——
stp mode切换会全网抖、MST 域三要素(域名+修订级+实例映射)必须逐台一致、stp root primary其实是把优先级设 0、边缘端口必须配 BPDU 保护、tc-protection - 4.3 H3C 设备配置详解 ——
stp global enable、stp edged-port(没有enable)、stp region-configuration+active region-configuration - 4.4 命令对照表 —— 全局开关、边缘端口这两处"多一个词/少一个词"的坑
- 4.5 配置验证 ——
display stp brief看根桥与端口角色、端口状态是不是 DISCARDING - 4.6 排错与故障树 —— 根桥跑到接入交换机、MSTP 实例不生效(三要素不一致或忘了 active)、边缘端口被 BPDU 保护打成 error-down、TC 计数飙升
- 4.7 新手踩坑 —— 两台都配
root primary、在 rstp 模式下指望实例映射生效 - 4.8 本章小结 —— 要点清单 + 自测题
重点提示:全网间歇性卡顿、ping 大量丢包且 MAC 表里同一个 MAC 在多个口闪现——别犹豫,按 4.6 第一行查环路。改 stp mode 会让全网红算,务必进维护窗口;把模式配成 rstp 却还指望 MSTP 实例负载均衡,是在白忙(4.2 讲清了原因)。
关联章节:链路冗余的另一种做法(聚合)见第 5 章——堆叠后成员间链路不参与 STP 计算;网关冗余见第 7 章;私接交换机引发的环路,端口安全的粘滞绑定见第 9 章。
4.1 功能原理与业务场景
4.1.1 这功能是干嘛的(通俗版)
二层网络中,「冗余」和「环路」是一对天生的冤家。为了不让一根网线断了导致业务中断,聪明的做法是多拉一根备用线——但这多出来的那一根,立刻构成一个环。以太网帧里没有「生存时间(TTL)」这种字段,一个帧进了环就永远出不来,会被无限复制,几十秒内就能把整台交换机的 CPU 和所有链路带宽打满。这就是网络里最著名的灾难:广播风暴。
生成树协议(Spanning Tree Protocol,STP)解决的就是这件事:在有环的物理拓扑上,自动算出一棵无环的逻辑树,把多余的链路主动「堵上」,只保留备用状态。当主链路断了,被堵上的那条会自动打开,业务在几十秒到几秒内恢复。
最形象的比喻是小区里的单行道调整:整个片区为了方便都希望四通八达,但有些小路必须设成单行或者直接拦住,否则车流会互相堵死。STP 就是那个每天早上站在路口告诉你「这条今天走不通、那条可以走」的交警。而这个交警的规则极其严格且确定——它不看心情,只看谁家的「门牌号」更小。
STP 有三个版本层次:STP(IEEE 802.1D[29],最老,收敛慢,30~50 秒)、RSTP(IEEE 802.1w[31],快速生成树,新增 P/A 机制,秒级收敛)、MSTP(IEEE 802.1s[32],多实例生成树,能按 VLAN 分别算树,实现负载均衡)。现代交换机缺省跑的都是 MSTP,而且 MSTP 能向下兼容 STP/RSTP 的报文。
4.1.2 在网络里怎么落地(设计视角)
先看一个典型的三层架构拓扑,这也是本章后面所有配置的模型:
[CORE-SW1]══════[CORE-SW2]
║ ║
(trunk 互联,横向链路形成环路)
║ ║
║ ║
[ACC-SW1] [ACC-SW3]
║ ║
╚══════╦═══════╝
║
(横向备用链路,形成环路)
║
[ACC-SW2]
│
PC(192.168.10.20)
图中存在一个明显的环:CORE-SW1 → ACC-SW1 → ACC-SW2 → ACC-SW3 → CORE-SW2 → CORE-SW1。STP 要做的是:选一个「老大」(根桥),让每台交换机都算出「到老大最近的路」,然后把「不在这棵最短路径树上的端口」堵掉。
STP 的选举分三步,顺序不能乱:
第一步:选根桥(Root Bridge)。所有交换机互相发 BPDU(Bridge Protocol Data Unit,桥协议数据单元)报文,报文里带自己的桥 ID(Bridge ID)。桥 ID = 桥优先级(2 字节,缺省 32768,步长 4096)+ 桥 MAC 地址(6 字节)。桥 ID 最小的当根桥。因为所有设备的缺省优先级都是 32768,所以缺省情况下 MAC 地址最小的设备当根桥——这是一个很糟糕的默认行为,因为 MAC 地址小纯属出厂随机,可能导致一台接入交换机当根桥,整网流量绕着它转。
第二步:每台非根交换机选根端口(Root Port)。根端口是「通往根桥代价最小的那个口」。比较规则依次是:根路径开销(Root Path Cost)最小 → 对端桥 ID 最小 → 对端端口 ID 最小。每台非根交换机有且只有一个根端口。
第三步:每条链路选指定端口(Designated Port)。一条链路两端各有一个口,其中「到根桥代价更小的那一端」成为指定端口,负责这条链路上向对方转发流量。根桥上的所有端口都是指定端口。剩下的、既不是根端口也不是指定端口的端口,就是阻塞端口(Alternate Port),逻辑上被堵上。
路径开销是这里的关键量,标准(802.1D-1998 及之后)按速率定:
| 链路速率 | 短整型开销(802.1D-1998) | 长整型开销(802.1t) |
|---|---|---|
| 10Mbps | 100 | 2000000 |
| 100Mbps | 19 | 200000 |
| 1Gbps | 4 | 20000 |
| 10Gbps | 2 | 2000 |
| 100Gbps | —(未定义) | 200 |
注意华为与 H3C 的缺省开销标准:主流版本缺省用长整型(IEEE 802.1t),但不同型号/版本的缺省可能不同,配置前一定要用 display stp 输出里的 Cost 值反推当前用的是哪套标准。
STP 的端口要经历四个状态才能转发:Blocking(阻塞)→ Listening(侦听)→ Learning(学习)→ Forwarding(转发),中间还有 Disabled(禁用)。从 Blocking 到 Forwarding 缺省需要 2 倍 Forward Delay(缺省 15 秒)= 30 秒,加上 Max Age(20 秒),一次收敛最坏要 50 秒。这就是老 STP 被诟病「慢」的原因。
RSTP 的改进是:新增边缘端口(直连终端,直接进转发)、新增 P/A(Proposal/Agreement)机制(点对点链路上用握手替代定时器等待)、端口角色精简为三种(Root、Designated、Alternate/Backup)、状态合并为三种(Discarding、Learning、Forwarding)。一次正常收敛可以做到 1 秒内。
MSTP 的改进是:把多个 VLAN 映射到不同的实例(Instance),每个实例独立算树。这样 VLAN 10 走左侧、VLAN 20 走右侧,两条链路都被利用,不再是「一条干活一条闲」。
适用版本:华为 VRP V200R019 及以上(S5735/S5700/S6700),H3C Comware V7(R2610 及以上)。缺省模式均为 MSTP;H3C V7 全局 STP 需
stp global enable开启(出厂配置启动时缺省开启,空配置启动时缺省关闭),这一条是本章最容易被忽略的差异。
4.2 华为设备配置详解
4.2.1 命令行基础速览(本章会用到的那几条)
| 命令 | 在哪敲 | 干什么 |
|---|---|---|
stp enable |
系统视图 | 全局开启 STP |
stp mode {stp|rstp|mstp} |
系统视图 | 设工作模式 |
stp root primary |
系统视图 | 指定本机为主根桥 |
stp root secondary |
系统视图 | 指定本机为备根桥 |
stp priority 4096 |
系统视图 | 设桥优先级(步长 4096) |
stp edged-port enable |
接口视图 | 边缘端口 |
stp bpdu-protection |
系统视图 | BPDU 保护(全局) |
stp root-protection |
接口视图 | 根保护 |
stp loop-protection |
接口视图 | 环路保护 |
stp tc-protection |
系统视图 | TC-BPDU 保护 |
display stp |
任意视图 | 看 STP 全局信息 |
display stp brief |
任意视图 | 看各口角色与状态 |
4.2.2 完整配置模板
以 4.1.2 的拓扑为例,两台核心做 MSTP 多实例负载均衡:实例 1 承载 VLAN 10、20,实例 2 承载 VLAN 30、40;CORE-SW1 是实例 1 的主根、实例 2 的备根,CORE-SW2 反过来。
# 核心交换机 CORE-SW1
system-view
sysname CORE-SW1
# 批量建 VLAN
vlan batch 10 20 30 40
# 全局开 STP,模式用 MSTP(缺省就是 MSTP,显式写出来更清楚)
stp enable
stp mode mstp
# 配置 MST 域(域内三要素必须全网一致:域名、修订级别、实例-VLAN 映射)
stp region-configuration
region-name RG-CAMPUS
revision-level 1
instance 1 vlan 10 20
instance 2 vlan 30 40
active region-configuration
quit
# 实例 1 主根,实例 2 备根
stp instance 1 root primary
stp instance 2 root secondary
# 开启 BPDU 保护(保护所有边缘端口)
stp bpdu-protection
# 开启 TC-BPDU 保护
stp tc-protection
stp tc-protection threshold 3
# 定义边缘端口相关的全局参数:保护后接口 err-down 的自动恢复
error-down auto-recovery cause bpdu-protection interval 300
# 下联接入交换机的口:根保护 + 环路保护(二选一,见说明)
interface GigabitEthernet0/0/1
description TO-ACC-SW1-GE0/0/24
stp root-protection
quit
interface GigabitEthernet0/0/2
description TO-ACC-SW3-GE0/0/24
stp root-protection
quit
quit
save
第二台核心 CORE-SW2 做主备互换(优先级与实例根配置对调):
# 核心交换机 CORE-SW2(主备互换)
system-view
sysname CORE-SW2
vlan batch 10 20 30 40
stp enable
stp mode mstp
stp region-configuration
region-name RG-CAMPUS
revision-level 1
instance 1 vlan 10 20
instance 2 vlan 30 40
active region-configuration
quit
stp instance 1 root secondary
stp instance 2 root primary
stp bpdu-protection
stp tc-protection
stp tc-protection threshold 3
error-down auto-recovery cause bpdu-protection interval 300
interface GigabitEthernet0/0/1
description TO-ACC-SW1-GE0/0/25
stp root-protection
quit
interface GigabitEthernet0/0/2
description TO-ACC-SW3-GE0/0/25
stp root-protection
quit
quit
save
接入交换机 ACC-SW1 的配置,重点是把接终端的口设为边缘端口:
# 接入交换机 ACC-SW1:所有接终端的口设边缘端口
system-view
sysname ACC-SW1
vlan batch 10 20 30 40
stp enable
stp mode mstp
stp region-configuration
region-name RG-CAMPUS
revision-level 1
instance 1 vlan 10 20
instance 2 vlan 30 40
active region-configuration
quit
stp bpdu-protection
stp tc-protection
# 接终端的口(假设 1~20 口接 PC)
interface range GigabitEthernet0/0/1 to GigabitEthernet0/0/20
stp edged-port enable
quit
# 上联核心的 trunk 口不放边缘端口
interface GigabitEthernet0/0/24
description TO-CORE-SW1-GE0/0/1
port link-type trunk
port trunk allow-pass vlan 10 20 30 40
quit
quit
save
4.2.3 逐行讲解
关于 stp enable:华为设备缺省是开 STP 的(出厂配置下 stp enable 已生效),所以这条命令更多是「显式确认」作用。但不要因此就跳过——某些型号出厂配置里 STP 是关的,一台设备关着 STP 进了网,就是一颗定时炸弹。通过 display stp 看输出第一行 Protocol Status 是不是 Enabled。
关于 stp mode:这里有一个必须讲清的细节——把模式从 MSTP 改成 STP 或 RSTP 时,设备会重启 STP 计算,全网会抖一下,因此必须在维护窗口做。反过来从 STP 改成 MSTP 也是一样。模式不一致的两台设备之间会协商失败,比如一端 stp mode rstp、一端 stp mode stp,RSTP 端会检测到对端发的是 STP 报文,自动降级为 STP——能通,但收敛慢,而且日志会一直报 STP mode mismatch。
关于 MST 域的三要素:这是 MSTP 最容易配错的地方。三个要素是 region-name(域名)、revision-level(修订级别)、instance vlan(实例与 VLAN 的映射)。只有三要素完全一致的设备才属于同一个 MST 域,才能在域内按实例算树;不一致的设备会被当作另一个域,域之间只能用 CIST(公共实例)通信,实例划分全部失效。所以接入交换机、汇聚、核心必须配成一模一样的三个参数——这也是为什么工程上习惯把这段配置做成模板批量下发。
还有一个坑:改完 stp region-configuration 下的内容后,必须执行 active region-configuration 才生效(H3C 官方原文:新配置的 MST 域参数不会马上生效,而是在使用 active region-configuration 激活、或使用 stp global enable 全局使能生成树协议后才生效)。忘了这一条,配置看着都在,display stp region-configuration 里显示的却是旧的映射——这是新手最常见的「配了没用」问题之一。H3C 上还有个 check region-configuration 命令可以在激活前先检查预配置是否正确,建议养成先查后激活的习惯。
另一个致命的答案:在 STP / RSTP / PVST 模式下,MST 域的相关配置根本不会生效(H3C 官方文档明确指出这一点)。所以如果你把模式配成了 stp mode rstp 却又指望实例映射起作用,那是在白忙——MSTP 的实例负载均衡必须先把 stp mode mstp 落实。
关于 H3C 的模式缺省值:stp mode { mstp | pvst | rstp | stp } 的缺省是 MSTP,与华为一致。H3C 各模式的兼容性官方描述是「MSTP 模式兼容 RSTP 模式,RSTP 模式兼容 STP 模式」;PVST 模式则比较特殊——对 Access 端口在任意 VLAN 都能与其他模式兼容,对 Trunk/Hybrid 端口则只在缺省 VLAN 中能兼容。
关于 stp root primary:这是一条「取巧」命令,它实际上是把优先级设成 0(因为 0 是所有设备里最小的,必然是根桥)。对应地,stp root secondary 是把优先级设成 4096(仅次于 0)。所以如果同时有两台设备都是 stp root primary,优先级都是 0,就要比 MAC 地址——结果又变成「谁 MAC 小谁当根」,失去控制。正确做法是全网只有一台 root primary、一台 root secondary。
stp priority 也是可用的手工方式,步长 4096,取值 0、4096、8192……61440。手工设的优先级如果和 root primary 冲突,后配的生效。
关于边缘端口:stp edged-port enable 让接口跳过监听、学习阶段,直接进转发。它适用于所有直连终端(PC、打印机、AP、IP 电话、服务器)的接口。好处是终端每次重启或换线后立刻能通,不用等 30 秒。风险是:边缘端口如果被误接了交换机,那它就不再是「边缘」的——它对端发来的 BPDU 会被忽略(缺省),于是可能形成环路。所以边缘端口必须配 BPDU 保护。
关于 BPDU 保护:stp bpdu-protection 在全局开。开启后,任何边缘端口一旦收到 BPDU,说明「这个口接的不是终端而是交换机」,设备会立刻把该口 error-down(物理上关闭),并在日志里报 BPDU_GUARD 告警。这正好防住了「实习生把家里的小路由器插到办公室网口」这一类事故。缺点是:口被关了之后需要人工恢复,或者配自动恢复:
# 华为:让被 BPDU 保护关掉的接口 300 秒后自动恢复
[HUAWEI] error-down auto-recovery cause bpdu-protection interval 300
关于根保护、环路保护、BPDU 保护的区分:这三个名字太像,务必分清:
| 保护 | 配在哪 | 防空什么 | 触发后行为 |
|---|---|---|---|
| BPDU 保护 | 全局(作用于边缘端口) | 边缘端口收到 BPDU | 端口 err-down |
| 根保护 | 设计好的根桥/汇聚的下联口 | 下联口收到「比根桥更优」的 BPDU(有人私接设备想抢根) | 端口进入 Discarding,BPDU 更优期间一直不转发 |
| 环路保护 | 根端口/备用端口 | 链路上 BPDU 丢失(单向链路故障)导致误转发 | 端口进入 Discarding |
| TC-BPDU 保护 | 全局 | 大量 TC-BPDU 刷新 MAC 表 | 限速处理,超出阈值的丢弃并只处理一定数量 |
一个工程原则:根保护配在「不许被抢根」的下联口上(汇聚到接入的口),环路保护配在「会因单向故障而误转发」的根端口上(核心之间的互联口),BPDU 保护配在接终端的边缘端口上。三者不冲突,但环路保护与根保护/边缘端口在同一口上互斥,别在同一个口上同时配。
关于 TC-BPDU 保护:拓扑变化(Topology Change)时,交换机会收到 TC-BPDU,触发 MAC 表老化和重新学习。有人恶意构造大量 TC-BPDU,可以让 MAC 表一直在刷新,转发性能崩溃。stp tc-protection 就是限制单位时间内处理的 TC 数量:
# 华为:每个保护周期内最多处理 3 次 TC,其余丢弃
[HUAWEI] stp tc-protection
[HUAWEI] stp tc-protection threshold 3
stp tc-protection threshold N 的含义是「在一个保护周期内,设备最多处理 N 次 TC(其余直接丢弃)」,周期长度缺省为 10 秒,可用 stp tc-protection interval 调整(并非所有型号都支持该命令,请以 ? 帮助为准)。
MSTP 负载均衡的原理与效果
MSTP 的负载均衡不靠「多路径分担」,而是靠「不同 VLAN 走不同的树」。本例中:
- 实例 1(VLAN 10、20):CORE-SW1 是根,从 CORE-SW1 到 ACC-SW2 的流量走左侧(ACC-SW1 那条链)。
- 实例 2(VLAN 30、40):CORE-SW2 是根,从 CORE-SW2 到 ACC-SW2 的流量走右侧(ACC-SW3 那条链)。
结果就是:左侧链路承载 VLAN 10、20,右侧链路承载 VLAN 30、40,两条链路都被利用。用 display stp instance 1 brief 和 display stp instance 2 brief 分别看,会发现同一个端口在两个实例里的角色/状态可以不同——这正是 MSTP 的核心能力。传统的单树 STP/RSTP 做不到这一点,永远有一条链路全闲。
4.3 H3C 设备配置详解
4.3.1 命令行基础速览
H3C 的 STP 命令与华为高度相似,但有三处必须先记住的关键差异:
| 命令 | 在哪敲 | 干什么 |
|---|---|---|
stp global enable |
系统视图 | 全局开启 STP(华为是 stp enable) |
stp enable |
接口视图 | 在端口上开启 STP(缺省开启) |
stp mode {stp|rstp|mstp|pvst} |
系统视图 | 设模式(H3C 还支持 PVST) |
stp root primary |
系统视图 | 主根 |
stp root secondary |
系统视图 | 备根 |
stp priority 4096 |
系统视图 | 桥优先级 |
stp edged-port |
接口视图 | 边缘端口(不带 enable) |
stp bpdu-protection |
系统视图 | BPDU 保护 |
stp root-protection |
接口视图 | 根保护 |
stp loop-protection |
接口视图 | 环路保护 |
stp tc-protection |
系统视图 | TC-BPDU 保护(缺省已开启) |
display stp |
任意视图 | 全局信息 |
display stp brief |
任意视图 | 各口角色与状态 |
4.3.2 完整配置模板
同样的 MSTP 多实例组网,H3C 侧的配置如下,注意全局开关是先决条件:
# H3C 核心交换机 CORE-SW1
system-view
sysname CORE-SW1
vlan 10 20 30 40
# 全局开启生成树(V7 关键差异)
stp global enable
stp mode mstp
# MST 域配置(三要素与华为版本完全一致,可跨厂商)
stp region-configuration
region-name RG-CAMPUS
revision-level 1
instance 1 vlan 10 20
instance 2 vlan 30 40
active region-configuration
quit
# 实例 1 主根、实例 2 备根
stp instance 1 root primary
stp instance 2 root secondary
# 保护功能
stp bpdu-protection
stp tc-protection
stp tc-protection threshold 3
# 下联口设根保护
interface GigabitEthernet1/0/1
description TO-ACC-SW1-GE1/0/24
port link-type trunk
port trunk permit vlan 10 20 30 40
stp root-protection
quit
quit
save force
H3C 接入交换机的等效配置,注意 stp edged-port 后面不带 enable:
# H3C 接入交换机:边缘端口(注意不带 enable)
system-view
sysname ACC-SW1
vlan 10 20 30 40
stp global enable
stp mode mstp
stp region-configuration
region-name RG-CAMPUS
revision-level 1
instance 1 vlan 10 20
instance 2 vlan 30 40
active region-configuration
quit
interface range GigabitEthernet1/0/1 to GigabitEthernet1/0/20
stp edged-port
quit
quit
save force
4.3.3 逐行讲解
stp global enable 是 H3C 最需要注意的一条。官方文档写得很清楚:设备空配置启动时,全局生成树处于关闭状态;出厂配置启动时,全局生成树处于开启状态。这意味着,一台被 reset saved-configuration 清空后重启的 H3C 交换机,STP 是关的。如果你把它接进一个有环的网络,就会立刻形成广播风暴。这个坑非常隐蔽,因为设备一切正常、display stp 也能看信息,只是状态是 Disabled。每次接入新设备,第一件事就是 display stp | include Global 确认状态。
stp edged-port 不带 enable:这是与华为最大的语法差异。华为 stp edged-port enable,H3C stp edged-port。抄配置时最容易在这一行报错。
H3C 的 BPDU 保护行为与华为不同:H3C 的 BPDU 保护在边缘端口收到 BPDU 时,不会直接把端口 shutdown,而是记录日志并让该端口作为非边缘端口参与 STP 计算(同时上报 BPDU_PROTECTION 告警)。如果你希望达到华为那种「端口直接关掉」的效果,需要配合其他机制(比如端口安全或 shutdown-interval 之类),或者依赖告警 + 人工处置。⚠ 版本差异:不同 Comware 版本的 BPDU 保护处置行为略有差异(有的版本会关闭端口,有的只上报告警),请以 display stp 输出中的 BPDU-Protection 状态与设备日志为准。
H3C 的 TC-BPDU 保护缺省是开的:华为的 stp tc-protection 需要你显式开,H3C V7 缺省已开启(stp tc-protection 缺省打开)。所以 H3C 设备上通常不需要特意配,但如果你排查过「TC 很多但没被限速」,就要确认一下状态。
H3C 还支持 PVST 模式:stp mode pvst 是每 VLAN 一棵生成树,这是 Cisco 体系的方案,H3C 为兼容思科设备而支持。它的缺点很明显:VLAN 多了以后实例数爆炸(每个 VLAN 一棵树,4094 个 VLAN 就是 4094 棵树),CPU 和内存压力大。同厂商环境一律用 MSTP,PVST 只在对接思科老网络时考虑。
H3C 与华为的 MSTP 互通
好消息是:MSTP 是标准协议,华为与 H3C 的 MSTP 可以互通,前提是两个 MST 域的三要素一致。实践中需要注意几点:
- 两家的定界差异(比如某些字段的默认值)可能影响协商,如果发现跨厂商的 MSTP 实例不通,先检查
display stp region-configuration输出中的「域配置摘要」是否一致。 - 端口角色和行为可能不完全一致,比如华为的
Alternate对应 H3C 的Alternate,这部分是标准的,通常没问题。 - 跨厂商链路建议显式指定开销和优先级,不要依赖两家的缺省值一致。
关于 STP 的版本兼容矩阵
| 华为模式 | H3C 模式 | 能否互通 | 说明 |
|---|---|---|---|
stp mode stp |
stp mode stp |
能 | 最兼容、最慢 |
stp mode rstp |
stp mode rstp |
能 | 标准 RSTP |
stp mode mstp |
stp mode mstp |
能(域一致时) | 推荐 |
stp mode mstp |
stp mode pvst |
不稳定 | 不建议混合 |
混编环境统一原则:全网都用 MSTP,且 MST 域三要素配成一样。
BPDU 报文长什么样
要读懂 STP 的日志和排障信息,得知道 BPDU 里到底装了什么。配置 BPDU 是 35 字节的固定结构,关键字段如下:
| 字段 | 长度 | 含义 |
|---|---|---|
| Protocol ID | 2 字节 | 固定 0x0000 |
| Protocol Version | 1 字节 | 0 = STP,2 = RSTP,3 = MSTP |
| BPDU Type | 1 字节 | 0x00 配置 BPDU,0x80 TCN BPDU,0x02 RSTP/MSTP 的 RST BPDU |
| Flags | 1 字节 | TC 位、TCA 位、P/A 位(RSTP 用) |
| Root ID | 8 字节 | 发送者认为的根桥 ID(优先级 + MAC) |
| Root Path Cost | 4 字节 | 发送者到根桥的开销 |
| Bridge ID | 8 字节 | 发送者自己的桥 ID |
| Port ID | 2 字节 | 发送端口 ID(端口优先级 + 端口号) |
| Message Age | 2 字节 | 报文在网络中已存活的秒数 |
| Max Age | 2 字节 | 缺省 20 秒 |
| Hello Time | 2 字节 | 缺省 2 秒 |
| Forward Delay | 2 字节 | 缺省 15 秒 |
排障时最有用的是 Root ID 与 Bridge ID 的比较:如果你在某个口上抓到一个 BPDU,发现它的 Root ID 比全网设计的根桥还要小(说明有人配了一个优先级 0 的设备在下面),同时 Bridge ID 又不是核心交换机,那就可以确定「下面有人私自接了设备并且在抢根」。这正是根保护要防的场景。
RSTP 的 RST BPDU 在这个结构基础上新增了 Version 1 Length 字段和更多 Flag 位(Proposal、Agreement、Learning、Forwarding、Role),也就是 P/A 机制的信息载体。
拓扑变化(TC)的传播机制
STP 里有一个容易被忽略但很关键的机制:拓扑变化通知。当某台交换机发现端口状态变化(有口 down 了、有口从阻塞变转发),它要知道「全网都需要刷新 MAC 表」,因为原来的路径可能失效了。
STP 的做法是:检测到变化的交换机向根桥方向逐跳发送 TCN BPDU(Topology Change Notification),根桥收到后把 TC 标志位置 1,在后续一段时间(缺省 35 秒 = Max Age + Forward Delay)内持续发送带 TC 位的配置 BPDU。所有交换机收到带 TC 位的 BPDU 后,把 MAC 老化时间从 300 秒临时缩短到 Forward Delay(15 秒),加速旧表项过期。
RSTP/MSTP 简化了这个流程:只有检测到变化的端口自己发 RST BPDU 带 TC 标志,直接泛洪出去。所以 RSTP 下 TC 的传播更快、影响面更广。
这也解释了一个现象:接入层一个终端反复插拔网线,会导致全网的 MAC 表被反复刷新。在生产网里,「一个实习生反复插拔网线」引发的全网抖动并不是段子。解决办法有两层:
- 把接终端的口设成边缘端口(边缘端口上下线不产生 TC,这是边缘端口除了快之外的第二个价值)。
- 全局开启 TC-BPDU 保护,限制单位时间内处理的 TC 数量。
根桥规划的工程实践
「根桥选谁」是 STP 设计的第一个决策,也是最容易被忽略的决策。工程上的标准做法:
| 步骤 | 做法 | 理由 |
|---|---|---|
| 1 | 选两台核心做 primary / secondary | 核心是流量的天然汇聚点,树形结构最短 |
| 2 | 所有汇聚、接入交换机不配任何 root 命令 | 保持缺省 32768,绝不抢根 |
| 3 | 下联口配根保护 | 防止下面的接入交换机被误配成 root |
| 4 | 记录根桥规划进网络文档 | 后续维护者知道该谁当根 |
| 5 | 变更后验证 display stp 的 CIST Root |
确认根桥没有漂移 |
还有一个容易忽略的细节:主备根之间的链路开销要合理。假设两台核心之间是 10Gbps,核心到汇聚是 1Gbps,那么从汇聚看,去主根的开销是 20000,去备根的开销是 2000(核心间)+ 20000(备根到汇聚)= 22000,主根优先,正常。但如果核心之间的链路是 1Gbps 且汇聚到备根的链路是万兆,那么去备根的开销可能更小——这其实是合理的(离得近的当根),只是与「主根规划」的意图不一致。所以设计时要用 stp cost 手工调整期望的路径,而不是完全依赖缺省值。
华为/H3C 混合组网下的 STP 要点
很多实际项目是华为与 H3C 混编的,这时有几条必须遵守:
- 域配置摘要一致:MSTP 的 BPDU 里带「配置标识符」和「配置摘要」(由域名、修订级别、VLAN 映射算出的哈希值)。两家的哈希算法遵循同一标准,所以只要三要素一致就能识别为同域。但要注意华为与 H3C 对默认 VLAN 映射的处理:如果某台设备上某个 VLAN 没有显式映射到实例,它缺省属于实例 0(CIST),而另一台设备把它映射到了实例 1,两边摘要就不同了——这就退化成跨域。解决办法是把所有 VLAN 都显式映射,不要依赖缺省。
- 开销标准一致:两家缺省可能都用长整型(802.1t),但如果某一台老设备配了
stp pathcost-standard dot1d-1998,树的形状会与预期完全不同。跨厂商链路上,显式写明端口开销最保险。 - 保护功能不要对端配置:比如华为核心配了根保护,H3C 汇聚正常,这没问题;但如果两端都配根保护,会互相把对方判为非法 BPDU 而阻塞,直接断链。根保护只配在「上级朝下级」的方向。
- 日志对照:两家的 STP 日志格式完全不同,华为用
MSTP/4/...,H3C 用STP/6/...,跨厂商排障时建议同时看两端的display stp brief,而不是只看一边的日志。
边缘端口为什么是接入网的第一优化项
如果把 STP 的所有优化按「性价比」排序,边缘端口排第一,理由有三:
第一,它是唯一能消除 30 秒等待的手段。终端开机、换线、休眠唤醒,PC 的网卡会重新连一次链路,如果这个口是普通 STP 端口,从链路 up 到能转发要经历 Listening(15 秒)→ Learning(15 秒),用户看到的是「网线插上后二十多秒才连上网」。边缘端口直接进 Forwarding,几乎是即插即用。
第二,它不会产生拓扑变化。这是很多人不知道的细节:边缘端口上下线时不发 TC-BPDU,所以不会触发全网的 MAC 表刷新。一个 2000 人的办公楼层,每天有几百次终端上下线,如果这些口都是普通端口,全网 MAC 表就会被反复刷新,转发性能一直被拖累。边缘端口把这部分开销直接归零。
第三,它与 BPDU 保护配合后变成一道安全防线。边缘端口本来假设「对端是终端、不会发 BPDU」,一旦真的发来了 BPDU,说明假设被打破——要么是有人私接了交换机,要么是有人在做攻击。这时 BPDU 保护立刻关掉端口,阻断风险扩散。
所以,接入层的每一个接终端口都应该配边缘端口,这是行业标准配置,不是可选项。唯一不能配的是:上联口、级联口、接 AP 的口(部分型号的 AP 会在口上跑 STP,需要保持普通端口)、接服务器的口(如果服务器上跑虚拟交换机,虚拟交换机可能发 BPDU)。
单向链路故障与环路保护的必要性
一个真实事故场景:两台交换机之间用一对光纤互联,其中一根纤被老鼠咬断。链路 layer1 表现为 up(因为接收方向还有信号?不,更常见的是发送方向断了)。光子是这样:A 的 TX → B 的 RX 断了,但 B 的 TX → A 的 RX 还通。于是:
- 从 A 看,接口是 up 的,能收到 B 的 BPDU。
- 从 B 看,接口是 up 的,但收不到 A 的 BPDU(因为 A→B 方向断了)。
结果 B 的根端口收不到 BPDU 超过 Max Age(20 秒),就认为「原根桥没了」,自动转成指定端口开始转发——这就形成了环路。这就是单向链路故障导致的 STP 环路。
环路保护(stp loop-protection)专治这种情况:配在根端口或替代端口上,它要求「这个口必须周期性收到 BPDU」,如果一段时间收不到,就把端口锁在 Discarding 状态,而不是让它转成指定端口。这样即使单向故障发生,也不会形成环路,代价是这条链路的流量暂时中断(但本来就已经断了)。
工程上,stp loop-protection 应该配在可能会发生单向故障的端口上:根端口、替代端口、以及使用了光模块互联的链路上。而在「设计好的根桥朝下」的端口上配根保护。两者都有明确的作用域,不要混用。
用镜像抓包彻底看清 STP 计算过程
如果读文档和看 display 输出还是不能理解 STP 怎么算的,最有效的学习方法是在 eNSP 或真实设备上搭一个小环,做端口镜像抓 BPDU,用 Wireshark 打开看每一个字段:
# 华为:把 trunk 口的报文镜像到抓包口
[HUAWEI] observe-port 1 interface GigabitEthernet0/0/10
[HUAWEI] interface GigabitEthernet0/0/24
[HUAWEI-GigabitEthernet0/0/24] port-mirroring to observe-port 1 both
抓到的 BPDU 在 Wireshark 里会显示成 Spanning Tree Protocol,展开后能看到 Root Identifier、Root Path Cost、Bridge Identifier、Port Identifier 等字段。你可以立刻验证:某台交换机发出的 BPDU 里,Root Identifier 是不是根桥的 ID,Root Path Cost 是不是它到根的开销,Port Identifier 是不是它的发送口。把三个交换机的 BPDU 放在一起对比,STP 的选举过程就不再是玄学。
抓包后把三台设备的 BPDU 字段整理成下面这样一张表,就能一眼看出谁离根更近:
抓包看到的三台设备 BPDU(示意)
CORE-SW1: Root=0.00e0-fc00-0001 Cost=0 Bridge=0.00e0-fc00-0001 Port=128.1
ACC-SW1 : Root=0.00e0-fc00-0001 Cost=20000 Bridge=32768.00e0-fc12-0001 Port=128.24
ACC-SW2 : Root=0.00e0-fc00-0001 Cost=40000 Bridge=32768.00e0-fc23-0001 Port=128.24
一眼就能看出:CORE-SW1 是根(Root = Bridge,Cost=0),ACC-SW1 离根一跳(Cost=20000),ACC-SW2 离根两跳(Cost=40000)。ACC-SW2 的两个上行口中,通 ACC-SW1 的那个 Cost 更小,所以是根端口;另一个是替代端口。整个选举逻辑就是这一张表的比较结果。
关于 STP 与「快速环回检测」的关系
最后提一个相关的、很多现场会用到的机制:STP 收敛是秒级甚至几十秒,而业务往往要求毫秒级。所以运营商和企业核心网会用别的机制做补充,比如华为的 RRPP(Rapid Ring Protection Protocol)、SEP(Smart Ethernet Protection),H3C 的 RRPP,这些是各厂商私有的环网保护协议,可以在 50ms 内完成倒换。
本章只需知道这个名词的存在与用途:当你在设备配置里看到 rrpp domain、rrpp ring 之类命令,那不是 STP,是厂商私有的快速环网保护,它的设计目标就是替代 STP 做环网快速倒换。企业办公网用 STP 就够了;运营商级城域网、工业环网才会用 RRPP/SEP。两套机制的选型和配置在第 37 章的校园网综合案例里不会再展开,但你在现场看到了要能认出来。
4.4 华为 / H3C 命令对照表
| 功能 | 华为(VRP) | H3C(Comware V7) | 差异说明 |
|---|---|---|---|
| 全局开启 | stp enable |
stp global enable |
H3C 多 global |
| 关闭 | stp disable |
undo stp global enable |
同上 |
| 模式 | stp mode mstp |
stp mode mstp |
相同 |
| 主根 | stp root primary |
stp root primary |
相同 |
| 备根 | stp root secondary |
stp root secondary |
相同 |
| 优先级 | stp priority 4096 |
stp priority 4096 |
相同,步长 4096 |
| 边缘端口 | stp edged-port enable |
stp edged-port |
H3C 无 enable |
| BPDU 保护 | stp bpdu-protection |
stp bpdu-protection |
命令相同,触发行为不同 |
| 根保护 | stp root-protection |
stp root-protection |
相同 |
| 环路保护 | stp loop-protection |
stp loop-protection |
相同 |
| TC 保护 | stp tc-protection |
stp tc-protection |
H3C 缺省开启 |
| TC 阈值 | stp tc-protection threshold 3 |
stp tc-protection threshold 3 |
相同 |
| MST 域 | stp region-configuration |
stp region-configuration |
相同 |
| 激活域 | active region-configuration |
active region-configuration |
相同 |
| 实例根 | stp instance 1 root primary |
stp instance 1 root primary |
相同 |
| 端口开销 | stp cost 20000 |
stp cost 20000 |
相同 |
| 端口优先级 | stp port priority 16 |
stp port priority 16 |
步长 16 |
| 查看 | display stp brief |
display stp brief |
输出格式不同 |
4.5 配置验证
STP 的验证核心是三个问题:谁是根桥、我的端口是什么角色、是不是按设计的样子在工作。
第一步:确认根桥。
<HUAWEI> display stp
正常输出(节选):
-------[CIST Global Info][Mode MSTP]-------
CIST Bridge :32768.00e0-fc12-3456
Config Times :Hello 2s MaxAge 20s FwDly 15s MaxHop 20
Active Times :Hello 2s MaxAge 20s FwDly 15s MaxHop 20
CIST Root/ERPC :0.00e0-fc00-0001 / 20000
CIST RegRoot/IRPC :0.00e0-fc00-0001 / 0
CIST RootPortId :128.1
BPDU-Protection :Enabled
TC or TCN received :126
关键读法:
CIST Bridge是本机的桥 ID(优先级.桥 MAC)。CIST Root/ERPC是根桥的 ID / 本机到根桥的根路径开销。如果CIST Bridge和这里的根桥 ID 相同,说明本机就是根桥。- 本例中
CIST Root/ERPC :0.00e0-fc00-0001,说明根桥优先级是 0(也就是配了root primary的设备),本机到根桥开销是 20000。 BPDU-Protection :Enabled确认保护开了。
第二步:确认端口角色。
<HUAWEI> display stp brief
正常输出:
MSTID Port Role STP State Protection
0 GigabitEthernet0/0/1 ROOT FORWARDING NONE
0 GigabitEthernet0/0/2 DESI FORWARDING ROOT
1 GigabitEthernet0/0/1 DESI FORWARDING NONE
1 GigabitEthernet0/0/2 DESI FORWARDING ROOT
2 GigabitEthernet0/0/1 ROOT FORWARDING NONE
2 GigabitEthernet0/0/2 ALTE DISCARDING NONE
读法:MSTID 是实例号(0 是 CIST/公共实例);Role 是端口角色(ROOT 根端口、DESI 指定端口、ALTE 替代/阻塞端口、BACK 备份端口);STP State 是状态(FORWARDING/DISCARDING/LEARNING);Protection 显示该口上启用了哪种保护(ROOT 表示根保护、LOOP 表示环路保护、NONE 表示没有)。同一个口在不同实例里角色不同,正是 MSTP 负载均衡在起作用——上面这个输出里 GE0/0/2 在实例 1 是指定端口(转发)、在实例 2 是阻塞端口,这就是实例 2 的流量走另一条链的证据。
第三步:确认实例与 VLAN 映射生效。
<HUAWEI> display stp region-configuration
正常输出:
Oper configuration
Format selector :0
Region name :RG-CAMPUS
Revision level :1
Instance VLANs Mapped
0 1 to 9, 11 to 19, 21 to 29, 31 to 39, 41 to 4094
1 10, 20
2 30, 40
如果 Instance 1 VLANs Mapped 还是空的、或者显示 0 1 to 4094,说明 active region-configuration 没执行或没生效——这是「MSTP 不工作」的头号原因。
第四步:验证边缘端口。
<HUAWEI> display stp interface GigabitEthernet0/0/1
输出里能看到 Edged-port : Config=enable/Active=enable,说明配了且已生效。Config 是配置值,Active 是实际生效值——只有 Active 是 enable 才算真的起作用。
第五步:看拓扑变化次数,这是判断网络是否稳定的核心指标:
<HUAWEI> display stp | include "TC or TCN"
如果这个计数在短时间内飞涨,说明网络在反复震荡(有链路抖动、有人插拔、或者有攻击)。
H3C 的验证命令:
<H3C> display stp
<H3C> display stp brief
<H3C> display stp region-configuration
<H3C> display stp interface GigabitEthernet1/0/1
H3C display stp brief 正常的格式与华为接近但多一列 VLAN:
VLAN ID Port Role STP State Protection
0 GigabitEthernet1/0/1 ROOT FORWARDING NONE
0 GigabitEthernet1/0/2 DESI FORWARDING ROOT
4.6 排错与故障树
| 症状 | 可能原因 | 排查命令 | 定位方法 |
|---|---|---|---|
| 网络间歇性卡顿、ping 大量丢包 | 存在未受控的环路 | display stp brief、display mac-address 看同一 MAC 多个口 |
检查所有 trunk 端口的 STP 状态,排查私接交换机 |
| 根桥变成了一台接入交换机 | 核心没配 root primary/secondary | display stp 看 CIST Root |
核心补 stp root primary,重算后再看 |
| MSTP 实例不生效、所有 VLAN 走同一棵树 | MST 域三要素不一致 / 忘了 active | 各设备 display stp region-configuration |
三要素逐台对齐 + active region-configuration |
| 边缘端口不生效、终端上线等 30 秒 | 端口没配边缘 / BPDU 保护关了它 | display stp interface 看 Active |
补 stp edged-port enable(华为)/ stp edged-port(H3C) |
| 端口一直 DISCARDING | 根保护生效 / 环路保护生效 | display stp brief 看 Protection 列 |
确认是否有非法 BPDU 来源;修好后端口自恢复 |
| 端口被 err-down | BPDU 保护触发 | display interface 看 ERR DOWN 原因 |
undo shutdown 恢复,或配 error-down auto-recovery |
| STP 完全没跑 | H3C 全局未 enable / 华为被 disable | display stp 首行 |
补 stp global enable / stp enable |
| TC 计数飞速上涨 | 频繁拓扑变化(链路抖动/上联插拔) | display stp | include TC |
查物理链路质量、查是否有终端反复上线 |
| 跨厂商 STP 不收敛 | 模式不一致(mstp vs rstp/stp) | 两端 display stp 看 Mode |
统一 MSTP + 三要素 |
| 私接的小交换机导致全网震荡 | 未开 BPDU 保护 | 日志查 BPDU_GUARD |
全网接入层开 BPDU 保护(第 4 章 4.2) |
故障树:
STP 相关故障
|
+-- 全网性能差 / 卡顿
| +-- 有环路?看 MAC 表里同一 MAC 是否在多个口闪现
| +-- 根桥是谁?核心是否 root primary
| +-- 有没有私接设备?查 BPDU 来源
|
+-- 收敛慢
| +-- 模式对不对?mstp / rstp
| +-- 边缘端口配了没?
| +-- 有没有一端还在跑 STP(拖慢全网)
|
+-- 端口不通但物理 up
| +-- 角色是 ALTE?那是正常的阻塞
| +-- 根保护/环路保护触发?看 Protection 列
| +-- err-down?看 display interface
|
+-- MSTP 负载均衡没生效
+-- 三要素一致?
+-- active region-configuration 执行了?
+-- 两个实例的 root primary 在不同设备上?
4.7 新手踩坑与注意事项
- H3C 空配置启动后 STP 是关的——症状:接进有环网络立刻风暴;怎么避:接入新设备第一件事
display stp确认,必要时stp global enable。 - 两台设备都配
stp root primary——症状:优先级都是 0,变成比 MAC,根桥不受控;怎么避:全网一台 primary、一台 secondary。 - MST 域三要素不一致——症状:MSTP 实例失效,所有 VLAN 一棵树;怎么避:做成模板批量下发 + 逐台
display stp region-configuration核对。 - 配完 MST 域忘了
active region-configuration——症状:配置都在但display stp region-configuration显示旧的;怎么避:改完立刻 active 并验证。 - 把上联 trunk 口配成边缘端口——症状:BPDU 保护触发,上联被 err-down,整台接入瘫痪;怎么避:边缘端口只配直连终端的口。
- 边缘端口不配 BPDU 保护——症状:有人私接交换机造成环路;怎么避:全局开
stp bpdu-protection。 - BPDU 保护触发后不知道怎么恢复——症状:端口一直 down;怎么避:配
error-down auto-recovery cause bpdu-protection interval 300,或手工undo shutdown。 - 在同一个口上同时配根保护和环路保护——症状:报错或其中一个不生效;怎么避:两功能在同口互斥,按需选一个。
- 为了「加快收敛」直接关掉 STP——症状:接上冗余链路立刻风暴;怎么避:永远不要关 STP,要快就用 RSTP + 边缘端口。
- 不同厂商设备之间配 PVST——症状:不收敛、状态乱;怎么避:跨厂商一律 MSTP。
- 修改 STP 模式不看业务时间——症状:改完全网抖 30 秒;怎么避:模式切换放维护窗口。
4.8 本章小结
- STP 的本质:在有环的物理拓扑上算出一棵无环的逻辑树,多余的链路阻塞但不拆除,故障时自动顶上。
- 三步选举:先选根桥(桥 ID 最小)→ 再选根端口(到根桥开销最小)→ 再选指定端口(链路两端开销小的那端)→ 剩下的阻塞。
- 三代协议:STP(慢,30~50 秒)、RSTP(P/A 机制,秒级)、MSTP(多实例,可负载均衡)。现代交换机缺省 MSTP。
- MSTP 三要素:域名、修订级别、实例-VLAN 映射必须全网一致,改完必须
active region-configuration。 - 四类保护:BPDU 保护(防私接)、根保护(防抢根)、环路保护(防单向故障误转发)、TC-BPDU 保护(防 TC 攻击)。
- 两家差异:H3C
stp global enablevs 华为stp enable;H3Cstp edged-portvs 华为stp edged-port enable。 - 验证三件事:谁是根桥、端口角色对不对、TC 计数是否稳定。
自测题
- 为什么「所有交换机都用缺省优先级」是一种危险的配置?
- MSTP 的负载均衡是怎么实现的?同一台交换机的同一个端口,在两个实例里可以是不同角色吗?
- 华为的
stp bpdu-protection和 H3C 的stp bpdu-protection在触发后的行为有什么不同? - 一台 H3C 交换机做了
reset saved-configuration并重启后,直接接入一个有环的网络会怎样? - 边缘端口、上联端口、核心之间的互联端口,分别应该配哪种 STP 保护?
- 因为所有设备优先级都是 32768,桥 ID 的比较大小时就变成了比较 MAC 地址,MAC 地址最小(纯出厂随机)的设备成为根桥。它可能是一台接入交换机,导致全网的流量绕到接入层再回来,浪费带宽、增加故障点、扩大广播域。正确做法是手工指定核心为主根、另一台核心为备根。
- 通过把不同 VLAN 映射到不同实例,并为每个实例指定不同的根桥来实现:实例 1 的主根是核心 A,实例 2 的主根是核心 B,于是不同实例的流量走不同的链路。是的,同一个端口在不同实例里可以有不同的角色和状态,这正是 MSTP 实现负载均衡的机制表现(如 GE0/0/2 在实例 1 是 DESI/FORWARDING,在实例 2 是 ALTE/DISCARDING)。
- 华为的 BPDU 保护在边缘端口收到 BPDU 时会将该端口置为
error-down(实际关闭端口),需要人工恢复或配置自动恢复。H3C 的 BPDU 保护在边缘端口收到 BPDU 时通常只记录日志并上报BPDU_PROTECTION告警、让端口作为非边缘端口参与计算,不一定关闭端口(具体行为与版本有关,需以设备日志和文档确认)。 - 会立刻形成广播风暴。因为 Comware 设备空配置启动时,全局生成树处于关闭状态,链路中没有任何 STP 参与计算,多余链路全部转发,环路形成。必须在接入前
stp global enable。 - 边缘端口配 BPDU 保护(全局开,作用于边缘端口);上联端口(汇聚到接入的口)配根保护;核心之间的互联口配环路保护。注意根保护与环路保护、边缘端口在同一口上互斥。
关于本书:《华为 / H3C 网络设备典型功能配置详解》—— 面向国内高校/企业网络环境, 华为 VRP 与 H3C Comware 双厂商并排配置的实操教材,共 43 章。 全书所有命令尽量有官方出处,查不到的显式标注「待核实」。 返回系列目录
本人保留对侵权者及其全家发动因果律武器的权利
版权提醒
如无特殊申明,本站所有文章均是本人原创。转载请务必附上原文链接:https://www.elliot98.top/post/huawei-h3c-book/04/。
如有其它需要,请邮件联系!版权所有,违者必究!