PFC(Priority-based Flow Control,基于优先级的流量控制)
一、基础定义
PFC 是 IEEE 802.1Qbb 标准定义的数据链路层流量控制技术,常用于数据中心以太网(DCE)、RoCE、RDMA 场景,解决传统以太网无丢包需求。
传统以太网 PAUSE(802.3x):对整个端口进行流量阻断,所有优先级队列一同暂停;
PFC :按 802.1p 优先级(CoS 0~7)逐队列独立流量控制,只阻塞拥塞的优先级数据流,不影响其他业务。
二、核心原理
- 以太网每个端口划分 8 个优先级队列(CoS 0~7);
- 接收方某队列缓冲区即将溢出时,向发送方发送 PFC PAUSE 帧;
- PAUSE 帧携带优先级掩码,仅通知发送方暂停对应优先级的报文;
- 暂停时长到期,或接收方缓冲区腾出空间后,发送方恢复该优先级发送;
- 其余优先级队列不受影响,继续转发。
PFC 帧关键信息
- 目的 MAC:
01-80-C2-00-00-01(标准组播地址) - EtherType:
0x8808 - 载荷包含:8bit 掩码标记哪些CoS需要暂停 + 各队列暂停定时器
三、典型应用场景
1. RoCE v2 / RDMA over Converged Ethernet(最主流)
RDMA 对丢包极其敏感,一旦报文丢失会引发严重性能暴跌。
PFC + ECN(显式拥塞通知,802.1Qau) 构成无损以太网基础:
- PFC:防止缓冲区溢出造成尾部丢弃,实现链路无损;
- ECN:提前标记拥塞,主动降速,减少频繁触发PFC。
常见组合:无损网络 = PFC + ECN + DCBX。
2. 存储网络
iWARP、FCoE(Fibre Channel over Ethernet),存储流量不能丢包,依赖PFC构建无损以太替代FC光纤通道。
四、DCBX(Data Center Bridging eXchange)配套
PFC 参数不能静态配置,依靠 DCBX(802.1Qaz) 在邻居设备间协商:
- 协商哪些优先级启用PFC;
- 同步CoS到流量组映射;
交换机、网卡自动协商无损参数,减少人工错配。
五、优势
✅ 粒度精细:按优先级队列控制,不一刀切阻塞整个端口
✅ 兼容802.1p VLAN优先级体系
✅ 支撑RDMA、FCoE等需要无损传输的业务
六、风险
1. PFC风暴(Headroom Congestion / PFC Deadlock,PFC死锁)
典型故障现象:
下游拥塞 → 向上游发送PFC暂停帧 → 上游队列被堵死;多条流互相等待资源,形成循环阻塞,全网流量卡死。
诱因:多对多复杂拓扑、缓冲区规划不合理、多条无损流交叉抢占队列。
缓解方案:
- 合理规划缓冲区 Headroom;
- 部署 PFC Watchdog(超时自动解除暂停);
- 优化路由避免环路依赖;
- 配合ECN做前置拥塞抑制,降低PFC触发频率。
2. 缓冲区占用变大
启用PFC后报文不会丢弃,会持续占用缓存,需要交换机预留更大buffer。
3. 时延增加
流量被暂停等待,高负载场景下引入排队时延与抖动。
七、典型配置逻辑(交换机视角通用思路)
- 定义需要无损的CoS优先级(例如CoS5用于RoCE);
- 接口开启PFC,只对选定CoS使能;
- 开启DCBX用于和网卡/邻居交换机协商;
- 配置队列buffer、headroom缓冲区;
- 配套ECN拥塞标记;
- 开启PFC死锁检测/Watchdog保护。
八、PFC vs 传统802.3x PAUSE
| 特性 | 802.3x PAUSE | PFC(802.1Qbb) |
|---|---|---|
| 控制粒度 | 整个物理端口 | 8个独立CoS优先级队列 |
| 标准 | IEEE 802.3x | IEEE 802.1Qbb |
| 适用场景 | 普通以太网流量控制 | 数据中心无损以太、RoCE、FCoE |
| 影响范围 | 端口所有业务全部暂停 | 仅拥塞优先级暂停 |
九、 PFC vs WRED 区别
一句话先行:
WRED = 主动提前丢包(拥塞预警,限速);PFC = 尽量不丢包、向上游发暂停指令(追求无损传输)。
二者解决拥塞的思路完全相反,常在数据中心RDMA场景搭配使用,也经常被混淆。
1. 基础定义
PFC(802.1Qbb 基于优先级流量控制)
- 层次:二层数据链路层
- 核心机制:
接收方缓存快满时,向上游发送PFC PAUSE帧 ,通知上游暂停发送对应优先级流量 ,不丢包。 - 目标:构建无损以太网,满足RoCE、FCoE等无法容忍丢包的业务。
WRED(Weighted Random Early Detection,加权随机早期检测)
- 层次:三层/队列调度层(IP队列)
- 核心机制:
队列占用达到最低阈值后,主动随机丢弃报文,提前通知源端TCP降低发送速率,避免队列彻底占满引发尾部丢弃。 - 目标:TCP网络拥塞管理,缓解队列震荡、防止全局同步,允许丢包。
2. 关键维度对比
| 对比项 | PFC | WRED |
|---|---|---|
| 工作层级 | 二层(以太网帧) | 三层IP队列机制 |
| 拥塞处理手段 | 向上游发暂停帧,尽量不丢包 | 主动提前丢包报文 |
| 控制对象 | 上游邻居设备(点对点链路) | 本设备本地出方向队列 |
| 粒度 | 基于802.1p CoS优先级队列 | 基于DSCP/队列权重 |
| 是否无损 | 设计目标:无损 | 设计目标:允许丢包 |
| 依赖协议 | 纯二层,无需IP | 主要配合TCP拥塞控制 |
| 典型业务 | RoCE v2、FCoE、RDMA | 普通TCP业务(互联网、业务服务器流量) |
| 典型风险 | PFC风暴、死锁、链路长时间阻塞 | 报文丢失、业务重传 |
| 反馈方式 | 反向控制上游发送速率 | 丢包间接告知发送方降速 |
3. 最容易理解的类比
一条单向管道,下游堵了:
- WRED:我这边快堵了,直接扔掉新来的货物,让发货人慢点送。
- PFC:别扔货!立刻通知上游先停止发货,等我腾出空间再继续送。
4. 重要技术细节
(1)WRED的短板 → 为什么RDMA不用单纯WRED
RDMA/RoCE 没有TCP重传机制 ,一旦报文被WRED丢弃,性能会断崖式下跌。
所以RDMA网络不能依赖WRED,需要PFC实现无损。
(2)PFC的短板
PFC不丢包,流量持续堆积缓存,容易引发:
- PFC死锁
- PFC风暴(一条拥塞链路导致上游大面积暂停)
因此现代RoCE组网策略:ECN + PFC 组合,尽量少触发PFC。
ECN:提前标记拥塞,让RDMA终端主动减速,尽可能避免缓冲区耗尽、避免触发PFC暂停。
(3)二者能不能同时部署?
可以,但不能对同一优先级混用:
- 无损队列(RoCE CoS):开启PFC,关闭WRED(丢包会导致RDMA故障)
- 普通TCP业务队列:关闭PFC,启用WRED,依靠丢包做拥塞控制
5. 延伸:和传统尾部丢弃的区别顺带理清
- 尾部丢弃(Drop-tail):队列满了才丢,一次性大量丢包,引发TCP全局同步
- WRED:队列未满就随机丢,平滑拥塞
- PFC:不走丢包路线,向上游限流
补充说明:RoCE v2无损以太网四大组件关系:PFC / ECN / DCBX / WRED 逻辑框图
RoCE 无损网络标准组合:DCBX + PFC + ECN
WRED 严禁在 RoCE 无损CoS队列开启 ,只用于普通TCP业务队列。
注:1. DCBX(802.1Qaz) :邻居协商协议(握手层)
PFC(802.1Qbb) :二层最后一道防线,防止缓存溢出丢包(兜底无损)
ECN(802.1Qau / IP ECN) :前置拥塞预警,减少PFC频繁触发(主动控流)
WRED :TCP流量拥塞管理,RoCE队列禁用,靠丢包实现拥塞控制
逻辑框图
┌─────────────────────────────────────────────────────────────┐
│ 终端:RoCEv2 网卡(RNIC) │
│ ┌──────────┐ ┌──────────┐ ┌──────────────────┐ │
│ │DCBX客户端│◄────►│RoCE队列 │◄──────►│RDMA拥塞控制(CC) │ │
│ │协商参数 │ │(无损CoS) │ │依据ECN标记减速 │ │
│ └──────────┘ └──────────┘ └──────────────────┘ │
└───────────────────────▲─────────────────────────────────────┘
│
│ 以太网链路
▼
┌─────────────────────────────────────────────────────────────┐
│ 叶/脊交换机 │
│ │
│ 【控制平面:邻居参数协商】 │
│ ┌─────────────────────────────────────────────────────┐ │
│ │ DCBX(802.1Qaz) │ │
│ │ ↳协商:PFC使能CoS、ECN使能、CoS→TC映射、优先级组 │ │
│ └─────────────────────────────────────────────────────┘ │
│ │
│ 【数据平面 - RoCE无损队列(TCx,例如CoS5)】 │
│ ┌─────────────┐ ┌─────────────┐ ┌────────────┐ │
│ │ ECN标记功能 │─────►│ PFC │─────►│Headroom缓存│ │
│ │早期拥塞标记 │ │802.1Qbb暂停 │ │预留缓冲池 │ │
│ └─────────────┘ └─────────────┘ └────────────┘ │
│ ▲ ▲ ▲ │
│ 队列占用达到阈值 缓存临近溢出 用于存放被PFC暂停报文
│ │
│ 【数据平面 - 普通TCP队列(其他CoS)】 │
│ ┌─────────────┐ │
│ │ WRED 拥塞管理│◄── RoCE队列**禁止配置WRED** │
│ │随机早期丢包 │ 丢包会直接造成RDMA报文丢失、性能雪崩 │
│ └─────────────┘ │
└───────────────────────▲─────────────────────────────────────┘
│
▼
对端RoCE RNIC 接收端
拥塞发生时先后顺序
阶段1:建链协商 --- DCBX(先行条件)
交换机 ↔ RNIC、交换机 ↔ 交换机之间通过DCBX交互:
- 哪些CoS开启PFC;
- 哪些TC开启ECN;
- 优先级映射关系。
如果DCBX协商不一致,一端开PFC一端关闭,链路会出现随机丢包,无损失效。
阶段2:轻度拥塞 --- ECN优先介入(最优路径)
交换机出方向队列占用达到ECN标记阈值 :
✅ 不丢包,在IP头ECN字段做标记(CE)
✅ 报文正常转发到接收RNIC
✅ 接收端回送 CNP(拥塞通知报文) 给发送端
✅ 发送RNIC的RDMA CC算法主动降低发送速率
👉 目标:通过终端主动限流,尽量不让缓存继续上涨,避免触发PFC
阶段3:重度拥塞(ECN控流来不及)--- PFC兜底无损
流量持续涌入,队列缓冲逼近溢出阈值:
✅ 接收侧交换机向上游直连设备发送PFC PAUSE帧
✅ 通知上游暂停对应优先级CoS的报文发送
✅ 依靠Headroom缓存临时承载正在传输的飞行报文
👉 目标:杜绝缓存溢出导致的尾部丢包,保证RoCE报文不丢失
⚠️ 风险:大量持续PFC会引发PFC风暴、死锁,因此ECN是第一道防线,PFC只是兜底。
普通TCP流量处理(与RoCE隔离队列)
普通业务队列:关闭PFC,启用WRED
队列达到阈值后主动随机丢包,触发TCP拥塞控制。
❗关键禁忌:RoCE无损队列不能同时启用WRED。WRED会主动丢弃报文,RDMA没有TCP完备重传机制,一旦丢包吞吐量暴跌、时延激增。
四大组件对比简表
| 组件 | 标准 | 层级 | 作用 | RoCE无损队列配置策略 |
|---|---|---|---|---|
| DCBX | 802.1Qaz | 二层控制协议 | 上下游自动协商无损参数 | 必须开启 |
| ECN | 802.1Qau/IP ECN | 三层/队列层 | 轻度拥塞,标记通知终端减速 | 必须开启(优先于PFC) |
| PFC | 802.1Qbb | 二层 | 缓存即将溢出,向上游暂停发送,实现无损 | 针对RoCE对应的CoS开启 |
| WRED | 队列拥塞机制 | 三层队列 | 主动提前丢包,管控TCP流量 | 关闭!禁止在无损TC启用 |
常见误区
- 误区:PFC和ECN二选一
✅ 正解:二者配合,ECN治本,PFC兜底;只开PFC极易产生PFC风暴 - 误区:所有队列统一开启PFC
✅ 正解:仅RoCE业务对应的CoS开启,普通业务不开启,防止无关流量触发暂停 - 误区:无损队列同时配置WRED+PFC
✅ 致命错误:WRED主动丢包直接破坏RDMA无损假设