diff options
author | Haixia Shi <[email protected]> | 2016-06-02 12:48:23 -0700 |
---|---|---|
committer | Emil Velikov <[email protected]> | 2016-06-07 12:30:25 +0100 |
commit | 1ea233c6f30a74e6ff5456c3521328237b01eed8 (patch) | |
tree | 702cc07b3964c51679f0608a90610973a97ea85d /src/egl/drivers | |
parent | b7f7ec78435771ab02f7d9a61bb1d4a11df720b8 (diff) |
platform_android: prevent deadlock in droid_swap_buffers
To avoid blocking other EGL calls, release the display mutex before
we enqueue buffer to android frameworks and re-acquire the mutex
upon return.
v2: moved lock/unlock inside droid_window_enqueue_buffer().
TEST=verify pinch zoom in Photos app no longer causes hangs
Signed-off-by: Haixia Shi <[email protected]>
Reviewed-by: Emil Velikov <[email protected]>
Diffstat (limited to 'src/egl/drivers')
-rw-r--r-- | src/egl/drivers/dri2/platform_android.c | 17 |
1 files changed, 12 insertions, 5 deletions
diff --git a/src/egl/drivers/dri2/platform_android.c b/src/egl/drivers/dri2/platform_android.c index 70bbdff33ae..b1d7272092c 100644 --- a/src/egl/drivers/dri2/platform_android.c +++ b/src/egl/drivers/dri2/platform_android.c @@ -160,8 +160,14 @@ droid_window_dequeue_buffer(struct dri2_egl_surface *dri2_surf) } static EGLBoolean -droid_window_enqueue_buffer(struct dri2_egl_surface *dri2_surf) +droid_window_enqueue_buffer(_EGLDisplay *disp, struct dri2_egl_surface *dri2_surf) { + /* To avoid blocking other EGL calls, release the display mutex before + * we enter droid_window_enqueue_buffer() and re-acquire the mutex upon + * return. + */ + mtx_unlock(&disp->Mutex); + #if ANDROID_VERSION >= 0x0402 /* Queue the buffer without a sync fence. This informs the ANativeWindow * that it may access the buffer immediately. @@ -185,14 +191,15 @@ droid_window_enqueue_buffer(struct dri2_egl_surface *dri2_surf) dri2_surf->buffer->common.decRef(&dri2_surf->buffer->common); dri2_surf->buffer = NULL; + mtx_lock(&disp->Mutex); return EGL_TRUE; } static void -droid_window_cancel_buffer(struct dri2_egl_surface *dri2_surf) +droid_window_cancel_buffer(_EGLDisplay *disp, struct dri2_egl_surface *dri2_surf) { /* no cancel buffer? */ - droid_window_enqueue_buffer(dri2_surf); + droid_window_enqueue_buffer(disp, dri2_surf); } static __DRIbuffer * @@ -325,7 +332,7 @@ droid_destroy_surface(_EGLDriver *drv, _EGLDisplay *disp, _EGLSurface *surf) if (dri2_surf->base.Type == EGL_WINDOW_BIT) { if (dri2_surf->buffer) - droid_window_cancel_buffer(dri2_surf); + droid_window_cancel_buffer(disp, dri2_surf); dri2_surf->window->common.decRef(&dri2_surf->window->common); } @@ -435,7 +442,7 @@ droid_swap_buffers(_EGLDriver *drv, _EGLDisplay *disp, _EGLSurface *draw) dri2_flush_drawable_for_swapbuffers(disp, draw); if (dri2_surf->buffer) - droid_window_enqueue_buffer(dri2_surf); + droid_window_enqueue_buffer(disp, dri2_surf); (*dri2_dpy->flush->invalidate)(dri2_surf->dri_drawable); |