]> Git Repo - qemu.git/blob - python/qemu/qmp/models.py
works with less than base ISA qemu-system-riscv32 -M virt -bios none -kernel output...
[qemu.git] / python / qemu / qmp / models.py
1 """
2 QMP Data Models
3
4 This module provides simplistic data classes that represent the few
5 structures that the QMP spec mandates; they are used to verify incoming
6 data to make sure it conforms to spec.
7 """
8 # pylint: disable=too-few-public-methods
9
10 from collections import abc
11 import copy
12 from typing import (
13     Any,
14     Dict,
15     Mapping,
16     Optional,
17     Sequence,
18 )
19
20
21 class Model:
22     """
23     Abstract data model, representing some QMP object of some kind.
24
25     :param raw: The raw object to be validated.
26     :raise KeyError: If any required fields are absent.
27     :raise TypeError: If any required fields have the wrong type.
28     """
29     def __init__(self, raw: Mapping[str, Any]):
30         self._raw = raw
31
32     def _check_key(self, key: str) -> None:
33         if key not in self._raw:
34             raise KeyError(f"'{self._name}' object requires '{key}' member")
35
36     def _check_value(self, key: str, type_: type, typestr: str) -> None:
37         assert key in self._raw
38         if not isinstance(self._raw[key], type_):
39             raise TypeError(
40                 f"'{self._name}' member '{key}' must be a {typestr}"
41             )
42
43     def _check_member(self, key: str, type_: type, typestr: str) -> None:
44         self._check_key(key)
45         self._check_value(key, type_, typestr)
46
47     @property
48     def _name(self) -> str:
49         return type(self).__name__
50
51     def __repr__(self) -> str:
52         return f"{self._name}({self._raw!r})"
53
54
55 class Greeting(Model):
56     """
57     Defined in qmp-spec.txt, section 2.2, "Server Greeting".
58
59     :param raw: The raw Greeting object.
60     :raise KeyError: If any required fields are absent.
61     :raise TypeError: If any required fields have the wrong type.
62     """
63     def __init__(self, raw: Mapping[str, Any]):
64         super().__init__(raw)
65         #: 'QMP' member
66         self.QMP: QMPGreeting  # pylint: disable=invalid-name
67
68         self._check_member('QMP', abc.Mapping, "JSON object")
69         self.QMP = QMPGreeting(self._raw['QMP'])
70
71     def _asdict(self) -> Dict[str, object]:
72         """
73         For compatibility with the iotests sync QMP wrapper.
74
75         The legacy QMP interface needs Greetings as a garden-variety Dict.
76
77         This interface is private in the hopes that it will be able to
78         be dropped again in the near-future. Caller beware!
79         """
80         return dict(copy.deepcopy(self._raw))
81
82
83 class QMPGreeting(Model):
84     """
85     Defined in qmp-spec.txt, section 2.2, "Server Greeting".
86
87     :param raw: The raw QMPGreeting object.
88     :raise KeyError: If any required fields are absent.
89     :raise TypeError: If any required fields have the wrong type.
90     """
91     def __init__(self, raw: Mapping[str, Any]):
92         super().__init__(raw)
93         #: 'version' member
94         self.version: Mapping[str, object]
95         #: 'capabilities' member
96         self.capabilities: Sequence[object]
97
98         self._check_member('version', abc.Mapping, "JSON object")
99         self.version = self._raw['version']
100
101         self._check_member('capabilities', abc.Sequence, "JSON array")
102         self.capabilities = self._raw['capabilities']
103
104
105 class ErrorResponse(Model):
106     """
107     Defined in qmp-spec.txt, section 2.4.2, "error".
108
109     :param raw: The raw ErrorResponse object.
110     :raise KeyError: If any required fields are absent.
111     :raise TypeError: If any required fields have the wrong type.
112     """
113     def __init__(self, raw: Mapping[str, Any]):
114         super().__init__(raw)
115         #: 'error' member
116         self.error: ErrorInfo
117         #: 'id' member
118         self.id: Optional[object] = None  # pylint: disable=invalid-name
119
120         self._check_member('error', abc.Mapping, "JSON object")
121         self.error = ErrorInfo(self._raw['error'])
122
123         if 'id' in raw:
124             self.id = raw['id']
125
126
127 class ErrorInfo(Model):
128     """
129     Defined in qmp-spec.txt, section 2.4.2, "error".
130
131     :param raw: The raw ErrorInfo object.
132     :raise KeyError: If any required fields are absent.
133     :raise TypeError: If any required fields have the wrong type.
134     """
135     def __init__(self, raw: Mapping[str, Any]):
136         super().__init__(raw)
137         #: 'class' member, with an underscore to avoid conflicts in Python.
138         self.class_: str
139         #: 'desc' member
140         self.desc: str
141
142         self._check_member('class', str, "string")
143         self.class_ = self._raw['class']
144
145         self._check_member('desc', str, "string")
146         self.desc = self._raw['desc']
This page took 0.0298 seconds and 4 git commands to generate.