48dc8f4c68
- Re-disable int10 on arm
235 lines
7.2 KiB
Diff
235 lines
7.2 KiB
Diff
From 1e37681072a69decce7441e762cb5f4ce1a80d73 Mon Sep 17 00:00:00 2001
|
|
From: Giovanni Campagna <gcampagn@redhat.com>
|
|
Date: Wed, 21 Aug 2013 09:53:26 +0200
|
|
Subject: [PATCH 12/38] xwayland: handle global object destruction
|
|
|
|
Certain global objects, such as outputs, can be destroyed during
|
|
the session. We must handle that and not crash.
|
|
---
|
|
hw/xfree86/xwayland/xwayland-drm.c | 7 ++++++
|
|
hw/xfree86/xwayland/xwayland-input.c | 7 ++++++
|
|
hw/xfree86/xwayland/xwayland-output.c | 40 +++++++++++++++++++++++++++++++---
|
|
hw/xfree86/xwayland/xwayland-private.h | 6 ++++-
|
|
hw/xfree86/xwayland/xwayland.c | 17 +++++++++++----
|
|
5 files changed, 69 insertions(+), 8 deletions(-)
|
|
|
|
diff --git a/hw/xfree86/xwayland/xwayland-drm.c b/hw/xfree86/xwayland/xwayland-drm.c
|
|
index ce56e4c..6e4c778 100644
|
|
--- a/hw/xfree86/xwayland/xwayland-drm.c
|
|
+++ b/hw/xfree86/xwayland/xwayland-drm.c
|
|
@@ -119,8 +119,15 @@ drm_handler(void *data, struct wl_registry *registry, uint32_t id,
|
|
}
|
|
}
|
|
|
|
+static void
|
|
+global_remove(void *data, struct wl_registry *registry, uint32_t name)
|
|
+{
|
|
+ /* Nothing to do here, wl_drm should not be removed */
|
|
+}
|
|
+
|
|
static const struct wl_registry_listener drm_listener = {
|
|
drm_handler,
|
|
+ global_remove
|
|
};
|
|
|
|
int
|
|
diff --git a/hw/xfree86/xwayland/xwayland-input.c b/hw/xfree86/xwayland/xwayland-input.c
|
|
index 2f8e0c7..d031b34 100644
|
|
--- a/hw/xfree86/xwayland/xwayland-input.c
|
|
+++ b/hw/xfree86/xwayland/xwayland-input.c
|
|
@@ -597,8 +597,15 @@ input_handler(void *data, struct wl_registry *registry, uint32_t id,
|
|
}
|
|
}
|
|
|
|
+static void
|
|
+global_remove(void *data, struct wl_registry *registry, uint32_t name)
|
|
+{
|
|
+ /* FIXME */
|
|
+}
|
|
+
|
|
static const struct wl_registry_listener input_listener = {
|
|
input_handler,
|
|
+ global_remove,
|
|
};
|
|
|
|
void
|
|
diff --git a/hw/xfree86/xwayland/xwayland-output.c b/hw/xfree86/xwayland/xwayland-output.c
|
|
index 8f087f6..46238f4 100644
|
|
--- a/hw/xfree86/xwayland/xwayland-output.c
|
|
+++ b/hw/xfree86/xwayland/xwayland-output.c
|
|
@@ -95,6 +95,14 @@ crtc_shadow_destroy(xf86CrtcPtr crtc, PixmapPtr rotate_pixmap, void *data)
|
|
{
|
|
}
|
|
|
|
+static void
|
|
+crtc_destroy(xf86CrtcPtr crtc)
|
|
+{
|
|
+ /* Nothing to do here, we only destroy CRTCs when instructed to do
|
|
+ so by wl_output changes
|
|
+ */
|
|
+}
|
|
+
|
|
static const xf86CrtcFuncsRec crtc_funcs = {
|
|
.dpms = crtc_dpms,
|
|
.set_mode_major = crtc_set_mode_major,
|
|
@@ -106,7 +114,7 @@ static const xf86CrtcFuncsRec crtc_funcs = {
|
|
.shadow_create = crtc_shadow_create,
|
|
.shadow_allocate = crtc_shadow_allocate,
|
|
.shadow_destroy = crtc_shadow_destroy,
|
|
- .destroy = NULL, /* XXX */
|
|
+ .destroy = crtc_destroy,
|
|
};
|
|
|
|
static void
|
|
@@ -246,7 +254,7 @@ display_handle_geometry(void *data, struct wl_output *wl_output, int x, int y,
|
|
xwl_output->x = x;
|
|
xwl_output->y = y;
|
|
|
|
- xwl_screen->xwl_output = xwl_output;
|
|
+ xorg_list_append (&xwl_output->link, &xwl_screen->output_list);
|
|
}
|
|
|
|
static void
|
|
@@ -277,13 +285,39 @@ global_handler(void *data, struct wl_registry *registry, uint32_t id,
|
|
xwl_output = xwl_output_create(xwl_screen);
|
|
xwl_output->output = wl_registry_bind(registry, id,
|
|
&wl_output_interface, 1);
|
|
+ xwl_output->name = id;
|
|
wl_output_add_listener(xwl_output->output,
|
|
&output_listener, xwl_output);
|
|
}
|
|
}
|
|
|
|
+void
|
|
+xwl_output_remove(struct xwl_output *xwl_output)
|
|
+{
|
|
+ xorg_list_del (&xwl_output->link);
|
|
+ xf86OutputDestroy (xwl_output->xf86output);
|
|
+ xf86CrtcDestroy (xwl_output->xf86crtc);
|
|
+
|
|
+ wl_output_destroy (xwl_output->output);
|
|
+}
|
|
+
|
|
+static void
|
|
+global_remove(void *data, struct wl_registry *registry, uint32_t name)
|
|
+{
|
|
+ struct xwl_screen *xwl_screen = data;
|
|
+ struct xwl_output *xwl_output, *tmp;
|
|
+
|
|
+ xorg_list_for_each_entry_safe (xwl_output, tmp, &xwl_screen->output_list, link) {
|
|
+ if (xwl_output->name == name) {
|
|
+ xwl_output_remove(xwl_output);
|
|
+ break;
|
|
+ }
|
|
+ }
|
|
+}
|
|
+
|
|
static const struct wl_registry_listener global_listener = {
|
|
global_handler,
|
|
+ global_remove
|
|
};
|
|
|
|
void
|
|
@@ -299,7 +333,7 @@ xwayland_screen_preinit_output(struct xwl_screen *xwl_screen, ScrnInfoPtr scrnin
|
|
wl_registry_add_listener(xwl_screen->output_registry, &global_listener,
|
|
xwl_screen);
|
|
|
|
- while (!xwl_screen->xwl_output) {
|
|
+ while (xwl_screen->output_list.next == &xwl_screen->output_list) {
|
|
ret = wl_display_roundtrip(xwl_screen->display);
|
|
if (ret == -1)
|
|
FatalError("failed to dispatch Wayland events: %s\n", strerror(errno));
|
|
diff --git a/hw/xfree86/xwayland/xwayland-private.h b/hw/xfree86/xwayland/xwayland-private.h
|
|
index e427316..7005db2 100644
|
|
--- a/hw/xfree86/xwayland/xwayland-private.h
|
|
+++ b/hw/xfree86/xwayland/xwayland-private.h
|
|
@@ -44,7 +44,6 @@ struct xwl_screen {
|
|
ScrnInfoPtr scrninfo;
|
|
int drm_fd;
|
|
int wayland_fd;
|
|
- struct xwl_output *xwl_output;
|
|
struct wl_display *display;
|
|
struct wl_registry *registry;
|
|
struct wl_registry *drm_registry;
|
|
@@ -58,6 +57,7 @@ struct xwl_screen {
|
|
uint32_t flags;
|
|
char *device_name;
|
|
uint32_t authenticated;
|
|
+ struct xorg_list output_list;
|
|
struct xorg_list seat_list;
|
|
struct xorg_list damage_window_list;
|
|
struct xorg_list window_list;
|
|
@@ -74,12 +74,14 @@ struct xwl_screen {
|
|
};
|
|
|
|
struct xwl_output {
|
|
+ struct xorg_list link;
|
|
struct wl_output *output;
|
|
struct xwl_screen *xwl_screen;
|
|
int32_t x, y, width, height;
|
|
xf86Monitor xf86monitor;
|
|
xf86OutputPtr xf86output;
|
|
xf86CrtcPtr xf86crtc;
|
|
+ int32_t name;
|
|
};
|
|
|
|
|
|
@@ -127,6 +129,8 @@ Bool xwl_drm_initialised(struct xwl_screen *screen);
|
|
|
|
void xwl_seat_set_cursor(struct xwl_seat *xwl_seat);
|
|
|
|
+void xwl_output_remove(struct xwl_output *output);
|
|
+
|
|
extern const struct xserver_listener xwl_server_listener;
|
|
|
|
#endif /* _XWAYLAND_PRIVATE_H_ */
|
|
diff --git a/hw/xfree86/xwayland/xwayland.c b/hw/xfree86/xwayland/xwayland.c
|
|
index 880b7ec..2047a85 100644
|
|
--- a/hw/xfree86/xwayland/xwayland.c
|
|
+++ b/hw/xfree86/xwayland/xwayland.c
|
|
@@ -103,8 +103,15 @@ registry_global(void *data, struct wl_registry *registry, uint32_t id,
|
|
}
|
|
}
|
|
|
|
+static void
|
|
+global_remove(void *data, struct wl_registry *registry, uint32_t name)
|
|
+{
|
|
+ /* Nothing to do here, wl_compositor and wl_shm should not be removed */
|
|
+}
|
|
+
|
|
static const struct wl_registry_listener registry_listener = {
|
|
registry_global,
|
|
+ global_remove
|
|
};
|
|
|
|
static void
|
|
@@ -230,6 +237,7 @@ xwl_screen_pre_init(ScrnInfoPtr scrninfo, struct xwl_screen *xwl_screen,
|
|
return FALSE;
|
|
}
|
|
|
|
+ xorg_list_init(&xwl_screen->output_list);
|
|
xorg_list_init(&xwl_screen->seat_list);
|
|
xorg_list_init(&xwl_screen->damage_window_list);
|
|
xorg_list_init(&xwl_screen->window_list);
|
|
@@ -318,12 +326,13 @@ void xwl_screen_close(struct xwl_screen *xwl_screen)
|
|
|
|
void xwl_screen_destroy(struct xwl_screen *xwl_screen)
|
|
{
|
|
- if (xwl_screen->xwl_output) {
|
|
- xf86OutputDestroy(xwl_screen->xwl_output->xf86output);
|
|
- xf86CrtcDestroy(xwl_screen->xwl_output->xf86crtc);
|
|
+ struct xwl_output *xwl_output, *tmp;
|
|
+
|
|
+ xorg_list_for_each_entry_safe (xwl_output, tmp, &xwl_screen->output_list, link) {
|
|
+ xwl_output_remove(xwl_output);
|
|
+ break;
|
|
}
|
|
|
|
- free(xwl_screen->xwl_output);
|
|
free(xwl_screen);
|
|
}
|
|
|
|
--
|
|
1.8.4.2
|
|
|