[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[PULL 20/42] tests/qtest: defer connection
From: |
Fabiano Rosas |
Subject: |
[PULL 20/42] tests/qtest: defer connection |
Date: |
Wed, 29 Jan 2025 13:00:37 -0300 |
From: Steve Sistare <steven.sistare@oracle.com>
Add an option to defer making the connecting to the monitor and qtest
sockets when calling qtest_init_with_env. The client makes the connection
later by calling qtest_connect and qtest_qmp_handshake.
Signed-off-by: Steve Sistare <steven.sistare@oracle.com>
Reviewed-by: Peter Xu <peterx@redhat.com>
Link:
1736967650-129648-20-git-send-email-steven.sistare@oracle.com">https://lore.kernel.org/r/1736967650-129648-20-git-send-email-steven.sistare@oracle.com
[plumb capabilities list into qtest_qmp_handshake]
Signed-off-by: Fabiano Rosas <farosas@suse.de>
---
tests/qtest/libqtest.c | 99 ++++++++++++++++++++-----------
tests/qtest/libqtest.h | 24 +++++++-
tests/qtest/migration/framework.c | 7 ++-
3 files changed, 90 insertions(+), 40 deletions(-)
diff --git a/tests/qtest/libqtest.c b/tests/qtest/libqtest.c
index a1e105f27f..fbb51e3e55 100644
--- a/tests/qtest/libqtest.c
+++ b/tests/qtest/libqtest.c
@@ -75,6 +75,8 @@ struct QTestState
{
int fd;
int qmp_fd;
+ int sock;
+ int qmpsock;
pid_t qemu_pid; /* our child QEMU process */
int wstatus;
#ifdef _WIN32
@@ -458,18 +460,19 @@ static QTestState *G_GNUC_PRINTF(2, 3)
qtest_spawn_qemu(const char *qemu_bin,
return s;
}
+static char *qtest_socket_path(const char *suffix)
+{
+ return g_strdup_printf("%s/qtest-%d.%s", g_get_tmp_dir(), getpid(),
suffix);
+}
+
static QTestState *qtest_init_internal(const char *qemu_bin,
- const char *extra_args)
+ const char *extra_args,
+ bool do_connect)
{
QTestState *s;
int sock, qmpsock, i;
- gchar *socket_path;
- gchar *qmp_socket_path;
-
- socket_path = g_strdup_printf("%s/qtest-%d.sock",
- g_get_tmp_dir(), getpid());
- qmp_socket_path = g_strdup_printf("%s/qtest-%d.qmp",
- g_get_tmp_dir(), getpid());
+ g_autofree gchar *socket_path = qtest_socket_path("sock");
+ g_autofree gchar *qmp_socket_path = qtest_socket_path("qmp");
/*
* It's possible that if an earlier test run crashed it might
@@ -501,22 +504,19 @@ static QTestState *qtest_init_internal(const char
*qemu_bin,
qtest_client_set_rx_handler(s, qtest_client_socket_recv_line);
qtest_client_set_tx_handler(s, qtest_client_socket_send);
- s->fd = socket_accept(sock);
- if (s->fd >= 0) {
- s->qmp_fd = socket_accept(qmpsock);
- }
- unlink(socket_path);
- unlink(qmp_socket_path);
- g_free(socket_path);
- g_free(qmp_socket_path);
-
- g_assert(s->fd >= 0 && s->qmp_fd >= 0);
-
s->rx = g_string_new("");
for (i = 0; i < MAX_IRQ; i++) {
s->irq_level[i] = false;
}
+ s->fd = -1;
+ s->qmp_fd = -1;
+ s->sock = sock;
+ s->qmpsock = qmpsock;
+ if (do_connect) {
+ qtest_connect(s);
+ }
+
/*
* Stopping QEMU for debugging is not supported on Windows.
*
@@ -531,28 +531,38 @@ static QTestState *qtest_init_internal(const char
*qemu_bin,
}
#endif
+ return s;
+}
+
+void qtest_connect(QTestState *s)
+{
+ g_autofree gchar *socket_path = qtest_socket_path("sock");
+ g_autofree gchar *qmp_socket_path = qtest_socket_path("qmp");
+
+ g_assert(s->sock >= 0 && s->qmpsock >= 0);
+ s->fd = socket_accept(s->sock);
+ if (s->fd >= 0) {
+ s->qmp_fd = socket_accept(s->qmpsock);
+ }
+ unlink(socket_path);
+ unlink(qmp_socket_path);
+ g_assert(s->fd >= 0 && s->qmp_fd >= 0);
+ s->sock = s->qmpsock = -1;
/* ask endianness of the target */
-
s->big_endian = qtest_query_target_endianness(s);
-
- return s;
}
QTestState *qtest_init_without_qmp_handshake(const char *extra_args)
{
- return qtest_init_internal(qtest_qemu_binary(NULL), extra_args);
+ return qtest_init_internal(qtest_qemu_binary(NULL), extra_args, true);
}
-QTestState *qtest_init_with_env_and_capabilities(const char *var,
- const char *extra_args,
- QList *capabilities)
+void qtest_qmp_handshake(QTestState *s, QList *capabilities)
{
- QTestState *s = qtest_init_internal(qtest_qemu_binary(var), extra_args);
- QDict *greeting;
-
/* Read the QMP greeting and then do the handshake */
- greeting = qtest_qmp_receive(s);
+ QDict *greeting = qtest_qmp_receive(s);
qobject_unref(greeting);
+
if (capabilities) {
qtest_qmp_assert_success(s,
"{ 'execute': 'qmp_capabilities', "
@@ -561,18 +571,37 @@ QTestState *qtest_init_with_env_and_capabilities(const
char *var,
} else {
qtest_qmp_assert_success(s, "{ 'execute': 'qmp_capabilities' }");
}
+}
+QTestState *qtest_init_with_env_and_capabilities(const char *var,
+ const char *extra_args,
+ QList *capabilities,
+ bool do_connect)
+{
+ QTestState *s = qtest_init_internal(qtest_qemu_binary(var), extra_args,
+ do_connect);
+
+ if (do_connect) {
+ qtest_qmp_handshake(s, capabilities);
+ } else {
+ /*
+ * If the connection is delayed, the capabilities must be set
+ * at that moment.
+ */
+ assert(!capabilities);
+ }
return s;
}
-QTestState *qtest_init_with_env(const char *var, const char *extra_args)
+QTestState *qtest_init_with_env(const char *var, const char *extra_args,
+ bool do_connect)
{
- return qtest_init_with_env_and_capabilities(var, extra_args, NULL);
+ return qtest_init_with_env_and_capabilities(var, extra_args, NULL, true);
}
QTestState *qtest_init(const char *extra_args)
{
- return qtest_init_with_env(NULL, extra_args);
+ return qtest_init_with_env(NULL, extra_args, true);
}
QTestState *qtest_vinitf(const char *fmt, va_list ap)
@@ -1580,7 +1609,7 @@ static struct MachInfo *qtest_get_machines(const char
*var)
silence_spawn_log = !g_test_verbose();
- qts = qtest_init_with_env(qemu_var, "-machine none");
+ qts = qtest_init_with_env(qemu_var, "-machine none", true);
response = qtest_qmp(qts, "{ 'execute': 'query-machines' }");
g_assert(response);
list = qdict_get_qlist(response, "return");
@@ -1635,7 +1664,7 @@ static struct CpuModel *qtest_get_cpu_models(void)
silence_spawn_log = !g_test_verbose();
- qts = qtest_init_with_env(NULL, "-machine none");
+ qts = qtest_init_with_env(NULL, "-machine none", true);
response = qtest_qmp(qts, "{ 'execute': 'query-cpu-definitions' }");
g_assert(response);
list = qdict_get_qlist(response, "return");
diff --git a/tests/qtest/libqtest.h b/tests/qtest/libqtest.h
index ce88d23eae..29f123e281 100644
--- a/tests/qtest/libqtest.h
+++ b/tests/qtest/libqtest.h
@@ -61,13 +61,15 @@ QTestState *qtest_init(const char *extra_args);
* @var: Environment variable from where to take the QEMU binary
* @extra_args: Other arguments to pass to QEMU. CAUTION: these
* arguments are subject to word splitting and shell evaluation.
+ * @do_connect: connect to qemu monitor and qtest socket.
*
* Like qtest_init(), but use a different environment variable for the
* QEMU binary.
*
* Returns: #QTestState instance.
*/
-QTestState *qtest_init_with_env(const char *var, const char *extra_args);
+QTestState *qtest_init_with_env(const char *var, const char *extra_args,
+ bool do_connect);
/**
* qtest_init_with_env_and_capabilities:
@@ -75,6 +77,7 @@ QTestState *qtest_init_with_env(const char *var, const char
*extra_args);
* @extra_args: Other arguments to pass to QEMU. CAUTION: these
* arguments are subject to word splitting and shell evaluation.
* @capabilities: list of QMP capabilities (strings) to enable
+ * @do_connect: connect to qemu monitor and qtest socket.
*
* Like qtest_init_with_env(), but enable specified capabilities during
* hadshake.
@@ -83,7 +86,8 @@ QTestState *qtest_init_with_env(const char *var, const char
*extra_args);
*/
QTestState *qtest_init_with_env_and_capabilities(const char *var,
const char *extra_args,
- QList *capabilities);
+ QList *capabilities,
+ bool do_connect);
/**
* qtest_init_without_qmp_handshake:
@@ -94,6 +98,22 @@ QTestState *qtest_init_with_env_and_capabilities(const char
*var,
*/
QTestState *qtest_init_without_qmp_handshake(const char *extra_args);
+/**
+ * qtest_connect
+ * @s: #QTestState instance to connect
+ * Connect to qemu monitor and qtest socket, after skipping them in
+ * qtest_init_with_env. Does not handshake with the monitor.
+ */
+void qtest_connect(QTestState *s);
+
+/**
+ * qtest_qmp_handshake:
+ * @s: #QTestState instance to operate on.
+ * @capabilities: list of QMP capabilities (strings) to enable
+ * Perform handshake after connecting to qemu monitor.
+ */
+void qtest_qmp_handshake(QTestState *s, QList *capabilities);
+
/**
* qtest_init_with_serial:
* @extra_args: other arguments to pass to QEMU. CAUTION: these
diff --git a/tests/qtest/migration/framework.c
b/tests/qtest/migration/framework.c
index 758e14abab..f7add75ed5 100644
--- a/tests/qtest/migration/framework.c
+++ b/tests/qtest/migration/framework.c
@@ -196,9 +196,10 @@ static void cleanup(const char *filename)
static QList *migrate_start_get_qmp_capabilities(const MigrateStart *args)
{
- QList *capabilities = qlist_new();
+ QList *capabilities = NULL;
if (args->oob) {
+ capabilities = qlist_new();
qlist_append_str(capabilities, "oob");
}
return capabilities;
@@ -333,7 +334,7 @@ int migrate_start(QTestState **from, QTestState **to, const
char *uri,
ignore_stderr);
if (!args->only_target) {
*from = qtest_init_with_env_and_capabilities(QEMU_ENV_SRC, cmd_source,
- capabilities);
+ capabilities, true);
qtest_qmp_set_event_callback(*from,
migrate_watch_for_events,
&src_state);
@@ -354,7 +355,7 @@ int migrate_start(QTestState **from, QTestState **to, const
char *uri,
args->opts_target ? args->opts_target : "",
ignore_stderr);
*to = qtest_init_with_env_and_capabilities(QEMU_ENV_DST, cmd_target,
- capabilities);
+ capabilities, true);
qtest_qmp_set_event_callback(*to,
migrate_watch_for_events,
&dst_state);
--
2.35.3
- [PULL 00/42] Migration patches for 2025-01-29, Fabiano Rosas, 2025/01/29
- [PULL 04/42] physmem: qemu_ram_alloc_from_fd extensions, Fabiano Rosas, 2025/01/29
- [PULL 05/42] physmem: fd-based shared memory, Fabiano Rosas, 2025/01/29
- [PULL 07/42] machine: aux-ram-share option, Fabiano Rosas, 2025/01/29
- [PULL 10/42] hostmem-memfd: preserve for cpr, Fabiano Rosas, 2025/01/29
- [PULL 02/42] backends/hostmem-shm: factor out allocation of "anonymous shared memory with an fd", Fabiano Rosas, 2025/01/29
- [PULL 12/42] migration: enhance migrate_uri_parse, Fabiano Rosas, 2025/01/29
- [PULL 15/42] migration: VMSTATE_FD, Fabiano Rosas, 2025/01/29
- [PULL 20/42] tests/qtest: defer connection,
Fabiano Rosas <=
- [PULL 22/42] tests/qtest: enhance migration channels, Fabiano Rosas, 2025/01/29
- [PULL 23/42] tests/qtest: assert qmp connected, Fabiano Rosas, 2025/01/29
- [PULL 26/42] migration: Remove postcopy implications in should_send_vmdesc(), Fabiano Rosas, 2025/01/29
- [PULL 30/42] migration: Drop inactivate_disk param in qemu_savevm_state_complete*, Fabiano Rosas, 2025/01/29
- [PULL 33/42] migration: Adjust locking in migration_maybe_pause(), Fabiano Rosas, 2025/01/29
- [PULL 03/42] physmem: fix qemu_ram_alloc_from_fd size calculation, Fabiano Rosas, 2025/01/29
- [PULL 06/42] memory: add RAM_PRIVATE, Fabiano Rosas, 2025/01/29
- [PULL 11/42] hostmem-shm: preserve for cpr, Fabiano Rosas, 2025/01/29
- [PULL 21/42] migration-test: defer connection, Fabiano Rosas, 2025/01/29
- [PULL 14/42] migration: SCM_RIGHTS for QEMUFile, Fabiano Rosas, 2025/01/29