[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [PATCH v2 2/2] x86/nestedsvm: honour L2's EFLAGS.IF when L1 clears V_INTR_MASKING


  • To: chunjie.zhu@xxxxxxxxxx
  • From: Ross Lagerwall <ross.lagerwall@xxxxxxxxxx>
  • Date: Tue, 10 Nov 2026 17:03:38 +0000
  • Arc-authentication-results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=citrix.com; dmarc=pass action=none header.from=citrix.com; dkim=pass header.d=citrix.com; arc=none
  • Arc-message-signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector10001; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=2twQqlpvAxEb1poHrghdnbDnMnNY4pHKKO6APh40+vM=; b=QpMVchoOIHkIeTyxVo2xuKLwWxdooela0jf2o/z8FZjH5dYNku679eEXAikO4tuaZ3A/t9P1L7NiQmseA8xmdtK98SnVivtTLKxYgP2YOUZ12rOpne/6G0UiOwl9aUfpDPRa1rQX0fdYfPeLX6q3sPnTGMX4o+wptAh3LLxwaWAK8yazVXd3W9sADiVb/X9kOAW8+Ze6L1CrIUpqreujrDJS8MWZIbZcnK1PdV1TjUMgtWO3gi9nXtznNt/3k1jGIM/zNZ9GiZYy62oscU+/jFnNkTFzMjiBMG43HyJrgFR1C1BcD6aYxVd97eJUHHBK5IF4AWpSmmgsXN8qg+qkAA==
  • Arc-seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=fJ+t5PiRJAkXcccEpuAE9F2w+uVzFXzQst27pMpayGy5lTKHD0bp2qojj0W7KIj9+is6OFkR/nnePJ+7AkBRAFFWmuIPAiW+5dTJNqNvSEUy/EIP7lOMlI9j7Sjurf5sbckCycWSd+nJVSE0n24pF6z4ieBhqKMWdkRMwzb1wzIs0rc6WiNfTPJ8LqbF16eCFlwK/xIpxfAnLua4xll5vJ1tjD7LkztyfwZ1Evobbm4Epy+Cg8nzhOTtTwM1Tiblb9GiZp6UpU+/WP5umzlU1eTMscOWpnNwNJ+qn2Pb2NFlSaAeH+2xkh19ctKglxIcd1mDuMwXeVqsjmKUwN7FjA==
  • Authentication-results: eu.smtp.expurgate.cloud; dkim=pass header.s=selector1 header.d=citrix.com header.i="@citrix.com" header.h="From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck"
  • Authentication-results: mx.microsoft.com 1; dkim=none (message not signed) header.d=none;dmarc=none action=none header.from=citrix.com;
  • Cc: andrew.cooper3@xxxxxxxxxx, jason.andryuk@xxxxxxx, jbeulich@xxxxxxxx, roger@xxxxxxxxxxxxxx, teddy.astie@xxxxxxxxxx, xen-devel@xxxxxxxxxxxxxxxxxxxx
  • Delivery-date: Tue, 10 Nov 2026 17:03:54 +0000
  • List-id: Xen developer discussion <xen-devel.lists.xenproject.org>

On 11/10/26 8:57 AM, chunjie.zhu@xxxxxxxxxx wrote:
From: Chunjie Zhu <chunjie.zhu@xxxxxxxxxx>

L0 always runs L2 with V_INTR_MASKING set, so a physical interrupt exits to
L0 regardless of L2's EFLAGS.IF.  nsvm_intr_blocked() only blocks when L1
requested V_INTR_MASKING=1 and L1's IF was clear.  With V_INTR_MASKING=0
and L2's IF clear, nestedsvm_vcpu_interrupt() would still inject
VMEXIT(INTR) into L1.

Per the APM (vol.2 rev 3.44 "Physical Interrupt Masking in EFLAGS"), with
V_INTR_MASKING=0 L2's IF masks physical interrupts, and a masked interrupt
must stay pending.  Return NSVM_INTR_MASKED for external interrupts in
that case.

Signed-off-by: Chunjie Zhu <chunjie.zhu@xxxxxxxxxx>
---
v2:
  * Move the check into nsvm_intr_blocked(), as suggested by Ross.

  xen/arch/x86/hvm/svm/nestedsvm.c | 12 ++++++++++--
  1 file changed, 10 insertions(+), 2 deletions(-)

diff --git a/xen/arch/x86/hvm/svm/nestedsvm.c b/xen/arch/x86/hvm/svm/nestedsvm.c
index a93681e9bbcd..e3b2d20ffce2 100644
--- a/xen/arch/x86/hvm/svm/nestedsvm.c
+++ b/xen/arch/x86/hvm/svm/nestedsvm.c
@@ -1222,8 +1222,16 @@ enum hvm_intblk cf_check nsvm_intr_blocked(struct vcpu 
*v)
      {
          struct vmcb_struct *n2vmcb = nv->nv_n2vmcx;
- if ( svm->ns_hostflags.fields.vintrmask &&
-             !svm->ns_hostflags.fields.rflagsif )
+        /*
+         * With V_INTR_MASKING, L1's EFLAGS.IF masks physical interrupts.
+         * Without it, L2's EFLAGS.IF does (APM vol.2 rev 3.44 "Physical
+         * Interrupt Masking in EFLAGS"); L0 always runs L2 with
+         * V_INTR_MASKING set, so the interrupt would otherwise exit to L0
+         * and be forwarded to L1 even with L2's IF clear.
+         */
+        if ( svm->ns_hostflags.fields.vintrmask
+             ? !svm->ns_hostflags.fields.rflagsif
+             : !(guest_cpu_user_regs()->eflags & X86_EFLAGS_IF) )
              return hvm_intblk_rflags_ie;
/* when l1 guest passes its devices through to the l2 guest

This only works if the function is called with v == current. I think it
is, but it should probably have an assert to confirm this (like
hvm_interrupt_blocked()).

Also note that this series needs rebasing on top of the latest staging
since it doesn't apply cleanly.

Ross



 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.