网段172.27 SSH 不通排查
ENV
| 类别 | 项 | 版本/信息 |
|---|---|---|
| 主机 | 主机名 | igo-node01 |
| 操作系统 | CentOS Linux 7 (Core) | 内核 3.10.0-1160.el7.x86_64 |
| 运行时间 | uptime | 38 weeks+ |
| 生产网卡 | bond0 | 10.10.10.53/24 |
| SSH | sshd | 端口 5008,监听 0.0.0.0:5008 |
| 容器 | Docker | 20.10.17 |
| 容器 | Docker Compose | v2.12.2 |
| 容器 | data-root | /data/docker |
| 容器 | default-runtime | nvidia |
| 编排 | igo-mineru gpu0 | 项目名 igo-mineru-gpu0,compose 文件 gpu0-compose.yaml |
| 业务容器 | igo-mineru-api-gpu0 | 镜像 igo-mineru:latest,端口 8004:8004 |
| K8s | 组件 | 节点存在 kube-proxy / Calico(cali-* 链、tunl0 等) |
| GPU | 驱动/运行时 | nvidia-container-runtime(daemon.json 配置) |
1. 现象
- 时间:约近 2 天起
- 表现:172.27 网段用户 SSH 连接
10.10.10.53:5008失败(超时/无响应) - 影响范围:来自 172.27 网段访问本机 SSH;业务容器
igo-mineru-api-gpu0(8004)本身可运行
2. 原因
2.1 结论
根因是 Docker 网络 igo-mineru-gpu0_default 自动占用 172.27.0.0/16,与生产 172.27 网段路由冲突,导致 SSH 回包走错接口。与 iptables DROP 无关。
2.2 定位推导过程
① 排除 iptables 直接拦截 SSH
iptables-save | grep 5008
iptables -L cali-from-host-endpoint -n -v --line-numbers
iptables -L DOCKER-USER -n -v --line-numbers
关键输出:
- 无 5008 相关规则
cali-from-host-endpoint为空链DOCKER-USER为空链- INPUT 默认策略
ACCEPT
判断: 非 INPUT 路径 DROP 导致。
② 确认 SYN 到达本机但无 SYN-ACK
timeout 8 tcpdump -i bond0 -n 'tcp port 5008 and src net 172.27.0.0/16' -c 5
关键输出:
172.27.100.23.xxxxx > 10.10.10.53.5008: Flags [S] ...
(仅 SYN 重传,无 SYN-ACK)
判断: 包能进本机,问题在本机处理/回包路径,非上游防火墙。
③ 定位回程路由错误
ip route get 172.27.100.23 from 10.10.10.53
ip route show | grep 172.27
故障时关键输出:
172.27.100.23 from 10.10.10.53 dev br-igo-old # 错误:走 Docker 网桥
172.27.0.0/16 dev br-igo-old proto kernel scope link src 172.27.0.1
判断: Docker 网桥 br-igo-old(igo-mineru-gpu0_default)抢占了 172.27/16 路由,SYN 从 bond0 进,SYN-ACK 却发往 Docker 网桥。
④ 确认冲突网络来源
docker ps --filter network=igo-mineru-gpu0_default --format '{{.Names}}'
docker network ls | grep igo-mineru
关键输出:
- 容器:
igo-mineru-api-gpu0 - 网络:
igo-mineru-gpu0_default - compose 路径:
/opt/igo/igo-mineru/gpu0-compose.yaml(原无 networks/subnet 配置)
判断: Docker 在本机已有 172.17–172.26 网络后,自动分配下一段 172.27.0.0/16,与生产网段重叠。
2.3 问题形成原因推测
运维/开发人员在 igo-node01 上部署 igo-mineru-api-gpu0(gpu0-compose.yaml)时未指定 Docker 网段;Docker 在已有多个 bridge 网络后自动为 igo-mineru-gpu0_default 分配了 172.27.0.0/16,与生产 172.27 网段冲突,导致来自 172.27 客户端的 SSH 回包被错误路由至 Docker 网桥,连接无法建立。
3. 方案
3.1 变更前备份
BACKUP_TIME=$(date +%Y%m%d%H%M)
cp -a /etc/docker/daemon.json /etc/docker/daemon.json.bak.${BACKUP_TIME}
cp -a /opt/igo/igo-mineru/gpu0-compose.yaml /opt/igo/igo-mineru/gpu0-compose.yaml.bak.${BACKUP_TIME}
echo "backup tag: ${BACKUP_TIME}"
示例 backup tag:202601011200
3.2 Docker 全局:限制自动分配网段(绕开 172.27)
文件: /etc/docker/daemon.json
{
"data-root": "/data/docker",
"default-address-pools": [
{"base": "172.28.0.0/16", "size": 24},
{"base": "172.29.0.0/16", "size": 24},
{"base": "172.30.0.0/16", "size": 24},
{"base": "172.31.0.0/16", "size": 24}
],
"default-runtime": "nvidia",
"log-driver": "json-file",
"log-opts": {"max-file": "3", "max-size": "100m"},
"runtimes": {
"nvidia": {"args": [], "path": "nvidia-container-runtime"}
}
}
python3 -m json.tool /etc/docker/daemon.json > /dev/null && systemctl restart docker
注意: 仅改 daemon.json 不会改变已有网络,须配合删除并重建冲突网络。
3.3 Compose:显式指定 gpu0 网段
文件: /opt/igo/igo-mineru/gpu0-compose.yaml 末尾追加:
networks:
default:
ipam:
config:
- subnet: 172.30.0.0/16
3.4 重建 gpu0 网络与容器
必须使用原项目名 -p igo-mineru-gpu0:
docker rm -f igo-mineru-api-gpu0
docker network rm igo-mineru-gpu0_default igo-mineru0618_default 2>/dev/null
cd /opt/igo/igo-mineru
docker compose -p igo-mineru-gpu0 -f gpu0-compose.yaml --profile api up -d
3.5 验证
路由与网络:
ip route show | grep -E '172\.27|172\.30'
ip route get 172.27.100.23 from 10.10.10.53
docker network inspect igo-mineru-gpu0_default --format '{{range .IPAM.Config}}{{.Subnet}}{{end}}'
修复后关键输出:
172.30.0.0/16 dev br-igo-new ... # 无 172.27 路由
172.27.100.23 ... via 10.10.10.254 dev bond0 # 回包走 bond0
172.30.0.0/16
业务与 SSH:
curl -sf http://localhost:8004/health && echo OK
timeout 8 tcpdump -i bond0 -n 'tcp port 5008 and host 172.27.100.23' -c 6
# 172.27 用户:ssh -p 5008 10.10.10.53
3.6 回退(backup tag: 202601011200)
docker rm -f igo-mineru-api-gpu0 2>/dev/null
docker network rm igo-mineru-gpu0_default 2>/dev/null
cp -a /etc/docker/daemon.json.bak.202601011200 /etc/docker/daemon.json
cp -a /opt/igo/igo-mineru/gpu0-compose.yaml.bak.202601011200 /opt/igo/igo-mineru/gpu0-compose.yaml
systemctl restart docker
cd /opt/igo/igo-mineru && docker compose -p igo-mineru-gpu0 -f gpu0-compose.yaml --profile api up -d
回退后可能再次分配到 172.27,SSH 问题可能复现。
4. 后续预防措施
-
所有 compose 文件显式配置
networks.subnet,部署前核对不与生产网段(172.27 等)重叠。 -
Docker daemon 配置
default-address-pools,新建网络自动避开 172.27。 -
compose 操作统一带项目名:
docker compose -p igo-mineru-gpu0 -f gpu0-compose.yaml --profile api <command> -
上线前检查:
ip route show | grep 172.27 ip route get <生产网段样例IP> from $(ip -4 addr show bond0 | awk '/inet /{print $2}' | cut -d/ -f1) -
维护本机 Docker 网络清单,新增 stack 前确认下一自动分配段是否会撞生产网段。
5. 建议配置参数
| 参数 | 当前值(修复前 → 修复后) | 建议值 | 原因/后果 |
|---|---|---|---|
gpu0-compose.yaml networks.subnet |
未配置(自动 172.27/16)→ 172.30.0.0/16 | 172.30.0.0/16 | 未配置时 Docker 顺序分配,易与生产 172.27 冲突 |
daemon.json default-address-pools |
无 → 172.28–172.31/16 | 配置多个不含 172.27 的 /16 池 | 防止未来新建网络再次自动分到 172.27 |
compose 项目名 -p |
曾误用目录名 igo-mineru0618 |
-p igo-mineru-gpu0 |
项目名不一致会导致 down/up 无法管理原容器 |
| SSH 端口 | 5008 | 保持 5008 | 与排查结论无关 |
| 生产 SSH 目标 IP | 应使用 10.10.10.53 |
不使用 172.27.0.1 |
172.27.0.1 为 Docker 网桥网关,非生产地址 |
报告状态: 已修复并验证(路由、8004 health、SSH 回包路径均正常)