[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH 06/10] memory: move ioeventfd ops to MemoryListener
From: |
Avi Kivity |
Subject: |
[Qemu-devel] [PATCH 06/10] memory: move ioeventfd ops to MemoryListener |
Date: |
Wed, 8 Feb 2012 17:27:55 +0200 |
This way the accelerator (kvm) can handle them directly.
Signed-off-by: Avi Kivity <address@hidden>
---
hw/vhost.c | 14 ++++++++++
kvm-all.c | 78 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
memory.c | 74 ++++++++++++++-------------------------------------------
memory.h | 4 +++
xen-all.c | 14 ++++++++++
5 files changed, 128 insertions(+), 56 deletions(-)
diff --git a/hw/vhost.c b/hw/vhost.c
index 4737145..e1e7e01 100644
--- a/hw/vhost.c
+++ b/hw/vhost.c
@@ -720,6 +720,18 @@ static void vhost_virtqueue_cleanup(struct vhost_dev *dev,
0, virtio_queue_get_desc_size(vdev, idx));
}
+static void vhost_eventfd_add(MemoryListener *listener,
+ MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+}
+
+static void vhost_eventfd_del(MemoryListener *listener,
+ MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+}
+
int vhost_dev_init(struct vhost_dev *hdev, int devfd, bool force)
{
uint64_t features;
@@ -751,6 +763,8 @@ int vhost_dev_init(struct vhost_dev *hdev, int devfd, bool
force)
.log_sync = vhost_log_sync,
.log_global_start = vhost_log_global_start,
.log_global_stop = vhost_log_global_stop,
+ .eventfd_add = vhost_eventfd_add,
+ .eventfd_del = vhost_eventfd_del,
.priority = 10
};
hdev->mem = g_malloc0(offsetof(struct vhost_memory, regions));
diff --git a/kvm-all.c b/kvm-all.c
index 6835fd4..a05e591 100644
--- a/kvm-all.c
+++ b/kvm-all.c
@@ -28,6 +28,7 @@
#include "kvm.h"
#include "bswap.h"
#include "memory.h"
+#include "exec-memory.h"
/* This check must be after config-host.h is included */
#ifdef CONFIG_EVENTFD
@@ -718,6 +719,81 @@ static void kvm_log_global_stop(struct MemoryListener
*listener)
assert(r >= 0);
}
+static void kvm_mem_ioeventfd_add(MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+ int r;
+
+ assert(match_data && section->size == 4);
+
+ r = kvm_set_ioeventfd_mmio_long(fd, section->offset_within_address_space,
+ data, true);
+ if (r < 0) {
+ abort();
+ }
+}
+
+static void kvm_mem_ioeventfd_del(MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+ int r;
+
+ r = kvm_set_ioeventfd_mmio_long(fd, section->offset_within_address_space,
+ data, false);
+ if (r < 0) {
+ abort();
+ }
+}
+
+static void kvm_io_ioeventfd_add(MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+ int r;
+
+ assert(match_data && section->size == 2);
+
+ r = kvm_set_ioeventfd_pio_word(fd, section->offset_within_address_space,
+ data, true);
+ if (r < 0) {
+ abort();
+ }
+}
+
+static void kvm_io_ioeventfd_del(MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+
+{
+ int r;
+
+ r = kvm_set_ioeventfd_pio_word(fd, section->offset_within_address_space,
+ data, false);
+ if (r < 0) {
+ abort();
+ }
+}
+
+static void kvm_eventfd_add(MemoryListener *listener,
+ MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+ if (section->address_space == get_system_memory()) {
+ kvm_mem_ioeventfd_add(section, match_data, data, fd);
+ } else {
+ kvm_io_ioeventfd_add(section, match_data, data, fd);
+ }
+}
+
+static void kvm_eventfd_del(MemoryListener *listener,
+ MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+ if (section->address_space == get_system_memory()) {
+ kvm_mem_ioeventfd_del(section, match_data, data, fd);
+ } else {
+ kvm_io_ioeventfd_del(section, match_data, data, fd);
+ }
+}
+
static MemoryListener kvm_memory_listener = {
.region_add = kvm_region_add,
.region_del = kvm_region_del,
@@ -726,6 +802,8 @@ static void kvm_log_global_stop(struct MemoryListener
*listener)
.log_sync = kvm_log_sync,
.log_global_start = kvm_log_global_start,
.log_global_stop = kvm_log_global_stop,
+ .eventfd_add = kvm_eventfd_add,
+ .eventfd_del = kvm_eventfd_del,
.priority = 10,
};
diff --git a/memory.c b/memory.c
index a1013bc..e1a31d4 100644
--- a/memory.c
+++ b/memory.c
@@ -202,8 +202,6 @@ struct AddressSpaceOps {
void (*range_del)(AddressSpace *as, FlatRange *fr);
void (*log_start)(AddressSpace *as, FlatRange *fr);
void (*log_stop)(AddressSpace *as, FlatRange *fr);
- void (*ioeventfd_add)(AddressSpace *as, MemoryRegionIoeventfd *fd);
- void (*ioeventfd_del)(AddressSpace *as, MemoryRegionIoeventfd *fd);
};
#define FOR_EACH_FLAT_RANGE(var, view) \
@@ -369,37 +367,11 @@ static void as_memory_log_stop(AddressSpace *as,
FlatRange *fr)
{
}
-static void as_memory_ioeventfd_add(AddressSpace *as, MemoryRegionIoeventfd
*fd)
-{
- int r;
-
- assert(fd->match_data && int128_get64(fd->addr.size) == 4);
-
- r = kvm_set_ioeventfd_mmio_long(fd->fd, int128_get64(fd->addr.start),
- fd->data, true);
- if (r < 0) {
- abort();
- }
-}
-
-static void as_memory_ioeventfd_del(AddressSpace *as, MemoryRegionIoeventfd
*fd)
-{
- int r;
-
- r = kvm_set_ioeventfd_mmio_long(fd->fd, int128_get64(fd->addr.start),
- fd->data, false);
- if (r < 0) {
- abort();
- }
-}
-
static const AddressSpaceOps address_space_ops_memory = {
.range_add = as_memory_range_add,
.range_del = as_memory_range_del,
.log_start = as_memory_log_start,
.log_stop = as_memory_log_stop,
- .ioeventfd_add = as_memory_ioeventfd_add,
- .ioeventfd_del = as_memory_ioeventfd_del,
};
static AddressSpace address_space_memory = {
@@ -493,35 +465,9 @@ static void as_io_range_del(AddressSpace *as, FlatRange
*fr)
int128_get64(fr->addr.size));
}
-static void as_io_ioeventfd_add(AddressSpace *as, MemoryRegionIoeventfd *fd)
-{
- int r;
-
- assert(fd->match_data && int128_get64(fd->addr.size) == 2);
-
- r = kvm_set_ioeventfd_pio_word(fd->fd, int128_get64(fd->addr.start),
- fd->data, true);
- if (r < 0) {
- abort();
- }
-}
-
-static void as_io_ioeventfd_del(AddressSpace *as, MemoryRegionIoeventfd *fd)
-{
- int r;
-
- r = kvm_set_ioeventfd_pio_word(fd->fd, int128_get64(fd->addr.start),
- fd->data, false);
- if (r < 0) {
- abort();
- }
-}
-
static const AddressSpaceOps address_space_ops_io = {
.range_add = as_io_range_add,
.range_del = as_io_range_del,
- .ioeventfd_add = as_io_ioeventfd_add,
- .ioeventfd_del = as_io_ioeventfd_del,
};
static AddressSpace address_space_io = {
@@ -653,6 +599,8 @@ static void address_space_add_del_ioeventfds(AddressSpace
*as,
unsigned fds_old_nb)
{
unsigned iold, inew;
+ MemoryRegionIoeventfd *fd;
+ MemoryRegionSection section;
/* Generate a symmetric difference of the old and new fd sets, adding
* and deleting as necessary.
@@ -664,13 +612,27 @@ static void address_space_add_del_ioeventfds(AddressSpace
*as,
&& (inew == fds_new_nb
|| memory_region_ioeventfd_before(fds_old[iold],
fds_new[inew]))) {
- as->ops->ioeventfd_del(as, &fds_old[iold]);
+ fd = &fds_old[iold];
+ section = (MemoryRegionSection) {
+ .address_space = as->root,
+ .offset_within_address_space = int128_get64(fd->addr.start),
+ .size = int128_get64(fd->addr.size),
+ };
+ MEMORY_LISTENER_CALL(eventfd_del, Forward, §ion,
+ fd->match_data, fd->data, fd->fd);
++iold;
} else if (inew < fds_new_nb
&& (iold == fds_old_nb
|| memory_region_ioeventfd_before(fds_new[inew],
fds_old[iold]))) {
- as->ops->ioeventfd_add(as, &fds_new[inew]);
+ fd = &fds_new[inew];
+ section = (MemoryRegionSection) {
+ .address_space = as->root,
+ .offset_within_address_space = int128_get64(fd->addr.start),
+ .size = int128_get64(fd->addr.size),
+ };
+ MEMORY_LISTENER_CALL(eventfd_add, Reverse, §ion,
+ fd->match_data, fd->data, fd->fd);
++inew;
} else {
++iold;
diff --git a/memory.h b/memory.h
index 954dc86..84bb67c 100644
--- a/memory.h
+++ b/memory.h
@@ -185,6 +185,10 @@ struct MemoryListener {
void (*log_sync)(MemoryListener *listener, MemoryRegionSection *section);
void (*log_global_start)(MemoryListener *listener);
void (*log_global_stop)(MemoryListener *listener);
+ void (*eventfd_add)(MemoryListener *listener, MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd);
+ void (*eventfd_del)(MemoryListener *listener, MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd);
/* Lower = earlier (during add), later (during del) */
unsigned priority;
QTAILQ_ENTRY(MemoryListener) link;
diff --git a/xen-all.c b/xen-all.c
index 8cb84ef..e005b63 100644
--- a/xen-all.c
+++ b/xen-all.c
@@ -487,6 +487,18 @@ static void xen_log_global_stop(MemoryListener *listener)
{
}
+static void xen_eventfd_add(MemoryListener *listener,
+ MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+}
+
+static void xen_eventfd_del(MemoryListener *listener,
+ MemoryRegionSection *section,
+ bool match_data, uint64_t data, int fd)
+{
+}
+
static MemoryListener xen_memory_listener = {
.region_add = xen_region_add,
.region_del = xen_region_del,
@@ -495,6 +507,8 @@ static void xen_log_global_stop(MemoryListener *listener)
.log_sync = xen_log_sync,
.log_global_start = xen_log_global_start,
.log_global_stop = xen_log_global_stop,
+ .eventfd_add = xen_eventfd_add,
+ .eventfd_del = xen_eventfd_del,
.priority = 10,
};
--
1.7.9
- [Qemu-devel] [PATCH 00/10] Remove AddressSpaceOps, Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 06/10] memory: move ioeventfd ops to MemoryListener,
Avi Kivity <=
- [Qemu-devel] [PATCH 05/10] memory: code motion: move MEMORY_LISTENER_CALL(), Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 04/10] memory: switch memory listeners to a QTAILQ, Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 02/10] memory: remove memory_region_set_offset(), Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 03/10] memory: add shorthand for invoking a callback on all listeners, Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 08/10] memory: don't pass ->readable attribute to cpu_register_physical_memory_log, Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 07/10] memory: add a readonly attribute to MemoryRegionSection, Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 01/10] ioport: change portio_list not to use memory_region_set_offset(), Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 10/10] memory: drop AddressSpaceOps, Avi Kivity, 2012/02/08
- [Qemu-devel] [PATCH 09/10] memory: use a MemoryListener for core memory map updates too, Avi Kivity, 2012/02/08