]>
Commit | Line | Data |
---|---|---|
87ecb68b PB |
1 | #ifndef QEMU_CHAR_H |
2 | #define QEMU_CHAR_H | |
3 | ||
9af23989 | 4 | #include "qapi/qapi-types-char.h" |
1de7afc9 | 5 | #include "qemu/main-loop.h" |
0a73336d | 6 | #include "qemu/bitmap.h" |
777357d7 | 7 | #include "qom/object.h" |
376253ec | 8 | |
ae92cbd5 JL |
9 | #define IAC_EOR 239 |
10 | #define IAC_SE 240 | |
11 | #define IAC_NOP 241 | |
12 | #define IAC_BREAK 243 | |
13 | #define IAC_IP 244 | |
14 | #define IAC_SB 250 | |
15 | #define IAC 255 | |
16 | ||
87ecb68b | 17 | /* character device */ |
4d43a603 | 18 | typedef struct CharBackend CharBackend; |
87ecb68b | 19 | |
8c260cb1 MAL |
20 | typedef enum { |
21 | CHR_EVENT_BREAK, /* serial break char */ | |
22 | CHR_EVENT_OPENED, /* new connection established */ | |
23 | CHR_EVENT_MUX_IN, /* mux-focus was set to this terminal */ | |
24 | CHR_EVENT_MUX_OUT, /* mux-focus will move on */ | |
d8861011 PX |
25 | CHR_EVENT_CLOSED /* connection closed. NOTE: currently this event |
26 | * is only bound to the read port of the chardev. | |
27 | * Normally the read port and write port of a | |
28 | * chardev should be the same, but it can be | |
29 | * different, e.g., for fd chardevs, when the two | |
30 | * fds are different. So when we received the | |
31 | * CLOSED event it's still possible that the out | |
32 | * port is still open. TODO: we should only send | |
33 | * the CLOSED event when both ports are closed. | |
34 | */ | |
8c260cb1 | 35 | } QEMUChrEvent; |
87ecb68b | 36 | |
f612143a | 37 | #define CHR_READ_BUF_LEN 4096 |
87ecb68b | 38 | |
0a73336d DB |
39 | typedef enum { |
40 | /* Whether the chardev peer is able to close and | |
41 | * reopen the data channel, thus requiring support | |
42 | * for qemu_chr_wait_connected() to wait for a | |
43 | * valid connection */ | |
44 | QEMU_CHAR_FEATURE_RECONNECTABLE, | |
45 | /* Whether it is possible to send/recv file descriptors | |
46 | * over the data channel */ | |
47 | QEMU_CHAR_FEATURE_FD_PASS, | |
5ebd6703 MAL |
48 | /* Whether replay or record mode is enabled */ |
49 | QEMU_CHAR_FEATURE_REPLAY, | |
9ac3788b MAL |
50 | /* Whether the gcontext can be changed after calling |
51 | * qemu_chr_be_update_read_handlers() */ | |
52 | QEMU_CHAR_FEATURE_GCONTEXT, | |
0a73336d DB |
53 | |
54 | QEMU_CHAR_FEATURE_LAST, | |
279b066e | 55 | } ChardevFeature; |
0a73336d | 56 | |
4d43a603 | 57 | #define qemu_chr_replay(chr) qemu_chr_has_feature(chr, QEMU_CHAR_FEATURE_REPLAY) |
0a73336d | 58 | |
0ec7b3e7 | 59 | struct Chardev { |
777357d7 MAL |
60 | Object parent_obj; |
61 | ||
9005b2a7 | 62 | QemuMutex chr_write_lock; |
a4afa548 | 63 | CharBackend *be; |
5ccfae10 AL |
64 | char *label; |
65 | char *filename; | |
d0d7708b | 66 | int logfd; |
16665b94 | 67 | int be_open; |
b19456dd | 68 | GSource *gsource; |
95eeeba6 | 69 | GMainContext *gcontext; |
0a73336d | 70 | DECLARE_BITMAP(features, QEMU_CHAR_FEATURE_LAST); |
87ecb68b PB |
71 | }; |
72 | ||
2011fe56 | 73 | /** |
5662576a MAL |
74 | * qemu_chr_new_from_opts: |
75 | * @opts: see qemu-config.c for a list of valid options | |
2011fe56 AL |
76 | * |
77 | * Create a new character backend from a QemuOpts list. | |
78 | * | |
0ec846bf AN |
79 | * Returns: on success: a new character backend |
80 | * otherwise: NULL; @errp specifies the error | |
81 | * or left untouched in case of help option | |
2011fe56 | 82 | */ |
0ec7b3e7 MAL |
83 | Chardev *qemu_chr_new_from_opts(QemuOpts *opts, |
84 | Error **errp); | |
2011fe56 | 85 | |
21a933ea | 86 | /** |
5662576a MAL |
87 | * qemu_chr_parse_common: |
88 | * @opts: the options that still need parsing | |
89 | * @backend: a new backend | |
21a933ea EB |
90 | * |
91 | * Parse the common options available to all character backends. | |
21a933ea EB |
92 | */ |
93 | void qemu_chr_parse_common(QemuOpts *opts, ChardevCommon *backend); | |
94 | ||
75b60160 | 95 | /** |
5662576a | 96 | * qemu_chr_parse_opts: |
75b60160 AN |
97 | * |
98 | * Parse the options to the ChardevBackend struct. | |
99 | * | |
100 | * Returns: a new backend or NULL on error | |
101 | */ | |
102 | ChardevBackend *qemu_chr_parse_opts(QemuOpts *opts, | |
103 | Error **errp); | |
104 | ||
2011fe56 | 105 | /** |
5662576a MAL |
106 | * qemu_chr_new: |
107 | * @label: the name of the backend | |
108 | * @filename: the URI | |
2011fe56 AL |
109 | * |
110 | * Create a new character backend from a URI. | |
95e30b2a | 111 | * Do not implicitly initialize a monitor if the chardev is muxed. |
2011fe56 | 112 | * |
2011fe56 AL |
113 | * Returns: a new character backend |
114 | */ | |
0ec7b3e7 | 115 | Chardev *qemu_chr_new(const char *label, const char *filename); |
94a40fc5 | 116 | |
7bb86085 | 117 | /** |
95e30b2a MAL |
118 | * qemu_chr_new_mux_mon: |
119 | * @label: the name of the backend | |
120 | * @filename: the URI | |
121 | * | |
122 | * Create a new character backend from a URI. | |
123 | * Implicitly initialize a monitor if the chardev is muxed. | |
124 | * | |
125 | * Returns: a new character backend | |
126 | */ | |
127 | Chardev *qemu_chr_new_mux_mon(const char *label, const char *filename); | |
128 | ||
129 | /** | |
130 | * qemu_chr_change: | |
131 | * @opts: the new backend options | |
7bb86085 AN |
132 | * |
133 | * Change an existing character backend | |
7bb86085 AN |
134 | */ |
135 | void qemu_chr_change(QemuOpts *opts, Error **errp); | |
136 | ||
aa5cb7f5 | 137 | /** |
5662576a | 138 | * qemu_chr_cleanup: |
aa5cb7f5 MAL |
139 | * |
140 | * Delete all chardevs (when leaving qemu) | |
141 | */ | |
142 | void qemu_chr_cleanup(void); | |
143 | ||
33577b47 | 144 | /** |
5662576a MAL |
145 | * qemu_chr_new_noreplay: |
146 | * @label: the name of the backend | |
147 | * @filename: the URI | |
95e30b2a | 148 | * @permit_mux_mon: if chardev is muxed, initialize a monitor |
33577b47 PD |
149 | * |
150 | * Create a new character backend from a URI. | |
151 | * Character device communications are not written | |
152 | * into the replay log. | |
153 | * | |
33577b47 PD |
154 | * Returns: a new character backend |
155 | */ | |
95e30b2a MAL |
156 | Chardev *qemu_chr_new_noreplay(const char *label, const char *filename, |
157 | bool permit_mux_mon); | |
33577b47 | 158 | |
2011fe56 | 159 | /** |
5662576a | 160 | * qemu_chr_be_can_write: |
2011fe56 AL |
161 | * |
162 | * Determine how much data the front end can currently accept. This function | |
163 | * returns the number of bytes the front end can accept. If it returns 0, the | |
164 | * front end cannot receive data at the moment. The function must be polled | |
165 | * to determine when data can be received. | |
166 | * | |
167 | * Returns: the number of bytes the front end can receive via @qemu_chr_be_write | |
168 | */ | |
0ec7b3e7 | 169 | int qemu_chr_be_can_write(Chardev *s); |
2011fe56 AL |
170 | |
171 | /** | |
5662576a MAL |
172 | * qemu_chr_be_write: |
173 | * @buf: a buffer to receive data from the front end | |
174 | * @len: the number of bytes to receive from the front end | |
2011fe56 AL |
175 | * |
176 | * Write data from the back end to the front end. Before issuing this call, | |
177 | * the caller should call @qemu_chr_be_can_write to determine how much data | |
178 | * the front end can currently accept. | |
2011fe56 | 179 | */ |
0ec7b3e7 | 180 | void qemu_chr_be_write(Chardev *s, uint8_t *buf, int len); |
2011fe56 | 181 | |
33577b47 | 182 | /** |
5662576a MAL |
183 | * qemu_chr_be_write_impl: |
184 | * @buf: a buffer to receive data from the front end | |
185 | * @len: the number of bytes to receive from the front end | |
33577b47 PD |
186 | * |
187 | * Implementation of back end writing. Used by replay module. | |
33577b47 | 188 | */ |
0ec7b3e7 | 189 | void qemu_chr_be_write_impl(Chardev *s, uint8_t *buf, int len); |
a425d23f | 190 | |
07241c20 | 191 | /** |
5662576a MAL |
192 | * qemu_chr_be_update_read_handlers: |
193 | * @context: the gcontext that will be used to attach the watch sources | |
07241c20 PX |
194 | * |
195 | * Invoked when frontend read handlers are setup | |
07241c20 PX |
196 | */ |
197 | void qemu_chr_be_update_read_handlers(Chardev *s, | |
198 | GMainContext *context); | |
199 | ||
a425d23f | 200 | /** |
5662576a MAL |
201 | * qemu_chr_be_event: |
202 | * @event: the event to send | |
a425d23f HG |
203 | * |
204 | * Send an event from the back end to the front end. | |
a425d23f | 205 | */ |
0ec7b3e7 | 206 | void qemu_chr_be_event(Chardev *s, int event); |
a425d23f | 207 | |
0ec7b3e7 MAL |
208 | int qemu_chr_add_client(Chardev *s, int fd); |
209 | Chardev *qemu_chr_find(const char *name); | |
ad5c679c | 210 | |
0ec7b3e7 | 211 | bool qemu_chr_has_feature(Chardev *chr, |
279b066e | 212 | ChardevFeature feature); |
0ec7b3e7 | 213 | void qemu_chr_set_feature(Chardev *chr, |
279b066e | 214 | ChardevFeature feature); |
95e30b2a MAL |
215 | QemuOpts *qemu_chr_parse_compat(const char *label, const char *filename, |
216 | bool permit_mux_mon); | |
4d43a603 MAL |
217 | int qemu_chr_write(Chardev *s, const uint8_t *buf, int len, bool write_all); |
218 | #define qemu_chr_write_all(s, buf, len) qemu_chr_write(s, buf, len, true) | |
d24ca4b8 | 219 | int qemu_chr_wait_connected(Chardev *chr, Error **errp); |
2011fe56 | 220 | |
777357d7 MAL |
221 | #define TYPE_CHARDEV "chardev" |
222 | #define CHARDEV(obj) OBJECT_CHECK(Chardev, (obj), TYPE_CHARDEV) | |
223 | #define CHARDEV_CLASS(klass) \ | |
224 | OBJECT_CLASS_CHECK(ChardevClass, (klass), TYPE_CHARDEV) | |
225 | #define CHARDEV_GET_CLASS(obj) \ | |
226 | OBJECT_GET_CLASS(ChardevClass, (obj), TYPE_CHARDEV) | |
227 | ||
228 | #define TYPE_CHARDEV_NULL "chardev-null" | |
229 | #define TYPE_CHARDEV_MUX "chardev-mux" | |
230 | #define TYPE_CHARDEV_RINGBUF "chardev-ringbuf" | |
231 | #define TYPE_CHARDEV_PTY "chardev-pty" | |
232 | #define TYPE_CHARDEV_CONSOLE "chardev-console" | |
233 | #define TYPE_CHARDEV_STDIO "chardev-stdio" | |
234 | #define TYPE_CHARDEV_PIPE "chardev-pipe" | |
235 | #define TYPE_CHARDEV_MEMORY "chardev-memory" | |
236 | #define TYPE_CHARDEV_PARALLEL "chardev-parallel" | |
237 | #define TYPE_CHARDEV_FILE "chardev-file" | |
238 | #define TYPE_CHARDEV_SERIAL "chardev-serial" | |
239 | #define TYPE_CHARDEV_SOCKET "chardev-socket" | |
240 | #define TYPE_CHARDEV_UDP "chardev-udp" | |
241 | ||
777357d7 MAL |
242 | #define CHARDEV_IS_RINGBUF(chr) \ |
243 | object_dynamic_cast(OBJECT(chr), TYPE_CHARDEV_RINGBUF) | |
244 | #define CHARDEV_IS_PTY(chr) \ | |
245 | object_dynamic_cast(OBJECT(chr), TYPE_CHARDEV_PTY) | |
246 | ||
247 | typedef struct ChardevClass { | |
248 | ObjectClass parent_class; | |
249 | ||
250 | bool internal; /* TODO: eventually use TYPE_USER_CREATABLE */ | |
88cace9f | 251 | void (*parse)(QemuOpts *opts, ChardevBackend *backend, Error **errp); |
777357d7 MAL |
252 | |
253 | void (*open)(Chardev *chr, ChardevBackend *backend, | |
254 | bool *be_opened, Error **errp); | |
255 | ||
256 | int (*chr_write)(Chardev *s, const uint8_t *buf, int len); | |
257 | int (*chr_sync_read)(Chardev *s, const uint8_t *buf, int len); | |
258 | GSource *(*chr_add_watch)(Chardev *s, GIOCondition cond); | |
bb86d05f | 259 | void (*chr_update_read_handler)(Chardev *s); |
777357d7 MAL |
260 | int (*chr_ioctl)(Chardev *s, int cmd, void *arg); |
261 | int (*get_msgfds)(Chardev *s, int* fds, int num); | |
262 | int (*set_msgfds)(Chardev *s, int *fds, int num); | |
263 | int (*chr_add_client)(Chardev *chr, int fd); | |
264 | int (*chr_wait_connected)(Chardev *chr, Error **errp); | |
777357d7 MAL |
265 | void (*chr_disconnect)(Chardev *chr); |
266 | void (*chr_accept_input)(Chardev *chr); | |
267 | void (*chr_set_echo)(Chardev *chr, bool echo); | |
268 | void (*chr_set_fe_open)(Chardev *chr, int fe_open); | |
d09c4a47 | 269 | void (*chr_be_event)(Chardev *s, int event); |
c7278b43 PX |
270 | /* Return 0 if succeeded, 1 if failed */ |
271 | int (*chr_machine_done)(Chardev *chr); | |
777357d7 MAL |
272 | } ChardevClass; |
273 | ||
777357d7 MAL |
274 | Chardev *qemu_chardev_new(const char *id, const char *typename, |
275 | ChardevBackend *backend, Error **errp); | |
276 | ||
0e82f34d AL |
277 | extern int term_escape_char; |
278 | ||
2c716ba1 PX |
279 | GSource *qemu_chr_timeout_add_ms(Chardev *chr, guint ms, |
280 | GSourceFunc func, void *private); | |
281 | ||
3840f842 | 282 | /* console.c */ |
6f974c84 | 283 | void qemu_chr_parse_vc(QemuOpts *opts, ChardevBackend *backend, Error **errp); |
fa19d025 | 284 | |
87ecb68b | 285 | #endif |