On 5/21/26 23:31, Andrey Drobyshev wrote:
> This email originated from an IP that might not be authorized by the domain 
> it was sent from.
> Do not click links or open attachments unless it is an email you expected to 
> receive.
> Commit 4ff28534c799 ("ms/vhost/vsock: Refuse the connection immediately
> when guest isn't ready") added a check which immediately returns
> EHOSTUNREACH when the guest isn't ready yet.  Namely, we check that guest
> hasn't enabled the RX vq yet, i.e. virtio-vsock has never beed enabled.
>
> However, the check also affects the transient state when backend is
> temporarily set to NULL during VHOST_VSOCK_SET_RUNNING(0).  Notably,
> this is the case with qemu-update operation, during which we perform
> VHOST_RESET_OWNER.  In this case sendmsg()/connect() on otherwise healthy
> connection gets EHOSTUNREACH.
>
> Gate the fast-fail on a sticky started_once bit set in
> vhost_vsock_start() and never cleared.  Once the guest has brought
> up virtio-vsock at least once, a NULL backend means a transient stop
> window and the packet must be queued for vhost_vsock_start() to drain
> on re-attach.
>
> Fixes: 4ff28534c799 ("ms/vhost/vsock: Refuse the connection immediately when 
> guest isn't ready")
> https://virtuozzo.atlassian.net/browse/VSTOR-131956
> Signed-off-by: Andrey Drobyshev <[email protected]>
> ---
>  drivers/vhost/vsock.c | 21 +++++++++++----------
>  1 file changed, 11 insertions(+), 10 deletions(-)
>
> diff --git a/drivers/vhost/vsock.c b/drivers/vhost/vsock.c
> index 0a518c3d1596..f39354db630e 100644
> --- a/drivers/vhost/vsock.c
> +++ b/drivers/vhost/vsock.c
> @@ -57,6 +57,7 @@ struct vhost_vsock {
>  
>       u32 guest_cid;
>       bool seqpacket_allow;
> +     bool started_once;      /* latched in vhost_vsock_start(); never 
> cleared */
>  };
>  
>  static u32 vhost_transport_get_local_cid(void)
> @@ -285,17 +286,14 @@ vhost_transport_send_pkt(struct sk_buff *skb)
>               return -ENODEV;
>       }
>  
> -     /* Fast-fail if the guest hasn't enabled the RX vq yet. Queuing the 
> packet
> -      * and making the caller wait is pointless: even if the guest manages 
> to init
> -      * within the timeout, it'll immediately reply with RST, because 
> there's no
> -      * listener on the port yet.
> -      *
> -      * vhost_vq_get_backend() without vq->mutex is acceptable here: locking
> -      * the mutex would be too expensive in this hot path, and we already 
> have
> -      * all the outcomes covered: if the backend becomes NULL right after 
> the check,
> -      * vhost_transport_do_send_pkt() will check it under the mutex anyway.
> +     /*
> +      * Fast-fail only when the guest has never enabled virtio-vsock.
> +      * Once it has, a NULL backend means a transient SET_RUNNING(0)
> +      * window (e.g. VHOST_RESET_OWNER); the packet must be
> +      * queued for vhost_vsock_start() to drain on re-attach.
>        */
> -     if 
> (unlikely(!data_race(vhost_vq_get_backend(&vsock->vqs[VSOCK_VQ_RX])))) {
> +     if (unlikely(!READ_ONCE(vsock->started_once)) &&
> +         !data_race(vhost_vq_get_backend(&vsock->vqs[VSOCK_VQ_RX]))) {
>               rcu_read_unlock();
>               kfree_skb(skb);
>               return -EHOSTUNREACH;
> @@ -615,6 +613,9 @@ static int vhost_vsock_start(struct vhost_vsock *vsock)
>        */
>       vhost_vq_work_queue(&vsock->vqs[VSOCK_VQ_RX], &vsock->send_pkt_work);
>  
> +     /* See vhost_transport_send_pkt(); never cleared. */
> +     WRITE_ONCE(vsock->started_once, true);
> +
>       mutex_unlock(&vsock->dev.mutex);
>       return 0;
>  
what about guest reset + stuck in BIOS?

Den
_______________________________________________
Devel mailing list
[email protected]
https://lists.openvz.org/mailman/listinfo/devel

Reply via email to