All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v5 0/5] Kconfig for PCI passthrough on ARM
@ 2023-11-02 19:59 Stewart Hildebrand
  2023-11-02 19:59 ` [PATCH v5 1/5] xen/arm: pci: introduce PCI_PASSTHROUGH Kconfig option Stewart Hildebrand
                   ` (4 more replies)
  0 siblings, 5 replies; 12+ messages in thread
From: Stewart Hildebrand @ 2023-11-02 19:59 UTC (permalink / raw)
  To: xen-devel
  Cc: Stewart Hildebrand, Stefano Stabellini, Julien Grall,
	Bertrand Marquis, Volodymyr Babchuk, Wei Liu, Anthony PERARD,
	Juergen Gross, Andrew Cooper, George Dunlap, Jan Beulich,
	Christian Lindig, David Scott, Marek Marczykowski-Górecki,
	Roger Pau Monné,
	Paul Durrant

There are multiple series in development/review [1], [2] that will benefit from
having a Kconfig option for PCI passthrough on ARM. Hence I have sent this
series independent from any other series.

v4->v5:
* add [FUTURE] tag to ("xen/arm: enable vPCI for dom0")
* address feedback in individual patches

v3->v4:
* rename ("xen/arm: pci: plumb xen_arch_domainconfig with pci info")
  to ("xen/vpci: move xen_domctl_createdomain vPCI flag to common")
* fold ("xen/arm: make has_vpci() depend on d->arch.has_vpci")
  into ("xen/vpci: move xen_domctl_createdomain vPCI flag to common")
* split ("xen/arm: enable vPCI for domUs") into separate hypervisor and
  tools patches

v2->v3:
* add ("xen/arm: pci: plumb xen_arch_domainconfig with pci info")
* rename ("xen/arm: make has_vpci depend on CONFIG_HAS_VPCI")
      to ("xen/arm: make has_vpci() depend on d->arch.has_vpci")
* add ("xen/arm: enable vPCI for dom0")

v1->v2:
* add ("[FUTURE] xen/arm: enable vPCI for domUs")

[1] https://lists.xenproject.org/archives/html/xen-devel/2023-10/msg00660.html
[2] https://lists.xenproject.org/archives/html/xen-devel/2023-10/msg00210.html

Rahul Singh (1):
  xen/arm: pci: introduce PCI_PASSTHROUGH Kconfig option

Stewart Hildebrand (4):
  xen/vpci: move xen_domctl_createdomain vPCI flag to common
  [FUTURE] xen/arm: enable vPCI for dom0
  [FUTURE] xen/arm: enable vPCI for domUs
  [FUTURE] tools/arm: enable vPCI for domUs

 tools/libs/light/libxl_arm.c       |  3 +++
 tools/libs/light/libxl_x86.c       |  5 ++++-
 tools/ocaml/libs/xc/xenctrl.ml     |  2 +-
 tools/ocaml/libs/xc/xenctrl.mli    |  2 +-
 tools/python/xen/lowlevel/xc/xc.c  |  5 ++++-
 xen/arch/arm/Kconfig               | 10 ++++++++++
 xen/arch/arm/domain.c              |  3 ++-
 xen/arch/arm/domain_build.c        |  6 ++++++
 xen/arch/arm/include/asm/domain.h  |  5 ++---
 xen/arch/arm/include/asm/pci.h     |  9 +++++++++
 xen/arch/arm/pci/pci-host-common.c | 11 ++++++++---
 xen/arch/arm/vpci.c                |  8 ++++++++
 xen/arch/x86/domain.c              | 13 ++++++++-----
 xen/arch/x86/include/asm/domain.h  | 15 ++++++++++-----
 xen/arch/x86/setup.c               |  4 ++--
 xen/common/domain.c                | 16 +++++++++++++++-
 xen/drivers/passthrough/pci.c      | 20 ++++++++++++++++++++
 xen/include/public/arch-x86/xen.h  |  5 +----
 xen/include/public/domctl.h        |  7 +++++--
 xen/include/xen/domain.h           | 12 ++++++++++++
 20 files changed, 131 insertions(+), 30 deletions(-)


base-commit: 649c190a1feafdb54440bebbcac58abc90fa335b
-- 
2.42.0



^ permalink raw reply	[flat|nested] 12+ messages in thread

* [PATCH v5 1/5] xen/arm: pci: introduce PCI_PASSTHROUGH Kconfig option
  2023-11-02 19:59 [PATCH v5 0/5] Kconfig for PCI passthrough on ARM Stewart Hildebrand
@ 2023-11-02 19:59 ` Stewart Hildebrand
  2023-11-02 19:59 ` [PATCH v5 2/5] xen/vpci: move xen_domctl_createdomain vPCI flag to common Stewart Hildebrand
                   ` (3 subsequent siblings)
  4 siblings, 0 replies; 12+ messages in thread
From: Stewart Hildebrand @ 2023-11-02 19:59 UTC (permalink / raw)
  To: xen-devel
  Cc: Rahul Singh, Stefano Stabellini, Julien Grall, Bertrand Marquis,
	Volodymyr Babchuk, Stefano Stabellini, Stewart Hildebrand,
	Julien Grall

From: Rahul Singh <rahul.singh@arm.com>

Setting CONFIG_PCI_PASSTHROUGH=y will enable PCI passthrough on ARM, even though
the feature is not yet complete in the current upstream codebase. The purpose of
this is to make it easier to enable the necessary configs (HAS_PCI, HAS_VPCI) for
testing and development of PCI passthrough on ARM.

Since PCI passthrough on ARM is still work in progress at this time, make it
depend on EXPERT.

Signed-off-by: Rahul Singh <rahul.singh@arm.com>
Signed-off-by: Stefano Stabellini <stefano.stabellini@amd.com>
Signed-off-by: Stewart Hildebrand <stewart.hildebrand@amd.com>
Acked-by: Julien Grall <jgrall@amazon.com>
---
(cherry picked from commit 9a08f1f7ce28ec619640ba9ce11018bf443e9a0e from the
 downstream branch [1])

v4->v5:
* no change

v3->v4:
* no change

v2->v3:
* add Julien's A-b

v1->v2:
* drop "ARM" naming since it is already in an ARM category
* depend on EXPERT instead of UNSUPPORTED

Changes from downstream to v1:
* depends on ARM_64 (Stefano)
* Don't select HAS_VPCI_GUEST_SUPPORT since this config option is not currently
  used in the upstream codebase. This will want to be re-added here once the
  vpci series [2] is merged.
* Don't select ARM_SMMU_V3 since this option can already be selected
  independently. While PCI passthrough on ARM depends on an SMMU, it does not
  depend on a particular version or variant of an SMMU.
* Don't select HAS_ITS since this option can already be selected independently.
  HAS_ITS may want to be added here once the MSI series [1] is merged.
* Don't select LATE_HWDOM since this option is unrelated to PCI passthrough.

[1] https://gitlab.com/xen-project/people/bmarquis/xen-arm-poc/-/commits/poc/pci-passthrough
[2] https://lists.xenproject.org/archives/html/xen-devel/2023-10/msg00660.html
---
 xen/arch/arm/Kconfig | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/xen/arch/arm/Kconfig b/xen/arch/arm/Kconfig
index 2939db429b78..5ff68e5d5979 100644
--- a/xen/arch/arm/Kconfig
+++ b/xen/arch/arm/Kconfig
@@ -190,6 +190,15 @@ config STATIC_SHM
 	help
 	  This option enables statically shared memory on a dom0less system.
 
+config PCI_PASSTHROUGH
+	bool "PCI passthrough" if EXPERT
+	depends on ARM_64
+	select HAS_PCI
+	select HAS_VPCI
+	default n
+	help
+	  This option enables PCI device passthrough
+
 endmenu
 
 menu "ARM errata workaround via the alternative framework"
-- 
2.42.0



^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH v5 2/5] xen/vpci: move xen_domctl_createdomain vPCI flag to common
  2023-11-02 19:59 [PATCH v5 0/5] Kconfig for PCI passthrough on ARM Stewart Hildebrand
  2023-11-02 19:59 ` [PATCH v5 1/5] xen/arm: pci: introduce PCI_PASSTHROUGH Kconfig option Stewart Hildebrand
@ 2023-11-02 19:59 ` Stewart Hildebrand
  2023-11-13 13:26   ` Jan Beulich
  2023-11-02 19:59 ` [PATCH v5 3/5] [FUTURE] xen/arm: enable vPCI for dom0 Stewart Hildebrand
                   ` (2 subsequent siblings)
  4 siblings, 1 reply; 12+ messages in thread
From: Stewart Hildebrand @ 2023-11-02 19:59 UTC (permalink / raw)
  To: xen-devel
  Cc: Stewart Hildebrand, Wei Liu, Anthony PERARD, Juergen Gross,
	Andrew Cooper, George Dunlap, Jan Beulich, Julien Grall,
	Stefano Stabellini, Christian Lindig, David Scott,
	Marek Marczykowski-Górecki, Bertrand Marquis,
	Volodymyr Babchuk, Roger Pau Monné,
	Oleksandr Andrushchenko, Rahul Singh, Christian Lindig

