From: Avi Kivity <avi@redhat.com>
To: qemu-devel@nongnu.org
Subject: [Qemu-devel] [PATCH 13/16] Direct dispatch through MemoryRegion
Date: Mon, 2 Jan 2012 18:33:32 +0200 [thread overview]
Message-ID: <1325522015-503-14-git-send-email-avi@redhat.com> (raw)
In-Reply-To: <1325522015-503-1-git-send-email-avi@redhat.com>
Now that all mmio goes through MemoryRegions, we can convert
io_mem_opaque to be a MemoryRegion pointer, and remove the thunks
that convert from old-style CPU{Read,Write}MemoryFunc to MemoryRegionOps.
Signed-off-by: Avi Kivity <avi@redhat.com>
---
exec-all.h | 4 +-
exec-obsolete.h | 5 +-
exec.c | 40 +++++-------------
memory.c | 122 ++++++++++++++++++-------------------------------------
4 files changed, 53 insertions(+), 118 deletions(-)
diff --git a/exec-all.h b/exec-all.h
index 3d72952..51d01f2 100644
--- a/exec-all.h
+++ b/exec-all.h
@@ -302,9 +302,7 @@ extern void *tci_tb_ptr;
uint64_t io_mem_read(int index, target_phys_addr_t addr, unsigned size);
void io_mem_write(int index, target_phys_addr_t addr, uint64_t value,
unsigned size);
-extern CPUWriteMemoryFunc *_io_mem_write[IO_MEM_NB_ENTRIES][4];
-extern CPUReadMemoryFunc *_io_mem_read[IO_MEM_NB_ENTRIES][4];
-extern void *io_mem_opaque[IO_MEM_NB_ENTRIES];
+extern struct MemoryRegion *io_mem_region[IO_MEM_NB_ENTRIES];
void tlb_fill(CPUState *env1, target_ulong addr, int is_write, int mmu_idx,
void *retaddr);
diff --git a/exec-obsolete.h b/exec-obsolete.h
index e08e750..f8af27e 100644
--- a/exec-obsolete.h
+++ b/exec-obsolete.h
@@ -31,9 +31,8 @@ ram_addr_t qemu_ram_alloc(ram_addr_t size, MemoryRegion *mr);
void qemu_ram_free(ram_addr_t addr);
void qemu_ram_free_from_ptr(ram_addr_t addr);
-int cpu_register_io_memory(CPUReadMemoryFunc * const *mem_read,
- CPUWriteMemoryFunc * const *mem_write,
- void *opaque);
+struct MemoryRegion;
+int cpu_register_io_memory(MemoryRegion *mr);
void cpu_unregister_io_memory(int table_address);
struct MemoryRegionSection;
diff --git a/exec.c b/exec.c
index fc1dcb7..b443dbb 100644
--- a/exec.c
+++ b/exec.c
@@ -208,9 +208,7 @@
static void memory_map_init(void);
/* io memory support */
-CPUWriteMemoryFunc *_io_mem_write[IO_MEM_NB_ENTRIES][4];
-CPUReadMemoryFunc *_io_mem_read[IO_MEM_NB_ENTRIES][4];
-void *io_mem_opaque[IO_MEM_NB_ENTRIES];
+MemoryRegion *io_mem_region[IO_MEM_NB_ENTRIES];
static char io_mem_used[IO_MEM_NB_ENTRIES];
static MemoryRegion io_mem_watch;
#endif
@@ -2563,8 +2561,10 @@ void cpu_register_physical_memory_log(MemoryRegionSection *section,
&p->phys_offset, orig_memory,
p->region_offset);
} else {
- subpage = io_mem_opaque[(orig_memory & ~TARGET_PAGE_MASK)
- >> IO_MEM_SHIFT];
+ MemoryRegion *mr
+ = io_mem_region[(orig_memory & ~TARGET_PAGE_MASK)
+ >> IO_MEM_SHIFT];
+ subpage = container_of(mr, subpage_t, iomem);
}
subpage_register(subpage, start_addr2, end_addr2, phys_offset,
region_offset);
@@ -3427,13 +3427,8 @@ static int get_free_io_mem_idx(void)
modified. If it is zero, a new io zone is allocated. The return
value can be used with cpu_register_physical_memory(). (-1) is
returned if error. */
-static int cpu_register_io_memory_fixed(int io_index,
- CPUReadMemoryFunc * const *mem_read,
- CPUWriteMemoryFunc * const *mem_write,
- void *opaque)
+static int cpu_register_io_memory_fixed(int io_index, MemoryRegion *mr)
{
- int i;
-
if (io_index <= 0) {
io_index = get_free_io_mem_idx();
if (io_index == -1)
@@ -3444,36 +3439,21 @@ static int cpu_register_io_memory_fixed(int io_index,
return -1;
}
- for (i = 0; i < 3; ++i) {
- assert(mem_read[i]);
- _io_mem_read[io_index][i] = mem_read[i];
- }
- for (i = 0; i < 3; ++i) {
- assert(mem_write[i]);
- _io_mem_write[io_index][i] = mem_write[i];
- }
- io_mem_opaque[io_index] = opaque;
+ io_mem_region[io_index] = mr;
return (io_index << IO_MEM_SHIFT);
}
-int cpu_register_io_memory(CPUReadMemoryFunc * const *mem_read,
- CPUWriteMemoryFunc * const *mem_write,
- void *opaque)
+int cpu_register_io_memory(MemoryRegion *mr)
{
- return cpu_register_io_memory_fixed(0, mem_read, mem_write, opaque);
+ return cpu_register_io_memory_fixed(0, mr);
}
void cpu_unregister_io_memory(int io_table_address)
{
- int i;
int io_index = io_table_address >> IO_MEM_SHIFT;
- for (i=0;i < 3; i++) {
- _io_mem_read[io_index][i] = NULL;
- _io_mem_write[io_index][i] = NULL;
- }
- io_mem_opaque[io_index] = NULL;
+ io_mem_region[io_index] = NULL;
io_mem_used[io_index] = 0;
}
diff --git a/memory.c b/memory.c
index e34bc65..25b36ff 100644
--- a/memory.c
+++ b/memory.c
@@ -906,11 +906,10 @@ static bool memory_region_access_valid(MemoryRegion *mr,
return true;
}
-static uint32_t memory_region_read_thunk_n(void *_mr,
- target_phys_addr_t addr,
- unsigned size)
+static uint64_t memory_region_dispatch_read1(MemoryRegion *mr,
+ target_phys_addr_t addr,
+ unsigned size)
{
- MemoryRegion *mr = _mr;
uint64_t data = 0;
if (!memory_region_access_valid(mr, addr, size, false)) {
@@ -930,17 +929,45 @@ static uint32_t memory_region_read_thunk_n(void *_mr,
return data;
}
-static void memory_region_write_thunk_n(void *_mr,
- target_phys_addr_t addr,
- unsigned size,
- uint64_t data)
+static void adjust_endianness(MemoryRegion *mr, uint64_t *data, unsigned size)
{
- MemoryRegion *mr = _mr;
+ if (memory_region_wrong_endianness(mr)) {
+ switch (size) {
+ case 1:
+ break;
+ case 2:
+ *data = bswap16(*data);
+ break;
+ case 4:
+ *data = bswap32(*data);
+ default:
+ abort();
+ }
+ }
+}
+
+static uint64_t memory_region_dispatch_read(MemoryRegion *mr,
+ target_phys_addr_t addr,
+ unsigned size)
+{
+ uint64_t ret;
+
+ ret = memory_region_dispatch_read1(mr, addr, size);
+ adjust_endianness(mr, &ret, size);
+ return ret;
+}
+static void memory_region_dispatch_write(MemoryRegion *mr,
+ target_phys_addr_t addr,
+ uint64_t data,
+ unsigned size)
+{
if (!memory_region_access_valid(mr, addr, size, true)) {
return; /* FIXME: better signalling */
}
+ adjust_endianness(mr, &data, size);
+
if (!mr->ops->write) {
mr->ops->old_mmio.write[bitops_ffsl(size)](mr->opaque, addr, data);
return;
@@ -953,69 +980,6 @@ static void memory_region_write_thunk_n(void *_mr,
memory_region_write_accessor, mr);
}
-static uint32_t memory_region_read_thunk_b(void *mr, target_phys_addr_t addr)
-{
- return memory_region_read_thunk_n(mr, addr, 1);
-}
-
-static uint32_t memory_region_read_thunk_w(void *mr, target_phys_addr_t addr)
-{
- uint32_t data;
-
- data = memory_region_read_thunk_n(mr, addr, 2);
- if (memory_region_wrong_endianness(mr)) {
- data = bswap16(data);
- }
- return data;
-}
-
-static uint32_t memory_region_read_thunk_l(void *mr, target_phys_addr_t addr)
-{
- uint32_t data;
-
- data = memory_region_read_thunk_n(mr, addr, 4);
- if (memory_region_wrong_endianness(mr)) {
- data = bswap32(data);
- }
- return data;
-}
-
-static void memory_region_write_thunk_b(void *mr, target_phys_addr_t addr,
- uint32_t data)
-{
- memory_region_write_thunk_n(mr, addr, 1, data);
-}
-
-static void memory_region_write_thunk_w(void *mr, target_phys_addr_t addr,
- uint32_t data)
-{
- if (memory_region_wrong_endianness(mr)) {
- data = bswap16(data);
- }
- memory_region_write_thunk_n(mr, addr, 2, data);
-}
-
-static void memory_region_write_thunk_l(void *mr, target_phys_addr_t addr,
- uint32_t data)
-{
- if (memory_region_wrong_endianness(mr)) {
- data = bswap32(data);
- }
- memory_region_write_thunk_n(mr, addr, 4, data);
-}
-
-static CPUReadMemoryFunc * const memory_region_read_thunk[] = {
- memory_region_read_thunk_b,
- memory_region_read_thunk_w,
- memory_region_read_thunk_l,
-};
-
-static CPUWriteMemoryFunc * const memory_region_write_thunk[] = {
- memory_region_write_thunk_b,
- memory_region_write_thunk_w,
- memory_region_write_thunk_l,
-};
-
void memory_region_init_io(MemoryRegion *mr,
const MemoryRegionOps *ops,
void *opaque,
@@ -1027,9 +991,7 @@ void memory_region_init_io(MemoryRegion *mr,
mr->opaque = opaque;
mr->terminates = true;
mr->destructor = memory_region_destructor_iomem;
- mr->ram_addr = cpu_register_io_memory(memory_region_read_thunk,
- memory_region_write_thunk,
- mr);
+ mr->ram_addr = cpu_register_io_memory(mr);
}
void memory_region_init_ram(MemoryRegion *mr,
@@ -1078,9 +1040,7 @@ void memory_region_init_rom_device(MemoryRegion *mr,
mr->terminates = true;
mr->destructor = memory_region_destructor_rom_device;
mr->ram_addr = qemu_ram_alloc(size, mr);
- mr->ram_addr |= cpu_register_io_memory(memory_region_read_thunk,
- memory_region_write_thunk,
- mr);
+ mr->ram_addr |= cpu_register_io_memory(mr);
mr->ram_addr |= IO_MEM_ROMD;
}
@@ -1552,15 +1512,13 @@ void set_system_io_map(MemoryRegion *mr)
uint64_t io_mem_read(int io_index, target_phys_addr_t addr, unsigned size)
{
- return _io_mem_read[io_index][bitops_ffsl(size)](io_mem_opaque[io_index],
- addr);
+ return memory_region_dispatch_read(io_mem_region[io_index], addr, size);
}
void io_mem_write(int io_index, target_phys_addr_t addr,
uint64_t val, unsigned size)
{
- _io_mem_write[io_index][bitops_ffsl(size)](io_mem_opaque[io_index],
- addr, val);
+ memory_region_dispatch_write(io_mem_region[io_index], addr, val, size);
}
typedef struct MemoryRegionList MemoryRegionList;
--
1.7.7.1
next prev parent reply other threads:[~2012-01-02 16:34 UTC|newest]
Thread overview: 26+ messages / expand[flat|nested] mbox.gz Atom feed top
2012-01-02 16:33 [Qemu-devel] [PATCH 00/16] Kill old-style I/O dispatch Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 01/16] memory: move endianness compensation to memory core Avi Kivity
2012-01-05 18:26 ` Andreas Färber
2012-01-07 7:52 ` Andreas Färber
2012-01-02 16:33 ` [Qemu-devel] [PATCH 02/16] exec: make phys_page_find() return a temporary Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 03/16] memory: move mmio access to functions Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 04/16] memory: remove MemoryRegion::backend_registered Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 05/16] Fix wrong region_offset when overlaying a page with another Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 06/16] Avoid range comparisons on io index types Avi Kivity
2012-01-02 21:58 ` Richard Henderson
2012-01-03 8:46 ` Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 07/16] Uninline get_page_addr_code() Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 08/16] Convert IO_MEM_{RAM, ROM, UNASSIGNED, NOTDIRTY} to MemoryRegions Avi Kivity
2012-01-02 22:16 ` Richard Henderson
2012-01-03 8:54 ` Avi Kivity
2012-01-06 8:31 ` Stefan Hajnoczi
2012-01-02 16:33 ` [Qemu-devel] [PATCH 09/16] Switch cpu_register_physical_memory_log() to use MemoryRegions Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 10/16] Convert the subpage wrapper to be a MemoryRegion Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 11/16] Convert IO_MEM_SUBPAGE_RAM " Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 12/16] Convert io_mem_watch " Avi Kivity
2012-01-02 16:33 ` Avi Kivity [this message]
2012-01-07 7:55 ` [Qemu-devel] [PATCH 13/16] Direct dispatch through MemoryRegion Andreas Färber
2012-01-02 16:33 ` [Qemu-devel] [PATCH 14/16] Remove IO_MEM_SUBPAGE Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 15/16] Drop IO_MEM_ROMD Avi Kivity
2012-01-02 16:33 ` [Qemu-devel] [PATCH 16/16] Remove IO_MEM_SHIFT Avi Kivity
2012-01-02 22:36 ` [Qemu-devel] [PATCH 00/16] Kill old-style I/O dispatch Richard Henderson
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=1325522015-503-14-git-send-email-avi@redhat.com \
--to=avi@redhat.com \
--cc=qemu-devel@nongnu.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).