From c7d14244b1b025199fed945e8eb51ebc5d804b4e Mon Sep 17 00:00:00 2001 From: Sebastian Keller Date: Fri, 24 Jul 2020 21:20:58 +0200 Subject: [PATCH] x11: Add STRING/UTF8_STRING targets for selection sources lacking them The memory selection source was only providing the "text/plain" or the "text/plain;charset=utf-8" mimetype, but not "STRING" or "UTF8_STRING", which some X11 clients, like wine, are looking for. This was breaking pasting from the clipboard in wine applications. Fix this by adding those targets when they are missing and the selection source provides the corresponding mimetypes. https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1369 --- src/x11/meta-x11-selection.c | 45 ++++++++++++++++++++++++++++++------ 1 file changed, 38 insertions(+), 7 deletions(-) diff --git a/src/x11/meta-x11-selection.c b/src/x11/meta-x11-selection.c index 77659fcfa..f9b3607a7 100644 --- a/src/x11/meta-x11-selection.c +++ b/src/x11/meta-x11-selection.c @@ -79,18 +79,49 @@ static GBytes * mimetypes_to_bytes (GList *mimetypes, Display *xdisplay) { - gint i = 0, len = g_list_length (mimetypes) + 2; - Atom *atoms = g_new0 (Atom, len); + GArray *atoms = g_array_new (FALSE, FALSE, sizeof (Atom)); GList *l; + char *mimetype; + Atom atom; + gboolean utf8_string_found = FALSE, utf8_string_mimetype_found = FALSE; + gboolean string_found = FALSE, string_mimetype_found = FALSE; + GBytes *bytes; for (l = mimetypes; l; l = l->next) - atoms[i++] = XInternAtom (xdisplay, l->data, False); + { + mimetype = l->data; + atom = XInternAtom (xdisplay, mimetype, False); + g_array_append_val (atoms, atom); + utf8_string_mimetype_found |= strcmp (mimetype, UTF8_STRING_MIMETYPE) == 0; + utf8_string_found |= strcmp (mimetype, "UTF8_STRING") == 0; + string_mimetype_found |= strcmp (mimetype, STRING_MIMETYPE) == 0; + string_found |= strcmp (mimetype, "STRING") == 0; + } - atoms[i++] = XInternAtom (xdisplay, "TARGETS", False); - atoms[i++] = XInternAtom (xdisplay, "TIMESTAMP", False); - g_assert (i == len); + /* Some X11 clients can only handle STRING/UTF8_STRING but not the + * corresponding mimetypes. */ + if (utf8_string_mimetype_found && !utf8_string_found) + { + atom = XInternAtom (xdisplay, "UTF8_STRING", False); + g_array_append_val (atoms, atom); + } - return g_bytes_new_take (atoms, len * sizeof (Atom)); + if (string_mimetype_found && !string_found) + { + atom = XInternAtom (xdisplay, "STRING", False); + g_array_append_val (atoms, atom); + } + + atom = XInternAtom (xdisplay, "TARGETS", False); + g_array_append_val (atoms, atom); + + atom = XInternAtom (xdisplay, "TIMESTAMP", False); + g_array_append_val (atoms, atom); + + bytes = g_bytes_new_take (atoms->data, atoms->len * sizeof (Atom)); + g_array_free (atoms, FALSE); + + return bytes; } static void