Both x86 and ARM need a way at domain creation time to specify whether
the domain needs vPCI emulation. Move the vPCI flag from x86
xen_domctl_createdomain.arch.emulation_flags to the common
xen_domctl_createdomain.flags.

Move has_vpci() macro to common header.

Bump XEN_DOMCTL_INTERFACE_VERSION since we're modifying flags inside
struct xen_domctl_createdomain and xen_arch_domainconfig.

Signed-off-by: Oleksandr Andrushchenko <oleksandr_andrushchenko@epam.com>
Signed-off-by: Rahul Singh <rahul.singh@arm.com>
Signed-off-by: Stewart Hildebrand <stewart.hildebrand@amd.com>
Acked-by: Christian Lindig <christian.lindig@cloud.com>
---
v4->v5:
* move flags_optional change in xen/arch/arm/domain.c to next patch
* change latter 2 args to emulation_flags_ok() to unsigned int
* move vpci && !hvm check to common code
* remove stray spaces in emulation_flags_ok(), and a minor style fixup
* add CONFIG_HAS_VPCI check into has_vpci()
* add Christian's A-b (OCaml)

v3->v4:
* renamed, was:
  ("xen/arm: pci: plumb xen_arch_domainconfig with pci info")
* reworked: move x86 vPCI flag to common instead of adding another arch
  specific vPCI flag
