排查容器网络笔记
排查容器网络问题笔记
ebtalbe总共有三张tables, 分别是filter,nat以及broute.
filter则是专注于Accept/Drop相关过滤的行为nat这边则专注于针对MacAddress相关的转换broute这边可以用来决定封包到底要进行Layer2 Bridging或是Layer3 Routing。算是一个比较特别的规则。
brouting: 这个 的chain执行顺序非常的早,基本上是ebtalbes里面最早的chain. 只要当任何linux bridge上面的任何一个port有收到任何Frame进来后,就会到这个Chain里面去进行比对. 这边通常不太会去设定,而是都会依赖后续的Bridging Decision透过Mac Address去决定封包到底该怎么走。
-
input: 如果今天封包的目标Mac Address是Linux Bridge本身的话,那封包就会进入到 来input chain处理。最常见的范例就是docker容器想要对不同网段进行存取,会先进入到gateway也就是所谓的linux bridge本身。 -
output: 针对要从Linux Bridge离开的封包都会进行处理的Chain,这类型的封包大致上有两种可能。第一种是主机本身产生的封包,目的就是要从该linux bridge底下的某些Port转发出去,或是该封包是从linux bridge的某些Port转发到其他的Port. -
forward: 针对会被Linux Bridge进行Layer2 Bridging转发的封包所进行的Chain. 基本上同网段的容器间传输的封包都会到这个阶段。 -
prerouting: 这个Chian就是其名称的解读,Pre-Routing, 再封包进入到Linux Bridge后,但是还没有碰到Bridging Decision前可以进行的阶段。 -
postrouting: 这个Chian就是其名称的解读,Post-Routing, 再封包准备离开Linux Bridge前,但是还没有碰到真正的透过网卡送出去前可以进行的阶段。

- 首先当封包从跟
Linux Bridge有关的网卡,左边的nic近来之后,首先会先进入到brouting这个chain,brouting这个chain里面只支援brouintg Table, 若有任何规则要将该封包直接透过routing处理的话,封包就会直接拉到kernel-space/layer3层级来处理, - 接者封包会跑到
Prerouting这边,该chain里面只有nat可以执行,这意味到这个阶段顶多只能对封包进行内容的修改,还没有办法丢弃。 这边要注意,这时候还没决定到底封包该怎么转送,所以可以透过修改封包的目标Mac Address来影响到底之后该怎么转送封包,因此这也是这边Chian为什么叫做PreRouting. - 接下来就会到所谓的
Bridging Decision. 这边其实就会运行Learning Bridging相关的算法,根据Mac Address来决定转发的方向,若目标对象是Linux Bridge本身,则会透过input chain一路往上送到Layer3去处理。 对于input来说,可以透过filter来进行封包的处理,决定哪些封包要过,哪些不要过。 - 如果只是该
Linux Bridge下不同连接埠的转发的话,就会走Forward这边,最后透过Postrouting这边进行后续的修改,最后就从目标的网卡将该封包送出去。

iptables/ebtables网络系统

