From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077371668436.476564658282; Mon, 26 Mar 2018 08:16:11 -0700 (PDT) Received: from localhost ([::1]:57308 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tr0-0002e5-NC for importer@patchew.org; Mon, 26 Mar 2018 11:16:10 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54814) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkg-00057A-LS for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:40 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tke-0002ij-Hq for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:38 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:38270 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tke-0002fO-CR for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:36 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 535527705F; Mon, 26 Mar 2018 15:09:28 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id DA3567C55; Mon, 26 Mar 2018 15:09:27 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:39 +0200 Message-Id: <20180326150916.9602-2-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:09:28 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:09:28 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 01/38] HACK: add back OOB X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" This adds back temporarily OOB for the sake of automated testing and for the rest of the patches that are based upon OOB, as well as a few pending fixes squashed together. Revert "qapi: Force UTF8 encoding when parsing qapi files" This reverts commit 39615354fc07af34e04ab5efb5b6d478b0d24e32. Revert "Revert "monitor: enable IO thread for (qmp & !mux) typed"" This reverts commit a4f90923b520f1dc0a768634877eb412e5052c26. Revert "Revert "tests: qmp-test: verify command batching"" This reverts commit cc797607c03722871a030f8a64d800a8df93b5b2. Revert "Revert "tests: qmp-test: add oob test"" This reverts commit 4fd78ad7934bbd002da8ea420ce16f73ad23f417. monitor: fix expected qmp_capabilities error description regression Fix regression introduced in commit cf869d53172920536a14180a83292b240e9d054= 5: Before: {"execute":"foo"} {"error": {"class": "CommandNotFound", "desc": "Expecting capabilities nego= tiation with 'qmp_capabilities'"}} After: {"execute":"foo"} {"error": {"class": "CommandNotFound", "desc": "The command foo has not bee= n found"}} Because qmp_cmd_oob_check() happens before monitor_qmp_dispatch_one(). Move the error manipulation code to monitor_qmp_respond() instead. migration: fix pfd leak Fix leak spotted by ASAN: Direct leak of 16 byte(s) in 1 object(s) allocated from: #0 0x7fe1abb80a38 in __interceptor_calloc (/lib64/libasan.so.4+0xdea38) #1 0x7fe1aaf1bf75 in g_malloc0 ../glib/gmem.c:124 #2 0x7fe1aaf1c249 in g_malloc0_n ../glib/gmem.c:355 #3 0x55f4841cfaa9 in postcopy_ram_fault_thread /home/elmarco/src/qemu/m= igration/postcopy-ram.c:596 #4 0x55f48479447b in qemu_thread_start /home/elmarco/src/qemu/util/qemu= -thread-posix.c:504 #5 0x7fe1a043550a in start_thread (/lib64/libpthread.so.0+0x750a) Regression introduced with commit 00fa4fc85b00f1a8a810068d158a7a66e88658eb. Signed-off-by: Marc-Andr=C3=A9 Lureau --- migration/postcopy-ram.c | 1 + monitor.c | 30 +++++++------ tests/qmp-test.c | 97 +++++++++++++++++++++++++++++++++++++++- tests/Makefile.include | 6 +-- 4 files changed, 116 insertions(+), 18 deletions(-) diff --git a/migration/postcopy-ram.c b/migration/postcopy-ram.c index efd77939af..4a0b33b373 100644 --- a/migration/postcopy-ram.c +++ b/migration/postcopy-ram.c @@ -754,6 +754,7 @@ static void *postcopy_ram_fault_thread(void *opaque) } } trace_postcopy_ram_fault_thread_exit(); + g_free(pfd); return NULL; } =20 diff --git a/monitor.c b/monitor.c index 77f4c41cfa..d57bbbb134 100644 --- a/monitor.c +++ b/monitor.c @@ -36,6 +36,7 @@ #include "net/slirp.h" #include "chardev/char-fe.h" #include "chardev/char-io.h" +#include "chardev/char-mux.h" #include "ui/qemu-spice.h" #include "sysemu/numa.h" #include "monitor/monitor.h" @@ -3996,6 +3997,18 @@ static void monitor_qmp_respond(Monitor *mon, QObjec= t *rsp, qdict_put_obj(qobject_to(QDict, rsp), "id", id); } =20 + if (mon->qmp.commands =3D=3D &qmp_cap_negotiation_commands) { + qdict =3D qdict_get_qdict(qobject_to(QDict, rsp), "error"); + if (qdict + && !g_strcmp0(qdict_get_try_str(qdict, "class"), + QapiErrorClass_str(ERROR_CLASS_COMMAND_NOT_FOUND= ))) { + /* Provide a more useful error message */ + qdict_del(qdict, "desc"); + qdict_put_str(qdict, "desc", "Expecting capabilities" + " negotiation with 'qmp_capabilities'"); + } + } + monitor_json_emitter(mon, rsp); } =20 @@ -4027,7 +4040,6 @@ static void monitor_qmp_dispatch_one(QMPRequest *req_= obj) { Monitor *mon, *old_mon; QObject *req, *rsp =3D NULL, *id; - QDict *qdict =3D NULL; bool need_resume; =20 req =3D req_obj->req; @@ -4050,18 +4062,6 @@ static void monitor_qmp_dispatch_one(QMPRequest *req= _obj) =20 cur_mon =3D old_mon; =20 - if (mon->qmp.commands =3D=3D &qmp_cap_negotiation_commands) { - qdict =3D qdict_get_qdict(qobject_to(QDict, rsp), "error"); - if (qdict - && !g_strcmp0(qdict_get_try_str(qdict, "class"), - QapiErrorClass_str(ERROR_CLASS_COMMAND_NOT_FOUND))) { - /* Provide a more useful error message */ - qdict_del(qdict, "desc"); - qdict_put_str(qdict, "desc", "Expecting capabilities negotiati= on" - " with 'qmp_capabilities'"); - } - } - /* Respond if necessary */ monitor_qmp_respond(mon, rsp, NULL, id); =20 @@ -4536,8 +4536,10 @@ static void monitor_qmp_setup_handlers_bh(void *opaq= ue) void monitor_init(Chardev *chr, int flags) { Monitor *mon =3D g_malloc(sizeof(*mon)); + /* Enable IOThread for QMPs that are not using MUX chardev backends. */ + bool use_io_thr =3D (!CHARDEV_IS_MUX(chr)) && (flags & MONITOR_USE_CON= TROL); =20 - monitor_data_init(mon, false, false); + monitor_data_init(mon, false, use_io_thr); =20 qemu_chr_fe_init(&mon->chr, chr, &error_abort); mon->flags =3D flags; diff --git a/tests/qmp-test.c b/tests/qmp-test.c index 558e83540c..07c0b87e27 100644 --- a/tests/qmp-test.c +++ b/tests/qmp-test.c @@ -80,6 +80,9 @@ static void test_qmp_protocol(void) QDict *resp, *q, *ret; QList *capabilities; QTestState *qts; + const QListEntry *entry; + QString *qstr; + int i; =20 qts =3D qtest_init_without_qmp_handshake(common_args); =20 @@ -89,7 +92,13 @@ static void test_qmp_protocol(void) g_assert(q); test_version(qdict_get(q, "version")); capabilities =3D qdict_get_qlist(q, "capabilities"); - g_assert(capabilities && qlist_empty(capabilities)); + g_assert(capabilities); + entry =3D qlist_first(capabilities); + g_assert(entry); + qstr =3D qobject_to(QString, entry->value); + g_assert(qstr); + g_assert_cmpstr(qstring_get_str(qstr), =3D=3D, "oob"); + QDECREF(resp); =20 /* Test valid command before handshake */ resp =3D qtest_qmp(qts, "{ 'execute': 'query-version' }"); @@ -131,9 +140,94 @@ static void test_qmp_protocol(void) g_assert_cmpint(qdict_get_int(resp, "id"), =3D=3D, 2); QDECREF(resp); =20 + /* + * Test command batching. In current test OOB is not enabled, we + * should be able to run as many commands in batch as we like. + * Using 16 (>8, which is OOB queue length) to make sure OOB won't + * break existing clients. Note: this test does not control the + * scheduling of QEMU's QMP command processing threads so it may + * not really trigger batching inside QEMU. This is just a + * best-effort test. + */ + for (i =3D 0; i < 16; i++) { + qtest_async_qmp(qts, "{ 'execute': 'query-version' }"); + } + /* Verify the replies to make sure no command is dropped. */ + for (i =3D 0; i < 16; i++) { + resp =3D qtest_qmp_receive(qts); + /* It should never be dropped. Each of them should be a reply. */ + g_assert(qdict_haskey(resp, "return")); + g_assert(!qdict_haskey(resp, "event")); + QDECREF(resp); + } + qtest_quit(qts); } =20 +/* Tests for Out-Of-Band support. */ +static void test_qmp_oob(void) +{ + QDict *resp; + int acks =3D 0; + const char *cmd_id; + + global_qtest =3D qtest_init_without_qmp_handshake(common_args); + + /* Ignore the greeting message. */ + resp =3D qmp_receive(); + g_assert(qdict_get_qdict(resp, "QMP")); + QDECREF(resp); + + /* Try a fake capability, it should fail. */ + resp =3D qmp("{ 'execute': 'qmp_capabilities', " + " 'arguments': { 'enable': [ 'cap-does-not-exist' ] } }"); + g_assert(qdict_haskey(resp, "error")); + QDECREF(resp); + + /* Now, enable OOB in current QMP session, it should succeed. */ + resp =3D qmp("{ 'execute': 'qmp_capabilities', " + " 'arguments': { 'enable': [ 'oob' ] } }"); + g_assert(qdict_haskey(resp, "return")); + QDECREF(resp); + + /* + * Try any command that does not support OOB but with OOB flag. We + * should get failure. + */ + resp =3D qmp("{ 'execute': 'query-cpus'," + " 'control': { 'run-oob': true } }"); + g_assert(qdict_haskey(resp, "error")); + QDECREF(resp); + + /* + * First send the "x-oob-test" command with lock=3Dtrue and + * oob=3Dfalse, it should hang the dispatcher and main thread; + * later, we send another lock=3Dfalse with oob=3Dtrue to continue + * that thread processing. Finally we should receive replies from + * both commands. + */ + qmp_async("{ 'execute': 'x-oob-test'," + " 'arguments': { 'lock': true }, " + " 'id': 'lock-cmd'}"); + qmp_async("{ 'execute': 'x-oob-test', " + " 'arguments': { 'lock': false }, " + " 'control': { 'run-oob': true }, " + " 'id': 'unlock-cmd' }"); + + /* Ignore all events. Wait for 2 acks */ + while (acks < 2) { + resp =3D qmp_receive(); + cmd_id =3D qdict_get_str(resp, "id"); + if (!g_strcmp0(cmd_id, "lock-cmd") || + !g_strcmp0(cmd_id, "unlock-cmd")) { + acks++; + } + QDECREF(resp); + } + + qtest_end(); +} + static int query_error_class(const char *cmd) { static struct { @@ -318,6 +412,7 @@ int main(int argc, char *argv[]) g_test_init(&argc, &argv, NULL); =20 qtest_add_func("qmp/protocol", test_qmp_protocol); + qtest_add_func("qmp/oob", test_qmp_oob); qmp_schema_init(&schema); add_query_tests(&schema); =20 diff --git a/tests/Makefile.include b/tests/Makefile.include index eb218a9539..0b277036df 100644 --- a/tests/Makefile.include +++ b/tests/Makefile.include @@ -669,13 +669,13 @@ tests/test-qapi-events.c tests/test-qapi-events.h \ tests/test-qapi-introspect.c tests/test-qapi-introspect.h: \ tests/test-qapi-gen-timestamp ; tests/test-qapi-gen-timestamp: $(SRC_PATH)/tests/qapi-schema/qapi-schema-t= est.json $(qapi-py) - $(call quiet-command,$(PYTHON_UTF8) $(SRC_PATH)/scripts/qapi-gen.py \ + $(call quiet-command,$(PYTHON) $(SRC_PATH)/scripts/qapi-gen.py \ -o tests -p "test-" $<, \ "GEN","$(@:%-timestamp=3D%)") @>$@ =20 tests/qapi-schema/doc-good.test.texi: $(SRC_PATH)/tests/qapi-schema/doc-go= od.json $(qapi-py) - $(call quiet-command,$(PYTHON_UTF8) $(SRC_PATH)/scripts/qapi-gen.py \ + $(call quiet-command,$(PYTHON) $(SRC_PATH)/scripts/qapi-gen.py \ -o tests/qapi-schema -p "doc-good-" $<, \ "GEN","$@") @mv tests/qapi-schema/doc-good-qapi-doc.texi $@ @@ -927,7 +927,7 @@ check-tests/qemu-iotests-quick.sh: tests/qemu-iotests-q= uick.sh qemu-img$(EXESUF) .PHONY: $(patsubst %, check-%, $(check-qapi-schema-y)) $(patsubst %, check-%, $(check-qapi-schema-y)): check-%.json: $(SRC_PATH)/= %.json $(call quiet-command, PYTHONPATH=3D$(SRC_PATH)/scripts \ - $(PYTHON_UTF8) $(SRC_PATH)/tests/qapi-schema/test-qapi.py \ + $(PYTHON) $(SRC_PATH)/tests/qapi-schema/test-qapi.py \ $^ >$*.test.out 2>$*.test.err; \ echo $$? >$*.test.exit, \ "TEST","$*.out") --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077094791707.7782193211416; Mon, 26 Mar 2018 08:11:34 -0700 (PDT) Received: from localhost ([::1]:57273 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TmX-0006WB-5r for importer@patchew.org; Mon, 26 Mar 2018 11:11:33 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54763) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkc-00054x-Hp for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:38 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TkZ-0002fv-Dk for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:34 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:38271 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TkZ-0002fQ-9Q for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:31 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id BCE83EB713; Mon, 26 Mar 2018 15:09:29 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 601BE2026E03; Mon, 26 Mar 2018 15:09:29 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:40 +0200 Message-Id: <20180326150916.9602-3-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:09:29 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:09:29 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 02/38] qmp-shell: learn to send commands with quoted arguments X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Use shlex to split the CLI command, respecting quoted arguments, and also comments. This allows to call for ex: (QEMU) human-monitor-command command-line=3D"screendump /dev/null" {"execute": "human-monitor-command", "arguments": {"command-line": "screend= ump /dev/null"}} Signed-off-by: Marc-Andr=C3=A9 Lureau Reviewed-by: Eduardo Habkost --- scripts/qmp/qmp-shell | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/scripts/qmp/qmp-shell b/scripts/qmp/qmp-shell index be449de621..af7033c765 100755 --- a/scripts/qmp/qmp-shell +++ b/scripts/qmp/qmp-shell @@ -73,6 +73,7 @@ import sys import os import errno import atexit +import shlex =20 class QMPCompleter(list): def complete(self, text, state): @@ -218,7 +219,7 @@ class QMPShell(qmp.QEMUMonitorProtocol): =20 < command-name > [ arg-name1=3Darg1 ] ... [ arg-nameN=3DargN ] """ - cmdargs =3D cmdline.split() + cmdargs =3D shlex.split(cmdline) =20 # Transactional CLI entry/exit: if cmdargs[0] =3D=3D 'transaction(': --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077099215198.17286966630002; Mon, 26 Mar 2018 08:11:39 -0700 (PDT) Received: from localhost ([::1]:57272 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TmT-0006UJ-VQ for importer@patchew.org; Mon, 26 Mar 2018 11:11:30 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54761) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkc-00054w-He for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:35 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TkZ-0002g8-Q0 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:34 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:57182 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TkZ-0002fr-K3 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:31 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.rdu2.redhat.com [10.11.54.6]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 4D5FB84256; Mon, 26 Mar 2018 15:09:31 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id D1A08215CDAE; Mon, 26 Mar 2018 15:09:30 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:41 +0200 Message-Id: <20180326150916.9602-4-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.6 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:09:31 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:09:31 +0000 (UTC) for IP:'10.11.54.6' DOMAIN:'int-mx06.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 03/38] Revert "qmp: isolate responses into io thread" X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" This reverts commit abe3cd0ff7f774966da6842620806ab7576fe4f3. There is no need to add an additional queue to send the reply to the IOThread, because QMP response is thread safe, and chardev write path is thread safe. It will schedule watcher in the associated IOThread. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 96 +------------------------------------------------------ 1 file changed, 1 insertion(+), 95 deletions(-) diff --git a/monitor.c b/monitor.c index d57bbbb134..59920ea872 100644 --- a/monitor.c +++ b/monitor.c @@ -180,8 +180,6 @@ typedef struct { QemuMutex qmp_queue_lock; /* Input queue that holds all the parsed QMP requests */ GQueue *qmp_requests; - /* Output queue contains all the QMP responses in order */ - GQueue *qmp_responses; } MonitorQMP; =20 /* @@ -208,7 +206,6 @@ struct Monitor { bool skip_flush; bool use_io_thr; =20 - /* We can't access guest memory when holding the lock */ QemuMutex out_lock; QString *outbuf; guint out_watch; @@ -231,8 +228,6 @@ static struct { IOThread *mon_iothread; /* Bottom half to dispatch the requests received from IO thread */ QEMUBH *qmp_dispatcher_bh; - /* Bottom half to deliver the responses back to clients */ - QEMUBH *qmp_respond_bh; } mon_global; =20 /* QMP checker flags */ @@ -422,8 +417,7 @@ int monitor_fprintf(FILE *stream, const char *fmt, ...) return 0; } =20 -static void monitor_json_emitter_raw(Monitor *mon, - QObject *data) +static void monitor_json_emitter(Monitor *mon, const QObject *data) { QString *json; =20 @@ -437,71 +431,6 @@ static void monitor_json_emitter_raw(Monitor *mon, QDECREF(json); } =20 -static void monitor_json_emitter(Monitor *mon, QObject *data) -{ - if (mon->use_io_thr) { - /* - * If using IO thread, we need to queue the item so that IO - * thread will do the rest for us. Take refcount so that - * caller won't free the data (which will be finally freed in - * responder thread). - */ - qobject_incref(data); - qemu_mutex_lock(&mon->qmp.qmp_queue_lock); - g_queue_push_tail(mon->qmp.qmp_responses, (void *)data); - qemu_mutex_unlock(&mon->qmp.qmp_queue_lock); - qemu_bh_schedule(mon_global.qmp_respond_bh); - } else { - /* - * If not using monitor IO thread, then we are in main thread. - * Do the emission right away. - */ - monitor_json_emitter_raw(mon, data); - } -} - -struct QMPResponse { - Monitor *mon; - QObject *data; -}; -typedef struct QMPResponse QMPResponse; - -/* - * Return one QMPResponse. The response is only valid if - * response.data is not NULL. - */ -static QMPResponse monitor_qmp_response_pop_one(void) -{ - Monitor *mon; - QObject *data =3D NULL; - - qemu_mutex_lock(&monitor_lock); - QTAILQ_FOREACH(mon, &mon_list, entry) { - qemu_mutex_lock(&mon->qmp.qmp_queue_lock); - data =3D g_queue_pop_head(mon->qmp.qmp_responses); - qemu_mutex_unlock(&mon->qmp.qmp_queue_lock); - if (data) { - break; - } - } - qemu_mutex_unlock(&monitor_lock); - return (QMPResponse) { .mon =3D mon, .data =3D data }; -} - -static void monitor_qmp_bh_responder(void *opaque) -{ - QMPResponse response; - - while (true) { - response =3D monitor_qmp_response_pop_one(); - if (!response.data) { - break; - } - monitor_json_emitter_raw(response.mon, response.data); - qobject_decref(response.data); - } -} - static MonitorQAPIEventConf monitor_qapi_event_conf[QAPI_EVENT__MAX] =3D { /* Limit guest-triggerable events to 1 per second */ [QAPI_EVENT_RTC_CHANGE] =3D { 1000 * SCALE_MS }, @@ -688,7 +617,6 @@ static void monitor_data_init(Monitor *mon, bool skip_f= lush, mon->skip_flush =3D skip_flush; mon->use_io_thr =3D use_io_thr; mon->qmp.qmp_requests =3D g_queue_new(); - mon->qmp.qmp_responses =3D g_queue_new(); } =20 static void monitor_data_destroy(Monitor *mon) @@ -703,7 +631,6 @@ static void monitor_data_destroy(Monitor *mon) qemu_mutex_destroy(&mon->out_lock); qemu_mutex_destroy(&mon->qmp.qmp_queue_lock); g_queue_free(mon->qmp.qmp_requests); - g_queue_free(mon->qmp.qmp_responses); } =20 char *qmp_human_monitor_command(const char *command_line, bool has_cpu_ind= ex, @@ -4443,15 +4370,6 @@ static void monitor_iothread_init(void) mon_global.qmp_dispatcher_bh =3D aio_bh_new(qemu_get_aio_context(), monitor_qmp_bh_dispatcher, NULL); - - /* - * Unlike the dispatcher BH, this must be run on the monitor IO - * thread, so that monitors that are using IO thread will make - * sure read/write operations are all done on the IO thread. - */ - mon_global.qmp_respond_bh =3D aio_bh_new(monitor_get_aio_context(), - monitor_qmp_bh_responder, - NULL); } =20 void monitor_init_globals(void) @@ -4597,19 +4515,9 @@ void monitor_cleanup(void) */ iothread_stop(mon_global.mon_iothread); =20 - /* - * After we have IOThread to send responses, it's possible that - * when we stop the IOThread there are still replies queued in the - * responder queue. Flush all of them. Note that even after this - * flush it's still possible that out buffer is not flushed. - * It'll be done in below monitor_flush() as the last resort. - */ - monitor_qmp_bh_responder(NULL); - qemu_mutex_lock(&monitor_lock); QTAILQ_FOREACH_SAFE(mon, &mon_list, entry, next) { QTAILQ_REMOVE(&mon_list, mon, entry); - monitor_flush(mon); monitor_data_destroy(mon); g_free(mon); } @@ -4618,8 +4526,6 @@ void monitor_cleanup(void) /* QEMUBHs needs to be deleted before destroying the IOThread. */ qemu_bh_delete(mon_global.qmp_dispatcher_bh); mon_global.qmp_dispatcher_bh =3D NULL; - qemu_bh_delete(mon_global.qmp_respond_bh); - mon_global.qmp_respond_bh =3D NULL; =20 iothread_destroy(mon_global.mon_iothread); mon_global.mon_iothread =3D NULL; --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077203630930.6676272412735; Mon, 26 Mar 2018 08:13:23 -0700 (PDT) Received: from localhost ([::1]:57288 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0ToI-0008AR-Km for importer@patchew.org; Mon, 26 Mar 2018 11:13:22 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54762) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkc-00054y-Hr for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:35 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tkb-0002gp-67 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:34 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:47462 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tkb-0002gd-0Z for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:33 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id A7D29401DE69; Mon, 26 Mar 2018 15:09:32 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 585CB202322B; Mon, 26 Mar 2018 15:09:32 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:42 +0200 Message-Id: <20180326150916.9602-5-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:09:32 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:09:32 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 04/38] monitor: no need to save need_resume X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" There is no need for per-command need_resume granularity, it should resume after running an non-oob command on oob-disabled monitor. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 16 ++++------------ 1 file changed, 4 insertions(+), 12 deletions(-) diff --git a/monitor.c b/monitor.c index 59920ea872..2428c7fcd4 100644 --- a/monitor.c +++ b/monitor.c @@ -3950,12 +3950,6 @@ struct QMPRequest { QObject *id; /* Request object to be handled */ QObject *req; - /* - * Whether we need to resume the monitor afterward. This flag is - * used to emulate the old QMP server behavior that the current - * command must be completed before execution of the next one. - */ - bool need_resume; }; typedef struct QMPRequest QMPRequest; =20 @@ -3963,7 +3957,7 @@ typedef struct QMPRequest QMPRequest; * Dispatch one single QMP request. The function will free the req_obj * and objects inside it before return. */ -static void monitor_qmp_dispatch_one(QMPRequest *req_obj) +static void monitor_qmp_dispatch_one(QMPRequest *req_obj, bool oob_cmd) { Monitor *mon, *old_mon; QObject *req, *rsp =3D NULL, *id; @@ -3972,7 +3966,7 @@ static void monitor_qmp_dispatch_one(QMPRequest *req_= obj) req =3D req_obj->req; mon =3D req_obj->mon; id =3D req_obj->id; - need_resume =3D req_obj->need_resume; + need_resume =3D !oob_cmd && !qmp_oob_enabled(mon); =20 g_free(req_obj); =20 @@ -4043,7 +4037,7 @@ static void monitor_qmp_bh_dispatcher(void *data) =20 if (req_obj) { trace_monitor_qmp_cmd_in_band(qobject_get_try_str(req_obj->id) ?: = ""); - monitor_qmp_dispatch_one(req_obj); + monitor_qmp_dispatch_one(req_obj, false); /* Reschedule instead of looping so the main loop stays responsive= */ qemu_bh_schedule(mon_global.qmp_dispatcher_bh); } @@ -4096,13 +4090,12 @@ static void handle_qmp_command(JSONMessageParser *p= arser, GQueue *tokens) req_obj->mon =3D mon; req_obj->id =3D id; req_obj->req =3D req; - req_obj->need_resume =3D false; =20 if (qmp_is_oob(qdict)) { /* Out-Of-Band (OOB) requests are executed directly in parser. */ trace_monitor_qmp_cmd_out_of_band(qobject_get_try_str(req_obj->id) ?: ""); - monitor_qmp_dispatch_one(req_obj); + monitor_qmp_dispatch_one(req_obj, true); return; } =20 @@ -4117,7 +4110,6 @@ static void handle_qmp_command(JSONMessageParser *par= ser, GQueue *tokens) */ if (!qmp_oob_enabled(mon)) { monitor_suspend(mon); - req_obj->need_resume =3D true; } else { /* Drop the request if queue is full. */ if (mon->qmp.qmp_requests->length >=3D QMP_REQ_QUEUE_LEN_MAX) { --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077568793452.2325849653904; Mon, 26 Mar 2018 08:19:28 -0700 (PDT) Received: from localhost ([::1]:57321 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tu8-0005GO-Gn for importer@patchew.org; Mon, 26 Mar 2018 11:19:24 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54785) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkd-00055V-LZ for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:42 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tkc-0002hk-Nl for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:35 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36624 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tkc-0002hK-K5 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:34 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.rdu2.redhat.com [10.11.54.6]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 4362C40711B2; Mon, 26 Mar 2018 15:09:34 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id E1BFB215CDAE; Mon, 26 Mar 2018 15:09:33 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:43 +0200 Message-Id: <20180326150916.9602-6-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.6 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:09:34 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:09:34 +0000 (UTC) for IP:'10.11.54.6' DOMAIN:'int-mx06.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 05/38] monitor: further simplify previous patch X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Move the resume code to the non-oob path. This patch could eventually be squashed with the previous patch. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 19 +++++++++---------- 1 file changed, 9 insertions(+), 10 deletions(-) diff --git a/monitor.c b/monitor.c index 2428c7fcd4..a8dcfa283e 100644 --- a/monitor.c +++ b/monitor.c @@ -3957,16 +3957,14 @@ typedef struct QMPRequest QMPRequest; * Dispatch one single QMP request. The function will free the req_obj * and objects inside it before return. */ -static void monitor_qmp_dispatch_one(QMPRequest *req_obj, bool oob_cmd) +static void monitor_qmp_dispatch_one(QMPRequest *req_obj) { Monitor *mon, *old_mon; QObject *req, *rsp =3D NULL, *id; - bool need_resume; =20 req =3D req_obj->req; mon =3D req_obj->mon; id =3D req_obj->id; - need_resume =3D !oob_cmd && !qmp_oob_enabled(mon); =20 g_free(req_obj); =20 @@ -3986,11 +3984,6 @@ static void monitor_qmp_dispatch_one(QMPRequest *req= _obj, bool oob_cmd) /* Respond if necessary */ monitor_qmp_respond(mon, rsp, NULL, id); =20 - /* This pairs with the monitor_suspend() in handle_qmp_command(). */ - if (need_resume) { - monitor_resume(mon); - } - qobject_decref(req); } =20 @@ -4036,8 +4029,14 @@ static void monitor_qmp_bh_dispatcher(void *data) QMPRequest *req_obj =3D monitor_qmp_requests_pop_one(); =20 if (req_obj) { + Monitor *mon =3D req_obj->mon; + bool need_resume =3D !qmp_oob_enabled(mon); trace_monitor_qmp_cmd_in_band(qobject_get_try_str(req_obj->id) ?: = ""); - monitor_qmp_dispatch_one(req_obj, false); + monitor_qmp_dispatch_one(req_obj); + /* This pairs with the monitor_suspend() in handle_qmp_command(). = */ + if (need_resume) { + monitor_resume(mon); + } /* Reschedule instead of looping so the main loop stays responsive= */ qemu_bh_schedule(mon_global.qmp_dispatcher_bh); } @@ -4095,7 +4094,7 @@ static void handle_qmp_command(JSONMessageParser *par= ser, GQueue *tokens) /* Out-Of-Band (OOB) requests are executed directly in parser. */ trace_monitor_qmp_cmd_out_of_band(qobject_get_try_str(req_obj->id) ?: ""); - monitor_qmp_dispatch_one(req_obj, true); + monitor_qmp_dispatch_one(req_obj); return; } =20 --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 152207731615780.02343107634272; Mon, 26 Mar 2018 08:15:16 -0700 (PDT) Received: from localhost ([::1]:57295 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tq7-0001nH-6u for importer@patchew.org; Mon, 26 Mar 2018 11:15:15 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54825) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tki-00058d-6C for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:43 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tke-0002iR-Ab for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:40 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36628 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tke-0002iI-6a for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:36 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id A222E40711D4; Mon, 26 Mar 2018 15:09:35 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 5572B7C50; Mon, 26 Mar 2018 15:09:35 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:44 +0200 Message-Id: <20180326150916.9602-7-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:09:35 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:09:35 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 06/38] monitor: no need to remove desc before replacing it X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" The following qdict_put() line does replace the value, as the documentation says. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 1 - 1 file changed, 1 deletion(-) diff --git a/monitor.c b/monitor.c index a8dcfa283e..5889a32231 100644 --- a/monitor.c +++ b/monitor.c @@ -3930,7 +3930,6 @@ static void monitor_qmp_respond(Monitor *mon, QObject= *rsp, && !g_strcmp0(qdict_get_try_str(qdict, "class"), QapiErrorClass_str(ERROR_CLASS_COMMAND_NOT_FOUND= ))) { /* Provide a more useful error message */ - qdict_del(qdict, "desc"); qdict_put_str(qdict, "desc", "Expecting capabilities" " negotiation with 'qmp_capabilities'"); } --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077765897194.42510867353803; Mon, 26 Mar 2018 08:22:45 -0700 (PDT) Received: from localhost ([::1]:57340 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TxF-0008EM-Kv for importer@patchew.org; Mon, 26 Mar 2018 11:22:37 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54842) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkl-0005B9-6P for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:44 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tkf-0002jE-GS for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:43 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:47466 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tkf-0002j4-BZ for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:37 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 0E4AD401DE69; Mon, 26 Mar 2018 15:09:37 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id B0E45D7DFA; Mon, 26 Mar 2018 15:09:36 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:45 +0200 Message-Id: <20180326150916.9602-8-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:09:37 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:09:37 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 07/38] json-parser: always set an error if return NULL X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Let's make json_parser_parse_err() suck less, and simplify caller error handling. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 4 ---- qobject/json-parser.c | 7 ++++++- 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/monitor.c b/monitor.c index 5889a32231..e9d0c4d172 100644 --- a/monitor.c +++ b/monitor.c @@ -4053,10 +4053,6 @@ static void handle_qmp_command(JSONMessageParser *pa= rser, GQueue *tokens) QMPRequest *req_obj; =20 req =3D json_parser_parse_err(tokens, NULL, &err); - if (!req && !err) { - /* json_parser_parse_err() sucks: can fail without setting @err */ - error_setg(&err, QERR_JSON_PARSING); - } if (err) { goto err; } diff --git a/qobject/json-parser.c b/qobject/json-parser.c index 769b960c9f..c39cd8e4d7 100644 --- a/qobject/json-parser.c +++ b/qobject/json-parser.c @@ -591,7 +591,12 @@ QObject *json_parser_parse_err(GQueue *tokens, va_list= *ap, Error **errp) =20 result =3D parse_value(ctxt, ap); =20 - error_propagate(errp, ctxt->err); + if (!result && !ctxt->err) { + /* TODO: improve error reporting */ + error_setg(errp, "Failed to parse JSON"); + } else { + error_propagate(errp, ctxt->err); + } =20 parser_context_free(ctxt); =20 --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077266549351.1401033499859; Mon, 26 Mar 2018 08:14:26 -0700 (PDT) Received: from localhost ([::1]:57291 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TpJ-0000wb-Hx for importer@patchew.org; Mon, 26 Mar 2018 11:14:25 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54856) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkm-0005EM-JJ for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:45 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tkg-0002kF-Sx for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:44 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:57190 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tkg-0002jx-Ob for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:38 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 6C464722C6; Mon, 26 Mar 2018 15:09:38 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 1EEBC2026E03; Mon, 26 Mar 2018 15:09:38 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:46 +0200 Message-Id: <20180326150916.9602-9-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:09:38 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:09:38 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 08/38] json-lexer: make it safe to call multiple times X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" We can easily avoid the burden of checking if the lexer was initialized prior to calling destroy by the caller, let's do it. Signed-off-by: Marc-Andr=C3=A9 Lureau --- qobject/json-lexer.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/qobject/json-lexer.c b/qobject/json-lexer.c index 980ba159d6..0eaba43a2c 100644 --- a/qobject/json-lexer.c +++ b/qobject/json-lexer.c @@ -386,5 +386,8 @@ int json_lexer_flush(JSONLexer *lexer) =20 void json_lexer_destroy(JSONLexer *lexer) { - g_string_free(lexer->token, true); + if (lexer->token) { + g_string_free(lexer->token, true); + lexer->token =3D NULL; + } } --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 152207710186754.734496218461686; Mon, 26 Mar 2018 08:11:41 -0700 (PDT) Received: from localhost ([::1]:57276 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tme-0006fc-VQ for importer@patchew.org; Mon, 26 Mar 2018 11:11:41 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54844) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkl-0005BO-D6 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:44 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tki-0002l1-Fe for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:43 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:47472 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tki-0002kk-Ac for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:40 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 019D8401DE69; Mon, 26 Mar 2018 15:09:40 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 867DE2026E03; Mon, 26 Mar 2018 15:09:39 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:47 +0200 Message-Id: <20180326150916.9602-10-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:09:40 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:09:40 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 09/38] json: remove useless return value from lexer/parser X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" The lexer always returns 0 when char feeding. Furthermore, none of the caller care about the return value. Signed-off-by: Marc-Andr=C3=A9 Lureau Reviewed-by: Markus Armbruster --- include/qapi/qmp/json-lexer.h | 4 ++-- include/qapi/qmp/json-streamer.h | 4 ++-- qobject/json-lexer.c | 23 ++++++++--------------- qobject/json-streamer.c | 8 ++++---- 4 files changed, 16 insertions(+), 23 deletions(-) diff --git a/include/qapi/qmp/json-lexer.h b/include/qapi/qmp/json-lexer.h index afee7828cd..66ccf0357c 100644 --- a/include/qapi/qmp/json-lexer.h +++ b/include/qapi/qmp/json-lexer.h @@ -47,9 +47,9 @@ struct JSONLexer =20 void json_lexer_init(JSONLexer *lexer, JSONLexerEmitter func); =20 -int json_lexer_feed(JSONLexer *lexer, const char *buffer, size_t size); +void json_lexer_feed(JSONLexer *lexer, const char *buffer, size_t size); =20 -int json_lexer_flush(JSONLexer *lexer); +void json_lexer_flush(JSONLexer *lexer); =20 void json_lexer_destroy(JSONLexer *lexer); =20 diff --git a/include/qapi/qmp/json-streamer.h b/include/qapi/qmp/json-strea= mer.h index 00d8a23af8..cb808cf27d 100644 --- a/include/qapi/qmp/json-streamer.h +++ b/include/qapi/qmp/json-streamer.h @@ -36,10 +36,10 @@ typedef struct JSONMessageParser void json_message_parser_init(JSONMessageParser *parser, void (*func)(JSONMessageParser *, GQueue *)); =20 -int json_message_parser_feed(JSONMessageParser *parser, +void json_message_parser_feed(JSONMessageParser *parser, const char *buffer, size_t size); =20 -int json_message_parser_flush(JSONMessageParser *parser); +void json_message_parser_flush(JSONMessageParser *parser); =20 void json_message_parser_destroy(JSONMessageParser *parser); =20 diff --git a/qobject/json-lexer.c b/qobject/json-lexer.c index 0eaba43a2c..89ccb180cc 100644 --- a/qobject/json-lexer.c +++ b/qobject/json-lexer.c @@ -290,7 +290,7 @@ void json_lexer_init(JSONLexer *lexer, JSONLexerEmitter= func) lexer->x =3D lexer->y =3D 0; } =20 -static int json_lexer_feed_char(JSONLexer *lexer, char ch, bool flush) +static void json_lexer_feed_char(JSONLexer *lexer, char ch, bool flush) { int char_consumed, new_state; =20 @@ -344,7 +344,7 @@ static int json_lexer_feed_char(JSONLexer *lexer, char = ch, bool flush) g_string_truncate(lexer->token, 0); new_state =3D IN_START; lexer->state =3D new_state; - return 0; + return; default: break; } @@ -359,29 +359,22 @@ static int json_lexer_feed_char(JSONLexer *lexer, cha= r ch, bool flush) g_string_truncate(lexer->token, 0); lexer->state =3D IN_START; } - - return 0; } =20 -int json_lexer_feed(JSONLexer *lexer, const char *buffer, size_t size) +void json_lexer_feed(JSONLexer *lexer, const char *buffer, size_t size) { size_t i; =20 for (i =3D 0; i < size; i++) { - int err; - - err =3D json_lexer_feed_char(lexer, buffer[i], false); - if (err < 0) { - return err; - } + json_lexer_feed_char(lexer, buffer[i], false); } - - return 0; } =20 -int json_lexer_flush(JSONLexer *lexer) +void json_lexer_flush(JSONLexer *lexer) { - return lexer->state =3D=3D IN_START ? 0 : json_lexer_feed_char(lexer, = 0, true); + if (lexer->state !=3D IN_START) { + json_lexer_feed_char(lexer, 0, true); + } } =20 void json_lexer_destroy(JSONLexer *lexer) diff --git a/qobject/json-streamer.c b/qobject/json-streamer.c index c51c2021f9..78dfff2aa0 100644 --- a/qobject/json-streamer.c +++ b/qobject/json-streamer.c @@ -118,15 +118,15 @@ void json_message_parser_init(JSONMessageParser *pars= er, json_lexer_init(&parser->lexer, json_message_process_token); } =20 -int json_message_parser_feed(JSONMessageParser *parser, +void json_message_parser_feed(JSONMessageParser *parser, const char *buffer, size_t size) { - return json_lexer_feed(&parser->lexer, buffer, size); + json_lexer_feed(&parser->lexer, buffer, size); } =20 -int json_message_parser_flush(JSONMessageParser *parser) +void json_message_parser_flush(JSONMessageParser *parser) { - return json_lexer_flush(&parser->lexer); + json_lexer_flush(&parser->lexer); } =20 void json_message_parser_destroy(JSONMessageParser *parser) --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077941377238.59114990206854; Mon, 26 Mar 2018 08:25:41 -0700 (PDT) Received: from localhost ([::1]:57354 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U0C-0002eu-Dn for importer@patchew.org; Mon, 26 Mar 2018 11:25:40 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54894) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkp-0005I5-NN for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:48 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tko-0002o8-Pz for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:47 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:48728 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tko-0002nv-LA for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:46 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 4E9D34040070; Mon, 26 Mar 2018 15:09:46 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 5DBEF10B0F20; Mon, 26 Mar 2018 15:09:41 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:48 +0200 Message-Id: <20180326150916.9602-11-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:09:46 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:09:46 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 10/38] tests: add a few qemu-qmp tests X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" These 2 tests exhibited two qmp bugs that were fixed in 2.7 (series from commit e64c75a9752c5d0fd64eb2e684c656a5ea7d03c6 to commit 1382d4abdf9619985e4078e37e49e487cea9935e) Signed-off-by: Marc-Andr=C3=A9 Lureau --- tests/qmp-test.c | 49 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 49 insertions(+) diff --git a/tests/qmp-test.c b/tests/qmp-test.c index 07c0b87e27..642f46a332 100644 --- a/tests/qmp-test.c +++ b/tests/qmp-test.c @@ -224,7 +224,50 @@ static void test_qmp_oob(void) } QDECREF(resp); } + qtest_end(); +} + +static void test_object_add_without_props(void) +{ + QDict *ret, *error; + const gchar *klass, *desc; + + qtest_start("-machine none"); =20 + ret =3D qmp("{'execute': 'object-add'," + " 'arguments': { 'qom-type': 'memory-backend-ram', 'id': 'ra= m1' } }"); + g_assert_nonnull(ret); + + error =3D qdict_get_qdict(ret, "error"); + klass =3D qdict_get_try_str(error, "class"); + desc =3D qdict_get_try_str(error, "desc"); + + g_assert_cmpstr(klass, =3D=3D, "GenericError"); + g_assert_cmpstr(desc, =3D=3D, "can't create backend with size 0"); + + QDECREF(ret); + qtest_end(); +} + +static void test_qom_set_without_value(void) +{ + QDict *ret, *error; + const gchar *klass, *desc; + + qtest_start("-machine none"); + + ret =3D qmp("{'execute': 'qom-set'," + " 'arguments': { 'path': '/machine', 'property': 'rtc-time' = } }"); + g_assert_nonnull(ret); + + error =3D qdict_get_qdict(ret, "error"); + klass =3D qdict_get_try_str(error, "class"); + desc =3D qdict_get_try_str(error, "desc"); + + g_assert_cmpstr(klass, =3D=3D, "GenericError"); + g_assert_cmpstr(desc, =3D=3D, "Parameter 'value' is missing"); + + QDECREF(ret); qtest_end(); } =20 @@ -411,13 +454,19 @@ int main(int argc, char *argv[]) =20 g_test_init(&argc, &argv, NULL); =20 + qtest_add_func("qmp/object-add-without-props", + test_object_add_without_props); + qtest_add_func("qmp/qom-set-without-value", + test_qom_set_without_value); qtest_add_func("qmp/protocol", test_qmp_protocol); qtest_add_func("qmp/oob", test_qmp_oob); + qmp_schema_init(&schema); add_query_tests(&schema); =20 ret =3D g_test_run(); =20 qmp_schema_cleanup(&schema); + return ret; } --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077259838366.08775022021086; Mon, 26 Mar 2018 08:14:19 -0700 (PDT) Received: from localhost ([::1]:57290 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TpC-0000mz-SA for importer@patchew.org; Mon, 26 Mar 2018 11:14:18 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54924) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tky-0005Qb-8Y for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:00 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tkv-0002rt-4C for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:56 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:48734 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tku-0002ri-Va for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:53 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id A36F9406803F; Mon, 26 Mar 2018 15:09:52 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 65956D7DFA; Mon, 26 Mar 2018 15:09:47 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:49 +0200 Message-Id: <20180326150916.9602-12-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:09:52 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:09:52 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 11/38] tests: change /0.15/* tests to /qmp/* X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Presumably 0.15 was the version it was first introduced, but qmp keeps evolving. There is no point in having that version as test prefix, 'qmp' makes more sense here. Signed-off-by: Marc-Andr=C3=A9 Lureau Reviewed-by: Eric Blake Reviewed-by: Markus Armbruster --- tests/test-qmp-cmds.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index 93fbbb1b73..b49e9dd029 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -273,11 +273,11 @@ int main(int argc, char **argv) { g_test_init(&argc, &argv, NULL); =20 - g_test_add_func("/0.15/dispatch_cmd", test_dispatch_cmd); - g_test_add_func("/0.15/dispatch_cmd_failure", test_dispatch_cmd_failur= e); - g_test_add_func("/0.15/dispatch_cmd_io", test_dispatch_cmd_io); - g_test_add_func("/0.15/dealloc_types", test_dealloc_types); - g_test_add_func("/0.15/dealloc_partial", test_dealloc_partial); + g_test_add_func("/qmp/dispatch_cmd", test_dispatch_cmd); + g_test_add_func("/qmp/dispatch_cmd_failure", test_dispatch_cmd_failure= ); + g_test_add_func("/qmp/dispatch_cmd_io", test_dispatch_cmd_io); + g_test_add_func("/qmp/dealloc_types", test_dealloc_types); + g_test_add_func("/qmp/dealloc_partial", test_dealloc_partial); =20 test_qmp_init_marshal(&qmp_commands); g_test_run(); --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077437051992.4658828211319; Mon, 26 Mar 2018 08:17:17 -0700 (PDT) Received: from localhost ([::1]:57311 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Ts0-0003Rk-C7 for importer@patchew.org; Mon, 26 Mar 2018 11:17:12 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54971) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tl2-0005VK-Pr for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:01 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tkw-0002sV-JD for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:00 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:38284 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tkw-0002sH-Dg for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:54 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 1677C7B4AD; Mon, 26 Mar 2018 15:09:54 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id B552CD7DFA; Mon, 26 Mar 2018 15:09:53 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:50 +0200 Message-Id: <20180326150916.9602-13-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:09:54 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:09:54 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 12/38] tests: add a qmp success-response test X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Verify the usage of this schema feature and the API behaviour. This should be the only case where qmp_dispatch() returns NULL without error. Signed-off-by: Marc-Andr=C3=A9 Lureau --- tests/test-qmp-cmds.c | 17 +++++++++++++++++ tests/qapi-schema/qapi-schema-test.json | 2 ++ tests/qapi-schema/qapi-schema-test.out | 2 ++ 3 files changed, 21 insertions(+) diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index b49e9dd029..02cbaf41a2 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -16,6 +16,10 @@ void qmp_user_def_cmd(Error **errp) { } =20 +void qmp_cmd_success_response(Error **errp) +{ +} + Empty2 *qmp_user_def_cmd0(Error **errp) { return g_new0(Empty2, 1); @@ -137,6 +141,17 @@ static void test_dispatch_cmd_failure(void) QDECREF(req); } =20 +static void test_dispatch_cmd_success_response(void) +{ + QDict *req =3D qdict_new(); + QObject *resp; + + qdict_put_str(req, "execute", "cmd-success-response"); + resp =3D qmp_dispatch(&qmp_commands, QOBJECT(req)); + assert(resp =3D=3D NULL); + QDECREF(req); +} + static QObject *test_qmp_dispatch(QDict *req) { QObject *resp_obj; @@ -276,6 +291,8 @@ int main(int argc, char **argv) g_test_add_func("/qmp/dispatch_cmd", test_dispatch_cmd); g_test_add_func("/qmp/dispatch_cmd_failure", test_dispatch_cmd_failure= ); g_test_add_func("/qmp/dispatch_cmd_io", test_dispatch_cmd_io); + g_test_add_func("/qmp/dispatch_cmd_success_response", + test_dispatch_cmd_success_response); g_test_add_func("/qmp/dealloc_types", test_dealloc_types); g_test_add_func("/qmp/dealloc_partial", test_dealloc_partial); =20 diff --git a/tests/qapi-schema/qapi-schema-test.json b/tests/qapi-schema/qa= pi-schema-test.json index c72dbd8050..96ff3a8e47 100644 --- a/tests/qapi-schema/qapi-schema-test.json +++ b/tests/qapi-schema/qapi-schema-test.json @@ -132,6 +132,8 @@ 'data': {'ud1a': 'UserDefOne', '*ud1b': 'UserDefOne'}, 'returns': 'UserDefTwo' } =20 +{ 'command': 'cmd-success-response', 'data': {}, 'success-response': false= } + # Returning a non-dictionary requires a name from the whitelist { 'command': 'guest-get-time', 'data': {'a': 'int', '*b': 'int' }, 'returns': 'int' } diff --git a/tests/qapi-schema/qapi-schema-test.out b/tests/qapi-schema/qap= i-schema-test.out index 012e7fc06a..cd3642be34 100644 --- a/tests/qapi-schema/qapi-schema-test.out +++ b/tests/qapi-schema/qapi-schema-test.out @@ -153,6 +153,8 @@ object q_obj_user_def_cmd2-arg member ud1b: UserDefOne optional=3DTrue command user_def_cmd2 q_obj_user_def_cmd2-arg -> UserDefTwo gen=3DTrue success_response=3DTrue boxed=3DFalse +command cmd-success-response None -> None + gen=3DTrue success_response=3DFalse boxed=3DFalse object q_obj_guest-get-time-arg member a: int optional=3DFalse member b: int optional=3DTrue --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078119494635.1683516585728; Mon, 26 Mar 2018 08:28:39 -0700 (PDT) Received: from localhost ([::1]:57374 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U34-0005B4-J3 for importer@patchew.org; Mon, 26 Mar 2018 11:28:38 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54935) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tkz-0005RK-3q for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:58 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tky-0002t6-2h for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:57 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:57200 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tkx-0002sw-T2 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:55 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 8AF7E722C5; Mon, 26 Mar 2018 15:09:55 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 354E7202322B; Mon, 26 Mar 2018 15:09:55 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:51 +0200 Message-Id: <20180326150916.9602-14-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:09:55 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:09:55 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 13/38] qga: process_event() simplification X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Simplify the code around qmp_dispatch(). Make qmp_dispatch_check_obj() a pre-requirement, same as qemu monitor. Have a single send_response() point. Signed-off-by: Marc-Andr=C3=A9 Lureau --- qga/main.c | 67 +++++++++++++++++++----------------------------------- 1 file changed, 23 insertions(+), 44 deletions(-) diff --git a/qga/main.c b/qga/main.c index df1888edc1..71468e68c2 100644 --- a/qga/main.c +++ b/qga/main.c @@ -579,67 +579,46 @@ static int send_response(GAState *s, QObject *payload) return 0; } =20 -static void process_command(GAState *s, QDict *req) -{ - QObject *rsp =3D NULL; - int ret; - - g_assert(req); - g_debug("processing command"); - rsp =3D qmp_dispatch(&ga_commands, QOBJECT(req)); - if (rsp) { - ret =3D send_response(s, rsp); - if (ret < 0) { - g_warning("error sending response: %s", strerror(-ret)); - } - qobject_decref(rsp); - } -} - /* handle requests/control events coming in over the channel */ static void process_event(JSONMessageParser *parser, GQueue *tokens) { GAState *s =3D container_of(parser, GAState, parser); - QDict *qdict; + QObject *req, *rsp =3D NULL; Error *err =3D NULL; int ret; =20 g_assert(s && parser); =20 g_debug("process_event: called"); - qdict =3D qobject_to(QDict, json_parser_parse_err(tokens, NULL, &err)); - if (err || !qdict) { - QDECREF(qdict); - qdict =3D qdict_new(); - if (!err) { - g_warning("failed to parse event: unknown error"); - error_setg(&err, QERR_JSON_PARSING); - } else { - g_warning("failed to parse event: %s", error_get_pretty(err)); - } + + req =3D json_parser_parse_err(tokens, NULL, &err); + if (err) { + goto end; + } + + qmp_dispatch_check_obj(req, &err); + if (err) { + goto end; + } + + g_debug("processing command"); + rsp =3D qmp_dispatch(&ga_commands, req); + +end: + if (err) { + QDict *qdict =3D qdict_new(); qdict_put_obj(qdict, "error", qmp_build_error_object(err)); error_free(err); + rsp =3D QOBJECT(qdict); } - - /* handle host->guest commands */ - if (qdict_haskey(qdict, "execute")) { - process_command(s, qdict); - } else { - if (!qdict_haskey(qdict, "error")) { - QDECREF(qdict); - qdict =3D qdict_new(); - g_warning("unrecognized payload format"); - error_setg(&err, QERR_UNSUPPORTED); - qdict_put_obj(qdict, "error", qmp_build_error_object(err)); - error_free(err); - } - ret =3D send_response(s, QOBJECT(qdict)); + if (rsp) { + ret =3D send_response(s, rsp); if (ret < 0) { g_warning("error sending error response: %s", strerror(-ret)); } + qobject_decref(rsp); } - - QDECREF(qdict); + qobject_decref(req); } =20 /* false return signals GAChannel to close the current client connection */ --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078291033466.5841450315571; Mon, 26 Mar 2018 08:31:31 -0700 (PDT) Received: from localhost ([::1]:57391 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U5q-0007nB-4f for importer@patchew.org; Mon, 26 Mar 2018 11:31:30 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54950) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tl0-0005St-Me for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:59 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tkz-0002u1-Ei for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:58 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:52740 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tkz-0002tl-9E for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:57 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id E558F8182D01; Mon, 26 Mar 2018 15:09:56 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 999F27C50; Mon, 26 Mar 2018 15:09:56 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:52 +0200 Message-Id: <20180326150916.9602-15-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:09:56 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:09:56 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 14/38] monitor: simplify monitor_qmp_respond() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Since the error path is at a single location, we can create the response object there, simplifying argument handling. While at it, also simplify id ownership: no need for the extra reference count. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 58 ++++++++++++++++++++----------------------------------- 1 file changed, 21 insertions(+), 37 deletions(-) diff --git a/monitor.c b/monitor.c index e9d0c4d172..0d01e17398 100644 --- a/monitor.c +++ b/monitor.c @@ -3899,46 +3899,27 @@ static int monitor_can_read(void *opaque) return !atomic_mb_read(&mon->suspend_cnt); } =20 -/* - * 1. This function takes ownership of rsp, err, and id. - * 2. rsp, err, and id may be NULL. - * 3. If err !=3D NULL then rsp must be NULL. - */ -static void monitor_qmp_respond(Monitor *mon, QObject *rsp, - Error *err, QObject *id) +/* take the ownership of rsp & id */ +static void monitor_qmp_respond(Monitor *mon, QObject *rsp, QObject *id) { - QDict *qdict =3D NULL; - - if (err) { - assert(!rsp); - qdict =3D qdict_new(); - qdict_put_obj(qdict, "error", qmp_build_error_object(err)); - error_free(err); - rsp =3D QOBJECT(qdict); - } - - if (rsp) { - if (id) { - /* This is for the qdict below. */ - qobject_incref(id); - qdict_put_obj(qobject_to(QDict, rsp), "id", id); - } + if (!rsp) { + return; + } =20 - if (mon->qmp.commands =3D=3D &qmp_cap_negotiation_commands) { - qdict =3D qdict_get_qdict(qobject_to(QDict, rsp), "error"); - if (qdict - && !g_strcmp0(qdict_get_try_str(qdict, "class"), + if (id) { + qdict_put_obj(qobject_to(QDict, rsp), "id", id); + } + if (mon->qmp.commands =3D=3D &qmp_cap_negotiation_commands) { + QDict *qdict =3D qdict_get_qdict(qobject_to(QDict, rsp), "error"); + if (qdict + && !g_strcmp0(qdict_get_try_str(qdict, "class"), QapiErrorClass_str(ERROR_CLASS_COMMAND_NOT_FOUND= ))) { - /* Provide a more useful error message */ - qdict_put_str(qdict, "desc", "Expecting capabilities" - " negotiation with 'qmp_capabilities'"); - } + /* Provide a more useful error message */ + qdict_put_str(qdict, "desc", "Expecting capabilities" + " negotiation with 'qmp_capabilities'"); } - - monitor_json_emitter(mon, rsp); } - - qobject_decref(id); + monitor_json_emitter(mon, rsp); qobject_decref(rsp); } =20 @@ -3981,7 +3962,7 @@ static void monitor_qmp_dispatch_one(QMPRequest *req_= obj) cur_mon =3D old_mon; =20 /* Respond if necessary */ - monitor_qmp_respond(mon, rsp, NULL, id); + monitor_qmp_respond(mon, rsp, id); =20 qobject_decref(req); } @@ -4131,7 +4112,10 @@ static void handle_qmp_command(JSONMessageParser *pa= rser, GQueue *tokens) return; =20 err: - monitor_qmp_respond(mon, NULL, err, NULL); + qdict =3D qdict_new(); + qdict_put_obj(qdict, "error", qmp_build_error_object(err)); + error_free(err); + monitor_qmp_respond(mon, QOBJECT(qdict), id); qobject_decref(req); } =20 --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (208.118.235.17 [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077505332385.12958656002274; Mon, 26 Mar 2018 08:18:25 -0700 (PDT) Received: from localhost ([::1]:57316 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tt3-0004Jr-Bg for importer@patchew.org; Mon, 26 Mar 2018 11:18:17 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54968) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tl2-0005Uw-Bg for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:06 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tl0-0002v3-UT for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:00 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:38298 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tl0-0002uf-OZ for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:09:58 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 703D577067; Mon, 26 Mar 2018 15:09:58 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 0917F202322B; Mon, 26 Mar 2018 15:09:57 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:53 +0200 Message-Id: <20180326150916.9602-16-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:09:58 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:09:58 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 15/38] qmp: pass and return a QDict to qmp_dispatch() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" qmp_dispatch_check_obj() now must be called before calling qmp_dispatch() and returns a dict. Change qmp_dispatch() arguments, clarifying the expected qobject types, and simplifying a bit the rest of the code. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 2 +- monitor.c | 24 +++++++++++++----------- qapi/qmp-dispatch.c | 15 +++++---------- qga/main.c | 18 +++++++++--------- tests/test-qmp-cmds.c | 36 +++++++++++++++--------------------- 5 files changed, 43 insertions(+), 52 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index ffb4652f71..8e0ac29300 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -40,7 +40,7 @@ void qmp_register_command(QmpCommandList *cmds, const cha= r *name, QmpCommandFunc *fn, QmpCommandOptions options); void qmp_unregister_command(QmpCommandList *cmds, const char *name); QmpCommand *qmp_find_command(QmpCommandList *cmds, const char *name); -QObject *qmp_dispatch(QmpCommandList *cmds, QObject *request); +QDict *qmp_dispatch(QmpCommandList *cmds, QDict *request); void qmp_disable_command(QmpCommandList *cmds, const char *name); void qmp_enable_command(QmpCommandList *cmds, const char *name); =20 diff --git a/monitor.c b/monitor.c index 0d01e17398..471c57e88c 100644 --- a/monitor.c +++ b/monitor.c @@ -3900,17 +3900,17 @@ static int monitor_can_read(void *opaque) } =20 /* take the ownership of rsp & id */ -static void monitor_qmp_respond(Monitor *mon, QObject *rsp, QObject *id) +static void monitor_qmp_respond(Monitor *mon, QDict *rsp, QObject *id) { if (!rsp) { return; } =20 if (id) { - qdict_put_obj(qobject_to(QDict, rsp), "id", id); + qdict_put_obj(rsp, "id", id); } if (mon->qmp.commands =3D=3D &qmp_cap_negotiation_commands) { - QDict *qdict =3D qdict_get_qdict(qobject_to(QDict, rsp), "error"); + QDict *qdict =3D qdict_get_qdict(rsp, "error"); if (qdict && !g_strcmp0(qdict_get_try_str(qdict, "class"), QapiErrorClass_str(ERROR_CLASS_COMMAND_NOT_FOUND= ))) { @@ -3919,8 +3919,8 @@ static void monitor_qmp_respond(Monitor *mon, QObject= *rsp, QObject *id) " negotiation with 'qmp_capabilities'"); } } - monitor_json_emitter(mon, rsp); - qobject_decref(rsp); + monitor_json_emitter(mon, QOBJECT(rsp)); + QDECREF(rsp); } =20 struct QMPRequest { @@ -3929,7 +3929,7 @@ struct QMPRequest { /* "id" field of the request */ QObject *id; /* Request object to be handled */ - QObject *req; + QDict *req; }; typedef struct QMPRequest QMPRequest; =20 @@ -3940,7 +3940,8 @@ typedef struct QMPRequest QMPRequest; static void monitor_qmp_dispatch_one(QMPRequest *req_obj) { Monitor *mon, *old_mon; - QObject *req, *rsp =3D NULL, *id; + QDict *req, *rsp =3D NULL; + QObject *id; =20 req =3D req_obj->req; mon =3D req_obj->mon; @@ -3949,7 +3950,7 @@ static void monitor_qmp_dispatch_one(QMPRequest *req_= obj) g_free(req_obj); =20 if (trace_event_get_state_backends(TRACE_HANDLE_QMP_COMMAND)) { - QString *req_json =3D qobject_to_json(req); + QString *req_json =3D qobject_to_json(QOBJECT(req)); trace_handle_qmp_command(mon, qstring_get_str(req_json)); QDECREF(req_json); } @@ -3964,7 +3965,8 @@ static void monitor_qmp_dispatch_one(QMPRequest *req_= obj) /* Respond if necessary */ monitor_qmp_respond(mon, rsp, id); =20 - qobject_decref(req); + + QDECREF(req); } =20 /* @@ -4064,7 +4066,7 @@ static void handle_qmp_command(JSONMessageParser *par= ser, GQueue *tokens) req_obj =3D g_new0(QMPRequest, 1); req_obj->mon =3D mon; req_obj->id =3D id; - req_obj->req =3D req; + req_obj->req =3D qdict; =20 if (qmp_is_oob(qdict)) { /* Out-Of-Band (OOB) requests are executed directly in parser. */ @@ -4115,7 +4117,7 @@ err: qdict =3D qdict_new(); qdict_put_obj(qdict, "error", qmp_build_error_object(err)); error_free(err); - monitor_qmp_respond(mon, QOBJECT(qdict), id); + monitor_qmp_respond(mon, qdict, id); qobject_decref(req); } =20 diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index dd05907265..66596b66a0 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -74,20 +74,15 @@ QDict *qmp_dispatch_check_obj(const QObject *request, E= rror **errp) return dict; } =20 -static QObject *do_qmp_dispatch(QmpCommandList *cmds, QObject *request, +static QObject *do_qmp_dispatch(QmpCommandList *cmds, QDict *dict, Error **errp) { Error *local_err =3D NULL; const char *command; - QDict *args, *dict; + QDict *args; QmpCommand *cmd; QObject *ret =3D NULL; =20 - dict =3D qmp_dispatch_check_obj(request, errp); - if (!dict) { - return NULL; - } - command =3D qdict_get_str(dict, "execute"); cmd =3D qmp_find_command(cmds, command); if (cmd =3D=3D NULL) { @@ -151,13 +146,13 @@ bool qmp_is_oob(QDict *dict) return qbool_get_bool(bool_obj); } =20 -QObject *qmp_dispatch(QmpCommandList *cmds, QObject *request) +QDict *qmp_dispatch(QmpCommandList *cmds, QDict *req) { Error *err =3D NULL; QObject *ret; QDict *rsp; =20 - ret =3D do_qmp_dispatch(cmds, request, &err); + ret =3D do_qmp_dispatch(cmds, req, &err); =20 rsp =3D qdict_new(); if (err) { @@ -170,5 +165,5 @@ QObject *qmp_dispatch(QmpCommandList *cmds, QObject *re= quest) return NULL; } =20 - return QOBJECT(rsp); + return rsp; } diff --git a/qga/main.c b/qga/main.c index 71468e68c2..04f7dad0b3 100644 --- a/qga/main.c +++ b/qga/main.c @@ -583,7 +583,8 @@ static int send_response(GAState *s, QObject *payload) static void process_event(JSONMessageParser *parser, GQueue *tokens) { GAState *s =3D container_of(parser, GAState, parser); - QObject *req, *rsp =3D NULL; + QObject *obj; + QDict *req, *rsp =3D NULL; Error *err =3D NULL; int ret; =20 @@ -591,12 +592,12 @@ static void process_event(JSONMessageParser *parser, = GQueue *tokens) =20 g_debug("process_event: called"); =20 - req =3D json_parser_parse_err(tokens, NULL, &err); + obj =3D json_parser_parse_err(tokens, NULL, &err); if (err) { goto end; } =20 - qmp_dispatch_check_obj(req, &err); + req =3D qmp_dispatch_check_obj(obj, &err); if (err) { goto end; } @@ -606,19 +607,18 @@ static void process_event(JSONMessageParser *parser, = GQueue *tokens) =20 end: if (err) { - QDict *qdict =3D qdict_new(); - qdict_put_obj(qdict, "error", qmp_build_error_object(err)); + rsp =3D qdict_new(); + qdict_put_obj(rsp, "error", qmp_build_error_object(err)); error_free(err); - rsp =3D QOBJECT(qdict); } if (rsp) { - ret =3D send_response(s, rsp); + ret =3D send_response(s, QOBJECT(rsp)); if (ret < 0) { g_warning("error sending error response: %s", strerror(-ret)); } - qobject_decref(rsp); + QDECREF(rsp); } - qobject_decref(req); + qobject_decref(obj); } =20 /* false return signals GAChannel to close the current client connection */ diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index 02cbaf41a2..52e2738a93 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -97,16 +97,15 @@ __org_qemu_x_Union1 *qmp___org_qemu_x_command(__org_qem= u_x_EnumList *a, /* test commands with no input and no return value */ static void test_dispatch_cmd(void) { - QDict *req =3D qdict_new(); - QObject *resp; + QDict *resp, *req =3D qdict_new(); =20 qdict_put_str(req, "execute", "user_def_cmd"); =20 - resp =3D qmp_dispatch(&qmp_commands, QOBJECT(req)); + resp =3D qmp_dispatch(&qmp_commands, req); assert(resp !=3D NULL); - assert(!qdict_haskey(qobject_to(QDict, resp), "error")); + assert(!qdict_haskey(resp, "error")); =20 - qobject_decref(resp); + QDECREF(resp); QDECREF(req); } =20 @@ -114,16 +113,15 @@ static void test_dispatch_cmd(void) static void test_dispatch_cmd_failure(void) { QDict *req =3D qdict_new(); - QDict *args =3D qdict_new(); - QObject *resp; + QDict *resp, *args =3D qdict_new(); =20 qdict_put_str(req, "execute", "user_def_cmd2"); =20 - resp =3D qmp_dispatch(&qmp_commands, QOBJECT(req)); + resp =3D qmp_dispatch(&qmp_commands, req); assert(resp !=3D NULL); - assert(qdict_haskey(qobject_to(QDict, resp), "error")); + assert(qdict_haskey(resp, "error")); =20 - qobject_decref(resp); + QDECREF(resp); QDECREF(req); =20 /* check that with extra arguments it throws an error */ @@ -133,39 +131,35 @@ static void test_dispatch_cmd_failure(void) =20 qdict_put_str(req, "execute", "user_def_cmd"); =20 - resp =3D qmp_dispatch(&qmp_commands, QOBJECT(req)); + resp =3D qmp_dispatch(&qmp_commands, req); assert(resp !=3D NULL); - assert(qdict_haskey(qobject_to(QDict, resp), "error")); + assert(qdict_haskey(resp, "error")); =20 - qobject_decref(resp); + QDECREF(resp); QDECREF(req); } =20 static void test_dispatch_cmd_success_response(void) { - QDict *req =3D qdict_new(); - QObject *resp; + QDict *resp, *req =3D qdict_new(); =20 qdict_put_str(req, "execute", "cmd-success-response"); - resp =3D qmp_dispatch(&qmp_commands, QOBJECT(req)); + resp =3D qmp_dispatch(&qmp_commands, req); assert(resp =3D=3D NULL); QDECREF(req); } =20 static QObject *test_qmp_dispatch(QDict *req) { - QObject *resp_obj; QDict *resp; QObject *ret; =20 - resp_obj =3D qmp_dispatch(&qmp_commands, QOBJECT(req)); - assert(resp_obj); - resp =3D qobject_to(QDict, resp_obj); + resp =3D qmp_dispatch(&qmp_commands, req); assert(resp && !qdict_haskey(resp, "error")); ret =3D qdict_get(resp, "return"); assert(ret); qobject_incref(ret); - qobject_decref(resp_obj); + QDECREF(resp); return ret; } =20 --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077692880976.5298435305954; Mon, 26 Mar 2018 08:21:32 -0700 (PDT) Received: from localhost ([::1]:57335 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TwB-0007L7-WE for importer@patchew.org; Mon, 26 Mar 2018 11:21:32 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55022) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlB-0005dX-5d for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:14 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tl7-0002xr-UB for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:09 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:52750 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tl7-0002xe-Og for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:05 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 6764E8182D2E; Mon, 26 Mar 2018 15:10:05 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 8885910B0F20; Mon, 26 Mar 2018 15:09:59 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:54 +0200 Message-Id: <20180326150916.9602-17-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:05 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:05 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 16/38] qmp: move 'id' copy to qmp_dispatch() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" This is convenient for other QMP users such as QGA and tests and simplifies a bit the qemu monitor code, and avoids modifying the request. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 23 ++++++----------------- qapi/qmp-dispatch.c | 5 +++++ tests/test-qmp-cmds.c | 17 +++++++++++++++++ 3 files changed, 28 insertions(+), 17 deletions(-) diff --git a/monitor.c b/monitor.c index 471c57e88c..ddcc3a5748 100644 --- a/monitor.c +++ b/monitor.c @@ -3899,16 +3899,9 @@ static int monitor_can_read(void *opaque) return !atomic_mb_read(&mon->suspend_cnt); } =20 -/* take the ownership of rsp & id */ -static void monitor_qmp_respond(Monitor *mon, QDict *rsp, QObject *id) +/* take the ownership of rsp */ +static void monitor_qmp_respond(Monitor *mon, QDict *rsp) { - if (!rsp) { - return; - } - - if (id) { - qdict_put_obj(rsp, "id", id); - } if (mon->qmp.commands =3D=3D &qmp_cap_negotiation_commands) { QDict *qdict =3D qdict_get_qdict(rsp, "error"); if (qdict @@ -3941,11 +3934,9 @@ static void monitor_qmp_dispatch_one(QMPRequest *req= _obj) { Monitor *mon, *old_mon; QDict *req, *rsp =3D NULL; - QObject *id; =20 req =3D req_obj->req; mon =3D req_obj->mon; - id =3D req_obj->id; =20 g_free(req_obj); =20 @@ -3963,7 +3954,9 @@ static void monitor_qmp_dispatch_one(QMPRequest *req_= obj) cur_mon =3D old_mon; =20 /* Respond if necessary */ - monitor_qmp_respond(mon, rsp, id); + if (rsp) { + monitor_qmp_respond(mon, rsp); + } =20 =20 QDECREF(req); @@ -4060,9 +4053,6 @@ static void handle_qmp_command(JSONMessageParser *par= ser, GQueue *tokens) goto err; } =20 - qobject_incref(id); - qdict_del(qdict, "id"); - req_obj =3D g_new0(QMPRequest, 1); req_obj->mon =3D mon; req_obj->id =3D id; @@ -4094,7 +4084,6 @@ static void handle_qmp_command(JSONMessageParser *par= ser, GQueue *tokens) qapi_event_send_command_dropped(id, COMMAND_DROP_REASON_QUEUE_FULL, &error_abort); - qobject_decref(id); qobject_decref(req); g_free(req_obj); return; @@ -4117,7 +4106,7 @@ err: qdict =3D qdict_new(); qdict_put_obj(qdict, "error", qmp_build_error_object(err)); error_free(err); - monitor_qmp_respond(mon, qdict, id); + monitor_qmp_respond(mon, qdict); qobject_decref(req); } =20 diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 66596b66a0..4be0648809 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -151,10 +151,15 @@ QDict *qmp_dispatch(QmpCommandList *cmds, QDict *req) Error *err =3D NULL; QObject *ret; QDict *rsp; + QObject *id =3D qdict_get(req, "id"); =20 ret =3D do_qmp_dispatch(cmds, req, &err); =20 rsp =3D qdict_new(); + if (id) { + qobject_incref(id); + qdict_put_obj(rsp, "id", id); + } if (err) { qdict_put_obj(rsp, "error", qmp_build_error_object(err)); error_free(err); diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index 52e2738a93..58d948b01f 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -277,6 +277,22 @@ static void test_dealloc_partial(void) qapi_free_UserDefTwo(ud2); } =20 +static void test_dispatch_cmd_id(void) +{ + QDict *resp, *req =3D qdict_new(); + + qdict_put_str(req, "execute", "user_def_cmd"); + qdict_put_str(req, "id", "ID42"); + + resp =3D qmp_dispatch(&qmp_commands, req); + assert(resp !=3D NULL); + assert(!qdict_haskey(resp, "error")); + assert(!strcmp(qdict_get_str(resp, "id"), "ID42")); + + QDECREF(resp); + QDECREF(req); +} + =20 int main(int argc, char **argv) { @@ -287,6 +303,7 @@ int main(int argc, char **argv) g_test_add_func("/qmp/dispatch_cmd_io", test_dispatch_cmd_io); g_test_add_func("/qmp/dispatch_cmd_success_response", test_dispatch_cmd_success_response); + g_test_add_func("/qmp/dispatch_cmd_id", test_dispatch_cmd_id); g_test_add_func("/qmp/dealloc_types", test_dealloc_types); g_test_add_func("/qmp/dealloc_partial", test_dealloc_partial); =20 --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077623483594.78784564639; Mon, 26 Mar 2018 08:20:23 -0700 (PDT) Received: from localhost ([::1]:57325 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tv4-00069I-Ks for importer@patchew.org; Mon, 26 Mar 2018 11:20:22 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55021) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlB-0005dW-5Q for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:10 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tl9-0002yr-A3 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:09 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:52756 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tl9-0002yW-5t for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:07 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id CE93A8182D2E; Mon, 26 Mar 2018 15:10:06 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 7B3AE202699A; Mon, 26 Mar 2018 15:10:06 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:55 +0200 Message-Id: <20180326150916.9602-18-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:06 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:06 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 17/38] qmp: constify qmp_is_oob() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 2 +- qapi/qmp-dispatch.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index 8e0ac29300..79fe7f18e0 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -49,7 +49,7 @@ const char *qmp_command_name(const QmpCommand *cmd); bool qmp_has_success_response(const QmpCommand *cmd); QObject *qmp_build_error_object(Error *err); QDict *qmp_dispatch_check_obj(const QObject *request, Error **errp); -bool qmp_is_oob(QDict *dict); +bool qmp_is_oob(const QDict *dict); =20 typedef void (*qmp_cmd_callback_fn)(QmpCommand *cmd, void *opaque); =20 diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 4be0648809..e8a14eb845 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -129,7 +129,7 @@ QObject *qmp_build_error_object(Error *err) * peeking at whether we have: { "control": { "run-oob": true } }. By * default commands are run in-band. */ -bool qmp_is_oob(QDict *dict) +bool qmp_is_oob(const QDict *dict) { QBool *bool_obj; =20 --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077818056964.7309922285982; Mon, 26 Mar 2018 08:23:38 -0700 (PDT) Received: from localhost ([::1]:57345 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TyC-0000ZL-RB for importer@patchew.org; Mon, 26 Mar 2018 11:23:36 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55039) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlC-0005er-J9 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:16 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlB-0002zY-1Y for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:10 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36644 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlA-0002zK-Rj for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:08 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 7E1864270949; Mon, 26 Mar 2018 15:10:08 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 1816B10B0F20; Mon, 26 Mar 2018 15:10:07 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:56 +0200 Message-Id: <20180326150916.9602-19-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:08 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:08 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 18/38] qmp: add QmpSession X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" This structure will hold various data related to a QMP session: the list of commands, the parser, the callbacks, the pending operations etc... Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 10 +++++++++- monitor.c | 20 +++++++++++--------- qapi/qmp-dispatch.c | 14 ++++++++++++-- qga/main.c | 6 ++++-- tests/test-qmp-cmds.c | 28 ++++++++++++++++++++++------ 5 files changed, 58 insertions(+), 20 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index 79fe7f18e0..10ba0745c7 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -36,11 +36,19 @@ typedef struct QmpCommand =20 typedef QTAILQ_HEAD(QmpCommandList, QmpCommand) QmpCommandList; =20 +typedef struct QmpSession QmpSession; + +struct QmpSession { + QmpCommandList *cmds; +}; + void qmp_register_command(QmpCommandList *cmds, const char *name, QmpCommandFunc *fn, QmpCommandOptions options); void qmp_unregister_command(QmpCommandList *cmds, const char *name); QmpCommand *qmp_find_command(QmpCommandList *cmds, const char *name); -QDict *qmp_dispatch(QmpCommandList *cmds, QDict *request); +void qmp_session_init(QmpSession *session, QmpCommandList *cmds); +void qmp_session_destroy(QmpSession *session); +QDict *qmp_dispatch(QmpSession *session, QDict *request); void qmp_disable_command(QmpCommandList *cmds, const char *name); void qmp_enable_command(QmpCommandList *cmds, const char *name); =20 diff --git a/monitor.c b/monitor.c index ddcc3a5748..b90f8566c8 100644 --- a/monitor.c +++ b/monitor.c @@ -171,7 +171,7 @@ typedef struct { * When command qmp_capabilities succeeds, we go into command * mode. */ - QmpCommandList *commands; + QmpSession session; bool qmp_caps[QMP_CAPABILITY__MAX]; /* * Protects qmp request/response queue. Please take monitor_lock @@ -454,7 +454,7 @@ static void monitor_qapi_event_emit(QAPIEvent event, QD= ict *qdict) trace_monitor_protocol_event_emit(event, qdict); QTAILQ_FOREACH(mon, &mon_list, entry) { if (monitor_is_qmp(mon) - && mon->qmp.commands !=3D &qmp_cap_negotiation_commands) { + && mon->qmp.session.cmds !=3D &qmp_cap_negotiation_commands) { monitor_json_emitter(mon, QOBJECT(qdict)); } } @@ -624,6 +624,7 @@ static void monitor_data_destroy(Monitor *mon) g_free(mon->mon_cpu_path); qemu_chr_fe_deinit(&mon->chr, false); if (monitor_is_qmp(mon)) { + qmp_session_destroy(&mon->qmp.session); json_message_parser_destroy(&mon->qmp.parser); } readline_free(mon->rs); @@ -961,7 +962,7 @@ CommandInfoList *qmp_query_commands(Error **errp) { CommandInfoList *list =3D NULL; =20 - qmp_for_each_command(cur_mon->qmp.commands, query_commands_cb, &list); + qmp_for_each_command(cur_mon->qmp.session.cmds, query_commands_cb, &li= st); =20 return list; } @@ -1129,7 +1130,7 @@ static bool qmp_cmd_oob_check(Monitor *mon, QDict *re= q, Error **errp) return false; } =20 - cmd =3D qmp_find_command(mon->qmp.commands, command); + cmd =3D qmp_find_command(mon->qmp.session.cmds, command); if (!cmd) { error_set(errp, ERROR_CLASS_COMMAND_NOT_FOUND, "The command %s has not been found", command); @@ -1157,7 +1158,7 @@ void qmp_qmp_capabilities(bool has_enable, QMPCapabil= ityList *enable, { Error *local_err =3D NULL; =20 - if (cur_mon->qmp.commands =3D=3D &qmp_commands) { + if (cur_mon->qmp.session.cmds =3D=3D &qmp_commands) { error_set(errp, ERROR_CLASS_COMMAND_NOT_FOUND, "Capabilities negotiation is already complete, command " "ignored"); @@ -1179,7 +1180,7 @@ void qmp_qmp_capabilities(bool has_enable, QMPCapabil= ityList *enable, qmp_caps_apply(cur_mon, enable); } =20 - cur_mon->qmp.commands =3D &qmp_commands; + cur_mon->qmp.session.cmds =3D &qmp_commands; } =20 /* set the current CPU defined by the user */ @@ -3902,7 +3903,7 @@ static int monitor_can_read(void *opaque) /* take the ownership of rsp */ static void monitor_qmp_respond(Monitor *mon, QDict *rsp) { - if (mon->qmp.commands =3D=3D &qmp_cap_negotiation_commands) { + if (mon->qmp.session.cmds =3D=3D &qmp_cap_negotiation_commands) { QDict *qdict =3D qdict_get_qdict(rsp, "error"); if (qdict && !g_strcmp0(qdict_get_try_str(qdict, "class"), @@ -3949,7 +3950,7 @@ static void monitor_qmp_dispatch_one(QMPRequest *req_= obj) old_mon =3D cur_mon; cur_mon =3D mon; =20 - rsp =3D qmp_dispatch(mon->qmp.commands, req); + rsp =3D qmp_dispatch(&mon->qmp.session, req); =20 cur_mon =3D old_mon; =20 @@ -4222,7 +4223,7 @@ static void monitor_qmp_event(void *opaque, int event) =20 switch (event) { case CHR_EVENT_OPENED: - mon->qmp.commands =3D &qmp_cap_negotiation_commands; + qmp_session_init(&mon->qmp.session, &qmp_cap_negotiation_commands); monitor_qmp_caps_reset(mon); data =3D get_qmp_greeting(mon); monitor_json_emitter(mon, data); @@ -4230,6 +4231,7 @@ static void monitor_qmp_event(void *opaque, int event) mon_refcount++; break; case CHR_EVENT_CLOSED: + qmp_session_destroy(&mon->qmp.session); json_message_parser_destroy(&mon->qmp.parser); json_message_parser_init(&mon->qmp.parser, handle_qmp_command); mon_refcount--; diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index e8a14eb845..7fd4e41b26 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -146,14 +146,24 @@ bool qmp_is_oob(const QDict *dict) return qbool_get_bool(bool_obj); } =20 -QDict *qmp_dispatch(QmpCommandList *cmds, QDict *req) +void qmp_session_init(QmpSession *session, QmpCommandList *cmds) +{ + session->cmds =3D cmds; +} + +void qmp_session_destroy(QmpSession *session) +{ + session->cmds =3D NULL; +} + +QDict *qmp_dispatch(QmpSession *session, QDict *req) { Error *err =3D NULL; QObject *ret; QDict *rsp; QObject *id =3D qdict_get(req, "id"); =20 - ret =3D do_qmp_dispatch(cmds, req, &err); + ret =3D do_qmp_dispatch(session->cmds, req, &err); =20 rsp =3D qdict_new(); if (id) { diff --git a/qga/main.c b/qga/main.c index 04f7dad0b3..b5d7cc9e8f 100644 --- a/qga/main.c +++ b/qga/main.c @@ -71,6 +71,7 @@ typedef struct GAPersistentState { } GAPersistentState; =20 struct GAState { + QmpSession session; JSONMessageParser parser; GMainLoop *main_loop; GAChannel *channel; @@ -603,7 +604,7 @@ static void process_event(JSONMessageParser *parser, GQ= ueue *tokens) } =20 g_debug("processing command"); - rsp =3D qmp_dispatch(&ga_commands, req); + rsp =3D qmp_dispatch(&s->session, req); =20 end: if (err) { @@ -1304,7 +1305,7 @@ static int run_agent(GAState *s, GAConfig *config, in= t socket_activation) ga_command_state_init(s, s->command_state); ga_command_state_init_all(s->command_state); json_message_parser_init(&s->parser, process_event); - + qmp_session_init(&s->session, &ga_commands); #ifndef _WIN32 if (!register_signal_handlers()) { g_critical("failed to register signal handlers"); @@ -1424,6 +1425,7 @@ int main(int argc, char **argv) =20 end: if (s->command_state) { + qmp_session_destroy(&s->session); ga_command_state_cleanup_all(s->command_state); ga_command_state_free(s->command_state); json_message_parser_destroy(&s->parser); diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index 58d948b01f..0c1fecb281 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -97,27 +97,32 @@ __org_qemu_x_Union1 *qmp___org_qemu_x_command(__org_qem= u_x_EnumList *a, /* test commands with no input and no return value */ static void test_dispatch_cmd(void) { + QmpSession session =3D { 0, }; QDict *resp, *req =3D qdict_new(); =20 + qmp_session_init(&session, &qmp_commands); qdict_put_str(req, "execute", "user_def_cmd"); =20 - resp =3D qmp_dispatch(&qmp_commands, req); + resp =3D qmp_dispatch(&session, req); assert(resp !=3D NULL); assert(!qdict_haskey(resp, "error")); =20 QDECREF(resp); QDECREF(req); + qmp_session_destroy(&session); } =20 /* test commands that return an error due to invalid parameters */ static void test_dispatch_cmd_failure(void) { + QmpSession session =3D { 0, }; QDict *req =3D qdict_new(); QDict *resp, *args =3D qdict_new(); =20 + qmp_session_init(&session, &qmp_commands); qdict_put_str(req, "execute", "user_def_cmd2"); =20 - resp =3D qmp_dispatch(&qmp_commands, req); + resp =3D qmp_dispatch(&session, req); assert(resp !=3D NULL); assert(qdict_haskey(resp, "error")); =20 @@ -131,35 +136,43 @@ static void test_dispatch_cmd_failure(void) =20 qdict_put_str(req, "execute", "user_def_cmd"); =20 - resp =3D qmp_dispatch(&qmp_commands, req); + resp =3D qmp_dispatch(&session, req); assert(resp !=3D NULL); assert(qdict_haskey(resp, "error")); =20 QDECREF(resp); QDECREF(req); + qmp_session_destroy(&session); } =20 static void test_dispatch_cmd_success_response(void) { + QmpSession session =3D { 0, }; QDict *resp, *req =3D qdict_new(); =20 + qmp_session_init(&session, &qmp_commands); qdict_put_str(req, "execute", "cmd-success-response"); - resp =3D qmp_dispatch(&qmp_commands, req); + resp =3D qmp_dispatch(&session, req); assert(resp =3D=3D NULL); QDECREF(req); + qmp_session_destroy(&session); } =20 + static QObject *test_qmp_dispatch(QDict *req) { + QmpSession session =3D { 0, }; QDict *resp; QObject *ret; =20 - resp =3D qmp_dispatch(&qmp_commands, req); + qmp_session_init(&session, &qmp_commands); + resp =3D qmp_dispatch(&session, req); assert(resp && !qdict_haskey(resp, "error")); ret =3D qdict_get(resp, "return"); assert(ret); qobject_incref(ret); QDECREF(resp); + qmp_session_destroy(&session); return ret; } =20 @@ -279,18 +292,21 @@ static void test_dealloc_partial(void) =20 static void test_dispatch_cmd_id(void) { + QmpSession session =3D { 0, }; QDict *resp, *req =3D qdict_new(); =20 + qmp_session_init(&session, &qmp_commands); qdict_put_str(req, "execute", "user_def_cmd"); qdict_put_str(req, "id", "ID42"); =20 - resp =3D qmp_dispatch(&qmp_commands, req); + resp =3D qmp_dispatch(&session, req); assert(resp !=3D NULL); assert(!qdict_haskey(resp, "error")); assert(!strcmp(qdict_get_str(resp, "id"), "ID42")); =20 QDECREF(resp); QDECREF(req); + qmp_session_destroy(&session); } =20 =20 --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078004088876.5163660480679; Mon, 26 Mar 2018 08:26:44 -0700 (PDT) Received: from localhost ([::1]:57364 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U1D-0003Ya-6C for importer@patchew.org; Mon, 26 Mar 2018 11:26:43 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55098) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlL-0005o7-81 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:21 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlC-00030T-La for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:19 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:48746 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlC-00030D-Gm for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:10 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 333524040074; Mon, 26 Mar 2018 15:10:10 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 981B2202322B; Mon, 26 Mar 2018 15:10:09 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:57 +0200 Message-Id: <20180326150916.9602-20-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:10:10 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:10:10 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 19/38] QmpSession: add a return_cb X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" The introduced return_cb will allow to delay finishing the dispatch and sending the response asynchronously. For now, this is just modifying qmp_dispatch() to call the callback synchronously, and return void. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 8 +++- monitor.c | 52 +++++++++++----------- qapi/qmp-dispatch.c | 19 ++++++-- qga/main.c | 25 ++++++----- tests/test-qmp-cmds.c | 86 ++++++++++++++++++------------------- 5 files changed, 101 insertions(+), 89 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index 10ba0745c7..7bf0b6a437 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -37,8 +37,10 @@ typedef struct QmpCommand typedef QTAILQ_HEAD(QmpCommandList, QmpCommand) QmpCommandList; =20 typedef struct QmpSession QmpSession; +typedef void (QmpDispatchReturn) (QmpSession *session, QDict *rsp); =20 struct QmpSession { + QmpDispatchReturn *return_cb; QmpCommandList *cmds; }; =20 @@ -46,9 +48,11 @@ void qmp_register_command(QmpCommandList *cmds, const ch= ar *name, QmpCommandFunc *fn, QmpCommandOptions options); void qmp_unregister_command(QmpCommandList *cmds, const char *name); QmpCommand *qmp_find_command(QmpCommandList *cmds, const char *name); -void qmp_session_init(QmpSession *session, QmpCommandList *cmds); +void qmp_session_init(QmpSession *session, + QmpCommandList *cmds, QmpDispatchReturn *return_cb); + void qmp_session_destroy(QmpSession *session); -QDict *qmp_dispatch(QmpSession *session, QDict *request); +void qmp_dispatch(QmpSession *session, QDict *request); void qmp_disable_command(QmpCommandList *cmds, const char *name); void qmp_enable_command(QmpCommandList *cmds, const char *name); =20 diff --git a/monitor.c b/monitor.c index b90f8566c8..93ecb03d04 100644 --- a/monitor.c +++ b/monitor.c @@ -3900,23 +3900,6 @@ static int monitor_can_read(void *opaque) return !atomic_mb_read(&mon->suspend_cnt); } =20 -/* take the ownership of rsp */ -static void monitor_qmp_respond(Monitor *mon, QDict *rsp) -{ - if (mon->qmp.session.cmds =3D=3D &qmp_cap_negotiation_commands) { - QDict *qdict =3D qdict_get_qdict(rsp, "error"); - if (qdict - && !g_strcmp0(qdict_get_try_str(qdict, "class"), - QapiErrorClass_str(ERROR_CLASS_COMMAND_NOT_FOUND= ))) { - /* Provide a more useful error message */ - qdict_put_str(qdict, "desc", "Expecting capabilities" - " negotiation with 'qmp_capabilities'"); - } - } - monitor_json_emitter(mon, QOBJECT(rsp)); - QDECREF(rsp); -} - struct QMPRequest { /* Owner of the request */ Monitor *mon; @@ -3927,6 +3910,24 @@ struct QMPRequest { }; typedef struct QMPRequest QMPRequest; =20 +static void dispatch_return_cb(QmpSession *session, QDict *rsp) +{ + Monitor *mon =3D container_of(session, Monitor, qmp.session); + + if (mon->qmp.session.cmds =3D=3D &qmp_cap_negotiation_commands) { + QDict *qdict =3D qdict =3D qdict_get_qdict(rsp, "error"); + if (qdict + && !g_strcmp0(qdict_get_try_str(qdict, "class"), + QapiErrorClass_str(ERROR_CLASS_COMMAND_NOT_FOUND))) { + /* Provide a more useful error message */ + qdict_put_str(qdict, "desc", "Expecting capabilities negotiati= on" + " with 'qmp_capabilities'"); + } + } + + monitor_json_emitter(mon, QOBJECT(rsp)); +} + /* * Dispatch one single QMP request. The function will free the req_obj * and objects inside it before return. @@ -3934,7 +3935,7 @@ typedef struct QMPRequest QMPRequest; static void monitor_qmp_dispatch_one(QMPRequest *req_obj) { Monitor *mon, *old_mon; - QDict *req, *rsp =3D NULL; + QDict *req; =20 req =3D req_obj->req; mon =3D req_obj->mon; @@ -3950,16 +3951,9 @@ static void monitor_qmp_dispatch_one(QMPRequest *req= _obj) old_mon =3D cur_mon; cur_mon =3D mon; =20 - rsp =3D qmp_dispatch(&mon->qmp.session, req); + qmp_dispatch(&mon->qmp.session, req); =20 cur_mon =3D old_mon; - - /* Respond if necessary */ - if (rsp) { - monitor_qmp_respond(mon, rsp); - } - - QDECREF(req); } =20 @@ -4107,7 +4101,8 @@ err: qdict =3D qdict_new(); qdict_put_obj(qdict, "error", qmp_build_error_object(err)); error_free(err); - monitor_qmp_respond(mon, qdict); + monitor_json_emitter(mon, QOBJECT(qdict)); + QDECREF(qdict); qobject_decref(req); } =20 @@ -4223,7 +4218,8 @@ static void monitor_qmp_event(void *opaque, int event) =20 switch (event) { case CHR_EVENT_OPENED: - qmp_session_init(&mon->qmp.session, &qmp_cap_negotiation_commands); + qmp_session_init(&mon->qmp.session, + &qmp_cap_negotiation_commands, dispatch_return_cb= ); monitor_qmp_caps_reset(mon); data =3D get_qmp_greeting(mon); monitor_json_emitter(mon, data); diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 7fd4e41b26..5274aa59cc 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -146,17 +146,27 @@ bool qmp_is_oob(const QDict *dict) return qbool_get_bool(bool_obj); } =20 -void qmp_session_init(QmpSession *session, QmpCommandList *cmds) +void qmp_session_init(QmpSession *session, + QmpCommandList *cmds, QmpDispatchReturn *return_cb) { + assert(return_cb); + assert(!session->return_cb); + session->cmds =3D cmds; + session->return_cb =3D return_cb; } =20 void qmp_session_destroy(QmpSession *session) { + if (!session->return_cb) { + return; + } + session->cmds =3D NULL; + session->return_cb =3D NULL; } =20 -QDict *qmp_dispatch(QmpSession *session, QDict *req) +void qmp_dispatch(QmpSession *session, QDict *req) { Error *err =3D NULL; QObject *ret; @@ -177,8 +187,9 @@ QDict *qmp_dispatch(QmpSession *session, QDict *req) qdict_put_obj(rsp, "return", ret); } else { QDECREF(rsp); - return NULL; + return; } =20 - return rsp; + session->return_cb(session, rsp); + QDECREF(rsp); } diff --git a/qga/main.c b/qga/main.c index b5d7cc9e8f..46349395ba 100644 --- a/qga/main.c +++ b/qga/main.c @@ -580,14 +580,22 @@ static int send_response(GAState *s, QObject *payload) return 0; } =20 +static void dispatch_return_cb(QmpSession *session, QDict *rsp) +{ + GAState *s =3D container_of(session, GAState, session); + int ret =3D send_response(s, QOBJECT(rsp)); + if (ret < 0) { + g_warning("error sending response: %s", strerror(-ret)); + } +} + /* handle requests/control events coming in over the channel */ static void process_event(JSONMessageParser *parser, GQueue *tokens) { GAState *s =3D container_of(parser, GAState, parser); QObject *obj; - QDict *req, *rsp =3D NULL; + QDict *req; Error *err =3D NULL; - int ret; =20 g_assert(s && parser); =20 @@ -604,19 +612,14 @@ static void process_event(JSONMessageParser *parser, = GQueue *tokens) } =20 g_debug("processing command"); - rsp =3D qmp_dispatch(&s->session, req); + qmp_dispatch(&s->session, req); =20 end: if (err) { - rsp =3D qdict_new(); + QDict *rsp =3D qdict_new(); qdict_put_obj(rsp, "error", qmp_build_error_object(err)); error_free(err); - } - if (rsp) { - ret =3D send_response(s, QOBJECT(rsp)); - if (ret < 0) { - g_warning("error sending error response: %s", strerror(-ret)); - } + dispatch_return_cb(&s->session, rsp); QDECREF(rsp); } qobject_decref(obj); @@ -1305,7 +1308,7 @@ static int run_agent(GAState *s, GAConfig *config, in= t socket_activation) ga_command_state_init(s, s->command_state); ga_command_state_init_all(s->command_state); json_message_parser_init(&s->parser, process_event); - qmp_session_init(&s->session, &ga_commands); + qmp_session_init(&s->session, &ga_commands, dispatch_return_cb); #ifndef _WIN32 if (!register_signal_handlers()) { g_critical("failed to register signal handlers"); diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index 0c1fecb281..5e6e75b133 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -93,85 +93,83 @@ __org_qemu_x_Union1 *qmp___org_qemu_x_command(__org_qem= u_x_EnumList *a, return ret; } =20 +static void dispatch_cmd_return(QmpSession *session, QDict *resp) +{ + assert(resp !=3D NULL); + assert(!qdict_haskey(resp, "error")); +} =20 /* test commands with no input and no return value */ static void test_dispatch_cmd(void) { QmpSession session =3D { 0, }; - QDict *resp, *req =3D qdict_new(); + QDict *req =3D qdict_new(); =20 - qmp_session_init(&session, &qmp_commands); + qmp_session_init(&session, &qmp_commands, dispatch_cmd_return); qdict_put_str(req, "execute", "user_def_cmd"); - - resp =3D qmp_dispatch(&session, req); - assert(resp !=3D NULL); - assert(!qdict_haskey(resp, "error")); - - QDECREF(resp); + qmp_dispatch(&session, req); QDECREF(req); qmp_session_destroy(&session); } =20 +static void dispatch_cmd_failure_return(QmpSession *session, QDict *resp) +{ + assert(resp !=3D NULL); + assert(qdict_haskey(resp, "error")); +} + /* test commands that return an error due to invalid parameters */ static void test_dispatch_cmd_failure(void) { QmpSession session =3D { 0, }; QDict *req =3D qdict_new(); - QDict *resp, *args =3D qdict_new(); + QDict *args =3D qdict_new(); =20 - qmp_session_init(&session, &qmp_commands); + qmp_session_init(&session, &qmp_commands, dispatch_cmd_failure_return); qdict_put_str(req, "execute", "user_def_cmd2"); - - resp =3D qmp_dispatch(&session, req); - assert(resp !=3D NULL); - assert(qdict_haskey(resp, "error")); - - QDECREF(resp); + qmp_dispatch(&session, req); QDECREF(req); =20 /* check that with extra arguments it throws an error */ req =3D qdict_new(); qdict_put_int(args, "a", 66); qdict_put(req, "arguments", args); - qdict_put_str(req, "execute", "user_def_cmd"); - - resp =3D qmp_dispatch(&session, req); - assert(resp !=3D NULL); - assert(qdict_haskey(resp, "error")); - - QDECREF(resp); + qmp_dispatch(&session, req); QDECREF(req); qmp_session_destroy(&session); } =20 +static QObject *dispatch_ret; + static void test_dispatch_cmd_success_response(void) { QmpSession session =3D { 0, }; - QDict *resp, *req =3D qdict_new(); + QDict *req =3D qdict_new(); =20 - qmp_session_init(&session, &qmp_commands); + qmp_session_init(&session, &qmp_commands, (QmpDispatchReturn *)abort); qdict_put_str(req, "execute", "cmd-success-response"); - resp =3D qmp_dispatch(&session, req); - assert(resp =3D=3D NULL); + qmp_dispatch(&session, req); QDECREF(req); qmp_session_destroy(&session); } =20 +static void dispatch_return(QmpSession *session, QDict *resp) +{ + assert(resp && !qdict_haskey(resp, "error")); + dispatch_ret =3D qdict_get(resp, "return"); + qobject_incref(dispatch_ret); +} =20 static QObject *test_qmp_dispatch(QDict *req) { QmpSession session =3D { 0, }; - QDict *resp; QObject *ret; =20 - qmp_session_init(&session, &qmp_commands); - resp =3D qmp_dispatch(&session, req); - assert(resp && !qdict_haskey(resp, "error")); - ret =3D qdict_get(resp, "return"); - assert(ret); - qobject_incref(ret); - QDECREF(resp); + qmp_session_init(&session, &qmp_commands, dispatch_return); + qmp_dispatch(&session, req); + ret =3D dispatch_ret; + dispatch_ret =3D NULL; qmp_session_destroy(&session); return ret; } @@ -290,21 +288,21 @@ static void test_dealloc_partial(void) qapi_free_UserDefTwo(ud2); } =20 +static void dispatch_return_id42(QmpSession *session, QDict *resp) +{ + assert(!qdict_haskey(resp, "error")); + assert(!strcmp(qdict_get_str(resp, "id"), "ID42")); +} + static void test_dispatch_cmd_id(void) { QmpSession session =3D { 0, }; - QDict *resp, *req =3D qdict_new(); + QDict *req =3D qdict_new(); =20 - qmp_session_init(&session, &qmp_commands); + qmp_session_init(&session, &qmp_commands, dispatch_return_id42); qdict_put_str(req, "execute", "user_def_cmd"); qdict_put_str(req, "id", "ID42"); - - resp =3D qmp_dispatch(&session, req); - assert(resp !=3D NULL); - assert(!qdict_haskey(resp, "error")); - assert(!strcmp(qdict_get_str(resp, "id"), "ID42")); - - QDECREF(resp); + qmp_dispatch(&session, req); QDECREF(req); qmp_session_destroy(&session); } --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077674272311.2993205196907; Mon, 26 Mar 2018 08:21:14 -0700 (PDT) Received: from localhost ([::1]:57334 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tvt-00071X-3f for importer@patchew.org; Mon, 26 Mar 2018 11:21:13 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55063) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlF-0005hg-Mx for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:20 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlE-00031O-6v for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:13 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:47498 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlE-000312-1P for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:12 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.rdu2.redhat.com [10.11.54.6]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id B0010401DE65; Mon, 26 Mar 2018 15:10:11 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 3F8AD215CDAE; Mon, 26 Mar 2018 15:10:11 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:58 +0200 Message-Id: <20180326150916.9602-21-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.6 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:10:11 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:10:11 +0000 (UTC) for IP:'10.11.54.6' DOMAIN:'int-mx06.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 20/38] QmpSession: add json parser and use it in qga X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Move JSON parser to QmpSession, and implement a simple handler to check the parsed tokens and call qmp_dispatch(). This is enough for a simple QMP client, like QGA. The QEMU monitor has more complicated handling of dispatching which will be adressed in following patch to benefit more common code. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 9 ++++++++ monitor.c | 7 ++----- qapi/qmp-dispatch.c | 32 +++++++++++++++++++++++++++++ qga/main.c | 41 +------------------------------------ 4 files changed, 44 insertions(+), 45 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index 7bf0b6a437..cd425b8574 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -15,6 +15,7 @@ #define QAPI_QMP_DISPATCH_H =20 #include "qemu/queue.h" +#include "qapi/qmp/json-streamer.h" =20 typedef void (QmpCommandFunc)(QDict *, QObject **, Error **); =20 @@ -40,6 +41,7 @@ typedef struct QmpSession QmpSession; typedef void (QmpDispatchReturn) (QmpSession *session, QDict *rsp); =20 struct QmpSession { + JSONMessageParser parser; QmpDispatchReturn *return_cb; QmpCommandList *cmds; }; @@ -48,9 +50,16 @@ void qmp_register_command(QmpCommandList *cmds, const ch= ar *name, QmpCommandFunc *fn, QmpCommandOptions options); void qmp_unregister_command(QmpCommandList *cmds, const char *name); QmpCommand *qmp_find_command(QmpCommandList *cmds, const char *name); + void qmp_session_init(QmpSession *session, QmpCommandList *cmds, QmpDispatchReturn *return_cb); =20 +static inline void +qmp_session_feed(QmpSession *session, const char *buf, size_t count) +{ + json_message_parser_feed(&session->parser, buf, count); +} + void qmp_session_destroy(QmpSession *session); void qmp_dispatch(QmpSession *session, QDict *request); void qmp_disable_command(QmpCommandList *cmds, const char *name); diff --git a/monitor.c b/monitor.c index 93ecb03d04..66046d4854 100644 --- a/monitor.c +++ b/monitor.c @@ -3934,11 +3934,8 @@ static void dispatch_return_cb(QmpSession *session, = QDict *rsp) */ static void monitor_qmp_dispatch_one(QMPRequest *req_obj) { - Monitor *mon, *old_mon; - QDict *req; - - req =3D req_obj->req; - mon =3D req_obj->mon; + Monitor *old_mon, *mon =3D req_obj->mon; + QDict *req =3D req_obj->req; =20 g_free(req_obj); =20 diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 5274aa59cc..5352b25e90 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -146,12 +146,43 @@ bool qmp_is_oob(const QDict *dict) return qbool_get_bool(bool_obj); } =20 +static void qmp_json_parser_emit(JSONMessageParser *parser, GQueue *tokens) +{ + QmpSession *session =3D container_of(parser, QmpSession, parser); + QObject *obj; + QDict *req; + Error *err =3D NULL; + + obj =3D json_parser_parse_err(tokens, NULL, &err); + if (err) { + goto end; + } + + req =3D qmp_dispatch_check_obj(obj, &err); + if (err) { + goto end; + } + + qmp_dispatch(session, req); + +end: + if (err) { + QDict *rsp =3D qdict_new(); + qdict_put_obj(rsp, "error", qmp_build_error_object(err)); + error_free(err); + session->return_cb(session, rsp); + QDECREF(rsp); + } + qobject_decref(obj); +} + void qmp_session_init(QmpSession *session, QmpCommandList *cmds, QmpDispatchReturn *return_cb) { assert(return_cb); assert(!session->return_cb); =20 + json_message_parser_init(&session->parser, qmp_json_parser_emit); session->cmds =3D cmds; session->return_cb =3D return_cb; } @@ -164,6 +195,7 @@ void qmp_session_destroy(QmpSession *session) =20 session->cmds =3D NULL; session->return_cb =3D NULL; + json_message_parser_destroy(&session->parser); } =20 void qmp_dispatch(QmpSession *session, QDict *req) diff --git a/qga/main.c b/qga/main.c index 46349395ba..ce7efff3b4 100644 --- a/qga/main.c +++ b/qga/main.c @@ -72,7 +72,6 @@ typedef struct GAPersistentState { =20 struct GAState { QmpSession session; - JSONMessageParser parser; GMainLoop *main_loop; GAChannel *channel; bool virtio; /* fastpath to check for virtio to deal with poll() quirk= s */ @@ -589,42 +588,6 @@ static void dispatch_return_cb(QmpSession *session, QD= ict *rsp) } } =20 -/* handle requests/control events coming in over the channel */ -static void process_event(JSONMessageParser *parser, GQueue *tokens) -{ - GAState *s =3D container_of(parser, GAState, parser); - QObject *obj; - QDict *req; - Error *err =3D NULL; - - g_assert(s && parser); - - g_debug("process_event: called"); - - obj =3D json_parser_parse_err(tokens, NULL, &err); - if (err) { - goto end; - } - - req =3D qmp_dispatch_check_obj(obj, &err); - if (err) { - goto end; - } - - g_debug("processing command"); - qmp_dispatch(&s->session, req); - -end: - if (err) { - QDict *rsp =3D qdict_new(); - qdict_put_obj(rsp, "error", qmp_build_error_object(err)); - error_free(err); - dispatch_return_cb(&s->session, rsp); - QDECREF(rsp); - } - qobject_decref(obj); -} - /* false return signals GAChannel to close the current client connection */ static gboolean channel_event_cb(GIOCondition condition, gpointer data) { @@ -639,7 +602,7 @@ static gboolean channel_event_cb(GIOCondition condition= , gpointer data) case G_IO_STATUS_NORMAL: buf[count] =3D 0; g_debug("read data, count: %d, data: %s", (int)count, buf); - json_message_parser_feed(&s->parser, (char *)buf, (int)count); + qmp_session_feed(&s->session, buf, count); break; case G_IO_STATUS_EOF: g_debug("received EOF"); @@ -1307,7 +1270,6 @@ static int run_agent(GAState *s, GAConfig *config, in= t socket_activation) s->command_state =3D ga_command_state_new(); ga_command_state_init(s, s->command_state); ga_command_state_init_all(s->command_state); - json_message_parser_init(&s->parser, process_event); qmp_session_init(&s->session, &ga_commands, dispatch_return_cb); #ifndef _WIN32 if (!register_signal_handlers()) { @@ -1431,7 +1393,6 @@ end: qmp_session_destroy(&s->session); ga_command_state_cleanup_all(s->command_state); ga_command_state_free(s->command_state); - json_message_parser_destroy(&s->parser); } if (s->channel) { ga_channel_free(s->channel); --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077859771479.7749954088483; Mon, 26 Mar 2018 08:24:19 -0700 (PDT) Received: from localhost ([::1]:57349 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tys-0001If-Sq for importer@patchew.org; Mon, 26 Mar 2018 11:24:18 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55107) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlM-0005ps-7w for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:21 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlF-000329-Qe for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:20 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36648 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlF-00031t-Lj for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:13 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.rdu2.redhat.com [10.11.54.6]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 4A6E44075392; Mon, 26 Mar 2018 15:10:13 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id D189F215CDAE; Mon, 26 Mar 2018 15:10:12 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:08:59 +0200 Message-Id: <20180326150916.9602-22-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.6 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:13 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:13 +0000 (UTC) for IP:'10.11.54.6' DOMAIN:'int-mx06.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 21/38] QmpSession: add a dispatch callback X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" In order to accomodate for QEMU monitor needs, allow to customize dispatching after JSON parsing. The default (for QGA and tests) can be simply qmp_dispatch(). Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 6 +++++- monitor.c | 4 +++- qapi/qmp-dispatch.c | 8 ++++++-- qga/main.c | 2 +- tests/test-qmp-cmds.c | 12 +++++++----- 5 files changed, 22 insertions(+), 10 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index cd425b8574..5329d0052a 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -38,10 +38,12 @@ typedef struct QmpCommand typedef QTAILQ_HEAD(QmpCommandList, QmpCommand) QmpCommandList; =20 typedef struct QmpSession QmpSession; +typedef void (QmpDispatch) (QmpSession *session, QDict *request); typedef void (QmpDispatchReturn) (QmpSession *session, QDict *rsp); =20 struct QmpSession { JSONMessageParser parser; + QmpDispatch *dispatch_cb; QmpDispatchReturn *return_cb; QmpCommandList *cmds; }; @@ -52,7 +54,9 @@ void qmp_unregister_command(QmpCommandList *cmds, const c= har *name); QmpCommand *qmp_find_command(QmpCommandList *cmds, const char *name); =20 void qmp_session_init(QmpSession *session, - QmpCommandList *cmds, QmpDispatchReturn *return_cb); + QmpCommandList *cmds, + QmpDispatch *dispatch_cb, + QmpDispatchReturn *return_cb); =20 static inline void qmp_session_feed(QmpSession *session, const char *buf, size_t count) diff --git a/monitor.c b/monitor.c index 66046d4854..ae8c055df0 100644 --- a/monitor.c +++ b/monitor.c @@ -4216,7 +4216,9 @@ static void monitor_qmp_event(void *opaque, int event) switch (event) { case CHR_EVENT_OPENED: qmp_session_init(&mon->qmp.session, - &qmp_cap_negotiation_commands, dispatch_return_cb= ); + &qmp_cap_negotiation_commands, + NULL, /* XXX: not in use yet, but in following pa= tch */ + dispatch_return_cb); monitor_qmp_caps_reset(mon); data =3D get_qmp_greeting(mon); monitor_json_emitter(mon, data); diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 5352b25e90..53d099d303 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -163,7 +163,7 @@ static void qmp_json_parser_emit(JSONMessageParser *par= ser, GQueue *tokens) goto end; } =20 - qmp_dispatch(session, req); + session->dispatch_cb(session, req); =20 end: if (err) { @@ -177,13 +177,16 @@ end: } =20 void qmp_session_init(QmpSession *session, - QmpCommandList *cmds, QmpDispatchReturn *return_cb) + QmpCommandList *cmds, + QmpDispatch *dispatch_cb, + QmpDispatchReturn *return_cb) { assert(return_cb); assert(!session->return_cb); =20 json_message_parser_init(&session->parser, qmp_json_parser_emit); session->cmds =3D cmds; + session->dispatch_cb =3D dispatch_cb; session->return_cb =3D return_cb; } =20 @@ -194,6 +197,7 @@ void qmp_session_destroy(QmpSession *session) } =20 session->cmds =3D NULL; + session->dispatch_cb =3D NULL; session->return_cb =3D NULL; json_message_parser_destroy(&session->parser); } diff --git a/qga/main.c b/qga/main.c index ce7efff3b4..dbb8f2cbbe 100644 --- a/qga/main.c +++ b/qga/main.c @@ -1270,7 +1270,7 @@ static int run_agent(GAState *s, GAConfig *config, in= t socket_activation) s->command_state =3D ga_command_state_new(); ga_command_state_init(s, s->command_state); ga_command_state_init_all(s->command_state); - qmp_session_init(&s->session, &ga_commands, dispatch_return_cb); + qmp_session_init(&s->session, &ga_commands, qmp_dispatch, dispatch_ret= urn_cb); #ifndef _WIN32 if (!register_signal_handlers()) { g_critical("failed to register signal handlers"); diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index 5e6e75b133..5246650f71 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -105,7 +105,7 @@ static void test_dispatch_cmd(void) QmpSession session =3D { 0, }; QDict *req =3D qdict_new(); =20 - qmp_session_init(&session, &qmp_commands, dispatch_cmd_return); + qmp_session_init(&session, &qmp_commands, qmp_dispatch, dispatch_cmd_r= eturn); qdict_put_str(req, "execute", "user_def_cmd"); qmp_dispatch(&session, req); QDECREF(req); @@ -125,7 +125,8 @@ static void test_dispatch_cmd_failure(void) QDict *req =3D qdict_new(); QDict *args =3D qdict_new(); =20 - qmp_session_init(&session, &qmp_commands, dispatch_cmd_failure_return); + qmp_session_init(&session, &qmp_commands, qmp_dispatch, + dispatch_cmd_failure_return); qdict_put_str(req, "execute", "user_def_cmd2"); qmp_dispatch(&session, req); QDECREF(req); @@ -147,7 +148,8 @@ static void test_dispatch_cmd_success_response(void) QmpSession session =3D { 0, }; QDict *req =3D qdict_new(); =20 - qmp_session_init(&session, &qmp_commands, (QmpDispatchReturn *)abort); + qmp_session_init(&session, &qmp_commands, qmp_dispatch, + (QmpDispatchReturn *)abort); qdict_put_str(req, "execute", "cmd-success-response"); qmp_dispatch(&session, req); QDECREF(req); @@ -166,7 +168,7 @@ static QObject *test_qmp_dispatch(QDict *req) QmpSession session =3D { 0, }; QObject *ret; =20 - qmp_session_init(&session, &qmp_commands, dispatch_return); + qmp_session_init(&session, &qmp_commands, qmp_dispatch, dispatch_retur= n); qmp_dispatch(&session, req); ret =3D dispatch_ret; dispatch_ret =3D NULL; @@ -299,7 +301,7 @@ static void test_dispatch_cmd_id(void) QmpSession session =3D { 0, }; QDict *req =3D qdict_new(); =20 - qmp_session_init(&session, &qmp_commands, dispatch_return_id42); + qmp_session_init(&session, &qmp_commands, qmp_dispatch, dispatch_retur= n_id42); qdict_put_str(req, "execute", "user_def_cmd"); qdict_put_str(req, "id", "ID42"); qmp_dispatch(&session, req); --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078046546643.2231469305494; Mon, 26 Mar 2018 08:27:26 -0700 (PDT) Received: from localhost ([::1]:57368 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U1t-0004AO-KW for importer@patchew.org; Mon, 26 Mar 2018 11:27:25 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55123) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlN-0005sf-P5 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:22 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlH-00034y-RB for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:21 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:52760 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlH-00034V-Kt for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:15 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 4B5798182D38; Mon, 26 Mar 2018 15:10:15 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id D3F2421A4699; Mon, 26 Mar 2018 15:10:14 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:00 +0200 Message-Id: <20180326150916.9602-23-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:15 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:15 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 22/38] monitor: use QmpSession parsing and common dispatch code X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" The previous patch allow to factorize some code out of monitor, and reuse the JSON parsing in QmpSession. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 50 ++++++++++++++++---------------------------------- 1 file changed, 16 insertions(+), 34 deletions(-) diff --git a/monitor.c b/monitor.c index ae8c055df0..94ad366c2d 100644 --- a/monitor.c +++ b/monitor.c @@ -58,8 +58,6 @@ #include "qapi/qmp/qnum.h" #include "qapi/qmp/qstring.h" #include "qapi/qmp/qjson.h" -#include "qapi/qmp/json-streamer.h" -#include "qapi/qmp/json-parser.h" #include "qapi/qmp/qlist.h" #include "qom/object_interfaces.h" #include "trace-root.h" @@ -625,7 +623,6 @@ static void monitor_data_destroy(Monitor *mon) qemu_chr_fe_deinit(&mon->chr, false); if (monitor_is_qmp(mon)) { qmp_session_destroy(&mon->qmp.session); - json_message_parser_destroy(&mon->qmp.parser); } readline_free(mon->rs); QDECREF(mon->outbuf); @@ -4011,32 +4008,20 @@ static void monitor_qmp_bh_dispatcher(void *data) =20 #define QMP_REQ_QUEUE_LEN_MAX (8) =20 -static void handle_qmp_command(JSONMessageParser *parser, GQueue *tokens) +static void qmp_dispatch_cb(QmpSession *session, QDict *req) { - QObject *req, *id =3D NULL; - QDict *qdict =3D NULL; - MonitorQMP *mon_qmp =3D container_of(parser, MonitorQMP, parser); - Monitor *mon =3D container_of(mon_qmp, Monitor, qmp); + QDict *rsp; + QObject *id; + Monitor *mon =3D container_of(session, Monitor, qmp.session); Error *err =3D NULL; QMPRequest *req_obj; =20 - req =3D json_parser_parse_err(tokens, NULL, &err); - if (err) { - goto err; - } - - /* Check against the request in general layout */ - qdict =3D qmp_dispatch_check_obj(req, &err); - if (!qdict) { - goto err; - } - /* Check against OOB specific */ - if (!qmp_cmd_oob_check(mon, qdict, &err)) { + if (!qmp_cmd_oob_check(mon, req, &err)) { goto err; } =20 - id =3D qdict_get(qdict, "id"); + id =3D qdict_get(req, "id"); =20 /* When OOB is enabled, the "id" field is mandatory. */ if (qmp_oob_enabled(mon) && !id) { @@ -4045,12 +4030,13 @@ static void handle_qmp_command(JSONMessageParser *p= arser, GQueue *tokens) goto err; } =20 + QINCREF(req); req_obj =3D g_new0(QMPRequest, 1); req_obj->mon =3D mon; req_obj->id =3D id; - req_obj->req =3D qdict; + req_obj->req =3D req; =20 - if (qmp_is_oob(qdict)) { + if (qmp_is_oob(req)) { /* Out-Of-Band (OOB) requests are executed directly in parser. */ trace_monitor_qmp_cmd_out_of_band(qobject_get_try_str(req_obj->id) ?: ""); @@ -4076,7 +4062,7 @@ static void handle_qmp_command(JSONMessageParser *par= ser, GQueue *tokens) qapi_event_send_command_dropped(id, COMMAND_DROP_REASON_QUEUE_FULL, &error_abort); - qobject_decref(req); + QDECREF(req); g_free(req_obj); return; } @@ -4095,19 +4081,18 @@ static void handle_qmp_command(JSONMessageParser *p= arser, GQueue *tokens) return; =20 err: - qdict =3D qdict_new(); - qdict_put_obj(qdict, "error", qmp_build_error_object(err)); + rsp =3D qdict_new(); + qdict_put_obj(rsp, "error", qmp_build_error_object(err)); error_free(err); - monitor_json_emitter(mon, QOBJECT(qdict)); - QDECREF(qdict); - qobject_decref(req); + monitor_json_emitter(mon, QOBJECT(rsp)); + QDECREF(rsp); } =20 static void monitor_qmp_read(void *opaque, const uint8_t *buf, int size) { Monitor *mon =3D opaque; =20 - json_message_parser_feed(&mon->qmp.parser, (const char *) buf, size); + qmp_session_feed(&mon->qmp.session, (const char *) buf, size); } =20 static void monitor_read(void *opaque, const uint8_t *buf, int size) @@ -4217,7 +4202,7 @@ static void monitor_qmp_event(void *opaque, int event) case CHR_EVENT_OPENED: qmp_session_init(&mon->qmp.session, &qmp_cap_negotiation_commands, - NULL, /* XXX: not in use yet, but in following pa= tch */ + qmp_dispatch_cb, dispatch_return_cb); monitor_qmp_caps_reset(mon); data =3D get_qmp_greeting(mon); @@ -4227,8 +4212,6 @@ static void monitor_qmp_event(void *opaque, int event) break; case CHR_EVENT_CLOSED: qmp_session_destroy(&mon->qmp.session); - json_message_parser_destroy(&mon->qmp.parser); - json_message_parser_init(&mon->qmp.parser, handle_qmp_command); mon_refcount--; monitor_fdsets_cleanup(); break; @@ -4429,7 +4412,6 @@ void monitor_init(Chardev *chr, int flags) =20 if (monitor_is_qmp(mon)) { qemu_chr_fe_set_echo(&mon->chr, true); - json_message_parser_init(&mon->qmp.parser, handle_qmp_command); if (mon->use_io_thr) { /* * Make sure the old iowatch is gone. It's possible when --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 152207821994754.76467716824675; Mon, 26 Mar 2018 08:30:19 -0700 (PDT) Received: from localhost ([::1]:57383 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U4h-0006cm-3n for importer@patchew.org; Mon, 26 Mar 2018 11:30:19 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55164) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlT-0005zm-Mf for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:33 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlO-0003Ak-V9 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:27 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36656 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlO-0003AW-Pg for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:22 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 728DD4072CFD; Mon, 26 Mar 2018 15:10:22 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 3301FD7DFA; Mon, 26 Mar 2018 15:10:17 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:01 +0200 Message-Id: <20180326150916.9602-24-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:22 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:22 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 23/38] QmpSession: introduce QmpReturn X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" QmpReturn and associated functions are used internally for synchronous dispatch return for now. They will be used for returning in an asynchronous way, by holding the pre-prepared response, and having some bookkeeping in QmpSession. They also help to factor out a bit of code preparing the json reply and calling the return_cb. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 33 +++++++++++++++++++ monitor.c | 7 +--- qapi/qmp-dispatch.c | 65 ++++++++++++++++++++++++------------- 3 files changed, 76 insertions(+), 29 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index 5329d0052a..7ca8ab17d9 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -17,6 +17,8 @@ #include "qemu/queue.h" #include "qapi/qmp/json-streamer.h" =20 +typedef struct QmpReturn QmpReturn; + typedef void (QmpCommandFunc)(QDict *, QObject **, Error **); =20 typedef enum QmpCommandOptions @@ -48,6 +50,37 @@ struct QmpSession { QmpCommandList *cmds; }; =20 +struct QmpReturn { + QmpSession *session; + QDict *rsp; +}; + +/* + * @qmp_return_new: + * + * Allocates and initializes a QmpReturn. + */ +QmpReturn *qmp_return_new(QmpSession *session, const QDict *req); + +/* + * @qmp_return_free: + * + * Free a QmpReturn. This shouldn't be needed if you actually return + * with qmp_return{_error}. + */ +void qmp_return_free(QmpReturn *qret); + +/* + * @qmp_return{_error}: + * + * Construct the command reply, and call the + * return_cb() associated with the session. + * + * Finally, free the QmpReturn. + */ +void qmp_return(QmpReturn *qret, QObject *rsp); +void qmp_return_error(QmpReturn *qret, Error *err); + void qmp_register_command(QmpCommandList *cmds, const char *name, QmpCommandFunc *fn, QmpCommandOptions options); void qmp_unregister_command(QmpCommandList *cmds, const char *name); diff --git a/monitor.c b/monitor.c index 94ad366c2d..73a06d4156 100644 --- a/monitor.c +++ b/monitor.c @@ -4010,7 +4010,6 @@ static void monitor_qmp_bh_dispatcher(void *data) =20 static void qmp_dispatch_cb(QmpSession *session, QDict *req) { - QDict *rsp; QObject *id; Monitor *mon =3D container_of(session, Monitor, qmp.session); Error *err =3D NULL; @@ -4081,11 +4080,7 @@ static void qmp_dispatch_cb(QmpSession *session, QDi= ct *req) return; =20 err: - rsp =3D qdict_new(); - qdict_put_obj(rsp, "error", qmp_build_error_object(err)); - error_free(err); - monitor_json_emitter(mon, QOBJECT(rsp)); - QDECREF(rsp); + qmp_return_error(qmp_return_new(session, req), err); } =20 static void monitor_qmp_read(void *opaque, const uint8_t *buf, int size) diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 53d099d303..7b57fa7987 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -19,6 +19,42 @@ #include "qapi/qmp/qjson.h" #include "qapi/qmp/qbool.h" =20 +QmpReturn *qmp_return_new(QmpSession *session, const QDict *req) +{ + QmpReturn *qret =3D g_new0(QmpReturn, 1); + QObject *id =3D req ? qdict_get(req, "id") : NULL; + + qret->session =3D session; + qret->rsp =3D qdict_new(); + if (id) { + qobject_incref(id); + qdict_put_obj(qret->rsp, "id", id); + } + + return qret; +} + +void qmp_return_free(QmpReturn *qret) +{ + QDECREF(qret->rsp); + g_free(qret); +} + +void qmp_return(QmpReturn *qret, QObject *rsp) +{ + qdict_put_obj(qret->rsp, "return", rsp ?: QOBJECT(qdict_new())); + qret->session->return_cb(qret->session, qret->rsp); + qmp_return_free(qret); +} + +void qmp_return_error(QmpReturn *qret, Error *err) +{ + qdict_put_obj(qret->rsp, "error", qmp_build_error_object(err)); + error_free(err); + qret->session->return_cb(qret->session, qret->rsp); + qmp_return_free(qret); +} + QDict *qmp_dispatch_check_obj(const QObject *request, Error **errp) { const QDictEntry *ent; @@ -150,7 +186,7 @@ static void qmp_json_parser_emit(JSONMessageParser *par= ser, GQueue *tokens) { QmpSession *session =3D container_of(parser, QmpSession, parser); QObject *obj; - QDict *req; + QDict *req =3D NULL; Error *err =3D NULL; =20 obj =3D json_parser_parse_err(tokens, NULL, &err); @@ -167,11 +203,7 @@ static void qmp_json_parser_emit(JSONMessageParser *pa= rser, GQueue *tokens) =20 end: if (err) { - QDict *rsp =3D qdict_new(); - qdict_put_obj(rsp, "error", qmp_build_error_object(err)); - error_free(err); - session->return_cb(session, rsp); - QDECREF(rsp); + qmp_return_error(qmp_return_new(session, req), err); } qobject_decref(obj); } @@ -204,28 +236,15 @@ void qmp_session_destroy(QmpSession *session) =20 void qmp_dispatch(QmpSession *session, QDict *req) { + QmpReturn *qret =3D qmp_return_new(session, req); Error *err =3D NULL; QObject *ret; - QDict *rsp; - QObject *id =3D qdict_get(req, "id"); =20 ret =3D do_qmp_dispatch(session->cmds, req, &err); - - rsp =3D qdict_new(); - if (id) { - qobject_incref(id); - qdict_put_obj(rsp, "id", id); - } if (err) { - qdict_put_obj(rsp, "error", qmp_build_error_object(err)); - error_free(err); + assert(!ret); + qmp_return_error(qret, err); } else if (ret) { - qdict_put_obj(rsp, "return", ret); - } else { - QDECREF(rsp); - return; + qmp_return(qret, ret); } - - session->return_cb(session, rsp); - QDECREF(rsp); } --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522077882055750.7850836062835; Mon, 26 Mar 2018 08:24:42 -0700 (PDT) Received: from localhost ([::1]:57350 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TzD-0001UV-1o for importer@patchew.org; Mon, 26 Mar 2018 11:24:39 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55166) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlT-0005zq-Of for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:28 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlQ-0003Bn-BD for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:27 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:52764 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlQ-0003BP-71 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:24 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id D6F848182D2A; Mon, 26 Mar 2018 15:10:23 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 886262026985; Mon, 26 Mar 2018 15:10:23 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:02 +0200 Message-Id: <20180326150916.9602-25-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:23 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:23 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 24/38] qmp: remove qmp_build_error_object() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Now that we have a single caller, we may as well fold the function. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 1 - qapi/qmp-dispatch.c | 12 ++++-------- 2 files changed, 4 insertions(+), 9 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index 7ca8ab17d9..c5ac3bd41e 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -105,7 +105,6 @@ void qmp_enable_command(QmpCommandList *cmds, const cha= r *name); bool qmp_command_is_enabled(const QmpCommand *cmd); const char *qmp_command_name(const QmpCommand *cmd); bool qmp_has_success_response(const QmpCommand *cmd); -QObject *qmp_build_error_object(Error *err); QDict *qmp_dispatch_check_obj(const QObject *request, Error **errp); bool qmp_is_oob(const QDict *dict); =20 diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 7b57fa7987..c6089de616 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -49,7 +49,10 @@ void qmp_return(QmpReturn *qret, QObject *rsp) =20 void qmp_return_error(QmpReturn *qret, Error *err) { - qdict_put_obj(qret->rsp, "error", qmp_build_error_object(err)); + qdict_put_obj(qret->rsp, "error", + qobject_from_jsonf("{ 'class': %s, 'desc': %s }", + QapiErrorClass_str(error_get_class(er= r)), + error_get_pretty(err))); error_free(err); qret->session->return_cb(qret->session, qret->rsp); qmp_return_free(qret); @@ -153,13 +156,6 @@ static QObject *do_qmp_dispatch(QmpCommandList *cmds, = QDict *dict, return ret; } =20 -QObject *qmp_build_error_object(Error *err) -{ - return qobject_from_jsonf("{ 'class': %s, 'desc': %s }", - QapiErrorClass_str(error_get_class(err)), - error_get_pretty(err)); -} - /* * Detect whether a request should be run out-of-band, by quickly * peeking at whether we have: { "control": { "run-oob": true } }. By --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078680739381.48182520399314; Mon, 26 Mar 2018 08:38:00 -0700 (PDT) Received: from localhost ([::1]:57426 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0UC7-0005Dp-SS for importer@patchew.org; Mon, 26 Mar 2018 11:37:59 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55241) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tlc-00068H-Fj for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:37 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlW-0003FJ-R2 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:36 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36666 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlW-0003Ez-M6 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:30 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 57B6B42EF0DA; Mon, 26 Mar 2018 15:10:30 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id E89A010B0F20; Mon, 26 Mar 2018 15:10:24 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:03 +0200 Message-Id: <20180326150916.9602-26-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:30 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:30 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 25/38] qmp: remove need for qobject_from_jsonf() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Signed-off-by: Marc-Andr=C3=A9 Lureau --- qapi/qmp-dispatch.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index c6089de616..92079c0621 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -49,10 +49,11 @@ void qmp_return(QmpReturn *qret, QObject *rsp) =20 void qmp_return_error(QmpReturn *qret, Error *err) { - qdict_put_obj(qret->rsp, "error", - qobject_from_jsonf("{ 'class': %s, 'desc': %s }", - QapiErrorClass_str(error_get_class(er= r)), - error_get_pretty(err))); + QDict *qdict =3D qdict_new(); + + qdict_put_str(qdict, "class", QapiErrorClass_str(error_get_class(err))= ); + qdict_put_str(qdict, "desc", error_get_pretty(err)); + qdict_put_obj(qret->rsp, "error", QOBJECT(qdict)); error_free(err); qret->session->return_cb(qret->session, qret->rsp); qmp_return_free(qret); --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 152207842288973.66431544295438; Mon, 26 Mar 2018 08:33:42 -0700 (PDT) Received: from localhost ([::1]:57400 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U7y-0001D1-0F for importer@patchew.org; Mon, 26 Mar 2018 11:33:42 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55209) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TlZ-00065Y-Jg for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:36 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0TlY-0003GI-J5 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:33 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:57280 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlY-0003Fs-2w for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:32 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.rdu2.redhat.com [10.11.54.6]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id B8376A27EB; Mon, 26 Mar 2018 15:10:31 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 67A6A215CDAE; Mon, 26 Mar 2018 15:10:31 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:04 +0200 Message-Id: <20180326150916.9602-27-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.6 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:10:31 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:10:31 +0000 (UTC) for IP:'10.11.54.6' DOMAIN:'int-mx06.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 26/38] qmp: fold do_qmp_dispatch() in qmp_dispatch() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" qmp_dispatch() is now a simple wrapper for do_qmp_dispatch(). In order to prepare for following asynchronous function, merge the two functions, which result in less code. Signed-off-by: Marc-Andr=C3=A9 Lureau --- qapi/qmp-dispatch.c | 62 ++++++++++++++++++--------------------------- 1 file changed, 25 insertions(+), 37 deletions(-) diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 92079c0621..4a73cf88b3 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -114,47 +114,50 @@ QDict *qmp_dispatch_check_obj(const QObject *request,= Error **errp) return dict; } =20 -static QObject *do_qmp_dispatch(QmpCommandList *cmds, QDict *dict, - Error **errp) +void qmp_dispatch(QmpSession *session, QDict *req) { - Error *local_err =3D NULL; const char *command; - QDict *args; + QDict *args =3D NULL; QmpCommand *cmd; - QObject *ret =3D NULL; + Error *err =3D NULL; =20 - command =3D qdict_get_str(dict, "execute"); - cmd =3D qmp_find_command(cmds, command); + command =3D qdict_get_str(req, "execute"); + cmd =3D qmp_find_command(session->cmds, command); if (cmd =3D=3D NULL) { - error_set(errp, ERROR_CLASS_COMMAND_NOT_FOUND, + error_set(&err, ERROR_CLASS_COMMAND_NOT_FOUND, "The command %s has not been found", command); - return NULL; + goto end; } if (!cmd->enabled) { - error_setg(errp, "The command %s has been disabled for this instan= ce", + error_setg(&err, "The command %s has been disabled for this instan= ce", command); - return NULL; + goto end; } =20 - if (!qdict_haskey(dict, "arguments")) { + if (!qdict_haskey(req, "arguments")) { args =3D qdict_new(); } else { - args =3D qdict_get_qdict(dict, "arguments"); + args =3D qdict_get_qdict(req, "arguments"); QINCREF(args); } =20 - cmd->fn(args, &ret, &local_err); - if (local_err) { - error_propagate(errp, local_err); - } else if (cmd->options & QCO_NO_SUCCESS_RESP) { - g_assert(!ret); - } else if (!ret) { - ret =3D QOBJECT(qdict_new()); + { + QObject *ret =3D NULL; + cmd->fn(args, &ret, &err); + if (err || cmd->options & QCO_NO_SUCCESS_RESP) { + assert(!ret); + goto end; + } else if (!ret) { + ret =3D QOBJECT(qdict_new()); + } + qmp_return(qmp_return_new(session, req), ret); } =20 +end: + if (err) { + qmp_return_error(qmp_return_new(session, req), err); + } QDECREF(args); - - return ret; } =20 /* @@ -230,18 +233,3 @@ void qmp_session_destroy(QmpSession *session) session->return_cb =3D NULL; json_message_parser_destroy(&session->parser); } - -void qmp_dispatch(QmpSession *session, QDict *req) -{ - QmpReturn *qret =3D qmp_return_new(session, req); - Error *err =3D NULL; - QObject *ret; - - ret =3D do_qmp_dispatch(session->cmds, req, &err); - if (err) { - assert(!ret); - qmp_return_error(qret, err); - } else if (ret) { - qmp_return(qret, ret); - } -} --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078249277468.54866601648166; Mon, 26 Mar 2018 08:30:49 -0700 (PDT) Received: from localhost ([::1]:57389 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U5A-00078U-CI for importer@patchew.org; Mon, 26 Mar 2018 11:30:48 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55244) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tlc-00068Z-Ps for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:37 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tla-0003Hm-98 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:36 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:52772 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0TlZ-0003HU-W1 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:34 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.rdu2.redhat.com [10.11.54.6]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 9EC0F82F33BB; Mon, 26 Mar 2018 15:10:33 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 401FD215CDAE; Mon, 26 Mar 2018 15:10:32 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:05 +0200 Message-Id: <20180326150916.9602-28-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.6 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:33 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.8]); Mon, 26 Mar 2018 15:10:33 +0000 (UTC) for IP:'10.11.54.6' DOMAIN:'int-mx06.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 27/38] QmpSession: keep a queue of pending commands X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" The following commit will introduce asynchronous commands. Let's keep the client aware of the pending commands, so we can do interesting things like order the replies, or cancel pending operations when the client is gone. The queue needs a lock, since QmpSession may be used from multiple threads. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 4 ++++ qapi/qmp-dispatch.c | 32 ++++++++++++++++++++++++++++++-- 2 files changed, 34 insertions(+), 2 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index c5ac3bd41e..94a272a5fb 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -15,6 +15,7 @@ #define QAPI_QMP_DISPATCH_H =20 #include "qemu/queue.h" +#include "qemu/thread.h" #include "qapi/qmp/json-streamer.h" =20 typedef struct QmpReturn QmpReturn; @@ -48,11 +49,14 @@ struct QmpSession { QmpDispatch *dispatch_cb; QmpDispatchReturn *return_cb; QmpCommandList *cmds; + QemuMutex pending_lock; + QTAILQ_HEAD(, QmpReturn) pending; }; =20 struct QmpReturn { QmpSession *session; QDict *rsp; + QTAILQ_ENTRY(QmpReturn) entry; }; =20 /* diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 4a73cf88b3..2c162642cb 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -31,11 +31,24 @@ QmpReturn *qmp_return_new(QmpSession *session, const QD= ict *req) qdict_put_obj(qret->rsp, "id", id); } =20 + qemu_mutex_lock(&session->pending_lock); + QTAILQ_INSERT_TAIL(&session->pending, qret, entry); + qemu_mutex_unlock(&session->pending_lock); + return qret; } =20 void qmp_return_free(QmpReturn *qret) { + QmpSession *session =3D qret->session; + + if (session) { + qemu_mutex_lock(&session->pending_lock); + } + QTAILQ_REMOVE(&session->pending, qret, entry); + if (session) { + qemu_mutex_unlock(&session->pending_lock); + } QDECREF(qret->rsp); g_free(qret); } @@ -43,7 +56,9 @@ void qmp_return_free(QmpReturn *qret) void qmp_return(QmpReturn *qret, QObject *rsp) { qdict_put_obj(qret->rsp, "return", rsp ?: QOBJECT(qdict_new())); - qret->session->return_cb(qret->session, qret->rsp); + if (qret->session) { + qret->session->return_cb(qret->session, qret->rsp); + } qmp_return_free(qret); } =20 @@ -55,7 +70,9 @@ void qmp_return_error(QmpReturn *qret, Error *err) qdict_put_str(qdict, "desc", error_get_pretty(err)); qdict_put_obj(qret->rsp, "error", QOBJECT(qdict)); error_free(err); - qret->session->return_cb(qret->session, qret->rsp); + if (qret->session) { + qret->session->return_cb(qret->session, qret->rsp); + } qmp_return_free(qret); } =20 @@ -220,16 +237,27 @@ void qmp_session_init(QmpSession *session, session->cmds =3D cmds; session->dispatch_cb =3D dispatch_cb; session->return_cb =3D return_cb; + qemu_mutex_init(&session->pending_lock); + QTAILQ_INIT(&session->pending); } =20 void qmp_session_destroy(QmpSession *session) { + QmpReturn *ret, *next; + if (!session->return_cb) { return; } =20 + qemu_mutex_lock(&session->pending_lock); + QTAILQ_FOREACH_SAFE(ret, &session->pending, entry, next) { + ret->session =3D NULL; + QTAILQ_REMOVE(&session->pending, ret, entry); + } + qemu_mutex_unlock(&session->pending_lock); session->cmds =3D NULL; session->dispatch_cb =3D NULL; session->return_cb =3D NULL; json_message_parser_destroy(&session->parser); + qemu_mutex_destroy(&session->pending_lock); } --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078254807460.73646916895825; Mon, 26 Mar 2018 08:30:54 -0700 (PDT) Received: from localhost ([::1]:57390 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U5F-0007DS-Ug for importer@patchew.org; Mon, 26 Mar 2018 11:30:53 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55267) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tld-00069Y-R3 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:43 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tlc-0003JC-Dk for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:37 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:38356 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tlc-0003IV-2T for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:36 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id B0E99EBFFE; Mon, 26 Mar 2018 15:10:35 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 48FDE10B0F20; Mon, 26 Mar 2018 15:10:35 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:06 +0200 Message-Id: <20180326150916.9602-29-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:10:35 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:10:35 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 28/38] QmpSession: return orderly X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" QEMU will gain support for asynchronous commands, and may thus finish commands in various order. However, the clients expect replies in order. Let's enforce ordering of replies in QmpReturn: starting from the older command, process each pending QmpReturn, and return until reaching one that is unfinished. Or if the command is OOB, it should return immediately. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 1 + qapi/qmp-dispatch.c | 59 ++++++++++++++++++++++++++++++------- tests/test-qmp-cmds.c | 36 ++++++++++++++++++++++ 3 files changed, 85 insertions(+), 11 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index 94a272a5fb..f6db06c164 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -56,6 +56,7 @@ struct QmpSession { struct QmpReturn { QmpSession *session; QDict *rsp; + bool oob; QTAILQ_ENTRY(QmpReturn) entry; }; =20 diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index 2c162642cb..aa8b71a2c0 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -24,6 +24,7 @@ QmpReturn *qmp_return_new(QmpSession *session, const QDic= t *req) QmpReturn *qret =3D g_new0(QmpReturn, 1); QObject *id =3D req ? qdict_get(req, "id") : NULL; =20 + qret->oob =3D req ? qmp_is_oob(req) : false; qret->session =3D session; qret->rsp =3D qdict_new(); if (id) { @@ -38,6 +39,15 @@ QmpReturn *qmp_return_new(QmpSession *session, const QDi= ct *req) return qret; } =20 +static void qmp_return_free_with_lock(QmpReturn *qret) +{ + if (qret->session) { + QTAILQ_REMOVE(&qret->session->pending, qret, entry); + } + QDECREF(qret->rsp); + g_free(qret); +} + void qmp_return_free(QmpReturn *qret) { QmpSession *session =3D qret->session; @@ -45,21 +55,51 @@ void qmp_return_free(QmpReturn *qret) if (session) { qemu_mutex_lock(&session->pending_lock); } - QTAILQ_REMOVE(&session->pending, qret, entry); + + qmp_return_free_with_lock(qret); + if (session) { qemu_mutex_unlock(&session->pending_lock); } - QDECREF(qret->rsp); - g_free(qret); +} + +static void qmp_return_orderly(QmpReturn *qret) +{ + QmpSession *session =3D qret->session; + QmpReturn *ret, *next; + + if (!session) { + /* the client was destroyed before return, discard */ + qmp_return_free(qret); + return; + } + if (qret->oob) { + session->return_cb(session, qret->rsp); + qmp_return_free(qret); + return; + } + + /* mark as finished */ + qret->session =3D NULL; + + qemu_mutex_lock(&session->pending_lock); + /* process the list of pending and return until reaching an unfinshed = */ + QTAILQ_FOREACH_SAFE(ret, &session->pending, entry, next) { + if (ret->session) { + goto end; + } + session->return_cb(session, ret->rsp); + ret->session =3D session; + qmp_return_free_with_lock(ret); + } +end: + qemu_mutex_unlock(&session->pending_lock); } =20 void qmp_return(QmpReturn *qret, QObject *rsp) { qdict_put_obj(qret->rsp, "return", rsp ?: QOBJECT(qdict_new())); - if (qret->session) { - qret->session->return_cb(qret->session, qret->rsp); - } - qmp_return_free(qret); + qmp_return_orderly(qret); } =20 void qmp_return_error(QmpReturn *qret, Error *err) @@ -70,10 +110,7 @@ void qmp_return_error(QmpReturn *qret, Error *err) qdict_put_str(qdict, "desc", error_get_pretty(err)); qdict_put_obj(qret->rsp, "error", QOBJECT(qdict)); error_free(err); - if (qret->session) { - qret->session->return_cb(qret->session, qret->rsp); - } - qmp_return_free(qret); + qmp_return_orderly(qret); } =20 QDict *qmp_dispatch_check_obj(const QObject *request, Error **errp) diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index 5246650f71..eeaac03d50 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -309,6 +309,41 @@ static void test_dispatch_cmd_id(void) qmp_session_destroy(&session); } =20 +typedef struct QmpReturnOrderly { + QmpSession session; + int returns; +} QmpReturnOrderly; + +static void dispatch_return_orderly(QmpSession *session, QDict *resp) +{ + QmpReturnOrderly *o =3D container_of(session, QmpReturnOrderly, sessio= n); + + o->returns++; +} + +static void test_qmp_return_orderly(void) +{ + QDict *dict =3D qdict_new(); + QDict *ctrl =3D qdict_new(); + QmpReturnOrderly o =3D { 0, }; + QmpReturn *r1, *r2, *r3; + + qmp_session_init(&o.session, &qmp_commands, + qmp_dispatch, dispatch_return_orderly); + r1 =3D qmp_return_new(&o.session, NULL); + qdict_put_bool(ctrl, "run-oob", true); + qdict_put_obj(dict, "control", QOBJECT(ctrl)); + r2 =3D qmp_return_new(&o.session, dict); + r3 =3D qmp_return_new(&o.session, NULL); + qmp_return(r3, NULL); + g_assert_cmpint(o.returns, =3D=3D, 0); + qmp_return(r2, NULL); + g_assert_cmpint(o.returns, =3D=3D, 1); + qmp_return(r1, NULL); + g_assert_cmpint(o.returns, =3D=3D, 3); + qmp_session_destroy(&o.session); + QDECREF(dict); +} =20 int main(int argc, char **argv) { @@ -322,6 +357,7 @@ int main(int argc, char **argv) g_test_add_func("/qmp/dispatch_cmd_id", test_dispatch_cmd_id); g_test_add_func("/qmp/dealloc_types", test_dealloc_types); g_test_add_func("/qmp/dealloc_partial", test_dealloc_partial); + g_test_add_func("/qmp/return_orderly", test_qmp_return_orderly); =20 test_qmp_init_marshal(&qmp_commands); g_test_run(); --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 152207846028723.3399348941648; Mon, 26 Mar 2018 08:34:20 -0700 (PDT) Received: from localhost ([::1]:57403 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U8Z-0001zu-FZ for importer@patchew.org; Mon, 26 Mar 2018 11:34:19 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55320) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tlj-0006GZ-Sp for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:47 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tld-0003KS-Sm for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:43 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:48776 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tld-0003K4-J3 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:37 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 3CB0C406FA25; Mon, 26 Mar 2018 15:10:37 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id C52FF10B0F20; Mon, 26 Mar 2018 15:10:36 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:07 +0200 Message-Id: <20180326150916.9602-30-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:10:37 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:10:37 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 29/38] qmp: introduce asynchronous command type X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Add a new type of command, QmpCommandFuncAsync: those commands can return later thanks to QmpReturn. This commit introduces the new type and register function and teach qmp_dipatch() to call it without qmp_return(). Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 9 ++++++++- qapi/qmp-dispatch.c | 4 +++- qapi/qmp-registry.c | 27 ++++++++++++++++++++++++--- 3 files changed, 35 insertions(+), 5 deletions(-) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index f6db06c164..e426317346 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -21,18 +21,23 @@ typedef struct QmpReturn QmpReturn; =20 typedef void (QmpCommandFunc)(QDict *, QObject **, Error **); +typedef void (QmpCommandAsyncFunc)(QDict *, QmpReturn *); =20 typedef enum QmpCommandOptions { QCO_NO_OPTIONS =3D 0x0, QCO_NO_SUCCESS_RESP =3D (1U << 0), QCO_ALLOW_OOB =3D (1U << 1), + QCO_ASYNC =3D (1U << 2), } QmpCommandOptions; =20 typedef struct QmpCommand { const char *name; - QmpCommandFunc *fn; + union { + QmpCommandFunc *fn; + QmpCommandAsyncFunc *async_fn; + }; QmpCommandOptions options; QTAILQ_ENTRY(QmpCommand) node; bool enabled; @@ -88,6 +93,8 @@ void qmp_return_error(QmpReturn *qret, Error *err); =20 void qmp_register_command(QmpCommandList *cmds, const char *name, QmpCommandFunc *fn, QmpCommandOptions options); +void qmp_register_async_command(QmpCommandList *cmds, const char *name, + QmpCommandAsyncFunc *fn, QmpCommandOptions optio= ns); void qmp_unregister_command(QmpCommandList *cmds, const char *name); QmpCommand *qmp_find_command(QmpCommandList *cmds, const char *name); =20 diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index aa8b71a2c0..f7d9931734 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -195,7 +195,9 @@ void qmp_dispatch(QmpSession *session, QDict *req) QINCREF(args); } =20 - { + if (cmd->options & QCO_ASYNC) { + cmd->async_fn(args, qmp_return_new(session, req)); + } else { QObject *ret =3D NULL; cmd->fn(args, &ret, &err); if (err || cmd->options & QCO_NO_SUCCESS_RESP) { diff --git a/qapi/qmp-registry.c b/qapi/qmp-registry.c index 5af484cd9a..180b1c1e69 100644 --- a/qapi/qmp-registry.c +++ b/qapi/qmp-registry.c @@ -15,16 +15,37 @@ #include "qemu/osdep.h" #include "qapi/qmp/dispatch.h" =20 -void qmp_register_command(QmpCommandList *cmds, const char *name, - QmpCommandFunc *fn, QmpCommandOptions options) + +static QmpCommand *qmp_command_new(QmpCommandList *cmds, const char *name, + QmpCommandOptions options) { QmpCommand *cmd =3D g_malloc0(sizeof(*cmd)); =20 cmd->name =3D name; - cmd->fn =3D fn; cmd->enabled =3D true; cmd->options =3D options; QTAILQ_INSERT_TAIL(cmds, cmd, node); + + return cmd; +} + + +void qmp_register_command(QmpCommandList *cmds, const char *name, + QmpCommandFunc *fn, QmpCommandOptions options) +{ + QmpCommand *cmd =3D qmp_command_new(cmds, name, options); + + assert(!(options & QCO_ASYNC)); + cmd->fn =3D fn; +} + +void qmp_register_async_command(QmpCommandList *cmds, const char *name, + QmpCommandAsyncFunc *fn, QmpCommandOptions opt= ions) +{ + QmpCommand *cmd =3D qmp_command_new(cmds, name, options); + + assert(options & QCO_ASYNC); + cmd->async_fn =3D fn; } =20 void qmp_unregister_command(QmpCommandList *cmds, const char *name) --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078087210833.1005097596008; Mon, 26 Mar 2018 08:28:07 -0700 (PDT) Received: from localhost ([::1]:57369 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U2Q-0004b1-I0 for importer@patchew.org; Mon, 26 Mar 2018 11:27:58 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55306) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tlh-0006Da-Ps for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:43 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tlf-0003LY-Ju for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:41 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36674 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tlf-0003L3-Dt for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:39 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 1116842BE1D7; Mon, 26 Mar 2018 15:10:39 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 7FC0D10B0F20; Mon, 26 Mar 2018 15:10:38 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:08 +0200 Message-Id: <20180326150916.9602-31-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:39 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:39 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 30/38] scripts: learn 'async' qapi commands X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Commands with the 'async' key will be registered as async type (see related commit), and will allow a synchronous (in scope callback) or asynchronous return (when ready, in idle etc) by keeping the given QmpReturn and calling qmp_return function later. Ex: { 'command': 'foo-async, 'data': {'arg': 'str'}, 'returns': 'Foo', 'async': true } generates the following marshaller: void qmp_marshal_foo_async(QDict *args, QmpReturn *qret) { Error *err =3D NULL; Visitor *v; q_obj_foo_async_arg arg =3D {0}; v =3D qmp_input_visitor_new(QOBJECT(args), true); visit_start_struct(v, NULL, NULL, 0, &err); if (err) { goto out; } visit_type_q_obj_foo_async_arg_members(v, &arg, &err); if (!err) { visit_check_struct(v, &err); } visit_end_struct(v, NULL); if (err) { goto out; } qmp_foo_async(arg.arg, qret); out: if (err) { qmp_return_error(qret, err); } visit_free(v); v =3D qapi_dealloc_visitor_new(); visit_start_struct(v, NULL, NULL, 0, NULL); visit_type_q_obj_foo_async_arg_members(v, &arg, NULL); visit_end_struct(v, NULL); visit_free(v); } and return helper: void qmp_foo_async_return(QmpReturn *qret, Foo *ret_in) { Error *err =3D NULL; QObject *ret_out =3D NULL; qmp_marshal_output_Foo(ret_in, &ret_out, &err); if (err) { qmp_return_error(qret, err); } else { qmp_return(qret, ret_out); } } The dispatched function may call the return helper within the calling scope or delay the return. To return an error, it should call qmp_return_error(). Signed-off-by: Marc-Andr=C3=A9 Lureau --- scripts/qapi/commands.py | 149 ++++++++++++++++++++---- scripts/qapi/common.py | 12 +- scripts/qapi/doc.py | 2 +- scripts/qapi/introspect.py | 2 +- tests/test-qmp-cmds.c | 60 ++++++++++ tests/qapi-schema/qapi-schema-test.json | 5 + tests/qapi-schema/qapi-schema-test.out | 8 ++ tests/qapi-schema/test-qapi.py | 7 +- 8 files changed, 210 insertions(+), 35 deletions(-) mode change 100644 =3D> 100755 scripts/qapi/doc.py diff --git a/scripts/qapi/commands.py b/scripts/qapi/commands.py index 0c5da3a54d..a292164169 100644 --- a/scripts/qapi/commands.py +++ b/scripts/qapi/commands.py @@ -16,18 +16,36 @@ See the COPYING file in the top-level directory. from qapi.common import * =20 =20 -def gen_command_decl(name, arg_type, boxed, ret_type): - return mcgen(''' -%(c_type)s qmp_%(c_name)s(%(params)s); +def gen_command_decl(name, arg_type, boxed, ret_type, success_response, as= ync): + if async: + extra =3D "QmpReturn *qret" + else: + extra =3D 'Error **errp' + + if async: + ret =3D mcgen(''' +void qmp_%(name)s(%(params)s); ''', - c_type=3D(ret_type and ret_type.c_type()) or 'void', - c_name=3Dc_name(name), - params=3Dbuild_params(arg_type, boxed, 'Error **errp')) + name=3Dc_name(name), + params=3Dbuild_params(arg_type, boxed, extra)) + if success_response: + ret +=3D mcgen(''' +void qmp_%(name)s_return(QmpReturn *qret%(c_type)s); +''', + c_type=3D(", " + ret_type.c_type() if ret_type els= e ""), + name=3Dc_name(name)) =20 + return ret + else: + return mcgen(''' +%(c_type)s qmp_%(c_name)s(%(params)s); +''', + c_type=3D(ret_type and ret_type.c_type()) or 'void', + c_name=3Dc_name(name), + params=3Dbuild_params(arg_type, boxed, extra)) =20 -def gen_call(name, arg_type, boxed, ret_type): - ret =3D '' =20 +def gen_argstr(arg_type, boxed): argstr =3D '' if boxed: assert arg_type and not arg_type.is_empty() @@ -39,6 +57,13 @@ def gen_call(name, arg_type, boxed, ret_type): argstr +=3D 'arg.has_%s, ' % c_name(memb.name) argstr +=3D 'arg.%s, ' % c_name(memb.name) =20 + return argstr + + +def gen_call(name, arg_type, boxed, ret_type): + ret =3D '' + + argstr =3D gen_argstr(arg_type, boxed) lhs =3D '' if ret_type: lhs =3D 'retval =3D ' @@ -60,6 +85,50 @@ def gen_call(name, arg_type, boxed, ret_type): return ret =20 =20 +def gen_async_call(name, arg_type, boxed): + argstr =3D gen_argstr(arg_type, boxed) + + push_indent() + ret =3D mcgen(''' + +qmp_%(c_name)s(%(args)sqret); +''', + c_name=3Dc_name(name), args=3Dargstr) + + pop_indent() + return ret + + +def gen_async_return(name, ret_type): + if ret_type: + return mcgen(''' + +void qmp_%(c_name)s_return(QmpReturn *qret, %(ret_type)s ret_in) +{ + Error *err =3D NULL; + QObject *ret_out =3D NULL; + + qmp_marshal_output_%(ret_c_name)s(ret_in, &ret_out, &err); + + if (err) { + qmp_return_error(qret, err); + } else { + qmp_return(qret, ret_out); + } +} +''', + c_name=3Dc_name(name), + ret_type=3Dret_type.c_type(), ret_c_name=3Dret_type.c= _name()) + else: + return mcgen(''' + +void qmp_%(c_name)s_return(QmpReturn *qret) +{ + qmp_return(qret, QOBJECT(qdict_new())); +} +''', + c_name=3Dc_name(name)) + def gen_marshal_output(ret_type): return mcgen(''' =20 @@ -83,19 +152,22 @@ static void qmp_marshal_output_%(c_name)s(%(c_type)s r= et_in, QObject **ret_out, c_type=3Dret_type.c_type(), c_name=3Dret_type.c_name()) =20 =20 -def build_marshal_proto(name): - return ('void qmp_marshal_%s(QDict *args, QObject **ret, Error **errp)' - % c_name(name)) +def build_marshal_proto(name, async): + if async: + tmpl =3D 'void qmp_marshal_%s(QDict *args, QmpReturn *qret)' + else: + tmpl =3D 'void qmp_marshal_%s(QDict *args, QObject **ret, Error **= errp)' + return tmpl % c_name(name) =20 =20 -def gen_marshal_decl(name): +def gen_marshal_decl(name, async): return mcgen(''' %(proto)s; ''', - proto=3Dbuild_marshal_proto(name)) + proto=3Dbuild_marshal_proto(name, async)) =20 =20 -def gen_marshal(name, arg_type, boxed, ret_type): +def gen_marshal(name, arg_type, boxed, ret_type, async): have_args =3D arg_type and not arg_type.is_empty() =20 ret =3D mcgen(''' @@ -104,9 +176,9 @@ def gen_marshal(name, arg_type, boxed, ret_type): { Error *err =3D NULL; ''', - proto=3Dbuild_marshal_proto(name)) + proto=3Dbuild_marshal_proto(name, async)) =20 - if ret_type: + if ret_type and not async: ret +=3D mcgen(''' %(c_type)s retval; ''', @@ -153,12 +225,28 @@ def gen_marshal(name, arg_type, boxed, ret_type): } ''') =20 - ret +=3D gen_call(name, arg_type, boxed, ret_type) + if async: + ret +=3D gen_async_call(name, arg_type, boxed) + else: + ret +=3D gen_call(name, arg_type, boxed, ret_type) =20 ret +=3D mcgen(''' =20 out: +''') + + if async: + ret +=3D mcgen(''' + if (err) { + qmp_return_error(qret, err); + } +''') + else: + ret +=3D mcgen(''' error_propagate(errp, err); +''') + + ret +=3D mcgen(''' visit_free(v); ''') =20 @@ -193,24 +281,31 @@ out: return ret =20 =20 -def gen_register_command(name, success_response, allow_oob): +def gen_register_command(name, success_response, allow_oob, async): options =3D [] =20 if not success_response: options +=3D ['QCO_NO_SUCCESS_RESP'] if allow_oob: options +=3D ['QCO_ALLOW_OOB'] + if async: + options +=3D ['QCO_ASYNC'] =20 if not options: options =3D ['QCO_NO_OPTIONS'] =20 options =3D " | ".join(options) =20 + if async: + regfn =3D 'qmp_register_async_command' + else: + regfn =3D 'qmp_register_command' + ret =3D mcgen(''' - qmp_register_command(cmds, "%(name)s", + %(regfn)s(cmds, "%(name)s", qmp_marshal_%(c_name)s, %(opts)s); ''', - name=3Dname, c_name=3Dc_name(name), + regfn=3Dregfn, name=3Dname, c_name=3Dc_name(name), opts=3Doptions) return ret =20 @@ -276,16 +371,20 @@ void %(c_prefix)sqmp_init_marshal(QmpCommandList *cmd= s); genc.add(gen_registry(self._regy, self._prefix)) =20 def visit_command(self, name, info, arg_type, ret_type, - gen, success_response, boxed, allow_oob): + gen, success_response, boxed, allow_oob, async): if not gen: return - self._genh.add(gen_command_decl(name, arg_type, boxed, ret_type)) + self._genh.add(gen_command_decl(name, arg_type, boxed, ret_type, + success_response, async)) if ret_type and ret_type not in self._visited_ret_types[self._genc= ]: self._visited_ret_types[self._genc].add(ret_type) self._genc.add(gen_marshal_output(ret_type)) - self._genh.add(gen_marshal_decl(name)) - self._genc.add(gen_marshal(name, arg_type, boxed, ret_type)) - self._regy +=3D gen_register_command(name, success_response, allow= _oob) + if async and success_response: + self._genc.add(gen_async_return(name, ret_type)) + self._genh.add(gen_marshal_decl(name, async)) + self._genc.add(gen_marshal(name, arg_type, boxed, ret_type, async)) + self._regy +=3D gen_register_command(name, success_response, + allow_oob, async) =20 =20 def gen_commands(schema, output_dir, prefix): diff --git a/scripts/qapi/common.py b/scripts/qapi/common.py index 2c05e3c284..109562ccb4 100644 --- a/scripts/qapi/common.py +++ b/scripts/qapi/common.py @@ -922,7 +922,7 @@ def check_exprs(exprs): meta =3D 'command' check_keys(expr_elem, 'command', [], ['data', 'returns', 'gen', 'success-response', - 'boxed', 'allow-oob']) + 'boxed', 'allow-oob', 'async']) elif 'event' in expr: meta =3D 'event' check_keys(expr_elem, 'event', [], ['data', 'boxed']) @@ -1045,7 +1045,7 @@ class QAPISchemaVisitor(object): pass =20 def visit_command(self, name, info, arg_type, ret_type, - gen, success_response, boxed, allow_oob): + gen, success_response, boxed, allow_oob, async): pass =20 def visit_event(self, name, info, arg_type, boxed): @@ -1422,7 +1422,7 @@ class QAPISchemaAlternateType(QAPISchemaType): =20 class QAPISchemaCommand(QAPISchemaEntity): def __init__(self, name, info, doc, arg_type, ret_type, - gen, success_response, boxed, allow_oob): + gen, success_response, boxed, allow_oob, async): QAPISchemaEntity.__init__(self, name, info, doc) assert not arg_type or isinstance(arg_type, str) assert not ret_type or isinstance(ret_type, str) @@ -1434,6 +1434,7 @@ class QAPISchemaCommand(QAPISchemaEntity): self.success_response =3D success_response self.boxed =3D boxed self.allow_oob =3D allow_oob + self.async =3D async =20 def check(self, schema): if self._arg_type_name: @@ -1458,7 +1459,7 @@ class QAPISchemaCommand(QAPISchemaEntity): visitor.visit_command(self.name, self.info, self.arg_type, self.ret_type, self.gen, self.success_response, - self.boxed, self.allow_oob) + self.boxed, self.allow_oob, self.async) =20 =20 class QAPISchemaEvent(QAPISchemaEntity): @@ -1678,6 +1679,7 @@ class QAPISchema(object): success_response =3D expr.get('success-response', True) boxed =3D expr.get('boxed', False) allow_oob =3D expr.get('allow-oob', False) + async =3D expr.get('async', False) if isinstance(data, OrderedDict): data =3D self._make_implicit_object_type( name, info, doc, 'arg', self._make_members(data, info)) @@ -1686,7 +1688,7 @@ class QAPISchema(object): rets =3D self._make_array_type(rets[0], info) self._def_entity(QAPISchemaCommand(name, info, doc, data, rets, gen, success_response, - boxed, allow_oob)) + boxed, allow_oob, async)) =20 def _def_event(self, expr, info, doc): name =3D expr['event'] diff --git a/scripts/qapi/doc.py b/scripts/qapi/doc.py old mode 100644 new mode 100755 index 9b312b2c51..33b26e2bef --- a/scripts/qapi/doc.py +++ b/scripts/qapi/doc.py @@ -227,7 +227,7 @@ class QAPISchemaGenDocVisitor(qapi.common.QAPISchemaVis= itor): body=3Dtexi_entity(doc, 'Members'))) =20 def visit_command(self, name, info, arg_type, ret_type, - gen, success_response, boxed, allow_oob): + gen, success_response, boxed, allow_oob, async): doc =3D self.cur_doc if boxed: body =3D texi_body(doc) diff --git a/scripts/qapi/introspect.py b/scripts/qapi/introspect.py index f9e67e8227..5de60d0357 100644 --- a/scripts/qapi/introspect.py +++ b/scripts/qapi/introspect.py @@ -172,7 +172,7 @@ const QLitObject %(c_name)s =3D %(c_string)s; for m in variants.variants]}) =20 def visit_command(self, name, info, arg_type, ret_type, - gen, success_response, boxed, allow_oob): + gen, success_response, boxed, allow_oob, async): arg_type =3D arg_type or self._schema.the_empty_object_type ret_type =3D ret_type or self._schema.the_empty_object_type self._gen_qlit(name, 'command', diff --git a/tests/test-qmp-cmds.c b/tests/test-qmp-cmds.c index eeaac03d50..f1e6cde990 100644 --- a/tests/test-qmp-cmds.c +++ b/tests/test-qmp-cmds.c @@ -20,6 +20,28 @@ void qmp_cmd_success_response(Error **errp) { } =20 +static gboolean cmd_async_idle(gpointer user_data) +{ + QmpReturn *qret =3D user_data; + + qmp_cmd_async_return(qret, g_new0(Empty2, 1)); + + return G_SOURCE_REMOVE; +} + +void qmp_cmd_async(const char *filename, QmpReturn *qret) +{ + g_idle_add(cmd_async_idle, qret); +} + +void qmp_cmd_success_response_async(const char *filename, QmpReturn *qret) +{ + Error *err =3D NULL; + + error_setg(&err, "no response, but error ok"); + qmp_return_error(qret, err); +} + Empty2 *qmp_user_def_cmd0(Error **errp) { return g_new0(Empty2, 1); @@ -345,6 +367,43 @@ static void test_qmp_return_orderly(void) QDECREF(dict); } =20 +typedef struct QmpReturnAsync { + QmpSession session; + GMainLoop *loop; +} QmpReturnAsync; + +static void dispatch_return_async(QmpSession *session, QDict *resp) +{ + QmpReturnAsync *a =3D container_of(session, QmpReturnAsync, session); + + g_main_loop_quit(a->loop); + g_main_loop_unref(a->loop); + a->loop =3D NULL; +} + +static void test_qmp_return_async(void) +{ + QmpReturnAsync a =3D { 0, }; + QDict *args =3D qdict_new(); + QDict *req =3D qdict_new(); + + a.loop =3D g_main_loop_new(NULL, TRUE); + qmp_session_init(&a.session, &qmp_commands, + qmp_dispatch, dispatch_return_async); + + qdict_put_str(args, "filename", "test-filename"); + qdict_put_str(req, "execute", "cmd-async"); + qdict_put(req, "arguments", args); + qmp_dispatch(&a.session, req); + g_assert(a.loop); + + g_main_loop_run(a.loop); + g_assert(!a.loop); + + qmp_session_destroy(&a.session); + QDECREF(req); +} + int main(int argc, char **argv) { g_test_init(&argc, &argv, NULL); @@ -358,6 +417,7 @@ int main(int argc, char **argv) g_test_add_func("/qmp/dealloc_types", test_dealloc_types); g_test_add_func("/qmp/dealloc_partial", test_dealloc_partial); g_test_add_func("/qmp/return_orderly", test_qmp_return_orderly); + g_test_add_func("/qmp/return_async", test_qmp_return_async); =20 test_qmp_init_marshal(&qmp_commands); g_test_run(); diff --git a/tests/qapi-schema/qapi-schema-test.json b/tests/qapi-schema/qa= pi-schema-test.json index 96ff3a8e47..383369cd58 100644 --- a/tests/qapi-schema/qapi-schema-test.json +++ b/tests/qapi-schema/qapi-schema-test.json @@ -134,6 +134,11 @@ =20 { 'command': 'cmd-success-response', 'data': {}, 'success-response': false= } =20 +{ 'command': 'cmd-async', 'data': {'filename': 'str'}, + 'returns': 'Empty2', 'async': true } +{ 'command': 'cmd-success-response-async', 'data': {'filename': 'str'}, + 'async': true, 'success-response': false} + # Returning a non-dictionary requires a name from the whitelist { 'command': 'guest-get-time', 'data': {'a': 'int', '*b': 'int' }, 'returns': 'int' } diff --git a/tests/qapi-schema/qapi-schema-test.out b/tests/qapi-schema/qap= i-schema-test.out index cd3642be34..aa18f2c811 100644 --- a/tests/qapi-schema/qapi-schema-test.out +++ b/tests/qapi-schema/qapi-schema-test.out @@ -155,6 +155,14 @@ command user_def_cmd2 q_obj_user_def_cmd2-arg -> UserD= efTwo gen=3DTrue success_response=3DTrue boxed=3DFalse command cmd-success-response None -> None gen=3DTrue success_response=3DFalse boxed=3DFalse +object q_obj_cmd-async-arg + member filename: str optional=3DFalse +command cmd-async q_obj_cmd-async-arg -> Empty2 + gen=3DTrue success_response=3DTrue boxed=3DFalse async=3DTrue +object q_obj_cmd-success-response-async-arg + member filename: str optional=3DFalse +command cmd-success-response-async q_obj_cmd-success-response-async-arg ->= None + gen=3DTrue success_response=3DFalse boxed=3DFalse async=3DTrue object q_obj_guest-get-time-arg member a: int optional=3DFalse member b: int optional=3DTrue diff --git a/tests/qapi-schema/test-qapi.py b/tests/qapi-schema/test-qapi.py index 10e68b01d9..491bdc73dd 100644 --- a/tests/qapi-schema/test-qapi.py +++ b/tests/qapi-schema/test-qapi.py @@ -42,11 +42,12 @@ class QAPISchemaTestVisitor(QAPISchemaVisitor): self._print_variants(variants) =20 def visit_command(self, name, info, arg_type, ret_type, - gen, success_response, boxed, allow_oob): + gen, success_response, boxed, allow_oob, async): print('command %s %s -> %s' % \ (name, arg_type and arg_type.name, ret_type and ret_type.nam= e)) - print(' gen=3D%s success_response=3D%s boxed=3D%s' % \ - (gen, success_response, boxed)) + print(' gen=3D%s success_response=3D%s boxed=3D%s%s' % \ + (gen, success_response, boxed, + ' async=3DTrue' if async else '')) =20 def visit_event(self, name, info, arg_type, boxed): print('event %s %s' % (name, arg_type and arg_type.name)) --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078853482493.1345672164882; Mon, 26 Mar 2018 08:40:53 -0700 (PDT) Received: from localhost ([::1]:57448 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0UEt-00085R-US for importer@patchew.org; Mon, 26 Mar 2018 11:40:51 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55344) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tln-0006Ky-5I for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:48 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tlm-0003Q1-1S for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:47 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:57308 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tll-0003Po-Sz for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:45 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 8B95D722C4; Mon, 26 Mar 2018 15:10:45 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 1E3837C55; Mon, 26 Mar 2018 15:10:39 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:09 +0200 Message-Id: <20180326150916.9602-32-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:10:45 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:10:45 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 31/38] qmp: add qmp_return_is_cancelled() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" If the client is gone, and the session finished, no need to return. The async handler can use this information to avoid unnecessary work and exit earlier. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/qapi/qmp/dispatch.h | 8 ++++++++ qapi/qmp-dispatch.c | 10 ++++++++++ 2 files changed, 18 insertions(+) diff --git a/include/qapi/qmp/dispatch.h b/include/qapi/qmp/dispatch.h index e426317346..6ee82371a2 100644 --- a/include/qapi/qmp/dispatch.h +++ b/include/qapi/qmp/dispatch.h @@ -91,6 +91,14 @@ void qmp_return_free(QmpReturn *qret); void qmp_return(QmpReturn *qret, QObject *rsp); void qmp_return_error(QmpReturn *qret, Error *err); =20 +/* + * @qmp_return_is_cancelled: + * + * Return true if the QmpReturn is cancelled, and free the QmpReturn + * in this case. + */ +bool qmp_return_is_cancelled(QmpReturn *qret); + void qmp_register_command(QmpCommandList *cmds, const char *name, QmpCommandFunc *fn, QmpCommandOptions options); void qmp_register_async_command(QmpCommandList *cmds, const char *name, diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c index f7d9931734..99f5128170 100644 --- a/qapi/qmp-dispatch.c +++ b/qapi/qmp-dispatch.c @@ -63,6 +63,16 @@ void qmp_return_free(QmpReturn *qret) } } =20 +bool qmp_return_is_cancelled(QmpReturn *qret) +{ + if (!qret->session) { + qmp_return_free(qret); + return true; + } + + return false; +} + static void qmp_return_orderly(QmpReturn *qret) { QmpSession *session =3D qret->session; --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078460491526.7625768974077; Mon, 26 Mar 2018 08:34:20 -0700 (PDT) Received: from localhost ([::1]:57402 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0U8V-0001uB-3p for importer@patchew.org; Mon, 26 Mar 2018 11:34:15 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55459) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tm0-0006Wy-EC for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:04 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tls-0003VM-Oo for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:00 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:47536 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tls-0003V3-Jo for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:52 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 400B3401DE65; Mon, 26 Mar 2018 15:10:52 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 36D6310B0F20; Mon, 26 Mar 2018 15:10:47 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:10 +0200 Message-Id: <20180326150916.9602-33-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:10:52 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:10:52 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 32/38] monitor: add qmp_return_get_monitor() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" If necessary, add an helper that can be used to retrieve the associated monitor. This is useful for asynchronous commands that may have to update cur_mon for various reasons. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/monitor/monitor.h | 3 +++ monitor.c | 6 ++++++ 2 files changed, 9 insertions(+) diff --git a/include/monitor/monitor.h b/include/monitor/monitor.h index 0cb0538a31..2052a6b4e4 100644 --- a/include/monitor/monitor.h +++ b/include/monitor/monitor.h @@ -5,6 +5,7 @@ #include "block/block.h" #include "qapi/qapi-types-misc.h" #include "qemu/readline.h" +#include "qapi/qmp/dispatch.h" =20 extern Monitor *cur_mon; =20 @@ -46,4 +47,6 @@ int monitor_fdset_dup_fd_add(int64_t fdset_id, int dup_fd= ); void monitor_fdset_dup_fd_remove(int dup_fd); int monitor_fdset_dup_fd_find(int dup_fd); =20 +Monitor *qmp_return_get_monitor(QmpReturn *qret); + #endif /* MONITOR_H */ diff --git a/monitor.c b/monitor.c index 73a06d4156..f7826f5626 100644 --- a/monitor.c +++ b/monitor.c @@ -281,6 +281,12 @@ bool monitor_cur_is_qmp(void) return cur_mon && monitor_is_qmp(cur_mon); } =20 +Monitor *qmp_return_get_monitor(QmpReturn *qret) +{ + return qret->session ? + container_of(qret->session, Monitor, qmp.session) : NULL; +} + void monitor_read_command(Monitor *mon, int show_prompt) { if (!mon->rs) --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522079000494588.3688027174535; Mon, 26 Mar 2018 08:43:20 -0700 (PDT) Received: from localhost ([::1]:57465 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0UHH-00023s-Gd for importer@patchew.org; Mon, 26 Mar 2018 11:43:19 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55434) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tly-0006VJ-Rr for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:00 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tlu-0003XI-Gl for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:58 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:48790 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tlu-0003WK-BS for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:54 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 011644068026; Mon, 26 Mar 2018 15:10:54 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 8C97710B0F20; Mon, 26 Mar 2018 15:10:53 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:11 +0200 Message-Id: <20180326150916.9602-34-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:10:54 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 26 Mar 2018 15:10:54 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 33/38] console: graphic_hw_update return true if async X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" qxl_render_update() returns true if the update is deferred. Let the caller know if the update is immediate or async. Signed-off-by: Marc-Andr=C3=A9 Lureau --- hw/display/qxl.h | 2 +- include/ui/console.h | 3 ++- hw/display/qxl-render.c | 5 +++-- hw/display/qxl.c | 8 ++++---- ui/console.c | 14 ++++++++++++-- 5 files changed, 22 insertions(+), 10 deletions(-) diff --git a/hw/display/qxl.h b/hw/display/qxl.h index 089696ef62..cc4f83f990 100644 --- a/hw/display/qxl.h +++ b/hw/display/qxl.h @@ -169,7 +169,7 @@ int qxl_log_command(PCIQXLDevice *qxl, const char *ring= , QXLCommandExt *ext); =20 /* qxl-render.c */ void qxl_render_resize(PCIQXLDevice *qxl); -void qxl_render_update(PCIQXLDevice *qxl); +bool qxl_render_update(PCIQXLDevice *qxl); int qxl_render_cursor(PCIQXLDevice *qxl, QXLCommandExt *ext); void qxl_render_update_area_done(PCIQXLDevice *qxl, QXLCookie *cookie); void qxl_render_update_area_bh(void *opaque); diff --git a/include/ui/console.h b/include/ui/console.h index 6d2c052068..d2b6c46a62 100644 --- a/include/ui/console.h +++ b/include/ui/console.h @@ -374,6 +374,7 @@ static inline void console_write_ch(console_ch_t *dest,= uint32_t ch) typedef struct GraphicHwOps { void (*invalidate)(void *opaque); void (*gfx_update)(void *opaque); + bool (*gfx_update_async)(void *opaque); void (*text_update)(void *opaque, console_ch_t *text); void (*update_interval)(void *opaque, uint64_t interval); int (*ui_info)(void *opaque, uint32_t head, QemuUIInfo *info); @@ -388,7 +389,7 @@ void graphic_console_set_hwops(QemuConsole *con, void *opaque); void graphic_console_close(QemuConsole *con); =20 -void graphic_hw_update(QemuConsole *con); +bool graphic_hw_update(QemuConsole *con); void graphic_hw_invalidate(QemuConsole *con); void graphic_hw_text_update(QemuConsole *con, console_ch_t *chardata); void graphic_hw_gl_block(QemuConsole *con, bool block); diff --git a/hw/display/qxl-render.c b/hw/display/qxl-render.c index e7ac4f8789..62574173a2 100644 --- a/hw/display/qxl-render.c +++ b/hw/display/qxl-render.c @@ -163,7 +163,7 @@ static void qxl_render_update_area_unlocked(PCIQXLDevic= e *qxl) * callbacks are called by spice_server thread, deferring to bh called fro= m the * io thread. */ -void qxl_render_update(PCIQXLDevice *qxl) +bool qxl_render_update(PCIQXLDevice *qxl) { QXLCookie *cookie; =20 @@ -172,7 +172,7 @@ void qxl_render_update(PCIQXLDevice *qxl) if (!runstate_is_running() || !qxl->guest_primary.commands) { qxl_render_update_area_unlocked(qxl); qemu_mutex_unlock(&qxl->ssd.lock); - return; + return false; } =20 qxl->guest_primary.commands =3D 0; @@ -183,6 +183,7 @@ void qxl_render_update(PCIQXLDevice *qxl) qxl_set_rect_to_surface(qxl, &cookie->u.render.area); qxl_spice_update_area(qxl, 0, &cookie->u.render.area, NULL, 0, 1 /* clear_dirty_region */, QXL_ASYNC, cookie= ); + return true; } =20 void qxl_render_update_area_bh(void *opaque) diff --git a/hw/display/qxl.c b/hw/display/qxl.c index a71714ccb4..7dda2ae576 100644 --- a/hw/display/qxl.c +++ b/hw/display/qxl.c @@ -136,7 +136,7 @@ static void qxl_reset_memslots(PCIQXLDevice *d); static void qxl_reset_surfaces(PCIQXLDevice *d); static void qxl_ring_set_dirty(PCIQXLDevice *qxl); =20 -static void qxl_hw_update(void *opaque); +static bool qxl_hw_update_async(void *opaque); =20 void qxl_set_guest_bug(PCIQXLDevice *qxl, const char *msg, ...) { @@ -1167,7 +1167,7 @@ static const QXLInterface qxl_interface =3D { }; =20 static const GraphicHwOps qxl_ops =3D { - .gfx_update =3D qxl_hw_update, + .gfx_update_async =3D qxl_hw_update_async, }; =20 static void qxl_enter_vga_mode(PCIQXLDevice *d) @@ -1889,11 +1889,11 @@ static void qxl_send_events(PCIQXLDevice *d, uint32= _t events) =20 /* graphics console */ =20 -static void qxl_hw_update(void *opaque) +static bool qxl_hw_update_async(void *opaque) { PCIQXLDevice *qxl =3D opaque; =20 - qxl_render_update(qxl); + return qxl_render_update(qxl); } =20 static void qxl_dirty_one_surface(PCIQXLDevice *qxl, QXLPHYSICAL pqxl, diff --git a/ui/console.c b/ui/console.c index 530a491987..0774cd3366 100644 --- a/ui/console.c +++ b/ui/console.c @@ -256,14 +256,24 @@ static void gui_setup_refresh(DisplayState *ds) ds->have_text =3D have_text; } =20 -void graphic_hw_update(QemuConsole *con) +bool graphic_hw_update(QemuConsole *con) { if (!con) { con =3D active_console; } - if (con && con->hw_ops->gfx_update) { + + if (!con) { + return false; + } + + if (con->hw_ops->gfx_update_async) { + return con->hw_ops->gfx_update_async(con->hw); + } else if (con->hw_ops->gfx_update) { con->hw_ops->gfx_update(con->hw); + return false; } + + return false; } =20 void graphic_hw_gl_block(QemuConsole *con, bool block) --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078980882708.2371393624144; Mon, 26 Mar 2018 08:43:00 -0700 (PDT) Received: from localhost ([::1]:57464 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0UGy-0001l4-3j for importer@patchew.org; Mon, 26 Mar 2018 11:43:00 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55422) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tlx-0006UE-OL for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:01 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tlv-0003Zd-Sf for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:57 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:57320 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tlv-0003Z6-OL for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:55 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 628B5722C5; Mon, 26 Mar 2018 15:10:55 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 14B74D7DFA; Mon, 26 Mar 2018 15:10:54 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:12 +0200 Message-Id: <20180326150916.9602-35-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:10:55 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 26 Mar 2018 15:10:55 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 34/38] console: add graphic_hw_update_done() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Add a function to be called when an async graphic update is done. Signed-off-by: Marc-Andr=C3=A9 Lureau --- include/ui/console.h | 1 + hw/display/qxl-render.c | 9 +++++++-- ui/console.c | 4 ++++ 3 files changed, 12 insertions(+), 2 deletions(-) diff --git a/include/ui/console.h b/include/ui/console.h index d2b6c46a62..fc21621656 100644 --- a/include/ui/console.h +++ b/include/ui/console.h @@ -390,6 +390,7 @@ void graphic_console_set_hwops(QemuConsole *con, void graphic_console_close(QemuConsole *con); =20 bool graphic_hw_update(QemuConsole *con); +void graphic_hw_update_done(QemuConsole *con); void graphic_hw_invalidate(QemuConsole *con); void graphic_hw_text_update(QemuConsole *con, console_ch_t *chardata); void graphic_hw_gl_block(QemuConsole *con, bool block); diff --git a/hw/display/qxl-render.c b/hw/display/qxl-render.c index 62574173a2..08722d2833 100644 --- a/hw/display/qxl-render.c +++ b/hw/display/qxl-render.c @@ -106,7 +106,7 @@ static void qxl_render_update_area_unlocked(PCIQXLDevic= e *qxl) qxl->guest_primary.surface= .mem, MEMSLOT_GROUP_GUEST); if (!qxl->guest_primary.data) { - return; + goto end; } qxl_set_rect_to_surface(qxl, &qxl->dirty[0]); qxl->num_dirty_rects =3D 1; @@ -134,7 +134,7 @@ static void qxl_render_update_area_unlocked(PCIQXLDevic= e *qxl) } =20 if (!qxl->guest_primary.data) { - return; + goto end; } for (i =3D 0; i < qxl->num_dirty_rects; i++) { if (qemu_spice_rect_is_empty(qxl->dirty+i)) { @@ -155,6 +155,11 @@ static void qxl_render_update_area_unlocked(PCIQXLDevi= ce *qxl) qxl->dirty[i].bottom - qxl->dirty[i].top); } qxl->num_dirty_rects =3D 0; + +end: + if (qxl->render_update_cookie_num =3D=3D 0) { + graphic_hw_update_done(qxl->ssd.dcl.con); + } } =20 /* diff --git a/ui/console.c b/ui/console.c index 0774cd3366..29234605a7 100644 --- a/ui/console.c +++ b/ui/console.c @@ -256,6 +256,10 @@ static void gui_setup_refresh(DisplayState *ds) ds->have_text =3D have_text; } =20 +void graphic_hw_update_done(QemuConsole *con) +{ +} + bool graphic_hw_update(QemuConsole *con) { if (!con) { --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078649362801.6201296065602; Mon, 26 Mar 2018 08:37:29 -0700 (PDT) Received: from localhost ([::1]:57424 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0UBc-0004l9-EO for importer@patchew.org; Mon, 26 Mar 2018 11:37:28 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55445) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tlz-0006W1-GH for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:01 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tlx-0003bO-SB for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:59 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:47546 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tlx-0003b6-L8 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:57 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 4F082401DE69; Mon, 26 Mar 2018 15:10:57 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 7E928202322B; Mon, 26 Mar 2018 15:10:56 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:13 +0200 Message-Id: <20180326150916.9602-36-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:10:57 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.6]); Mon, 26 Mar 2018 15:10:57 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 35/38] console: make screendump asynchronous X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Make screendump asynchronous to provide correct screendumps. HMP doesn't have async support, so it has to remain synchronous and potentially incorrect to avoid potential races. Fixes: https://bugzilla.redhat.com/show_bug.cgi?id=3D1230527 Signed-off-by: Marc-Andr=C3=A9 Lureau --- qapi/ui.json | 3 +- include/ui/console.h | 3 ++ hmp.c | 2 +- ui/console.c | 99 ++++++++++++++++++++++++++++++++++++++++---- 4 files changed, 96 insertions(+), 11 deletions(-) diff --git a/qapi/ui.json b/qapi/ui.json index 5d01ad4304..4d2c326fb9 100644 --- a/qapi/ui.json +++ b/qapi/ui.json @@ -96,7 +96,8 @@ # ## { 'command': 'screendump', - 'data': {'filename': 'str', '*device': 'str', '*head': 'int'} } + 'data': {'filename': 'str', '*device': 'str', '*head': 'int'}, + 'async': true } =20 ## # =3D=3D Spice diff --git a/include/ui/console.h b/include/ui/console.h index fc21621656..0c02190963 100644 --- a/include/ui/console.h +++ b/include/ui/console.h @@ -74,6 +74,9 @@ struct MouseTransformInfo { }; =20 void hmp_mouse_set(Monitor *mon, const QDict *qdict); +void hmp_screendump_sync(const char *filename, + bool has_device, const char *device, + bool has_head, int64_t head, Error **errp); =20 /* keysym is a unicode code except for special keys (see QEMU_KEY_xxx constants) */ diff --git a/hmp.c b/hmp.c index 679467d85a..da9008fe63 100644 --- a/hmp.c +++ b/hmp.c @@ -2144,7 +2144,7 @@ void hmp_screendump(Monitor *mon, const QDict *qdict) int64_t head =3D qdict_get_try_int(qdict, "head", 0); Error *err =3D NULL; =20 - qmp_screendump(filename, id !=3D NULL, id, id !=3D NULL, head, &err); + hmp_screendump_sync(filename, id !=3D NULL, id, id !=3D NULL, head, &e= rr); hmp_handle_error(mon, &err); } =20 diff --git a/ui/console.c b/ui/console.c index 29234605a7..da51861191 100644 --- a/ui/console.c +++ b/ui/console.c @@ -32,6 +32,7 @@ #include "chardev/char-fe.h" #include "trace.h" #include "exec/memory.h" +#include "monitor/monitor.h" =20 #define DEFAULT_BACKSCROLL 512 #define CONSOLE_CURSOR_PERIOD 500 @@ -116,6 +117,12 @@ typedef enum { TEXT_CONSOLE_FIXED_SIZE } console_type_t; =20 +struct qmp_screendump { + gchar *filename; + QmpReturn *ret; + QLIST_ENTRY(qmp_screendump) link; +}; + struct QemuConsole { Object parent; =20 @@ -165,6 +172,8 @@ struct QemuConsole { QEMUFIFO out_fifo; uint8_t out_fifo_buf[16]; QEMUTimer *kbd_timer; + + QLIST_HEAD(, qmp_screendump) qmp_screendumps; }; =20 struct DisplayState { @@ -190,6 +199,8 @@ static void dpy_refresh(DisplayState *s); static DisplayState *get_alloc_displaystate(void); static void text_console_update_cursor_timer(void); static void text_console_update_cursor(void *opaque); +static void ppm_save(const char *filename, DisplaySurface *ds, + Error **errp); =20 static void gui_update(void *opaque) { @@ -256,8 +267,42 @@ static void gui_setup_refresh(DisplayState *ds) ds->have_text =3D have_text; } =20 +static void qmp_screendump_finish(QemuConsole *con, const char *filename, + QmpReturn *ret) +{ + Error *err =3D NULL; + DisplaySurface *surface; + Monitor *prev_mon =3D cur_mon; + + if (qmp_return_is_cancelled(ret)) { + return; + } + + cur_mon =3D qmp_return_get_monitor(ret); + surface =3D qemu_console_surface(con); + + /* FIXME: async save with coroutine? it would have to copy or lock + * the surface. */ + ppm_save(filename, surface, &err); + + if (err) { + qmp_return_error(ret, err); + } else { + qmp_screendump_return(ret); + } + cur_mon =3D prev_mon; +} + void graphic_hw_update_done(QemuConsole *con) { + struct qmp_screendump *dump, *next; + + QLIST_FOREACH_SAFE(dump, &con->qmp_screendumps, link, next) { + qmp_screendump_finish(con, dump->filename, dump->ret); + g_free(dump->filename); + QLIST_REMOVE(dump, link); + g_free(dump); + } } =20 bool graphic_hw_update(QemuConsole *con) @@ -358,35 +403,70 @@ write_err: goto out; } =20 -void qmp_screendump(const char *filename, bool has_device, const char *dev= ice, - bool has_head, int64_t head, Error **errp) + +static QemuConsole *get_console(bool has_device, const char *device, + bool has_head, int64_t head, Error **errp) { - QemuConsole *con; - DisplaySurface *surface; + QemuConsole *con =3D NULL; =20 if (has_device) { con =3D qemu_console_lookup_by_device_name(device, has_head ? head= : 0, errp); - if (!con) { - return; - } } else { if (has_head) { error_setg(errp, "'head' must be specified together with 'devi= ce'"); - return; + return NULL; } con =3D qemu_console_lookup_by_index(0); if (!con) { error_setg(errp, "There is no console to take a screendump fro= m"); - return; } } =20 + return con; +} + +void hmp_screendump_sync(const char *filename, + bool has_device, const char *device, + bool has_head, int64_t head, Error **errp) +{ + DisplaySurface *surface; + QemuConsole *con =3D get_console(has_device, device, has_head, head, e= rrp); + + if (!con) { + return; + } + /* This may not complete the drawing with Spice, you may have + * glitches or outdated dumps, use qmp instead! */ graphic_hw_update(con); surface =3D qemu_console_surface(con); ppm_save(filename, surface, errp); } =20 +void qmp_screendump(const char *filename, + bool has_device, const char *device, + bool has_head, int64_t head, + QmpReturn *qret) +{ + Error *err =3D NULL; + bool async; + QemuConsole *con =3D get_console(has_device, device, has_head, head, &= err); + + if (!con) { + qmp_return_error(qret, err); + return; + } + async =3D graphic_hw_update(con); + if (async) { + struct qmp_screendump *dump =3D g_new(struct qmp_screendump, 1); + dump->filename =3D g_strdup(filename); + dump->ret =3D qret; + QLIST_INSERT_HEAD(&con->qmp_screendumps, dump, link); + } else { + qmp_screendump_finish(con, filename, qret); + } +} + void graphic_hw_text_update(QemuConsole *con, console_ch_t *chardata) { if (!con) { @@ -1280,6 +1360,7 @@ static QemuConsole *new_console(DisplayState *ds, con= sole_type_t console_type, obj =3D object_new(TYPE_QEMU_CONSOLE); s =3D QEMU_CONSOLE(obj); s->head =3D head; + QLIST_INIT(&s->qmp_screendumps); object_property_add_link(obj, "device", TYPE_DEVICE, (Object **)&s->device, object_property_allow_set_link, --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522078822556854.089366444054; Mon, 26 Mar 2018 08:40:22 -0700 (PDT) Received: from localhost ([::1]:57441 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0UEP-0007Yp-Hl for importer@patchew.org; Mon, 26 Mar 2018 11:40:21 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55454) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tm0-0006Wh-6m for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:01 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tlz-0003cZ-Bu for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:00 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36686 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tlz-0003c1-1D for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:10:59 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.rdu2.redhat.com [10.11.54.6]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id AC16E406E8A4; Mon, 26 Mar 2018 15:10:58 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 5C2C3215CDAE; Mon, 26 Mar 2018 15:10:58 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:14 +0200 Message-Id: <20180326150916.9602-37-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.6 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:58 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:10:58 +0000 (UTC) for IP:'10.11.54.6' DOMAIN:'int-mx06.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 36/38] monitor: start making qmp_human_monitor_command() asynchronous X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" This prepares the work for HMP commands to be asynchronous. For now this will and the return synchronously. Signed-off-by: Marc-Andr=C3=A9 Lureau --- qapi/misc.json | 3 ++- monitor.c | 14 ++++++++------ 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/qapi/misc.json b/qapi/misc.json index 5636f4a149..04e704eb6c 100644 --- a/qapi/misc.json +++ b/qapi/misc.json @@ -1307,7 +1307,8 @@ ## { 'command': 'human-monitor-command', 'data': {'command-line': 'str', '*cpu-index': 'int'}, - 'returns': 'str' } + 'returns': 'str', + 'async': true } =20 ## # @ObjectPropertyInfo: diff --git a/monitor.c b/monitor.c index f7826f5626..e11c0abdca 100644 --- a/monitor.c +++ b/monitor.c @@ -637,8 +637,8 @@ static void monitor_data_destroy(Monitor *mon) g_queue_free(mon->qmp.qmp_requests); } =20 -char *qmp_human_monitor_command(const char *command_line, bool has_cpu_ind= ex, - int64_t cpu_index, Error **errp) +void qmp_human_monitor_command(const char *command_line, bool has_cpu_inde= x, + int64_t cpu_index, QmpReturn *qret) { char *output =3D NULL; Monitor *old_mon, hmp; @@ -651,15 +651,15 @@ char *qmp_human_monitor_command(const char *command_l= ine, bool has_cpu_index, if (has_cpu_index) { int ret =3D monitor_set_cpu(cpu_index); if (ret < 0) { - cur_mon =3D old_mon; - error_setg(errp, QERR_INVALID_PARAMETER_VALUE, "cpu-index", + Error *err =3D NULL; + error_setg(&err, QERR_INVALID_PARAMETER_VALUE, "cpu-index", "a CPU number"); + qmp_return_error(qret, err); goto out; } } =20 handle_hmp_command(&hmp, command_line); - cur_mon =3D old_mon; =20 qemu_mutex_lock(&hmp.out_lock); if (qstring_get_length(hmp.outbuf) > 0) { @@ -669,9 +669,11 @@ char *qmp_human_monitor_command(const char *command_li= ne, bool has_cpu_index, } qemu_mutex_unlock(&hmp.out_lock); =20 + qmp_human_monitor_command_return(qret, output); + out: monitor_data_destroy(&hmp); - return output; + cur_mon =3D old_mon; } =20 static int compare_cmd(const char *name, const char *list) --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522079165423464.4688628098744; Mon, 26 Mar 2018 08:46:05 -0700 (PDT) Received: from localhost ([::1]:57483 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0UJw-0004la-GH for importer@patchew.org; Mon, 26 Mar 2018 11:46:04 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55517) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0Tm8-0006g0-Rc for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:10 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tm5-0003fR-LV for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:08 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:36690 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tm5-0003fA-G9 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:05 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.rdu2.redhat.com [10.11.54.5]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 2B22B406E971; Mon, 26 Mar 2018 15:11:05 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id C9CA3D7DFA; Mon, 26 Mar 2018 15:10:59 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:15 +0200 Message-Id: <20180326150916.9602-38-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.11.54.5 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:11:05 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.7]); Mon, 26 Mar 2018 15:11:05 +0000 (UTC) for IP:'10.11.54.5' DOMAIN:'int-mx05.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 37/38] monitor: teach HMP about asynchronous commands X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Similar to how we handle both synchronous and asynchronous commands in QMP, HMP gains a new async_cmd() that will allow the command to complete asynchronously. For interactive reasons, and command ordering, the HMP monitor is suspended until the asynchronous command completes. Note that QMP human-monitor-command is modified to deal with it, by using a specialized QmpSession return callback to destroy the temporary HMP monitor. Signed-off-by: Marc-Andr=C3=A9 Lureau --- monitor.c | 106 ++++++++++++++++++++++++++++++++++++++++-------------- 1 file changed, 79 insertions(+), 27 deletions(-) diff --git a/monitor.c b/monitor.c index e11c0abdca..018bd9280f 100644 --- a/monitor.c +++ b/monitor.c @@ -127,13 +127,17 @@ typedef struct mon_cmd_t { const char *args_type; const char *params; const char *help; - void (*cmd)(Monitor *mon, const QDict *qdict); + union { + void (*cmd)(Monitor *mon, const QDict *qdict); + void (*async_cmd)(Monitor *mon, const QDict *qdict, QmpReturn *qre= t); + }; /* @sub_table is a list of 2nd level of commands. If it does not exist, * cmd should be used. If it exists, sub_table[?].cmd should be * used, and cmd of 1st level plays the role of help function. */ struct mon_cmd_t *sub_table; void (*command_completion)(ReadLineState *rs, int nb_args, const char = *str); + bool async; } mon_cmd_t; =20 /* file descriptors passed via SCM_RIGHTS */ @@ -203,6 +207,7 @@ struct Monitor { int suspend_cnt; /* Needs to be accessed atomically */ bool skip_flush; bool use_io_thr; + QmpReturn *for_qmp_command; =20 QemuMutex out_lock; QString *outbuf; @@ -607,7 +612,7 @@ static void monitor_qapi_event_init(void) qmp_event_set_func_emit(monitor_qapi_event_queue); } =20 -static void handle_hmp_command(Monitor *mon, const char *cmdline); +static bool handle_hmp_command(Monitor *mon, const char *cmdline); =20 static void monitor_data_init(Monitor *mon, bool skip_flush, bool use_io_thr) @@ -637,16 +642,68 @@ static void monitor_data_destroy(Monitor *mon) g_queue_free(mon->qmp.qmp_requests); } =20 +static void free_temporary_hmp(void *opaque) +{ + Monitor *hmp =3D opaque; + + qmp_session_destroy(&hmp->qmp.session); + monitor_data_destroy(hmp); + g_free(hmp); +} + +static AioContext *monitor_get_aio_context(void) +{ + return iothread_get_aio_context(mon_global.mon_iothread); +} + +static void qmp_human_monitor_command_finish(Monitor *hmp, QmpReturn *qret) +{ + char *output; + + if (qstring_get_length(hmp->outbuf) > 0) { + output =3D g_strdup(qstring_get_str(hmp->outbuf)); + } else { + output =3D g_strdup(""); + } + + qmp_human_monitor_command_return(qret, output); + + if (hmp->for_qmp_command) { + aio_bh_schedule_oneshot(monitor_get_aio_context(), + free_temporary_hmp, hmp); + } +} + +static void hmp_dispatch_return_cb(QmpSession *session, QDict *rsp) +{ + Monitor *hmp =3D container_of(session, Monitor, qmp.session); + QDict *err =3D qdict_get_qdict(rsp, "error"); + Monitor *old_mon =3D cur_mon; + + cur_mon =3D hmp; + if (err) { + error_report("%s", qdict_get_str(err, "desc")); + } /* XXX: else, report depending on command */ + + if (hmp->for_qmp_command) { + qmp_human_monitor_command_finish(hmp, hmp->for_qmp_command); + } else { + monitor_resume(hmp); + } + cur_mon =3D old_mon; +} + void qmp_human_monitor_command(const char *command_line, bool has_cpu_inde= x, int64_t cpu_index, QmpReturn *qret) { - char *output =3D NULL; - Monitor *old_mon, hmp; + Monitor *old_mon, *hmp =3D g_new0(Monitor, 1); =20 - monitor_data_init(&hmp, true, false); + monitor_data_init(hmp, true, false); + qmp_session_init(&hmp->qmp.session, NULL, NULL, hmp_dispatch_return_cb= ); + hmp->for_qmp_command =3D qret; =20 old_mon =3D cur_mon; - cur_mon =3D &hmp; + cur_mon =3D hmp; =20 if (has_cpu_index) { int ret =3D monitor_set_cpu(cpu_index); @@ -659,20 +716,11 @@ void qmp_human_monitor_command(const char *command_li= ne, bool has_cpu_index, } } =20 - handle_hmp_command(&hmp, command_line); - - qemu_mutex_lock(&hmp.out_lock); - if (qstring_get_length(hmp.outbuf) > 0) { - output =3D g_strdup(qstring_get_str(hmp.outbuf)); - } else { - output =3D g_strdup(""); + if (!handle_hmp_command(hmp, command_line)) { + qmp_human_monitor_command_finish(hmp, qret); } - qemu_mutex_unlock(&hmp.out_lock); - - qmp_human_monitor_command_return(qret, output); =20 out: - monitor_data_destroy(&hmp); cur_mon =3D old_mon; } =20 @@ -3244,7 +3292,7 @@ fail: return NULL; } =20 -static void handle_hmp_command(Monitor *mon, const char *cmdline) +static bool handle_hmp_command(Monitor *mon, const char *cmdline) { QDict *qdict; const mon_cmd_t *cmd; @@ -3253,18 +3301,25 @@ static void handle_hmp_command(Monitor *mon, const = char *cmdline) =20 cmd =3D monitor_parse_command(mon, cmdline, &cmdline, mon->cmd_table); if (!cmd) { - return; + return false; } =20 qdict =3D monitor_parse_arguments(mon, &cmdline, cmd); if (!qdict) { monitor_printf(mon, "Try \"help %s\" for more information\n", cmd->name); - return; + return false; + } + if (cmd->async) { + QmpReturn *qret =3D qmp_return_new(&mon->qmp.session, NULL); + monitor_suspend(mon); + cmd->async_cmd(mon, qdict, qret); + } else { + cmd->cmd(mon, qdict); } - - cmd->cmd(mon, qdict); QDECREF(qdict); + + return cmd->async; } =20 static void cmd_completion(Monitor *mon, const char *name, const char *lis= t) @@ -4296,11 +4351,6 @@ static GMainContext *monitor_get_io_context(void) return iothread_get_g_main_context(mon_global.mon_iothread); } =20 -static AioContext *monitor_get_aio_context(void) -{ - return iothread_get_aio_context(mon_global.mon_iothread); -} - static void monitor_iothread_init(void) { mon_global.mon_iothread =3D iothread_create("mon_iothread", @@ -4439,6 +4489,8 @@ void monitor_init(Chardev *chr, int flags) NULL, mon, NULL, true); } } else { + qmp_session_init(&mon->qmp.session, + NULL, NULL, hmp_dispatch_return_cb); qemu_chr_fe_set_handlers(&mon->chr, monitor_can_read, monitor_read, monitor_event, NULL, mon, NULL, true); } --=20 2.17.0.rc1.1.g4c4f2b46a3 From nobody Thu May 2 09:48:48 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1522079142037334.5633931957377; Mon, 26 Mar 2018 08:45:42 -0700 (PDT) Received: from localhost ([::1]:57476 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0UJV-0004MO-GY for importer@patchew.org; Mon, 26 Mar 2018 11:45:37 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:55525) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1f0TmB-0006iB-55 for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:12 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1f0Tm7-0003gC-1b for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:11 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:38380 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1f0Tm6-0003fo-TB for qemu-devel@nongnu.org; Mon, 26 Mar 2018 11:11:06 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.rdu2.redhat.com [10.11.54.6]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 8B2257705F; Mon, 26 Mar 2018 15:11:06 +0000 (UTC) Received: from localhost (ovpn-112-61.ams2.redhat.com [10.36.112.61]) by smtp.corp.redhat.com (Postfix) with ESMTP id 3CE41215CDAE; Mon, 26 Mar 2018 15:11:06 +0000 (UTC) From: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= To: qemu-devel@nongnu.org Date: Mon, 26 Mar 2018 17:09:16 +0200 Message-Id: <20180326150916.9602-39-marcandre.lureau@redhat.com> In-Reply-To: <20180326150916.9602-1-marcandre.lureau@redhat.com> References: <20180326150916.9602-1-marcandre.lureau@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.6 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:11:06 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.1]); Mon, 26 Mar 2018 15:11:06 +0000 (UTC) for IP:'10.11.54.6' DOMAIN:'int-mx06.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'marcandre.lureau@redhat.com' RCPT:'' Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH v3 38/38] hmp: call the asynchronous QMP screendump to fix outdated/glitches X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Eduardo Habkost , Juan Quintela , Markus Armbruster , "Dr. David Alan Gilbert" , Gerd Hoffmann , Cleber Rosa , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Michael Roth Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" In order to fix the bad screendumps (same as rhbz#1230527), call into the asynchonous version of the QMP command. Signed-off-by: Marc-Andr=C3=A9 Lureau --- hmp.h | 3 ++- hmp.c | 6 ++---- ui/console.c | 17 ----------------- hmp-commands.hx | 3 ++- 4 files changed, 6 insertions(+), 23 deletions(-) diff --git a/hmp.h b/hmp.h index 4e2ec375b0..6ad43b7828 100644 --- a/hmp.h +++ b/hmp.h @@ -16,6 +16,7 @@ =20 #include "qemu-common.h" #include "qemu/readline.h" +#include "qapi/qmp/dispatch.h" =20 void hmp_info_name(Monitor *mon, const QDict *qdict); void hmp_info_version(Monitor *mon, const QDict *qdict); @@ -96,7 +97,7 @@ void hmp_netdev_del(Monitor *mon, const QDict *qdict); void hmp_getfd(Monitor *mon, const QDict *qdict); void hmp_closefd(Monitor *mon, const QDict *qdict); void hmp_sendkey(Monitor *mon, const QDict *qdict); -void hmp_screendump(Monitor *mon, const QDict *qdict); +void hmp_screendump_async(Monitor *mon, const QDict *qdict, QmpReturn *qre= t); void hmp_nbd_server_start(Monitor *mon, const QDict *qdict); void hmp_nbd_server_add(Monitor *mon, const QDict *qdict); void hmp_nbd_server_remove(Monitor *mon, const QDict *qdict); diff --git a/hmp.c b/hmp.c index da9008fe63..ca1ee8e146 100644 --- a/hmp.c +++ b/hmp.c @@ -2137,15 +2137,13 @@ err_out: goto out; } =20 -void hmp_screendump(Monitor *mon, const QDict *qdict) +void hmp_screendump_async(Monitor *mon, const QDict *qdict, QmpReturn *qre= t) { const char *filename =3D qdict_get_str(qdict, "filename"); const char *id =3D qdict_get_try_str(qdict, "device"); int64_t head =3D qdict_get_try_int(qdict, "head", 0); - Error *err =3D NULL; =20 - hmp_screendump_sync(filename, id !=3D NULL, id, id !=3D NULL, head, &e= rr); - hmp_handle_error(mon, &err); + qmp_screendump(filename, id !=3D NULL, id, id !=3D NULL, head, qret); } =20 void hmp_nbd_server_start(Monitor *mon, const QDict *qdict) diff --git a/ui/console.c b/ui/console.c index da51861191..f1cbbd6317 100644 --- a/ui/console.c +++ b/ui/console.c @@ -426,23 +426,6 @@ static QemuConsole *get_console(bool has_device, const= char *device, return con; } =20 -void hmp_screendump_sync(const char *filename, - bool has_device, const char *device, - bool has_head, int64_t head, Error **errp) -{ - DisplaySurface *surface; - QemuConsole *con =3D get_console(has_device, device, has_head, head, e= rrp); - - if (!con) { - return; - } - /* This may not complete the drawing with Spice, you may have - * glitches or outdated dumps, use qmp instead! */ - graphic_hw_update(con); - surface =3D qemu_console_surface(con); - ppm_save(filename, surface, errp); -} - void qmp_screendump(const char *filename, bool has_device, const char *device, bool has_head, int64_t head, diff --git a/hmp-commands.hx b/hmp-commands.hx index 35d862a5d2..4911fc6474 100644 --- a/hmp-commands.hx +++ b/hmp-commands.hx @@ -258,7 +258,8 @@ ETEXI .params =3D "filename [device [head]]", .help =3D "save screen from head 'head' of display device 'd= evice' " "into PPM image 'filename'", - .cmd =3D hmp_screendump, + .async_cmd =3D hmp_screendump_async, + .async =3D true, }, =20 STEXI --=20 2.17.0.rc1.1.g4c4f2b46a3