* folded ("xen/arm: make has_vpci() depend on d->arch.has_vpci") into
  this patch (retain Signed-off-by's from [1] and [2])

v2->v3:
* new patch

[1] https://gitlab.com/xen-project/people/bmarquis/xen-arm-poc/-/commit/27be1729ce8128dbe37275ce7946b2fbd2e5a382
[2] https://github.com/xen-troops/xen/commit/bf12185e6fb2e31db0d8e6ea9ccd8a02abadec17
---
 tools/libs/light/libxl_x86.c      |  5 ++++-
 tools/ocaml/libs/xc/xenctrl.ml    |  2 +-
 tools/ocaml/libs/xc/xenctrl.mli   |  2 +-
 tools/python/xen/lowlevel/xc/xc.c |  5 ++++-
 xen/arch/arm/include/asm/domain.h |  3 ---
 xen/arch/x86/domain.c             | 13 ++++++++-----
 xen/arch/x86/include/asm/domain.h |  6 +-----
 xen/arch/x86/setup.c              |  4 ++--
 xen/common/domain.c               | 16 +++++++++++++++-
 xen/include/public/arch-x86/xen.h |  5 +----
 xen/include/public/domctl.h       |  7 +++++--
 xen/include/xen/domain.h          |  3 +++
 12 files changed, 45 insertions(+), 26 deletions(-)

diff --git a/tools/libs/light/libxl_x86.c b/tools/libs/light/libxl_x86.c
index d16573e72cd4..ebce1552accd 100644
--- a/tools/libs/light/libxl_x86.c
+++ b/tools/libs/light/libxl_x86.c
@@ -8,13 +8,16 @@ int libxl__arch_domain_prepare_config(libxl__gc *gc,
 {
     switch(d_config->c_info.type) {
     case LIBXL_DOMAIN_TYPE_HVM:
-        config->arch.emulation_flags = (XEN_X86_EMU_ALL & ~XEN_X86_EMU_VPCI);
+        config->arch.emulation_flags = XEN_X86_EMU_ALL;
+        config->flags &= ~XEN_DOMCTL_CDF_vpci;
         break;
     case LIBXL_DOMAIN_TYPE_PVH:
         config->arch.emulation_flags = XEN_X86_EMU_LAPIC;
+        config->flags &= ~XEN_DOMCTL_CDF_vpci;
         break;
     case LIBXL_DOMAIN_TYPE_PV:
         config->arch.emulation_flags = 0;
+        config->flags &= ~XEN_DOMCTL_CDF_vpci;
         break;
     default:
         abort();
diff --git a/tools/ocaml/libs/xc/xenctrl.ml b/tools/ocaml/libs/xc/xenctrl.ml
index d6c6eb73db44..6f3da9c6e064 100644
--- a/tools/ocaml/libs/xc/xenctrl.ml
+++ b/tools/ocaml/libs/xc/xenctrl.ml
@@ -46,7 +46,6 @@ type x86_arch_emulation_flags =
   | X86_EMU_IOMMU
   | X86_EMU_PIT
   | X86_EMU_USE_PIRQ
-  | X86_EMU_VPCI
 
 type x86_arch_misc_flags =
   | X86_MSR_RELAXED
@@ -70,6 +69,7 @@ type domain_create_flag =
   | CDF_IOMMU
   | CDF_NESTED_VIRT
   | CDF_VPMU
+  | CDF_VPCI
 
 type domain_create_iommu_opts =
   | IOMMU_NO_SHAREPT
diff --git a/tools/ocaml/libs/xc/xenctrl.mli b/tools/ocaml/libs/xc/xenctrl.mli
index 3bfc16edba96..e2dd02bec962 100644
--- a/tools/ocaml/libs/xc/xenctrl.mli
+++ b/tools/ocaml/libs/xc/xenctrl.mli
@@ -40,7 +40,6 @@ type x86_arch_emulation_flags =
   | X86_EMU_IOMMU
   | X86_EMU_PIT
   | X86_EMU_USE_PIRQ
-  | X86_EMU_VPCI
 
 type x86_arch_misc_flags =
   | X86_MSR_RELAXED
@@ -63,6 +62,7 @@ type domain_create_flag =
   | CDF_IOMMU
   | CDF_NESTED_VIRT
   | CDF_VPMU
+  | CDF_VPCI
 
 type domain_create_iommu_opts =
   | IOMMU_NO_SHAREPT
diff --git a/tools/python/xen/lowlevel/xc/xc.c b/tools/python/xen/lowlevel/xc/xc.c
index d3ea350e07b9..e3623cdcb90d 100644
--- a/tools/python/xen/lowlevel/xc/xc.c
+++ b/tools/python/xen/lowlevel/xc/xc.c
@@ -159,7 +159,10 @@ static PyObject *pyxc_domain_create(XcObject *self,
 
 #if defined (__i386) || defined(__x86_64__)
     if ( config.flags & XEN_DOMCTL_CDF_hvm )
-        config.arch.emulation_flags = (XEN_X86_EMU_ALL & ~XEN_X86_EMU_VPCI);
+    {
+        config.arch.emulation_flags = XEN_X86_EMU_ALL;
+        config.flags &= ~XEN_DOMCTL_CDF_vpci;
+    }
 #elif defined (__arm__) || defined(__aarch64__)
     config.arch.gic_version = XEN_DOMCTL_CONFIG_GIC_NATIVE;
 #else
diff --git a/xen/arch/arm/include/asm/domain.h b/xen/arch/arm/include/asm/domain.h
index 99e798ffff68..be9ed39c9d42 100644
--- a/xen/arch/arm/include/asm/domain.h
+++ b/xen/arch/arm/include/asm/domain.h
@@ -298,9 +298,6 @@ static inline void arch_vcpu_block(struct vcpu *v) {}
 
 #define arch_vm_assist_valid_mask(d) (1UL << VMASST_TYPE_runstate_update_flag)
 
-/* vPCI is not available on Arm */
-#define has_vpci(d)    ({ (void)(d); false; })
-
 struct arch_vcpu_io {
     struct instr_details dabt_instr; /* when the instruction is decoded */
 };
diff --git a/xen/arch/x86/domain.c b/xen/arch/x86/domain.c
index 3712e36df930..98f0397686cf 100644
--- a/xen/arch/x86/domain.c
+++ b/xen/arch/x86/domain.c
@@ -712,7 +712,8 @@ int arch_sanitise_domain_config(struct xen_domctl_createdomain *config)
     return 0;
 }
 
-static bool emulation_flags_ok(const struct domain *d, uint32_t emflags)
+static bool emulation_flags_ok(const struct domain *d, unsigned int emflags,
+                               unsigned int cdf)
 {
 #ifdef CONFIG_HVM
     /* This doesn't catch !CONFIG_HVM case but it is better than nothing */
@@ -722,11 +723,13 @@ static bool emulation_flags_ok(const struct domain *d, uint32_t emflags)
     if ( is_hvm_domain(d) )
     {
         if ( is_hardware_domain(d) &&
-             emflags != (X86_EMU_VPCI | X86_EMU_LAPIC | X86_EMU_IOAPIC) )
+             (!(cdf & XEN_DOMCTL_CDF_vpci) ||
+              emflags != (X86_EMU_LAPIC | X86_EMU_IOAPIC)) )
             return false;
         if ( !is_hardware_domain(d) &&
-             emflags != (X86_EMU_ALL & ~X86_EMU_VPCI) &&
-             emflags != X86_EMU_LAPIC )
+             ((cdf & XEN_DOMCTL_CDF_vpci) ||
+              (emflags != X86_EMU_ALL &&
+               emflags != X86_EMU_LAPIC)) )
             return false;
     }
     else if ( emflags != 0 && emflags != X86_EMU_PIT )
@@ -798,7 +801,7 @@ int arch_domain_create(struct domain *d,
         return -EINVAL;
     }
 
-    if ( !emulation_flags_ok(d, emflags) )
+    if ( !emulation_flags_ok(d, emflags, config->flags) )
     {
         printk(XENLOG_G_ERR "d%d: Xen does not allow %s domain creation "
                "with the current selection of emulators: %#x\n",
diff --git a/xen/arch/x86/include/asm/domain.h b/xen/arch/x86/include/asm/domain.h
index 619e667938ed..cb02a4d1ebb2 100644
--- a/xen/arch/x86/include/asm/domain.h
+++ b/xen/arch/x86/include/asm/domain.h
@@ -471,7 +471,6 @@ struct arch_domain
 #define X86_EMU_VGA      XEN_X86_EMU_VGA
 #define X86_EMU_IOMMU    XEN_X86_EMU_IOMMU
 #define X86_EMU_USE_PIRQ XEN_X86_EMU_USE_PIRQ
-#define X86_EMU_VPCI     XEN_X86_EMU_VPCI
 #else
 #define X86_EMU_LAPIC    0
 #define X86_EMU_HPET     0
@@ -482,7 +481,6 @@ struct arch_domain
 #define X86_EMU_VGA      0
 #define X86_EMU_IOMMU    0
 #define X86_EMU_USE_PIRQ 0
-#define X86_EMU_VPCI     0
 #endif
 
 #define X86_EMU_PIT     XEN_X86_EMU_PIT
@@ -492,8 +490,7 @@ struct arch_domain
                                  X86_EMU_PM | X86_EMU_RTC |             \
                                  X86_EMU_IOAPIC | X86_EMU_PIC |         \
                                  X86_EMU_VGA | X86_EMU_IOMMU |          \
-                                 X86_EMU_PIT | X86_EMU_USE_PIRQ |       \
-                                 X86_EMU_VPCI)
+                                 X86_EMU_PIT | X86_EMU_USE_PIRQ)
 
 #define has_vlapic(d)      (!!((d)->arch.emulation_flags & X86_EMU_LAPIC))
 #define has_vhpet(d)       (!!((d)->arch.emulation_flags & X86_EMU_HPET))
@@ -505,7 +502,6 @@ struct arch_domain
 #define has_viommu(d)      (!!((d)->arch.emulation_flags & X86_EMU_IOMMU))
 #define has_vpit(d)        (!!((d)->arch.emulation_flags & X86_EMU_PIT))
 #define has_pirq(d)        (!!((d)->arch.emulation_flags & X86_EMU_USE_PIRQ))
-#define has_vpci(d)        (!!((d)->arch.emulation_flags & X86_EMU_VPCI))
 
 #define gdt_ldt_pt_idx(v) \
       ((v)->vcpu_id >> (PAGETABLE_ORDER - GDT_LDT_VCPU_SHIFT))
diff --git a/xen/arch/x86/setup.c b/xen/arch/x86/setup.c
index a3d3f797bb1e..00dfcf231e21 100644
--- a/xen/arch/x86/setup.c
+++ b/xen/arch/x86/setup.c
@@ -890,12 +890,12 @@ static struct domain *__init create_dom0(const module_t *image,
 
     if ( opt_dom0_pvh )
     {
-        dom0_cfg.flags |= (XEN_DOMCTL_CDF_hvm |
+        dom0_cfg.flags |= (XEN_DOMCTL_CDF_hvm | XEN_DOMCTL_CDF_vpci |
                            ((hvm_hap_supported() && !opt_dom0_shadow) ?
                             XEN_DOMCTL_CDF_hap : 0));
 
         dom0_cfg.arch.emulation_flags |=
-            XEN_X86_EMU_LAPIC | XEN_X86_EMU_IOAPIC | XEN_X86_EMU_VPCI;
+            XEN_X86_EMU_LAPIC | XEN_X86_EMU_IOAPIC;
     }
 
     if ( iommu_enabled )
diff --git a/xen/common/domain.c b/xen/common/domain.c
index 8f9ab01c0cb7..6a42eb6d8c18 100644
--- a/xen/common/domain.c
+++ b/xen/common/domain.c
@@ -509,12 +509,14 @@ static int sanitise_domain_config(struct xen_domctl_createdomain *config)
     bool hap = config->flags & XEN_DOMCTL_CDF_hap;
     bool iommu = config->flags & XEN_DOMCTL_CDF_iommu;
     bool vpmu = config->flags & XEN_DOMCTL_CDF_vpmu;
+    bool vpci = config->flags & XEN_DOMCTL_CDF_vpci;
 
     if ( config->flags &
          ~(XEN_DOMCTL_CDF_hvm | XEN_DOMCTL_CDF_hap |
            XEN_DOMCTL_CDF_s3_integrity | XEN_DOMCTL_CDF_oos_off |
            XEN_DOMCTL_CDF_xs_domain | XEN_DOMCTL_CDF_iommu |
-           XEN_DOMCTL_CDF_nested_virt | XEN_DOMCTL_CDF_vpmu) )
+           XEN_DOMCTL_CDF_nested_virt | XEN_DOMCTL_CDF_vpmu |
+           XEN_DOMCTL_CDF_vpci) )
     {
         dprintk(XENLOG_INFO, "Unknown CDF flags %#x\n", config->flags);
         return -EINVAL;
@@ -575,6 +577,18 @@ static int sanitise_domain_config(struct xen_domctl_createdomain *config)
         return -EINVAL;
     }
 
+    if ( vpci && !hvm )
+    {
+        dprintk(XENLOG_INFO, "vPCI requested for non-HVM guest\n");
+        return -EINVAL;
+    }
+
+    if ( vpci && !IS_ENABLED(CONFIG_HAS_VPCI) )
+    {
+        dprintk(XENLOG_INFO, "vPCI requested but not enabled\n");
+        return -EINVAL;
+    }
+
     return arch_sanitise_domain_config(config);
 }
 
diff --git a/xen/include/public/arch-x86/xen.h b/xen/include/public/arch-x86/xen.h
index c0f4551247f4..4cf066761c6b 100644
--- a/xen/include/public/arch-x86/xen.h
+++ b/xen/include/public/arch-x86/xen.h
@@ -283,15 +283,12 @@ struct xen_arch_domainconfig {
 #define XEN_X86_EMU_PIT             (1U<<_XEN_X86_EMU_PIT)
 #define _XEN_X86_EMU_USE_PIRQ       9
 #define XEN_X86_EMU_USE_PIRQ        (1U<<_XEN_X86_EMU_USE_PIRQ)
-#define _XEN_X86_EMU_VPCI           10
-#define XEN_X86_EMU_VPCI            (1U<<_XEN_X86_EMU_VPCI)
 
 #define XEN_X86_EMU_ALL             (XEN_X86_EMU_LAPIC | XEN_X86_EMU_HPET |  \
                                      XEN_X86_EMU_PM | XEN_X86_EMU_RTC |      \
                                      XEN_X86_EMU_IOAPIC | XEN_X86_EMU_PIC |  \
                                      XEN_X86_EMU_VGA | XEN_X86_EMU_IOMMU |   \
-                                     XEN_X86_EMU_PIT | XEN_X86_EMU_USE_PIRQ |\
-                                     XEN_X86_EMU_VPCI)
+                                     XEN_X86_EMU_PIT | XEN_X86_EMU_USE_PIRQ)
     uint32_t emulation_flags;
 
 /*
diff --git a/xen/include/public/domctl.h b/xen/include/public/domctl.h
index a33f9ec32b08..5f3b5579c377 100644
--- a/xen/include/public/domctl.h
+++ b/xen/include/public/domctl.h
@@ -21,7 +21,7 @@
 #include "hvm/save.h"
 #include "memory.h"
 
-#define XEN_DOMCTL_INTERFACE_VERSION 0x00000016
+#define XEN_DOMCTL_INTERFACE_VERSION 0x00000017
 
 /*
  * NB. xen_domctl.domain is an IN/OUT parameter for this operation.
@@ -55,9 +55,12 @@ struct xen_domctl_createdomain {
 #define XEN_DOMCTL_CDF_nested_virt    (1U << _XEN_DOMCTL_CDF_nested_virt)
 /* Should we expose the vPMU to the guest? */
 #define XEN_DOMCTL_CDF_vpmu           (1U << 7)
+/* Should vPCI be enabled for the guest? */
+#define _XEN_DOMCTL_CDF_vpci          8
+#define XEN_DOMCTL_CDF_vpci           (1U<<_XEN_DOMCTL_CDF_vpci)
 
 /* Max XEN_DOMCTL_CDF_* constant.  Used for ABI checking. */
-#define XEN_DOMCTL_CDF_MAX XEN_DOMCTL_CDF_vpmu
+#define XEN_DOMCTL_CDF_MAX XEN_DOMCTL_CDF_vpci
 
     uint32_t flags;
 
diff --git a/xen/include/xen/domain.h b/xen/include/xen/domain.h
index 54d88bf5e34b..ab8f06c5f6a2 100644
--- a/xen/include/xen/domain.h
+++ b/xen/include/xen/domain.h
@@ -51,6 +51,9 @@ void arch_get_domain_info(const struct domain *d,
 
 #define is_domain_using_staticmem(d) ((d)->cdf & CDF_staticmem)
 
+#define has_vpci(d) (((d)->options & XEN_DOMCTL_CDF_vpci) && \
+                     IS_ENABLED(CONFIG_HAS_VPCI))
+
 /*
  * Arch-specifics.
  */
-- 
2.42.0



^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH v5 3/5] [FUTURE] xen/arm: enable vPCI for dom0
  2023-11-02 19:59 [PATCH v5 0/5] Kconfig for PCI passthrough on ARM Stewart Hildebrand
  2023-11-02 19:59 ` [PATCH v5 1/5] xen/arm: pci: introduce PCI_PASSTHROUGH Kconfig option Stewart Hildebrand
  2023-11-02 19:59 ` [PATCH v5 2/5] xen/vpci: move xen_domctl_createdomain vPCI flag to common Stewart Hildebrand
