--- tags: [计算机网络, CSMA-CD, 以太网退避, 冲突检测] create time: 2026-05-17 23:00 --- # CSMA/CD 与以太网退避 ## 概述 CSMA/CD(Carrier Sense Multiple Access / Collision Detection,载波监听多路访问/冲突检测)是早期共享式以太网的 MAC 子层协议。虽然现代交换式以太网已不再使用它,但理解其原理对掌握网络演进和碰撞域概念至关重要。 > [!QUESTION] 为什么需要 CSMA/CD? > 在共享介质(如同轴电缆或 Hub 集线器)上,多台设备共用同一根网线。如果没有协调机制,两台同时发送会导致信号叠加破坏——就像两个人同时在同一频道说话,谁也听不清。 ## CSMA/CD 工作流程 ```mermaid flowchart TD Start["有帧要发送"] --> Wait["等待信道空闲?"] Wait -->|"空闲"| Send["开始发送"] Wait -->|"忙碌"| Wait Send --> Check{"是否在 512bit
时间内检测到冲突?"} Check -->|"否"| Done["发送完成 ✅"] Check -->|"是"| Collide["发生冲突 → 发送 Jam Signal"] Collide --> Backoff["指数退避算法计算等待时间"] Backoff --> Retry{"重传次数 < 16?"} Retry -->|"是"| Wait Retry -->|"否"| Fail["丢弃帧,上报错误 ❌"] style Done fill:#98FB98,color:#000 style Fail fill:#FF6B6B,color:#fff ``` ### 四个步骤详解 | 步骤 | 英文名称 | 说明 | |------|---------|------| | 1 | **Carrier Sense** | 发送前先监听:信道忙就等,空闲才发 | | 2 | **Multiple Access** | 多个设备共享同一介质 | | 3 | **Collision Detection** | 发送过程中持续监测是否有冲突信号 | | 4 | **Collision Handling** | 检测到冲突 → 发 Jam Signal → 执行退避 → 重试 | ## 二进制指数退避算法 冲突后的等待时间通过随机退避来避免再次冲突: $$\text{等待时间} = \min(r, 2^{10}-1) \times 512 \text{ bit-time}$$ 其中 $r$ 为重传次数,`512 bit-time` 是最小帧长对应的传输时间(即争用期)。 ```mermaid flowchart TD k["重传次数 k"] --> r["r = random(0 ~ 2^k - 1)"] r --> capped["capped at 2^10 - 1 = 1023 (k > 10)"] capped --> backoff["backoff_time = r × 512 bit-time"] style k fill:#DDA0DD,color:#000 style backoff fill:#98FB98,color:#000 ``` ### 退避表 | 重传次数 k | 窗口大小 2^k - 1 | 可能等待的 slot 数范围 | |-----------|------------------|---------------------| | 1 | 1 | {0, 1} | | 2 | 3 | {0, 1, 2, 3} | | 3 | 7 | {0..7} | | 4 | 15 | {0..15} | | 5–10 | 最大值 1023 | {0..1023} | | >10 | 仍为 1023 | 上限固定 | 如果重传 16 次仍然失败,帧被丢弃并向上层报告错误。 ### 示例 假设节点 A 和 B 同时发送,发生冲突: ``` 时刻 0ms: A 和 B 同时发送 → 冲突! 两者都发送 32bit Jam Signal 时刻 0.1ms: A 选 r=3 → 等 3×512bit-time = 3×51.2μs ≈ 154μs B 选 r=1 → 等 1×51.2μs ≈ 51μs 时刻 0.05ms: B 先等完,先尝试发送 → A 还在等 时刻 0.15ms: A 等完,发现信道已被 B 占用 → 退避重选 r ... ``` ## 最小帧长与争用期 ### 为什么最小帧是 64 字节? 关键公式:**帧传输时间 ≥ 2 × 端到端传播延迟** 如果帧太短,可能在冲突信号到达之前就已经发完了——发送方根本不知道发生过冲突。 ```mermaid sequenceDiagram participant A as 节点 A participant H as 最远节点 H Note over A,H: 传播延迟 = τ A->>H: 开始发送一个超短帧 (长度 < 2τ) H->>A: 冲突信号沿原路返回 Note over A: 此时 A 已经发完了...
没检测到冲突!🔥 ``` 所以规定: $$\text{最小帧长} \geq 2 \times \tau \times \text{带宽}$$ 对于经典 10Mbps 以太网,最长电缆段 2500m,$\tau \approx 12.5\mu s$: $$\text{最小帧长} \geq 2 \times 12.5\mu s \times 10^7 \text{ bps} = 250,000 \text{ bits?}$$ 等等,实际工程中使用了中继器和更短的网段组合,最终标准定为 **512 bit-time = 64 bytes**。 ## 现代以太网中的命运 | 年代 | 拓扑 | 介质 | CSMA/CD? | |------|------|------|---------| | 1980s | 总线型 | 同轴电缆 | ✅ 必需 | | 1990s | 星型 + Hub | 双绞线 | ✅ 存在但极少冲突 | | 2000s+ | 全双工 Switch | 双绞线/光纤 | ❌ 已禁用 | 全双工模式下,收发通道分离(两根线对),不存在碰撞的可能,CSMA/CD 自动关闭。从 Gigabit Ethernet (802.3ab) 起,交换机端口默认全双工运行。 > [!note] 如何检查当前网卡是否启用了 CSMA/CD? > ```bash > $ ethtool eth0 | grep -i coll > Supports Collision Detection: yes > Current Collision Detection: disabled (full-duplex) > ``` ## 关联笔记 - [[hhs/NETWORK/Ethernet帧结构]] — 以太网 II 帧的格式定义 - [[hhs/NETWORK/Switch与路由器]] — Switch 如何通过全双工消除冲突 - [[hhs/NETWORK/VLAN与Trunk]] — VLAN 隔离冲突域