《理解Linux Bridge、Tun/Tap、Veth Pair》
kvm虚拟机中能查到自己对应的虚拟交换机吗,为什么在虚拟机中用lldpcli show nei看不到邻居?
在 KVM 虚拟机中无法直接查到自己对应的虚拟交换机,且默认情况下用 lldpcli show nei 看不到邻居设备(如物理交换机),这与 KVM 的网络虚拟化机制和 LLDP 报文的转发逻辑密切相关。
一、为什么 KVM 虚拟机中查不到对应的虚拟交换机?
KVM 的虚拟交换机通常是宿主机上的 Linux 网桥(Bridge)(如 virbr0、br0 等),它是宿主机内核中的虚拟网络设备,并非虚拟机内部可见的 “实体”。
虚拟机的网络适配器(如 eth0)通过 TAP 设备 与宿主机的网桥连接,虚拟机只能感知到自己的虚拟网卡和对应的网络(如 IP 地址、网关),但无法直接 “看到” 宿主机上的网桥(虚拟交换机)的存在。
虚拟交换机的配置和信息(如网桥名称、连接的物理网卡)仅存在于宿主机中,虚拟机作为独立的操作系统,无法直接访问宿主机的内核网络设备信息。
如果需要查看虚拟机对应的虚拟交换机,必须在宿主机上操作(如通过 virsh dumpxml 虚拟机名 查看网桥关联,或 brctl show 查看网桥配置)。
二、为什么虚拟机中用 lldpcli show nei 看不到邻居?
LLDP(链路层发现协议)用于设备间交换邻居信息(如交换机端口、VLAN 配置等),但在 KVM 环境中,虚拟机默认无法收到物理交换机的 LLDP 报文,主要原因如下:
- 虚拟交换机(网桥)默认不转发 LLDP 报文
宿主机的 Linux 网桥默认工作在 二层转发模式,但 LLDP 报文属于 链路层控制帧(目的 MAC 为 01:80:c2:00:00:0e 等特殊地址),这类帧通常被网桥视为 “本地帧”,不会转发到连接的虚拟机(TAP 设备)。
网桥的设计初衷是转发普通数据帧(如 IP 报文),而控制帧(如 LLDP、STP 等)默认被拦截在宿主机,不会传递给虚拟机。 - 虚拟机与物理交换机之间的 “隔离”
虚拟机的网络流量需经过 TAP 设备 → 宿主机网桥 → 物理网卡 才能到达物理交换机,而 LLDP 报文能否通过这个路径,取决于宿主机的配置:
若宿主机未开启 “允许 LLDP 报文透传”,物理交换机发送的 LLDP 报文会被宿主机网桥拦截,虚拟机无法收到。
即使宿主机网桥转发了 LLDP 报文,虚拟机内部也需要安装 lldpd 并启用(如 systemctl start lldpd),否则无法解析和显示邻居信息。
三、如何让虚拟机收到 LLDP 报文?
若需要在 KVM 虚拟机中通过 LLDP 查看物理交换机等邻居信息,需在 宿主机上配置网桥转发 LLDP 报文,步骤如下:
- 允许网桥转发 LLDP 控制帧
Linux 网桥通过 bridge 模块的参数控制是否转发特殊控制帧,需开启对 LLDP 报文的转发:
#临时生效(重启后失效)
echo 0 > /sys/class/net/br0/bridge/group_fwd_mask
# 说明:group_fwd_mask 默认为 0x1(仅转发 802.1d 协议帧),设为 0 表示允许转发所有控制帧(包括 LLDP)
- 持久化配置(避免重启失效)
在 /etc/sysctl.conf 或网桥配置文件中添加规则(以 br0 为例):
# 创建网桥配置文件
cat > /etc/udev/rules.d/99-bridge-lldp.rules << EOF
ACTION=="add", SUBSYSTEM=="net", NAME=="br0", RUN+="/bin/sh -c 'echo 0 > /sys/class/net/br0/bridge/group_fwd_mask'"
EOF
在虚拟机中安装并启动 lldpd
# CentOS/RHEL 安装
sudo dnf install lldpd -y
# 启动服务
sudo systemctl start lldpd
sudo systemctl enable lldpd
# 查看邻居
lldpcli show neighbors
总结
KVM 虚拟机中无法直接查看对应的虚拟交换机,需在宿主机上通过 virsh 或网桥工具查询。
虚拟机默认看不到 LLDP 邻居,是因为宿主机网桥默认不转发链路层控制帧,需手动配置网桥允许转发 LLDP 报文,并在虚拟机中启用 lldpd 服务。