@ 2023-11-02 19:59 ` Stewart Hildebrand
  2023-11-02 19:59 ` [PATCH v5 4/5] [FUTURE] xen/arm: enable vPCI for domUs Stewart Hildebrand
  2023-11-02 19:59 ` [PATCH v5 5/5] [FUTURE] tools/arm: " Stewart Hildebrand
  4 siblings, 0 replies; 12+ messages in thread
From: Stewart Hildebrand @ 2023-11-02 19:59 UTC (permalink / raw)
  To: xen-devel
  Cc: Stewart Hildebrand, Stefano Stabellini, Julien Grall,
	Bertrand Marquis, Volodymyr Babchuk

Set the vPCI flag in xen_domctl_createdomain to enable vPCI for dom0 if
iommu and PCI passthrough are enabled and there exists a PCI host bridge
in the system.

Adjust pci_host_iterate_bridges_and_count() to count the number of host
bridges if no callback is provided.

Signed-off-by: Stewart Hildebrand <stewart.hildebrand@amd.com>
---
Allowing/enabling vPCI for dom0 on ARM should follow or be part of the
PCI passthrough SMMU series [1]. I'm including it here due to
prerequisites in this Kconfig series. Once the prerequisites are
committed I'll move this patch to the PCI passthrough SMMU series.

v4->v5:
* add [FUTURE] tag
* move flags_optional change from the previous patch to here

v3->v4:
* depend on iommu_enabled, pci_passthrough_enabled, and whether there
  is a pci host bridge

v2->v3:
* new patch

[1] https://lists.xenproject.org/archives/html/xen-devel/2023-10/msg00210.html
---
 xen/arch/arm/domain.c              |  3 ++-
 xen/arch/arm/domain_build.c        |  6 ++++++
 xen/arch/arm/include/asm/pci.h     |  9 +++++++++
 xen/arch/arm/pci/pci-host-common.c | 11 ++++++++---
 4 files changed, 25 insertions(+), 4 deletions(-)

diff --git a/xen/arch/arm/domain.c b/xen/arch/arm/domain.c
index 28e3aaa5e482..1409a4235e13 100644
--- a/xen/arch/arm/domain.c
+++ b/xen/arch/arm/domain.c
@@ -607,7 +607,8 @@ int arch_sanitise_domain_config(struct xen_domctl_createdomain *config)
 {
     unsigned int max_vcpus;
     unsigned int flags_required = (XEN_DOMCTL_CDF_hvm | XEN_DOMCTL_CDF_hap);
-    unsigned int flags_optional = (XEN_DOMCTL_CDF_iommu | XEN_DOMCTL_CDF_vpmu);
+    unsigned int flags_optional = (XEN_DOMCTL_CDF_iommu | XEN_DOMCTL_CDF_vpmu |
+                                   XEN_DOMCTL_CDF_vpci);
     unsigned int sve_vl_bits = sve_decode_vl(config->arch.sve_vl);
 
     if ( (config->flags & ~flags_optional) != flags_required )
diff --git a/xen/arch/arm/domain_build.c b/xen/arch/arm/domain_build.c
index 49792dd590ee..4750f5c6ad31 100644
--- a/xen/arch/arm/domain_build.c
+++ b/xen/arch/arm/domain_build.c
@@ -3915,6 +3915,12 @@ void __init create_dom0(void)
             panic("SVE vector length error\n");
     }
 
+    if ( IS_ENABLED(CONFIG_HAS_VPCI) &&
+         iommu_enabled &&
+         is_pci_passthrough_enabled() &&
+         (pci_host_iterate_bridges_and_count(NULL, NULL) > 0) )
+        dom0_cfg.flags |= XEN_DOMCTL_CDF_vpci;
+
     dom0 = domain_create(0, &dom0_cfg, CDF_privileged | CDF_directmap);
     if ( IS_ERR(dom0) )
         panic("Error creating domain 0 (rc = %ld)\n", PTR_ERR(dom0));
diff --git a/xen/arch/arm/include/asm/pci.h b/xen/arch/arm/include/asm/pci.h
index 8cb46f6b7185..4ae4d8cff8bf 100644
--- a/xen/arch/arm/include/asm/pci.h
+++ b/xen/arch/arm/include/asm/pci.h
@@ -154,5 +154,14 @@ static inline int pci_get_new_domain_nr(void)
     return -1;
 }
 
+struct pci_host_bridge;
+
+static inline int pci_host_iterate_bridges_and_count(
+    struct domain *d,
+    int (*cb)(struct domain *d, struct pci_host_bridge *bridge))
+{
+    return 0;
+}
+
 #endif  /*!CONFIG_HAS_PCI*/
 #endif /* __ARM_PCI_H__ */
diff --git a/xen/arch/arm/pci/pci-host-common.c b/xen/arch/arm/pci/pci-host-common.c
index c0faf0f43675..e6a03ae668f8 100644
--- a/xen/arch/arm/pci/pci-host-common.c
+++ b/xen/arch/arm/pci/pci-host-common.c
@@ -319,9 +319,14 @@ int pci_host_iterate_bridges_and_count(struct domain *d,
     {
         int ret;
 
-        ret = cb(d, bridge);
-        if ( ret < 0 )
-            return ret;
+        if ( cb )
+        {
+            ret = cb(d, bridge);
+            if ( ret < 0 )
+                return ret;
+        }
+        else
+            ret = 1;
         count += ret;
     }
     return count;
-- 
2.42.0



^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH v5 4/5] [FUTURE] xen/arm: enable vPCI for domUs
  2023-11-02 19:59 [PATCH v5 0/5] Kconfig for PCI passthrough on ARM Stewart Hildebrand
                   ` (2 preceding siblings ...)
  2023-11-02 19:59 ` [PATCH v5 3/5] [FUTURE] xen/arm: enable vPCI for dom0 Stewart Hildebrand
@ 2023-11-02 19:59 ` Stewart Hildebrand
  2023-11-06  9:26   ` Jan Beulich
  2023-11-02 19:59 ` [PATCH v5 5/5] [FUTURE] tools/arm: " Stewart Hildebrand
  4 siblings, 1 reply; 12+ messages in thread
From: Stewart Hildebrand @ 2023-11-02 19:59 UTC (permalink / raw)
  To: xen-devel
  Cc: Stewart Hildebrand, Stefano Stabellini, Julien Grall,
	Bertrand Marquis, Volodymyr Babchuk, Andrew Cooper,
	George Dunlap, Jan Beulich, Wei Liu, Roger Pau Monné,
	Paul Durrant

Select HAS_VPCI_GUEST_SUPPORT in Kconfig for enabling vPCI support for
domUs.

Add checks to fail guest creation if the configuration is invalid.

Signed-off-by: Stewart Hildebrand <stewart.hildebrand@amd.com>
---
As the tag implies, this patch is not intended to be merged (yet).

Note that CONFIG_HAS_VPCI_GUEST_SUPPORT is not currently used in the
upstream code base. It will be used by the vPCI series [1]. This patch
is intended to be merged as part of the vPCI series. I'll coordinate
with Volodymyr to include this in the vPCI series or resend afterwards.
Meanwhile, I'll include it here until the Kconfig and
xen_domctl_createdomain prerequisites have been committed.

v4->v5:
* replace is_system_domain() check with dom_io check
* return an error in XEN_DOMCTL_assign_device (thanks Jan!)
* remove CONFIG_ARM check
* add needs_vpci() and arch_needs_vpci()
* add HAS_VPCI_GUEST_SUPPORT check to has_vpci()

