Skip to content
Snippets Groups Projects

Compare revisions

Changes are shown as if the source revision was being merged into the target revision. Learn more about comparing revisions.

Source

Select target project
No results found

Target

Select target project
  • chengbo7135/xserver
  • wjp/xserver
  • DemiMarie/xserver
  • alanc/xserver
  • uvas/xserver
  • cl91/xserver
  • heymiaoO/xserver
  • oreaus/xserver
  • stapelberg/xserver
  • PaulKocialkowski/xserver
  • CendioOssman/xserver
  • wiz/xserver
  • maos20008/xserver
  • dougvj/xserver
  • mgorse1/xserver
  • gldrk/xserver
  • TMR5454/xserver
  • Kyawswat/xserver
  • hexiaodong/xserver
  • gilvbp/xserver
  • vliaskov/xserver
  • aarondill/xserver
  • zzyiwei/xserver
  • kleinerm/xserver
  • jcherry/xserver
  • jcristau/xserver
  • nathankidd/xserver
  • jexposit/xserver
  • refi_64/xserver
  • kbrenneman/xserver
  • kupper.pa/xserver
  • LickmeDown/xserver
  • zboszor/xserver
  • jadahl/xserver
  • shadeslayer/xserver
  • mherrb/xserver
  • Julia/xserver
  • twaik/xserver
  • fvalasiad/xserver
  • zzxyb/xserver
  • HermannSW/xserver
  • erwinou/xserver
  • ekurzinger/xserver
  • nacho.resa/xserver
  • agoins/xserver
  • NSUTanghaixiang/xserver
  • p12tic/xserver
  • huxd1532/xserver
  • keithp/xserver
  • vinilokorlok/xserver
  • bbeckett/xserver
  • dslater38/xserver
  • zzag/xserver
  • emersion/xserver
  • djlucas/xserver
  • ccullumbine2018/xserver
  • daniels/xserver
  • llandwerlin/xserver
  • matt335672/xserver
  • doraskayo/xserver
  • afett/xserver
  • XDXTHX/xserver
  • xexaxo/xserver
  • ecurtin/xserver
  • rbernon/xserver
  • pekdon/xserver
  • karolherbst/xserver
  • russellcnv/xserver
  • mbiebl/xserver
  • orbea/xserver
  • vsyrjala/xserver
  • lyudess/xserver
  • manu/xserver
  • lucmann/xserver
  • tholin/xserver
  • yarivb/xserver
  • tmlind/xserver
  • chema/xserver
  • J-Bu/xserver
  • chenhuacai/xserver
  • E5ten/xserver
  • haagch/xserver
  • whot/xserver
  • strassek/xserver
  • mntmn/xserver
  • liyi42/xserver
  • YusufKhan-gamedev/xserver
  • iv-m/xserver
  • vanvugt/xserver
  • Rui511/xserver
  • catap/xserver
  • tjbp/xserver
  • webi123/xserver
  • noblock/xserver
  • freemangordon/xserver
  • xdandys/xserver
  • jbeich/xserver
  • zeising/xserver
  • romangg/xserver
  • pq/xserver
  • azhadchenko/xserver
  • Emantor/xserver
  • carlosg/xserver
  • kwg/xserver
  • pichika/xserver
  • klniu/xserver
  • TAAPArthur/xserver
  • sjoerd/xserver
  • Sjecai2/xserver
  • jturney/xserver
  • pkubaj/xserver
  • os369510/xserver
  • Zamundaaa/xserver
  • Gorg/xserver
  • lkundrak/xserver
  • niveditharau/xserver
  • ForTheReallys/xserver
  • jmonteiro/xserver
  • jocelyn/xserver
  • ThatMG393/xserver
  • fweimer/xserver
  • mlankhorst/xserver
  • marv/xserver
  • dbn/xserver
  • mattrope/xserver
  • coypoop/xserver
  • mwyraz/xserver
  • frog/xserver
  • 3v1n0/xserver
  • awilfox/xserver
  • muesli4/xserver
  • rarbab/xserver
  • yshui/xserver
  • jannau/xserver
  • mikeroyal/xserver
  • andrebsguedes/xserver
  • JeffyCN/xserver
  • ipominov/xserver
  • gtrentalancia/xserver
  • josch/xserver
  • lucyllewy/xserver
  • tomty89/xserver
  • qarmin/xserver
  • tagr/xserver
  • zwenna/xserver
  • bkylerussell/xserver
  • mupuf/xserver
  • zubzub/xserver
  • galaxytgtabiday/xserver
  • OlCe/xserver
  • ashafer/xserver
  • dengbo/xserver
  • valpackett/xserver
  • andreyknyazev077/xserver
  • antonovitch/xserver
  • contactshashanksharma/xserver-fork-shashank
  • akihiko.odaki/xserver
  • sknsean/xserver
  • rnpnr/xserver
  • hitong602/xserver
  • halfline/xserver
  • ismailsiege/xserver
  • dongwonk/xserver
  • Fatton1/xserver
  • GermanAizek/xserver
  • daenzer/xserver
  • FeepingCreature/xserver
  • mvlad/xserver
  • puleglot/xserver
  • smelenius/xserver
  • sewn/xserver
  • kaichuan.hsieh/xserver
  • SimonPilkington/xserver
  • adamdruppe/xserver
  • floppym/xserver
  • trevdave/xserver
  • luke-jr/xserver
  • headrush/xserver
  • davidriley/xserver
  • heitbaum/xserver
  • mrisaacb/xserver
  • goosen78/xserver
  • Ma/xserver
  • gmbr3/xserver
  • tsutsui/xserver
  • sherrodejjohnson/xserver
  • hassoon1986/xserver
  • lanodan/xserver
  • ydc-dadada/xserver
  • wengxt/xserver
  • icenowy/xserver
  • denisfa/xserver
  • StarsGreen/xserver
  • adamjrichter/xserver
  • bigon/xserver
  • djacewicz/xserver
  • davidre/xserver
  • kylin0061/xserver
  • arrowd/xserver
  • ernstp/xserver
  • bbrezillon/xserver
  • penguin42/xserver
  • anarsoul/xserver
  • marvinjr35/xserver
  • gerddie/xserver
  • xry111/xserver
  • psyruss85/xserver
  • volkanorhan/xserver
  • luporl/xserver
  • cbur201592/xserver
  • bphaslett/xserver
  • guillem/xserver
  • haihao/xserver
  • peterh/xserver
  • miztake/xserver
  • zaps166/xserver
  • lostgoat/xserver
  • vfjpl/xserver
  • bentiss/xserver
  • rilian-la-te/xserver
  • wujiangGitHub/xserver
  • cubanismo/xserver
  • arichardson/xserver
  • schreibemirhalt/xserver
  • jsg/xserver
  • karlosrangel337/xserver
  • knisht/xserver
  • manuelcrack642/xserver
  • ross/xserver
  • topimiettinen/xserver
  • davidedmundson/xserver
  • DPA/xserver
  • dkorkmazturk/xserver
  • karamjameelmoore/xserver
  • lihongtao/xserver
  • sthibaul/xserver
  • RyzenDew/xserver
  • christian-rauch/xserver
  • Vivek/xserver
  • peigongdsd/xserver
  • peng.jin/xserver
  • alagner/xserver
  • mehdigh419/xserver
  • dixler/xserver
  • BBaoVanC/xserver
  • Drakulix/xserver
  • Acidburn0zzz/xserver
  • bafanahub/xserver
  • benpicco/xserver
  • yangxiaojuan-loongson/xserver
  • kaocher82/xserver
  • pepp/xserver
  • cgzones/xserver
  • luyn/xserver
  • 1740301466jxz/xserver
  • ids1024/xserver
  • svalaskevicius/xserver
  • ZhiJie.Zhang/xserver
  • metux/xserver
  • eschwartz/xserver
  • jayantpranjal0/xserver
  • hmazlan/xserver
  • kerneltoast/xserver
  • Michaelypk/xserver
  • dottedmag/xserver
  • aplattner/xserver
  • sergiomb/xserver
  • looi/xserver
  • robclark/xserver
  • tzimmermann/xserver
  • vitoux.pascal/xserver
  • aditj/xserver
  • kennylevinsen/xserver
  • Kishore409/xserver
  • Daasin/xserver
  • dirbaio/xserver
  • xinbowang/xserver
  • mwei/xserver
  • SpikyCaterpillar1/xserver
  • devin11911191/xserver
  • xorg/xserver
  • alex-tu-cc/xserver
  • kaniini/xserver
  • jcourreges/xserver
  • n3rdopolis/xserver
  • zagursky/xserver
  • thesamesam/xserver
  • anholt/xserver
  • themaister/xserver
  • jrtc27/xserver
  • JoseExposito/xserver
  • Hi-Angel/xserver
  • City-busz/xserver
  • ydirson/xserver
  • dawnhan/xserver
  • avolkov/xserver
  • meMuszr/xserver
  • dk/xserver
  • cooperch/xserver
  • Tuetuopay/xserver
  • gabifalk/xserver
  • jeremyhu/xserver
  • 1480c1/xserver
  • Spintzyk/xserver
  • MisterDA/xserver
  • starnight/xserver
  • abono/xserver
  • ajax/xserver
  • dougg3/xserver
  • chenx_dust/xserver
  • EXtremeExploit/xserver
  • jwrdegoede/xserver
  • road2react/xserver
  • acelan/xserver
  • airlied/xserver
  • gfxstrand/xorg-xserver
  • justazarsky/xserver
  • sri-ka1ki/xserver
  • rgfernandes/xserver
  • lynxeye/xserver
  • tintou/xserver
  • mattst88/xserver
  • rmader/xserver
  • linkmauve/xserver
  • kamarul6401/xserver
  • andy-zetier/xserver
  • gsittyz/xserver
  • bernhardu/xserver
  • causztic/xserver
  • cpmichael/modesetting
  • ryanneph/xserver
  • zhangyaning/xserver
  • olv/xserver
  • hongaoo/xserver
  • LiChenG-P/xserver
  • Ivaniku/x-taylan
  • dkg/xserver
  • ofourdan/xserver
  • mahkoh/xserver
  • AkiSakurai/xserver
  • msizanoen1/xserver
