From nobody Sun Dec 14 12:16:11 2025 Received: from mail-pj1-f74.google.com (mail-pj1-f74.google.com [209.85.216.74]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 665CE20B81E for ; Fri, 23 May 2025 01:00:16 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.216.74 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1747962017; cv=none; b=pi/AzwCcMa9aZDrEgmC8igMTpGPhB+SD2Ta2+4eM/CyJI9/EqFK11kHR3KBGeG+CKoh48tsKGgDfeI6iVXwpm0lePxPklDlhif14lXf5fzL+WKFLsKE1fuPlZnE0jWBXoWXUkiQnY68EAg1j1MlF6zHNwq0dM5bofzjhBnwhnus= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1747962017; c=relaxed/simple; bh=x9Js4xRf2fagahtWsIdqeRgieCQlq12uWu+DkKct3A0=; h=Date:In-Reply-To:Mime-Version:References:Message-ID:Subject:From: To:Cc:Content-Type; b=GVgcjFlUKwZj6bEoJNbNUt+w3DGMv38u5hAmdfHX/rK/B0D3AobOlSA7CJyntiRRI9w6eGEI7IchGrL6THfC3muQrVg4ne3trH1NX9tGrx12x5lJnnVu974sUaDbt7Fj7BOBEeVZItfba7dR5lPb6Z3/z2TOTRJAiFsJ6ikwHw8= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com; spf=pass smtp.mailfrom=flex--seanjc.bounces.google.com; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b=jBW6HKRJ; arc=none smtp.client-ip=209.85.216.74 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=flex--seanjc.bounces.google.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="jBW6HKRJ" Received: by mail-pj1-f74.google.com with SMTP id 98e67ed59e1d1-30e810d6901so5670358a91.3 for ; Thu, 22 May 2025 18:00:16 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20230601; t=1747962016; x=1748566816; darn=vger.kernel.org; h=cc:to:from:subject:message-id:references:mime-version:in-reply-to :date:reply-to:from:to:cc:subject:date:message-id:reply-to; bh=f+eDLIQHFMcpEOYcHglDhK5o4FzkgGqWkRl/nqwWdGk=; b=jBW6HKRJsvqLsDyZjV2jHRRVDKAhoCyAKDrRFB02ilfP5H2YtkT7M01pXGmWgJrnP1 zLMX0jpy5c/rdcypLQj6TUw6OnjPehaFQGTrrPPRkEaoBb7DrEXqGbmr2Bx4wr/pj/jg kjp3c+/5ND3/HUhvVBR2FjP6hVzaw4s6+pjvNSoeSLqoHq4kR27nblPjiKx7ud7JdPxk 0uM4ti+M2NuR2ZrDxaon52Fj3AWUEk81IkAWPvr2KVxjkhAKRFmAvxGuP7GkPXNB3pJE vgfZayoDs9NjGem6nLwGVBCzzjFQqGXvdApn26J7uZuJ8T88F3CzII8ZPtgy/aJb49Y0 3OhA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1747962016; x=1748566816; h=cc:to:from:subject:message-id:references:mime-version:in-reply-to :date:reply-to:x-gm-message-state:from:to:cc:subject:date:message-id :reply-to; bh=f+eDLIQHFMcpEOYcHglDhK5o4FzkgGqWkRl/nqwWdGk=; b=vtapF0HCmyIcujF5XPL9Kc4VmRDPOJjcdNngioMZPmsB7rSlYY24yZgZPKHFng6oAc DbcQK6l5MzOmaB1SxMgARpMSfGWopDmSM2CZzfY23qj8T6O5IxlOD1f/AFN7gLMrM5mN QXnVbe6ix+tDpeSV2VE/JX56w9h4rj6Wtmg+twiCfebuLMg+lveE+a18Yr8nOThRYJ8s JKkQrXQi/xVTyy0HqhMgA9go0P0V1KBiMAIwRqbD9XRFcUoPC0GMIdgEYhHBmIlbvOPg frfKgAcyTewiLSjvRYNvKXg+buLWWB17BIBsKuk8VByUOf8cS2idfIWjAxeghwQX/Rhl 2tIA== X-Forwarded-Encrypted: i=1; AJvYcCXyEgXBevyafdE78+MSOVTXKnbq+OEyRNn2MVxN7fBVj++K0k3OX1Is/7kIpbgk2JyM3F7lt5El18yG/HU=@vger.kernel.org X-Gm-Message-State: AOJu0YyC/wdZayo5v1+0MnRkQxHaFLUuKaFPcgtsKO3teJ8TR56LY6j4 nCSFM6j6hPcHuG0OiFmC5VI5IHqB/VaD0jqbS2uif7Ir3z9Y4Cyz4lPJIrcmNzxic4h1Vspp/ZE odqXLuw== X-Google-Smtp-Source: AGHT+IFRK4pCGNx5RVFqayo33KWfIvlE7D1S00v4g5t5HPuyq20BbcD+1Y9gRM+96VncuPv0B1J4drbDnBM= X-Received: from pjbsn15.prod.google.com ([2002:a17:90b:2e8f:b0:30c:4b1f:78ca]) (user=seanjc job=prod-delivery.src-stubby-dispatcher) by 2002:a17:90b:4c87:b0:2fe:d766:ad8e with SMTP id 98e67ed59e1d1-310e96b6d28mr1783221a91.4.1747962015762; Thu, 22 May 2025 18:00:15 -0700 (PDT) Reply-To: Sean Christopherson Date: Thu, 22 May 2025 17:59:08 -0700 In-Reply-To: <20250523010004.3240643-1-seanjc@google.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: Mime-Version: 1.0 References: <20250523010004.3240643-1-seanjc@google.com> X-Mailer: git-send-email 2.49.0.1151.ga128411c76-goog Message-ID: <20250523010004.3240643-4-seanjc@google.com> Subject: [PATCH v2 03/59] KVM: SVM: Delete IRTE link from previous vCPU before setting new IRTE From: Sean Christopherson To: Sean Christopherson , Paolo Bonzini , Joerg Roedel , David Woodhouse , Lu Baolu Cc: kvm@vger.kernel.org, iommu@lists.linux.dev, linux-kernel@vger.kernel.org, Sairaj Kodilkar , Vasant Hegde , Maxim Levitsky , Joao Martins , Francesco Lavra , David Matlack Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Delete the previous per-vCPU IRTE link prior to modifying the IRTE. If forcing the IRTE back to remapped mode fails, the IRQ is already broken; keeping stale metadata won't change that, and the IOMMU should be sufficiently paranoid to sanitize the IRTE when the IRQ is freed and reallocated. This will allow hoisting the vCPU tracking to common x86, which in turn will allow most of the IRTE update code to be deduplicated. Tested-by: Sairaj Kodilkar Signed-off-by: Sean Christopherson --- arch/x86/kvm/svm/avic.c | 60 +++++++++------------------------------ include/linux/kvm_irqfd.h | 1 + 2 files changed, 14 insertions(+), 47 deletions(-) diff --git a/arch/x86/kvm/svm/avic.c b/arch/x86/kvm/svm/avic.c index d33c01379421..ed7374f0bd5a 100644 --- a/arch/x86/kvm/svm/avic.c +++ b/arch/x86/kvm/svm/avic.c @@ -766,23 +766,19 @@ static int avic_set_pi_irte_mode(struct kvm_vcpu *vcp= u, bool activate) return ret; } =20 -static void svm_ir_list_del(struct vcpu_svm *svm, - struct kvm_kernel_irqfd *irqfd, - struct amd_iommu_pi_data *pi) +static void svm_ir_list_del(struct kvm_kernel_irqfd *irqfd) { + struct kvm_vcpu *vcpu =3D irqfd->irq_bypass_vcpu; unsigned long flags; - struct kvm_kernel_irqfd *cur; =20 - spin_lock_irqsave(&svm->ir_list_lock, flags); - list_for_each_entry(cur, &svm->ir_list, vcpu_list) { - if (cur->irq_bypass_data !=3D pi->ir_data) - continue; - if (WARN_ON_ONCE(cur !=3D irqfd)) - continue; - list_del(&irqfd->vcpu_list); - break; - } - spin_unlock_irqrestore(&svm->ir_list_lock, flags); + if (!vcpu) + return; + + spin_lock_irqsave(&to_svm(vcpu)->ir_list_lock, flags); + list_del(&irqfd->vcpu_list); + spin_unlock_irqrestore(&to_svm(vcpu)->ir_list_lock, flags); + + irqfd->irq_bypass_vcpu =3D NULL; } =20 static int svm_ir_list_add(struct vcpu_svm *svm, @@ -795,24 +791,7 @@ static int svm_ir_list_add(struct vcpu_svm *svm, if (WARN_ON_ONCE(!pi->ir_data)) return -EINVAL; =20 - /** - * In some cases, the existing irte is updated and re-set, - * so we need to check here if it's already been * added - * to the ir_list. - */ - if (pi->prev_ga_tag) { - struct kvm *kvm =3D svm->vcpu.kvm; - u32 vcpu_id =3D AVIC_GATAG_TO_VCPUID(pi->prev_ga_tag); - struct kvm_vcpu *prev_vcpu =3D kvm_get_vcpu_by_id(kvm, vcpu_id); - struct vcpu_svm *prev_svm; - - if (!prev_vcpu) - return -EINVAL; - - prev_svm =3D to_svm(prev_vcpu); - svm_ir_list_del(prev_svm, irqfd, pi); - } - + irqfd->irq_bypass_vcpu =3D &svm->vcpu; irqfd->irq_bypass_data =3D pi->ir_data; =20 spin_lock_irqsave(&svm->ir_list_lock, flags); @@ -904,6 +883,8 @@ int avic_pi_update_irte(struct kvm_kernel_irqfd *irqfd,= struct kvm *kvm, =20 WARN_ON_ONCE(new && memcmp(e, new, sizeof(*new))); =20 + svm_ir_list_del(irqfd); + /** * Here, we setup with legacy mode in the following cases: * 1. When cannot target interrupt to a specific vcpu. @@ -962,21 +943,6 @@ int avic_pi_update_irte(struct kvm_kernel_irqfd *irqfd= , struct kvm *kvm, pi.prev_ga_tag =3D 0; pi.is_guest_mode =3D false; ret =3D irq_set_vcpu_affinity(host_irq, &pi); - - /** - * Check if the posted interrupt was previously - * setup with the guest_mode by checking if the ga_tag - * was cached. If so, we need to clean up the per-vcpu - * ir_list. - */ - if (!ret && pi.prev_ga_tag) { - int id =3D AVIC_GATAG_TO_VCPUID(pi.prev_ga_tag); - struct kvm_vcpu *vcpu; - - vcpu =3D kvm_get_vcpu_by_id(kvm, id); - if (vcpu) - svm_ir_list_del(to_svm(vcpu), irqfd, &pi); - } } out: srcu_read_unlock(&kvm->irq_srcu, idx); diff --git a/include/linux/kvm_irqfd.h b/include/linux/kvm_irqfd.h index 6510a48e62aa..361c07f4466d 100644 --- a/include/linux/kvm_irqfd.h +++ b/include/linux/kvm_irqfd.h @@ -60,6 +60,7 @@ struct kvm_kernel_irqfd { struct irq_bypass_consumer consumer; struct irq_bypass_producer *producer; =20 + struct kvm_vcpu *irq_bypass_vcpu; struct list_head vcpu_list; void *irq_bypass_data; }; --=20 2.49.0.1151.ga128411c76-goog