From: Arianna Avanzini <avanzini.arianna@gmail.com>
To: xen-devel@lists.xen.org
Cc: Ian.Campbell@eu.citrix.com, paolo.valente@unimore.it,
keir@xen.org, stefano.stabellini@eu.citrix.com,
Ian.Jackson@eu.citrix.com, dario.faggioli@citrix.com,
tim@xen.org, julien.grall@citrix.com, etrudeau@broadcom.com,
andrew.cooper3@citrix.com, JBeulich@suse.com,
avanzini.arianna@gmail.com, viktor.kleinik@globallogic.com
Subject: [PATCH v10 11/12] tools/libxl: explicitly grant access to needed I/O-memory ranges
Date: Tue, 29 Jul 2014 00:12:08 +0200 [thread overview]
Message-ID: <1406585529-32193-12-git-send-email-avanzini.arianna@gmail.com> (raw)
In-Reply-To: <1406585529-32193-1-git-send-email-avanzini.arianna@gmail.com>
This commit changes the existing libxl code to be sure to grant access
permission to PCI-related I/O memory ranges, while setting up passthrough
of PCI devices specified in the domain's configuration, and to VGA-related
memory ranges, while setting up VGA passthrough (if gfx_passthru = 1 and
gfx_passthru_primary = 1 in the domain's configuration).
As for the latter, the newly-added code does not replace any existing one,
but instead matches the calls to xc_domain_memory_mapping() performed by
QEMU on the path that is executed if gfx passthru is enabled and follows
the registration of a new VGA controller (in register_vga_regions(),
defined in hw/pt-graphics.c). In fact, VGA needs some extra memory
ranges to be mapped with respect to PCI; QEMU expects that access to those
memory ranges is implicitly granted when he calls the hypervisor with the
function xc_domain_memory_mapping(): this commit calls iomem_permission
for it when needed for a primary GPU by checking the passthru PCI devices'
class.
This commit is instrumental to the following one, which will separate
the functions of the iomem_permission and memory_mapping DOMCTLs, so
that requesting an I/O-memory range will not imply that access to such a
range is implicitly granted.
Signed-off-by: Arianna Avanzini <avanzini.arianna@gmail.com>
Cc: Dario Faggioli <dario.faggioli@citrix.com>
Cc: Paolo Valente <paolo.valente@unimore.it>
Cc: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
Cc: Julien Grall <julien.grall@citrix.com>
Cc: Ian Campbell <Ian.Campbell@eu.citrix.com>
Cc: Jan Beulich <JBeulich@suse.com>
Cc: Keir Fraser <keir@xen.org>
Cc: Tim Deegan <tim@xen.org>
Cc: Ian Jackson <Ian.Jackson@eu.citrix.com>
Cc: Andrew Cooper <andrew.cooper3@citrix.com>
Cc: Eric Trudeau <etrudeau@broadcom.com>
Cc: Viktor Kleinik <viktor.kleinik@globallogic.com>
---
v10:
- Use a class-based check on the PCI device to determine if VGA-related
I/O-memory ranges must be made accessible to a guest that needs gfx
passthrough.
v9:
- Allow a domain access to the VGA framebuffer only if the user has
signaled that one of the passthru GPUs is primary via domain config.
v8:
- Explain better in the commit description VGA-related code additions.
- Fix v6 changelog which, being too generic, ended up to uncorrectly
state that one of the requests had been addressed.
- Remove tentative phrases from commit description.
v7:
- Let libxl not handle I/O ports and I/O memory differently when access
to a PCI device is allowed to a domain.
- Change the construct used by libxl during PCI-related initialization
from a switch to an if to better suit the new execution flow.
---
tools/libxl/libxl_create.c | 60 ++++++++++++++++++++++++++++++++++++++++++++++
tools/libxl/libxl_pci.c | 26 ++++++++------------
tools/libxl/xl_cmdimpl.c | 1 +
3 files changed, 71 insertions(+), 16 deletions(-)
diff --git a/tools/libxl/libxl_create.c b/tools/libxl/libxl_create.c
index 1217310..b5bc07a 100644
--- a/tools/libxl/libxl_create.c
+++ b/tools/libxl/libxl_create.c
@@ -19,6 +19,7 @@
#include "libxl_internal.h"
#include "libxl_arch.h"
+#include "libxl_pci.h"
#include <xc_dom.h>
#include <xenguest.h>
@@ -1194,6 +1195,65 @@ static void domcreate_launch_dm(libxl__egc *egc, libxl__multidev *multidev,
libxl__spawn_stub_dm(egc, &dcs->dmss);
else
libxl__spawn_local_dm(egc, &dcs->dmss.dm);
+
+ /*
+ * If VGA passthru is enabled by domain config and one of the
+ * passthru GPUs is of VGA class, be sure that the related
+ * stubdomain and the domain itself can access the VGA
+ * framebuffer.
+ */
+ for (i = 0 ; d_config->b_info.u.hvm.gfx_passthru.val &&
+ i < d_config->num_pcidevs ; i++) {
+ uint64_t vga_iomem_start = 0xa0000 >> XC_PAGE_SHIFT;
+ int stubdom_domid;
+ libxl_device_pci *pcidev = &d_config->pcidevs[i];
+ char *pci_device_class_path =
+ libxl__sprintf(gc, SYSFS_PCI_DEV"/"PCI_BDF"/class",
+ pcidev->domain, pcidev->bus, pcidev->dev,
+ pcidev->func);
+ int read_items;
+ unsigned long pci_device_class;
+ FILE *f = fopen(pci_device_class_path, "r");
+ if (!f) {
+ LOGE(ERROR,
+ "pci device "PCI_BDF" does not have class attribute",
+ pcidev->domain, pcidev->bus, pcidev->dev, pcidev->func);
+ continue;
+ }
+ read_items = fscanf(f, "0x%lx\n", &pci_device_class);
+ fclose(f);
+ if (read_items != 1) {
+ LOGE(ERROR,
+ "cannot read class of pci device "PCI_BDF,
+ pcidev->domain, pcidev->bus, pcidev->dev, pcidev->func);
+ continue;
+ }
+ if (pci_device_class != 0x030000)
+ continue;
+
+ stubdom_domid = libxl_get_stubdom_id(CTX, domid);
+ ret = xc_domain_iomem_permission(CTX->xch, stubdom_domid,
+ vga_iomem_start, 0x20, 1);
+ if (ret < 0) {
+ LOGE(ERROR,
+ "failed to give stubdom%d access to iomem range "
+ "%"PRIx64"-%"PRIx64" for VGA passthru",
+ stubdom_domid,
+ vga_iomem_start, (vga_iomem_start + 0x20 - 1));
+ goto error_out;
+ }
+ ret = xc_domain_iomem_permission(CTX->xch, domid,
+ vga_iomem_start, 0x20, 1);
+ if (ret < 0) {
+ LOGE(ERROR,
+ "failed to give dom%d access to iomem range "
+ "%"PRIx64"-%"PRIx64" for VGA passthru",
+ domid, vga_iomem_start, (vga_iomem_start + 0x20 - 1));
+ goto error_out;
+ }
+ break;
+ }
+
return;
}
case LIBXL_DOMAIN_TYPE_PV:
diff --git a/tools/libxl/libxl_pci.c b/tools/libxl/libxl_pci.c
index 21ecab1..1524170 100644
--- a/tools/libxl/libxl_pci.c
+++ b/tools/libxl/libxl_pci.c
@@ -841,10 +841,13 @@ static int qemu_pci_add_xenstore(libxl__gc *gc, uint32_t domid,
static int do_pci_add(libxl__gc *gc, uint32_t domid, libxl_device_pci *pcidev, int starting)
{
libxl_ctx *ctx = libxl__gc_owner(gc);
+ libxl_domain_type type = libxl__domain_type(gc, domid);
int rc, hvm = 0;
- switch (libxl__domain_type(gc, domid)) {
- case LIBXL_DOMAIN_TYPE_HVM:
+ if (type == LIBXL_DOMAIN_TYPE_INVALID)
+ return ERROR_FAIL;
+
+ if (type == LIBXL_DOMAIN_TYPE_HVM) {
hvm = 1;
if (libxl__wait_for_device_model_deprecated(gc, domid, "running",
NULL, NULL, NULL) < 0) {
@@ -862,8 +865,7 @@ static int do_pci_add(libxl__gc *gc, uint32_t domid, libxl_device_pci *pcidev, i
}
if ( rc )
return ERROR_FAIL;
- break;
- case LIBXL_DOMAIN_TYPE_PV:
+ }
{
char *sysfs_path = libxl__sprintf(gc, SYSFS_PCI_DEV"/"PCI_BDF"/resource", pcidev->domain,
pcidev->bus, pcidev->dev, pcidev->func);
@@ -932,10 +934,6 @@ static int do_pci_add(libxl__gc *gc, uint32_t domid, libxl_device_pci *pcidev, i
return ERROR_FAIL;
}
}
- break;
- }
- case LIBXL_DOMAIN_TYPE_INVALID:
- return ERROR_FAIL;
}
out:
if (!libxl_is_stubdom(ctx, domid, NULL)) {
@@ -1161,6 +1159,7 @@ static int do_pci_remove(libxl__gc *gc, uint32_t domid,
{
libxl_ctx *ctx = libxl__gc_owner(gc);
libxl_device_pci *assigned;
+ libxl_domain_type type = libxl__domain_type(gc, domid);
int hvm = 0, rc, num;
int stubdomid = 0;
@@ -1176,8 +1175,7 @@ static int do_pci_remove(libxl__gc *gc, uint32_t domid,
}
rc = ERROR_FAIL;
- switch (libxl__domain_type(gc, domid)) {
- case LIBXL_DOMAIN_TYPE_HVM:
+ if (type == LIBXL_DOMAIN_TYPE_HVM) {
hvm = 1;
if (libxl__wait_for_device_model_deprecated(gc, domid, "running",
NULL, NULL, NULL) < 0)
@@ -1198,8 +1196,8 @@ static int do_pci_remove(libxl__gc *gc, uint32_t domid,
rc = ERROR_FAIL;
goto out_fail;
}
- break;
- case LIBXL_DOMAIN_TYPE_PV:
+ } else if (type != LIBXL_DOMAIN_TYPE_PV)
+ abort();
{
char *sysfs_path = libxl__sprintf(gc, SYSFS_PCI_DEV"/"PCI_BDF"/resource", pcidev->domain,
pcidev->bus, pcidev->dev, pcidev->func);
@@ -1249,10 +1247,6 @@ skip1:
}
}
fclose(f);
- break;
- }
- default:
- abort();
}
out:
/* don't do multiple resets while some functions are still passed through */
diff --git a/tools/libxl/xl_cmdimpl.c b/tools/libxl/xl_cmdimpl.c
index e035e97..7f1bb6b 100644
--- a/tools/libxl/xl_cmdimpl.c
+++ b/tools/libxl/xl_cmdimpl.c
@@ -1422,6 +1422,7 @@ skip_vfb:
if (!xlu_cfg_get_list (config, "pci", &pcis, 0, 0)) {
d_config->num_pcidevs = 0;
d_config->pcidevs = NULL;
+ fprintf(stderr, "XEN parsing pci list\n");
for(i = 0; (buf = xlu_cfg_get_listitem (pcis, i)) != NULL; i++) {
libxl_device_pci *pcidev;
--
2.0.3
next prev parent reply other threads:[~2014-07-28 22:12 UTC|newest]
Thread overview: 34+ messages / expand[flat|nested] mbox.gz Atom feed top
2014-07-28 22:11 [PATCH v10 00/12] Implement the XEN_DOMCTL_memory_mapping hypercall for ARM Arianna Avanzini
2014-07-28 22:11 ` [PATCH v10 01/12] arch/arm: add consistency check to REMOVE p2m changes Arianna Avanzini
2014-07-29 11:55 ` Julien Grall
2014-07-29 12:01 ` Ian Campbell
2014-07-29 12:02 ` Andrew Cooper
2014-07-28 22:11 ` [PATCH v10 02/12] arch/arm: unmap partially-mapped I/O-memory regions Arianna Avanzini
2014-07-29 12:00 ` Julien Grall
2014-07-28 22:12 ` [PATCH v10 03/12] arch/x86: warn if to-be-removed mapping does not exist Arianna Avanzini
2014-07-28 22:12 ` [PATCH v10 04/12] arch/x86: cleanup memory_mapping DOMCTL Arianna Avanzini
2014-07-28 22:12 ` [PATCH v10 05/12] xen/common: add ARM stub for the function memory_type_changed() Arianna Avanzini
2014-07-28 22:12 ` [PATCH v10 06/12] xen/x86: factor out map and unmap from the memory_mapping DOMCTL Arianna Avanzini
2014-07-29 7:27 ` Jan Beulich
2014-07-29 12:02 ` Julien Grall
2014-07-28 22:12 ` [PATCH v10 07/12] xen/common: move the memory_mapping DOMCTL hypercall to common code Arianna Avanzini
2014-07-30 15:59 ` Julien Grall
2014-07-28 22:12 ` [PATCH v10 08/12] tools/libxl: parse optional start gfn from the iomem config option Arianna Avanzini
2014-08-04 13:39 ` Julien Grall
2014-07-28 22:12 ` [PATCH v10 09/12] tools/libxl: handle the iomem parameter with the memory_mapping hcall Arianna Avanzini
2014-07-28 22:12 ` [PATCH v10 10/12] tools/libxl: move PCI-related macros in a header file Arianna Avanzini
2014-07-28 22:12 ` Arianna Avanzini [this message]
2014-07-30 11:33 ` [PATCH v10 11/12] tools/libxl: explicitly grant access to needed I/O-memory ranges Ian Campbell
2014-07-28 22:12 ` [PATCH v10 12/12] xen/common: do not implicitly permit access to mapped I/O memory Arianna Avanzini
2014-07-29 7:29 ` Jan Beulich
2014-08-18 19:50 ` [PATCH v10 00/12] Implement the XEN_DOMCTL_memory_mapping hypercall for ARM Andrii Tseglytskyi
2014-08-20 18:50 ` Arianna Avanzini
2014-08-20 19:15 ` Andrii Tseglytskyi
2014-08-21 15:43 ` Andrii Tseglytskyi
2014-08-22 14:25 ` Arianna Avanzini
2014-08-22 18:27 ` Andrii Tseglytskyi
2014-08-22 18:36 ` Arianna Avanzini
2014-08-22 19:31 ` Andrii Tseglytskyi
2014-08-22 23:51 ` Stefano Stabellini
2014-08-23 12:07 ` Arianna Avanzini
2014-08-23 17:36 ` Andrii Tseglytskyi
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1406585529-32193-12-git-send-email-avanzini.arianna@gmail.com \
--to=avanzini.arianna@gmail.com \
--cc=Ian.Campbell@eu.citrix.com \
--cc=Ian.Jackson@eu.citrix.com \
--cc=JBeulich@suse.com \
--cc=andrew.cooper3@citrix.com \
--cc=dario.faggioli@citrix.com \
--cc=etrudeau@broadcom.com \
--cc=julien.grall@citrix.com \
--cc=keir@xen.org \
--cc=paolo.valente@unimore.it \
--cc=stefano.stabellini@eu.citrix.com \
--cc=tim@xen.org \
--cc=viktor.kleinik@globallogic.com \
--cc=xen-devel@lists.xen.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).