Skip to content

Commit 57ad6ab

Browse files
Steve SistareFabiano Rosas
authored andcommitted
backends/hostmem-shm: factor out allocation of "anonymous shared memory with an fd"
Let's factor it out so we can reuse it. Signed-off-by: David Hildenbrand <[email protected]> Signed-off-by: Steve Sistare <[email protected]> Reviewed-by: Peter Xu <[email protected]> Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Fabiano Rosas <[email protected]>
1 parent ed19620 commit 57ad6ab

File tree

5 files changed

+69
-43
lines changed

5 files changed

+69
-43
lines changed

backends/hostmem-shm.c

Lines changed: 4 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -25,11 +25,9 @@ struct HostMemoryBackendShm {
2525
static bool
2626
shm_backend_memory_alloc(HostMemoryBackend *backend, Error **errp)
2727
{
28-
g_autoptr(GString) shm_name = g_string_new(NULL);
2928
g_autofree char *backend_name = NULL;
3029
uint32_t ram_flags;
31-
int fd, oflag;
32-
mode_t mode;
30+
int fd;
3331

3432
if (!backend->size) {
3533
error_setg(errp, "can't create shm backend with size 0");
@@ -41,48 +39,13 @@ shm_backend_memory_alloc(HostMemoryBackend *backend, Error **errp)
4139
return false;
4240
}
4341

44-
/*
45-
* Let's use `mode = 0` because we don't want other processes to open our
46-
* memory unless we share the file descriptor with them.
47-
*/
48-
mode = 0;
49-
oflag = O_RDWR | O_CREAT | O_EXCL;
50-
backend_name = host_memory_backend_get_name(backend);
51-
52-
/*
53-
* Some operating systems allow creating anonymous POSIX shared memory
54-
* objects (e.g. FreeBSD provides the SHM_ANON constant), but this is not
55-
* defined by POSIX, so let's create a unique name.
56-
*
57-
* From Linux's shm_open(3) man-page:
58-
* For portable use, a shared memory object should be identified
59-
* by a name of the form /somename;"
60-
*/
61-
g_string_printf(shm_name, "/qemu-" FMT_pid "-shm-%s", getpid(),
62-
backend_name);
63-
64-
fd = shm_open(shm_name->str, oflag, mode);
42+
fd = qemu_shm_alloc(backend->size, errp);
6543
if (fd < 0) {
66-
error_setg_errno(errp, errno,
67-
"failed to create POSIX shared memory");
68-
return false;
69-
}
70-
71-
/*
72-
* We have the file descriptor, so we no longer need to expose the
73-
* POSIX shared memory object. However it will remain allocated as long as
74-
* there are file descriptors pointing to it.
75-
*/
76-
shm_unlink(shm_name->str);
77-
78-
if (ftruncate(fd, backend->size) == -1) {
79-
error_setg_errno(errp, errno,
80-
"failed to resize POSIX shared memory to %" PRIu64,
81-
backend->size);
82-
close(fd);
8344
return false;
8445
}
8546

47+
/* Let's do the same as memory-backend-ram,share=on would do. */
48+
backend_name = host_memory_backend_get_name(backend);
8649
ram_flags = RAM_SHARED;
8750
ram_flags |= backend->reserve ? 0 : RAM_NORESERVE;
8851

include/qemu/osdep.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -509,6 +509,7 @@ int qemu_daemon(int nochdir, int noclose);
509509
void *qemu_anon_ram_alloc(size_t size, uint64_t *align, bool shared,
510510
bool noreserve);
511511
void qemu_anon_ram_free(void *ptr, size_t size);
512+
int qemu_shm_alloc(size_t size, Error **errp);
512513

513514
#ifdef _WIN32
514515
#define HAVE_CHARDEV_SERIAL 1

meson.build

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3696,9 +3696,13 @@ libqemuutil = static_library('qemuutil',
36963696
build_by_default: false,
36973697
sources: util_ss.sources() + stub_ss.sources() + genh,
36983698
dependencies: [util_ss.dependencies(), libm, threads, glib, socket, malloc])
3699+
qemuutil_deps = [event_loop_base]
3700+
if host_os != 'windows'
3701+
qemuutil_deps += [rt]
3702+
endif
36993703
qemuutil = declare_dependency(link_with: libqemuutil,
37003704
sources: genh + version_res,
3701-
dependencies: [event_loop_base])
3705+
dependencies: qemuutil_deps)
37023706

37033707
if have_system or have_user
37043708
decodetree = generator(find_program('scripts/decodetree.py'),
@@ -4357,7 +4361,7 @@ if have_tools
43574361
subdir('contrib/elf2dmp')
43584362

43594363
executable('qemu-edid', files('qemu-edid.c', 'hw/display/edid-generate.c'),
4360-
dependencies: qemuutil,
4364+
dependencies: [qemuutil, rt],
43614365
install: true)
43624366

43634367
if have_vhost_user

util/oslib-posix.c

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -931,3 +931,55 @@ void qemu_close_all_open_fd(const int *skip, unsigned int nskip)
931931
qemu_close_all_open_fd_fallback(skip, nskip, open_max);
932932
}
933933
}
934+
935+
int qemu_shm_alloc(size_t size, Error **errp)
936+
{
937+
g_autoptr(GString) shm_name = g_string_new(NULL);
938+
int fd, oflag, cur_sequence;
939+
static int sequence;
940+
mode_t mode;
941+
942+
cur_sequence = qatomic_fetch_inc(&sequence);
943+
944+
/*
945+
* Let's use `mode = 0` because we don't want other processes to open our
946+
* memory unless we share the file descriptor with them.
947+
*/
948+
mode = 0;
949+
oflag = O_RDWR | O_CREAT | O_EXCL;
950+
951+
/*
952+
* Some operating systems allow creating anonymous POSIX shared memory
953+
* objects (e.g. FreeBSD provides the SHM_ANON constant), but this is not
954+
* defined by POSIX, so let's create a unique name.
955+
*
956+
* From Linux's shm_open(3) man-page:
957+
* For portable use, a shared memory object should be identified
958+
* by a name of the form /somename;"
959+
*/
960+
g_string_printf(shm_name, "/qemu-" FMT_pid "-shm-%d", getpid(),
961+
cur_sequence);
962+
963+
fd = shm_open(shm_name->str, oflag, mode);
964+
if (fd < 0) {
965+
error_setg_errno(errp, errno,
966+
"failed to create POSIX shared memory");
967+
return -1;
968+
}
969+
970+
/*
971+
* We have the file descriptor, so we no longer need to expose the
972+
* POSIX shared memory object. However it will remain allocated as long as
973+
* there are file descriptors pointing to it.
974+
*/
975+
shm_unlink(shm_name->str);
976+
977+
if (ftruncate(fd, size) == -1) {
978+
error_setg_errno(errp, errno,
979+
"failed to resize POSIX shared memory to %zu", size);
980+
close(fd);
981+
return -1;
982+
}
983+
984+
return fd;
985+
}

util/oslib-win32.c

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -877,3 +877,9 @@ void qemu_win32_map_free(void *ptr, HANDLE h, Error **errp)
877877
}
878878
CloseHandle(h);
879879
}
880+
881+
int qemu_shm_alloc(size_t size, Error **errp)
882+
{
883+
error_setg(errp, "Shared memory is not supported.");
884+
return -1;
885+
}

0 commit comments

Comments
 (0)