v3->v4:
* refuse to create domain if configuration is invalid
* split toolstack change into separate patch

v2->v3:
* set pci flags in toolstack

v1->v2:
* new patch

[1] https://lists.xenproject.org/archives/html/xen-devel/2023-10/msg00660.html
---
 xen/arch/arm/Kconfig              |  1 +
 xen/arch/arm/include/asm/domain.h |  2 ++
 xen/arch/arm/vpci.c               |  8 ++++++++
 xen/arch/x86/include/asm/domain.h |  9 +++++++++
 xen/drivers/passthrough/pci.c     | 20 ++++++++++++++++++++
 xen/include/xen/domain.h          | 13 +++++++++++--
 6 files changed, 51 insertions(+), 2 deletions(-)

diff --git a/xen/arch/arm/Kconfig b/xen/arch/arm/Kconfig
index 5ff68e5d5979..3845b238a33f 100644
--- a/xen/arch/arm/Kconfig
+++ b/xen/arch/arm/Kconfig
@@ -195,6 +195,7 @@ config PCI_PASSTHROUGH
 	depends on ARM_64
 	select HAS_PCI
 	select HAS_VPCI
+	select HAS_VPCI_GUEST_SUPPORT
 	default n
 	help
 	  This option enables PCI device passthrough
diff --git a/xen/arch/arm/include/asm/domain.h b/xen/arch/arm/include/asm/domain.h
index be9ed39c9d42..e4b4a12233f0 100644
--- a/xen/arch/arm/include/asm/domain.h
+++ b/xen/arch/arm/include/asm/domain.h
@@ -31,6 +31,8 @@ enum domain_type {
 
 #define is_domain_direct_mapped(d) ((d)->cdf & CDF_directmap)
 
+#define arch_needs_vpci(d) ({ (void)(d); true; })
+
 /*
  * Is the domain using the host memory layout?
  *
diff --git a/xen/arch/arm/vpci.c b/xen/arch/arm/vpci.c
index 3bc4bb55082a..61e0edcedea9 100644
--- a/xen/arch/arm/vpci.c
+++ b/xen/arch/arm/vpci.c
@@ -2,6 +2,7 @@
 /*
  * xen/arch/arm/vpci.c
  */
+#include <xen/lib.h>
 #include <xen/sched.h>
 #include <xen/vpci.h>
 
@@ -90,8 +91,15 @@ int domain_vpci_init(struct domain *d)
             return ret;
     }
     else
+    {
+        if ( !IS_ENABLED(CONFIG_HAS_VPCI_GUEST_SUPPORT) )
+        {
+            gdprintk(XENLOG_ERR, "vPCI requested but guest support not enabled\n");
+            return -EINVAL;
+        }
         register_mmio_handler(d, &vpci_mmio_handler,
                               GUEST_VPCI_ECAM_BASE, GUEST_VPCI_ECAM_SIZE, NULL);
+    }
 
     return 0;
 }
diff --git a/xen/arch/x86/include/asm/domain.h b/xen/arch/x86/include/asm/domain.h
index cb02a4d1ebb2..57bbe842e18d 100644
--- a/xen/arch/x86/include/asm/domain.h
+++ b/xen/arch/x86/include/asm/domain.h
@@ -503,6 +503,15 @@ struct arch_domain
 #define has_vpit(d)        (!!((d)->arch.emulation_flags & X86_EMU_PIT))
 #define has_pirq(d)        (!!((d)->arch.emulation_flags & X86_EMU_USE_PIRQ))
 
+#define is_pvh_domain(d) ({                                  \
+    unsigned int _emflags = (d)->arch.emulation_flags;       \
+    IS_ENABLED(CONFIG_HVM) &&                                \
+        ((_emflags == X86_EMU_LAPIC) ||                      \
+         (_emflags == (X86_EMU_LAPIC | X86_EMU_IOAPIC))); })
+
+/* PCI passthrough may be backed by qemu for non-PVH domains */
+#define arch_needs_vpci(d) is_pvh_domain(d)
+
 #define gdt_ldt_pt_idx(v) \
       ((v)->vcpu_id >> (PAGETABLE_ORDER - GDT_LDT_VCPU_SHIFT))
 #define pv_gdt_ptes(v) \
diff --git a/xen/drivers/passthrough/pci.c b/xen/drivers/passthrough/pci.c
index 04d00c7c37df..2203725a2aa6 100644
--- a/xen/drivers/passthrough/pci.c
+++ b/xen/drivers/passthrough/pci.c
@@ -1542,6 +1542,18 @@ void iommu_dev_iotlb_flush_timeout(struct domain *d, struct pci_dev *pdev)
     pcidevs_unlock();
 }
 
+static bool needs_vpci(const struct domain *d)
+{
+    if ( is_hardware_domain(d) )
+        return false;
+
+    if ( d == dom_io )
+        /* xl pci-assignable-add assigns PCI devices to domIO */
+        return false;
+
+    return arch_needs_vpci(d);
+}
+
 int iommu_do_pci_domctl(
     struct xen_domctl *domctl, struct domain *d,
     XEN_GUEST_HANDLE_PARAM(xen_domctl_t) u_domctl)
@@ -1618,6 +1630,14 @@ int iommu_do_pci_domctl(
         bus = PCI_BUS(machine_sbdf);
         devfn = PCI_DEVFN(machine_sbdf);
 
+        if ( needs_vpci(d) && !has_vpci(d) )
+        {
+            printk(XENLOG_G_WARNING "Cannot assign %pp to %pd: vPCI support not enabled\n",
+                   &PCI_SBDF(seg, bus, devfn), d);
+            ret = -EPERM;
+            break;
+        }
+
         pcidevs_lock();
         ret = device_assigned(seg, bus, devfn);
         if ( domctl->cmd == XEN_DOMCTL_test_assign_device )
diff --git a/xen/include/xen/domain.h b/xen/include/xen/domain.h
index ab8f06c5f6a2..c3364d6e2e44 100644
--- a/xen/include/xen/domain.h
+++ b/xen/include/xen/domain.h
@@ -51,8 +51,17 @@ void arch_get_domain_info(const struct domain *d,
 
 #define is_domain_using_staticmem(d) ((d)->cdf & CDF_staticmem)
 
-#define has_vpci(d) (((d)->options & XEN_DOMCTL_CDF_vpci) && \
-                     IS_ENABLED(CONFIG_HAS_VPCI))
+#define has_vpci(d) ({                                                        \
+    const struct domain *_d = (d);                                            \
+    bool _has_vpci = false;                                                   \
+    if ( (_d->options & XEN_DOMCTL_CDF_vpci) && IS_ENABLED(CONFIG_HAS_VPCI) ) \
+    {                                                                         \
+        if ( is_hardware_domain(_d) )                                         \
+            _has_vpci = true;                                                 \
+        else if ( IS_ENABLED(CONFIG_HAS_VPCI_GUEST_SUPPORT) )                 \
+            _has_vpci = true;                                                 \
+    }                                                                         \
+    _has_vpci; })
 
 /*
  * Arch-specifics.
-- 
2.42.0



^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH v5 5/5] [FUTURE] tools/arm: enable vPCI for domUs
  2023-11-02 19:59 [PATCH v5 0/5] Kconfig for PCI passthrough on ARM Stewart Hildebrand
                   ` (3 preceding siblings ...)
  2023-11-02 19:59 ` [PATCH v5 4/5] [FUTURE] xen/arm: enable vPCI for domUs Stewart Hildebrand
@ 2023-11-02 19:59 ` Stewart Hildebrand
  4 siblings, 0 replies; 12+ messages in thread
From: Stewart Hildebrand @ 2023-11-02 19:59 UTC (permalink / raw)
  To: xen-devel; +Cc: Stewart Hildebrand, Wei Liu, Anthony PERARD, Juergen Gross

Set the vPCI flag in xen_domctl_createdomain to enable vPCI if a pci
device has been specified in the xl domain config file.

Signed-off-by: Stewart Hildebrand <stewart.hildebrand@amd.com>
---
Same story as the patch before this regarding the [FUTURE] tag.

v4->v5:
* no change

v3->v4:
* split from ("xen/arm: enable vPCI for domUs")
---
 tools/libs/light/libxl_arm.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/tools/libs/light/libxl_arm.c b/tools/libs/light/libxl_arm.c
index 15391917748c..6daed958e598 100644
--- a/tools/libs/light/libxl_arm.c
+++ b/tools/libs/light/libxl_arm.c
@@ -222,6 +222,9 @@ int libxl__arch_domain_prepare_config(libxl__gc *gc,
         config->arch.sve_vl = d_config->b_info.arch_arm.sve_vl / 128U;
     }
 
+    if (d_config->num_pcidevs)
+        config->flags |= XEN_DOMCTL_CDF_vpci;
+
     return 0;
 }
 
-- 
2.42.0



^ permalink raw reply related	[flat|nested] 12+ messages in thread

* Re: [PATCH v5 4/5] [FUTURE] xen/arm: enable vPCI for domUs
  2023-11-02 19:59 ` [PATCH v5 4/5] [FUTURE] xen/arm: enable vPCI for domUs Stewart Hildebrand
@ 2023-11-06  9:26   ` Jan Beulich
  2023-11-13 21:10     ` Stewart Hildebrand
  0 siblings, 1 reply; 12+ messages in thread
From: Jan Beulich @ 2023-11-06  9:26 UTC (permalink / raw)
  To: Stewart Hildebrand
  Cc: Stefano Stabellini, Julien Grall, Bertrand Marquis,
	Volodymyr Babchuk, Andrew Cooper, George Dunlap, Wei Liu,
	Roger Pau Monné,
	Paul Durrant, xen-devel

On 02.11.2023 20:59, Stewart Hildebrand wrote:
> --- a/xen/arch/x86/include/asm/domain.h
> +++ b/xen/arch/x86/include/asm/domain.h
> @@ -503,6 +503,15 @@ struct arch_domain
>  #define has_vpit(d)        (!!((d)->arch.emulation_flags & X86_EMU_PIT))
>  #define has_pirq(d)        (!!((d)->arch.emulation_flags & X86_EMU_USE_PIRQ))
>  
> +#define is_pvh_domain(d) ({                                  \
> +    unsigned int _emflags = (d)->arch.emulation_flags;       \
> +    IS_ENABLED(CONFIG_HVM) &&                                \
> +        ((_emflags == X86_EMU_LAPIC) ||                      \
> +         (_emflags == (X86_EMU_LAPIC | X86_EMU_IOAPIC))); })

I'm not convinced we want to re-introduce such a predicate; it'll be at
risk of going stale when the boundary between HVM and PVH becomes more
"fuzzy".

> +/* PCI passthrough may be backed by qemu for non-PVH domains */
> +#define arch_needs_vpci(d) is_pvh_domain(d)

