On 09/13/2018 03:54 AM, Lin Ma wrote:
When we call qemuARPGetInterfaces to get IP from the host's arp
table, We
ignore VIR_DOMAIN_NET_TYPE_ETHERNET, VIR_DOMAIN_NET_TYPE_VHOSTUSER and
VIR_DOMAIN_NET_TYPE_DIRECT due to the host's arp table won't include the
ip <-> mac entries about these type of backends.
That's not necessarily true. A tap device created by <interface
type='ethernet'> can be given a host-side IP address/prefix (right in
the XML as a matter of fact:
https://libvirt.org/formatdomain.html#ipconfig ) thus making traffic on
that interface available to the host's IP stack, and this adds a direct
route on the host to the subnet for that address/prefix. If the guest
has an IP on that same subnet, then the arp table on the host will
contain an entry for the guest (if the guest has sent any traffic from
that IP address).
Likewise, if an interface is of type='direct' (macvtap) and the switch
connected to the physdev of that macvtap device is "hairpinning" traffic
(to enable guest<->host communication), or alternately if there is a
different physdev on the host connected to the same switch, then there
will be an entry in the arp table on the host (again, if the guest has
sent or broadcast packets from the IP address of that interface).
Likewise, I have no personal experience with vhostuser but it's entirely
possible that the vhostuser interface of the guest ends up being in the
same broadcast domain as one of the devices (physical or virtual) on the
host that has an IP address, and in that case there will be an entry in
the host's arp table for the vhostuser device's MAC.
I guess the conclusion I would draw from this is that we shouldn't
immediately discount *any* type of interface (e.g., a hostdev interface
could also show up in the arp table, but of course the change that
you've made here actually *adds* the ability to look for those). I would
say we should check for the MAC regardless of the type.
(BTW, if you were going to do something based on the type of interface,
it would be more correct to use
virDomainNetGetActualType(vm->dev->nets[i]) rather than
vm->dev->nets[i]->type, although I'm saying that you simply shouldn't
check the type at all in this case.)
Signed-off-by: Lin Ma <lma(a)suse.com>
---
src/qemu/qemu_driver.c | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 2f8d6915e1..f066e02f36 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -20940,7 +20940,9 @@ qemuARPGetInterfaces(virDomainObjPtr vm,
goto cleanup;
for (i = 0; i < vm->def->nnets; i++) {
- if (vm->def->nets[i]->type != VIR_DOMAIN_NET_TYPE_NETWORK)
+ if (vm->def->nets[i]->type == VIR_DOMAIN_NET_TYPE_ETHERNET ||
+ vm->def->nets[i]->type == VIR_DOMAIN_NET_TYPE_VHOSTUSER ||
+ vm->def->nets[i]->type == VIR_DOMAIN_NET_TYPE_DIRECT)
continue;
virMacAddrFormat(&(vm->def->nets[i]->mac), macaddr);