1f66e7ac8SMarkus Armbruster /*
2f66e7ac8SMarkus Armbruster * QMP protocol test cases
3f66e7ac8SMarkus Armbruster *
4aed877c5SMarkus Armbruster * Copyright (c) 2017-2018 Red Hat Inc.
5f66e7ac8SMarkus Armbruster *
6f66e7ac8SMarkus Armbruster * Authors:
7d93bb9d5SMarkus Armbruster * Markus Armbruster <armbru@redhat.com>
8f66e7ac8SMarkus Armbruster *
9f66e7ac8SMarkus Armbruster * This work is licensed under the terms of the GNU GPL, version 2 or later.
10f66e7ac8SMarkus Armbruster * See the COPYING file in the top-level directory.
11f66e7ac8SMarkus Armbruster */
12f66e7ac8SMarkus Armbruster
13f66e7ac8SMarkus Armbruster #include "qemu/osdep.h"
14907b5105SMarc-André Lureau #include "libqtest.h"
15f66e7ac8SMarkus Armbruster #include "qapi/error.h"
16fa4dcf57SKevin Wolf #include "qapi/qapi-visit-control.h"
17*407bc4bfSDaniel P. Berrangé #include "qobject/qdict.h"
18*407bc4bfSDaniel P. Berrangé #include "qobject/qlist.h"
19f66e7ac8SMarkus Armbruster #include "qapi/qobject-input-visitor.h"
20*407bc4bfSDaniel P. Berrangé #include "qobject/qstring.h"
21f66e7ac8SMarkus Armbruster
22f66e7ac8SMarkus Armbruster const char common_args[] = "-nodefaults -machine none";
23f66e7ac8SMarkus Armbruster
test_version(QObject * version)24f66e7ac8SMarkus Armbruster static void test_version(QObject *version)
25f66e7ac8SMarkus Armbruster {
26f66e7ac8SMarkus Armbruster Visitor *v;
27f66e7ac8SMarkus Armbruster VersionInfo *vinfo;
28f66e7ac8SMarkus Armbruster
29f66e7ac8SMarkus Armbruster g_assert(version);
30048abb7bSMarkus Armbruster v = qobject_input_visitor_new(version);
31f66e7ac8SMarkus Armbruster visit_type_VersionInfo(v, "version", &vinfo, &error_abort);
32f66e7ac8SMarkus Armbruster qapi_free_VersionInfo(vinfo);
33f66e7ac8SMarkus Armbruster visit_free(v);
34f66e7ac8SMarkus Armbruster }
35f66e7ac8SMarkus Armbruster
assert_recovered(QTestState * qts)36ebb4d82dSMarc-André Lureau static void assert_recovered(QTestState *qts)
37aed877c5SMarkus Armbruster {
38aed877c5SMarkus Armbruster QDict *resp;
39aed877c5SMarkus Armbruster
40aed877c5SMarkus Armbruster resp = qtest_qmp(qts, "{ 'execute': 'no-such-cmd' }");
413bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "CommandNotFound");
42aed877c5SMarkus Armbruster }
43aed877c5SMarkus Armbruster
test_malformed(QTestState * qts)446a5c88f5SEric Blake static void test_malformed(QTestState *qts)
45f66e7ac8SMarkus Armbruster {
46f66e7ac8SMarkus Armbruster QDict *resp;
47f66e7ac8SMarkus Armbruster
48aed877c5SMarkus Armbruster /* syntax error */
49aed877c5SMarkus Armbruster qtest_qmp_send_raw(qts, "{]\n");
501c3e2a38SMaxim Levitsky resp = qtest_qmp_receive_dict(qts);
513bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
52ebb4d82dSMarc-André Lureau assert_recovered(qts);
53aed877c5SMarkus Armbruster
54aed877c5SMarkus Armbruster /* lexical error: impossible byte outside string */
55aed877c5SMarkus Armbruster qtest_qmp_send_raw(qts, "{\xFF");
561c3e2a38SMaxim Levitsky resp = qtest_qmp_receive_dict(qts);
573bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
58ebb4d82dSMarc-André Lureau assert_recovered(qts);
59aed877c5SMarkus Armbruster
606bc93a34SMarkus Armbruster /* lexical error: funny control character outside string */
616bc93a34SMarkus Armbruster qtest_qmp_send_raw(qts, "{\x01");
621c3e2a38SMaxim Levitsky resp = qtest_qmp_receive_dict(qts);
633bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
64ebb4d82dSMarc-André Lureau assert_recovered(qts);
656bc93a34SMarkus Armbruster
66aed877c5SMarkus Armbruster /* lexical error: impossible byte in string */
67aed877c5SMarkus Armbruster qtest_qmp_send_raw(qts, "{'bad \xFF");
681c3e2a38SMaxim Levitsky resp = qtest_qmp_receive_dict(qts);
693bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
70ebb4d82dSMarc-André Lureau assert_recovered(qts);
71aed877c5SMarkus Armbruster
726bc93a34SMarkus Armbruster /* lexical error: control character in string */
73340db1edSMarkus Armbruster qtest_qmp_send_raw(qts, "{'execute': 'nonexistent', 'id':'\n");
741c3e2a38SMaxim Levitsky resp = qtest_qmp_receive_dict(qts);
753bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
76ebb4d82dSMarc-André Lureau assert_recovered(qts);
776bc93a34SMarkus Armbruster
78aed877c5SMarkus Armbruster /* lexical error: interpolation */
790f07a5d5SMarkus Armbruster qtest_qmp_send_raw(qts, "%%p");
801c3e2a38SMaxim Levitsky resp = qtest_qmp_receive_dict(qts);
813bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
82ebb4d82dSMarc-André Lureau assert_recovered(qts);
83aed877c5SMarkus Armbruster
84f66e7ac8SMarkus Armbruster /* Not even a dictionary */
856a5c88f5SEric Blake resp = qtest_qmp(qts, "null");
863bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
87f66e7ac8SMarkus Armbruster
88f66e7ac8SMarkus Armbruster /* No "execute" key */
896a5c88f5SEric Blake resp = qtest_qmp(qts, "{}");
903bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
91f66e7ac8SMarkus Armbruster
92f66e7ac8SMarkus Armbruster /* "execute" isn't a string */
936a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': true }");
943bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
95f66e7ac8SMarkus Armbruster
96f66e7ac8SMarkus Armbruster /* "arguments" isn't a dictionary */
976a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': 'no-such-cmd', 'arguments': [] }");
983bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
99f66e7ac8SMarkus Armbruster
100f66e7ac8SMarkus Armbruster /* extra key */
1016a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': 'no-such-cmd', 'extra': true }");
1023bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
103f66e7ac8SMarkus Armbruster }
104f66e7ac8SMarkus Armbruster
test_qmp_protocol(void)105f66e7ac8SMarkus Armbruster static void test_qmp_protocol(void)
106f66e7ac8SMarkus Armbruster {
107f66e7ac8SMarkus Armbruster QDict *resp, *q, *ret;
108f66e7ac8SMarkus Armbruster QList *capabilities;
1096a5c88f5SEric Blake QTestState *qts;
110f66e7ac8SMarkus Armbruster
111192f26a7SPeter Xu qts = qtest_init_without_qmp_handshake(common_args);
112f66e7ac8SMarkus Armbruster
113f66e7ac8SMarkus Armbruster /* Test greeting */
1141c3e2a38SMaxim Levitsky resp = qtest_qmp_receive_dict(qts);
115f66e7ac8SMarkus Armbruster q = qdict_get_qdict(resp, "QMP");
116f66e7ac8SMarkus Armbruster g_assert(q);
117f66e7ac8SMarkus Armbruster test_version(qdict_get(q, "version"));
118f66e7ac8SMarkus Armbruster capabilities = qdict_get_qlist(q, "capabilities");
1198258292eSPeter Xu g_assert(capabilities);
120cb3e7f08SMarc-André Lureau qobject_unref(resp);
121f66e7ac8SMarkus Armbruster
122f66e7ac8SMarkus Armbruster /* Test valid command before handshake */
1236a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': 'query-version' }");
1243bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "CommandNotFound");
125f66e7ac8SMarkus Armbruster
126f66e7ac8SMarkus Armbruster /* Test malformed commands before handshake */
1276a5c88f5SEric Blake test_malformed(qts);
128f66e7ac8SMarkus Armbruster
129f66e7ac8SMarkus Armbruster /* Test handshake */
1306a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': 'qmp_capabilities' }");
131f66e7ac8SMarkus Armbruster ret = qdict_get_qdict(resp, "return");
132f66e7ac8SMarkus Armbruster g_assert(ret && !qdict_size(ret));
133cb3e7f08SMarc-André Lureau qobject_unref(resp);
134f66e7ac8SMarkus Armbruster
135f66e7ac8SMarkus Armbruster /* Test repeated handshake */
1366a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': 'qmp_capabilities' }");
1373bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "CommandNotFound");
138f66e7ac8SMarkus Armbruster
139f66e7ac8SMarkus Armbruster /* Test valid command */
1406a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': 'query-version' }");
141f66e7ac8SMarkus Armbruster test_version(qdict_get(resp, "return"));
142cb3e7f08SMarc-André Lureau qobject_unref(resp);
143f66e7ac8SMarkus Armbruster
144f66e7ac8SMarkus Armbruster /* Test malformed commands */
1456a5c88f5SEric Blake test_malformed(qts);
146f66e7ac8SMarkus Armbruster
147f66e7ac8SMarkus Armbruster /* Test 'id' */
1486a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': 'query-name', 'id': 'cookie#1' }");
149f66e7ac8SMarkus Armbruster ret = qdict_get_qdict(resp, "return");
150f66e7ac8SMarkus Armbruster g_assert(ret);
151f66e7ac8SMarkus Armbruster g_assert_cmpstr(qdict_get_try_str(resp, "id"), ==, "cookie#1");
152cb3e7f08SMarc-André Lureau qobject_unref(resp);
153f66e7ac8SMarkus Armbruster
154f66e7ac8SMarkus Armbruster /* Test command failure with 'id' */
1556a5c88f5SEric Blake resp = qtest_qmp(qts, "{ 'execute': 'human-monitor-command', 'id': 2 }");
156f66e7ac8SMarkus Armbruster g_assert_cmpint(qdict_get_int(resp, "id"), ==, 2);
1573bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
158f66e7ac8SMarkus Armbruster
1596a5c88f5SEric Blake qtest_quit(qts);
160f66e7ac8SMarkus Armbruster }
161f66e7ac8SMarkus Armbruster
162b82cbbf0SBin Meng #ifndef _WIN32
163b82cbbf0SBin Meng
16497ca0712SMarkus Armbruster /* Out-of-band tests */
16597ca0712SMarkus Armbruster
166c12fea71SBin Meng char *tmpdir;
16797ca0712SMarkus Armbruster char *fifo_name;
16897ca0712SMarkus Armbruster
setup_blocking_cmd(void)16997ca0712SMarkus Armbruster static void setup_blocking_cmd(void)
17097ca0712SMarkus Armbruster {
171c12fea71SBin Meng GError *err = NULL;
172c12fea71SBin Meng tmpdir = g_dir_make_tmp("qmp-test-XXXXXX", &err);
173c12fea71SBin Meng g_assert_no_error(err);
174c12fea71SBin Meng
17597ca0712SMarkus Armbruster fifo_name = g_strdup_printf("%s/fifo", tmpdir);
17697ca0712SMarkus Armbruster if (mkfifo(fifo_name, 0666)) {
17797ca0712SMarkus Armbruster g_error("mkfifo: %s", strerror(errno));
17897ca0712SMarkus Armbruster }
17997ca0712SMarkus Armbruster }
18097ca0712SMarkus Armbruster
cleanup_blocking_cmd(void)18197ca0712SMarkus Armbruster static void cleanup_blocking_cmd(void)
18297ca0712SMarkus Armbruster {
18397ca0712SMarkus Armbruster unlink(fifo_name);
18497ca0712SMarkus Armbruster rmdir(tmpdir);
185c12fea71SBin Meng g_free(tmpdir);
18697ca0712SMarkus Armbruster }
18797ca0712SMarkus Armbruster
send_cmd_that_blocks(QTestState * s,const char * id)18897ca0712SMarkus Armbruster static void send_cmd_that_blocks(QTestState *s, const char *id)
18997ca0712SMarkus Armbruster {
1904277f1ebSMarkus Armbruster qtest_qmp_send(s, "{ 'execute': 'blockdev-add', 'id': %s,"
19197ca0712SMarkus Armbruster " 'arguments': {"
19297ca0712SMarkus Armbruster " 'driver': 'blkdebug', 'node-name': %s,"
19397ca0712SMarkus Armbruster " 'config': %s,"
194ca1ef1e6SAndrey Shinkevich " 'image': { 'driver': 'null-co', 'read-zeroes': true } } }",
19597ca0712SMarkus Armbruster id, id, fifo_name);
19697ca0712SMarkus Armbruster }
19797ca0712SMarkus Armbruster
unblock_blocked_cmd(void)19897ca0712SMarkus Armbruster static void unblock_blocked_cmd(void)
19997ca0712SMarkus Armbruster {
20097ca0712SMarkus Armbruster int fd = open(fifo_name, O_WRONLY);
20197ca0712SMarkus Armbruster g_assert(fd >= 0);
20297ca0712SMarkus Armbruster close(fd);
20397ca0712SMarkus Armbruster }
20497ca0712SMarkus Armbruster
send_oob_cmd_that_fails(QTestState * s,const char * id)20597ca0712SMarkus Armbruster static void send_oob_cmd_that_fails(QTestState *s, const char *id)
20697ca0712SMarkus Armbruster {
2074277f1ebSMarkus Armbruster qtest_qmp_send(s, "{ 'exec-oob': 'migrate-pause', 'id': %s }", id);
20897ca0712SMarkus Armbruster }
20997ca0712SMarkus Armbruster
recv_cmd_id(QTestState * s,const char * id)21097ca0712SMarkus Armbruster static void recv_cmd_id(QTestState *s, const char *id)
21197ca0712SMarkus Armbruster {
2121c3e2a38SMaxim Levitsky QDict *resp = qtest_qmp_receive_dict(s);
21397ca0712SMarkus Armbruster
21497ca0712SMarkus Armbruster g_assert_cmpstr(qdict_get_try_str(resp, "id"), ==, id);
21597ca0712SMarkus Armbruster qobject_unref(resp);
21697ca0712SMarkus Armbruster }
21797ca0712SMarkus Armbruster
test_qmp_oob(void)218fa198ad9SPeter Xu static void test_qmp_oob(void)
219fa198ad9SPeter Xu {
220fa198ad9SPeter Xu QTestState *qts;
221fa198ad9SPeter Xu QDict *resp, *q;
222fa198ad9SPeter Xu const QListEntry *entry;
223fa198ad9SPeter Xu QList *capabilities;
224fa198ad9SPeter Xu QString *qstr;
225fa198ad9SPeter Xu
226192f26a7SPeter Xu qts = qtest_init_without_qmp_handshake(common_args);
227fa198ad9SPeter Xu
228fa198ad9SPeter Xu /* Check the greeting message. */
2291c3e2a38SMaxim Levitsky resp = qtest_qmp_receive_dict(qts);
230fa198ad9SPeter Xu q = qdict_get_qdict(resp, "QMP");
231fa198ad9SPeter Xu g_assert(q);
232fa198ad9SPeter Xu capabilities = qdict_get_qlist(q, "capabilities");
233fa198ad9SPeter Xu g_assert(capabilities && !qlist_empty(capabilities));
234fa198ad9SPeter Xu entry = qlist_first(capabilities);
235fa198ad9SPeter Xu g_assert(entry);
236fa198ad9SPeter Xu qstr = qobject_to(QString, entry->value);
237fa198ad9SPeter Xu g_assert(qstr);
238fa198ad9SPeter Xu g_assert_cmpstr(qstring_get_str(qstr), ==, "oob");
239cb3e7f08SMarc-André Lureau qobject_unref(resp);
240fa198ad9SPeter Xu
241fa198ad9SPeter Xu /* Try a fake capability, it should fail. */
242fa198ad9SPeter Xu resp = qtest_qmp(qts,
243fa198ad9SPeter Xu "{ 'execute': 'qmp_capabilities', "
244fa198ad9SPeter Xu " 'arguments': { 'enable': [ 'cap-does-not-exist' ] } }");
245fa198ad9SPeter Xu g_assert(qdict_haskey(resp, "error"));
246cb3e7f08SMarc-André Lureau qobject_unref(resp);
247fa198ad9SPeter Xu
248fa198ad9SPeter Xu /* Now, enable OOB in current QMP session, it should succeed. */
249fa198ad9SPeter Xu resp = qtest_qmp(qts,
250fa198ad9SPeter Xu "{ 'execute': 'qmp_capabilities', "
251fa198ad9SPeter Xu " 'arguments': { 'enable': [ 'oob' ] } }");
252fa198ad9SPeter Xu g_assert(qdict_haskey(resp, "return"));
253cb3e7f08SMarc-André Lureau qobject_unref(resp);
254fa198ad9SPeter Xu
255fa198ad9SPeter Xu /*
256fa198ad9SPeter Xu * Try any command that does not support OOB but with OOB flag. We
257fa198ad9SPeter Xu * should get failure.
258fa198ad9SPeter Xu */
2598af54b91SDaniel P. Berrangé resp = qtest_qmp(qts, "{ 'exec-oob': 'query-cpus-fast' }");
260fa198ad9SPeter Xu g_assert(qdict_haskey(resp, "error"));
261cb3e7f08SMarc-André Lureau qobject_unref(resp);
262fa198ad9SPeter Xu
26397ca0712SMarkus Armbruster /* OOB command overtakes slow in-band command */
26497ca0712SMarkus Armbruster setup_blocking_cmd();
26597ca0712SMarkus Armbruster send_cmd_that_blocks(qts, "ib-blocks-1");
2664277f1ebSMarkus Armbruster qtest_qmp_send(qts, "{ 'execute': 'query-name', 'id': 'ib-quick-1' }");
26797ca0712SMarkus Armbruster send_oob_cmd_that_fails(qts, "oob-1");
26897ca0712SMarkus Armbruster recv_cmd_id(qts, "oob-1");
26997ca0712SMarkus Armbruster unblock_blocked_cmd();
27097ca0712SMarkus Armbruster recv_cmd_id(qts, "ib-blocks-1");
2712970b446SMarkus Armbruster recv_cmd_id(qts, "ib-quick-1");
272e8f4a221SMarkus Armbruster
27369240fe6SMarkus Armbruster /* Even malformed in-band command fails in-band */
274e8f4a221SMarkus Armbruster send_cmd_that_blocks(qts, "blocks-2");
2754277f1ebSMarkus Armbruster qtest_qmp_send(qts, "{ 'id': 'err-2' }");
276e8f4a221SMarkus Armbruster unblock_blocked_cmd();
277e8f4a221SMarkus Armbruster recv_cmd_id(qts, "blocks-2");
27869240fe6SMarkus Armbruster recv_cmd_id(qts, "err-2");
27997ca0712SMarkus Armbruster cleanup_blocking_cmd();
280fa198ad9SPeter Xu
281fa198ad9SPeter Xu qtest_quit(qts);
282fa198ad9SPeter Xu }
283fa198ad9SPeter Xu
284b82cbbf0SBin Meng #endif /* _WIN32 */
285b82cbbf0SBin Meng
28697ca0712SMarkus Armbruster /* Preconfig tests */
28797ca0712SMarkus Armbruster
test_qmp_preconfig(void)288fb1e58f7SIgor Mammedov static void test_qmp_preconfig(void)
289fb1e58f7SIgor Mammedov {
290fb1e58f7SIgor Mammedov QDict *rsp, *ret;
29188b988c8SMarkus Armbruster QTestState *qs = qtest_initf("%s --preconfig", common_args);
292fb1e58f7SIgor Mammedov
293fb1e58f7SIgor Mammedov /* preconfig state */
294fb1e58f7SIgor Mammedov /* enabled commands, no error expected */
295fb1e58f7SIgor Mammedov g_assert(!qmp_rsp_is_err(qtest_qmp(qs, "{ 'execute': 'query-commands' }")));
296fb1e58f7SIgor Mammedov
297fb1e58f7SIgor Mammedov /* forbidden commands, expected error */
2988af54b91SDaniel P. Berrangé g_assert(qmp_rsp_is_err(qtest_qmp(qs, "{ 'execute': 'query-cpus-fast' }")));
299fb1e58f7SIgor Mammedov
300fb1e58f7SIgor Mammedov /* check that query-status returns preconfig state */
301fb1e58f7SIgor Mammedov rsp = qtest_qmp(qs, "{ 'execute': 'query-status' }");
302fb1e58f7SIgor Mammedov ret = qdict_get_qdict(rsp, "return");
303fb1e58f7SIgor Mammedov g_assert(ret);
304164dafd1SPaolo Bonzini g_assert_cmpstr(qdict_get_try_str(ret, "status"), ==, "prelaunch");
305fb1e58f7SIgor Mammedov qobject_unref(rsp);
306fb1e58f7SIgor Mammedov
307fb1e58f7SIgor Mammedov /* exit preconfig state */
308361ac948SMarkus Armbruster g_assert(!qmp_rsp_is_err(qtest_qmp(qs, "{ 'execute': 'x-exit-preconfig' }")));
309fb1e58f7SIgor Mammedov qtest_qmp_eventwait(qs, "RESUME");
310fb1e58f7SIgor Mammedov
311fb1e58f7SIgor Mammedov /* check that query-status returns running state */
312fb1e58f7SIgor Mammedov rsp = qtest_qmp(qs, "{ 'execute': 'query-status' }");
313fb1e58f7SIgor Mammedov ret = qdict_get_qdict(rsp, "return");
314fb1e58f7SIgor Mammedov g_assert(ret);
315fb1e58f7SIgor Mammedov g_assert_cmpstr(qdict_get_try_str(ret, "status"), ==, "running");
316fb1e58f7SIgor Mammedov qobject_unref(rsp);
317fb1e58f7SIgor Mammedov
318361ac948SMarkus Armbruster /* check that x-exit-preconfig returns error after exiting preconfig */
319361ac948SMarkus Armbruster g_assert(qmp_rsp_is_err(qtest_qmp(qs, "{ 'execute': 'x-exit-preconfig' }")));
320fb1e58f7SIgor Mammedov
321fb1e58f7SIgor Mammedov /* enabled commands, no error expected */
3228af54b91SDaniel P. Berrangé g_assert(!qmp_rsp_is_err(qtest_qmp(qs, "{ 'execute': 'query-cpus-fast' }")));
323fb1e58f7SIgor Mammedov
324fb1e58f7SIgor Mammedov qtest_quit(qs);
325fb1e58f7SIgor Mammedov }
326fb1e58f7SIgor Mammedov
test_qmp_missing_any_arg(void)32761793a62SMarc-André Lureau static void test_qmp_missing_any_arg(void)
32861793a62SMarc-André Lureau {
32961793a62SMarc-André Lureau QTestState *qts;
33061793a62SMarc-André Lureau QDict *resp;
33161793a62SMarc-André Lureau
33261793a62SMarc-André Lureau qts = qtest_init(common_args);
33361793a62SMarc-André Lureau resp = qtest_qmp(qts, "{'execute': 'qom-set', 'arguments':"
33461793a62SMarc-André Lureau " { 'path': '/machine', 'property': 'rtc-time' } }");
33561793a62SMarc-André Lureau g_assert_nonnull(resp);
3363bc1b8eeSMarkus Armbruster qmp_expect_error_and_unref(resp, "GenericError");
33761793a62SMarc-André Lureau qtest_quit(qts);
33861793a62SMarc-André Lureau }
33961793a62SMarc-André Lureau
main(int argc,char * argv[])340f66e7ac8SMarkus Armbruster int main(int argc, char *argv[])
341f66e7ac8SMarkus Armbruster {
342f66e7ac8SMarkus Armbruster g_test_init(&argc, &argv, NULL);
343f66e7ac8SMarkus Armbruster
344f66e7ac8SMarkus Armbruster qtest_add_func("qmp/protocol", test_qmp_protocol);
345b82cbbf0SBin Meng #ifndef _WIN32
346b82cbbf0SBin Meng /* This case calls mkfifo() which does not exist on win32 */
347fa198ad9SPeter Xu qtest_add_func("qmp/oob", test_qmp_oob);
348b82cbbf0SBin Meng #endif
349fb1e58f7SIgor Mammedov qtest_add_func("qmp/preconfig", test_qmp_preconfig);
35061793a62SMarc-André Lureau qtest_add_func("qmp/missing-any-arg", test_qmp_missing_any_arg);
351f66e7ac8SMarkus Armbruster
352d93bb9d5SMarkus Armbruster return g_test_run();
353f66e7ac8SMarkus Armbruster }
354