2026-11-05 Daniel P. Berrangé Bump version to 1.6.0 and update NEWS add object properties for TLS attributes Remove gboolean return value from setters that can't fail Add API docs for recent methods skip clipboard sync if not yet initialized This prevents a crash on early startup if seeing clipboard changes. 2026-11-04 Daniel P. Berrangé examples: add --tls-cert-dir and --tls-priority args to gvncviewer This allows control over important TLS settings. src: add debug logging about cert path resolution tools: add docs about TLS cert search paths tools: add --tls-cert-dir and --tls-priority args to gvnccapture This allows control over important TLS settings. src: favour $HOME/.pki over /etc/pki for certs This allows the user to override the system defaults src: add ability to set the TLS algorithm priority Currently the algorithm priority is determined at build time, and potentially via the global gnutls config file. It is desirable to allow full runtime configuration at the API level though. src: add ability to set the TLS cert directory explicitly Instead of constructing a TLS cert dir based on a set of standard dirs and a client name, allow the dir to be set explicitly. src: look for CA cert and CRL in same dir as client cert/key This allows all TLS credentials to be placed in a single directory. src: resolve multiple TLS key/cert pairs in parallel Allow loading upto 4 pairs of key/cert files, with the naming 'clientcertNNN.pem' and 'clientkeyNNN.pem' for NNN in range 0-3. The first missing index terminates the search. If none are found, falls back to the non-indexed file names. src: add tracking of multiple key/cert pairs This will open up the possibility of using multiple key/cert pairs depending on the algorithms required/desired. src: allow loading key from same directory as cert Using the 'private/' subdir for the key serves no useful purpose as both must be readable to the same process for them to be useful. src: load TLS cert and key from same directory location When searching for a TLS cert and key they must come as a matched pair, so if we find key in one directory tree, we must get the cert from the same tree. src: avoid theoretical use after free When the "CLIENTNAME" credential is set, we free() the existing cert paths, on the expectation that vnc_connection_set_credential_x509() will allocate new paths. If the file on disk we previously detected has since been deleted, however, there is a risk of use-after-free, as in that case the vnc_connection_set_credential_x509() method won't set new paths. Moving the frees into vnc_connection_set_credential_x509() makes the memory mgmt responsibility more clear. examples: fix leak of many local variables in gvncviewer tools: fix leak of many local variables in gvnccapture src: fix leak of TLS cert search dirs src: ensure TLS credentials are freed The TLS credentials need to be kept alive for as long as the TLS session object has a reference. 2026-11-03 Daniel P. Berrangé src: wire up auto-sync via cut text protocol If the extended clipboard protocol is not available, we can still help applications by providing automatic sync via the legacy cut text protocol. examples: illustrate controlling clipboard sync src: add APIs to control clipboard target UNIX platforms historically have at least two distinct clipboards, * PRIMARY - the selected text * CLIPBOARD - the Windows like shared clipboard Currently the code sends text stored in PRIMARY and when receiving text stores it in both. Add the ability to control this by allowing to send from either or both, as well as storing in either or both. The default is to use CLIPBOARD exclusively. src: add APIs to control clipboard synchronization When the VNC server is connected to a virtual machine, the remote peer may not be trustworthy. If a host admin is using a password manager which copies a password into the clipboard, it is highly undesirable for that to be automatically synchronized to an untrusted virtual machine. This introduces a way to control the clipboard synchronization activity. By default it is fully disabled, and an opt in can enable outgoing synchronization (client to server), or incoming synchronization (server to client), or both. src: stop tracking server clipboard action flags We can only provide a meaningful impl if all the action flags are set, except for "PEEK". src: add API to determine if extended clipboard is available src: return error status from clipboard APIs It is normal practice in APIs to return !vnc_connection_has_error() src: refer to clipboard "text" instead of "data" in APIs/signals While the RFB protocol can handle many types of clipboard data, the code exclusively handles UTF8 text. The APIs and signals used to deal with the clipboard should refer to "text", so that we have the "data" name available for future more general use. src: rename public clipboard APIs to have consistent naming Ensure "vnc_connection_clipboard_" is used as the name prefix for everything that is in the public API. 2026-10-13 Roy-Magne Mo Add Norwegian Nynorsk translation 2026-08-13 Daniel P. Berrangé Make credential list parameter const 2026-08-10 Mikel Rychliski Fix SASL auth with older QEMU servers QEMU releases prior to 9.2 do not correctly ensure the padding byte is NUL. Restore compatibility with these releases by correcting the response. 2026-08-06 Patrick Monnerat Add support for server certificate custom validation. New connection artefacts are introduced: - type VncConnectionValidationStatus features 3-state values to represent an X509 certificate validation status. - property "validation-status" holds the last certificate validation status for the connection. - new functions vnc_connection_get_validation_status() and vnc_connection_set_validation_status() get/set the above property. - signal "vnc-auth-validate" emitted when a server certificate has to be validated. Signal handlers receive the certificate chain in an argument that contains an array of GBytes items, each of them in DER format. Handlers are supposed to set the "validation-status" property. The default handler is triggered last to let a chance to a custom handler to bypass it. Should a handler behavior depend on the default validation process, connect it "after" and monitor the validation status previously set. 2026-08-04 Daniel P. Berrangé src: fully skip clipboard notify in read-only widgets 2026-07-31 Daniel P. Berrangé examples: illustrate providing CA cert via API and CLI Don't unconditionally ask for VNC_CONNECTION_CREDENTIAL_CA_CERT_DATA The change to introduce VNC_CONNECTION_CREDENTIAL_CA_CERT_DATA meant that for any TLS connection, the 'vnc-auth-credential' signal will always include the new credential type. No existing application is expecting that type and if following the example programs, will treat that as a fatal error. IOW, introducing the VNC_CONNECTION_CREDENTIAL_CA_CERT_DATA was an inadvertant API/ABI incompatibility. To fix that regression, and allow for introducing further credential types in future, introduce an opt-in mechanism for credentials. If it is willing to handle credentials beyond the historical three of password, username, clientname, the application must now call the vnc_connection_set_credential_types method, providing the list of credential types it can handle. The code will never ask for new credentials unless requested, so old auth handlers connected to 'vnc-auth-credential' won't raise errors. 2026-07-24 Mikhail Dmitrichenko vncconnection: Avoid truncating Tight pixel sums Tight gradient decoding adds the encoded delta pixel to the predicted pixel and then masks the result back to the component range. For the narrower specializations, storing the component sums in src_pixel_t can narrow the intermediate result before the mask is applied. Use gint for the temporary component sums, matching the prediction path, so the arithmetic is performed at integer width before repacking the pixel. vncconnection: Avoid truncating Tight gradient components Tight gradient prediction computes color components as the sum of the left and upper pixels minus the upper-left pixel, then clamps the result to the component mask. For the 8bpp specialization, ssrc_pixel_t is gint8. This means the intermediate int result can be narrowed before the clamp is applied, producing an incorrect predicted pixel for 8bpp true-color formats with component masks larger than signed 8-bit can represent. Use gint for the component accumulators so the clamp is applied before packing the pixel value. vncconnection: Fix auth type array bounds checks The auth negotiation code stores advertised authentication types in a fixed-size unsigned int auth[20] array. Two bounds checks compared the number of advertised types against sizeof(auth), which is the size in bytes, not the number of array elements. On typical platforms this allowed up to 80 entries through, while the array only has 20 elements. Use G_N_ELEMENTS(auth) so the check matches the indexed writes that follow. 2026-07-17 Lin Ma src: fix extended clipboard (Host->VM direction) issue in Plasma-Wayland The extended clipboard (Host -> VM direction) does not function in Plasma-Wayland. When users double-click to select text on host, virt-viewer/virt-manager window does not have focus. Unlike Gnome Wayland, Under Plasma Wayland, applications do not read other applications' selections when they do not have focus; It only sends the current selection to the application that gains focus when focus switches. The differences in behavior between Gnome Wayland and Plasma Wayland necessitate two separate paths: * Gnome Wayland path (normal): select text on host -> owner-change [virt-viewer has no focus at this point] -> handle_clipboard_change (pending=TRUE, announce FALSE) -> Focus acquired -> flush_pending_clipboard (pending=TRUE -> announce TRUE -> VM receives) * Plasma Wayland path (where the issue lies): select text on host -> [no owner-change, because virt-viewer has no focus] -> focus acquired -> flush_pending_clipboard (pending=FALSE -> does nothing) -> owner-change [Plasma Wayland triggers this only after focus is acquired] -> handle_clipboard_change (pending=TRUE, announce FALSE) -> [No new focus events] -> flush is never called The newly added 'gtk_widget_has_focus' check fills this gap: When 'handle_clipboard_change' is called, if virt-viewer window already has focus (in the Plasma Wayland scenario), 'flush_pending_clipboard' is called immediately without waiting for a focus event that will not occur again. In Gnome Wayland scenario, 'owner-change' is triggered when virt-viewer window does not have focus, so 'gtk_widget_has_focus' returns FALSE, following the original path with no change in behavior. 2026-06-30 Daniel P. Berrangé src: stop declaring get_type funcs with G_GNUC_CONST This was always technically invalid but happened to work, but is now broken by GCC 16: https://gitlab.gnome.org/GNOME/glib/-/work_items/3984 https://blogs.gnome.org/mcatanzaro/2026/06/29/your-_get_type-function-is-not-g_gnuc_const-part-two/ src: ignore received clipboard text if read-only If the server sends us clipboard text while the widget is readonly we should decline to update the local clipboard. src: check read-only state if server requests clipboard We should not send a "notify" message to the server about clipboard data availability if read-only. None the less, protect against a server unconditionally asking for data by checknig the read-only state again. 2026-06-06 Lin Ma vncdisplay: let GLib manages the lifecycle of VncDisplay GObject In gtk-vnc project, all other signals are connected to priv->conn, GLib automatically cleans up these connections when vnc_display_finalize calls g_object_unref(priv->conn). The clipboard signal is an exception, it's connected to the global singleton GtkClipboard, doesn't automatically disconnect when the VncDisplay is destroyed. This leads to a race condition issue: If an app like virt-manager/virt-viewer destroys a 'VncDisplay' at some point during the guest's startup process for some reason, and the user happens to trigger a clipboard event (double-clicking to select text on host) after the 'VncDisplay' is destroyed, it causes a crash. E.g Using host libthread_db library "/lib64/libthread_db.so.1". Core was generated by `/usr/bin/virt-manager /usr/bin/virt-manager'. Program terminated with signal SIGSEGV, Segmentation fault. #0 on_primary_owner_change (clipboard=0x55869a5f7cc0, event=0x558699b78bd0, \ opaque=0x55869e0f02b0) at ../src/vncdisplay.c:1944 1944 if (priv->primary_selection_timer_id != 0) { [Current thread is 1 (Thread 0x7f15bd4535c0 (LWP 2730))] (gdb) l 1939 { 1940 VncDisplay *display = VNC_DISPLAY(opaque); 1941 VncDisplayPrivate *priv = display->priv; 1942 1943 /* If a timer is already running, cancel it first. */ 1944 if (priv->primary_selection_timer_id != 0) { // CRASHES HERE 1945 g_source_remove(priv->primary_selection_timer_id); 1946 } (gdb) info locals display = 0x55869e0f02b0 priv = 0x0 (gdb) print display $1 = (VncDisplay *) 0x55869e0f02b0 (gdb) print *display $2 = {parent = {widget = {parent_instance = {g_type_instance = {g_class = \ 0x55869eddc590}, ref_count = 0, qdata = 0x55869e8783a0}, priv = 0x0}, dummy = \ 0x0}, priv = 0x0} We can see GtkWidget's priv is NULL, indicating that dispose has been executed; ref_count is 0, indicating the object has entered the destruction process. The crash occurred in on_primary_owner_change, the callback function to the GtkClipboard::owner-change signal. The GtkClipboard returned by gtk_clipboard_get(GDK_SELECTION_PRIMARY) is a global singleton with a lifecycle identical to the entire application. This signal was never disconnected in vnc_display_finalize. Crash sequence supposed to be: VncDisplay creation -> init() connects to the clipboard signal -> VncDisplay destruction -> finalize() releases priv -> At some point, user selects text -> the clipboard "owner-change" signal is triggered -> on_primary_owner_change() retrieves the destroyed display pointer -> display->priv is NULL -> SIGSEGV This patch fixes the issue by using g_signal_connect_object instead of g_signal_connect so that GLib will automatically disconnect the signal connection when the display object is finalized. 2026-03-15 Baurzhan Muftakhidinov Add Kazakh translation 2026-03-02 Daniel P. Berrangé src: improve extended clipboard debug messages 2026-02-27 Daniel P. Berrangé src: add missing error return when clipboard is unsupported src: emit extended clipboard signal in main context The signal must not be emitted directly from coroutine context. src: remove use of buffered write APIs in extended clipboard The extended clipboard handlers incorrectly used the buffered write APIs instead of the coroutine write APIs. examples: illustrate simple server clipboard handling src: fix emitting auth signal from main thread src: drop use of gnutls_global_init This is called automatically since GNUTLS 3.3.0 and does not need to be run manually anymore. src: drop disabled gnutls logging code This can be done automatically via environment variables supported by GNUTLS: https://gnutls.org/manual/html_node/Debugging-and-auditing.html src: drop obsolete code generated DH parameters This is documented as not required sine GNUTLS >= 3.6.0 which our min versioned check satisfies. src: remove vncclipboard.h header file The RFB protocol constants should not be part of the public API src: avoid needless redirection via GString for clipboard Per the RFB protocol, the server provided clipboard buffer should be plain text, and the client code forces NUL termination in case it is not present in the data in the wire. The signal emitted by the VncConnection only takes a raw string, so there is no way to handle embedded NULs in the middle of the text. This all makes the use of a GString needless redirection. src: add notes about coroutines to helper readers src: fix error handling in main thread context The vnc_connection_set_error method assumes it is running in coroutine context and so crashes in main thread context, trying to yield from a coroutine that is not active. Introduce a separate vnc_connection_co_set_error for use in coroutine context and make vnc_connection_set_error work in main thread context. This completes standardization on 'vnc_connection_co_' prefix for all functions that must be run in coroutine context, as opposed to main loop context. src: rename initialization and message handlers to vnc_connection_co_* Continue to standardize on 'vnc_connection_co_' prefix for all functions that must be run in coroutine context, as opposed to main loop context. src: rename psuedo encoding handlers to vnc_connection_co_* Continue to standardize on 'vnc_connection_co_' prefix for all functions that must be run in coroutine context, as opposed to main loop context. src: rename framebuffer encoding handlers to vnc_connection_co_update_* Continue to standardize on 'vnc_connection_co_' prefix for all functions that must be run in coroutine context, as opposed to main loop context. src: rename vnc_connection_coroutine to vnc_connection_co_main Continue to standardize on 'vnc_connection_co_' prefix for all functions that must be run in coroutine context, as opposed to main loop context. src: rename vnc_connection_write* to vnc_connection_co_write* Continue to standardize on 'vnc_connection_co_' prefix for all functions that must be run in coroutine context, as opposed to main loop context. src: rename vnc_connection_read* to vnc_connection_co_read* Continue to standardize on 'vnc_connection_co_' prefix for all functions that must be run in coroutine context, as opposed to main loop context. src: rename vnc_connection_emit_main_context to vnc_connection_co_signal_emit Start to standardize on 'vnc_connection_co_' prefix for all functions that must be run in coroutine context, as opposed to main loop context. src: remove stray newline from log message src: fix syntax check violations in clipboard code src: fixup indentation / formatting 2026-02-26 Daniel P. Berrangé Don't drop Tight encoding when Jpeg is missing The Tight encoding only permits use of the Jpeg encoding if a Jpeg quality level is advertized. So if jpeg pixbuf support is missing, there is no reason to skip Tight encoding entirely. 2026-02-17 Daniel P. Berrangé Add debug messages for Tight framebuffer update encodings examples: don't let menu bar expand 2026-02-02 Patrick Monnerat display: properly draw background of a zoomed out image When cutting the image hole out of the background rectangle, take scaling into account. display: take zoom level into account in offsets computation The frame buffer is unscaled while the window is: their sizes should then not be compared without being adjusted. display: do not round scale from zoom level When computing scale factors from zoom level, rounding restricts the formers to exact values 0..4, which causes "jumpy" zooming and forbids shrinking the display image. This commit preserves the fractional scaling values. 2026-01-27 Flynn Peck Add Cornish translation 2026-01-14 Baxrom Raxmatov Add Uzbek (Latin) translation 2025-12-02 Marc-André Lureau display: fix extended key handling on win32 MapVirtualKey() of keys that require extended code (like VK_DOWN 0x28) maps to ambiguous or state sensitive code (like XT Numpad 2 0x50). Even MAPVK_VK_TO_VSC_EX does not seem to hold its promise. Instead, use the more direct GDK API provided by 3.22 and convert to the QNUM/VNC encoding. Fixes: https://issues.redhat.com/browse/RHEL-132127 2025-10-12 Lin Ma Complete server-to-client data sync (PROVIDE) This patch implements the final stage of the server-to-client extended clipboard synchronization, enabling the client to receive and process the actual data sent by the server via 'VNC_CLIPBOARD_ACTION_PROVIDE'. The main workflow is as follows: 1. Upon receiving a 'PROVIDE' message, VncConnection reads and decompresses the data payload using zlib. 2. It parses the decompressed data, extracts the text content, and handles any potential Unicode escape sequences. 3. After validating the data as legal UTF-8, it emits a new GObject signal, 'vnc-clipboard-data-received', passing the text as an argument. 4. VncDisplay listens for this signal and, in its callback, sets the received text to the local 'CLIPBOARD' and 'PRIMARY' selections. Implement handling of server clipboard NOTIFY action This patch implements the first step in the server-to-client clipboard synchronization flow: the client's response to a server update notification. The specific changes are as follows: - When VncConnection receives a message from the server with the 'VNC_CLIPBOARD_ACTION_NOTIFY' flag, the new 'vnc_connection_handle_clipboard_notify' function is called. - Within this function, the client checks if the server supports the 'REQUEST' action. If so, the client immediately sends back a 'REQUEST' message, asking the server to provide its clipboard data. - Additionally, upon receiving a notification from the server, any pending client-to-server clipboard update ('pendingClientClipboard') is cancelled. This ensures correct clipboard state synchronization. This commit establishes the "Notify -> Request" interaction, laying the groundwork for the client to receive clipboard data from the server. Implement response to server clipboard REQUEST action This patch implements the full logic for the client to handle a server's VNC_CLIPBOARD_ACTION_REQUEST and send back the clipboard data. When the VncConnection receives a data request from the server, it now: 1. Emits a new GObject signal, 'clipboard-request', to propagate the protocol event to the upper VncDisplay layer. 2. VncDisplay, upon catching this signal, asynchronously requests the text content of the 'PRIMARY' selection from GTK. 3. After successfully fetching the text, it passes the data back to the VncConnection via the public API vnc_connection_send_clipboard_data. 4. The VncConnection then compresses the data using zlib and sends it to the server side. This implementation handles the decoupling of the protocol and UI layers, manages GTK's asynchronous clipboard operations, and completes the request-response loop for client-to-server data synchronization. Flush pending clipboard on focus-in event This patch introduces a mechanism to handle clipboard synchronization when the VNC client window regains focus. Previously, if a user copied content while the VNC window was inactive, the clipboard change state 'pendingClientClipboard' was recorded but not immediately notified to the server. This commit addresses this by: - Making VncDisplay listen for the 'focus-in-event' signal. - When the widget gains focus, the vnc_connection_flush_pending_clipboard function is called. - This function checks for a pending clipboard update and, if one exists, immediately sends a NOTIFY message to the server side, announcing that clipboard content is available. This "lazy synchronization" strategy ensures that the clipboard state is updated only when the user re-engages with the VNC session. Implement client-to-server clipboard update notification This patch implements the mechanism for notifying the VNC server side when the client's local clipboard content has changed. On the VncDisplay (UI) layer: - It detects local clipboard changes by listening to the 'owner-change' signal on the GDK 'PRIMARY' selection. - A 50ms timer is used to debounce events, filtering out transient, invalid events caused by actions like double-clicks. - When valid clipboard content is confirmed, it calls the underlying VncConnection function. On the VncConnection (protocol) layer: - A new public function vnc_connection_handle_clipboard_change, is added to serve as the entry point for triggering clipboard notifications from the UI layer. - The vnc_connection_write_clipboard_notify function is implemented to construct and send an extended clipboard message with the NOTIFY action. This patch completes the "announcement" phase of a client-side clipboard update, laying the groundwork for the server to subsequently request the data. Implement extended clipboard capability negotiation This patch implements the initial capability negotiation for the RFB Extended Clipboard protocol. It modifies the vnc_connection_server_message to detect the extended ServerCutText messages, which are identified by a negative length value. Upon receiving a message with the VNC_CLIPBOARD_ACTION_CAPS flag, The vnc_connection_handle_clipboard_caps function is called. This function parses the list of formats and their maximum sizes advertised by the server and stores them in the private connection state. After processing the server's capabilities, Client responds by sending its own capabilities back. The vnc_connection_write_clipboard_caps function constructs this response, announcing the client's supported formats and actions. New fields have been added to the VncConnectionPrivate struct to track the negotiation state and the server's capabilities. This commit establishes the foundational handshake required for all subsequent extended clipboard operations. Add the extended clipboard pseudo-encoding src: introduce a vncclipboard.h header file This header file defines the formats and the actions agreed upon by the RFB extended clipboard protocol. 2025-09-25 twlvnn kraftwerk Add Bulgarian translation 2025-06-11 Emilio Sepúlveda Add Interlingua translation 2025-06-08 Ahmed Najmawi Add Arabic translation 2025-06-02 Michael Hansen Update documentation to clarify button masks, and make truncation explicit. 2025-05-29 Michael Hansen Protect against a bad message using the old API with the new feature. Callers using the old vnc_connection_pointer_event() API when the extended mouse buttons Pseudo-encoding is supported may trigger a bad message to the server, since the high bit's meaning is changed. 2025-05-28 Michael Hansen Add support for extended mouse buttons pseudo-encoding. When supported by the server (e.g. TigerVNC 1.15), this enables the use of mouse buttons 8 and 9 (commonly called "Back" and "Forward" buttons). 2025-02-19 Daniel P. Berrangé Expand log message to include log domain and timestamp This helps correlate and distinguish logs from other components make --gtk-vnc-debug work with new glib Glib 2.80 changed its logging impl so that G_MESSAGES_DEBUG is only ever read once, which makes it impossible for --gtk-vnc-debug to change in many cases. The only viable way to change logging at runtime is to register a custom handler and print to the console ourselves. This is what we probably should have done from the start. Fix compat with older glib g_string_free_and_steal is only available in >= 2.76 Fix compat with older gmp The gmp_randstate_ptr typedef does not exist in 6.2.0. Set the min version to 6.2.0 since we don't target any distros with older versions.