qapi2texi: Fix to actually fail when 'doc-required' is false
[qemu.git] / ui / vnc.c
blob6e93b883b544384d4374c43a3c788b541ee110f5
1 /*
2 * QEMU VNC display driver
4 * Copyright (C) 2006 Anthony Liguori <anthony@codemonkey.ws>
5 * Copyright (C) 2006 Fabrice Bellard
6 * Copyright (C) 2009 Red Hat, Inc
8 * Permission is hereby granted, free of charge, to any person obtaining a copy
9 * of this software and associated documentation files (the "Software"), to deal
10 * in the Software without restriction, including without limitation the rights
11 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
12 * copies of the Software, and to permit persons to whom the Software is
13 * furnished to do so, subject to the following conditions:
15 * The above copyright notice and this permission notice shall be included in
16 * all copies or substantial portions of the Software.
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24 * THE SOFTWARE.
27 #include "qemu/osdep.h"
28 #include "vnc.h"
29 #include "vnc-jobs.h"
30 #include "trace.h"
31 #include "hw/qdev.h"
32 #include "sysemu/sysemu.h"
33 #include "qemu/error-report.h"
34 #include "qemu/sockets.h"
35 #include "qemu/timer.h"
36 #include "qemu/acl.h"
37 #include "qemu/config-file.h"
38 #include "qapi/qmp/qerror.h"
39 #include "qapi/qmp/types.h"
40 #include "qmp-commands.h"
41 #include "ui/input.h"
42 #include "qapi-event.h"
43 #include "crypto/hash.h"
44 #include "crypto/tlscredsanon.h"
45 #include "crypto/tlscredsx509.h"
46 #include "qom/object_interfaces.h"
47 #include "qemu/cutils.h"
48 #include "io/dns-resolver.h"
50 #define VNC_REFRESH_INTERVAL_BASE GUI_REFRESH_INTERVAL_DEFAULT
51 #define VNC_REFRESH_INTERVAL_INC 50
52 #define VNC_REFRESH_INTERVAL_MAX GUI_REFRESH_INTERVAL_IDLE
53 static const struct timeval VNC_REFRESH_STATS = { 0, 500000 };
54 static const struct timeval VNC_REFRESH_LOSSY = { 2, 0 };
56 #include "vnc_keysym.h"
57 #include "crypto/cipher.h"
59 static QTAILQ_HEAD(, VncDisplay) vnc_displays =
60 QTAILQ_HEAD_INITIALIZER(vnc_displays);
62 static int vnc_cursor_define(VncState *vs);
63 static void vnc_release_modifiers(VncState *vs);
65 static void vnc_set_share_mode(VncState *vs, VncShareMode mode)
67 #ifdef _VNC_DEBUG
68 static const char *mn[] = {
69 [0] = "undefined",
70 [VNC_SHARE_MODE_CONNECTING] = "connecting",
71 [VNC_SHARE_MODE_SHARED] = "shared",
72 [VNC_SHARE_MODE_EXCLUSIVE] = "exclusive",
73 [VNC_SHARE_MODE_DISCONNECTED] = "disconnected",
75 fprintf(stderr, "%s/%p: %s -> %s\n", __func__,
76 vs->ioc, mn[vs->share_mode], mn[mode]);
77 #endif
79 switch (vs->share_mode) {
80 case VNC_SHARE_MODE_CONNECTING:
81 vs->vd->num_connecting--;
82 break;
83 case VNC_SHARE_MODE_SHARED:
84 vs->vd->num_shared--;
85 break;
86 case VNC_SHARE_MODE_EXCLUSIVE:
87 vs->vd->num_exclusive--;
88 break;
89 default:
90 break;
93 vs->share_mode = mode;
95 switch (vs->share_mode) {
96 case VNC_SHARE_MODE_CONNECTING:
97 vs->vd->num_connecting++;
98 break;
99 case VNC_SHARE_MODE_SHARED:
100 vs->vd->num_shared++;
101 break;
102 case VNC_SHARE_MODE_EXCLUSIVE:
103 vs->vd->num_exclusive++;
104 break;
105 default:
106 break;
111 static void vnc_init_basic_info(SocketAddress *addr,
112 VncBasicInfo *info,
113 Error **errp)
115 switch (addr->type) {
116 case SOCKET_ADDRESS_KIND_INET:
117 info->host = g_strdup(addr->u.inet.data->host);
118 info->service = g_strdup(addr->u.inet.data->port);
119 if (addr->u.inet.data->ipv6) {
120 info->family = NETWORK_ADDRESS_FAMILY_IPV6;
121 } else {
122 info->family = NETWORK_ADDRESS_FAMILY_IPV4;
124 break;
126 case SOCKET_ADDRESS_KIND_UNIX:
127 info->host = g_strdup("");
128 info->service = g_strdup(addr->u.q_unix.data->path);
129 info->family = NETWORK_ADDRESS_FAMILY_UNIX;
130 break;
132 default:
133 error_setg(errp, "Unsupported socket kind %d",
134 addr->type);
135 break;
138 return;
141 static void vnc_init_basic_info_from_server_addr(QIOChannelSocket *ioc,
142 VncBasicInfo *info,
143 Error **errp)
145 SocketAddress *addr = NULL;
147 if (!ioc) {
148 error_setg(errp, "No listener socket available");
149 return;
152 addr = qio_channel_socket_get_local_address(ioc, errp);
153 if (!addr) {
154 return;
157 vnc_init_basic_info(addr, info, errp);
158 qapi_free_SocketAddress(addr);
161 static void vnc_init_basic_info_from_remote_addr(QIOChannelSocket *ioc,
162 VncBasicInfo *info,
163 Error **errp)
165 SocketAddress *addr = NULL;
167 addr = qio_channel_socket_get_remote_address(ioc, errp);
168 if (!addr) {
169 return;
172 vnc_init_basic_info(addr, info, errp);
173 qapi_free_SocketAddress(addr);
176 static const char *vnc_auth_name(VncDisplay *vd) {
177 switch (vd->auth) {
178 case VNC_AUTH_INVALID:
179 return "invalid";
180 case VNC_AUTH_NONE:
181 return "none";
182 case VNC_AUTH_VNC:
183 return "vnc";
184 case VNC_AUTH_RA2:
185 return "ra2";
186 case VNC_AUTH_RA2NE:
187 return "ra2ne";
188 case VNC_AUTH_TIGHT:
189 return "tight";
190 case VNC_AUTH_ULTRA:
191 return "ultra";
192 case VNC_AUTH_TLS:
193 return "tls";
194 case VNC_AUTH_VENCRYPT:
195 switch (vd->subauth) {
196 case VNC_AUTH_VENCRYPT_PLAIN:
197 return "vencrypt+plain";
198 case VNC_AUTH_VENCRYPT_TLSNONE:
199 return "vencrypt+tls+none";
200 case VNC_AUTH_VENCRYPT_TLSVNC:
201 return "vencrypt+tls+vnc";
202 case VNC_AUTH_VENCRYPT_TLSPLAIN:
203 return "vencrypt+tls+plain";
204 case VNC_AUTH_VENCRYPT_X509NONE:
205 return "vencrypt+x509+none";
206 case VNC_AUTH_VENCRYPT_X509VNC:
207 return "vencrypt+x509+vnc";
208 case VNC_AUTH_VENCRYPT_X509PLAIN:
209 return "vencrypt+x509+plain";
210 case VNC_AUTH_VENCRYPT_TLSSASL:
211 return "vencrypt+tls+sasl";
212 case VNC_AUTH_VENCRYPT_X509SASL:
213 return "vencrypt+x509+sasl";
214 default:
215 return "vencrypt";
217 case VNC_AUTH_SASL:
218 return "sasl";
220 return "unknown";
223 static VncServerInfo *vnc_server_info_get(VncDisplay *vd)
225 VncServerInfo *info;
226 Error *err = NULL;
228 if (!vd->nlsock) {
229 return NULL;
232 info = g_malloc0(sizeof(*info));
233 vnc_init_basic_info_from_server_addr(vd->lsock[0],
234 qapi_VncServerInfo_base(info), &err);
235 info->has_auth = true;
236 info->auth = g_strdup(vnc_auth_name(vd));
237 if (err) {
238 qapi_free_VncServerInfo(info);
239 info = NULL;
240 error_free(err);
242 return info;
245 static void vnc_client_cache_auth(VncState *client)
247 if (!client->info) {
248 return;
251 if (client->tls) {
252 client->info->x509_dname =
253 qcrypto_tls_session_get_peer_name(client->tls);
254 client->info->has_x509_dname =
255 client->info->x509_dname != NULL;
257 #ifdef CONFIG_VNC_SASL
258 if (client->sasl.conn &&
259 client->sasl.username) {
260 client->info->has_sasl_username = true;
261 client->info->sasl_username = g_strdup(client->sasl.username);
263 #endif
266 static void vnc_client_cache_addr(VncState *client)
268 Error *err = NULL;
270 client->info = g_malloc0(sizeof(*client->info));
271 vnc_init_basic_info_from_remote_addr(client->sioc,
272 qapi_VncClientInfo_base(client->info),
273 &err);
274 if (err) {
275 qapi_free_VncClientInfo(client->info);
276 client->info = NULL;
277 error_free(err);
281 static void vnc_qmp_event(VncState *vs, QAPIEvent event)
283 VncServerInfo *si;
285 if (!vs->info) {
286 return;
289 si = vnc_server_info_get(vs->vd);
290 if (!si) {
291 return;
294 switch (event) {
295 case QAPI_EVENT_VNC_CONNECTED:
296 qapi_event_send_vnc_connected(si, qapi_VncClientInfo_base(vs->info),
297 &error_abort);
298 break;
299 case QAPI_EVENT_VNC_INITIALIZED:
300 qapi_event_send_vnc_initialized(si, vs->info, &error_abort);
301 break;
302 case QAPI_EVENT_VNC_DISCONNECTED:
303 qapi_event_send_vnc_disconnected(si, vs->info, &error_abort);
304 break;
305 default:
306 break;
309 qapi_free_VncServerInfo(si);
312 static VncClientInfo *qmp_query_vnc_client(const VncState *client)
314 VncClientInfo *info;
315 Error *err = NULL;
317 info = g_malloc0(sizeof(*info));
319 vnc_init_basic_info_from_remote_addr(client->sioc,
320 qapi_VncClientInfo_base(info),
321 &err);
322 if (err) {
323 error_free(err);
324 qapi_free_VncClientInfo(info);
325 return NULL;
328 info->websocket = client->websocket;
330 if (client->tls) {
331 info->x509_dname = qcrypto_tls_session_get_peer_name(client->tls);
332 info->has_x509_dname = info->x509_dname != NULL;
334 #ifdef CONFIG_VNC_SASL
335 if (client->sasl.conn && client->sasl.username) {
336 info->has_sasl_username = true;
337 info->sasl_username = g_strdup(client->sasl.username);
339 #endif
341 return info;
344 static VncDisplay *vnc_display_find(const char *id)
346 VncDisplay *vd;
348 if (id == NULL) {
349 return QTAILQ_FIRST(&vnc_displays);
351 QTAILQ_FOREACH(vd, &vnc_displays, next) {
352 if (strcmp(id, vd->id) == 0) {
353 return vd;
356 return NULL;
359 static VncClientInfoList *qmp_query_client_list(VncDisplay *vd)
361 VncClientInfoList *cinfo, *prev = NULL;
362 VncState *client;
364 QTAILQ_FOREACH(client, &vd->clients, next) {
365 cinfo = g_new0(VncClientInfoList, 1);
366 cinfo->value = qmp_query_vnc_client(client);
367 cinfo->next = prev;
368 prev = cinfo;
370 return prev;
373 VncInfo *qmp_query_vnc(Error **errp)
375 VncInfo *info = g_malloc0(sizeof(*info));
376 VncDisplay *vd = vnc_display_find(NULL);
377 SocketAddress *addr = NULL;
379 if (vd == NULL || !vd->nlsock) {
380 info->enabled = false;
381 } else {
382 info->enabled = true;
384 /* for compatibility with the original command */
385 info->has_clients = true;
386 info->clients = qmp_query_client_list(vd);
388 if (vd->lsock == NULL) {
389 return info;
392 addr = qio_channel_socket_get_local_address(vd->lsock[0], errp);
393 if (!addr) {
394 goto out_error;
397 switch (addr->type) {
398 case SOCKET_ADDRESS_KIND_INET:
399 info->host = g_strdup(addr->u.inet.data->host);
400 info->service = g_strdup(addr->u.inet.data->port);
401 if (addr->u.inet.data->ipv6) {
402 info->family = NETWORK_ADDRESS_FAMILY_IPV6;
403 } else {
404 info->family = NETWORK_ADDRESS_FAMILY_IPV4;
406 break;
408 case SOCKET_ADDRESS_KIND_UNIX:
409 info->host = g_strdup("");
410 info->service = g_strdup(addr->u.q_unix.data->path);
411 info->family = NETWORK_ADDRESS_FAMILY_UNIX;
412 break;
414 default:
415 error_setg(errp, "Unsupported socket kind %d",
416 addr->type);
417 goto out_error;
420 info->has_host = true;
421 info->has_service = true;
422 info->has_family = true;
424 info->has_auth = true;
425 info->auth = g_strdup(vnc_auth_name(vd));
428 qapi_free_SocketAddress(addr);
429 return info;
431 out_error:
432 qapi_free_SocketAddress(addr);
433 qapi_free_VncInfo(info);
434 return NULL;
438 static void qmp_query_auth(int auth, int subauth,
439 VncPrimaryAuth *qmp_auth,
440 VncVencryptSubAuth *qmp_vencrypt,
441 bool *qmp_has_vencrypt);
443 static VncServerInfo2List *qmp_query_server_entry(QIOChannelSocket *ioc,
444 bool websocket,
445 int auth,
446 int subauth,
447 VncServerInfo2List *prev)
449 VncServerInfo2List *list;
450 VncServerInfo2 *info;
451 Error *err = NULL;
452 SocketAddress *addr;
454 addr = qio_channel_socket_get_local_address(ioc, &err);
455 if (!addr) {
456 error_free(err);
457 return prev;
460 info = g_new0(VncServerInfo2, 1);
461 vnc_init_basic_info(addr, qapi_VncServerInfo2_base(info), &err);
462 qapi_free_SocketAddress(addr);
463 if (err) {
464 qapi_free_VncServerInfo2(info);
465 error_free(err);
466 return prev;
468 info->websocket = websocket;
470 qmp_query_auth(auth, subauth, &info->auth,
471 &info->vencrypt, &info->has_vencrypt);
473 list = g_new0(VncServerInfo2List, 1);
474 list->value = info;
475 list->next = prev;
476 return list;
479 static void qmp_query_auth(int auth, int subauth,
480 VncPrimaryAuth *qmp_auth,
481 VncVencryptSubAuth *qmp_vencrypt,
482 bool *qmp_has_vencrypt)
484 switch (auth) {
485 case VNC_AUTH_VNC:
486 *qmp_auth = VNC_PRIMARY_AUTH_VNC;
487 break;
488 case VNC_AUTH_RA2:
489 *qmp_auth = VNC_PRIMARY_AUTH_RA2;
490 break;
491 case VNC_AUTH_RA2NE:
492 *qmp_auth = VNC_PRIMARY_AUTH_RA2NE;
493 break;
494 case VNC_AUTH_TIGHT:
495 *qmp_auth = VNC_PRIMARY_AUTH_TIGHT;
496 break;
497 case VNC_AUTH_ULTRA:
498 *qmp_auth = VNC_PRIMARY_AUTH_ULTRA;
499 break;
500 case VNC_AUTH_TLS:
501 *qmp_auth = VNC_PRIMARY_AUTH_TLS;
502 break;
503 case VNC_AUTH_VENCRYPT:
504 *qmp_auth = VNC_PRIMARY_AUTH_VENCRYPT;
505 *qmp_has_vencrypt = true;
506 switch (subauth) {
507 case VNC_AUTH_VENCRYPT_PLAIN:
508 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_PLAIN;
509 break;
510 case VNC_AUTH_VENCRYPT_TLSNONE:
511 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_TLS_NONE;
512 break;
513 case VNC_AUTH_VENCRYPT_TLSVNC:
514 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_TLS_VNC;
515 break;
516 case VNC_AUTH_VENCRYPT_TLSPLAIN:
517 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_TLS_PLAIN;
518 break;
519 case VNC_AUTH_VENCRYPT_X509NONE:
520 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_X509_NONE;
521 break;
522 case VNC_AUTH_VENCRYPT_X509VNC:
523 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_X509_VNC;
524 break;
525 case VNC_AUTH_VENCRYPT_X509PLAIN:
526 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_X509_PLAIN;
527 break;
528 case VNC_AUTH_VENCRYPT_TLSSASL:
529 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_TLS_SASL;
530 break;
531 case VNC_AUTH_VENCRYPT_X509SASL:
532 *qmp_vencrypt = VNC_VENCRYPT_SUB_AUTH_X509_SASL;
533 break;
534 default:
535 *qmp_has_vencrypt = false;
536 break;
538 break;
539 case VNC_AUTH_SASL:
540 *qmp_auth = VNC_PRIMARY_AUTH_SASL;
541 break;
542 case VNC_AUTH_NONE:
543 default:
544 *qmp_auth = VNC_PRIMARY_AUTH_NONE;
545 break;
549 VncInfo2List *qmp_query_vnc_servers(Error **errp)
551 VncInfo2List *item, *prev = NULL;
552 VncInfo2 *info;
553 VncDisplay *vd;
554 DeviceState *dev;
555 size_t i;
557 QTAILQ_FOREACH(vd, &vnc_displays, next) {
558 info = g_new0(VncInfo2, 1);
559 info->id = g_strdup(vd->id);
560 info->clients = qmp_query_client_list(vd);
561 qmp_query_auth(vd->auth, vd->subauth, &info->auth,
562 &info->vencrypt, &info->has_vencrypt);
563 if (vd->dcl.con) {
564 dev = DEVICE(object_property_get_link(OBJECT(vd->dcl.con),
565 "device", NULL));
566 info->has_display = true;
567 info->display = g_strdup(dev->id);
569 for (i = 0; i < vd->nlsock; i++) {
570 info->server = qmp_query_server_entry(
571 vd->lsock[i], false, vd->auth, vd->subauth, info->server);
573 for (i = 0; i < vd->nlwebsock; i++) {
574 info->server = qmp_query_server_entry(
575 vd->lwebsock[i], true, vd->ws_auth,
576 vd->ws_subauth, info->server);
579 item = g_new0(VncInfo2List, 1);
580 item->value = info;
581 item->next = prev;
582 prev = item;
584 return prev;
587 /* TODO
588 1) Get the queue working for IO.
589 2) there is some weirdness when using the -S option (the screen is grey
590 and not totally invalidated
591 3) resolutions > 1024
594 static int vnc_update_client(VncState *vs, int has_dirty, bool sync);
595 static void vnc_disconnect_start(VncState *vs);
597 static void vnc_colordepth(VncState *vs);
598 static void framebuffer_update_request(VncState *vs, int incremental,
599 int x_position, int y_position,
600 int w, int h);
601 static void vnc_refresh(DisplayChangeListener *dcl);
602 static int vnc_refresh_server_surface(VncDisplay *vd);
604 static int vnc_width(VncDisplay *vd)
606 return MIN(VNC_MAX_WIDTH, ROUND_UP(surface_width(vd->ds),
607 VNC_DIRTY_PIXELS_PER_BIT));
610 static int vnc_height(VncDisplay *vd)
612 return MIN(VNC_MAX_HEIGHT, surface_height(vd->ds));
615 static void vnc_set_area_dirty(DECLARE_BITMAP(dirty[VNC_MAX_HEIGHT],
616 VNC_MAX_WIDTH / VNC_DIRTY_PIXELS_PER_BIT),
617 VncDisplay *vd,
618 int x, int y, int w, int h)
620 int width = vnc_width(vd);
621 int height = vnc_height(vd);
623 /* this is needed this to ensure we updated all affected
624 * blocks if x % VNC_DIRTY_PIXELS_PER_BIT != 0 */
625 w += (x % VNC_DIRTY_PIXELS_PER_BIT);
626 x -= (x % VNC_DIRTY_PIXELS_PER_BIT);
628 x = MIN(x, width);
629 y = MIN(y, height);
630 w = MIN(x + w, width) - x;
631 h = MIN(y + h, height);
633 for (; y < h; y++) {
634 bitmap_set(dirty[y], x / VNC_DIRTY_PIXELS_PER_BIT,
635 DIV_ROUND_UP(w, VNC_DIRTY_PIXELS_PER_BIT));
639 static void vnc_dpy_update(DisplayChangeListener *dcl,
640 int x, int y, int w, int h)
642 VncDisplay *vd = container_of(dcl, VncDisplay, dcl);
643 struct VncSurface *s = &vd->guest;
645 vnc_set_area_dirty(s->dirty, vd, x, y, w, h);
648 void vnc_framebuffer_update(VncState *vs, int x, int y, int w, int h,
649 int32_t encoding)
651 vnc_write_u16(vs, x);
652 vnc_write_u16(vs, y);
653 vnc_write_u16(vs, w);
654 vnc_write_u16(vs, h);
656 vnc_write_s32(vs, encoding);
660 static void vnc_desktop_resize(VncState *vs)
662 if (vs->ioc == NULL || !vnc_has_feature(vs, VNC_FEATURE_RESIZE)) {
663 return;
665 if (vs->client_width == pixman_image_get_width(vs->vd->server) &&
666 vs->client_height == pixman_image_get_height(vs->vd->server)) {
667 return;
669 vs->client_width = pixman_image_get_width(vs->vd->server);
670 vs->client_height = pixman_image_get_height(vs->vd->server);
671 vnc_lock_output(vs);
672 vnc_write_u8(vs, VNC_MSG_SERVER_FRAMEBUFFER_UPDATE);
673 vnc_write_u8(vs, 0);
674 vnc_write_u16(vs, 1); /* number of rects */
675 vnc_framebuffer_update(vs, 0, 0, vs->client_width, vs->client_height,
676 VNC_ENCODING_DESKTOPRESIZE);
677 vnc_unlock_output(vs);
678 vnc_flush(vs);
681 static void vnc_abort_display_jobs(VncDisplay *vd)
683 VncState *vs;
685 QTAILQ_FOREACH(vs, &vd->clients, next) {
686 vnc_lock_output(vs);
687 vs->abort = true;
688 vnc_unlock_output(vs);
690 QTAILQ_FOREACH(vs, &vd->clients, next) {
691 vnc_jobs_join(vs);
693 QTAILQ_FOREACH(vs, &vd->clients, next) {
694 vnc_lock_output(vs);
695 vs->abort = false;
696 vnc_unlock_output(vs);
700 int vnc_server_fb_stride(VncDisplay *vd)
702 return pixman_image_get_stride(vd->server);
705 void *vnc_server_fb_ptr(VncDisplay *vd, int x, int y)
707 uint8_t *ptr;
709 ptr = (uint8_t *)pixman_image_get_data(vd->server);
710 ptr += y * vnc_server_fb_stride(vd);
711 ptr += x * VNC_SERVER_FB_BYTES;
712 return ptr;
715 static void vnc_update_server_surface(VncDisplay *vd)
717 int width, height;
719 qemu_pixman_image_unref(vd->server);
720 vd->server = NULL;
722 if (QTAILQ_EMPTY(&vd->clients)) {
723 return;
726 width = vnc_width(vd);
727 height = vnc_height(vd);
728 vd->server = pixman_image_create_bits(VNC_SERVER_FB_FORMAT,
729 width, height,
730 NULL, 0);
732 memset(vd->guest.dirty, 0x00, sizeof(vd->guest.dirty));
733 vnc_set_area_dirty(vd->guest.dirty, vd, 0, 0,
734 width, height);
737 static void vnc_dpy_switch(DisplayChangeListener *dcl,
738 DisplaySurface *surface)
740 VncDisplay *vd = container_of(dcl, VncDisplay, dcl);
741 VncState *vs;
743 vnc_abort_display_jobs(vd);
744 vd->ds = surface;
746 /* server surface */
747 vnc_update_server_surface(vd);
749 /* guest surface */
750 qemu_pixman_image_unref(vd->guest.fb);
751 vd->guest.fb = pixman_image_ref(surface->image);
752 vd->guest.format = surface->format;
754 QTAILQ_FOREACH(vs, &vd->clients, next) {
755 vnc_colordepth(vs);
756 vnc_desktop_resize(vs);
757 if (vs->vd->cursor) {
758 vnc_cursor_define(vs);
760 memset(vs->dirty, 0x00, sizeof(vs->dirty));
761 vnc_set_area_dirty(vs->dirty, vd, 0, 0,
762 vnc_width(vd),
763 vnc_height(vd));
767 /* fastest code */
768 static void vnc_write_pixels_copy(VncState *vs,
769 void *pixels, int size)
771 vnc_write(vs, pixels, size);
774 /* slowest but generic code. */
775 void vnc_convert_pixel(VncState *vs, uint8_t *buf, uint32_t v)
777 uint8_t r, g, b;
779 #if VNC_SERVER_FB_FORMAT == PIXMAN_FORMAT(32, PIXMAN_TYPE_ARGB, 0, 8, 8, 8)
780 r = (((v & 0x00ff0000) >> 16) << vs->client_pf.rbits) >> 8;
781 g = (((v & 0x0000ff00) >> 8) << vs->client_pf.gbits) >> 8;
782 b = (((v & 0x000000ff) >> 0) << vs->client_pf.bbits) >> 8;
783 #else
784 # error need some bits here if you change VNC_SERVER_FB_FORMAT
785 #endif
786 v = (r << vs->client_pf.rshift) |
787 (g << vs->client_pf.gshift) |
788 (b << vs->client_pf.bshift);
789 switch (vs->client_pf.bytes_per_pixel) {
790 case 1:
791 buf[0] = v;
792 break;
793 case 2:
794 if (vs->client_be) {
795 buf[0] = v >> 8;
796 buf[1] = v;
797 } else {
798 buf[1] = v >> 8;
799 buf[0] = v;
801 break;
802 default:
803 case 4:
804 if (vs->client_be) {
805 buf[0] = v >> 24;
806 buf[1] = v >> 16;
807 buf[2] = v >> 8;
808 buf[3] = v;
809 } else {
810 buf[3] = v >> 24;
811 buf[2] = v >> 16;
812 buf[1] = v >> 8;
813 buf[0] = v;
815 break;
819 static void vnc_write_pixels_generic(VncState *vs,
820 void *pixels1, int size)
822 uint8_t buf[4];
824 if (VNC_SERVER_FB_BYTES == 4) {
825 uint32_t *pixels = pixels1;
826 int n, i;
827 n = size >> 2;
828 for (i = 0; i < n; i++) {
829 vnc_convert_pixel(vs, buf, pixels[i]);
830 vnc_write(vs, buf, vs->client_pf.bytes_per_pixel);
835 int vnc_raw_send_framebuffer_update(VncState *vs, int x, int y, int w, int h)
837 int i;
838 uint8_t *row;
839 VncDisplay *vd = vs->vd;
841 row = vnc_server_fb_ptr(vd, x, y);
842 for (i = 0; i < h; i++) {
843 vs->write_pixels(vs, row, w * VNC_SERVER_FB_BYTES);
844 row += vnc_server_fb_stride(vd);
846 return 1;
849 int vnc_send_framebuffer_update(VncState *vs, int x, int y, int w, int h)
851 int n = 0;
852 bool encode_raw = false;
853 size_t saved_offs = vs->output.offset;
855 switch(vs->vnc_encoding) {
856 case VNC_ENCODING_ZLIB:
857 n = vnc_zlib_send_framebuffer_update(vs, x, y, w, h);
858 break;
859 case VNC_ENCODING_HEXTILE:
860 vnc_framebuffer_update(vs, x, y, w, h, VNC_ENCODING_HEXTILE);
861 n = vnc_hextile_send_framebuffer_update(vs, x, y, w, h);
862 break;
863 case VNC_ENCODING_TIGHT:
864 n = vnc_tight_send_framebuffer_update(vs, x, y, w, h);
865 break;
866 case VNC_ENCODING_TIGHT_PNG:
867 n = vnc_tight_png_send_framebuffer_update(vs, x, y, w, h);
868 break;
869 case VNC_ENCODING_ZRLE:
870 n = vnc_zrle_send_framebuffer_update(vs, x, y, w, h);
871 break;
872 case VNC_ENCODING_ZYWRLE:
873 n = vnc_zywrle_send_framebuffer_update(vs, x, y, w, h);
874 break;
875 default:
876 encode_raw = true;
877 break;
880 /* If the client has the same pixel format as our internal buffer and
881 * a RAW encoding would need less space fall back to RAW encoding to
882 * save bandwidth and processing power in the client. */
883 if (!encode_raw && vs->write_pixels == vnc_write_pixels_copy &&
884 12 + h * w * VNC_SERVER_FB_BYTES <= (vs->output.offset - saved_offs)) {
885 vs->output.offset = saved_offs;
886 encode_raw = true;
889 if (encode_raw) {
890 vnc_framebuffer_update(vs, x, y, w, h, VNC_ENCODING_RAW);
891 n = vnc_raw_send_framebuffer_update(vs, x, y, w, h);
894 return n;
897 static void vnc_mouse_set(DisplayChangeListener *dcl,
898 int x, int y, int visible)
900 /* can we ask the client(s) to move the pointer ??? */
903 static int vnc_cursor_define(VncState *vs)
905 QEMUCursor *c = vs->vd->cursor;
906 int isize;
908 if (vnc_has_feature(vs, VNC_FEATURE_RICH_CURSOR)) {
909 vnc_lock_output(vs);
910 vnc_write_u8(vs, VNC_MSG_SERVER_FRAMEBUFFER_UPDATE);
911 vnc_write_u8(vs, 0); /* padding */
912 vnc_write_u16(vs, 1); /* # of rects */
913 vnc_framebuffer_update(vs, c->hot_x, c->hot_y, c->width, c->height,
914 VNC_ENCODING_RICH_CURSOR);
915 isize = c->width * c->height * vs->client_pf.bytes_per_pixel;
916 vnc_write_pixels_generic(vs, c->data, isize);
917 vnc_write(vs, vs->vd->cursor_mask, vs->vd->cursor_msize);
918 vnc_unlock_output(vs);
919 return 0;
921 return -1;
924 static void vnc_dpy_cursor_define(DisplayChangeListener *dcl,
925 QEMUCursor *c)
927 VncDisplay *vd = container_of(dcl, VncDisplay, dcl);
928 VncState *vs;
930 cursor_put(vd->cursor);
931 g_free(vd->cursor_mask);
933 vd->cursor = c;
934 cursor_get(vd->cursor);
935 vd->cursor_msize = cursor_get_mono_bpl(c) * c->height;
936 vd->cursor_mask = g_malloc0(vd->cursor_msize);
937 cursor_get_mono_mask(c, 0, vd->cursor_mask);
939 QTAILQ_FOREACH(vs, &vd->clients, next) {
940 vnc_cursor_define(vs);
944 static int find_and_clear_dirty_height(VncState *vs,
945 int y, int last_x, int x, int height)
947 int h;
949 for (h = 1; h < (height - y); h++) {
950 if (!test_bit(last_x, vs->dirty[y + h])) {
951 break;
953 bitmap_clear(vs->dirty[y + h], last_x, x - last_x);
956 return h;
959 static int vnc_update_client(VncState *vs, int has_dirty, bool sync)
961 if (vs->disconnecting) {
962 vnc_disconnect_finish(vs);
963 return 0;
966 vs->has_dirty += has_dirty;
967 if (vs->need_update && !vs->disconnecting) {
968 VncDisplay *vd = vs->vd;
969 VncJob *job;
970 int y;
971 int height, width;
972 int n = 0;
974 if (vs->output.offset && !vs->audio_cap && !vs->force_update)
975 /* kernel send buffers are full -> drop frames to throttle */
976 return 0;
978 if (!vs->has_dirty && !vs->audio_cap && !vs->force_update)
979 return 0;
982 * Send screen updates to the vnc client using the server
983 * surface and server dirty map. guest surface updates
984 * happening in parallel don't disturb us, the next pass will
985 * send them to the client.
987 job = vnc_job_new(vs);
989 height = pixman_image_get_height(vd->server);
990 width = pixman_image_get_width(vd->server);
992 y = 0;
993 for (;;) {
994 int x, h;
995 unsigned long x2;
996 unsigned long offset = find_next_bit((unsigned long *) &vs->dirty,
997 height * VNC_DIRTY_BPL(vs),
998 y * VNC_DIRTY_BPL(vs));
999 if (offset == height * VNC_DIRTY_BPL(vs)) {
1000 /* no more dirty bits */
1001 break;
1003 y = offset / VNC_DIRTY_BPL(vs);
1004 x = offset % VNC_DIRTY_BPL(vs);
1005 x2 = find_next_zero_bit((unsigned long *) &vs->dirty[y],
1006 VNC_DIRTY_BPL(vs), x);
1007 bitmap_clear(vs->dirty[y], x, x2 - x);
1008 h = find_and_clear_dirty_height(vs, y, x, x2, height);
1009 x2 = MIN(x2, width / VNC_DIRTY_PIXELS_PER_BIT);
1010 if (x2 > x) {
1011 n += vnc_job_add_rect(job, x * VNC_DIRTY_PIXELS_PER_BIT, y,
1012 (x2 - x) * VNC_DIRTY_PIXELS_PER_BIT, h);
1014 if (!x && x2 == width / VNC_DIRTY_PIXELS_PER_BIT) {
1015 y += h;
1016 if (y == height) {
1017 break;
1022 vnc_job_push(job);
1023 if (sync) {
1024 vnc_jobs_join(vs);
1026 vs->force_update = 0;
1027 vs->has_dirty = 0;
1028 return n;
1031 if (vs->disconnecting) {
1032 vnc_disconnect_finish(vs);
1033 } else if (sync) {
1034 vnc_jobs_join(vs);
1037 return 0;
1040 /* audio */
1041 static void audio_capture_notify(void *opaque, audcnotification_e cmd)
1043 VncState *vs = opaque;
1045 switch (cmd) {
1046 case AUD_CNOTIFY_DISABLE:
1047 vnc_lock_output(vs);
1048 vnc_write_u8(vs, VNC_MSG_SERVER_QEMU);
1049 vnc_write_u8(vs, VNC_MSG_SERVER_QEMU_AUDIO);
1050 vnc_write_u16(vs, VNC_MSG_SERVER_QEMU_AUDIO_END);
1051 vnc_unlock_output(vs);
1052 vnc_flush(vs);
1053 break;
1055 case AUD_CNOTIFY_ENABLE:
1056 vnc_lock_output(vs);
1057 vnc_write_u8(vs, VNC_MSG_SERVER_QEMU);
1058 vnc_write_u8(vs, VNC_MSG_SERVER_QEMU_AUDIO);
1059 vnc_write_u16(vs, VNC_MSG_SERVER_QEMU_AUDIO_BEGIN);
1060 vnc_unlock_output(vs);
1061 vnc_flush(vs);
1062 break;
1066 static void audio_capture_destroy(void *opaque)
1070 static void audio_capture(void *opaque, void *buf, int size)
1072 VncState *vs = opaque;
1074 vnc_lock_output(vs);
1075 vnc_write_u8(vs, VNC_MSG_SERVER_QEMU);
1076 vnc_write_u8(vs, VNC_MSG_SERVER_QEMU_AUDIO);
1077 vnc_write_u16(vs, VNC_MSG_SERVER_QEMU_AUDIO_DATA);
1078 vnc_write_u32(vs, size);
1079 vnc_write(vs, buf, size);
1080 vnc_unlock_output(vs);
1081 vnc_flush(vs);
1084 static void audio_add(VncState *vs)
1086 struct audio_capture_ops ops;
1088 if (vs->audio_cap) {
1089 error_report("audio already running");
1090 return;
1093 ops.notify = audio_capture_notify;
1094 ops.destroy = audio_capture_destroy;
1095 ops.capture = audio_capture;
1097 vs->audio_cap = AUD_add_capture(&vs->as, &ops, vs);
1098 if (!vs->audio_cap) {
1099 error_report("Failed to add audio capture");
1103 static void audio_del(VncState *vs)
1105 if (vs->audio_cap) {
1106 AUD_del_capture(vs->audio_cap, vs);
1107 vs->audio_cap = NULL;
1111 static void vnc_disconnect_start(VncState *vs)
1113 if (vs->disconnecting) {
1114 return;
1116 vnc_set_share_mode(vs, VNC_SHARE_MODE_DISCONNECTED);
1117 if (vs->ioc_tag) {
1118 g_source_remove(vs->ioc_tag);
1120 qio_channel_close(vs->ioc, NULL);
1121 vs->disconnecting = TRUE;
1124 void vnc_disconnect_finish(VncState *vs)
1126 int i;
1128 vnc_jobs_join(vs); /* Wait encoding jobs */
1130 vnc_lock_output(vs);
1131 vnc_qmp_event(vs, QAPI_EVENT_VNC_DISCONNECTED);
1133 buffer_free(&vs->input);
1134 buffer_free(&vs->output);
1136 qapi_free_VncClientInfo(vs->info);
1138 vnc_zlib_clear(vs);
1139 vnc_tight_clear(vs);
1140 vnc_zrle_clear(vs);
1142 #ifdef CONFIG_VNC_SASL
1143 vnc_sasl_client_cleanup(vs);
1144 #endif /* CONFIG_VNC_SASL */
1145 audio_del(vs);
1146 vnc_release_modifiers(vs);
1148 if (vs->mouse_mode_notifier.notify != NULL) {
1149 qemu_remove_mouse_mode_change_notifier(&vs->mouse_mode_notifier);
1151 QTAILQ_REMOVE(&vs->vd->clients, vs, next);
1152 if (QTAILQ_EMPTY(&vs->vd->clients)) {
1153 /* last client gone */
1154 vnc_update_server_surface(vs->vd);
1157 vnc_unlock_output(vs);
1159 qemu_mutex_destroy(&vs->output_mutex);
1160 if (vs->bh != NULL) {
1161 qemu_bh_delete(vs->bh);
1163 buffer_free(&vs->jobs_buffer);
1165 for (i = 0; i < VNC_STAT_ROWS; ++i) {
1166 g_free(vs->lossy_rect[i]);
1168 g_free(vs->lossy_rect);
1170 object_unref(OBJECT(vs->ioc));
1171 vs->ioc = NULL;
1172 object_unref(OBJECT(vs->sioc));
1173 vs->sioc = NULL;
1174 g_free(vs);
1177 ssize_t vnc_client_io_error(VncState *vs, ssize_t ret, Error **errp)
1179 if (ret <= 0) {
1180 if (ret == 0) {
1181 VNC_DEBUG("Closing down client sock: EOF\n");
1182 vnc_disconnect_start(vs);
1183 } else if (ret != QIO_CHANNEL_ERR_BLOCK) {
1184 VNC_DEBUG("Closing down client sock: ret %zd (%s)\n",
1185 ret, errp ? error_get_pretty(*errp) : "Unknown");
1186 vnc_disconnect_start(vs);
1189 if (errp) {
1190 error_free(*errp);
1191 *errp = NULL;
1193 return 0;
1195 return ret;
1199 void vnc_client_error(VncState *vs)
1201 VNC_DEBUG("Closing down client sock: protocol error\n");
1202 vnc_disconnect_start(vs);
1207 * Called to write a chunk of data to the client socket. The data may
1208 * be the raw data, or may have already been encoded by SASL.
1209 * The data will be written either straight onto the socket, or
1210 * written via the GNUTLS wrappers, if TLS/SSL encryption is enabled
1212 * NB, it is theoretically possible to have 2 layers of encryption,
1213 * both SASL, and this TLS layer. It is highly unlikely in practice
1214 * though, since SASL encryption will typically be a no-op if TLS
1215 * is active
1217 * Returns the number of bytes written, which may be less than
1218 * the requested 'datalen' if the socket would block. Returns
1219 * -1 on error, and disconnects the client socket.
1221 ssize_t vnc_client_write_buf(VncState *vs, const uint8_t *data, size_t datalen)
1223 Error *err = NULL;
1224 ssize_t ret;
1225 ret = qio_channel_write(
1226 vs->ioc, (const char *)data, datalen, &err);
1227 VNC_DEBUG("Wrote wire %p %zd -> %ld\n", data, datalen, ret);
1228 return vnc_client_io_error(vs, ret, &err);
1233 * Called to write buffered data to the client socket, when not
1234 * using any SASL SSF encryption layers. Will write as much data
1235 * as possible without blocking. If all buffered data is written,
1236 * will switch the FD poll() handler back to read monitoring.
1238 * Returns the number of bytes written, which may be less than
1239 * the buffered output data if the socket would block. Returns
1240 * -1 on error, and disconnects the client socket.
1242 static ssize_t vnc_client_write_plain(VncState *vs)
1244 ssize_t ret;
1246 #ifdef CONFIG_VNC_SASL
1247 VNC_DEBUG("Write Plain: Pending output %p size %zd offset %zd. Wait SSF %d\n",
1248 vs->output.buffer, vs->output.capacity, vs->output.offset,
1249 vs->sasl.waitWriteSSF);
1251 if (vs->sasl.conn &&
1252 vs->sasl.runSSF &&
1253 vs->sasl.waitWriteSSF) {
1254 ret = vnc_client_write_buf(vs, vs->output.buffer, vs->sasl.waitWriteSSF);
1255 if (ret)
1256 vs->sasl.waitWriteSSF -= ret;
1257 } else
1258 #endif /* CONFIG_VNC_SASL */
1259 ret = vnc_client_write_buf(vs, vs->output.buffer, vs->output.offset);
1260 if (!ret)
1261 return 0;
1263 buffer_advance(&vs->output, ret);
1265 if (vs->output.offset == 0) {
1266 if (vs->ioc_tag) {
1267 g_source_remove(vs->ioc_tag);
1269 vs->ioc_tag = qio_channel_add_watch(
1270 vs->ioc, G_IO_IN, vnc_client_io, vs, NULL);
1273 return ret;
1278 * First function called whenever there is data to be written to
1279 * the client socket. Will delegate actual work according to whether
1280 * SASL SSF layers are enabled (thus requiring encryption calls)
1282 static void vnc_client_write_locked(VncState *vs)
1284 #ifdef CONFIG_VNC_SASL
1285 if (vs->sasl.conn &&
1286 vs->sasl.runSSF &&
1287 !vs->sasl.waitWriteSSF) {
1288 vnc_client_write_sasl(vs);
1289 } else
1290 #endif /* CONFIG_VNC_SASL */
1292 vnc_client_write_plain(vs);
1296 static void vnc_client_write(VncState *vs)
1299 vnc_lock_output(vs);
1300 if (vs->output.offset) {
1301 vnc_client_write_locked(vs);
1302 } else if (vs->ioc != NULL) {
1303 if (vs->ioc_tag) {
1304 g_source_remove(vs->ioc_tag);
1306 vs->ioc_tag = qio_channel_add_watch(
1307 vs->ioc, G_IO_IN, vnc_client_io, vs, NULL);
1309 vnc_unlock_output(vs);
1312 void vnc_read_when(VncState *vs, VncReadEvent *func, size_t expecting)
1314 vs->read_handler = func;
1315 vs->read_handler_expect = expecting;
1320 * Called to read a chunk of data from the client socket. The data may
1321 * be the raw data, or may need to be further decoded by SASL.
1322 * The data will be read either straight from to the socket, or
1323 * read via the GNUTLS wrappers, if TLS/SSL encryption is enabled
1325 * NB, it is theoretically possible to have 2 layers of encryption,
1326 * both SASL, and this TLS layer. It is highly unlikely in practice
1327 * though, since SASL encryption will typically be a no-op if TLS
1328 * is active
1330 * Returns the number of bytes read, which may be less than
1331 * the requested 'datalen' if the socket would block. Returns
1332 * -1 on error, and disconnects the client socket.
1334 ssize_t vnc_client_read_buf(VncState *vs, uint8_t *data, size_t datalen)
1336 ssize_t ret;
1337 Error *err = NULL;
1338 ret = qio_channel_read(
1339 vs->ioc, (char *)data, datalen, &err);
1340 VNC_DEBUG("Read wire %p %zd -> %ld\n", data, datalen, ret);
1341 return vnc_client_io_error(vs, ret, &err);
1346 * Called to read data from the client socket to the input buffer,
1347 * when not using any SASL SSF encryption layers. Will read as much
1348 * data as possible without blocking.
1350 * Returns the number of bytes read. Returns -1 on error, and
1351 * disconnects the client socket.
1353 static ssize_t vnc_client_read_plain(VncState *vs)
1355 ssize_t ret;
1356 VNC_DEBUG("Read plain %p size %zd offset %zd\n",
1357 vs->input.buffer, vs->input.capacity, vs->input.offset);
1358 buffer_reserve(&vs->input, 4096);
1359 ret = vnc_client_read_buf(vs, buffer_end(&vs->input), 4096);
1360 if (!ret)
1361 return 0;
1362 vs->input.offset += ret;
1363 return ret;
1366 static void vnc_jobs_bh(void *opaque)
1368 VncState *vs = opaque;
1370 vnc_jobs_consume_buffer(vs);
1374 * First function called whenever there is more data to be read from
1375 * the client socket. Will delegate actual work according to whether
1376 * SASL SSF layers are enabled (thus requiring decryption calls)
1377 * Returns 0 on success, -1 if client disconnected
1379 static int vnc_client_read(VncState *vs)
1381 ssize_t ret;
1383 #ifdef CONFIG_VNC_SASL
1384 if (vs->sasl.conn && vs->sasl.runSSF)
1385 ret = vnc_client_read_sasl(vs);
1386 else
1387 #endif /* CONFIG_VNC_SASL */
1388 ret = vnc_client_read_plain(vs);
1389 if (!ret) {
1390 if (vs->disconnecting) {
1391 vnc_disconnect_finish(vs);
1392 return -1;
1394 return 0;
1397 while (vs->read_handler && vs->input.offset >= vs->read_handler_expect) {
1398 size_t len = vs->read_handler_expect;
1399 int ret;
1401 ret = vs->read_handler(vs, vs->input.buffer, len);
1402 if (vs->disconnecting) {
1403 vnc_disconnect_finish(vs);
1404 return -1;
1407 if (!ret) {
1408 buffer_advance(&vs->input, len);
1409 } else {
1410 vs->read_handler_expect = ret;
1413 return 0;
1416 gboolean vnc_client_io(QIOChannel *ioc G_GNUC_UNUSED,
1417 GIOCondition condition, void *opaque)
1419 VncState *vs = opaque;
1420 if (condition & G_IO_IN) {
1421 if (vnc_client_read(vs) < 0) {
1422 return TRUE;
1425 if (condition & G_IO_OUT) {
1426 vnc_client_write(vs);
1428 return TRUE;
1432 void vnc_write(VncState *vs, const void *data, size_t len)
1434 buffer_reserve(&vs->output, len);
1436 if (vs->ioc != NULL && buffer_empty(&vs->output)) {
1437 if (vs->ioc_tag) {
1438 g_source_remove(vs->ioc_tag);
1440 vs->ioc_tag = qio_channel_add_watch(
1441 vs->ioc, G_IO_IN | G_IO_OUT, vnc_client_io, vs, NULL);
1444 buffer_append(&vs->output, data, len);
1447 void vnc_write_s32(VncState *vs, int32_t value)
1449 vnc_write_u32(vs, *(uint32_t *)&value);
1452 void vnc_write_u32(VncState *vs, uint32_t value)
1454 uint8_t buf[4];
1456 buf[0] = (value >> 24) & 0xFF;
1457 buf[1] = (value >> 16) & 0xFF;
1458 buf[2] = (value >> 8) & 0xFF;
1459 buf[3] = value & 0xFF;
1461 vnc_write(vs, buf, 4);
1464 void vnc_write_u16(VncState *vs, uint16_t value)
1466 uint8_t buf[2];
1468 buf[0] = (value >> 8) & 0xFF;
1469 buf[1] = value & 0xFF;
1471 vnc_write(vs, buf, 2);
1474 void vnc_write_u8(VncState *vs, uint8_t value)
1476 vnc_write(vs, (char *)&value, 1);
1479 void vnc_flush(VncState *vs)
1481 vnc_lock_output(vs);
1482 if (vs->ioc != NULL && vs->output.offset) {
1483 vnc_client_write_locked(vs);
1485 vnc_unlock_output(vs);
1488 static uint8_t read_u8(uint8_t *data, size_t offset)
1490 return data[offset];
1493 static uint16_t read_u16(uint8_t *data, size_t offset)
1495 return ((data[offset] & 0xFF) << 8) | (data[offset + 1] & 0xFF);
1498 static int32_t read_s32(uint8_t *data, size_t offset)
1500 return (int32_t)((data[offset] << 24) | (data[offset + 1] << 16) |
1501 (data[offset + 2] << 8) | data[offset + 3]);
1504 uint32_t read_u32(uint8_t *data, size_t offset)
1506 return ((data[offset] << 24) | (data[offset + 1] << 16) |
1507 (data[offset + 2] << 8) | data[offset + 3]);
1510 static void client_cut_text(VncState *vs, size_t len, uint8_t *text)
1514 static void check_pointer_type_change(Notifier *notifier, void *data)
1516 VncState *vs = container_of(notifier, VncState, mouse_mode_notifier);
1517 int absolute = qemu_input_is_absolute();
1519 if (vnc_has_feature(vs, VNC_FEATURE_POINTER_TYPE_CHANGE) && vs->absolute != absolute) {
1520 vnc_lock_output(vs);
1521 vnc_write_u8(vs, VNC_MSG_SERVER_FRAMEBUFFER_UPDATE);
1522 vnc_write_u8(vs, 0);
1523 vnc_write_u16(vs, 1);
1524 vnc_framebuffer_update(vs, absolute, 0,
1525 pixman_image_get_width(vs->vd->server),
1526 pixman_image_get_height(vs->vd->server),
1527 VNC_ENCODING_POINTER_TYPE_CHANGE);
1528 vnc_unlock_output(vs);
1529 vnc_flush(vs);
1531 vs->absolute = absolute;
1534 static void pointer_event(VncState *vs, int button_mask, int x, int y)
1536 static uint32_t bmap[INPUT_BUTTON__MAX] = {
1537 [INPUT_BUTTON_LEFT] = 0x01,
1538 [INPUT_BUTTON_MIDDLE] = 0x02,
1539 [INPUT_BUTTON_RIGHT] = 0x04,
1540 [INPUT_BUTTON_WHEEL_UP] = 0x08,
1541 [INPUT_BUTTON_WHEEL_DOWN] = 0x10,
1543 QemuConsole *con = vs->vd->dcl.con;
1544 int width = pixman_image_get_width(vs->vd->server);
1545 int height = pixman_image_get_height(vs->vd->server);
1547 if (vs->last_bmask != button_mask) {
1548 qemu_input_update_buttons(con, bmap, vs->last_bmask, button_mask);
1549 vs->last_bmask = button_mask;
1552 if (vs->absolute) {
1553 qemu_input_queue_abs(con, INPUT_AXIS_X, x, width);
1554 qemu_input_queue_abs(con, INPUT_AXIS_Y, y, height);
1555 } else if (vnc_has_feature(vs, VNC_FEATURE_POINTER_TYPE_CHANGE)) {
1556 qemu_input_queue_rel(con, INPUT_AXIS_X, x - 0x7FFF);
1557 qemu_input_queue_rel(con, INPUT_AXIS_Y, y - 0x7FFF);
1558 } else {
1559 if (vs->last_x != -1) {
1560 qemu_input_queue_rel(con, INPUT_AXIS_X, x - vs->last_x);
1561 qemu_input_queue_rel(con, INPUT_AXIS_Y, y - vs->last_y);
1563 vs->last_x = x;
1564 vs->last_y = y;
1566 qemu_input_event_sync();
1569 static void reset_keys(VncState *vs)
1571 int i;
1572 for(i = 0; i < 256; i++) {
1573 if (vs->modifiers_state[i]) {
1574 qemu_input_event_send_key_number(vs->vd->dcl.con, i, false);
1575 qemu_input_event_send_key_delay(vs->vd->key_delay_ms);
1576 vs->modifiers_state[i] = 0;
1581 static void press_key(VncState *vs, int keysym)
1583 int keycode = keysym2scancode(vs->vd->kbd_layout, keysym) & SCANCODE_KEYMASK;
1584 qemu_input_event_send_key_number(vs->vd->dcl.con, keycode, true);
1585 qemu_input_event_send_key_delay(vs->vd->key_delay_ms);
1586 qemu_input_event_send_key_number(vs->vd->dcl.con, keycode, false);
1587 qemu_input_event_send_key_delay(vs->vd->key_delay_ms);
1590 static void vnc_led_state_change(VncState *vs)
1592 if (!vnc_has_feature(vs, VNC_FEATURE_LED_STATE)) {
1593 return;
1596 vnc_lock_output(vs);
1597 vnc_write_u8(vs, VNC_MSG_SERVER_FRAMEBUFFER_UPDATE);
1598 vnc_write_u8(vs, 0);
1599 vnc_write_u16(vs, 1);
1600 vnc_framebuffer_update(vs, 0, 0, 1, 1, VNC_ENCODING_LED_STATE);
1601 vnc_write_u8(vs, vs->vd->ledstate);
1602 vnc_unlock_output(vs);
1603 vnc_flush(vs);
1606 static void kbd_leds(void *opaque, int ledstate)
1608 VncDisplay *vd = opaque;
1609 VncState *client;
1611 trace_vnc_key_guest_leds((ledstate & QEMU_CAPS_LOCK_LED),
1612 (ledstate & QEMU_NUM_LOCK_LED),
1613 (ledstate & QEMU_SCROLL_LOCK_LED));
1615 if (ledstate == vd->ledstate) {
1616 return;
1619 vd->ledstate = ledstate;
1621 QTAILQ_FOREACH(client, &vd->clients, next) {
1622 vnc_led_state_change(client);
1626 static void do_key_event(VncState *vs, int down, int keycode, int sym)
1628 /* QEMU console switch */
1629 switch(keycode) {
1630 case 0x2a: /* Left Shift */
1631 case 0x36: /* Right Shift */
1632 case 0x1d: /* Left CTRL */
1633 case 0x9d: /* Right CTRL */
1634 case 0x38: /* Left ALT */
1635 case 0xb8: /* Right ALT */
1636 if (down)
1637 vs->modifiers_state[keycode] = 1;
1638 else
1639 vs->modifiers_state[keycode] = 0;
1640 break;
1641 case 0x02 ... 0x0a: /* '1' to '9' keys */
1642 if (vs->vd->dcl.con == NULL &&
1643 down && vs->modifiers_state[0x1d] && vs->modifiers_state[0x38]) {
1644 /* Reset the modifiers sent to the current console */
1645 reset_keys(vs);
1646 console_select(keycode - 0x02);
1647 return;
1649 break;
1650 case 0x3a: /* CapsLock */
1651 case 0x45: /* NumLock */
1652 if (down)
1653 vs->modifiers_state[keycode] ^= 1;
1654 break;
1657 /* Turn off the lock state sync logic if the client support the led
1658 state extension.
1660 if (down && vs->vd->lock_key_sync &&
1661 !vnc_has_feature(vs, VNC_FEATURE_LED_STATE) &&
1662 keycode_is_keypad(vs->vd->kbd_layout, keycode)) {
1663 /* If the numlock state needs to change then simulate an additional
1664 keypress before sending this one. This will happen if the user
1665 toggles numlock away from the VNC window.
1667 if (keysym_is_numlock(vs->vd->kbd_layout, sym & 0xFFFF)) {
1668 if (!vs->modifiers_state[0x45]) {
1669 trace_vnc_key_sync_numlock(true);
1670 vs->modifiers_state[0x45] = 1;
1671 press_key(vs, 0xff7f);
1673 } else {
1674 if (vs->modifiers_state[0x45]) {
1675 trace_vnc_key_sync_numlock(false);
1676 vs->modifiers_state[0x45] = 0;
1677 press_key(vs, 0xff7f);
1682 if (down && vs->vd->lock_key_sync &&
1683 !vnc_has_feature(vs, VNC_FEATURE_LED_STATE) &&
1684 ((sym >= 'A' && sym <= 'Z') || (sym >= 'a' && sym <= 'z'))) {
1685 /* If the capslock state needs to change then simulate an additional
1686 keypress before sending this one. This will happen if the user
1687 toggles capslock away from the VNC window.
1689 int uppercase = !!(sym >= 'A' && sym <= 'Z');
1690 int shift = !!(vs->modifiers_state[0x2a] | vs->modifiers_state[0x36]);
1691 int capslock = !!(vs->modifiers_state[0x3a]);
1692 if (capslock) {
1693 if (uppercase == shift) {
1694 trace_vnc_key_sync_capslock(false);
1695 vs->modifiers_state[0x3a] = 0;
1696 press_key(vs, 0xffe5);
1698 } else {
1699 if (uppercase != shift) {
1700 trace_vnc_key_sync_capslock(true);
1701 vs->modifiers_state[0x3a] = 1;
1702 press_key(vs, 0xffe5);
1707 if (qemu_console_is_graphic(NULL)) {
1708 qemu_input_event_send_key_number(vs->vd->dcl.con, keycode, down);
1709 qemu_input_event_send_key_delay(vs->vd->key_delay_ms);
1710 } else {
1711 bool numlock = vs->modifiers_state[0x45];
1712 bool control = (vs->modifiers_state[0x1d] ||
1713 vs->modifiers_state[0x9d]);
1714 /* QEMU console emulation */
1715 if (down) {
1716 switch (keycode) {
1717 case 0x2a: /* Left Shift */
1718 case 0x36: /* Right Shift */
1719 case 0x1d: /* Left CTRL */
1720 case 0x9d: /* Right CTRL */
1721 case 0x38: /* Left ALT */
1722 case 0xb8: /* Right ALT */
1723 break;
1724 case 0xc8:
1725 kbd_put_keysym(QEMU_KEY_UP);
1726 break;
1727 case 0xd0:
1728 kbd_put_keysym(QEMU_KEY_DOWN);
1729 break;
1730 case 0xcb:
1731 kbd_put_keysym(QEMU_KEY_LEFT);
1732 break;
1733 case 0xcd:
1734 kbd_put_keysym(QEMU_KEY_RIGHT);
1735 break;
1736 case 0xd3:
1737 kbd_put_keysym(QEMU_KEY_DELETE);
1738 break;
1739 case 0xc7:
1740 kbd_put_keysym(QEMU_KEY_HOME);
1741 break;
1742 case 0xcf:
1743 kbd_put_keysym(QEMU_KEY_END);
1744 break;
1745 case 0xc9:
1746 kbd_put_keysym(QEMU_KEY_PAGEUP);
1747 break;
1748 case 0xd1:
1749 kbd_put_keysym(QEMU_KEY_PAGEDOWN);
1750 break;
1752 case 0x47:
1753 kbd_put_keysym(numlock ? '7' : QEMU_KEY_HOME);
1754 break;
1755 case 0x48:
1756 kbd_put_keysym(numlock ? '8' : QEMU_KEY_UP);
1757 break;
1758 case 0x49:
1759 kbd_put_keysym(numlock ? '9' : QEMU_KEY_PAGEUP);
1760 break;
1761 case 0x4b:
1762 kbd_put_keysym(numlock ? '4' : QEMU_KEY_LEFT);
1763 break;
1764 case 0x4c:
1765 kbd_put_keysym('5');
1766 break;
1767 case 0x4d:
1768 kbd_put_keysym(numlock ? '6' : QEMU_KEY_RIGHT);
1769 break;
1770 case 0x4f:
1771 kbd_put_keysym(numlock ? '1' : QEMU_KEY_END);
1772 break;
1773 case 0x50:
1774 kbd_put_keysym(numlock ? '2' : QEMU_KEY_DOWN);
1775 break;
1776 case 0x51:
1777 kbd_put_keysym(numlock ? '3' : QEMU_KEY_PAGEDOWN);
1778 break;
1779 case 0x52:
1780 kbd_put_keysym('0');
1781 break;
1782 case 0x53:
1783 kbd_put_keysym(numlock ? '.' : QEMU_KEY_DELETE);
1784 break;
1786 case 0xb5:
1787 kbd_put_keysym('/');
1788 break;
1789 case 0x37:
1790 kbd_put_keysym('*');
1791 break;
1792 case 0x4a:
1793 kbd_put_keysym('-');
1794 break;
1795 case 0x4e:
1796 kbd_put_keysym('+');
1797 break;
1798 case 0x9c:
1799 kbd_put_keysym('\n');
1800 break;
1802 default:
1803 if (control) {
1804 kbd_put_keysym(sym & 0x1f);
1805 } else {
1806 kbd_put_keysym(sym);
1808 break;
1814 static void vnc_release_modifiers(VncState *vs)
1816 static const int keycodes[] = {
1817 /* shift, control, alt keys, both left & right */
1818 0x2a, 0x36, 0x1d, 0x9d, 0x38, 0xb8,
1820 int i, keycode;
1822 if (!qemu_console_is_graphic(NULL)) {
1823 return;
1825 for (i = 0; i < ARRAY_SIZE(keycodes); i++) {
1826 keycode = keycodes[i];
1827 if (!vs->modifiers_state[keycode]) {
1828 continue;
1830 qemu_input_event_send_key_number(vs->vd->dcl.con, keycode, false);
1831 qemu_input_event_send_key_delay(vs->vd->key_delay_ms);
1835 static const char *code2name(int keycode)
1837 return QKeyCode_lookup[qemu_input_key_number_to_qcode(keycode)];
1840 static void key_event(VncState *vs, int down, uint32_t sym)
1842 int keycode;
1843 int lsym = sym;
1845 if (lsym >= 'A' && lsym <= 'Z' && qemu_console_is_graphic(NULL)) {
1846 lsym = lsym - 'A' + 'a';
1849 keycode = keysym2scancode(vs->vd->kbd_layout, lsym & 0xFFFF) & SCANCODE_KEYMASK;
1850 trace_vnc_key_event_map(down, sym, keycode, code2name(keycode));
1851 do_key_event(vs, down, keycode, sym);
1854 static void ext_key_event(VncState *vs, int down,
1855 uint32_t sym, uint16_t keycode)
1857 /* if the user specifies a keyboard layout, always use it */
1858 if (keyboard_layout) {
1859 key_event(vs, down, sym);
1860 } else {
1861 trace_vnc_key_event_ext(down, sym, keycode, code2name(keycode));
1862 do_key_event(vs, down, keycode, sym);
1866 static void framebuffer_update_request(VncState *vs, int incremental,
1867 int x, int y, int w, int h)
1869 vs->need_update = 1;
1871 if (incremental) {
1872 return;
1875 vs->force_update = 1;
1876 vnc_set_area_dirty(vs->dirty, vs->vd, x, y, w, h);
1879 static void send_ext_key_event_ack(VncState *vs)
1881 vnc_lock_output(vs);
1882 vnc_write_u8(vs, VNC_MSG_SERVER_FRAMEBUFFER_UPDATE);
1883 vnc_write_u8(vs, 0);
1884 vnc_write_u16(vs, 1);
1885 vnc_framebuffer_update(vs, 0, 0,
1886 pixman_image_get_width(vs->vd->server),
1887 pixman_image_get_height(vs->vd->server),
1888 VNC_ENCODING_EXT_KEY_EVENT);
1889 vnc_unlock_output(vs);
1890 vnc_flush(vs);
1893 static void send_ext_audio_ack(VncState *vs)
1895 vnc_lock_output(vs);
1896 vnc_write_u8(vs, VNC_MSG_SERVER_FRAMEBUFFER_UPDATE);
1897 vnc_write_u8(vs, 0);
1898 vnc_write_u16(vs, 1);
1899 vnc_framebuffer_update(vs, 0, 0,
1900 pixman_image_get_width(vs->vd->server),
1901 pixman_image_get_height(vs->vd->server),
1902 VNC_ENCODING_AUDIO);
1903 vnc_unlock_output(vs);
1904 vnc_flush(vs);
1907 static void set_encodings(VncState *vs, int32_t *encodings, size_t n_encodings)
1909 int i;
1910 unsigned int enc = 0;
1912 vs->features = 0;
1913 vs->vnc_encoding = 0;
1914 vs->tight.compression = 9;
1915 vs->tight.quality = -1; /* Lossless by default */
1916 vs->absolute = -1;
1919 * Start from the end because the encodings are sent in order of preference.
1920 * This way the preferred encoding (first encoding defined in the array)
1921 * will be set at the end of the loop.
1923 for (i = n_encodings - 1; i >= 0; i--) {
1924 enc = encodings[i];
1925 switch (enc) {
1926 case VNC_ENCODING_RAW:
1927 vs->vnc_encoding = enc;
1928 break;
1929 case VNC_ENCODING_COPYRECT:
1930 vs->features |= VNC_FEATURE_COPYRECT_MASK;
1931 break;
1932 case VNC_ENCODING_HEXTILE:
1933 vs->features |= VNC_FEATURE_HEXTILE_MASK;
1934 vs->vnc_encoding = enc;
1935 break;
1936 case VNC_ENCODING_TIGHT:
1937 vs->features |= VNC_FEATURE_TIGHT_MASK;
1938 vs->vnc_encoding = enc;
1939 break;
1940 #ifdef CONFIG_VNC_PNG
1941 case VNC_ENCODING_TIGHT_PNG:
1942 vs->features |= VNC_FEATURE_TIGHT_PNG_MASK;
1943 vs->vnc_encoding = enc;
1944 break;
1945 #endif
1946 case VNC_ENCODING_ZLIB:
1947 vs->features |= VNC_FEATURE_ZLIB_MASK;
1948 vs->vnc_encoding = enc;
1949 break;
1950 case VNC_ENCODING_ZRLE:
1951 vs->features |= VNC_FEATURE_ZRLE_MASK;
1952 vs->vnc_encoding = enc;
1953 break;
1954 case VNC_ENCODING_ZYWRLE:
1955 vs->features |= VNC_FEATURE_ZYWRLE_MASK;
1956 vs->vnc_encoding = enc;
1957 break;
1958 case VNC_ENCODING_DESKTOPRESIZE:
1959 vs->features |= VNC_FEATURE_RESIZE_MASK;
1960 break;
1961 case VNC_ENCODING_POINTER_TYPE_CHANGE:
1962 vs->features |= VNC_FEATURE_POINTER_TYPE_CHANGE_MASK;
1963 break;
1964 case VNC_ENCODING_RICH_CURSOR:
1965 vs->features |= VNC_FEATURE_RICH_CURSOR_MASK;
1966 if (vs->vd->cursor) {
1967 vnc_cursor_define(vs);
1969 break;
1970 case VNC_ENCODING_EXT_KEY_EVENT:
1971 send_ext_key_event_ack(vs);
1972 break;
1973 case VNC_ENCODING_AUDIO:
1974 send_ext_audio_ack(vs);
1975 break;
1976 case VNC_ENCODING_WMVi:
1977 vs->features |= VNC_FEATURE_WMVI_MASK;
1978 break;
1979 case VNC_ENCODING_LED_STATE:
1980 vs->features |= VNC_FEATURE_LED_STATE_MASK;
1981 break;
1982 case VNC_ENCODING_COMPRESSLEVEL0 ... VNC_ENCODING_COMPRESSLEVEL0 + 9:
1983 vs->tight.compression = (enc & 0x0F);
1984 break;
1985 case VNC_ENCODING_QUALITYLEVEL0 ... VNC_ENCODING_QUALITYLEVEL0 + 9:
1986 if (vs->vd->lossy) {
1987 vs->tight.quality = (enc & 0x0F);
1989 break;
1990 default:
1991 VNC_DEBUG("Unknown encoding: %d (0x%.8x): %d\n", i, enc, enc);
1992 break;
1995 vnc_desktop_resize(vs);
1996 check_pointer_type_change(&vs->mouse_mode_notifier, NULL);
1997 vnc_led_state_change(vs);
2000 static void set_pixel_conversion(VncState *vs)
2002 pixman_format_code_t fmt = qemu_pixman_get_format(&vs->client_pf);
2004 if (fmt == VNC_SERVER_FB_FORMAT) {
2005 vs->write_pixels = vnc_write_pixels_copy;
2006 vnc_hextile_set_pixel_conversion(vs, 0);
2007 } else {
2008 vs->write_pixels = vnc_write_pixels_generic;
2009 vnc_hextile_set_pixel_conversion(vs, 1);
2013 static void send_color_map(VncState *vs)
2015 int i;
2017 vnc_write_u8(vs, VNC_MSG_SERVER_SET_COLOUR_MAP_ENTRIES);
2018 vnc_write_u8(vs, 0); /* padding */
2019 vnc_write_u16(vs, 0); /* first color */
2020 vnc_write_u16(vs, 256); /* # of colors */
2022 for (i = 0; i < 256; i++) {
2023 PixelFormat *pf = &vs->client_pf;
2025 vnc_write_u16(vs, (((i >> pf->rshift) & pf->rmax) << (16 - pf->rbits)));
2026 vnc_write_u16(vs, (((i >> pf->gshift) & pf->gmax) << (16 - pf->gbits)));
2027 vnc_write_u16(vs, (((i >> pf->bshift) & pf->bmax) << (16 - pf->bbits)));
2031 static void set_pixel_format(VncState *vs, int bits_per_pixel,
2032 int big_endian_flag, int true_color_flag,
2033 int red_max, int green_max, int blue_max,
2034 int red_shift, int green_shift, int blue_shift)
2036 if (!true_color_flag) {
2037 /* Expose a reasonable default 256 color map */
2038 bits_per_pixel = 8;
2039 red_max = 7;
2040 green_max = 7;
2041 blue_max = 3;
2042 red_shift = 0;
2043 green_shift = 3;
2044 blue_shift = 6;
2047 switch (bits_per_pixel) {
2048 case 8:
2049 case 16:
2050 case 32:
2051 break;
2052 default:
2053 vnc_client_error(vs);
2054 return;
2057 vs->client_pf.rmax = red_max ? red_max : 0xFF;
2058 vs->client_pf.rbits = hweight_long(red_max);
2059 vs->client_pf.rshift = red_shift;
2060 vs->client_pf.rmask = red_max << red_shift;
2061 vs->client_pf.gmax = green_max ? green_max : 0xFF;
2062 vs->client_pf.gbits = hweight_long(green_max);
2063 vs->client_pf.gshift = green_shift;
2064 vs->client_pf.gmask = green_max << green_shift;
2065 vs->client_pf.bmax = blue_max ? blue_max : 0xFF;
2066 vs->client_pf.bbits = hweight_long(blue_max);
2067 vs->client_pf.bshift = blue_shift;
2068 vs->client_pf.bmask = blue_max << blue_shift;
2069 vs->client_pf.bits_per_pixel = bits_per_pixel;
2070 vs->client_pf.bytes_per_pixel = bits_per_pixel / 8;
2071 vs->client_pf.depth = bits_per_pixel == 32 ? 24 : bits_per_pixel;
2072 vs->client_be = big_endian_flag;
2074 if (!true_color_flag) {
2075 send_color_map(vs);
2078 set_pixel_conversion(vs);
2080 graphic_hw_invalidate(vs->vd->dcl.con);
2081 graphic_hw_update(vs->vd->dcl.con);
2084 static void pixel_format_message (VncState *vs) {
2085 char pad[3] = { 0, 0, 0 };
2087 vs->client_pf = qemu_default_pixelformat(32);
2089 vnc_write_u8(vs, vs->client_pf.bits_per_pixel); /* bits-per-pixel */
2090 vnc_write_u8(vs, vs->client_pf.depth); /* depth */
2092 #ifdef HOST_WORDS_BIGENDIAN
2093 vnc_write_u8(vs, 1); /* big-endian-flag */
2094 #else
2095 vnc_write_u8(vs, 0); /* big-endian-flag */
2096 #endif
2097 vnc_write_u8(vs, 1); /* true-color-flag */
2098 vnc_write_u16(vs, vs->client_pf.rmax); /* red-max */
2099 vnc_write_u16(vs, vs->client_pf.gmax); /* green-max */
2100 vnc_write_u16(vs, vs->client_pf.bmax); /* blue-max */
2101 vnc_write_u8(vs, vs->client_pf.rshift); /* red-shift */
2102 vnc_write_u8(vs, vs->client_pf.gshift); /* green-shift */
2103 vnc_write_u8(vs, vs->client_pf.bshift); /* blue-shift */
2104 vnc_write(vs, pad, 3); /* padding */
2106 vnc_hextile_set_pixel_conversion(vs, 0);
2107 vs->write_pixels = vnc_write_pixels_copy;
2110 static void vnc_colordepth(VncState *vs)
2112 if (vnc_has_feature(vs, VNC_FEATURE_WMVI)) {
2113 /* Sending a WMVi message to notify the client*/
2114 vnc_lock_output(vs);
2115 vnc_write_u8(vs, VNC_MSG_SERVER_FRAMEBUFFER_UPDATE);
2116 vnc_write_u8(vs, 0);
2117 vnc_write_u16(vs, 1); /* number of rects */
2118 vnc_framebuffer_update(vs, 0, 0,
2119 pixman_image_get_width(vs->vd->server),
2120 pixman_image_get_height(vs->vd->server),
2121 VNC_ENCODING_WMVi);
2122 pixel_format_message(vs);
2123 vnc_unlock_output(vs);
2124 vnc_flush(vs);
2125 } else {
2126 set_pixel_conversion(vs);
2130 static int protocol_client_msg(VncState *vs, uint8_t *data, size_t len)
2132 int i;
2133 uint16_t limit;
2134 VncDisplay *vd = vs->vd;
2136 if (data[0] > 3) {
2137 update_displaychangelistener(&vd->dcl, VNC_REFRESH_INTERVAL_BASE);
2140 switch (data[0]) {
2141 case VNC_MSG_CLIENT_SET_PIXEL_FORMAT:
2142 if (len == 1)
2143 return 20;
2145 set_pixel_format(vs, read_u8(data, 4),
2146 read_u8(data, 6), read_u8(data, 7),
2147 read_u16(data, 8), read_u16(data, 10),
2148 read_u16(data, 12), read_u8(data, 14),
2149 read_u8(data, 15), read_u8(data, 16));
2150 break;
2151 case VNC_MSG_CLIENT_SET_ENCODINGS:
2152 if (len == 1)
2153 return 4;
2155 if (len == 4) {
2156 limit = read_u16(data, 2);
2157 if (limit > 0)
2158 return 4 + (limit * 4);
2159 } else
2160 limit = read_u16(data, 2);
2162 for (i = 0; i < limit; i++) {
2163 int32_t val = read_s32(data, 4 + (i * 4));
2164 memcpy(data + 4 + (i * 4), &val, sizeof(val));
2167 set_encodings(vs, (int32_t *)(data + 4), limit);
2168 break;
2169 case VNC_MSG_CLIENT_FRAMEBUFFER_UPDATE_REQUEST:
2170 if (len == 1)
2171 return 10;
2173 framebuffer_update_request(vs,
2174 read_u8(data, 1), read_u16(data, 2), read_u16(data, 4),
2175 read_u16(data, 6), read_u16(data, 8));
2176 break;
2177 case VNC_MSG_CLIENT_KEY_EVENT:
2178 if (len == 1)
2179 return 8;
2181 key_event(vs, read_u8(data, 1), read_u32(data, 4));
2182 break;
2183 case VNC_MSG_CLIENT_POINTER_EVENT:
2184 if (len == 1)
2185 return 6;
2187 pointer_event(vs, read_u8(data, 1), read_u16(data, 2), read_u16(data, 4));
2188 break;
2189 case VNC_MSG_CLIENT_CUT_TEXT:
2190 if (len == 1) {
2191 return 8;
2193 if (len == 8) {
2194 uint32_t dlen = read_u32(data, 4);
2195 if (dlen > (1 << 20)) {
2196 error_report("vnc: client_cut_text msg payload has %u bytes"
2197 " which exceeds our limit of 1MB.", dlen);
2198 vnc_client_error(vs);
2199 break;
2201 if (dlen > 0) {
2202 return 8 + dlen;
2206 client_cut_text(vs, read_u32(data, 4), data + 8);
2207 break;
2208 case VNC_MSG_CLIENT_QEMU:
2209 if (len == 1)
2210 return 2;
2212 switch (read_u8(data, 1)) {
2213 case VNC_MSG_CLIENT_QEMU_EXT_KEY_EVENT:
2214 if (len == 2)
2215 return 12;
2217 ext_key_event(vs, read_u16(data, 2),
2218 read_u32(data, 4), read_u32(data, 8));
2219 break;
2220 case VNC_MSG_CLIENT_QEMU_AUDIO:
2221 if (len == 2)
2222 return 4;
2224 switch (read_u16 (data, 2)) {
2225 case VNC_MSG_CLIENT_QEMU_AUDIO_ENABLE:
2226 audio_add(vs);
2227 break;
2228 case VNC_MSG_CLIENT_QEMU_AUDIO_DISABLE:
2229 audio_del(vs);
2230 break;
2231 case VNC_MSG_CLIENT_QEMU_AUDIO_SET_FORMAT:
2232 if (len == 4)
2233 return 10;
2234 switch (read_u8(data, 4)) {
2235 case 0: vs->as.fmt = AUD_FMT_U8; break;
2236 case 1: vs->as.fmt = AUD_FMT_S8; break;
2237 case 2: vs->as.fmt = AUD_FMT_U16; break;
2238 case 3: vs->as.fmt = AUD_FMT_S16; break;
2239 case 4: vs->as.fmt = AUD_FMT_U32; break;
2240 case 5: vs->as.fmt = AUD_FMT_S32; break;
2241 default:
2242 VNC_DEBUG("Invalid audio format %d\n", read_u8(data, 4));
2243 vnc_client_error(vs);
2244 break;
2246 vs->as.nchannels = read_u8(data, 5);
2247 if (vs->as.nchannels != 1 && vs->as.nchannels != 2) {
2248 VNC_DEBUG("Invalid audio channel coount %d\n",
2249 read_u8(data, 5));
2250 vnc_client_error(vs);
2251 break;
2253 vs->as.freq = read_u32(data, 6);
2254 break;
2255 default:
2256 VNC_DEBUG("Invalid audio message %d\n", read_u8(data, 4));
2257 vnc_client_error(vs);
2258 break;
2260 break;
2262 default:
2263 VNC_DEBUG("Msg: %d\n", read_u16(data, 0));
2264 vnc_client_error(vs);
2265 break;
2267 break;
2268 default:
2269 VNC_DEBUG("Msg: %d\n", data[0]);
2270 vnc_client_error(vs);
2271 break;
2274 vnc_read_when(vs, protocol_client_msg, 1);
2275 return 0;
2278 static int protocol_client_init(VncState *vs, uint8_t *data, size_t len)
2280 char buf[1024];
2281 VncShareMode mode;
2282 int size;
2284 mode = data[0] ? VNC_SHARE_MODE_SHARED : VNC_SHARE_MODE_EXCLUSIVE;
2285 switch (vs->vd->share_policy) {
2286 case VNC_SHARE_POLICY_IGNORE:
2288 * Ignore the shared flag. Nothing to do here.
2290 * Doesn't conform to the rfb spec but is traditional qemu
2291 * behavior, thus left here as option for compatibility
2292 * reasons.
2294 break;
2295 case VNC_SHARE_POLICY_ALLOW_EXCLUSIVE:
2297 * Policy: Allow clients ask for exclusive access.
2299 * Implementation: When a client asks for exclusive access,
2300 * disconnect all others. Shared connects are allowed as long
2301 * as no exclusive connection exists.
2303 * This is how the rfb spec suggests to handle the shared flag.
2305 if (mode == VNC_SHARE_MODE_EXCLUSIVE) {
2306 VncState *client;
2307 QTAILQ_FOREACH(client, &vs->vd->clients, next) {
2308 if (vs == client) {
2309 continue;
2311 if (client->share_mode != VNC_SHARE_MODE_EXCLUSIVE &&
2312 client->share_mode != VNC_SHARE_MODE_SHARED) {
2313 continue;
2315 vnc_disconnect_start(client);
2318 if (mode == VNC_SHARE_MODE_SHARED) {
2319 if (vs->vd->num_exclusive > 0) {
2320 vnc_disconnect_start(vs);
2321 return 0;
2324 break;
2325 case VNC_SHARE_POLICY_FORCE_SHARED:
2327 * Policy: Shared connects only.
2328 * Implementation: Disallow clients asking for exclusive access.
2330 * Useful for shared desktop sessions where you don't want
2331 * someone forgetting to say -shared when running the vnc
2332 * client disconnect everybody else.
2334 if (mode == VNC_SHARE_MODE_EXCLUSIVE) {
2335 vnc_disconnect_start(vs);
2336 return 0;
2338 break;
2340 vnc_set_share_mode(vs, mode);
2342 if (vs->vd->num_shared > vs->vd->connections_limit) {
2343 vnc_disconnect_start(vs);
2344 return 0;
2347 vs->client_width = pixman_image_get_width(vs->vd->server);
2348 vs->client_height = pixman_image_get_height(vs->vd->server);
2349 vnc_write_u16(vs, vs->client_width);
2350 vnc_write_u16(vs, vs->client_height);
2352 pixel_format_message(vs);
2354 if (qemu_name) {
2355 size = snprintf(buf, sizeof(buf), "QEMU (%s)", qemu_name);
2356 if (size > sizeof(buf)) {
2357 size = sizeof(buf);
2359 } else {
2360 size = snprintf(buf, sizeof(buf), "QEMU");
2363 vnc_write_u32(vs, size);
2364 vnc_write(vs, buf, size);
2365 vnc_flush(vs);
2367 vnc_client_cache_auth(vs);
2368 vnc_qmp_event(vs, QAPI_EVENT_VNC_INITIALIZED);
2370 vnc_read_when(vs, protocol_client_msg, 1);
2372 return 0;
2375 void start_client_init(VncState *vs)
2377 vnc_read_when(vs, protocol_client_init, 1);
2380 static void make_challenge(VncState *vs)
2382 int i;
2384 srand(time(NULL)+getpid()+getpid()*987654+rand());
2386 for (i = 0 ; i < sizeof(vs->challenge) ; i++)
2387 vs->challenge[i] = (int) (256.0*rand()/(RAND_MAX+1.0));
2390 static int protocol_client_auth_vnc(VncState *vs, uint8_t *data, size_t len)
2392 unsigned char response[VNC_AUTH_CHALLENGE_SIZE];
2393 size_t i, pwlen;
2394 unsigned char key[8];
2395 time_t now = time(NULL);
2396 QCryptoCipher *cipher = NULL;
2397 Error *err = NULL;
2399 if (!vs->vd->password) {
2400 VNC_DEBUG("No password configured on server");
2401 goto reject;
2403 if (vs->vd->expires < now) {
2404 VNC_DEBUG("Password is expired");
2405 goto reject;
2408 memcpy(response, vs->challenge, VNC_AUTH_CHALLENGE_SIZE);
2410 /* Calculate the expected challenge response */
2411 pwlen = strlen(vs->vd->password);
2412 for (i=0; i<sizeof(key); i++)
2413 key[i] = i<pwlen ? vs->vd->password[i] : 0;
2415 cipher = qcrypto_cipher_new(
2416 QCRYPTO_CIPHER_ALG_DES_RFB,
2417 QCRYPTO_CIPHER_MODE_ECB,
2418 key, G_N_ELEMENTS(key),
2419 &err);
2420 if (!cipher) {
2421 VNC_DEBUG("Cannot initialize cipher %s",
2422 error_get_pretty(err));
2423 error_free(err);
2424 goto reject;
2427 if (qcrypto_cipher_encrypt(cipher,
2428 vs->challenge,
2429 response,
2430 VNC_AUTH_CHALLENGE_SIZE,
2431 &err) < 0) {
2432 VNC_DEBUG("Cannot encrypt challenge %s",
2433 error_get_pretty(err));
2434 error_free(err);
2435 goto reject;
2438 /* Compare expected vs actual challenge response */
2439 if (memcmp(response, data, VNC_AUTH_CHALLENGE_SIZE) != 0) {
2440 VNC_DEBUG("Client challenge response did not match\n");
2441 goto reject;
2442 } else {
2443 VNC_DEBUG("Accepting VNC challenge response\n");
2444 vnc_write_u32(vs, 0); /* Accept auth */
2445 vnc_flush(vs);
2447 start_client_init(vs);
2450 qcrypto_cipher_free(cipher);
2451 return 0;
2453 reject:
2454 vnc_write_u32(vs, 1); /* Reject auth */
2455 if (vs->minor >= 8) {
2456 static const char err[] = "Authentication failed";
2457 vnc_write_u32(vs, sizeof(err));
2458 vnc_write(vs, err, sizeof(err));
2460 vnc_flush(vs);
2461 vnc_client_error(vs);
2462 qcrypto_cipher_free(cipher);
2463 return 0;
2466 void start_auth_vnc(VncState *vs)
2468 make_challenge(vs);
2469 /* Send client a 'random' challenge */
2470 vnc_write(vs, vs->challenge, sizeof(vs->challenge));
2471 vnc_flush(vs);
2473 vnc_read_when(vs, protocol_client_auth_vnc, sizeof(vs->challenge));
2477 static int protocol_client_auth(VncState *vs, uint8_t *data, size_t len)
2479 /* We only advertise 1 auth scheme at a time, so client
2480 * must pick the one we sent. Verify this */
2481 if (data[0] != vs->auth) { /* Reject auth */
2482 VNC_DEBUG("Reject auth %d because it didn't match advertized\n", (int)data[0]);
2483 vnc_write_u32(vs, 1);
2484 if (vs->minor >= 8) {
2485 static const char err[] = "Authentication failed";
2486 vnc_write_u32(vs, sizeof(err));
2487 vnc_write(vs, err, sizeof(err));
2489 vnc_client_error(vs);
2490 } else { /* Accept requested auth */
2491 VNC_DEBUG("Client requested auth %d\n", (int)data[0]);
2492 switch (vs->auth) {
2493 case VNC_AUTH_NONE:
2494 VNC_DEBUG("Accept auth none\n");
2495 if (vs->minor >= 8) {
2496 vnc_write_u32(vs, 0); /* Accept auth completion */
2497 vnc_flush(vs);
2499 start_client_init(vs);
2500 break;
2502 case VNC_AUTH_VNC:
2503 VNC_DEBUG("Start VNC auth\n");
2504 start_auth_vnc(vs);
2505 break;
2507 case VNC_AUTH_VENCRYPT:
2508 VNC_DEBUG("Accept VeNCrypt auth\n");
2509 start_auth_vencrypt(vs);
2510 break;
2512 #ifdef CONFIG_VNC_SASL
2513 case VNC_AUTH_SASL:
2514 VNC_DEBUG("Accept SASL auth\n");
2515 start_auth_sasl(vs);
2516 break;
2517 #endif /* CONFIG_VNC_SASL */
2519 default: /* Should not be possible, but just in case */
2520 VNC_DEBUG("Reject auth %d server code bug\n", vs->auth);
2521 vnc_write_u8(vs, 1);
2522 if (vs->minor >= 8) {
2523 static const char err[] = "Authentication failed";
2524 vnc_write_u32(vs, sizeof(err));
2525 vnc_write(vs, err, sizeof(err));
2527 vnc_client_error(vs);
2530 return 0;
2533 static int protocol_version(VncState *vs, uint8_t *version, size_t len)
2535 char local[13];
2537 memcpy(local, version, 12);
2538 local[12] = 0;
2540 if (sscanf(local, "RFB %03d.%03d\n", &vs->major, &vs->minor) != 2) {
2541 VNC_DEBUG("Malformed protocol version %s\n", local);
2542 vnc_client_error(vs);
2543 return 0;
2545 VNC_DEBUG("Client request protocol version %d.%d\n", vs->major, vs->minor);
2546 if (vs->major != 3 ||
2547 (vs->minor != 3 &&
2548 vs->minor != 4 &&
2549 vs->minor != 5 &&
2550 vs->minor != 7 &&
2551 vs->minor != 8)) {
2552 VNC_DEBUG("Unsupported client version\n");
2553 vnc_write_u32(vs, VNC_AUTH_INVALID);
2554 vnc_flush(vs);
2555 vnc_client_error(vs);
2556 return 0;
2558 /* Some broken clients report v3.4 or v3.5, which spec requires to be treated
2559 * as equivalent to v3.3 by servers
2561 if (vs->minor == 4 || vs->minor == 5)
2562 vs->minor = 3;
2564 if (vs->minor == 3) {
2565 if (vs->auth == VNC_AUTH_NONE) {
2566 VNC_DEBUG("Tell client auth none\n");
2567 vnc_write_u32(vs, vs->auth);
2568 vnc_flush(vs);
2569 start_client_init(vs);
2570 } else if (vs->auth == VNC_AUTH_VNC) {
2571 VNC_DEBUG("Tell client VNC auth\n");
2572 vnc_write_u32(vs, vs->auth);
2573 vnc_flush(vs);
2574 start_auth_vnc(vs);
2575 } else {
2576 VNC_DEBUG("Unsupported auth %d for protocol 3.3\n", vs->auth);
2577 vnc_write_u32(vs, VNC_AUTH_INVALID);
2578 vnc_flush(vs);
2579 vnc_client_error(vs);
2581 } else {
2582 VNC_DEBUG("Telling client we support auth %d\n", vs->auth);
2583 vnc_write_u8(vs, 1); /* num auth */
2584 vnc_write_u8(vs, vs->auth);
2585 vnc_read_when(vs, protocol_client_auth, 1);
2586 vnc_flush(vs);
2589 return 0;
2592 static VncRectStat *vnc_stat_rect(VncDisplay *vd, int x, int y)
2594 struct VncSurface *vs = &vd->guest;
2596 return &vs->stats[y / VNC_STAT_RECT][x / VNC_STAT_RECT];
2599 void vnc_sent_lossy_rect(VncState *vs, int x, int y, int w, int h)
2601 int i, j;
2603 w = (x + w) / VNC_STAT_RECT;
2604 h = (y + h) / VNC_STAT_RECT;
2605 x /= VNC_STAT_RECT;
2606 y /= VNC_STAT_RECT;
2608 for (j = y; j <= h; j++) {
2609 for (i = x; i <= w; i++) {
2610 vs->lossy_rect[j][i] = 1;
2615 static int vnc_refresh_lossy_rect(VncDisplay *vd, int x, int y)
2617 VncState *vs;
2618 int sty = y / VNC_STAT_RECT;
2619 int stx = x / VNC_STAT_RECT;
2620 int has_dirty = 0;
2622 y = y / VNC_STAT_RECT * VNC_STAT_RECT;
2623 x = x / VNC_STAT_RECT * VNC_STAT_RECT;
2625 QTAILQ_FOREACH(vs, &vd->clients, next) {
2626 int j;
2628 /* kernel send buffers are full -> refresh later */
2629 if (vs->output.offset) {
2630 continue;
2633 if (!vs->lossy_rect[sty][stx]) {
2634 continue;
2637 vs->lossy_rect[sty][stx] = 0;
2638 for (j = 0; j < VNC_STAT_RECT; ++j) {
2639 bitmap_set(vs->dirty[y + j],
2640 x / VNC_DIRTY_PIXELS_PER_BIT,
2641 VNC_STAT_RECT / VNC_DIRTY_PIXELS_PER_BIT);
2643 has_dirty++;
2646 return has_dirty;
2649 static int vnc_update_stats(VncDisplay *vd, struct timeval * tv)
2651 int width = MIN(pixman_image_get_width(vd->guest.fb),
2652 pixman_image_get_width(vd->server));
2653 int height = MIN(pixman_image_get_height(vd->guest.fb),
2654 pixman_image_get_height(vd->server));
2655 int x, y;
2656 struct timeval res;
2657 int has_dirty = 0;
2659 for (y = 0; y < height; y += VNC_STAT_RECT) {
2660 for (x = 0; x < width; x += VNC_STAT_RECT) {
2661 VncRectStat *rect = vnc_stat_rect(vd, x, y);
2663 rect->updated = false;
2667 qemu_timersub(tv, &VNC_REFRESH_STATS, &res);
2669 if (timercmp(&vd->guest.last_freq_check, &res, >)) {
2670 return has_dirty;
2672 vd->guest.last_freq_check = *tv;
2674 for (y = 0; y < height; y += VNC_STAT_RECT) {
2675 for (x = 0; x < width; x += VNC_STAT_RECT) {
2676 VncRectStat *rect= vnc_stat_rect(vd, x, y);
2677 int count = ARRAY_SIZE(rect->times);
2678 struct timeval min, max;
2680 if (!timerisset(&rect->times[count - 1])) {
2681 continue ;
2684 max = rect->times[(rect->idx + count - 1) % count];
2685 qemu_timersub(tv, &max, &res);
2687 if (timercmp(&res, &VNC_REFRESH_LOSSY, >)) {
2688 rect->freq = 0;
2689 has_dirty += vnc_refresh_lossy_rect(vd, x, y);
2690 memset(rect->times, 0, sizeof (rect->times));
2691 continue ;
2694 min = rect->times[rect->idx];
2695 max = rect->times[(rect->idx + count - 1) % count];
2696 qemu_timersub(&max, &min, &res);
2698 rect->freq = res.tv_sec + res.tv_usec / 1000000.;
2699 rect->freq /= count;
2700 rect->freq = 1. / rect->freq;
2703 return has_dirty;
2706 double vnc_update_freq(VncState *vs, int x, int y, int w, int h)
2708 int i, j;
2709 double total = 0;
2710 int num = 0;
2712 x = (x / VNC_STAT_RECT) * VNC_STAT_RECT;
2713 y = (y / VNC_STAT_RECT) * VNC_STAT_RECT;
2715 for (j = y; j <= y + h; j += VNC_STAT_RECT) {
2716 for (i = x; i <= x + w; i += VNC_STAT_RECT) {
2717 total += vnc_stat_rect(vs->vd, i, j)->freq;
2718 num++;
2722 if (num) {
2723 return total / num;
2724 } else {
2725 return 0;
2729 static void vnc_rect_updated(VncDisplay *vd, int x, int y, struct timeval * tv)
2731 VncRectStat *rect;
2733 rect = vnc_stat_rect(vd, x, y);
2734 if (rect->updated) {
2735 return ;
2737 rect->times[rect->idx] = *tv;
2738 rect->idx = (rect->idx + 1) % ARRAY_SIZE(rect->times);
2739 rect->updated = true;
2742 static int vnc_refresh_server_surface(VncDisplay *vd)
2744 int width = MIN(pixman_image_get_width(vd->guest.fb),
2745 pixman_image_get_width(vd->server));
2746 int height = MIN(pixman_image_get_height(vd->guest.fb),
2747 pixman_image_get_height(vd->server));
2748 int cmp_bytes, server_stride, line_bytes, guest_ll, guest_stride, y = 0;
2749 uint8_t *guest_row0 = NULL, *server_row0;
2750 VncState *vs;
2751 int has_dirty = 0;
2752 pixman_image_t *tmpbuf = NULL;
2754 struct timeval tv = { 0, 0 };
2756 if (!vd->non_adaptive) {
2757 gettimeofday(&tv, NULL);
2758 has_dirty = vnc_update_stats(vd, &tv);
2762 * Walk through the guest dirty map.
2763 * Check and copy modified bits from guest to server surface.
2764 * Update server dirty map.
2766 server_row0 = (uint8_t *)pixman_image_get_data(vd->server);
2767 server_stride = guest_stride = guest_ll =
2768 pixman_image_get_stride(vd->server);
2769 cmp_bytes = MIN(VNC_DIRTY_PIXELS_PER_BIT * VNC_SERVER_FB_BYTES,
2770 server_stride);
2771 if (vd->guest.format != VNC_SERVER_FB_FORMAT) {
2772 int width = pixman_image_get_width(vd->server);
2773 tmpbuf = qemu_pixman_linebuf_create(VNC_SERVER_FB_FORMAT, width);
2774 } else {
2775 int guest_bpp =
2776 PIXMAN_FORMAT_BPP(pixman_image_get_format(vd->guest.fb));
2777 guest_row0 = (uint8_t *)pixman_image_get_data(vd->guest.fb);
2778 guest_stride = pixman_image_get_stride(vd->guest.fb);
2779 guest_ll = pixman_image_get_width(vd->guest.fb) * ((guest_bpp + 7) / 8);
2781 line_bytes = MIN(server_stride, guest_ll);
2783 for (;;) {
2784 int x;
2785 uint8_t *guest_ptr, *server_ptr;
2786 unsigned long offset = find_next_bit((unsigned long *) &vd->guest.dirty,
2787 height * VNC_DIRTY_BPL(&vd->guest),
2788 y * VNC_DIRTY_BPL(&vd->guest));
2789 if (offset == height * VNC_DIRTY_BPL(&vd->guest)) {
2790 /* no more dirty bits */
2791 break;
2793 y = offset / VNC_DIRTY_BPL(&vd->guest);
2794 x = offset % VNC_DIRTY_BPL(&vd->guest);
2796 server_ptr = server_row0 + y * server_stride + x * cmp_bytes;
2798 if (vd->guest.format != VNC_SERVER_FB_FORMAT) {
2799 qemu_pixman_linebuf_fill(tmpbuf, vd->guest.fb, width, 0, y);
2800 guest_ptr = (uint8_t *)pixman_image_get_data(tmpbuf);
2801 } else {
2802 guest_ptr = guest_row0 + y * guest_stride;
2804 guest_ptr += x * cmp_bytes;
2806 for (; x < DIV_ROUND_UP(width, VNC_DIRTY_PIXELS_PER_BIT);
2807 x++, guest_ptr += cmp_bytes, server_ptr += cmp_bytes) {
2808 int _cmp_bytes = cmp_bytes;
2809 if (!test_and_clear_bit(x, vd->guest.dirty[y])) {
2810 continue;
2812 if ((x + 1) * cmp_bytes > line_bytes) {
2813 _cmp_bytes = line_bytes - x * cmp_bytes;
2815 assert(_cmp_bytes >= 0);
2816 if (memcmp(server_ptr, guest_ptr, _cmp_bytes) == 0) {
2817 continue;
2819 memcpy(server_ptr, guest_ptr, _cmp_bytes);
2820 if (!vd->non_adaptive) {
2821 vnc_rect_updated(vd, x * VNC_DIRTY_PIXELS_PER_BIT,
2822 y, &tv);
2824 QTAILQ_FOREACH(vs, &vd->clients, next) {
2825 set_bit(x, vs->dirty[y]);
2827 has_dirty++;
2830 y++;
2832 qemu_pixman_image_unref(tmpbuf);
2833 return has_dirty;
2836 static void vnc_refresh(DisplayChangeListener *dcl)
2838 VncDisplay *vd = container_of(dcl, VncDisplay, dcl);
2839 VncState *vs, *vn;
2840 int has_dirty, rects = 0;
2842 if (QTAILQ_EMPTY(&vd->clients)) {
2843 update_displaychangelistener(&vd->dcl, VNC_REFRESH_INTERVAL_MAX);
2844 return;
2847 graphic_hw_update(vd->dcl.con);
2849 if (vnc_trylock_display(vd)) {
2850 update_displaychangelistener(&vd->dcl, VNC_REFRESH_INTERVAL_BASE);
2851 return;
2854 has_dirty = vnc_refresh_server_surface(vd);
2855 vnc_unlock_display(vd);
2857 QTAILQ_FOREACH_SAFE(vs, &vd->clients, next, vn) {
2858 rects += vnc_update_client(vs, has_dirty, false);
2859 /* vs might be free()ed here */
2862 if (has_dirty && rects) {
2863 vd->dcl.update_interval /= 2;
2864 if (vd->dcl.update_interval < VNC_REFRESH_INTERVAL_BASE) {
2865 vd->dcl.update_interval = VNC_REFRESH_INTERVAL_BASE;
2867 } else {
2868 vd->dcl.update_interval += VNC_REFRESH_INTERVAL_INC;
2869 if (vd->dcl.update_interval > VNC_REFRESH_INTERVAL_MAX) {
2870 vd->dcl.update_interval = VNC_REFRESH_INTERVAL_MAX;
2875 static void vnc_connect(VncDisplay *vd, QIOChannelSocket *sioc,
2876 bool skipauth, bool websocket)
2878 VncState *vs = g_new0(VncState, 1);
2879 bool first_client = QTAILQ_EMPTY(&vd->clients);
2880 int i;
2882 vs->sioc = sioc;
2883 object_ref(OBJECT(vs->sioc));
2884 vs->ioc = QIO_CHANNEL(sioc);
2885 object_ref(OBJECT(vs->ioc));
2886 vs->vd = vd;
2888 buffer_init(&vs->input, "vnc-input/%p", sioc);
2889 buffer_init(&vs->output, "vnc-output/%p", sioc);
2890 buffer_init(&vs->jobs_buffer, "vnc-jobs_buffer/%p", sioc);
2892 buffer_init(&vs->tight.tight, "vnc-tight/%p", sioc);
2893 buffer_init(&vs->tight.zlib, "vnc-tight-zlib/%p", sioc);
2894 buffer_init(&vs->tight.gradient, "vnc-tight-gradient/%p", sioc);
2895 #ifdef CONFIG_VNC_JPEG
2896 buffer_init(&vs->tight.jpeg, "vnc-tight-jpeg/%p", sioc);
2897 #endif
2898 #ifdef CONFIG_VNC_PNG
2899 buffer_init(&vs->tight.png, "vnc-tight-png/%p", sioc);
2900 #endif
2901 buffer_init(&vs->zlib.zlib, "vnc-zlib/%p", sioc);
2902 buffer_init(&vs->zrle.zrle, "vnc-zrle/%p", sioc);
2903 buffer_init(&vs->zrle.fb, "vnc-zrle-fb/%p", sioc);
2904 buffer_init(&vs->zrle.zlib, "vnc-zrle-zlib/%p", sioc);
2906 if (skipauth) {
2907 vs->auth = VNC_AUTH_NONE;
2908 vs->subauth = VNC_AUTH_INVALID;
2909 } else {
2910 if (websocket) {
2911 vs->auth = vd->ws_auth;
2912 vs->subauth = VNC_AUTH_INVALID;
2913 } else {
2914 vs->auth = vd->auth;
2915 vs->subauth = vd->subauth;
2918 VNC_DEBUG("Client sioc=%p ws=%d auth=%d subauth=%d\n",
2919 sioc, websocket, vs->auth, vs->subauth);
2921 vs->lossy_rect = g_malloc0(VNC_STAT_ROWS * sizeof (*vs->lossy_rect));
2922 for (i = 0; i < VNC_STAT_ROWS; ++i) {
2923 vs->lossy_rect[i] = g_new0(uint8_t, VNC_STAT_COLS);
2926 VNC_DEBUG("New client on socket %p\n", vs->sioc);
2927 update_displaychangelistener(&vd->dcl, VNC_REFRESH_INTERVAL_BASE);
2928 qio_channel_set_blocking(vs->ioc, false, NULL);
2929 if (websocket) {
2930 vs->websocket = 1;
2931 if (vd->tlscreds) {
2932 vs->ioc_tag = qio_channel_add_watch(
2933 vs->ioc, G_IO_IN, vncws_tls_handshake_io, vs, NULL);
2934 } else {
2935 vs->ioc_tag = qio_channel_add_watch(
2936 vs->ioc, G_IO_IN, vncws_handshake_io, vs, NULL);
2938 } else {
2939 vs->ioc_tag = qio_channel_add_watch(
2940 vs->ioc, G_IO_IN, vnc_client_io, vs, NULL);
2943 vnc_client_cache_addr(vs);
2944 vnc_qmp_event(vs, QAPI_EVENT_VNC_CONNECTED);
2945 vnc_set_share_mode(vs, VNC_SHARE_MODE_CONNECTING);
2947 vs->last_x = -1;
2948 vs->last_y = -1;
2950 vs->as.freq = 44100;
2951 vs->as.nchannels = 2;
2952 vs->as.fmt = AUD_FMT_S16;
2953 vs->as.endianness = 0;
2955 qemu_mutex_init(&vs->output_mutex);
2956 vs->bh = qemu_bh_new(vnc_jobs_bh, vs);
2958 QTAILQ_INSERT_TAIL(&vd->clients, vs, next);
2959 if (first_client) {
2960 vnc_update_server_surface(vd);
2963 graphic_hw_update(vd->dcl.con);
2965 if (!vs->websocket) {
2966 vnc_start_protocol(vs);
2969 if (vd->num_connecting > vd->connections_limit) {
2970 QTAILQ_FOREACH(vs, &vd->clients, next) {
2971 if (vs->share_mode == VNC_SHARE_MODE_CONNECTING) {
2972 vnc_disconnect_start(vs);
2973 return;
2979 void vnc_start_protocol(VncState *vs)
2981 vnc_write(vs, "RFB 003.008\n", 12);
2982 vnc_flush(vs);
2983 vnc_read_when(vs, protocol_version, 12);
2985 vs->mouse_mode_notifier.notify = check_pointer_type_change;
2986 qemu_add_mouse_mode_change_notifier(&vs->mouse_mode_notifier);
2989 static gboolean vnc_listen_io(QIOChannel *ioc,
2990 GIOCondition condition,
2991 void *opaque)
2993 VncDisplay *vd = opaque;
2994 QIOChannelSocket *sioc = NULL;
2995 Error *err = NULL;
2996 bool isWebsock = false;
2997 size_t i;
2999 for (i = 0; i < vd->nlwebsock; i++) {
3000 if (ioc == QIO_CHANNEL(vd->lwebsock[i])) {
3001 isWebsock = true;
3002 break;
3006 sioc = qio_channel_socket_accept(QIO_CHANNEL_SOCKET(ioc), &err);
3007 if (sioc != NULL) {
3008 qio_channel_set_name(QIO_CHANNEL(sioc),
3009 isWebsock ? "vnc-ws-server" : "vnc-server");
3010 qio_channel_set_delay(QIO_CHANNEL(sioc), false);
3011 vnc_connect(vd, sioc, false, isWebsock);
3012 object_unref(OBJECT(sioc));
3013 } else {
3014 /* client probably closed connection before we got there */
3015 error_free(err);
3018 return TRUE;
3021 static const DisplayChangeListenerOps dcl_ops = {
3022 .dpy_name = "vnc",
3023 .dpy_refresh = vnc_refresh,
3024 .dpy_gfx_update = vnc_dpy_update,
3025 .dpy_gfx_switch = vnc_dpy_switch,
3026 .dpy_gfx_check_format = qemu_pixman_check_format,
3027 .dpy_mouse_set = vnc_mouse_set,
3028 .dpy_cursor_define = vnc_dpy_cursor_define,
3031 void vnc_display_init(const char *id)
3033 VncDisplay *vd;
3035 if (vnc_display_find(id) != NULL) {
3036 return;
3038 vd = g_malloc0(sizeof(*vd));
3040 vd->id = strdup(id);
3041 QTAILQ_INSERT_TAIL(&vnc_displays, vd, next);
3043 QTAILQ_INIT(&vd->clients);
3044 vd->expires = TIME_MAX;
3046 if (keyboard_layout) {
3047 trace_vnc_key_map_init(keyboard_layout);
3048 vd->kbd_layout = init_keyboard_layout(name2keysym, keyboard_layout);
3049 } else {
3050 vd->kbd_layout = init_keyboard_layout(name2keysym, "en-us");
3053 if (!vd->kbd_layout) {
3054 exit(1);
3057 vd->share_policy = VNC_SHARE_POLICY_ALLOW_EXCLUSIVE;
3058 vd->connections_limit = 32;
3060 qemu_mutex_init(&vd->mutex);
3061 vnc_start_worker_thread();
3063 vd->dcl.ops = &dcl_ops;
3064 register_displaychangelistener(&vd->dcl);
3068 static void vnc_display_close(VncDisplay *vd)
3070 size_t i;
3071 if (!vd) {
3072 return;
3074 vd->is_unix = false;
3075 for (i = 0; i < vd->nlsock; i++) {
3076 if (vd->lsock_tag[i]) {
3077 g_source_remove(vd->lsock_tag[i]);
3079 object_unref(OBJECT(vd->lsock[i]));
3081 g_free(vd->lsock);
3082 g_free(vd->lsock_tag);
3083 vd->lsock = NULL;
3084 vd->lsock_tag = NULL;
3085 vd->nlsock = 0;
3087 for (i = 0; i < vd->nlwebsock; i++) {
3088 if (vd->lwebsock_tag[i]) {
3089 g_source_remove(vd->lwebsock_tag[i]);
3091 object_unref(OBJECT(vd->lwebsock[i]));
3093 g_free(vd->lwebsock);
3094 g_free(vd->lwebsock_tag);
3095 vd->lwebsock = NULL;
3096 vd->lwebsock_tag = NULL;
3097 vd->nlwebsock = 0;
3099 vd->auth = VNC_AUTH_INVALID;
3100 vd->subauth = VNC_AUTH_INVALID;
3101 if (vd->tlscreds) {
3102 object_unparent(OBJECT(vd->tlscreds));
3103 vd->tlscreds = NULL;
3105 g_free(vd->tlsaclname);
3106 vd->tlsaclname = NULL;
3107 if (vd->lock_key_sync) {
3108 qemu_remove_led_event_handler(vd->led);
3109 vd->led = NULL;
3113 int vnc_display_password(const char *id, const char *password)
3115 VncDisplay *vd = vnc_display_find(id);
3117 if (!vd) {
3118 return -EINVAL;
3120 if (vd->auth == VNC_AUTH_NONE) {
3121 error_printf_unless_qmp("If you want use passwords please enable "
3122 "password auth using '-vnc ${dpy},password'.\n");
3123 return -EINVAL;
3126 g_free(vd->password);
3127 vd->password = g_strdup(password);
3129 return 0;
3132 int vnc_display_pw_expire(const char *id, time_t expires)
3134 VncDisplay *vd = vnc_display_find(id);
3136 if (!vd) {
3137 return -EINVAL;
3140 vd->expires = expires;
3141 return 0;
3144 static void vnc_display_print_local_addr(VncDisplay *vd)
3146 SocketAddress *addr;
3147 Error *err = NULL;
3149 if (!vd->nlsock) {
3150 return;
3153 addr = qio_channel_socket_get_local_address(vd->lsock[0], &err);
3154 if (!addr) {
3155 return;
3158 if (addr->type != SOCKET_ADDRESS_KIND_INET) {
3159 qapi_free_SocketAddress(addr);
3160 return;
3162 error_printf_unless_qmp("VNC server running on %s:%s\n",
3163 addr->u.inet.data->host,
3164 addr->u.inet.data->port);
3165 qapi_free_SocketAddress(addr);
3168 static QemuOptsList qemu_vnc_opts = {
3169 .name = "vnc",
3170 .head = QTAILQ_HEAD_INITIALIZER(qemu_vnc_opts.head),
3171 .implied_opt_name = "vnc",
3172 .desc = {
3174 .name = "vnc",
3175 .type = QEMU_OPT_STRING,
3177 .name = "websocket",
3178 .type = QEMU_OPT_STRING,
3180 .name = "tls-creds",
3181 .type = QEMU_OPT_STRING,
3183 /* Deprecated in favour of tls-creds */
3184 .name = "x509",
3185 .type = QEMU_OPT_STRING,
3187 .name = "share",
3188 .type = QEMU_OPT_STRING,
3190 .name = "display",
3191 .type = QEMU_OPT_STRING,
3193 .name = "head",
3194 .type = QEMU_OPT_NUMBER,
3196 .name = "connections",
3197 .type = QEMU_OPT_NUMBER,
3199 .name = "to",
3200 .type = QEMU_OPT_NUMBER,
3202 .name = "ipv4",
3203 .type = QEMU_OPT_BOOL,
3205 .name = "ipv6",
3206 .type = QEMU_OPT_BOOL,
3208 .name = "password",
3209 .type = QEMU_OPT_BOOL,
3211 .name = "reverse",
3212 .type = QEMU_OPT_BOOL,
3214 .name = "lock-key-sync",
3215 .type = QEMU_OPT_BOOL,
3217 .name = "key-delay-ms",
3218 .type = QEMU_OPT_NUMBER,
3220 .name = "sasl",
3221 .type = QEMU_OPT_BOOL,
3223 /* Deprecated in favour of tls-creds */
3224 .name = "tls",
3225 .type = QEMU_OPT_BOOL,
3227 /* Deprecated in favour of tls-creds */
3228 .name = "x509verify",
3229 .type = QEMU_OPT_STRING,
3231 .name = "acl",
3232 .type = QEMU_OPT_BOOL,
3234 .name = "lossy",
3235 .type = QEMU_OPT_BOOL,
3237 .name = "non-adaptive",
3238 .type = QEMU_OPT_BOOL,
3240 { /* end of list */ }
3245 static int
3246 vnc_display_setup_auth(int *auth,
3247 int *subauth,
3248 QCryptoTLSCreds *tlscreds,
3249 bool password,
3250 bool sasl,
3251 bool websocket,
3252 Error **errp)
3255 * We have a choice of 3 authentication options
3257 * 1. none
3258 * 2. vnc
3259 * 3. sasl
3261 * The channel can be run in 2 modes
3263 * 1. clear
3264 * 2. tls
3266 * And TLS can use 2 types of credentials
3268 * 1. anon
3269 * 2. x509
3271 * We thus have 9 possible logical combinations
3273 * 1. clear + none
3274 * 2. clear + vnc
3275 * 3. clear + sasl
3276 * 4. tls + anon + none
3277 * 5. tls + anon + vnc
3278 * 6. tls + anon + sasl
3279 * 7. tls + x509 + none
3280 * 8. tls + x509 + vnc
3281 * 9. tls + x509 + sasl
3283 * These need to be mapped into the VNC auth schemes
3284 * in an appropriate manner. In regular VNC, all the
3285 * TLS options get mapped into VNC_AUTH_VENCRYPT
3286 * sub-auth types.
3288 * In websockets, the https:// protocol already provides
3289 * TLS support, so there is no need to make use of the
3290 * VeNCrypt extension. Furthermore, websockets browser
3291 * clients could not use VeNCrypt even if they wanted to,
3292 * as they cannot control when the TLS handshake takes
3293 * place. Thus there is no option but to rely on https://,
3294 * meaning combinations 4->6 and 7->9 will be mapped to
3295 * VNC auth schemes in the same way as combos 1->3.
3297 * Regardless of fact that we have a different mapping to
3298 * VNC auth mechs for plain VNC vs websockets VNC, the end
3299 * result has the same security characteristics.
3301 if (websocket || !tlscreds) {
3302 if (password) {
3303 VNC_DEBUG("Initializing VNC server with password auth\n");
3304 *auth = VNC_AUTH_VNC;
3305 } else if (sasl) {
3306 VNC_DEBUG("Initializing VNC server with SASL auth\n");
3307 *auth = VNC_AUTH_SASL;
3308 } else {
3309 VNC_DEBUG("Initializing VNC server with no auth\n");
3310 *auth = VNC_AUTH_NONE;
3312 *subauth = VNC_AUTH_INVALID;
3313 } else {
3314 bool is_x509 = object_dynamic_cast(OBJECT(tlscreds),
3315 TYPE_QCRYPTO_TLS_CREDS_X509) != NULL;
3316 bool is_anon = object_dynamic_cast(OBJECT(tlscreds),
3317 TYPE_QCRYPTO_TLS_CREDS_ANON) != NULL;
3319 if (!is_x509 && !is_anon) {
3320 error_setg(errp,
3321 "Unsupported TLS cred type %s",
3322 object_get_typename(OBJECT(tlscreds)));
3323 return -1;
3325 *auth = VNC_AUTH_VENCRYPT;
3326 if (password) {
3327 if (is_x509) {
3328 VNC_DEBUG("Initializing VNC server with x509 password auth\n");
3329 *subauth = VNC_AUTH_VENCRYPT_X509VNC;
3330 } else {
3331 VNC_DEBUG("Initializing VNC server with TLS password auth\n");
3332 *subauth = VNC_AUTH_VENCRYPT_TLSVNC;
3335 } else if (sasl) {
3336 if (is_x509) {
3337 VNC_DEBUG("Initializing VNC server with x509 SASL auth\n");
3338 *subauth = VNC_AUTH_VENCRYPT_X509SASL;
3339 } else {
3340 VNC_DEBUG("Initializing VNC server with TLS SASL auth\n");
3341 *subauth = VNC_AUTH_VENCRYPT_TLSSASL;
3343 } else {
3344 if (is_x509) {
3345 VNC_DEBUG("Initializing VNC server with x509 no auth\n");
3346 *subauth = VNC_AUTH_VENCRYPT_X509NONE;
3347 } else {
3348 VNC_DEBUG("Initializing VNC server with TLS no auth\n");
3349 *subauth = VNC_AUTH_VENCRYPT_TLSNONE;
3353 return 0;
3358 * Handle back compat with old CLI syntax by creating some
3359 * suitable QCryptoTLSCreds objects
3361 static QCryptoTLSCreds *
3362 vnc_display_create_creds(bool x509,
3363 bool x509verify,
3364 const char *dir,
3365 const char *id,
3366 Error **errp)
3368 gchar *credsid = g_strdup_printf("tlsvnc%s", id);
3369 Object *parent = object_get_objects_root();
3370 Object *creds;
3371 Error *err = NULL;
3373 if (x509) {
3374 creds = object_new_with_props(TYPE_QCRYPTO_TLS_CREDS_X509,
3375 parent,
3376 credsid,
3377 &err,
3378 "endpoint", "server",
3379 "dir", dir,
3380 "verify-peer", x509verify ? "yes" : "no",
3381 NULL);
3382 } else {
3383 creds = object_new_with_props(TYPE_QCRYPTO_TLS_CREDS_ANON,
3384 parent,
3385 credsid,
3386 &err,
3387 "endpoint", "server",
3388 NULL);
3391 g_free(credsid);
3393 if (err) {
3394 error_propagate(errp, err);
3395 return NULL;
3398 return QCRYPTO_TLS_CREDS(creds);
3402 static int vnc_display_get_address(const char *addrstr,
3403 bool websocket,
3404 int displaynum,
3405 int to,
3406 bool has_ipv4,
3407 bool has_ipv6,
3408 bool ipv4,
3409 bool ipv6,
3410 SocketAddress **retaddr,
3411 Error **errp)
3413 int ret = -1;
3414 SocketAddress *addr = NULL;
3416 addr = g_new0(SocketAddress, 1);
3418 if (strncmp(addrstr, "unix:", 5) == 0) {
3419 addr->type = SOCKET_ADDRESS_KIND_UNIX;
3420 addr->u.q_unix.data = g_new0(UnixSocketAddress, 1);
3421 addr->u.q_unix.data->path = g_strdup(addrstr + 5);
3423 if (websocket) {
3424 error_setg(errp, "UNIX sockets not supported with websock");
3425 goto cleanup;
3428 if (to) {
3429 error_setg(errp, "Port range not support with UNIX socket");
3430 goto cleanup;
3432 ret = 0;
3433 } else {
3434 const char *port;
3435 size_t hostlen;
3436 unsigned long long baseport = 0;
3437 InetSocketAddress *inet;
3439 port = strrchr(addrstr, ':');
3440 if (!port) {
3441 if (websocket) {
3442 hostlen = 0;
3443 port = addrstr;
3444 } else {
3445 error_setg(errp, "no vnc port specified");
3446 goto cleanup;
3448 } else {
3449 hostlen = port - addrstr;
3450 port++;
3451 if (*port == '\0') {
3452 error_setg(errp, "vnc port cannot be empty");
3453 goto cleanup;
3457 addr->type = SOCKET_ADDRESS_KIND_INET;
3458 inet = addr->u.inet.data = g_new0(InetSocketAddress, 1);
3459 if (addrstr[0] == '[' && addrstr[hostlen - 1] == ']') {
3460 inet->host = g_strndup(addrstr + 1, hostlen - 2);
3461 } else {
3462 inet->host = g_strndup(addrstr, hostlen);
3464 /* plain VNC port is just an offset, for websocket
3465 * port is absolute */
3466 if (websocket) {
3467 if (g_str_equal(addrstr, "") ||
3468 g_str_equal(addrstr, "on")) {
3469 if (displaynum == -1) {
3470 error_setg(errp, "explicit websocket port is required");
3471 goto cleanup;
3473 inet->port = g_strdup_printf(
3474 "%d", displaynum + 5700);
3475 if (to) {
3476 inet->has_to = true;
3477 inet->to = to + 5700;
3479 } else {
3480 inet->port = g_strdup(port);
3482 } else {
3483 if (parse_uint_full(port, &baseport, 10) < 0) {
3484 error_setg(errp, "can't convert to a number: %s", port);
3485 goto cleanup;
3487 if (baseport > 65535 ||
3488 baseport + 5900 > 65535) {
3489 error_setg(errp, "port %s out of range", port);
3490 goto cleanup;
3492 inet->port = g_strdup_printf(
3493 "%d", (int)baseport + 5900);
3495 if (to) {
3496 inet->has_to = true;
3497 inet->to = to + 5900;
3501 inet->ipv4 = ipv4;
3502 inet->has_ipv4 = has_ipv4;
3503 inet->ipv6 = ipv6;
3504 inet->has_ipv6 = has_ipv6;
3506 ret = baseport;
3509 *retaddr = addr;
3511 cleanup:
3512 if (ret < 0) {
3513 qapi_free_SocketAddress(addr);
3515 return ret;
3518 static int vnc_display_get_addresses(QemuOpts *opts,
3519 SocketAddress ***retsaddr,
3520 size_t *retnsaddr,
3521 SocketAddress ***retwsaddr,
3522 size_t *retnwsaddr,
3523 Error **errp)
3525 SocketAddress *saddr = NULL;
3526 SocketAddress *wsaddr = NULL;
3527 QemuOptsIter addriter;
3528 const char *addr;
3529 int to = qemu_opt_get_number(opts, "to", 0);
3530 bool has_ipv4 = qemu_opt_get(opts, "ipv4");
3531 bool has_ipv6 = qemu_opt_get(opts, "ipv6");
3532 bool ipv4 = qemu_opt_get_bool(opts, "ipv4", false);
3533 bool ipv6 = qemu_opt_get_bool(opts, "ipv6", false);
3534 size_t i;
3535 int displaynum = -1;
3536 int ret = -1;
3538 *retsaddr = NULL;
3539 *retnsaddr = 0;
3540 *retwsaddr = NULL;
3541 *retnwsaddr = 0;
3543 addr = qemu_opt_get(opts, "vnc");
3544 if (addr == NULL || g_str_equal(addr, "none")) {
3545 ret = 0;
3546 goto cleanup;
3548 if (qemu_opt_get(opts, "websocket") &&
3549 !qcrypto_hash_supports(QCRYPTO_HASH_ALG_SHA1)) {
3550 error_setg(errp,
3551 "SHA1 hash support is required for websockets");
3552 goto cleanup;
3555 qemu_opt_iter_init(&addriter, opts, "vnc");
3556 while ((addr = qemu_opt_iter_next(&addriter)) != NULL) {
3557 int rv;
3558 rv = vnc_display_get_address(addr, false, 0, to,
3559 has_ipv4, has_ipv6,
3560 ipv4, ipv6,
3561 &saddr, errp);
3562 if (rv < 0) {
3563 goto cleanup;
3565 /* Historical compat - first listen address can be used
3566 * to set the default websocket port
3568 if (displaynum == -1) {
3569 displaynum = rv;
3571 *retsaddr = g_renew(SocketAddress *, *retsaddr, *retnsaddr + 1);
3572 (*retsaddr)[(*retnsaddr)++] = saddr;
3575 /* If we had multiple primary displays, we don't do defaults
3576 * for websocket, and require explicit config instead. */
3577 if (*retnsaddr > 1) {
3578 displaynum = -1;
3581 qemu_opt_iter_init(&addriter, opts, "websocket");
3582 while ((addr = qemu_opt_iter_next(&addriter)) != NULL) {
3583 if (vnc_display_get_address(addr, true, displaynum, to,
3584 has_ipv4, has_ipv6,
3585 ipv4, ipv6,
3586 &wsaddr, errp) < 0) {
3587 goto cleanup;
3590 /* Historical compat - if only a single listen address was
3591 * provided, then this is used to set the default listen
3592 * address for websocket too
3594 if (*retnsaddr == 1 &&
3595 (*retsaddr)[0]->type == SOCKET_ADDRESS_KIND_INET &&
3596 wsaddr->type == SOCKET_ADDRESS_KIND_INET &&
3597 g_str_equal(wsaddr->u.inet.data->host, "") &&
3598 !g_str_equal((*retsaddr)[0]->u.inet.data->host, "")) {
3599 g_free(wsaddr->u.inet.data->host);
3600 wsaddr->u.inet.data->host =
3601 g_strdup((*retsaddr)[0]->u.inet.data->host);
3604 *retwsaddr = g_renew(SocketAddress *, *retwsaddr, *retnwsaddr + 1);
3605 (*retwsaddr)[(*retnwsaddr)++] = wsaddr;
3608 ret = 0;
3609 cleanup:
3610 if (ret < 0) {
3611 for (i = 0; i < *retnsaddr; i++) {
3612 qapi_free_SocketAddress((*retsaddr)[i]);
3614 g_free(*retsaddr);
3615 for (i = 0; i < *retnwsaddr; i++) {
3616 qapi_free_SocketAddress((*retwsaddr)[i]);
3618 g_free(*retwsaddr);
3619 *retsaddr = *retwsaddr = NULL;
3620 *retnsaddr = *retnwsaddr = 0;
3622 return ret;
3625 static int vnc_display_connect(VncDisplay *vd,
3626 SocketAddress **saddr,
3627 size_t nsaddr,
3628 SocketAddress **wsaddr,
3629 size_t nwsaddr,
3630 Error **errp)
3632 /* connect to viewer */
3633 QIOChannelSocket *sioc = NULL;
3634 if (nwsaddr != 0) {
3635 error_setg(errp, "Cannot use websockets in reverse mode");
3636 return -1;
3638 if (nsaddr != 1) {
3639 error_setg(errp, "Expected a single address in reverse mode");
3640 return -1;
3642 vd->is_unix = saddr[0]->type == SOCKET_ADDRESS_KIND_UNIX;
3643 sioc = qio_channel_socket_new();
3644 qio_channel_set_name(QIO_CHANNEL(sioc), "vnc-reverse");
3645 if (qio_channel_socket_connect_sync(sioc, saddr[0], errp) < 0) {
3646 return -1;
3648 vnc_connect(vd, sioc, false, false);
3649 object_unref(OBJECT(sioc));
3650 return 0;
3654 static int vnc_display_listen_addr(VncDisplay *vd,
3655 SocketAddress *addr,
3656 const char *name,
3657 QIOChannelSocket ***lsock,
3658 guint **lsock_tag,
3659 size_t *nlsock,
3660 Error **errp)
3662 QIODNSResolver *resolver = qio_dns_resolver_get_instance();
3663 SocketAddress **rawaddrs = NULL;
3664 size_t nrawaddrs = 0;
3665 Error *listenerr = NULL;
3666 bool listening = false;
3667 size_t i;
3669 if (qio_dns_resolver_lookup_sync(resolver, addr, &nrawaddrs,
3670 &rawaddrs, errp) < 0) {
3671 return -1;
3674 for (i = 0; i < nrawaddrs; i++) {
3675 QIOChannelSocket *sioc = qio_channel_socket_new();
3677 qio_channel_set_name(QIO_CHANNEL(sioc), name);
3678 if (qio_channel_socket_listen_sync(
3679 sioc, rawaddrs[i], listenerr == NULL ? &listenerr : NULL) < 0) {
3680 object_unref(OBJECT(sioc));
3681 continue;
3683 listening = true;
3684 (*nlsock)++;
3685 *lsock = g_renew(QIOChannelSocket *, *lsock, *nlsock);
3686 *lsock_tag = g_renew(guint, *lsock_tag, *nlsock);
3688 (*lsock)[*nlsock - 1] = sioc;
3689 (*lsock_tag)[*nlsock - 1] = 0;
3692 for (i = 0; i < nrawaddrs; i++) {
3693 qapi_free_SocketAddress(rawaddrs[i]);
3695 g_free(rawaddrs);
3697 if (listenerr) {
3698 if (!listening) {
3699 error_propagate(errp, listenerr);
3700 return -1;
3701 } else {
3702 error_free(listenerr);
3706 for (i = 0; i < *nlsock; i++) {
3707 (*lsock_tag)[i] = qio_channel_add_watch(
3708 QIO_CHANNEL((*lsock)[i]),
3709 G_IO_IN, vnc_listen_io, vd, NULL);
3712 return 0;
3716 static int vnc_display_listen(VncDisplay *vd,
3717 SocketAddress **saddr,
3718 size_t nsaddr,
3719 SocketAddress **wsaddr,
3720 size_t nwsaddr,
3721 Error **errp)
3723 size_t i;
3725 for (i = 0; i < nsaddr; i++) {
3726 if (vnc_display_listen_addr(vd, saddr[i],
3727 "vnc-listen",
3728 &vd->lsock,
3729 &vd->lsock_tag,
3730 &vd->nlsock,
3731 errp) < 0) {
3732 return -1;
3735 for (i = 0; i < nwsaddr; i++) {
3736 if (vnc_display_listen_addr(vd, wsaddr[i],
3737 "vnc-ws-listen",
3738 &vd->lwebsock,
3739 &vd->lwebsock_tag,
3740 &vd->nlwebsock,
3741 errp) < 0) {
3742 return -1;
3746 return 0;
3750 void vnc_display_open(const char *id, Error **errp)
3752 VncDisplay *vd = vnc_display_find(id);
3753 QemuOpts *opts = qemu_opts_find(&qemu_vnc_opts, id);
3754 SocketAddress **saddr = NULL, **wsaddr = NULL;
3755 size_t nsaddr, nwsaddr;
3756 const char *share, *device_id;
3757 QemuConsole *con;
3758 bool password = false;
3759 bool reverse = false;
3760 const char *credid;
3761 bool sasl = false;
3762 #ifdef CONFIG_VNC_SASL
3763 int saslErr;
3764 #endif
3765 int acl = 0;
3766 int lock_key_sync = 1;
3767 int key_delay_ms;
3768 size_t i;
3770 if (!vd) {
3771 error_setg(errp, "VNC display not active");
3772 return;
3774 vnc_display_close(vd);
3776 if (!opts) {
3777 return;
3780 if (vnc_display_get_addresses(opts, &saddr, &nsaddr,
3781 &wsaddr, &nwsaddr, errp) < 0) {
3782 goto fail;
3785 if (saddr == NULL) {
3786 return;
3789 password = qemu_opt_get_bool(opts, "password", false);
3790 if (password) {
3791 if (fips_get_state()) {
3792 error_setg(errp,
3793 "VNC password auth disabled due to FIPS mode, "
3794 "consider using the VeNCrypt or SASL authentication "
3795 "methods as an alternative");
3796 goto fail;
3798 if (!qcrypto_cipher_supports(
3799 QCRYPTO_CIPHER_ALG_DES_RFB, QCRYPTO_CIPHER_MODE_ECB)) {
3800 error_setg(errp,
3801 "Cipher backend does not support DES RFB algorithm");
3802 goto fail;
3806 reverse = qemu_opt_get_bool(opts, "reverse", false);
3807 lock_key_sync = qemu_opt_get_bool(opts, "lock-key-sync", true);
3808 key_delay_ms = qemu_opt_get_number(opts, "key-delay-ms", 1);
3809 sasl = qemu_opt_get_bool(opts, "sasl", false);
3810 #ifndef CONFIG_VNC_SASL
3811 if (sasl) {
3812 error_setg(errp, "VNC SASL auth requires cyrus-sasl support");
3813 goto fail;
3815 #endif /* CONFIG_VNC_SASL */
3816 credid = qemu_opt_get(opts, "tls-creds");
3817 if (credid) {
3818 Object *creds;
3819 if (qemu_opt_get(opts, "tls") ||
3820 qemu_opt_get(opts, "x509") ||
3821 qemu_opt_get(opts, "x509verify")) {
3822 error_setg(errp,
3823 "'tls-creds' parameter is mutually exclusive with "
3824 "'tls', 'x509' and 'x509verify' parameters");
3825 goto fail;
3828 creds = object_resolve_path_component(
3829 object_get_objects_root(), credid);
3830 if (!creds) {
3831 error_setg(errp, "No TLS credentials with id '%s'",
3832 credid);
3833 goto fail;
3835 vd->tlscreds = (QCryptoTLSCreds *)
3836 object_dynamic_cast(creds,
3837 TYPE_QCRYPTO_TLS_CREDS);
3838 if (!vd->tlscreds) {
3839 error_setg(errp, "Object with id '%s' is not TLS credentials",
3840 credid);
3841 goto fail;
3843 object_ref(OBJECT(vd->tlscreds));
3845 if (vd->tlscreds->endpoint != QCRYPTO_TLS_CREDS_ENDPOINT_SERVER) {
3846 error_setg(errp,
3847 "Expecting TLS credentials with a server endpoint");
3848 goto fail;
3850 } else {
3851 const char *path;
3852 bool tls = false, x509 = false, x509verify = false;
3853 tls = qemu_opt_get_bool(opts, "tls", false);
3854 if (tls) {
3855 path = qemu_opt_get(opts, "x509");
3857 if (path) {
3858 x509 = true;
3859 } else {
3860 path = qemu_opt_get(opts, "x509verify");
3861 if (path) {
3862 x509 = true;
3863 x509verify = true;
3866 vd->tlscreds = vnc_display_create_creds(x509,
3867 x509verify,
3868 path,
3869 vd->id,
3870 errp);
3871 if (!vd->tlscreds) {
3872 goto fail;
3876 acl = qemu_opt_get_bool(opts, "acl", false);
3878 share = qemu_opt_get(opts, "share");
3879 if (share) {
3880 if (strcmp(share, "ignore") == 0) {
3881 vd->share_policy = VNC_SHARE_POLICY_IGNORE;
3882 } else if (strcmp(share, "allow-exclusive") == 0) {
3883 vd->share_policy = VNC_SHARE_POLICY_ALLOW_EXCLUSIVE;
3884 } else if (strcmp(share, "force-shared") == 0) {
3885 vd->share_policy = VNC_SHARE_POLICY_FORCE_SHARED;
3886 } else {
3887 error_setg(errp, "unknown vnc share= option");
3888 goto fail;
3890 } else {
3891 vd->share_policy = VNC_SHARE_POLICY_ALLOW_EXCLUSIVE;
3893 vd->connections_limit = qemu_opt_get_number(opts, "connections", 32);
3895 #ifdef CONFIG_VNC_JPEG
3896 vd->lossy = qemu_opt_get_bool(opts, "lossy", false);
3897 #endif
3898 vd->non_adaptive = qemu_opt_get_bool(opts, "non-adaptive", false);
3899 /* adaptive updates are only used with tight encoding and
3900 * if lossy updates are enabled so we can disable all the
3901 * calculations otherwise */
3902 if (!vd->lossy) {
3903 vd->non_adaptive = true;
3906 if (acl) {
3907 if (strcmp(vd->id, "default") == 0) {
3908 vd->tlsaclname = g_strdup("vnc.x509dname");
3909 } else {
3910 vd->tlsaclname = g_strdup_printf("vnc.%s.x509dname", vd->id);
3912 qemu_acl_init(vd->tlsaclname);
3914 #ifdef CONFIG_VNC_SASL
3915 if (acl && sasl) {
3916 char *aclname;
3918 if (strcmp(vd->id, "default") == 0) {
3919 aclname = g_strdup("vnc.username");
3920 } else {
3921 aclname = g_strdup_printf("vnc.%s.username", vd->id);
3923 vd->sasl.acl = qemu_acl_init(aclname);
3924 g_free(aclname);
3926 #endif
3928 if (vnc_display_setup_auth(&vd->auth, &vd->subauth,
3929 vd->tlscreds, password,
3930 sasl, false, errp) < 0) {
3931 goto fail;
3934 if (vnc_display_setup_auth(&vd->ws_auth, &vd->ws_subauth,
3935 vd->tlscreds, password,
3936 sasl, true, errp) < 0) {
3937 goto fail;
3940 #ifdef CONFIG_VNC_SASL
3941 if ((saslErr = sasl_server_init(NULL, "qemu")) != SASL_OK) {
3942 error_setg(errp, "Failed to initialize SASL auth: %s",
3943 sasl_errstring(saslErr, NULL, NULL));
3944 goto fail;
3946 #endif
3947 vd->lock_key_sync = lock_key_sync;
3948 if (lock_key_sync) {
3949 vd->led = qemu_add_led_event_handler(kbd_leds, vd);
3951 vd->ledstate = 0;
3952 vd->key_delay_ms = key_delay_ms;
3954 device_id = qemu_opt_get(opts, "display");
3955 if (device_id) {
3956 int head = qemu_opt_get_number(opts, "head", 0);
3957 Error *err = NULL;
3959 con = qemu_console_lookup_by_device_name(device_id, head, &err);
3960 if (err) {
3961 error_propagate(errp, err);
3962 goto fail;
3964 } else {
3965 con = NULL;
3968 if (con != vd->dcl.con) {
3969 unregister_displaychangelistener(&vd->dcl);
3970 vd->dcl.con = con;
3971 register_displaychangelistener(&vd->dcl);
3974 if (reverse) {
3975 if (vnc_display_connect(vd, saddr, nsaddr, wsaddr, nwsaddr, errp) < 0) {
3976 goto fail;
3978 } else {
3979 if (vnc_display_listen(vd, saddr, nsaddr, wsaddr, nwsaddr, errp) < 0) {
3980 goto fail;
3984 if (qemu_opt_get(opts, "to")) {
3985 vnc_display_print_local_addr(vd);
3988 cleanup:
3989 for (i = 0; i < nsaddr; i++) {
3990 qapi_free_SocketAddress(saddr[i]);
3992 for (i = 0; i < nwsaddr; i++) {
3993 qapi_free_SocketAddress(wsaddr[i]);
3995 return;
3997 fail:
3998 vnc_display_close(vd);
3999 goto cleanup;
4002 void vnc_display_add_client(const char *id, int csock, bool skipauth)
4004 VncDisplay *vd = vnc_display_find(id);
4005 QIOChannelSocket *sioc;
4007 if (!vd) {
4008 return;
4011 sioc = qio_channel_socket_new_fd(csock, NULL);
4012 if (sioc) {
4013 qio_channel_set_name(QIO_CHANNEL(sioc), "vnc-server");
4014 vnc_connect(vd, sioc, skipauth, false);
4015 object_unref(OBJECT(sioc));
4019 static void vnc_auto_assign_id(QemuOptsList *olist, QemuOpts *opts)
4021 int i = 2;
4022 char *id;
4024 id = g_strdup("default");
4025 while (qemu_opts_find(olist, id)) {
4026 g_free(id);
4027 id = g_strdup_printf("vnc%d", i++);
4029 qemu_opts_set_id(opts, id);
4032 QemuOpts *vnc_parse(const char *str, Error **errp)
4034 QemuOptsList *olist = qemu_find_opts("vnc");
4035 QemuOpts *opts = qemu_opts_parse(olist, str, true, errp);
4036 const char *id;
4038 if (!opts) {
4039 return NULL;
4042 id = qemu_opts_id(opts);
4043 if (!id) {
4044 /* auto-assign id if not present */
4045 vnc_auto_assign_id(olist, opts);
4047 return opts;
4050 int vnc_init_func(void *opaque, QemuOpts *opts, Error **errp)
4052 Error *local_err = NULL;
4053 char *id = (char *)qemu_opts_id(opts);
4055 assert(id);
4056 vnc_display_init(id);
4057 vnc_display_open(id, &local_err);
4058 if (local_err != NULL) {
4059 error_reportf_err(local_err, "Failed to start VNC server: ");
4060 exit(1);
4062 return 0;
4065 static void vnc_register_config(void)
4067 qemu_add_opts(&qemu_vnc_opts);
4069 opts_init(vnc_register_config);