aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--exec.c37
-rw-r--r--hw/core/loader.c2
-rw-r--r--hw/display/exynos4210_fimd.c4
-rw-r--r--hw/display/framebuffer.c3
-rw-r--r--hw/misc/vfio.c4
-rw-r--r--hw/virtio/dataplane/hostmem.c2
-rw-r--r--hw/virtio/vhost.c4
-rw-r--r--hw/virtio/virtio-balloon.c2
-rw-r--r--hw/xen/xen_pt.c6
-rw-r--r--include/exec/memory.h5
-rw-r--r--include/qemu/int128.h19
-rw-r--r--kvm-all.c23
-rw-r--r--memory.c18
-rw-r--r--target-sparc/mmu_helper.c2
-rw-r--r--xen-all.c6
15 files changed, 85 insertions, 52 deletions
diff --git a/exec.c b/exec.c
index b070b436d9..77eedd8725 100644
--- a/exec.c
+++ b/exec.c
@@ -801,7 +801,7 @@ static void register_subpage(AddressSpaceDispatch *d, MemoryRegionSection *secti
MemoryRegionSection *existing = phys_page_find(d, base >> TARGET_PAGE_BITS);
MemoryRegionSection subsection = {
.offset_within_address_space = base,
- .size = TARGET_PAGE_SIZE,
+ .size = int128_make64(TARGET_PAGE_SIZE),
};
hwaddr start, end;
@@ -816,16 +816,18 @@ static void register_subpage(AddressSpaceDispatch *d, MemoryRegionSection *secti
subpage = container_of(existing->mr, subpage_t, iomem);
}
start = section->offset_within_address_space & ~TARGET_PAGE_MASK;
- end = start + section->size - 1;
+ end = start + int128_get64(section->size) - 1;
subpage_register(subpage, start, end, phys_section_add(section));
}
-static void register_multipage(AddressSpaceDispatch *d, MemoryRegionSection *section)
+static void register_multipage(AddressSpaceDispatch *d,
+ MemoryRegionSection *section)
{
hwaddr start_addr = section->offset_within_address_space;
uint16_t section_index = phys_section_add(section);
- uint64_t num_pages = section->size >> TARGET_PAGE_BITS;
+ uint64_t num_pages = int128_get64(int128_rshift(section->size,
+ TARGET_PAGE_BITS));
assert(num_pages);
phys_page_set(d, start_addr >> TARGET_PAGE_BITS, num_pages, section_index);
@@ -835,28 +837,29 @@ static void mem_add(MemoryListener *listener, MemoryRegionSection *section)
{
AddressSpaceDispatch *d = container_of(listener, AddressSpaceDispatch, listener);
MemoryRegionSection now = *section, remain = *section;
+ Int128 page_size = int128_make64(TARGET_PAGE_SIZE);
if (now.offset_within_address_space & ~TARGET_PAGE_MASK) {
uint64_t left = TARGET_PAGE_ALIGN(now.offset_within_address_space)
- now.offset_within_address_space;
- now.size = MIN(left, now.size);
+ now.size = int128_min(int128_make64(left), now.size);
register_subpage(d, &now);
} else {
- now.size = 0;
+ now.size = int128_zero();
}
- while (remain.size != now.size) {
- remain.size -= now.size;
- remain.offset_within_address_space += now.size;
- remain.offset_within_region += now.size;
+ while (int128_ne(remain.size, now.size)) {
+ remain.size = int128_sub(remain.size, now.size);
+ remain.offset_within_address_space += int128_get64(now.size);
+ remain.offset_within_region += int128_get64(now.size);
now = remain;
- if (remain.size < TARGET_PAGE_SIZE) {
+ if (int128_lt(remain.size, page_size)) {
register_subpage(d, &now);
} else if (remain.offset_within_region & ~TARGET_PAGE_MASK) {
- now.size = TARGET_PAGE_SIZE;
+ now.size = page_size;
register_subpage(d, &now);
} else {
- now.size &= -TARGET_PAGE_SIZE;
+ now.size = int128_and(now.size, int128_neg(page_size));
register_multipage(d, &now);
}
}
@@ -1666,7 +1669,7 @@ static uint16_t dummy_section(MemoryRegion *mr)
.mr = mr,
.offset_within_address_space = 0,
.offset_within_region = 0,
- .size = UINT64_MAX,
+ .size = int128_2_64(),
};
return phys_section_add(&section);
@@ -1735,14 +1738,16 @@ static void io_region_add(MemoryListener *listener,
mrio->mr = section->mr;
mrio->offset = section->offset_within_region;
iorange_init(&mrio->iorange, &memory_region_iorange_ops,
- section->offset_within_address_space, section->size);
+ section->offset_within_address_space,
+ int128_get64(section->size));
ioport_register(&mrio->iorange);
}
static void io_region_del(MemoryListener *listener,
MemoryRegionSection *section)
{
- isa_unassign_ioport(section->offset_within_address_space, section->size);
+ isa_unassign_ioport(section->offset_within_address_space,
+ int128_get64(section->size));
}
static MemoryListener core_memory_listener = {
diff --git a/hw/core/loader.c b/hw/core/loader.c
index a711145178..d56963699b 100644
--- a/hw/core/loader.c
+++ b/hw/core/loader.c
@@ -726,7 +726,7 @@ int rom_load_all(void)
addr = rom->addr;
addr += rom->romsize;
section = memory_region_find(get_system_memory(), rom->addr, 1);
- rom->isrom = section.size && memory_region_is_rom(section.mr);
+ rom->isrom = int128_nz(section.size) && memory_region_is_rom(section.mr);
}
qemu_register_reset(rom_reset, NULL);
roms_loaded = 1;
diff --git a/hw/display/exynos4210_fimd.c b/hw/display/exynos4210_fimd.c
index 6cb5016aa8..0da00a9f96 100644
--- a/hw/display/exynos4210_fimd.c
+++ b/hw/display/exynos4210_fimd.c
@@ -1133,7 +1133,7 @@ static void fimd_update_memory_section(Exynos4210fimdState *s, unsigned win)
DPRINT_TRACE("Window %u framebuffer changed: address=0x%08x, len=0x%x\n",
win, fb_start_addr, w->fb_len);
- if (w->mem_section.size != w->fb_len ||
+ if (int128_get64(w->mem_section.size) != w->fb_len ||
!memory_region_is_ram(w->mem_section.mr)) {
DPRINT_ERROR("Failed to find window %u framebuffer region\n", win);
goto error_return;
@@ -1155,7 +1155,7 @@ static void fimd_update_memory_section(Exynos4210fimdState *s, unsigned win)
error_return:
w->mem_section.mr = NULL;
- w->mem_section.size = 0;
+ w->mem_section.size = int128_zero();
w->host_fb_addr = NULL;
w->fb_len = 0;
}
diff --git a/hw/display/framebuffer.c b/hw/display/framebuffer.c
index 6be31db2b5..49c9e59043 100644
--- a/hw/display/framebuffer.c
+++ b/hw/display/framebuffer.c
@@ -54,7 +54,8 @@ void framebuffer_update_display(
src_len = src_width * rows;
mem_section = memory_region_find(address_space, base, src_len);
- if (mem_section.size != src_len || !memory_region_is_ram(mem_section.mr)) {
+ if (int128_get64(mem_section.size) != src_len ||
+ !memory_region_is_ram(mem_section.mr)) {
return;
}
mem = mem_section.mr;
diff --git a/hw/misc/vfio.c b/hw/misc/vfio.c
index 693a9ffdda..c89676b3ff 100644
--- a/hw/misc/vfio.c
+++ b/hw/misc/vfio.c
@@ -1953,7 +1953,7 @@ static void vfio_listener_region_add(MemoryListener *listener,
}
iova = TARGET_PAGE_ALIGN(section->offset_within_address_space);
- end = (section->offset_within_address_space + section->size) &
+ end = (section->offset_within_address_space + int128_get64(section->size)) &
TARGET_PAGE_MASK;
if (iova >= end) {
@@ -1997,7 +1997,7 @@ static void vfio_listener_region_del(MemoryListener *listener,
}
iova = TARGET_PAGE_ALIGN(section->offset_within_address_space);
- end = (section->offset_within_address_space + section->size) &
+ end = (section->offset_within_address_space + int128_get64(section->size)) &
TARGET_PAGE_MASK;
if (iova >= end) {
diff --git a/hw/virtio/dataplane/hostmem.c b/hw/virtio/dataplane/hostmem.c
index 37292ffd00..7e46723eb1 100644
--- a/hw/virtio/dataplane/hostmem.c
+++ b/hw/virtio/dataplane/hostmem.c
@@ -90,7 +90,7 @@ static void hostmem_append_new_region(HostMem *hostmem,
hostmem->new_regions[num] = (HostMemRegion){
.host_addr = ram_ptr + section->offset_within_region,
.guest_addr = section->offset_within_address_space,
- .size = section->size,
+ .size = int128_get64(section->size),
.readonly = section->readonly,
};
hostmem->num_new_regions++;
diff --git a/hw/virtio/vhost.c b/hw/virtio/vhost.c
index fbabf99f5e..baf84ea0bd 100644
--- a/hw/virtio/vhost.c
+++ b/hw/virtio/vhost.c
@@ -81,7 +81,7 @@ static int vhost_sync_dirty_bitmap(struct vhost_dev *dev,
return 0;
}
start_addr = section->offset_within_address_space;
- end_addr = range_get_last(start_addr, section->size);
+ end_addr = range_get_last(start_addr, int128_get64(section->size));
start_addr = MAX(first, start_addr);
end_addr = MIN(last, end_addr);
@@ -379,7 +379,7 @@ static void vhost_set_memory(MemoryListener *listener,
struct vhost_dev *dev = container_of(listener, struct vhost_dev,
memory_listener);
hwaddr start_addr = section->offset_within_address_space;
- ram_addr_t size = section->size;
+ ram_addr_t size = int128_get64(section->size);
bool log_dirty = memory_region_is_logging(section->mr);
int s = offsetof(struct vhost_memory, regions) +
(dev->mem->nregions + 1) * sizeof dev->mem->regions[0];
diff --git a/hw/virtio/virtio-balloon.c b/hw/virtio/virtio-balloon.c
index d669756a7f..a27051c2e7 100644
--- a/hw/virtio/virtio-balloon.c
+++ b/hw/virtio/virtio-balloon.c
@@ -197,7 +197,7 @@ static void virtio_balloon_handle_output(VirtIODevice *vdev, VirtQueue *vq)
/* FIXME: remove get_system_memory(), but how? */
section = memory_region_find(get_system_memory(), pa, 1);
- if (!section.size || !memory_region_is_ram(section.mr))
+ if (!int128_nz(section.size) || !memory_region_is_ram(section.mr))
continue;
/* Using memory_region_get_ram_ptr is bending the rules a bit, but
diff --git a/hw/xen/xen_pt.c b/hw/xen/xen_pt.c
index c199818dc6..c31a28a3a9 100644
--- a/hw/xen/xen_pt.c
+++ b/hw/xen/xen_pt.c
@@ -547,7 +547,7 @@ static void xen_pt_region_update(XenPCIPassthroughState *s,
struct CheckBarArgs args = {
.s = s,
.addr = sec->offset_within_address_space,
- .size = sec->size,
+ .size = int128_get64(sec->size),
.rc = false,
};
@@ -576,7 +576,7 @@ static void xen_pt_region_update(XenPCIPassthroughState *s,
if (d->io_regions[bar].type & PCI_BASE_ADDRESS_SPACE_IO) {
uint32_t guest_port = sec->offset_within_address_space;
uint32_t machine_port = s->bases[bar].access.pio_base;
- uint32_t size = sec->size;
+ uint32_t size = int128_get64(sec->size);
rc = xc_domain_ioport_mapping(xen_xc, xen_domid,
guest_port, machine_port, size,
op);
@@ -588,7 +588,7 @@ static void xen_pt_region_update(XenPCIPassthroughState *s,
pcibus_t guest_addr = sec->offset_within_address_space;
pcibus_t machine_addr = s->bases[bar].access.maddr
+ sec->offset_within_region;
- pcibus_t size = sec->size;
+ pcibus_t size = int128_get64(sec->size);
rc = xc_domain_memory_mapping(xen_xc, xen_domid,
XEN_PFN(guest_addr + XC_PAGE_SIZE - 1),
XEN_PFN(machine_addr + XC_PAGE_SIZE - 1),
diff --git a/include/exec/memory.h b/include/exec/memory.h
index c11a3f8e9c..fddc6ada27 100644
--- a/include/exec/memory.h
+++ b/include/exec/memory.h
@@ -26,6 +26,9 @@
#include "exec/ioport.h"
#include "qemu/int128.h"
+#define MAX_PHYS_ADDR_SPACE_BITS 62
+#define MAX_PHYS_ADDR (((hwaddr)1 << MAX_PHYS_ADDR_SPACE_BITS) - 1)
+
typedef struct MemoryRegionOps MemoryRegionOps;
typedef struct MemoryRegionPortio MemoryRegionPortio;
typedef struct MemoryRegionMmio MemoryRegionMmio;
@@ -185,7 +188,7 @@ struct MemoryRegionSection {
MemoryRegion *mr;
AddressSpace *address_space;
hwaddr offset_within_region;
- uint64_t size;
+ Int128 size;
hwaddr offset_within_address_space;
bool readonly;
};
diff --git a/include/qemu/int128.h b/include/qemu/int128.h
index b3864b6cd4..bfe7678a04 100644
--- a/include/qemu/int128.h
+++ b/include/qemu/int128.h
@@ -34,6 +34,25 @@ static inline Int128 int128_2_64(void)
return (Int128) { 0, 1 };
}
+static inline Int128 int128_and(Int128 a, Int128 b)
+{
+ return (Int128) { a.lo & b.lo, a.hi & b.hi };
+}
+
+static inline Int128 int128_rshift(Int128 a, int n)
+{
+ int64_t h;
+ if (!n) {
+ return a;
+ }
+ h = a.hi >> (n & 63);
+ if (n >= 64) {
+ return (Int128) { h, h >> 63 };
+ } else {
+ return (Int128) { (a.lo >> n) | (a.hi << (64 - n)), h };
+ }
+}
+
static inline Int128 int128_add(Int128 a, Int128 b)
{
Int128 r = { a.lo + b.lo, a.hi + b.hi };
diff --git a/kvm-all.c b/kvm-all.c
index 405480ef59..e6b262f04f 100644
--- a/kvm-all.c
+++ b/kvm-all.c
@@ -329,7 +329,7 @@ static void kvm_log_start(MemoryListener *listener,
int r;
r = kvm_dirty_pages_log_change(section->offset_within_address_space,
- section->size, true);
+ int128_get64(section->size), true);
if (r < 0) {
abort();
}
@@ -341,7 +341,7 @@ static void kvm_log_stop(MemoryListener *listener,
int r;
r = kvm_dirty_pages_log_change(section->offset_within_address_space,
- section->size, false);
+ int128_get64(section->size), false);
if (r < 0) {
abort();
}
@@ -379,7 +379,8 @@ static int kvm_get_dirty_pages_log_range(MemoryRegionSection *section,
unsigned int i, j;
unsigned long page_number, c;
hwaddr addr, addr1;
- unsigned int len = ((section->size / getpagesize()) + HOST_LONG_BITS - 1) / HOST_LONG_BITS;
+ unsigned int pages = int128_get64(section->size) / getpagesize();
+ unsigned int len = (pages + HOST_LONG_BITS - 1) / HOST_LONG_BITS;
unsigned long hpratio = getpagesize() / TARGET_PAGE_SIZE;
/*
@@ -422,7 +423,7 @@ static int kvm_physical_sync_dirty_bitmap(MemoryRegionSection *section)
KVMSlot *mem;
int ret = 0;
hwaddr start_addr = section->offset_within_address_space;
- hwaddr end_addr = start_addr + section->size;
+ hwaddr end_addr = start_addr + int128_get64(section->size);
d.dirty_bitmap = NULL;
while (start_addr < end_addr) {
@@ -634,7 +635,7 @@ static void kvm_set_phys_mem(MemoryRegionSection *section, bool add)
bool writeable = !mr->readonly && !mr->rom_device;
bool readonly_flag = mr->readonly || memory_region_is_romd(mr);
hwaddr start_addr = section->offset_within_address_space;
- ram_addr_t size = section->size;
+ ram_addr_t size = int128_get64(section->size);
void *ram = NULL;
unsigned delta;
@@ -832,7 +833,8 @@ static void kvm_mem_ioeventfd_add(MemoryListener *listener,
int r;
r = kvm_set_ioeventfd_mmio(fd, section->offset_within_address_space,
- data, true, section->size, match_data);
+ data, true, int128_get64(section->size),
+ match_data);
if (r < 0) {
abort();
}
@@ -847,7 +849,8 @@ static void kvm_mem_ioeventfd_del(MemoryListener *listener,
int r;
r = kvm_set_ioeventfd_mmio(fd, section->offset_within_address_space,
- data, false, section->size, match_data);
+ data, false, int128_get64(section->size),
+ match_data);
if (r < 0) {
abort();
}
@@ -862,7 +865,8 @@ static void kvm_io_ioeventfd_add(MemoryListener *listener,
int r;
r = kvm_set_ioeventfd_pio(fd, section->offset_within_address_space,
- data, true, section->size, match_data);
+ data, true, int128_get64(section->size),
+ match_data);
if (r < 0) {
abort();
}
@@ -878,7 +882,8 @@ static void kvm_io_ioeventfd_del(MemoryListener *listener,
int r;
r = kvm_set_ioeventfd_pio(fd, section->offset_within_address_space,
- data, false, section->size, match_data);
+ data, false, int128_get64(section->size),
+ match_data);
if (r < 0) {
abort();
}
diff --git a/memory.c b/memory.c
index 5cb8f4a8b2..2b197455b4 100644
--- a/memory.c
+++ b/memory.c
@@ -152,7 +152,7 @@ static bool memory_listener_match(MemoryListener *listener,
.mr = (fr)->mr, \
.address_space = (as), \
.offset_within_region = (fr)->offset_in_region, \
- .size = int128_get64((fr)->addr.size), \
+ .size = (fr)->addr.size, \
.offset_within_address_space = int128_get64((fr)->addr.start), \
.readonly = (fr)->readonly, \
}))
@@ -634,7 +634,7 @@ static void address_space_add_del_ioeventfds(AddressSpace *as,
section = (MemoryRegionSection) {
.address_space = as,
.offset_within_address_space = int128_get64(fd->addr.start),
- .size = int128_get64(fd->addr.size),
+ .size = fd->addr.size,
};
MEMORY_LISTENER_CALL(eventfd_del, Forward, &section,
fd->match_data, fd->data, fd->e);
@@ -647,7 +647,7 @@ static void address_space_add_del_ioeventfds(AddressSpace *as,
section = (MemoryRegionSection) {
.address_space = as,
.offset_within_address_space = int128_get64(fd->addr.start),
- .size = int128_get64(fd->addr.size),
+ .size = fd->addr.size,
};
MEMORY_LISTENER_CALL(eventfd_add, Reverse, &section,
fd->match_data, fd->data, fd->e);
@@ -1215,7 +1215,7 @@ static void memory_region_update_coalesced_range_as(MemoryRegion *mr, AddressSpa
section = (MemoryRegionSection) {
.address_space = as,
.offset_within_address_space = int128_get64(fr->addr.start),
- .size = int128_get64(fr->addr.size),
+ .size = fr->addr.size,
};
MEMORY_LISTENER_CALL(coalesced_mmio_del, Reverse, &section,
@@ -1506,7 +1506,7 @@ static FlatRange *address_space_lookup(AddressSpace *as, AddrRange addr)
MemoryRegionSection memory_region_find(MemoryRegion *mr,
hwaddr addr, uint64_t size)
{
- MemoryRegionSection ret = { .mr = NULL, .size = 0 };
+ MemoryRegionSection ret = { .mr = NULL };
MemoryRegion *root;
AddressSpace *as;
AddrRange range;
@@ -1536,7 +1536,7 @@ MemoryRegionSection memory_region_find(MemoryRegion *mr,
ret.offset_within_region = fr->offset_in_region;
ret.offset_within_region += int128_get64(int128_sub(range.start,
fr->addr.start));
- ret.size = int128_get64(range.size);
+ ret.size = range.size;
ret.offset_within_address_space = int128_get64(range.start);
ret.readonly = fr->readonly;
return ret;
@@ -1584,7 +1584,7 @@ static void listener_add_address_space(MemoryListener *listener,
.mr = fr->mr,
.address_space = as,
.offset_within_region = fr->offset_in_region,
- .size = int128_get64(fr->addr.size),
+ .size = fr->addr.size,
.offset_within_address_space = int128_get64(fr->addr.start),
.readonly = fr->readonly,
};
@@ -1712,7 +1712,7 @@ static void mtree_print_mr(fprintf_function mon_printf, void *f,
"-" TARGET_FMT_plx "\n",
base + mr->addr,
base + mr->addr
- + (hwaddr)int128_get64(mr->size) - 1,
+ + (hwaddr)int128_get64(int128_sub(mr->size, int128_make64(1))),
mr->priority,
mr->romd_mode ? 'R' : '-',
!mr->readonly && !(mr->rom_device && mr->romd_mode) ? 'W'
@@ -1727,7 +1727,7 @@ static void mtree_print_mr(fprintf_function mon_printf, void *f,
TARGET_FMT_plx "-" TARGET_FMT_plx " (prio %d, %c%c): %s\n",
base + mr->addr,
base + mr->addr
- + (hwaddr)int128_get64(mr->size) - 1,
+ + (hwaddr)int128_get64(int128_sub(mr->size, int128_make64(1))),
mr->priority,
mr->romd_mode ? 'R' : '-',
!mr->readonly && !(mr->rom_device && mr->romd_mode) ? 'W'
diff --git a/target-sparc/mmu_helper.c b/target-sparc/mmu_helper.c
index a9649ae064..3983c96589 100644
--- a/target-sparc/mmu_helper.c
+++ b/target-sparc/mmu_helper.c
@@ -845,7 +845,7 @@ hwaddr cpu_get_phys_page_debug(CPUSPARCState *env, target_ulong addr)
}
}
section = memory_region_find(get_system_memory(), phys_addr, 1);
- if (!section.size) {
+ if (!int128_nz(section.size)) {
return -1;
}
return phys_addr;
diff --git a/xen-all.c b/xen-all.c
index 1a1d7bbdcc..9b5735048d 100644
--- a/xen-all.c
+++ b/xen-all.c
@@ -418,7 +418,7 @@ static void xen_set_memory(struct MemoryListener *listener,
{
XenIOState *state = container_of(listener, XenIOState, memory_listener);
hwaddr start_addr = section->offset_within_address_space;
- ram_addr_t size = section->size;
+ ram_addr_t size = int128_get64(section->size);
bool log_dirty = memory_region_is_logging(section->mr);
hvmmem_type_t mem_type;
@@ -522,7 +522,7 @@ static void xen_log_start(MemoryListener *listener,
XenIOState *state = container_of(listener, XenIOState, memory_listener);
xen_sync_dirty_bitmap(state, section->offset_within_address_space,
- section->size);
+ int128_get64(section->size));
}
static void xen_log_stop(MemoryListener *listener, MemoryRegionSection *section)
@@ -539,7 +539,7 @@ static void xen_log_sync(MemoryListener *listener, MemoryRegionSection *section)
XenIOState *state = container_of(listener, XenIOState, memory_listener);
xen_sync_dirty_bitmap(state, section->offset_within_address_space,
- section->size);
+ int128_get64(section->size));
}
static void xen_log_global_start(MemoryListener *listener)