mirror of https://github.com/xemu-project/xemu.git
qtest: add qtest_add_abrt_handler()
Allow a test to add abort handlers, use GHook for all handlers. There is currently no way to remove a handler, but it could be later added if needed. Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com> Reviewed-by: Claudio Fontana <claudio.fontana@huawei.com>
This commit is contained in:
parent
43b11a91dd
commit
063c23d909
|
@ -48,6 +48,7 @@ struct QTestState
|
||||||
pid_t qemu_pid; /* our child QEMU process */
|
pid_t qemu_pid; /* our child QEMU process */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static GHookList abrt_hooks;
|
||||||
static GList *qtest_instances;
|
static GList *qtest_instances;
|
||||||
static struct sigaction sigact_old;
|
static struct sigaction sigact_old;
|
||||||
|
|
||||||
|
@ -111,10 +112,7 @@ static void kill_qemu(QTestState *s)
|
||||||
|
|
||||||
static void sigabrt_handler(int signo)
|
static void sigabrt_handler(int signo)
|
||||||
{
|
{
|
||||||
GList *elem;
|
g_hook_list_invoke(&abrt_hooks, FALSE);
|
||||||
for (elem = qtest_instances; elem; elem = elem->next) {
|
|
||||||
kill_qemu(elem->data);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void setup_sigabrt_handler(void)
|
static void setup_sigabrt_handler(void)
|
||||||
|
@ -135,6 +133,23 @@ static void cleanup_sigabrt_handler(void)
|
||||||
sigaction(SIGABRT, &sigact_old, NULL);
|
sigaction(SIGABRT, &sigact_old, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void qtest_add_abrt_handler(void (*fn), const void *data)
|
||||||
|
{
|
||||||
|
GHook *hook;
|
||||||
|
|
||||||
|
/* Only install SIGABRT handler once */
|
||||||
|
if (!abrt_hooks.is_setup) {
|
||||||
|
g_hook_list_init(&abrt_hooks, sizeof(GHook));
|
||||||
|
setup_sigabrt_handler();
|
||||||
|
}
|
||||||
|
|
||||||
|
hook = g_hook_alloc(&abrt_hooks);
|
||||||
|
hook->func = fn;
|
||||||
|
hook->data = (void *)data;
|
||||||
|
|
||||||
|
g_hook_prepend(&abrt_hooks, hook);
|
||||||
|
}
|
||||||
|
|
||||||
QTestState *qtest_init(const char *extra_args)
|
QTestState *qtest_init(const char *extra_args)
|
||||||
{
|
{
|
||||||
QTestState *s;
|
QTestState *s;
|
||||||
|
@ -155,12 +170,7 @@ QTestState *qtest_init(const char *extra_args)
|
||||||
sock = init_socket(socket_path);
|
sock = init_socket(socket_path);
|
||||||
qmpsock = init_socket(qmp_socket_path);
|
qmpsock = init_socket(qmp_socket_path);
|
||||||
|
|
||||||
/* Only install SIGABRT handler once */
|
qtest_add_abrt_handler(kill_qemu, s);
|
||||||
if (!qtest_instances) {
|
|
||||||
setup_sigabrt_handler();
|
|
||||||
}
|
|
||||||
|
|
||||||
qtest_instances = g_list_prepend(qtest_instances, s);
|
|
||||||
|
|
||||||
s->qemu_pid = fork();
|
s->qemu_pid = fork();
|
||||||
if (s->qemu_pid == 0) {
|
if (s->qemu_pid == 0) {
|
||||||
|
@ -208,13 +218,14 @@ QTestState *qtest_init(const char *extra_args)
|
||||||
|
|
||||||
void qtest_quit(QTestState *s)
|
void qtest_quit(QTestState *s)
|
||||||
{
|
{
|
||||||
|
qtest_instances = g_list_remove(qtest_instances, s);
|
||||||
|
g_hook_destroy_link(&abrt_hooks, g_hook_find_data(&abrt_hooks, TRUE, s));
|
||||||
|
|
||||||
/* Uninstall SIGABRT handler on last instance */
|
/* Uninstall SIGABRT handler on last instance */
|
||||||
if (qtest_instances && !qtest_instances->next) {
|
if (!qtest_instances) {
|
||||||
cleanup_sigabrt_handler();
|
cleanup_sigabrt_handler();
|
||||||
}
|
}
|
||||||
|
|
||||||
qtest_instances = g_list_remove(qtest_instances, s);
|
|
||||||
|
|
||||||
kill_qemu(s);
|
kill_qemu(s);
|
||||||
close(s->fd);
|
close(s->fd);
|
||||||
close(s->qmp_fd);
|
close(s->qmp_fd);
|
||||||
|
|
|
@ -450,6 +450,8 @@ void qtest_add_data_func(const char *str, const void *data, void (*fn));
|
||||||
g_free(path); \
|
g_free(path); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
|
void qtest_add_abrt_handler(void (*fn), const void *data);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* qtest_start:
|
* qtest_start:
|
||||||
* @args: other arguments to pass to QEMU
|
* @args: other arguments to pass to QEMU
|
||||||
|
|
Loading…
Reference in New Issue