Wouldn't we want to check for exactly what the comment alludes to then,
i.e. whether the domain has any (specific?) device model attached?

> --- a/xen/include/xen/domain.h
> +++ b/xen/include/xen/domain.h
> @@ -51,8 +51,17 @@ void arch_get_domain_info(const struct domain *d,
>  
>  #define is_domain_using_staticmem(d) ((d)->cdf & CDF_staticmem)
>  
> -#define has_vpci(d) (((d)->options & XEN_DOMCTL_CDF_vpci) && \
> -                     IS_ENABLED(CONFIG_HAS_VPCI))
> +#define has_vpci(d) ({                                                        \
> +    const struct domain *_d = (d);                                            \
> +    bool _has_vpci = false;                                                   \
> +    if ( (_d->options & XEN_DOMCTL_CDF_vpci) && IS_ENABLED(CONFIG_HAS_VPCI) ) \
> +    {                                                                         \
> +        if ( is_hardware_domain(_d) )                                         \
> +            _has_vpci = true;                                                 \
> +        else if ( IS_ENABLED(CONFIG_HAS_VPCI_GUEST_SUPPORT) )                 \
> +            _has_vpci = true;                                                 \
> +    }                                                                         \
> +    _has_vpci; })

This is a commonly executed check, and as such wants to remain as simple as
possible. Wouldn't it be better anyway to prevent XEN_DOMCTL_CDF_vpci getting
set for a domain which cannot possibly have vPCI?

Jan


^ permalink raw reply	[flat|nested] 12+ messages in thread

* Re: [PATCH v5 2/5] xen/vpci: move xen_domctl_createdomain vPCI flag to common
  2023-11-02 19:59 ` [PATCH v5 2/5] xen/vpci: move xen_domctl_createdomain vPCI flag to common Stewart Hildebrand
@ 2023-11-13 13:26   ` Jan Beulich
  2023-11-13 19:05     ` Stewart Hildebrand
  0 siblings, 1 reply; 12+ messages in thread
From: Jan Beulich @ 2023-11-13 13:26 UTC (permalink / raw)
  To: Stewart Hildebrand
  Cc: Wei Liu, Anthony PERARD, Juergen Gross, Andrew Cooper,
	George Dunlap, Julien Grall, Stefano Stabellini,
	Christian Lindig, David Scott, Marek Marczykowski-Górecki,
	Bertrand Marquis, Volodymyr Babchuk, Roger Pau Monné,
	Oleksandr Andrushchenko, Rahul Singh, Christian Lindig,
	xen-devel

On 02.11.2023 20:59, Stewart Hildebrand wrote:
> --- a/tools/libs/light/libxl_x86.c
> +++ b/tools/libs/light/libxl_x86.c
> @@ -8,13 +8,16 @@ int libxl__arch_domain_prepare_config(libxl__gc *gc,
>  {
>      switch(d_config->c_info.type) {
>      case LIBXL_DOMAIN_TYPE_HVM:
> -        config->arch.emulation_flags = (XEN_X86_EMU_ALL & ~XEN_X86_EMU_VPCI);
> +        config->arch.emulation_flags = XEN_X86_EMU_ALL;
> +        config->flags &= ~XEN_DOMCTL_CDF_vpci;
>          break;
>      case LIBXL_DOMAIN_TYPE_PVH:
>          config->arch.emulation_flags = XEN_X86_EMU_LAPIC;
> +        config->flags &= ~XEN_DOMCTL_CDF_vpci;
>          break;
>      case LIBXL_DOMAIN_TYPE_PV:
>          config->arch.emulation_flags = 0;
> +        config->flags &= ~XEN_DOMCTL_CDF_vpci;
>          break;

Why all this explicit clearing of XEN_DOMCTL_CDF_vpci? I can't even spot
where the bit would be set.

> --- a/tools/python/xen/lowlevel/xc/xc.c
> +++ b/tools/python/xen/lowlevel/xc/xc.c
> @@ -159,7 +159,10 @@ static PyObject *pyxc_domain_create(XcObject *self,
>  
>  #if defined (__i386) || defined(__x86_64__)
>      if ( config.flags & XEN_DOMCTL_CDF_hvm )
> -        config.arch.emulation_flags = (XEN_X86_EMU_ALL & ~XEN_X86_EMU_VPCI);
> +    {
> +        config.arch.emulation_flags = XEN_X86_EMU_ALL;
> +        config.flags &= ~XEN_DOMCTL_CDF_vpci;
> +    }

Same question here then.

> @@ -575,6 +577,18 @@ static int sanitise_domain_config(struct xen_domctl_createdomain *config)
>          return -EINVAL;
>      }
>  
> +    if ( vpci && !hvm )
> +    {
> +        dprintk(XENLOG_INFO, "vPCI requested for non-HVM guest\n");
> +        return -EINVAL;
> +    }
> +
> +    if ( vpci && !IS_ENABLED(CONFIG_HAS_VPCI) )
> +    {
> +        dprintk(XENLOG_INFO, "vPCI requested but not enabled\n");
> +        return -EINVAL;
> +    }

Maybe flip the order of these checks? But I'm uncertain about the first
one anyway: Isn't this something that needs deciding per-arch?

> --- a/xen/include/public/arch-x86/xen.h
> +++ b/xen/include/public/arch-x86/xen.h
> @@ -283,15 +283,12 @@ struct xen_arch_domainconfig {
>  #define XEN_X86_EMU_PIT             (1U<<_XEN_X86_EMU_PIT)
>  #define _XEN_X86_EMU_USE_PIRQ       9
>  #define XEN_X86_EMU_USE_PIRQ        (1U<<_XEN_X86_EMU_USE_PIRQ)
> -#define _XEN_X86_EMU_VPCI           10
> -#define XEN_X86_EMU_VPCI            (1U<<_XEN_X86_EMU_VPCI)

This, aiui, being the reason for ...

> --- a/xen/include/public/domctl.h
> +++ b/xen/include/public/domctl.h
> @@ -21,7 +21,7 @@
>  #include "hvm/save.h"
>  #include "memory.h"
>  
> -#define XEN_DOMCTL_INTERFACE_VERSION 0x00000016
> +#define XEN_DOMCTL_INTERFACE_VERSION 0x00000017

... this bump, I wonder whether nevertheless we wouldn't better leave a
comment there to indicate that bit 10 better wouldn't be used again any
time soon.

> @@ -55,9 +55,12 @@ struct xen_domctl_createdomain {
>  #define XEN_DOMCTL_CDF_nested_virt    (1U << _XEN_DOMCTL_CDF_nested_virt)
>  /* Should we expose the vPMU to the guest? */
>  #define XEN_DOMCTL_CDF_vpmu           (1U << 7)
> +/* Should vPCI be enabled for the guest? */
> +#define _XEN_DOMCTL_CDF_vpci          8

What is this needed for besides ...

> +#define XEN_DOMCTL_CDF_vpci           (1U<<_XEN_DOMCTL_CDF_vpci)

... its use here? Imo like was done for vpmu, there should be only one
new identifier. As an aside, there are blanks missing around <<.

> --- a/xen/include/xen/domain.h
> +++ b/xen/include/xen/domain.h
> @@ -51,6 +51,9 @@ void arch_get_domain_info(const struct domain *d,
>  
>  #define is_domain_using_staticmem(d) ((d)->cdf & CDF_staticmem)
>  
> +#define has_vpci(d) (((d)->options & XEN_DOMCTL_CDF_vpci) && \
> +                     IS_ENABLED(CONFIG_HAS_VPCI))

Aiui the IS_ENABLED() is wanted so where suitable code conditional upon
this predicate can be eliminated by the compiler. Question is whether
we can't achieve this by, say, overriding XEN_DOMCTL_CDF_vpci to 0 in
such cases (without touching what you add to the public header, i.e.
not as easy as what we do in xen/arch/x86/include/asm/domain.h for
X86_EMU_*).

Jan


^ permalink raw reply	[flat|nested] 12+ messages in thread

* Re: [PATCH v5 2/5] xen/vpci: move xen_domctl_createdomain vPCI flag to common
  2023-11-13 13:26   ` Jan Beulich
