From 1fe8249bbc782d28185e0e893504e8ac3a1fcaec Mon Sep 17 00:00:00 2001 From: Louis Burda Date: Mon, 23 Jan 2023 22:24:55 +0100 Subject: Move kvm to guest process and add ipc for synchronization --- test/util.c | 88 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 88 insertions(+) (limited to 'test/util.c') diff --git a/test/util.c b/test/util.c index f03a7ca..6fc38d2 100644 --- a/test/util.c +++ b/test/util.c @@ -2,6 +2,8 @@ #include "test/util.h" +#include +#include #include #include #include @@ -104,3 +106,89 @@ print_counts_raw(uint8_t *counts) } printf("\n"); } + +struct ipc * +ipc_alloc(void) +{ + pthread_mutexattr_t mutex_attr; + pthread_condattr_t cond_attr; + struct ipc *ipc; + + pthread_condattr_init(&cond_attr); + pthread_condattr_setpshared(&cond_attr, PTHREAD_PROCESS_SHARED); + + pthread_mutexattr_init(&mutex_attr); + pthread_mutexattr_setpshared(&mutex_attr, PTHREAD_PROCESS_SHARED); + + ipc = mmap(NULL, sizeof(struct ipc), PROT_READ | PROT_WRITE, + MAP_SHARED | MAP_ANONYMOUS, -1, 0); + if (ipc == MAP_FAILED) err(1, "mmap"); + + pthread_mutex_init(&ipc->lock, &mutex_attr); + + pthread_cond_init(&ipc->sig_parent, &cond_attr); + ipc->has_sig_parent = false; + + pthread_cond_init(&ipc->sig_child, &cond_attr); + ipc->has_sig_child = false; + + ipc->init = true; + + return ipc; +} + +void +ipc_free(struct ipc *ipc) +{ + if (ipc->init) { + pthread_mutex_destroy(&ipc->lock); + pthread_cond_destroy(&ipc->sig_parent); + pthread_cond_destroy(&ipc->sig_child); + ipc->init = false; + } + munmap(ipc, sizeof(ipc)); +} + +void +ipc_signal_parent(struct ipc *ipc) +{ + if (!ipc->init) errx(1, "ipc deinit"); + pthread_mutex_lock(&ipc->lock); + if (!ipc->has_sig_child) + pthread_cond_signal(&ipc->sig_child); + ipc->has_sig_child = true; + pthread_mutex_unlock(&ipc->lock); +} + +void +ipc_wait_child(struct ipc *ipc) +{ + if (!ipc->init) errx(1, "ipc deinit"); + pthread_mutex_lock(&ipc->lock); + while (!ipc->has_sig_child) + pthread_cond_wait(&ipc->sig_child, &ipc->lock); + ipc->has_sig_child = false; + pthread_mutex_unlock(&ipc->lock); +} + +void +ipc_signal_child(struct ipc *ipc) +{ + if (!ipc->init) errx(1, "ipc deinit"); + pthread_mutex_lock(&ipc->lock); + if (!ipc->has_sig_parent) + pthread_cond_signal(&ipc->sig_parent); + ipc->has_sig_parent = true; + pthread_mutex_unlock(&ipc->lock); +} + +void +ipc_wait_parent(struct ipc *ipc) +{ + if (!ipc->init) errx(1, "ipc deinit"); + pthread_mutex_lock(&ipc->lock); + while (!ipc->has_sig_parent) + pthread_cond_wait(&ipc->sig_parent, &ipc->lock); + ipc->has_sig_parent = false; + pthread_mutex_unlock(&ipc->lock); +} -- cgit v1.2.3-71-gd317