xwayland: Generate a Xauth file and pass this to Xwayland when starting it
Before this commit, sudo x11-app, e.g. sudo gvim /etc/some-file, fails when running a Wayland session. Where as doing this under a "GNOME on Xorg" session works fine. For a user switching from the Xorg session to the Wayland session, this is regression, which we want to avoid. This commit fixes this by creating and passing an xauth file to Xwayland when mutter starts it. Just like gdm or startx pass a xauth file to Xorg when they start Xorg. Fixes #643 https://gitlab.gnome.org/GNOME/mutter/issues/643
This commit is contained in:
parent
769a02b630
commit
a8984a81c2
@ -116,6 +116,7 @@ xrandr_dep = dependency('xrandr', version: xrandr_req)
|
|||||||
xcb_randr_dep = dependency('xcb-randr')
|
xcb_randr_dep = dependency('xcb-randr')
|
||||||
xcb_res_dep = dependency('xcb-res')
|
xcb_res_dep = dependency('xcb-res')
|
||||||
xinerama_dep = dependency('xinerama')
|
xinerama_dep = dependency('xinerama')
|
||||||
|
xau_dep = dependency('xau')
|
||||||
ice_dep = dependency('ice')
|
ice_dep = dependency('ice')
|
||||||
atk_dep = dependency('atk', version: atk_req)
|
atk_dep = dependency('atk', version: atk_req)
|
||||||
libcanberra_dep = dependency('libcanberra', version: libcanberra_req)
|
libcanberra_dep = dependency('libcanberra', version: libcanberra_req)
|
||||||
|
@ -101,6 +101,7 @@ if have_x11
|
|||||||
x11_xcb_dep,
|
x11_xcb_dep,
|
||||||
xcb_randr_dep,
|
xcb_randr_dep,
|
||||||
xcb_res_dep,
|
xcb_res_dep,
|
||||||
|
xau_dep,
|
||||||
]
|
]
|
||||||
|
|
||||||
if have_sm
|
if have_sm
|
||||||
|
@ -52,6 +52,7 @@ typedef struct
|
|||||||
struct wl_client *client;
|
struct wl_client *client;
|
||||||
struct wl_resource *xserver_resource;
|
struct wl_resource *xserver_resource;
|
||||||
char *display_name;
|
char *display_name;
|
||||||
|
char *auth_file;
|
||||||
|
|
||||||
GCancellable *xserver_died_cancellable;
|
GCancellable *xserver_died_cancellable;
|
||||||
GSubprocess *proc;
|
GSubprocess *proc;
|
||||||
|
@ -361,6 +361,12 @@ meta_wayland_override_display_name (const char *display_name)
|
|||||||
_display_name_override = g_strdup (display_name);
|
_display_name_override = g_strdup (display_name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static const char *
|
||||||
|
meta_wayland_get_xwayland_auth_file (MetaWaylandCompositor *compositor)
|
||||||
|
{
|
||||||
|
return compositor->xwayland_manager.auth_file;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
meta_wayland_init (void)
|
meta_wayland_init (void)
|
||||||
{
|
{
|
||||||
@ -438,7 +444,10 @@ meta_wayland_init (void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (meta_should_autostart_x11_display ())
|
if (meta_should_autostart_x11_display ())
|
||||||
|
{
|
||||||
set_gnome_env ("DISPLAY", meta_wayland_get_xwayland_display_name (compositor));
|
set_gnome_env ("DISPLAY", meta_wayland_get_xwayland_display_name (compositor));
|
||||||
|
set_gnome_env ("XAUTHORITY", meta_wayland_get_xwayland_auth_file (compositor));
|
||||||
|
}
|
||||||
|
|
||||||
set_gnome_env ("WAYLAND_DISPLAY", meta_wayland_get_wayland_display_name (compositor));
|
set_gnome_env ("WAYLAND_DISPLAY", meta_wayland_get_wayland_display_name (compositor));
|
||||||
}
|
}
|
||||||
|
@ -31,6 +31,9 @@
|
|||||||
#include <glib.h>
|
#include <glib.h>
|
||||||
#include <sys/socket.h>
|
#include <sys/socket.h>
|
||||||
#include <sys/un.h>
|
#include <sys/un.h>
|
||||||
|
#include <sys/random.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <X11/Xauth.h>
|
||||||
|
|
||||||
#include "compositor/meta-surface-actor-wayland.h"
|
#include "compositor/meta-surface-actor-wayland.h"
|
||||||
#include "meta/main.h"
|
#include "meta/main.h"
|
||||||
@ -438,6 +441,75 @@ choose_xdisplay (MetaXWaylandManager *manager)
|
|||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
G_DEFINE_AUTOPTR_CLEANUP_FUNC (FILE, fclose)
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
prepare_auth_file (MetaXWaylandManager *manager)
|
||||||
|
{
|
||||||
|
Xauth auth_entry = { 0 };
|
||||||
|
g_autoptr (FILE) fp = NULL;
|
||||||
|
char hostname[HOST_NAME_MAX + 1];
|
||||||
|
char auth_data[16];
|
||||||
|
int fd;
|
||||||
|
|
||||||
|
manager->auth_file = g_build_filename (g_get_user_runtime_dir (),
|
||||||
|
".mutter-Xwaylandauth.XXXXXX",
|
||||||
|
NULL);
|
||||||
|
|
||||||
|
if (gethostname (hostname, HOST_NAME_MAX) < 0)
|
||||||
|
g_strlcpy (hostname, "localhost", HOST_NAME_MAX);
|
||||||
|
|
||||||
|
if (getrandom (auth_data, sizeof (auth_data), 0) != sizeof (auth_data))
|
||||||
|
{
|
||||||
|
g_warning ("Failed to get random data: %s", g_strerror (errno));
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
auth_entry.family = FamilyLocal;
|
||||||
|
auth_entry.address = hostname;
|
||||||
|
auth_entry.address_length = strlen (auth_entry.address);
|
||||||
|
auth_entry.name = (char *) "MIT-MAGIC-COOKIE-1";
|
||||||
|
auth_entry.name_length = strlen (auth_entry.name);
|
||||||
|
auth_entry.data = auth_data;
|
||||||
|
auth_entry.data_length = sizeof (auth_data);
|
||||||
|
|
||||||
|
fd = g_mkstemp (manager->auth_file);
|
||||||
|
if (fd < 0)
|
||||||
|
{
|
||||||
|
g_warning ("Failed to open Xauthority file: %s", g_strerror (errno));
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
fp = fdopen (fd, "w+");
|
||||||
|
if (!fp)
|
||||||
|
{
|
||||||
|
g_warning ("Failed to open Xauthority stream: %s", g_strerror (errno));
|
||||||
|
close (fd);
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!XauWriteAuth (fp, &auth_entry))
|
||||||
|
{
|
||||||
|
g_warning ("Error writing to Xauthority file: %s", g_strerror (errno));
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
auth_entry.family = FamilyWild;
|
||||||
|
if (!XauWriteAuth (fp, &auth_entry))
|
||||||
|
{
|
||||||
|
g_warning ("Error writing to Xauthority file: %s", g_strerror (errno));
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fflush (fp) == EOF)
|
||||||
|
{
|
||||||
|
g_warning ("Error writing to Xauthority file: %s", g_strerror (errno));
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
xserver_finished_init (MetaXWaylandManager *manager)
|
xserver_finished_init (MetaXWaylandManager *manager)
|
||||||
{
|
{
|
||||||
@ -512,6 +584,7 @@ meta_xwayland_init_xserver (MetaXWaylandManager *manager)
|
|||||||
"-noreset",
|
"-noreset",
|
||||||
"-accessx",
|
"-accessx",
|
||||||
"-core",
|
"-core",
|
||||||
|
"-auth", manager->auth_file,
|
||||||
"-listen", "4",
|
"-listen", "4",
|
||||||
"-listen", "5",
|
"-listen", "5",
|
||||||
"-displayfd", "6",
|
"-displayfd", "6",
|
||||||
@ -545,6 +618,9 @@ meta_xwayland_start (MetaXWaylandManager *manager,
|
|||||||
if (!choose_xdisplay (manager))
|
if (!choose_xdisplay (manager))
|
||||||
return FALSE;
|
return FALSE;
|
||||||
|
|
||||||
|
if (!prepare_auth_file (manager))
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
manager->wayland_display = wl_display;
|
manager->wayland_display = wl_display;
|
||||||
return meta_xwayland_init_xserver (manager);
|
return meta_xwayland_init_xserver (manager);
|
||||||
}
|
}
|
||||||
@ -584,6 +660,11 @@ meta_xwayland_stop (MetaXWaylandManager *manager)
|
|||||||
unlink (path);
|
unlink (path);
|
||||||
|
|
||||||
g_clear_pointer (&manager->display_name, g_free);
|
g_clear_pointer (&manager->display_name, g_free);
|
||||||
|
if (manager->auth_file)
|
||||||
|
{
|
||||||
|
unlink (manager->auth_file);
|
||||||
|
g_clear_pointer (&manager->auth_file, g_free);
|
||||||
|
}
|
||||||
if (manager->lock_file)
|
if (manager->lock_file)
|
||||||
{
|
{
|
||||||
unlink (manager->lock_file);
|
unlink (manager->lock_file);
|
||||||
|
Loading…
Reference in New Issue
Block a user