diff options
author | Michael S. Tsirkin <mst@redhat.com> | 2015-09-10 16:36:51 +0300 |
---|---|---|
committer | Michael S. Tsirkin <mst@redhat.com> | 2015-10-01 16:16:52 +0300 |
commit | c2dfc5ba3fb3a1b7278c99bfd3bf350202169434 (patch) | |
tree | 2f8db5fe1a3ed277d719eb8f354cbfb46a4586e2 | |
parent | 0cf33fb6b49a19de32859e2cdc6021334f448fb3 (diff) | |
download | hqemu-c2dfc5ba3fb3a1b7278c99bfd3bf350202169434.zip hqemu-c2dfc5ba3fb3a1b7278c99bfd3bf350202169434.tar.gz |
oslib: rework anonimous RAM allocation
At the moment we first allocate RAM, sometimes more than necessary for
alignment reasons. We then free the extra RAM.
Rework this to avoid the temporary allocation: reserve the
range by mapping it with PROT_NONE, then use just the
necessary range with MAP_FIXED.
Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Paolo Bonzini <pbonzini@redhat.com>
Acked-by: Paolo Bonzini <pbonzini@redhat.com>
-rw-r--r-- | util/oslib-posix.c | 12 |
1 files changed, 10 insertions, 2 deletions
diff --git a/util/oslib-posix.c b/util/oslib-posix.c index 3ae4987..27972d4 100644 --- a/util/oslib-posix.c +++ b/util/oslib-posix.c @@ -129,9 +129,9 @@ void *qemu_anon_ram_alloc(size_t size, uint64_t *alignment) { size_t align = QEMU_VMALLOC_ALIGN; size_t total = size + align - getpagesize(); - void *ptr = mmap(0, total, PROT_READ | PROT_WRITE, - MAP_ANONYMOUS | MAP_PRIVATE, -1, 0); + void *ptr = mmap(0, total, PROT_NONE, MAP_ANONYMOUS | MAP_PRIVATE, -1, 0); size_t offset = QEMU_ALIGN_UP((uintptr_t)ptr, align) - (uintptr_t)ptr; + void *ptr1; if (ptr == MAP_FAILED) { return NULL; @@ -140,6 +140,14 @@ void *qemu_anon_ram_alloc(size_t size, uint64_t *alignment) if (alignment) { *alignment = align; } + + ptr1 = mmap(ptr + offset, size, PROT_READ | PROT_WRITE, + MAP_FIXED | MAP_ANONYMOUS | MAP_PRIVATE, -1, 0); + if (ptr1 == MAP_FAILED) { + munmap(ptr, total); + return NULL; + } + ptr += offset; total -= offset; |