怎么知道这个封包到底是要Routing还是要Bridge? 实际上在Linux Kernel来说,是透过所谓的netdev_rx_handler_register来注册每张网卡收到封包后该怎么处理。 以Linux Bridge来看,当透过brctl addif br1 xxx这个方式把xxx加入到br1这个bridge时,就会把xxx这个网卡的接收封包函式设定成bridge有关,所以之后近来的封包就会走Layer2的方式去跑,反之亦然其他按照相同道理就会走Layer3的流程。
对于Layer3 来说;Layer3这边来处理,那处理的流程基本上就跟本文前半部分描述的雷同,唯一不同点只有当进行完毕Routing Decision后,在选择FORWARDd的阶段,若转送目的地网卡对应到的是属于本机上面的Linux Bridge网卡,则封包最后又会走到Layer2那层,在这情况下就会在经过iptables后又会马上转接ebtables,最后就会送到网卡出去。
如果封包一开始进入点就是Linux Bridge的网卡,这时候可以在brouting chain进行一次检查,如果这时候有透过ebtables特别将封包送到Layer3处理的话,那流程就会如同上述一样,从conntrack一路走到Routing Decision. 如果继续决定走layer2来处理封包的话,那流程就会跟前篇文章讲解ebtables叙述的流程一样。只是这边要特别注意的是,实际上iptables也会混杂在layer2的处理过程中,所以在真正进行Bridge Decision前也会遇到iptables PREROUTING进行处理。
如果透过Bridge Decision查询目标的MAC Address后决定将封包转送到Linux Bridge本身的话,那最后就会走向Layer3上层的走法,否则则会继续在Layer2这边将封包往其他的Bridge Port去转发。
在Bridge Port转发的过程中,也是会牵扯到iptables相关的规则。所以若只是单纯的两个Bridge底下的封包互相转传的话,其实也是可以透过iptables使用IP去控制封包转送,或是透过ebtables透过MAC Adddress去控制封包转送。
?可以看到brouting chain 进行检查的时候,有时候会将报文送到Layer3 处理;什么时候呢?
1、报文目的地址是 bridge 主机自身
即:
-
报文目的 MAC 是本机网卡的 MAC
-
或者桥接接口本身的 IP 被设置,并且该报文 IP 是它的
2、启用 bridge-nf-call-* 系列参数
3、ebtables 中使用 broute 表将报文交给 routing 层处理
sysctl -w net.bridge.bridge-nf-call-iptables=1
sysctl -w net.ipv4.ip_forward=1
SO:所以报文是两个 bridge 成员之间 L2 转发的(MAC 不匹配本机)不会上升到 L3 的情况:
看以前笔记https://www.cnblogs.com/codestack/p/17719317.html
find-container-by-veth.sh 查找接口连接容器?
#!/bin/bash # 检查是否提供了veth接口名称 if [ -z "$1" ]; then echo "用法: $0 <veth接口名称>" exit 1 fi VETH_HOST="$1" # 获取对端接口索引 (peer_ifindex) PEER_IFINDEX=$(ethtool -S "$VETH_HOST" 2>/dev/null | grep 'peer_ifindex' | awk '{print $2}') if [ -z "$PEER_IFINDEX" ]; then echo "错误:无法获取 $VETH_HOST 的 peer_ifindex" exit 1 fi # 遍历所有容器,检查网络命名空间中的接口索引 FOUND=0 while read -r CONTAINER_ID; do PID=$(docker inspect --format '{{.State.Pid}}' "$CONTAINER_ID" 2>/dev/null) if [ -z "$PID" ]; then continue fi # 获取容器内的接口索引 CONTAINER_IFINDEX=$(nsenter -t "$PID" -n ip -o link 2>/dev/null | \ awk -F': ' -v idx="$PEER_IFINDEX" '$1 == idx {print $1}') if [ "$CONTAINER_IFINDEX" = "$PEER_IFINDEX" ]; then CONTAINER_NAME=$(docker inspect --format '{{.Name}}' "$CONTAINER_ID" | sed 's#^/##') echo "找到关联容器:" echo "容器名称: $CONTAINER_NAME" echo "容器ID : $CONTAINER_ID" FOUND=1 fi done < <(docker ps -q) if [ "$FOUND" -eq 0 ]; then echo "未找到与 $VETH_HOST 关联的容器" fi

