]> Git Repo - qemu.git/blob - tests/qmp-test.c
iotests: Add preallocated growth test for qcow2
[qemu.git] / tests / qmp-test.c
1 /*
2  * QMP protocol test cases
3  *
4  * Copyright (c) 2017 Red Hat Inc.
5  *
6  * Authors:
7  *  Markus Armbruster <[email protected]>,
8  *
9  * This work is licensed under the terms of the GNU GPL, version 2 or later.
10  * See the COPYING file in the top-level directory.
11  */
12
13 #include "qemu/osdep.h"
14 #include "libqtest.h"
15 #include "qapi-visit.h"
16 #include "qapi/error.h"
17 #include "qapi/qobject-input-visitor.h"
18 #include "qapi/visitor.h"
19
20 const char common_args[] = "-nodefaults -machine none";
21
22 static const char *get_error_class(QDict *resp)
23 {
24     QDict *error = qdict_get_qdict(resp, "error");
25     const char *desc = qdict_get_try_str(error, "desc");
26
27     g_assert(desc);
28     return error ? qdict_get_try_str(error, "class") : NULL;
29 }
30
31 static void test_version(QObject *version)
32 {
33     Visitor *v;
34     VersionInfo *vinfo;
35
36     g_assert(version);
37     v = qobject_input_visitor_new(version);
38     visit_type_VersionInfo(v, "version", &vinfo, &error_abort);
39     qapi_free_VersionInfo(vinfo);
40     visit_free(v);
41 }
42
43 static void test_malformed(void)
44 {
45     QDict *resp;
46
47     /* Not even a dictionary */
48     resp = qmp("null");
49     g_assert_cmpstr(get_error_class(resp), ==, "GenericError");
50     QDECREF(resp);
51
52     /* No "execute" key */
53     resp = qmp("{}");
54     g_assert_cmpstr(get_error_class(resp), ==, "GenericError");
55     QDECREF(resp);
56
57     /* "execute" isn't a string */
58     resp = qmp("{ 'execute': true }");
59     g_assert_cmpstr(get_error_class(resp), ==, "GenericError");
60     QDECREF(resp);
61
62     /* "arguments" isn't a dictionary */
63     resp = qmp("{ 'execute': 'no-such-cmd', 'arguments': [] }");
64     g_assert_cmpstr(get_error_class(resp), ==, "GenericError");
65     QDECREF(resp);
66
67     /* extra key */
68     resp = qmp("{ 'execute': 'no-such-cmd', 'extra': true }");
69     g_assert_cmpstr(get_error_class(resp), ==, "GenericError");
70     QDECREF(resp);
71 }
72
73 static void test_qmp_protocol(void)
74 {
75     QDict *resp, *q, *ret;
76     QList *capabilities;
77
78     global_qtest = qtest_init_without_qmp_handshake(common_args);
79
80     /* Test greeting */
81     resp = qmp_receive();
82     q = qdict_get_qdict(resp, "QMP");
83     g_assert(q);
84     test_version(qdict_get(q, "version"));
85     capabilities = qdict_get_qlist(q, "capabilities");
86     g_assert(capabilities && qlist_empty(capabilities));
87     QDECREF(resp);
88
89     /* Test valid command before handshake */
90     resp = qmp("{ 'execute': 'query-version' }");
91     g_assert_cmpstr(get_error_class(resp), ==, "CommandNotFound");
92     QDECREF(resp);
93
94     /* Test malformed commands before handshake */
95     test_malformed();
96
97     /* Test handshake */
98     resp = qmp("{ 'execute': 'qmp_capabilities' }");
99     ret = qdict_get_qdict(resp, "return");
100     g_assert(ret && !qdict_size(ret));
101     QDECREF(resp);
102
103     /* Test repeated handshake */
104     resp = qmp("{ 'execute': 'qmp_capabilities' }");
105     g_assert_cmpstr(get_error_class(resp), ==, "CommandNotFound");
106     QDECREF(resp);
107
108     /* Test valid command */
109     resp = qmp("{ 'execute': 'query-version' }");
110     test_version(qdict_get(resp, "return"));
111     QDECREF(resp);
112
113     /* Test malformed commands */
114     test_malformed();
115
116     /* Test 'id' */
117     resp = qmp("{ 'execute': 'query-name', 'id': 'cookie#1' }");
118     ret = qdict_get_qdict(resp, "return");
119     g_assert(ret);
120     g_assert_cmpstr(qdict_get_try_str(resp, "id"), ==, "cookie#1");
121     QDECREF(resp);
122
123     /* Test command failure with 'id' */
124     resp = qmp("{ 'execute': 'human-monitor-command', 'id': 2 }");
125     g_assert_cmpstr(get_error_class(resp), ==, "GenericError");
126     g_assert_cmpint(qdict_get_int(resp, "id"), ==, 2);
127     QDECREF(resp);
128
129     qtest_end();
130 }
131
132 int main(int argc, char *argv[])
133 {
134     g_test_init(&argc, &argv, NULL);
135
136     qtest_add_func("qmp/protocol", test_qmp_protocol);
137
138     return g_test_run();
139 }
This page took 0.031364 seconds and 4 git commands to generate.