@ 2023-11-13 19:05     ` Stewart Hildebrand
  2023-11-14  8:52       ` Jan Beulich
  0 siblings, 1 reply; 12+ messages in thread
From: Stewart Hildebrand @ 2023-11-13 19:05 UTC (permalink / raw)
  To: Jan Beulich
  Cc: Wei Liu, Anthony PERARD, Juergen Gross, Andrew Cooper,
	George Dunlap, Julien Grall, Stefano Stabellini,
	Christian Lindig, David Scott, Marek Marczykowski-Górecki,
	Bertrand Marquis, Volodymyr Babchuk, Roger Pau Monné,
	Oleksandr Andrushchenko, Rahul Singh, Christian Lindig,
	xen-devel

On 11/13/23 08:26, Jan Beulich wrote:
> On 02.11.2023 20:59, Stewart Hildebrand wrote:
>> --- a/tools/libs/light/libxl_x86.c
>> +++ b/tools/libs/light/libxl_x86.c
>> @@ -8,13 +8,16 @@ int libxl__arch_domain_prepare_config(libxl__gc *gc,
>>  {
>>      switch(d_config->c_info.type) {
>>      case LIBXL_DOMAIN_TYPE_HVM:
>> -        config->arch.emulation_flags = (XEN_X86_EMU_ALL & ~XEN_X86_EMU_VPCI);
>> +        config->arch.emulation_flags = XEN_X86_EMU_ALL;
>> +        config->flags &= ~XEN_DOMCTL_CDF_vpci;
>>          break;
>>      case LIBXL_DOMAIN_TYPE_PVH:
>>          config->arch.emulation_flags = XEN_X86_EMU_LAPIC;
>> +        config->flags &= ~XEN_DOMCTL_CDF_vpci;
>>          break;
>>      case LIBXL_DOMAIN_TYPE_PV:
>>          config->arch.emulation_flags = 0;
>> +        config->flags &= ~XEN_DOMCTL_CDF_vpci;
>>          break;
> 
> Why all this explicit clearing of XEN_DOMCTL_CDF_vpci? I can't even spot
> where the bit would be set.

You're right, it's not being set currently, so no need to explicitly clear the bit here. I'll remove.

> 
>> --- a/tools/python/xen/lowlevel/xc/xc.c
>> +++ b/tools/python/xen/lowlevel/xc/xc.c
>> @@ -159,7 +159,10 @@ static PyObject *pyxc_domain_create(XcObject *self,
>>  
>>  #if defined (__i386) || defined(__x86_64__)
>>      if ( config.flags & XEN_DOMCTL_CDF_hvm )
>> -        config.arch.emulation_flags = (XEN_X86_EMU_ALL & ~XEN_X86_EMU_VPCI);
>> +    {
>> +        config.arch.emulation_flags = XEN_X86_EMU_ALL;
>> +        config.flags &= ~XEN_DOMCTL_CDF_vpci;
>> +    }
> 
> Same question here then.

Same answer here.

> 
>> @@ -575,6 +577,18 @@ static int sanitise_domain_config(struct xen_domctl_createdomain *config)
>>          return -EINVAL;
>>      }
>>  
>> +    if ( vpci && !hvm )
>> +    {
>> +        dprintk(XENLOG_INFO, "vPCI requested for non-HVM guest\n");
>> +        return -EINVAL;
>> +    }
>> +
>> +    if ( vpci && !IS_ENABLED(CONFIG_HAS_VPCI) )
>> +    {
>> +        dprintk(XENLOG_INFO, "vPCI requested but not enabled\n");
>> +        return -EINVAL;
>> +    }
> 
> Maybe flip the order of these checks? But I'm uncertain about the first
> one anyway: Isn't this something that needs deciding per-arch?

In v4, the equivalent of the ( vpci && !hvm ) check was indeed in xen/arch/x86/domain.c:emulation_flags_ok(), but it seemed there was a suggestion that it be moved to common code... See discussion at [1]. How about putting it back into xen/arch/x86/domain.c, in arch_sanitise_domain_config(), not emulation_flags_ok()?

[1] https://lists.xenproject.org/archives/html/xen-devel/2023-10/msg02345.html

> 
>> --- a/xen/include/public/arch-x86/xen.h
>> +++ b/xen/include/public/arch-x86/xen.h
>> @@ -283,15 +283,12 @@ struct xen_arch_domainconfig {
>>  #define XEN_X86_EMU_PIT             (1U<<_XEN_X86_EMU_PIT)
>>  #define _XEN_X86_EMU_USE_PIRQ       9
>>  #define XEN_X86_EMU_USE_PIRQ        (1U<<_XEN_X86_EMU_USE_PIRQ)
>> -#define _XEN_X86_EMU_VPCI           10
>> -#define XEN_X86_EMU_VPCI            (1U<<_XEN_X86_EMU_VPCI)
> 
> This, aiui, being the reason for ...
> 
>> --- a/xen/include/public/domctl.h
>> +++ b/xen/include/public/domctl.h
>> @@ -21,7 +21,7 @@
>>  #include "hvm/save.h"
>>  #include "memory.h"
>>  
>> -#define XEN_DOMCTL_INTERFACE_VERSION 0x00000016
>> +#define XEN_DOMCTL_INTERFACE_VERSION 0x00000017
> 
> ... this bump, I wonder whether nevertheless we wouldn't better leave a
> comment there to indicate that bit 10 better wouldn't be used again any
> time soon.

I'll add a comment (above, in arch-x86/xen.h)

> 
>> @@ -55,9 +55,12 @@ struct xen_domctl_createdomain {
>>  #define XEN_DOMCTL_CDF_nested_virt    (1U << _XEN_DOMCTL_CDF_nested_virt)
>>  /* Should we expose the vPMU to the guest? */
>>  #define XEN_DOMCTL_CDF_vpmu           (1U << 7)
>> +/* Should vPCI be enabled for the guest? */
>> +#define _XEN_DOMCTL_CDF_vpci          8
> 
> What is this needed for besides ...
> 
>> +#define XEN_DOMCTL_CDF_vpci           (1U<<_XEN_DOMCTL_CDF_vpci)
> 
> ... its use here? Imo like was done for vpmu, there should be only one
> new identifier. As an aside, there are blanks missing around <<.

OK, I'll fix this

> 
>> --- a/xen/include/xen/domain.h
>> +++ b/xen/include/xen/domain.h
>> @@ -51,6 +51,9 @@ void arch_get_domain_info(const struct domain *d,
>>  
>>  #define is_domain_using_staticmem(d) ((d)->cdf & CDF_staticmem)
>>  
>> +#define has_vpci(d) (((d)->options & XEN_DOMCTL_CDF_vpci) && \
>> +                     IS_ENABLED(CONFIG_HAS_VPCI))
> 
> Aiui the IS_ENABLED() is wanted so where suitable code conditional upon
> this predicate can be eliminated by the compiler. Question is whether
> we can't achieve this by, say, overriding XEN_DOMCTL_CDF_vpci to 0 in
> such cases (without touching what you add to the public header, i.e.
> not as easy as what we do in xen/arch/x86/include/asm/domain.h for
> X86_EMU_*).

I had only added the IS_ENABLED() here due to some (unnecessary) related changes in the later patch ("xen/arm: enable vPCI for domUs"). I hadn't considered the compiler optimization aspect. I can understand the potential benefit, but I'm not ready to introduce such complexity at this time. I'm in favor of "simpler is better" in this case, so I'll change it back to how it was in v4:

#define has_vpci(d) (!!((d)->options & XEN_DOMCTL_CDF_vpci))

> 
> Jan


^ permalink raw reply	[flat|nested] 12+ messages in thread

* Re: [PATCH v5 4/5] [FUTURE] xen/arm: enable vPCI for domUs
  2023-11-06  9:26   ` Jan Beulich
@ 2023-11-13 21:10     ` Stewart Hildebrand
  2023-11-14  8:58       ` Jan Beulich
  0 siblings, 1 reply; 12+ messages in thread
From: Stewart Hildebrand @ 2023-11-13 21:10 UTC (permalink / raw)
  To: Jan Beulich
  Cc: Stefano Stabellini, Julien Grall, Bertrand Marquis,
	Volodymyr Babchuk, Andrew Cooper, George Dunlap, Wei Liu,
	Roger Pau Monné,
	Paul Durrant, xen-devel

On 11/6/23 04:26, Jan Beulich wrote:
> On 02.11.2023 20:59, Stewart Hildebrand wrote:
>> --- a/xen/arch/x86/include/asm/domain.h
>> +++ b/xen/arch/x86/include/asm/domain.h
>> @@ -503,6 +503,15 @@ struct arch_domain
>>  #define has_vpit(d)        (!!((d)->arch.emulation_flags & X86_EMU_PIT))
>>  #define has_pirq(d)        (!!((d)->arch.emulation_flags & X86_EMU_USE_PIRQ))
>>  
>> +#define is_pvh_domain(d) ({                                  \
>> +    unsigned int _emflags = (d)->arch.emulation_flags;       \
>> +    IS_ENABLED(CONFIG_HVM) &&                                \
>> +        ((_emflags == X86_EMU_LAPIC) ||                      \
>> +         (_emflags == (X86_EMU_LAPIC | X86_EMU_IOAPIC))); })
> 
> I'm not convinced we want to re-introduce such a predicate; it'll be at
> risk of going stale when the boundary between HVM and PVH becomes more
> "fuzzy".

OK, I'll drop it

> 
>> +/* PCI passthrough may be backed by qemu for non-PVH domains */
>> +#define arch_needs_vpci(d) is_pvh_domain(d)
> 
> Wouldn't we want to check for exactly what the comment alludes to then,
> i.e. whether the domain has any (specific?) device model attached?

This patch is primarily dealing with Arm, so I'm considering simply making it return false for now:

#define arch_needs_vpci(d) ({ (void)(d); false; })

If it needs to be changed in the future when we enable vPCI for PVH domUs, we can deal with it at that time.

> 
>> --- a/xen/include/xen/domain.h
>> +++ b/xen/include/xen/domain.h
>> @@ -51,8 +51,17 @@ void arch_get_domain_info(const struct domain *d,
>>  
>>  #define is_domain_using_staticmem(d) ((d)->cdf & CDF_staticmem)
>>  
>> -#define has_vpci(d) (((d)->options & XEN_DOMCTL_CDF_vpci) && \
>> -                     IS_ENABLED(CONFIG_HAS_VPCI))
>> +#define has_vpci(d) ({                                                        \
>> +    const struct domain *_d = (d);                                            \
>> +    bool _has_vpci = false;                                                   \
>> +    if ( (_d->options & XEN_DOMCTL_CDF_vpci) && IS_ENABLED(CONFIG_HAS_VPCI) ) \
>> +    {                                                                         \
>> +        if ( is_hardware_domain(_d) )                                         \
>> +            _has_vpci = true;                                                 \
>> +        else if ( IS_ENABLED(CONFIG_HAS_VPCI_GUEST_SUPPORT) )                 \
>> +            _has_vpci = true;                                                 \
>> +    }                                                                         \
>> +    _has_vpci; })
> 
> This is a commonly executed check, and as such wants to remain as simple as
> possible. Wouldn't it be better anyway to prevent XEN_DOMCTL_CDF_vpci getting
> set for a domain which cannot possibly have vPCI?

Yes, agreed, I'll leave has_vpci alone

> 
> Jan


^ permalink raw reply	[flat|nested] 12+ messages in thread

* Re: [PATCH v5 2/5] xen/vpci: move xen_domctl_createdomain vPCI flag to common
  2023-11-13 19:05     ` Stewart Hildebrand
@ 2023-11-14  8:52       ` Jan Beulich
  0 siblings, 0 replies; 12+ messages in thread
From: Jan Beulich @ 2023-11-14  8:52 UTC (permalink / raw)
  To: Stewart Hildebrand
  Cc: Wei Liu, Anthony PERARD, Juergen Gross, Andrew Cooper,
	George Dunlap, Julien Grall, Stefano Stabellini,
	Christian Lindig, David Scott, Marek Marczykowski-Górecki,
	Bertrand Marquis, Volodymyr Babchuk, Roger Pau Monné,
	Oleksandr Andrushchenko, Rahul Singh, Christian Lindig,
	xen-devel

On 13.11.2023 20:05, Stewart Hildebrand wrote:
> On 11/13/23 08:26, Jan Beulich wrote:
>> On 02.11.2023 20:59, Stewart Hildebrand wrote:
>>> @@ -575,6 +577,18 @@ static int sanitise_domain_config(struct xen_domctl_createdomain *config)
>>>          return -EINVAL;
>>>      }
>>>  
>>> +    if ( vpci && !hvm )
>>> +    {
>>> +        dprintk(XENLOG_INFO, "vPCI requested for non-HVM guest\n");
>>> +        return -EINVAL;
>>> +    }
>>> +
>>> +    if ( vpci && !IS_ENABLED(CONFIG_HAS_VPCI) )
>>> +    {
>>> +        dprintk(XENLOG_INFO, "vPCI requested but not enabled\n");
>>> +        return -EINVAL;
>>> +    }
>>
>> Maybe flip the order of these checks? But I'm uncertain about the first
>> one anyway: Isn't this something that needs deciding per-arch?
> 
> In v4, the equivalent of the ( vpci && !hvm ) check was indeed in xen/arch/x86/domain.c:emulation_flags_ok(), but it seemed there was a suggestion that it be moved to common code... See discussion at [1]. How about putting it back into xen/arch/x86/domain.c, in arch_sanitise_domain_config(), not emulation_flags_ok()?

Actually no, I take back that part of the comment. I think I mistakenly
considered PVH as "non-HVM" (as the log message has it).

Jan

> [1] https://lists.xenproject.org/archives/html/xen-devel/2023-10/msg02345.html



^ permalink raw reply	[flat|nested] 12+ messages in thread

* Re: [PATCH v5 4/5] [FUTURE] xen/arm: enable vPCI for domUs
  2023-11-13 21:10     ` Stewart Hildebrand
@ 2023-11-14  8:58       ` Jan Beulich
  0 siblings, 0 replies; 12+ messages in thread
From: Jan Beulich @ 2023-11-14  8:58 UTC (permalink / raw)
  To: Stewart Hildebrand
  Cc: Stefano Stabellini, Julien Grall, Bertrand Marquis,
	Volodymyr Babchuk, Andrew Cooper, George Dunlap, Wei Liu,
	Roger Pau Monné,
	Paul Durrant, xen-devel

On 13.11.2023 22:10, Stewart Hildebrand wrote:
> On 11/6/23 04:26, Jan Beulich wrote:
>> On 02.11.2023 20:59, Stewart Hildebrand wrote:
>>> +/* PCI passthrough may be backed by qemu for non-PVH domains */
>>> +#define arch_needs_vpci(d) is_pvh_domain(d)
>>
>> Wouldn't we want to check for exactly what the comment alludes to then,
>> i.e. whether the domain has any (specific?) device model attached?
> 
> This patch is primarily dealing with Arm, so I'm considering simply making it return false for now:
> 
> #define arch_needs_vpci(d) ({ (void)(d); false; })

But that's wrong for hwdom, as much as - strictly speaking - needs_vpci()
returning false for hwdom is wrong in the PVH case. This would then at
least need clarifying comments.

Jan


^ permalink raw reply	[flat|nested] 12+ messages in thread

end of thread, other threads:[~2023-11-14  8:58 UTC | newest]

Thread overview: 12+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-11-02 19:59 [PATCH v5 0/5] Kconfig for PCI passthrough on ARM Stewart Hildebrand
2023-11-02 19:59 ` [PATCH v5 1/5] xen/arm: pci: introduce PCI_PASSTHROUGH Kconfig option Stewart Hildebrand
2023-11-02 19:59 ` [PATCH v5 2/5] xen/vpci: move xen_domctl_createdomain vPCI flag to common Stewart Hildebrand
2023-11-13 13:26   ` Jan Beulich
2023-11-13 19:05     ` Stewart Hildebrand
2023-11-14  8:52       ` Jan Beulich
2023-11-02 19:59 ` [PATCH v5 3/5] [FUTURE] xen/arm: enable vPCI for dom0 Stewart Hildebrand
2023-11-02 19:59 ` [PATCH v5 4/5] [FUTURE] xen/arm: enable vPCI for domUs Stewart Hildebrand
2023-11-06  9:26   ` Jan Beulich
2023-11-13 21:10     ` Stewart Hildebrand
2023-11-14  8:58       ` Jan Beulich
2023-11-02 19:59 ` [PATCH v5 5/5] [FUTURE] tools/arm: " Stewart Hildebrand

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.