Container to WAN
dmesg -T [四 5月 8 16:38:11 2025] ebtable/nat-PREROUTE IN=vethdcc08d7 OUT= MAC source = 02:42:c0:a8:de:02 MAC dest = 02:42:ed:1a:30:67 proto = 0x0800 [四 5月 8 16:38:11 2025] iptable/raw-PREROUTEIN=br-d13c50d4c15b OUT= PHYSIN=vethdcc08d7 MAC=02:42:ed:1a:30:67:02:42:c0:a8:de:02:08:00 SRC=192.168.222.2 DST=8.8.8.8 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=52922 DF PROTO=ICMP TYPE=8 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] iptable/mangle-PREROUTEIN=br-d13c50d4c15b OUT= PHYSIN=vethdcc08d7 MAC=02:42:ed:1a:30:67:02:42:c0:a8:de:02:08:00 SRC=192.168.222.2 DST=8.8.8.8 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=52922 DF PROTO=ICMP TYPE=8 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] ebtable/filter-INPUT IN=vethdcc08d7 OUT= MAC source = 02:42:c0:a8:de:02 MAC dest = 02:42:ed:1a:30:67 proto = 0x0800 [四 5月 8 16:38:11 2025] iptable/mangle-FORWARDIN=br-d13c50d4c15b OUT=enp4s0 PHYSIN=vethdcc08d7 MAC=02:42:ed:1a:30:67:02:42:c0:a8:de:02:08:00 SRC=192.168.222.2 DST=8.8.8.8 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=52922 DF PROTO=ICMP TYPE=8 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] iptable/filter-FORWARDIN=br-d13c50d4c15b OUT=enp4s0 PHYSIN=vethdcc08d7 MAC=02:42:ed:1a:30:67:02:42:c0:a8:de:02:08:00 SRC=192.168.222.2 DST=8.8.8.8 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=52922 DF PROTO=ICMP TYPE=8 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] iptable/mangle-POSTROUTEIN=br-d13c50d4c15b OUT=enp4s0 PHYSIN=vethdcc08d7 MAC=02:42:ed:1a:30:67:02:42:c0:a8:de:02:08:00 SRC=192.168.222.2 DST=8.8.8.8 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=52922 DF PROTO=ICMP TYPE=8 CODE=0 ID=52844 SEQ=9
WAN to Container
[四 5月 8 16:38:11 2025] iptable/raw-PREROUTEIN=enp4s0 OUT= MAC=84:a9:38:b3:f5:6b:54:e0:05:2b:be:78:08:00 SRC=8.8.8.8 DST=192.168.1.201 LEN=84 TOS=0x00 PREC=0x00 TTL=114 ID=0 PROTO=ICMP TYPE=0 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] iptable/mangle-PREROUTEIN=enp4s0 OUT= MAC=84:a9:38:b3:f5:6b:54:e0:05:2b:be:78:08:00 SRC=8.8.8.8 DST=192.168.1.201 LEN=84 TOS=0x00 PREC=0x00 TTL=114 ID=0 PROTO=ICMP TYPE=0 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] iptable/mangle-FORWARDIN=enp4s0 OUT=br-d13c50d4c15b MAC=84:a9:38:b3:f5:6b:54:e0:05:2b:be:78:08:00 SRC=8.8.8.8 DST=192.168.222.2 LEN=84 TOS=0x00 PREC=0x00 TTL=113 ID=0 PROTO=ICMP TYPE=0 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] iptable/filter-FORWARDIN=enp4s0 OUT=br-d13c50d4c15b MAC=84:a9:38:b3:f5:6b:54:e0:05:2b:be:78:08:00 SRC=8.8.8.8 DST=192.168.222.2 LEN=84 TOS=0x00 PREC=0x00 TTL=113 ID=0 PROTO=ICMP TYPE=0 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] iptable/mangle-POSTROUTEIN=enp4s0 OUT=br-d13c50d4c15b MAC=84:a9:38:b3:f5:6b:54:e0:05:2b:be:78:08:00 SRC=8.8.8.8 DST=192.168.222.2 LEN=84 TOS=0x00 PREC=0x00 TTL=113 ID=0 PROTO=ICMP TYPE=0 CODE=0 ID=52844 SEQ=9 [四 5月 8 16:38:11 2025] ebtable/filter-OUTPUT IN= OUT=vethdcc08d7 MAC source = 02:42:ed:1a:30:67 MAC dest = 02:42:c0:a8:de:02 proto = 0x0800 [四 5月 8 16:38:11 2025] ebtable/nat-OUTPUT IN= OUT=vethdcc08d7 MAC source = 02:42:ed:1a:30:67 MAC dest = 02:42:c0:a8:de:02 proto = 0x0800 [四 5月 8 16:38:11 2025] ebtable/nat-POSTROUTE IN= OUT=vethdcc08d7 MAC source = 02:42:ed:1a:30:67 MAC dest = 02:42:c0:a8:de:02 proto = 0x0800



浙公网安备 33010602011771号