scripts/qmp: Fix shebang and imports
[qemu.git] / scripts / qmp / qmp
1 #!/usr/bin/env python3
2 #
3 # QMP command line tool
4 #
5 # Copyright IBM, Corp. 2011
6 #
7 # Authors:
8 #  Anthony Liguori <aliguori@us.ibm.com>
9 #
10 # This work is licensed under the terms of the GNU GPLv2 or later.
11 # See the COPYING file in the top-level directory.
12
13 import sys, os
14
15 sys.path.append(os.path.join(os.path.dirname(__file__), '..', '..', 'python'))
16 from qemu.qmp import QEMUMonitorProtocol
17
18 def print_response(rsp, prefix=[]):
19     if type(rsp) == list:
20         i = 0
21         for item in rsp:
22             if prefix == []:
23                 prefix = ['item']
24             print_response(item, prefix[:-1] + ['%s[%d]' % (prefix[-1], i)])
25             i += 1
26     elif type(rsp) == dict:
27         for key in rsp.keys():
28             print_response(rsp[key], prefix + [key])
29     else:
30         if len(prefix):
31             print('%s: %s' % ('.'.join(prefix), rsp))
32         else:
33             print('%s' % (rsp))
34
35 def main(args):
36     path = None
37
38     # Use QMP_PATH if it's set
39     if 'QMP_PATH' in os.environ:
40         path = os.environ['QMP_PATH']
41
42     while len(args):
43         arg = args[0]
44
45         if arg.startswith('--'):
46             arg = arg[2:]
47             if arg.find('=') == -1:
48                 value = True
49             else:
50                 arg, value = arg.split('=', 1)
51
52             if arg in ['path']:
53                 if type(value) == str:
54                     path = value
55             elif arg in ['help']:
56                 os.execlp('man', 'man', 'qmp')
57             else:
58                 print('Unknown argument "%s"' % arg)
59
60             args = args[1:]
61         else:
62             break
63
64     if not path:
65         print("QMP path isn't set, use --path=qmp-monitor-address or set QMP_PATH")
66         return 1
67
68     if len(args):
69         command, args = args[0], args[1:]
70     else:
71         print('No command found')
72         print('Usage: "qmp [--path=qmp-monitor-address] qmp-cmd arguments"')
73         return 1
74
75     if command in ['help']:
76         os.execlp('man', 'man', 'qmp')
77
78     srv = QEMUMonitorProtocol(path)
79     srv.connect()
80
81     def do_command(srv, cmd, **kwds):
82         rsp = srv.cmd(cmd, kwds)
83         if 'error' in rsp:
84             raise Exception(rsp['error']['desc'])
85         return rsp['return']
86
87     commands = map(lambda x: x['name'], do_command(srv, 'query-commands'))
88
89     srv.close()
90
91     if command not in commands:
92         fullcmd = 'qmp-%s' % command
93         try:
94             os.environ['QMP_PATH'] = path
95             os.execvp(fullcmd, [fullcmd] + args)
96         except OSError as exc:
97             if exc.errno == 2:
98                 print('Command "%s" not found.' % (fullcmd))
99                 return 1
100             raise
101         return 0
102
103     srv = QEMUMonitorProtocol(path)
104     srv.connect()
105
106     arguments = {}
107     for arg in args:
108         if not arg.startswith('--'):
109             print('Unknown argument "%s"' % arg)
110             return 1
111
112         arg = arg[2:]
113         if arg.find('=') == -1:
114             value = True
115         else:
116             arg, value = arg.split('=', 1)
117
118         if arg in ['help']:
119             os.execlp('man', 'man', 'qmp-%s' % command)
120             return 1
121
122         arguments[arg] = value
123
124     rsp = do_command(srv, command, **arguments)
125     print_response(rsp)
126
127 if __name__ == '__main__':
128     sys.exit(main(sys.argv[1:]))