[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[RFC 7/8] multiprocess: add ioregionfd memory region in proxy
From: |
Elena Ufimtseva |
Subject: |
[RFC 7/8] multiprocess: add ioregionfd memory region in proxy |
Date: |
Mon, 7 Feb 2022 23:22:21 -0800 |
Signed-off-by: Elena Ufimtseva <elena.ufimtseva@oracle.com>
---
include/hw/remote/proxy.h | 1 +
hw/remote/proxy.c | 66 ++++++++++++++++++++++++++++++++++++---
2 files changed, 63 insertions(+), 4 deletions(-)
diff --git a/include/hw/remote/proxy.h b/include/hw/remote/proxy.h
index 741def71f1..9efef0b935 100644
--- a/include/hw/remote/proxy.h
+++ b/include/hw/remote/proxy.h
@@ -29,6 +29,7 @@ struct PCIProxyDev {
PCIDevice parent_dev;
char *fd;
+ char *ioregfd;
/*
* Mutex used to protect the QIOChannel fd from
* the concurrent access by the VCPUs since proxy
diff --git a/hw/remote/proxy.c b/hw/remote/proxy.c
index bad164299d..ba1aa20d78 100644
--- a/hw/remote/proxy.c
+++ b/hw/remote/proxy.c
@@ -146,6 +146,33 @@ static void pci_proxy_dev_exit(PCIDevice *pdev)
event_notifier_cleanup(&dev->resample);
}
+static void config_get_ioregionfd_info(PCIProxyDev *pdev, uint32_t reg_num,
+ uint32_t *val, bool memory)
+{
+ MPQemuMsg msg = { 0 };
+ Error *local_err = NULL;
+ uint64_t ret = -EINVAL;
+
+ memset(&msg, 0, sizeof(MPQemuMsg));
+ msg.cmd = MPQEMU_CMD_BAR_INFO;
+ msg.num_fds = 0;
+ msg.data.u64 = (uint64_t)reg_num & MAKE_64BIT_MASK(0, 32);
+
+ msg.data.u64 |= memory ? (1ULL << 32) : 0;
+ msg.size = sizeof(msg.data.u64);
+
+ ret = mpqemu_msg_send_and_await_reply(&msg, pdev, &local_err);
+ if (local_err) {
+ error_report_err(local_err);
+ error_report("Error while receiving reply from remote about fd");
+ }
+ if (ret == UINT64_MAX) {
+ error_report("Failed to request bar info for %d", reg_num);
+ }
+
+ *val = (uint32_t)ret;
+}
+
static void config_op_send(PCIProxyDev *pdev, uint32_t addr, uint32_t *val,
int len, unsigned int op)
{
@@ -198,6 +225,7 @@ static void pci_proxy_write_config(PCIDevice *d, uint32_t
addr, uint32_t val,
static Property proxy_properties[] = {
DEFINE_PROP_STRING("fd", PCIProxyDev, fd),
+ DEFINE_PROP_STRING("ioregfd", PCIProxyDev, ioregfd),
DEFINE_PROP_END_OF_LIST(),
};
@@ -297,7 +325,7 @@ const MemoryRegionOps proxy_mr_ops = {
static void probe_pci_info(PCIDevice *dev, Error **errp)
{
PCIDeviceClass *pc = PCI_DEVICE_GET_CLASS(dev);
- uint32_t orig_val, new_val, base_class, val;
+ uint32_t orig_val, new_val, base_class, val, ioregionfd_bar;
PCIProxyDev *pdev = PCI_PROXY_DEV(dev);
DeviceClass *dc = DEVICE_CLASS(pc);
uint8_t type;
@@ -342,6 +370,9 @@ static void probe_pci_info(PCIDevice *dev, Error **errp)
}
for (i = 0; i < PCI_NUM_REGIONS; i++) {
+ bool init_ioregionfd = false;
+ int fd = -1;
+
config_op_send(pdev, PCI_BASE_ADDRESS_0 + (4 * i), &orig_val, 4,
MPQEMU_CMD_PCI_CFGREAD);
new_val = 0xffffffff;
@@ -362,9 +393,36 @@ static void probe_pci_info(PCIDevice *dev, Error **errp)
if (type == PCI_BASE_ADDRESS_SPACE_MEMORY) {
pdev->region[i].memory = true;
}
- memory_region_init_io(&pdev->region[i].mr, OBJECT(pdev),
- &proxy_mr_ops, &pdev->region[i],
- name, size);
+#ifdef CONFIG_IOREGIONFD
+ /*
+ * Currently, only one fd per device is supported.
+ * TODO: Drop this limit.
+ */
+ if (pdev->ioregfd) {
+ fd = monitor_fd_param(monitor_cur(), pdev->ioregfd, errp);
+ if (fd == -1) {
+ error_prepend(errp, "Could not parse ioregionfd fd %s:",
+ pdev->ioregfd);
+ }
+
+ config_get_ioregionfd_info(pdev, i, &ioregionfd_bar,
+ pdev->region[i].memory);
+ if (ioregionfd_bar == i) {
+ init_ioregionfd = true;
+ }
+ }
+#endif
+ if (init_ioregionfd) {
+ memory_region_init_io(&pdev->region[i].mr, OBJECT(pdev),
+ NULL, &pdev->region[i],
+ name, size);
+ memory_region_add_ioregionfd(&pdev->region[i].mr, 0, size, i,
+ fd, false);
+ } else {
+ memory_region_init_io(&pdev->region[i].mr, OBJECT(pdev),
+ &proxy_mr_ops, &pdev->region[i],
+ name, size);
+ }
pci_register_bar(dev, i, type, &pdev->region[i].mr);
}
}
--
2.25.1
- [RFC 0/8] ioregionfd introduction, Elena Ufimtseva, 2022/02/08
- [RFC 2/8] multiprocess: place RemoteObject definition in a header file, Elena Ufimtseva, 2022/02/08
- [RFC 1/8] ioregionfd: introduce a syscall and memory API, Elena Ufimtseva, 2022/02/08
- [RFC 7/8] multiprocess: add ioregionfd memory region in proxy,
Elena Ufimtseva <=
- [RFC 5/8] multiprocess: prepare ioregionfds for remote device, Elena Ufimtseva, 2022/02/08
- [RFC 3/8] ioregionfd: introduce memory API functions, Elena Ufimtseva, 2022/02/08
- [RFC 6/8] multiprocess: add MPQEMU_CMD_BAR_INFO, Elena Ufimtseva, 2022/02/08
- [RFC 8/8] multiprocess: handle ioregionfd commands, Elena Ufimtseva, 2022/02/08
- Re: [RFC 0/8] ioregionfd introduction, Stefan Hajnoczi, 2022/02/09
- Re: [RFC 0/8] ioregionfd introduction, Stefan Hajnoczi, 2022/02/14