Commit b6705274 authored by Michel Dänzer's avatar Michel Dänzer Committed by Michel Dänzer
Browse files

xwayland: Free all remaining events in xwl_present_cleanup



These events aren't reachable after xwl_present_cleanup, so they're
leaked if we don't free them first.

This requires storing the pixmap pointer in struct xwl_present_window.
Luckily, the buffer pointer isn't used for anything, so just replace
that.

v2:
* Bump pixmap reference count in xwl_present_flip and drop it in
  xwl_present_free_event, fixes use-after-free in the latter due to the
  pixmap already being destroyed.
Reviewed-by: default avatarDave Airlie <airlied@redhat.com>
parent 1beffba6
Pipeline #167512 passed with stages
in 4 minutes and 33 seconds
......@@ -120,6 +120,16 @@ xwl_present_reset_timer(struct xwl_present_window *xwl_present_window)
static void
xwl_present_free_event(struct xwl_present_event *event)
{
if (!event)
return;
if (event->pixmap) {
if (!event->buffer_released)
xwl_pixmap_del_buffer_release_cb(event->pixmap);
dixDestroyPixmap(event->pixmap, event->pixmap->drawable.id);
}
xorg_list_del(&event->list);
free(event);
}
......@@ -144,21 +154,10 @@ xwl_present_cleanup(WindowPtr window)
xorg_list_for_each_entry_safe(event, tmp, &xwl_present_window->event_list, list)
xwl_present_free_event(event);
/* Clear remaining buffer releases and inform Present about free ressources */
event = xwl_present_window->sync_flip;
xwl_present_window->sync_flip = NULL;
if (event) {
if (event->buffer_released) {
xwl_present_free_event(event);
} else {
event->pending = FALSE;
event->abort = TRUE;
}
}
xorg_list_for_each_entry_safe(event, tmp, &xwl_present_window->release_queue, list) {
xorg_list_del(&event->list);
event->abort = TRUE;
}
xwl_present_free_event(xwl_present_window->sync_flip);
xorg_list_for_each_entry_safe(event, tmp, &xwl_present_window->release_queue, list)
xwl_present_free_event(event);
/* Clear timer */
xwl_present_free_timer(xwl_present_window);
......@@ -356,6 +355,7 @@ xwl_present_queue_vblank(WindowPtr present_window,
return BadAlloc;
event->event_id = event_id;
event->pixmap = NULL;
event->xwl_present_window = xwl_present_window;
event->target_msc = msc;
......@@ -459,11 +459,12 @@ xwl_present_flip(WindowPtr present_window,
if (!event)
return FALSE;
pixmap->refcnt++;
buffer = xwl_glamor_pixmap_get_wl_buffer(pixmap, NULL);
event->event_id = event_id;
event->xwl_present_window = xwl_present_window;
event->buffer = buffer;
event->pixmap = pixmap;
event->target_msc = target_msc;
event->pending = TRUE;
event->abort = FALSE;
......
......@@ -59,7 +59,7 @@ struct xwl_present_event {
Bool buffer_released;
struct xwl_present_window *xwl_present_window;
struct wl_buffer *buffer;
PixmapPtr pixmap;
struct xorg_list list;
};
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment