Received: by 2002:ab2:3350:0:b0:1f4:6588:b3a7 with SMTP id o16csp190746lqe; Fri, 5 Apr 2024 18:35:21 -0700 (PDT) X-Forwarded-Encrypted: i=3; AJvYcCUG4ZgDprfT6WmaMe/1ZvQKz5RD/ZRiiZX4Cu1VM2DSAGvLrtGcPrbPNnrH+VdZ7dERnAnBW4t0Oyi8TTSbDPf+v4jP5sNR4I9SLFvkrA== X-Google-Smtp-Source: AGHT+IHgyyYvdv4SG+8KbvY/yQBsXQEbcfxVzqBF4ILb7KiG2E0j99LNuCRZEdPU+nTVSzIpf27M X-Received: by 2002:a05:6870:b48d:b0:22e:ed14:3e3d with SMTP id y13-20020a056870b48d00b0022eed143e3dmr1034448oap.33.1712367321352; Fri, 05 Apr 2024 18:35:21 -0700 (PDT) ARC-Seal: i=2; a=rsa-sha256; t=1712367321; cv=pass; d=google.com; s=arc-20160816; b=uQx9+PhLttV1gJp7Y2CF6oVacy+Th13zpC8ewUkAUiEe5pUji1HM6/hxFeIfNkSoGJ 1cfu650juovf9KS4UwlLbDRx9ateZTLoQaqz4T3dmBkfB9hVT2FoTpQSNA0RthRwhfaU ZY0Ub5C9Jv/kQTtPcN9JAlkcAVqcLl42c72J5WwXtb8ZtW12kNCe5XwrwSWku2cMod09 rF7aU5avr33mBNY/qCyTIrue9WqDxalmXvntrTv7tS96qwb2RZeubbiJKeqKrdg56g+j l2ydwQ6pdLHPR9M0BzZGR+VEeu5EIHPYNW0LAqfHmkH3eXRSn/IP/0nUWtSKlPXtCvek jkdA== ARC-Message-Signature: i=2; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=content-transfer-encoding:mime-version:list-unsubscribe :list-subscribe:list-id:precedence:references:in-reply-to:message-id :date:subject:cc:to:from:dkim-signature; bh=eVwNBc0X2VjEsRwYBb9d/JNvLrw+T2qG/zK4CTJhk+E=; fh=bhqlPbXjHBxQzd6TvgdNdBs+Har8pRoecv6ZHfN2TWo=; b=T7ly4UE+YlRgmIEGHbg7f0BX3HQTk+RBNgParjOqMLLAms8GYhk+m2k9qWiS5XS1ub PMeQy03Kxs0c4/un+b+BBDeOTgcNlApncp58YGIuXwPsTYjhFzpvxKELnCsE2sftrdyi w/ZVJBAPxMgeLbvh1mxyYUv1SInLJGxPoMV0GnW/fE2RTqScFFg/wOplk9x/CnKRLXX4 GIAL0h13el8Zx/i4yCvNz/lvKdxRuSYa7px77wVn2+qJ1anuRCksePyA3kDpgh8jys3K 9vLfL/DHPzFh4o3ySdq7TTnji2rqJq9pGi2EOXdOW+hd51uRI27mZ0flqWzkc+9ybFDf P0zA==; dara=google.com ARC-Authentication-Results: i=2; mx.google.com; dkim=pass header.i=@intel.com header.s=Intel header.b=TnJGte1Y; arc=pass (i=1 dkim=pass dkdomain=intel.com dmarc=pass fromdomain=linux.intel.com); spf=pass (google.com: domain of linux-kernel+bounces-133681-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45e3:2400::1 as permitted sender) smtp.mailfrom="linux-kernel+bounces-133681-linux.lists.archive=gmail.com@vger.kernel.org"; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=intel.com Return-Path: Received: from sv.mirrors.kernel.org (sv.mirrors.kernel.org. [2604:1380:45e3:2400::1]) by mx.google.com with ESMTPS id j31-20020a63fc1f000000b005e4e759dd6fsi2236290pgi.433.2024.04.05.18.35.21 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 05 Apr 2024 18:35:21 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel+bounces-133681-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45e3:2400::1 as permitted sender) client-ip=2604:1380:45e3:2400::1; Authentication-Results: mx.google.com; dkim=pass header.i=@intel.com header.s=Intel header.b=TnJGte1Y; arc=pass (i=1 dkim=pass dkdomain=intel.com dmarc=pass fromdomain=linux.intel.com); spf=pass (google.com: domain of linux-kernel+bounces-133681-linux.lists.archive=gmail.com@vger.kernel.org designates 2604:1380:45e3:2400::1 as permitted sender) smtp.mailfrom="linux-kernel+bounces-133681-linux.lists.archive=gmail.com@vger.kernel.org"; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=intel.com Received: from smtp.subspace.kernel.org (wormhole.subspace.kernel.org [52.25.139.140]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by sv.mirrors.kernel.org (Postfix) with ESMTPS id 4F5C2286A60 for ; Fri, 5 Apr 2024 22:30:29 +0000 (UTC) Received: from localhost.localdomain (localhost.localdomain [127.0.0.1]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 9920717B501; Fri, 5 Apr 2024 22:26:58 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=intel.com header.i=@intel.com header.b="TnJGte1Y" Received: from mgamail.intel.com (mgamail.intel.com [192.198.163.10]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id D2694179961; Fri, 5 Apr 2024 22:26:55 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=192.198.163.10 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1712356017; cv=none; b=QOETdDAbPKkz2KDw9OAQGOxPCNxMrqd7YU4VA32G0F6+3V2x7R2LwZfigt7VIqwiU7ChF4qaeGAlg9Q65+r+UaIjGQz1bzs3V/b/q51PM/jCy3xMtWc+524ktG0Cmn51ESHcBGKIzZL/dgmDEC4jwDcs0mPgSu1QaFm5x+mx4Wk= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1712356017; c=relaxed/simple; bh=ZGWBCczfujdRtFbtPKsDRo5XDo8fcTnRO3bkTJQexVw=; h=From:To:Cc:Subject:Date:Message-Id:In-Reply-To:References: MIME-Version; b=Q1AnuOLSod+XXPNUNAldrVt4aUJrAUHXF7Odi9as2yCq9ffJv3vEUiydUdcLK9fiki9EQxMaICsv6TgVTFSZHI45iWxA6pGvd1IKX4GdHIY4OvInhUjDWv9e/Z+/XD7gcrXAPEJEQ4Lplvns8AoLAd6s9/PgjksZnwJ9I/ClAjY= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=linux.intel.com; spf=none smtp.mailfrom=linux.intel.com; dkim=pass (2048-bit key) header.d=intel.com header.i=@intel.com header.b=TnJGte1Y; arc=none smtp.client-ip=192.198.163.10 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=linux.intel.com Authentication-Results: smtp.subspace.kernel.org; spf=none smtp.mailfrom=linux.intel.com DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1712356016; x=1743892016; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=ZGWBCczfujdRtFbtPKsDRo5XDo8fcTnRO3bkTJQexVw=; b=TnJGte1YL+nyCRoQLZcXNkdQ2AfgvE3IQg/foLXtWevw6xCX22aY/XQE xlMuHjz/Zqp04UmVke+k7W2p4p1g3ElEgC+15CqJIWoQRr9OsnzA6kFwB 5ZZCFh5+qQEWuZYwnuyShe/P48uVl29tQraCJXq6MIdXoRAWKia4bt73K qVz4W5BN8j1wh+h9pSgT5cYt9guxxTWOqcB4mtpa7962ag6zpS4hm2qAf mbAQlit4JQF6dKkZNYdCD3tTq4sZmTKUGURrfx8OtkcfhSiTTGrSVhyiS CS0yTqwUBIkW+WjES0489u0HYSGYHwGw0RMq218IceN24+BMZ0cdAMs1/ w==; X-CSE-ConnectionGUID: Run8SIX+SWiU9HpnW8Geyw== X-CSE-MsgGUID: NC5Ia1NgTe6WY+u2eFMCrA== X-IronPort-AV: E=McAfee;i="6600,9927,11035"; a="19062853" X-IronPort-AV: E=Sophos;i="6.07,182,1708416000"; d="scan'208";a="19062853" Received: from fmviesa004.fm.intel.com ([10.60.135.144]) by fmvoesa104.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 05 Apr 2024 15:26:54 -0700 X-CSE-ConnectionGUID: dqE0TdDNQ62K5gm9q66mFQ== X-CSE-MsgGUID: icfEMMlNRoyitei5C2xCcw== X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="6.07,182,1708416000"; d="scan'208";a="23928356" Received: from jacob-builder.jf.intel.com ([10.54.39.125]) by fmviesa004.fm.intel.com with ESMTP; 05 Apr 2024 15:26:52 -0700 From: Jacob Pan To: LKML , X86 Kernel , Peter Zijlstra , iommu@lists.linux.dev, Thomas Gleixner , "Lu Baolu" , kvm@vger.kernel.org, Dave Hansen , Joerg Roedel , "H. Peter Anvin" , "Borislav Petkov" , "Ingo Molnar" Cc: Paul Luse , Dan Williams , Jens Axboe , Raj Ashok , "Tian, Kevin" , maz@kernel.org, seanjc@google.com, "Robin Murphy" , jim.harris@samsung.com, a.manzanares@samsung.com, "Bjorn Helgaas" , guang.zeng@intel.com, robert.hoo.linux@gmail.com, Jacob Pan Subject: [PATCH v2 13/13] iommu/vt-d: Enable posted mode for device MSIs Date: Fri, 5 Apr 2024 15:31:10 -0700 Message-Id: <20240405223110.1609888-14-jacob.jun.pan@linux.intel.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20240405223110.1609888-1-jacob.jun.pan@linux.intel.com> References: <20240405223110.1609888-1-jacob.jun.pan@linux.intel.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: 8bit With posted MSI feature enabled on the CPU side, iommu interrupt remapping table entries (IRTEs) for device MSI/x can be allocated, activated, and programed in posted mode. This means that IRTEs are linked with their respective PIDs of the target CPU. Handlers for the posted MSI notification vector will de-multiplex device MSI handlers. CPU notifications are coalesced if interrupts arrive at a high frequency. Excluding the following: - legacy devices IOAPIC, HPET (may be needed for booting, not a source of high MSIs) - VT-d's own IRQs (not remappable). Suggested-by: Thomas Gleixner Signed-off-by: Jacob Pan --- v2: Fold in helper function for retrieving PID address v1: Added a warning if the effective affinity mask is not set up --- drivers/iommu/intel/irq_remapping.c | 69 +++++++++++++++++++++++++++-- 1 file changed, 65 insertions(+), 4 deletions(-) diff --git a/drivers/iommu/intel/irq_remapping.c b/drivers/iommu/intel/irq_remapping.c index fa719936b44e..ac5f9e83943b 100644 --- a/drivers/iommu/intel/irq_remapping.c +++ b/drivers/iommu/intel/irq_remapping.c @@ -19,6 +19,7 @@ #include #include #include +#include #include "iommu.h" #include "../irq_remapping.h" @@ -49,6 +50,7 @@ struct irq_2_iommu { u16 sub_handle; u8 irte_mask; enum irq_mode mode; + bool posted_msi; }; struct intel_ir_data { @@ -1118,6 +1120,14 @@ static void prepare_irte(struct irte *irte, int vector, unsigned int dest) irte->redir_hint = 1; } +static void prepare_irte_posted(struct irte *irte) +{ + memset(irte, 0, sizeof(*irte)); + + irte->present = 1; + irte->p_pst = 1; +} + struct irq_remap_ops intel_irq_remap_ops = { .prepare = intel_prepare_irq_remapping, .enable = intel_enable_irq_remapping, @@ -1126,6 +1136,47 @@ struct irq_remap_ops intel_irq_remap_ops = { .enable_faulting = enable_drhd_fault_handling, }; +#ifdef CONFIG_X86_POSTED_MSI + +static phys_addr_t get_pi_desc_addr(struct irq_data *irqd) +{ + int cpu = cpumask_first(irq_data_get_effective_affinity_mask(irqd)); + + if (WARN_ON(cpu >= nr_cpu_ids)) + return 0; + + return __pa(per_cpu_ptr(&posted_interrupt_desc, cpu)); +} + +static void intel_ir_reconfigure_irte_posted(struct irq_data *irqd) +{ + struct intel_ir_data *ir_data = irqd->chip_data; + struct irte *irte = &ir_data->irte_entry; + struct irte irte_pi; + u64 pid_addr; + + pid_addr = get_pi_desc_addr(irqd); + + if (!pid_addr) { + pr_warn("Failed to setup IRQ %d for posted mode", irqd->irq); + return; + } + + memset(&irte_pi, 0, sizeof(irte_pi)); + + /* The shared IRTE already be set up as posted during alloc_irte */ + dmar_copy_shared_irte(&irte_pi, irte); + + irte_pi.pda_l = (pid_addr >> (32 - PDA_LOW_BIT)) & ~(-1UL << PDA_LOW_BIT); + irte_pi.pda_h = (pid_addr >> 32) & ~(-1UL << PDA_HIGH_BIT); + + modify_irte(&ir_data->irq_2_iommu, &irte_pi); +} + +#else +static inline void intel_ir_reconfigure_irte_posted(struct irq_data *irqd) {} +#endif + static void intel_ir_reconfigure_irte(struct irq_data *irqd, bool force) { struct intel_ir_data *ir_data = irqd->chip_data; @@ -1139,8 +1190,9 @@ static void intel_ir_reconfigure_irte(struct irq_data *irqd, bool force) irte->vector = cfg->vector; irte->dest_id = IRTE_DEST(cfg->dest_apicid); - /* Update the hardware only if the interrupt is in remapped mode. */ - if (force || ir_data->irq_2_iommu.mode == IRQ_REMAPPING) + if (ir_data->irq_2_iommu.posted_msi) + intel_ir_reconfigure_irte_posted(irqd); + else if (force || ir_data->irq_2_iommu.mode == IRQ_REMAPPING) modify_irte(&ir_data->irq_2_iommu, irte); } @@ -1194,7 +1246,7 @@ static int intel_ir_set_vcpu_affinity(struct irq_data *data, void *info) struct intel_ir_data *ir_data = data->chip_data; struct vcpu_data *vcpu_pi_info = info; - /* stop posting interrupts, back to remapping mode */ + /* stop posting interrupts, back to the default mode */ if (!vcpu_pi_info) { modify_irte(&ir_data->irq_2_iommu, &ir_data->irte_entry); } else { @@ -1320,6 +1372,11 @@ static void intel_irq_remapping_prepare_irte(struct intel_ir_data *data, break; case X86_IRQ_ALLOC_TYPE_PCI_MSI: case X86_IRQ_ALLOC_TYPE_PCI_MSIX: + if (posted_msi_supported()) { + prepare_irte_posted(irte); + data->irq_2_iommu.posted_msi = 1; + } + set_msi_sid(irte, pci_real_dma_dev(msi_desc_to_pci_dev(info->desc))); break; @@ -1407,7 +1464,11 @@ static int intel_irq_remapping_alloc(struct irq_domain *domain, irq_data->hwirq = (index << 16) + i; irq_data->chip_data = ird; - irq_data->chip = &intel_ir_chip; + if (posted_msi_supported() && + ((info->type == X86_IRQ_ALLOC_TYPE_PCI_MSI) || (info->type == X86_IRQ_ALLOC_TYPE_PCI_MSIX))) + irq_data->chip = &intel_ir_chip_post_msi; + else + irq_data->chip = &intel_ir_chip; intel_irq_remapping_prepare_irte(ird, irq_cfg, info, index, i); irq_set_status_flags(virq + i, IRQ_MOVE_PCNTXT); } -- 2.25.1