341 results
Show changes
Commits on Source (12)
  • Olivier Fourdan's avatar
    xwayland/window-buffers: Promote xwl_window_buffer · 0e0472a0
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    Make the (opaque) definition of the xwl_window_buffer generally
    available.
    
    No functional change.
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1571>
    0e0472a0
  • Olivier Fourdan's avatar
    xwayland/window-buffers: Add xwl_window_buffer_release() · b5082073
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    We want to decorrelate the explicit buffer synchronization from the
    window buffers, and move that to the GLAMOR/GBM code instead.
    
    To do that, we need to be able to invoke the xwl_window_buffer's
    release_callback() routine from outside the window buffer code.
    
    For that purpose, introduce xwl_window_buffer_release() which calls
    xwl_window_buffer_release_callback() for us.
    
    This is preparation work for the following changes, no functional change
    intended at this point.
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1571>
    b5082073
  • Olivier Fourdan's avatar
    xwayland/glamor/gbm: Copy explicit sync code to GLAMOR/GBM · cc021aca
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    Copy the code to deal with synchronization objects from the window
    buffers to the GLAMOR/GBM code.
    
    The idea is to deal with synchronizations for all pixmaps, even when
    there is no window buffer involved.
    
    This is still preparation work for the following commits, no functional
    change intended at this point.
    
    v2: Use a "xwl_window_buffer *" instead of a "void *data" (Michel)
    v3: Bail early if there's no xwl_window_buffer (Michel)
    v4: Rename xwl_window_submit_pixmap() to
        xwl_glamor_gbm_wait_release_fence() (Michel)
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <!1571>
    cc021aca
  • Olivier Fourdan's avatar
    xwayland/window-buffers: Use synchronization from GLAMOR/GBM · 256cef8b
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    Now that we have the buffer synchronization implemented in the
    GLAMOR/GBM code, switch to use that code.
    
    At this point, there is still not functional change intended, this is
    still preparation work for a fix that is still to come.
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1571>
    256cef8b
  • Olivier Fourdan's avatar
    xwayland/window-buffers: Do not always set syncpnts · aab01c73
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    The function xwl_window_swap_pixmap() can be called from two places,
    either from xwl_window_attach_buffer() or from damage_report().
    
    When called from xwl_window_attach_buffer(), the new buffer is attached
    and the surface committed.
    
    However, when called from damage_report(), a new buffer might not be
    attached before the surface is committed.
    
    That's fine with implicit synchronization, but if we use explicit
    synchronization, committing a surface without a new buffer attached but
    with a release timeline point set is a protocol error:
    
    | If at surface commit time there is a pending release timeline point
    | set but no pending buffer attached, a no_buffer error is raised.
    
    To avoid such an issue, add a new parameter to xwl_window_swap_pixmap()
    to hint whether it should set the synchronization points, and have the
    synchronization points set only from xwl_window_attach_buffer().
    
    v2: Rename param to handle_sync (Michel)
    
    Suggested-by: default avatarMichel Dänzer <mdaenzer@redhat.com>
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1571>
    aab01c73
  • Olivier Fourdan's avatar
    xwayland/window-buffers: Move code to submit pixmaps · 33330f0d
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    Move the code which takes care of submitting pixmaps and the
    synchronization points to its own function.
    
    This will allow to reuse that code from different code path.
    
    No functional change intended.
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1571>
    33330f0d
  • Olivier Fourdan's avatar
    xwayland/window-buffers: Set syncpnts for all pixmaps · bc9bf563
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    The wp_linux_drm_syncobj_v1 protocol states that :
    
    | If at surface commit time there is a pending buffer attached but no
    | pending release timeline point set, the no_release_point protocol
    | error is raised.
    
    So we need to set a release timeline point in any case from the swap
    pixmap routine, even for the early out code paths.
    
    Failing to do so may cause a Wayland protocol error that is fatal to the
    Wayland client, in this case Xwayland:
    
    | wp_linux_drm_syncobj_surface_v1: error 4: No Acquire point provided
    | (EE) failed to dispatch Wayland events: Protocol error
    
    Closes: xorg/xserver#1688
    
    
    Fixes: 87bf2caf - xwayland: add support for wp_linux_drm_syncobj_v1
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1571>
    bc9bf563
  • Olivier Fourdan's avatar
    xwayland: Move xwl_window disposal to its own function · 74be7a7f
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    No functional change intended, this is just preparation work for the
    next commit.
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1589>
    74be7a7f
  • Olivier Fourdan's avatar
    xwayland: Make sure we do not leak xwl_window on destroy · 0e1a98f5
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    Right now, we would dispose the xwl_window and all the data associated
    with it on unrealize.
    
    But not all window destruction go through the unrealize code path, for
    example when the root window (running rootful) is destroyed from the
    resource manager on server reset, we do not get to the unrealize window
    step, but straight to destroy window.
    
    As a result, we are leaking the xwl_window and all the data associated
    with it, for example:
    
    | 65,536 bytes in 1 blocks are possibly lost in loss record 12,462 of 12,488
    |    at 0x484A0FC: calloc (vg_replace_malloc.c:1675)
    |    by 0x48B661C: UnknownInlinedFun (pixman-bits-image.c:1273)
    |    by 0x48B661C: _pixman_bits_image_init (pixman-bits-image.c:1296)
    |    by 0x48B6754: create_bits_image_internal (pixman-bits-image.c:1349)
    |    by 0x64180DE: UnknownInlinedFun (cairo-image-surface.c:380)
    |    by 0x64180DE: UnknownInlinedFun (cairo-image-surface.c:366)
    |    by 0x64180DE: cairo_image_surface_create (cairo-image-surface.c:432)
    |    by 0x6346B44: UnknownInlinedFun (libdecor-gtk.c:467)
    |    by 0x6346B44: libdecor_plugin_gtk_frame_new (libdecor-gtk.c:546)
    |    by 0x4B7F297: libdecor_decorate (libdecor.c:559)
    |    by 0x42C6F3: xwl_create_root_surface (xwayland-window.c:1266)
    |    by 0x42CD97: ensure_surface_for_window (xwayland-window.c:1466)
    |    by 0x42D0D1: xwl_realize_window (xwayland-window.c:1560)
    |    by 0x50858F: compRealizeWindow (compwindow.c:279)
    |    by 0x4FF2A2: MapWindow (window.c:2706)
    |    by 0x4F9E7F: InitRootWindow (window.c:697)
    
    To avoid that issue, check whether there is still an xwl_window
    associated with the X11 window on destroy, and if that's the case,
    dispose the xwl_window.
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1589>
    0e1a98f5
  • Olivier Fourdan's avatar
    xwayland/window-buffers: Move buffer disposal to its own function · 571cb133
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    No functional change, this is just preparation work for the next commit.
    
    v2: Reshuffle functions (Michel)
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1589>
    571cb133
  • Olivier Fourdan's avatar
    xwayland/window-buffers: optionally force disposal · fa04e15a
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    For cases (to come) where we would want to force the disposal of the
    window buffers, add a parameter to force the disposal by calling
    dispose() directly instead of maybe_dispose().
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Part-of: <xorg/xserver!1589>
    fa04e15a
  • Olivier Fourdan's avatar
    xwayland: Force disposal of windows buffers for root on destroy · a5e86396
    Olivier Fourdan authored and Marge Bot's avatar Marge Bot committed
    
    With explicit buffer synchronization in use, the window buffers use a
    file descriptor for event notification to keep the buffer alive for
    synchronization purpose.
    
    When running rootful, the root window (which is visible) is destroyed
    directly from the resource manager on server reset, and the window
    buffer's eventfd will trigger after the window is destroyed, leading to
    a use after free and a crash of the xserver.
    
    To avoid the issue, check whether the window being destroyed is the root
    window in rootless mode, and make sure to force the disposal of the
    window buffers in that case.
    
    Signed-off-by: default avatarOlivier Fourdan <ofourdan@redhat.com>
    Closes: #1699
    Part-of: <!1589>
    a5e86396
