public inbox for passt-dev@passt.top
 help / color / mirror / code / Atom feed
From: David Gibson <david@gibson.dropbear.id.au>
To: Volker Diels-Grabsch <v@njh.eu>
Cc: passt-dev@passt.top
Subject: Re: [PATCH] Send an initial ARP and NDP request to resolve the guest IP address
Date: Wed, 10 Sep 2025 13:32:34 +1000	[thread overview]
Message-ID: <aMDxUvzIt8JBRa4t@zatzit> (raw)
In-Reply-To: <20250909145516.762957-2-v@njh.eu>

[-- Attachment #1: Type: text/plain, Size: 4160 bytes --]

On Tue, Sep 09, 2025 at 04:49:20PM +0200, Volker Diels-Grabsch wrote:
> When restarting passt while QEMU keeps running with a configured
> "reconnect-ms" setting, the port forwardings will stop working until
> the guest sends some outgoing network traffic.
> 
> Reason: Although QEMU reconnects successfully to the unix domain
> socket of the new passt process, that one no longer knows the guest's
> MAC address and uses instead the broadcast MAC address.  However, this
> is ignored by the guest, at least if the guest runs Linux.  Only after
> the guest sends some network package on its own initiative, passt will
> know the MAC address and will be able to establish forwarded
> connections.
> 
> This change fixes this issue by sending an ARP and an NDP request to
> resolve the guest's MAC address via its IPv4 and IPv6 address, which
> we do know, right after the unix domain socket (re)connection.
> 
> The only case where the IP is "wrong" would be if the configuration
> changed, or on the very first start right after qemu started.  But in
> those cases, we just wouldn't get an ARP/NDP response, and can't do
> anything until we receive the guest's DHCP request - just as before.
> In other words, in the worst case the ARP/NDP requests would be
> harmless.
> 
> Signed-off-by: Volker Diels-Grabsch <v@njh.eu>

Reviewed-by: David Gibson <david@gibson.dropbear.id.au>

Two tiny nits that aren't worth a respin, but maybe Stefano will want
to change on merge:

[snip]
> diff --git a/tap.c b/tap.c
> index 7ba6399..ea61eae 100644
> --- a/tap.c
> +++ b/tap.c
> @@ -1088,6 +1088,7 @@ void tap_add_packet(struct ctx *c, struct iov_tail *data,
>  {
>  	struct ethhdr eh_storage;
>  	const struct ethhdr *eh;
> +	char bufmac[ETH_ADDRSTRLEN];

We'd generally prefer to move this local to the if block where it's
used.


>  
>  	pcap_iov(data->iov, data->cnt, data->off);
>  
> @@ -1097,6 +1098,7 @@ void tap_add_packet(struct ctx *c, struct iov_tail *data,
>  
>  	if (memcmp(c->guest_mac, eh->h_source, ETH_ALEN)) {
>  		memcpy(c->guest_mac, eh->h_source, ETH_ALEN);
> +		info("Guest MAC address: %s", eth_ntop(c->guest_mac, bufmac, sizeof(bufmac)));
>  		proto_update_l2_buf(c->guest_mac, NULL);
>  	}
>  
> @@ -1355,6 +1357,11 @@ static void tap_start_connection(const struct ctx *c)
>  	ev.events = EPOLLIN | EPOLLRDHUP;
>  	ev.data.u64 = ref.u64;
>  	epoll_ctl(c->epollfd, EPOLL_CTL_ADD, c->fd_tap, &ev);
> +
> +	info("Sending initial ARP and NDP request to retrieve"
> +	     " guest MAC address after reconnect");

I think it's going to be rare that we care about this, so I'd demote
it to a debug().

> +	arp_send_init_req(c);
> +	ndp_send_init_req(c);
>  }
>  
>  /**
> @@ -1503,11 +1510,12 @@ void tap_backend_init(struct ctx *c)
>  	case MODE_PASST:
>  		tap_sock_unix_init(c);
>  
> -		/* In passt mode, we don't know the guest's MAC address until it
> -		 * sends us packets.  Use the broadcast address so that our
> -		 * first packets will reach it.
> +		/* In passt mode, we don't know the guest's MAC address until
> +		 * it sends us packets (e.g. responds to our initial ARP or
> +		 * NDP request).  Until then, use the broadcast address so
> +		 * that our first packets will have a chance to reach it.
>  		 */
> -		memset(&c->guest_mac, 0xff, sizeof(c->guest_mac));
> +		memcpy(&c->guest_mac, MAC_BROADCAST, sizeof(c->guest_mac));
>  		break;
>  	}
>  
> diff --git a/util.h b/util.h
> index 2a8c38f..3719f0c 100644
> --- a/util.h
> +++ b/util.h
> @@ -97,6 +97,7 @@ void abort_with_msg(const char *fmt, ...)
>  #define FD_PROTO(x, proto)						\
>  	(IN_INTERVAL(c->proto.fd_min, c->proto.fd_max, (x)))
>  
> +#define MAC_BROADCAST		((uint8_t [ETH_ALEN]){ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff })
>  #define MAC_ZERO		((uint8_t [ETH_ALEN]){ 0 })
>  #define MAC_IS_ZERO(addr)	(!memcmp((addr), MAC_ZERO, ETH_ALEN))
>  
> -- 
> 2.47.3
> 

-- 
David Gibson (he or they)	| I'll have my music baroque, and my code
david AT gibson.dropbear.id.au	| minimalist, thank you, not the other way
				| around.
http://www.ozlabs.org/~dgibson

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 833 bytes --]

  reply	other threads:[~2025-09-10  3:33 UTC|newest]

Thread overview: 14+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2025-09-07 11:01 [PATCH] Send an initial ARP " Volker Diels-Grabsch
2025-09-08  4:00 ` David Gibson
2025-09-08  9:12   ` [PATCH v2] " Volker Diels-Grabsch
2025-09-08  9:22     ` Volker Diels-Grabsch
2025-09-09  2:52       ` David Gibson
2025-09-09 10:10         ` Volker Diels-Grabsch
2025-09-09 14:49           ` Volker Diels-Grabsch
2025-09-09 14:49             ` [PATCH] Send an initial ARP and NDP request to resolve the guest IP address Volker Diels-Grabsch
2025-09-10  3:32               ` David Gibson [this message]
2025-09-10  9:29               ` Stefano Brivio
2025-09-10 10:33                 ` Volker Diels-Grabsch
2025-09-10 14:01                   ` Stefano Brivio
2025-09-09 15:55           ` [PATCH v2] Send an initial ARP " Stefano Brivio
2025-09-10  3:33             ` David Gibson

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=aMDxUvzIt8JBRa4t@zatzit \
    --to=david@gibson.dropbear.id.au \
    --cc=passt-dev@passt.top \
    --cc=v@njh.eu \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://passt.top/passt

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for IMAP folder(s).