......@@ -752,7 +752,7 @@ xwl_window_dmabuf_feedback_done(void *data,
/* If the linux-dmabuf v4 per-surface feedback changed, make sure the
* window buffers get re-created with appropriate parameters.
*/
xwl_window_buffers_dispose(xwl_window);
xwl_window_buffers_dispose(xwl_window, FALSE);
xwl_window_realloc_pixmap(xwl_window);
}
......
......@@ -32,6 +32,8 @@
#include <fcntl.h>
#include <errno.h>
#include <poll.h>
#include <sys/eventfd.h>
#include <sys/stat.h>
#include <xf86drm.h>
#include <drm_fourcc.h>
......@@ -55,6 +57,7 @@
#include "xwayland-glamor-gbm.h"
#include "xwayland-pixmap.h"
#include "xwayland-screen.h"
#include "xwayland-window-buffers.h"
#include "linux-dmabuf-unstable-v1-client-protocol.h"
#include "linux-drm-syncobj-v1-client-protocol.h"
......@@ -82,6 +85,12 @@ struct xwl_pixmap {
unsigned int texture;
struct gbm_bo *bo;
Bool implicit_modifier;
#ifdef DRI3
struct dri3_syncobj *syncobj;
uint64_t timeline_point;
int efd;
struct xwl_window_buffer *xwl_window_buffer;
#endif /* DRI3 */
};
static DevPrivateKeyRec xwl_gbm_private_key;
......@@ -225,6 +234,9 @@ xwl_glamor_gbm_create_pixmap_for_bo(ScreenPtr screen, struct gbm_bo *bo,
xwl_pixmap->bo = bo;
xwl_pixmap->buffer = NULL;
xwl_pixmap->implicit_modifier = implicit_modifier;
#ifdef XWL_HAS_GLAMOR
xwl_pixmap->efd = -1;
#endif /* XWL_HAS_GLAMOR */
#ifdef GBM_BO_FD_FOR_PLANE
if (xwl_gbm->dmabuf_capable) {
......@@ -445,6 +457,7 @@ xwl_glamor_gbm_destroy_pixmap(PixmapPtr pixmap)
eglDestroyImageKHR(xwl_screen->egl_display, xwl_pixmap->image);
if (xwl_pixmap->bo)
gbm_bo_destroy(xwl_pixmap->bo);
xwl_glamor_gbm_dispose_syncpts(pixmap);
free(xwl_pixmap);
}
......@@ -1388,6 +1401,21 @@ xwl_glamor_gbm_has_egl_extension(void)
epoxy_has_egl_extension(NULL, "EGL_KHR_platform_gbm"));
}
#ifdef DRI3
static void
xwl_glamor_gbm_release_fence_avail(int fd, int xevents, void *data)
{
struct xwl_pixmap *xwl_pixmap = data;
struct xwl_window_buffer *xwl_window_buffer = xwl_pixmap->xwl_window_buffer;
SetNotifyFd(fd, NULL, 0, NULL);
close(fd);
xwl_pixmap->efd = -1;
xwl_window_buffer_release(xwl_window_buffer);
}
#endif /* DRI3 */
Bool
xwl_glamor_supports_implicit_sync(struct xwl_screen *xwl_screen)
{
......@@ -1403,6 +1431,122 @@ xwl_glamor_supports_syncobjs(struct xwl_screen *xwl_screen)
xwl_gbm_get(xwl_screen)->supports_syncobjs;
}
Bool
xwl_glamor_gbm_set_syncpts(struct xwl_window *xwl_window, PixmapPtr pixmap)
{
#ifdef DRI3
struct xwl_screen *xwl_screen = xwl_window->xwl_screen;
struct xwl_pixmap *xwl_pixmap = xwl_pixmap_get(pixmap);
uint64_t acquire_point;
uint64_t release_point;
int fence_fd;
if (!xwl_screen->glamor)
return FALSE;
if (!xwl_pixmap) {
ErrorF("XWAYLAND: Failed to set synchronization point, no backing xwl_pixmap!\n");
return FALSE;
}
acquire_point = ++xwl_pixmap->timeline_point;
release_point = ++xwl_pixmap->timeline_point;
if (!xwl_pixmap->syncobj) {
struct dri3_syncobj *syncobj = xwl_glamor_dri3_syncobj_create(xwl_screen);
if (!syncobj)
goto fail;
xwl_pixmap->syncobj = syncobj;
}
fence_fd = xwl_glamor_get_fence(xwl_screen);
if (fence_fd >= 0)
xwl_pixmap->syncobj->import_fence(xwl_pixmap->syncobj, acquire_point, fence_fd);
else
goto fail;
xwl_glamor_dri3_syncobj_passthrough(xwl_window,
xwl_pixmap->syncobj,
xwl_pixmap->syncobj,
acquire_point,
release_point);
return TRUE;
fail:
/* can't use explicit sync, we will do a glFinish() before presenting */
if (xwl_pixmap->syncobj) {
xwl_pixmap->syncobj->free(xwl_pixmap->syncobj);
xwl_pixmap->syncobj = NULL;
}
#endif /* DRI3 */
return FALSE;
}
void
xwl_glamor_gbm_dispose_syncpts(PixmapPtr pixmap)
{
#ifdef DRI3
struct xwl_pixmap *xwl_pixmap = xwl_pixmap_get(pixmap);
struct xwl_screen *xwl_screen = xwl_screen_get(pixmap->drawable.pScreen);
if (!xwl_screen->glamor || !xwl_pixmap)
return;
if (xwl_pixmap->syncobj) {
xwl_pixmap->syncobj->free(xwl_pixmap->syncobj);
xwl_pixmap->syncobj = NULL;
}
if (xwl_pixmap->efd >= 0) {
SetNotifyFd(xwl_pixmap->efd, NULL, 0, NULL);
close(xwl_pixmap->efd);
}
#endif /* DRI3 */
}
void
xwl_glamor_gbm_wait_syncpts(PixmapPtr pixmap)
{
#ifdef DRI3
struct xwl_screen *xwl_screen = xwl_screen_get(pixmap->drawable.pScreen);
struct xwl_pixmap *xwl_pixmap = xwl_pixmap_get(pixmap);
int fence_fd;
if (!xwl_screen->glamor || !xwl_pixmap)
return;
if (xwl_pixmap->syncobj) {
fence_fd = xwl_pixmap->syncobj->export_fence(xwl_pixmap->syncobj,
xwl_pixmap->timeline_point);
xwl_glamor_wait_fence(xwl_screen, fence_fd);
close(fence_fd);
}
#endif /* DRI3 */
}
void
xwl_glamor_gbm_wait_release_fence(struct xwl_window *xwl_window,
PixmapPtr pixmap,
struct xwl_window_buffer *xwl_window_buffer)
{
#ifdef DRI3
struct xwl_pixmap *xwl_pixmap = xwl_pixmap_get(pixmap);
struct xwl_screen *xwl_screen = xwl_screen_get(pixmap->drawable.pScreen);
if (!xwl_screen->glamor || !xwl_pixmap || !xwl_window_buffer)
return;
xwl_pixmap->xwl_window_buffer = xwl_window_buffer;
/* wait until the release fence is available before re-using this buffer */
xwl_pixmap->efd = eventfd(0, EFD_CLOEXEC);
SetNotifyFd(xwl_pixmap->efd, xwl_glamor_gbm_release_fence_avail, X_NOTIFY_READ,
xwl_pixmap);
xwl_pixmap->syncobj->submitted_eventfd(xwl_pixmap->syncobj,
xwl_pixmap->timeline_point,
xwl_pixmap->efd);
#endif /* DRI3 */
}
static Bool
xwl_glamor_try_to_make_context_current(struct xwl_screen *xwl_screen)
{
......
......@@ -42,4 +42,12 @@ Bool xwl_glamor_gbm_init_egl(struct xwl_screen *xwl_screen);
Bool xwl_glamor_gbm_init_screen(struct xwl_screen *xwl_screen);
drmDevice *xwl_gbm_get_main_device(struct xwl_screen *xwl_screen);
/* Explicit buffer synchronization points */
Bool xwl_glamor_gbm_set_syncpts(struct xwl_window *xwl_window, PixmapPtr pixmap);
void xwl_glamor_gbm_dispose_syncpts(PixmapPtr pixmap);
void xwl_glamor_gbm_wait_syncpts(PixmapPtr pixmap);
void xwl_glamor_gbm_wait_release_fence(struct xwl_window *xwl_window,
PixmapPtr pixmap,
struct xwl_window_buffer *xwl_window_buffer);
#endif /* XWAYLAND_GLAMOR_GBM_H */
......@@ -31,5 +31,6 @@ struct xwl_window;
struct xwl_screen;
struct xwl_drm_lease;
struct xwl_output;
struct xwl_window_buffer;
#endif /* XWAYLAND_TYPES_H */
......@@ -31,6 +31,7 @@
#include "xwayland-window.h"
#include "xwayland-pixmap.h"
#include "xwayland-screen.h"
#include "xwayland-glamor-gbm.h"
#include "xwayland-window-buffers.h"
#ifdef XWL_HAS_GLAMOR
#include "glamor.h"
......@@ -47,11 +48,6 @@ struct xwl_window_buffer {
struct xwl_window *xwl_window;
PixmapPtr pixmap;
RegionPtr damage_region;
#ifdef XWL_HAS_GLAMOR
struct dri3_syncobj *syncobj;
uint64_t timeline_point;
int efd;
#endif /* XWL_HAS_GLAMOR */
int refcnt;
uint32_t time;
struct xorg_list link_buffer;
......@@ -90,9 +86,6 @@ xwl_window_buffer_new(struct xwl_window *xwl_window)
xwl_window_buffer->damage_region = RegionCreate(NullBox, 1);
xwl_window_buffer->pixmap = NullPixmap;
xwl_window_buffer->refcnt = 1;
#ifdef XWL_HAS_GLAMOR
xwl_window_buffer->efd = -1;
#endif /* XWL_HAS_GLAMOR */
xorg_list_init(&xwl_window_buffer->link_buffer);
......@@ -109,31 +102,31 @@ xwl_window_buffer_destroy_pixmap(struct xwl_window_buffer *xwl_window_buffer)
xwl_window_buffer->pixmap = NullPixmap;
}
static Bool
xwl_window_buffer_maybe_dispose(struct xwl_window_buffer *xwl_window_buffer)
static void
xwl_window_buffer_dispose(struct xwl_window_buffer *xwl_window_buffer)
{
assert(xwl_window_buffer->refcnt > 0);
if (--xwl_window_buffer->refcnt)
return FALSE;
RegionDestroy(xwl_window_buffer->damage_region);
if (xwl_window_buffer->pixmap)
xwl_window_buffer_destroy_pixmap (xwl_window_buffer);
if (xwl_window_buffer->pixmap) {
#ifdef XWL_HAS_GLAMOR
if (xwl_window_buffer->syncobj)
xwl_window_buffer->syncobj->free(xwl_window_buffer->syncobj);
if (xwl_window_buffer->efd >= 0) {
SetNotifyFd(xwl_window_buffer->efd, NULL, 0, NULL);
close(xwl_window_buffer->efd);
}
xwl_glamor_gbm_dispose_syncpts(xwl_window_buffer->pixmap);
#endif /* XWL_HAS_GLAMOR */
xwl_window_buffer_destroy_pixmap (xwl_window_buffer);
}
xorg_list_del(&xwl_window_buffer->link_buffer);
free(xwl_window_buffer);
}
static Bool
xwl_window_buffer_maybe_dispose(struct xwl_window_buffer *xwl_window_buffer)
{
assert(xwl_window_buffer->refcnt > 0);
if (--xwl_window_buffer->refcnt)
return FALSE;
xwl_window_buffer_dispose(xwl_window_buffer);
return TRUE;
}
......@@ -238,19 +231,11 @@ xwl_window_buffer_release_callback(void *data)
xwl_window);
}
#ifdef XWL_HAS_GLAMOR
static void
xwl_window_buffers_release_fence_avail(int fd, int xevents, void *data)
void
xwl_window_buffer_release(struct xwl_window_buffer *xwl_window_buffer)
{
struct xwl_window_buffer *xwl_window_buffer = data;
SetNotifyFd(fd, NULL, 0, NULL);
close(fd);
xwl_window_buffer->efd = -1;
xwl_window_buffer_release_callback(data);
xwl_window_buffer_release_callback(xwl_window_buffer);
}
#endif /* XWL_HAS_GLAMOR */
void
xwl_window_buffers_init(struct xwl_window *xwl_window)
......@@ -259,8 +244,17 @@ xwl_window_buffers_init(struct xwl_window *xwl_window)
xorg_list_init(&xwl_window->window_buffers_unavailable);
}
static void
xwl_window_buffer_disposal(struct xwl_window_buffer *xwl_window_buffer, Bool force)
{
if (force)
xwl_window_buffer_dispose(xwl_window_buffer);
else
xwl_window_buffer_maybe_dispose(xwl_window_buffer);
}
void
xwl_window_buffers_dispose(struct xwl_window *xwl_window)
xwl_window_buffers_dispose(struct xwl_window *xwl_window, Bool force)
{
struct xwl_window_buffer *xwl_window_buffer, *tmp;
......@@ -272,14 +266,14 @@ xwl_window_buffers_dispose(struct xwl_window *xwl_window)
&xwl_window->window_buffers_available,
link_buffer) {
xorg_list_del(&xwl_window_buffer->link_buffer);
xwl_window_buffer_maybe_dispose(xwl_window_buffer);
xwl_window_buffer_disposal(xwl_window_buffer, force);
}
xorg_list_for_each_entry_safe(xwl_window_buffer, tmp,
&xwl_window->window_buffers_unavailable,
link_buffer) {
xorg_list_del(&xwl_window_buffer->link_buffer);
xwl_window_buffer_maybe_dispose(xwl_window_buffer);
xwl_window_buffer_disposal(xwl_window_buffer, force);
}
if (xwl_window->window_buffers_timer)
......@@ -370,54 +364,39 @@ xwl_window_realloc_pixmap(struct xwl_window *xwl_window)
screen->DestroyPixmap(window_pixmap);
}
#ifdef XWL_HAS_GLAMOR
static Bool
xwl_window_buffers_set_syncpts(struct xwl_window_buffer *xwl_window_buffer)
xwl_window_handle_pixmap_sync(struct xwl_window *xwl_window,
PixmapPtr pixmap,
struct xwl_window_buffer *xwl_window_buffer)
{
struct xwl_window *xwl_window = xwl_window_buffer->xwl_window;
Bool implicit_sync = TRUE;
#ifdef XWL_HAS_GLAMOR
struct xwl_screen *xwl_screen = xwl_window->xwl_screen;
uint64_t acquire_point = ++xwl_window_buffer->timeline_point;
uint64_t release_point = ++xwl_window_buffer->timeline_point;
if (!xwl_window_buffer->syncobj) {
struct dri3_syncobj *syncobj = xwl_glamor_dri3_syncobj_create(xwl_screen);
if (!syncobj)
goto fail;
xwl_window_buffer->syncobj = syncobj;
}
int fence_fd = xwl_glamor_get_fence(xwl_screen);
if (fence_fd >= 0)
xwl_window_buffer->syncobj->import_fence(xwl_window_buffer->syncobj,
acquire_point, fence_fd);
else
goto fail;
xwl_glamor_dri3_syncobj_passthrough(xwl_window,
xwl_window_buffer->syncobj,
xwl_window_buffer->syncobj,
acquire_point,
release_point);
return TRUE;
fail:
/* can't use explicit sync, we will do a glFinish() before presenting */
if (xwl_window_buffer->syncobj) {
xwl_window_buffer->syncobj->free(xwl_window_buffer->syncobj);
xwl_window_buffer->syncobj = NULL;
if (!xwl_glamor_supports_implicit_sync(xwl_screen)) {
if (xwl_screen->explicit_sync && xwl_glamor_gbm_set_syncpts(xwl_window, pixmap)) {
implicit_sync = FALSE;
/* wait until the release fence is available before re-using this buffer */
xwl_glamor_gbm_wait_release_fence(xwl_window, pixmap, xwl_window_buffer);
} else {
/* If glamor does not support implicit sync and we can't use
* explicit sync, wait for the GPU to be idle before presenting.
* Note that buffer re-use will still be unsynchronized :(
*/
glamor_finish(xwl_screen->screen);
}
}
return FALSE;
}
#endif /* XWL_HAS_GLAMOR */
return implicit_sync;
}
PixmapPtr
xwl_window_swap_pixmap(struct xwl_window *xwl_window)
xwl_window_swap_pixmap(struct xwl_window *xwl_window, Bool handle_sync)
{
struct xwl_screen *xwl_screen = xwl_window->xwl_screen;
WindowPtr surface_window = xwl_window->surface_window;
struct xwl_window_buffer *xwl_window_buffer;
PixmapPtr window_pixmap;
Bool implicit_sync = TRUE;
window_pixmap = (*xwl_screen->screen->GetWindowPixmap) (surface_window);
......@@ -428,17 +407,9 @@ xwl_window_swap_pixmap(struct xwl_window *xwl_window)
RegionPtr full_damage = xwl_window_buffer->damage_region;
BoxPtr pBox = RegionRects(full_damage);
int nBox = RegionNumRects(full_damage);
#ifdef XWL_HAS_GLAMOR
if (xwl_window_buffer->syncobj) {
int fence_fd =
xwl_window_buffer->syncobj->export_fence(xwl_window_buffer->syncobj,
xwl_window_buffer->timeline_point);
xwl_glamor_wait_fence(xwl_screen, fence_fd);
close(fence_fd);
}
xwl_glamor_gbm_wait_syncpts(xwl_window_buffer->pixmap);
#endif /* XWL_HAS_GLAMOR */
while (nBox--) {
copy_pixmap_area(window_pixmap,
xwl_window_buffer->pixmap,
......@@ -458,6 +429,8 @@ xwl_window_swap_pixmap(struct xwl_window *xwl_window)
if (xwl_is_client_pixmap(window_pixmap)) {
xwl_window_buffer->pixmap = NULL;
xwl_window_buffer_maybe_dispose(xwl_window_buffer);
if (handle_sync)
xwl_window_handle_pixmap_sync(xwl_window, window_pixmap, NULL);
return window_pixmap;
}
} else {
......@@ -468,8 +441,11 @@ xwl_window_swap_pixmap(struct xwl_window *xwl_window)
window_pixmap->refcnt++;
xwl_window_realloc_pixmap(xwl_window);
if (!xwl_window_buffer)
if (!xwl_window_buffer) {
if (handle_sync)
xwl_window_handle_pixmap_sync(xwl_window, window_pixmap, NULL);
return window_pixmap;
}
}
xwl_window_buffer->pixmap = window_pixmap;
......@@ -477,27 +453,8 @@ xwl_window_swap_pixmap(struct xwl_window *xwl_window)
/* Hold a reference on the buffer until it's released by the compositor */
xwl_window_buffer->refcnt++;
#ifdef XWL_HAS_GLAMOR
if (!xwl_glamor_supports_implicit_sync(xwl_screen)) {
if (xwl_screen->explicit_sync && xwl_window_buffers_set_syncpts(xwl_window_buffer)) {
implicit_sync = FALSE;
/* wait until the release fence is available before re-using this buffer */
xwl_window_buffer->efd = eventfd(0, EFD_CLOEXEC);
SetNotifyFd(xwl_window_buffer->efd, xwl_window_buffers_release_fence_avail,
X_NOTIFY_READ, xwl_window_buffer);
xwl_window_buffer->syncobj->submitted_eventfd(xwl_window_buffer->syncobj,
xwl_window_buffer->timeline_point,
xwl_window_buffer->efd);
} else
/* If glamor does not support implicit sync and we can't use
* explicit sync, wait for the GPU to be idle before presenting.
* Note that buffer re-use will still be unsynchronized :(
*/
glamor_finish(xwl_screen->screen);
}
#endif /* XWL_HAS_GLAMOR */
if (implicit_sync) {
if (handle_sync &&
xwl_window_handle_pixmap_sync(xwl_window, window_pixmap, xwl_window_buffer)) {
xwl_pixmap_set_buffer_release_cb(xwl_window_buffer->pixmap,
xwl_window_buffer_release_callback,
xwl_window_buffer);
......
......@@ -31,12 +31,11 @@
#include "xwayland-types.h"
struct xwl_window_buffer;
void xwl_window_buffer_add_damage_region(struct xwl_window *xwl_window);
void xwl_window_buffer_release(struct xwl_window_buffer *xwl_window_buffer);
void xwl_window_buffers_init(struct xwl_window *xwl_window);
void xwl_window_buffers_dispose(struct xwl_window *xwl_window);
void xwl_window_buffers_dispose(struct xwl_window *xwl_window, Bool force);
void xwl_window_realloc_pixmap(struct xwl_window *xwl_window);
PixmapPtr xwl_window_swap_pixmap(struct xwl_window *xwl_window);
PixmapPtr xwl_window_swap_pixmap(struct xwl_window *xwl_window, Bool handle_sync);
#endif /* XWAYLAND_WINDOW_BUFFERS_H */
......@@ -318,7 +318,7 @@ damage_report(DamagePtr pDamage, RegionPtr pRegion, void *data)
window_pixmap = xwl_screen->screen->GetWindowPixmap(xwl_window->surface_window);
if (xwl_is_client_pixmap(window_pixmap))
xwl_screen->screen->DestroyPixmap(xwl_window_swap_pixmap(xwl_window));
xwl_screen->screen->DestroyPixmap(xwl_window_swap_pixmap(xwl_window, FALSE));
}
static void
......@@ -1407,7 +1407,7 @@ xwl_window_update_surface_window(struct xwl_window *xwl_window)
}
if (surface_window->drawable.depth != xwl_window->surface_window->drawable.depth)
xwl_window_buffers_dispose(xwl_window);
xwl_window_buffers_dispose(xwl_window, FALSE);
xwl_window->surface_window = surface_window;
register_damage(xwl_window);
......@@ -1643,28 +1643,15 @@ release_wl_surface_for_window(struct xwl_window *xwl_window)
release_wl_surface_for_window_legacy_delay(xwl_window);
}
Bool
xwl_unrealize_window(WindowPtr window)
static void
xwl_window_dispose(struct xwl_window *xwl_window)
{
ScreenPtr screen = window->drawable.pScreen;
struct xwl_screen *xwl_screen;
struct xwl_window *xwl_window;
struct xwl_screen *xwl_screen = xwl_window->xwl_screen;
struct xwl_seat *xwl_seat;
Bool ret;
xwl_screen = xwl_screen_get(screen);
xwl_window = xwl_window_get(window);
if (xwl_window)
compUnredirectWindow(serverClient, window, CompositeRedirectManual);
screen->UnrealizeWindow = xwl_screen->UnrealizeWindow;
ret = (*screen->UnrealizeWindow) (window);
xwl_screen->UnrealizeWindow = screen->UnrealizeWindow;
screen->UnrealizeWindow = xwl_unrealize_window;
WindowPtr window = xwl_window->toplevel;
ScreenPtr screen = xwl_screen->screen;
if (!xwl_window)
return ret;
compUnredirectWindow(serverClient, window, CompositeRedirectManual);
xorg_list_for_each_entry(xwl_seat, &xwl_screen->seat_list, link) {
if (xwl_seat->focus_window == xwl_window)
......@@ -1704,9 +1691,10 @@ xwl_unrealize_window(WindowPtr window)
release_wl_surface_for_window(xwl_window);
xorg_list_del(&xwl_window->link_damage);
xorg_list_del(&xwl_window->link_window);
unregister_damage(xwl_window);
xwl_window_buffers_dispose(xwl_window);
/* Special case for the root window in rootful mode */
xwl_window_buffers_dispose(xwl_window,
(!xwl_screen->rootless && window == screen->root));
if (xwl_window->window_buffers_timer)
TimerFree(xwl_window->window_buffers_timer);
......@@ -1718,6 +1706,25 @@ xwl_unrealize_window(WindowPtr window)
free(xwl_window);
dixSetPrivate(&window->devPrivates, &xwl_window_private_key, NULL);
}
Bool
xwl_unrealize_window(WindowPtr window)
{
ScreenPtr screen = window->drawable.pScreen;
struct xwl_screen *xwl_screen = xwl_screen_get(screen);
struct xwl_window *xwl_window = xwl_window_get(window);
Bool ret;
if (xwl_window) {
unregister_damage(xwl_window);
xwl_window_dispose(xwl_window);
}
screen->UnrealizeWindow = xwl_screen->UnrealizeWindow;
ret = (*screen->UnrealizeWindow) (window);
xwl_screen->UnrealizeWindow = screen->UnrealizeWindow;
screen->UnrealizeWindow = xwl_unrealize_window;
return ret;
}
......@@ -1749,7 +1756,7 @@ xwl_window_set_window_pixmap(WindowPtr window,
old_pixmap->drawable.height == pixmap->drawable.height))
return;
xwl_window_buffers_dispose(xwl_window);
xwl_window_buffers_dispose(xwl_window, FALSE);
}
Bool
......@@ -1926,11 +1933,15 @@ xwl_destroy_window(WindowPtr window)
{
ScreenPtr screen = window->drawable.pScreen;
struct xwl_screen *xwl_screen = xwl_screen_get(screen);
struct xwl_window *xwl_window = xwl_window_get(window);
Bool ret;
if (xwl_screen->present)
xwl_present_cleanup(window);
if (xwl_window)
xwl_window_dispose(xwl_window);
screen->DestroyWindow = xwl_screen->DestroyWindow;
if (screen->DestroyWindow)
......@@ -1955,7 +1966,7 @@ xwl_window_attach_buffer(struct xwl_window *xwl_window)
PixmapPtr pixmap;
int i;
pixmap = xwl_window_swap_pixmap(xwl_window);
pixmap = xwl_window_swap_pixmap(xwl_window, TRUE);
buffer = xwl_pixmap_get_wl_buffer(pixmap);
if (!buffer) {
......