egl: Allow creation of per surface out fence
[mesa.git] / src / egl / drivers / dri2 / platform_android.c
index a864a2af3d799be6ba61d060026f5200986d6386..d08a8b22b7d34ee507ee5d52ea7233ab248a80a3 100644 (file)
@@ -229,19 +229,18 @@ droid_window_enqueue_buffer(_EGLDisplay *disp, struct dri2_egl_surface *dri2_sur
     */
    mtx_unlock(&disp->Mutex);
 
-   /* Queue the buffer without a sync fence. This informs the ANativeWindow
-    * that it may access the buffer immediately.
+   /* Queue the buffer with stored out fence fd. The ANativeWindow or buffer
+    * consumer may choose to wait for the fence to signal before accessing
+    * it. If fence fd value is -1, buffer can be accessed by consumer
+    * immediately. Consumer or application shouldn't rely on timestamp
+    * associated with fence if the fence fd is -1.
     *
-    * From ANativeWindow::dequeueBuffer:
-    *
-    *    The fenceFd argument specifies a libsync fence file descriptor for
-    *    a fence that must signal before the buffer can be accessed.  If
-    *    the buffer can be accessed immediately then a value of -1 should
-    *    be used.  The caller must not use the file descriptor after it
-    *    is passed to queueBuffer, and the ANativeWindow implementation
-    *    is responsible for closing it.
+    * Ownership of fd is transferred to consumer after queueBuffer and the
+    * consumer is responsible for closing it. Caller must not use the fd
+    * after passing it to queueBuffer.
     */
-   int fence_fd = -1;
+   int fence_fd = dri2_surf->out_fence_fd;
+   dri2_surf->out_fence_fd = -1;
    dri2_surf->window->queueBuffer(dri2_surf->window, dri2_surf->buffer,
                                   fence_fd);
 
@@ -263,8 +262,11 @@ static void
 droid_window_cancel_buffer(struct dri2_egl_surface *dri2_surf)
 {
    int ret;
+   int fence_fd = dri2_surf->out_fence_fd;
 
-   ret = dri2_surf->window->cancelBuffer(dri2_surf->window, dri2_surf->buffer, -1);
+   dri2_surf->out_fence_fd = -1;
+   ret = dri2_surf->window->cancelBuffer(dri2_surf->window,
+                                         dri2_surf->buffer, fence_fd);
    if (ret < 0) {
       _eglLog(_EGL_WARNING, "ANativeWindow::cancelBuffer failed");
       dri2_surf->base.Lost = EGL_TRUE;
@@ -289,7 +291,7 @@ droid_create_surface(_EGLDriver *drv, _EGLDisplay *disp, EGLint type,
       return NULL;
    }
 
-   if (!_eglInitSurface(&dri2_surf->base, disp, type, conf, attrib_list))
+   if (!dri2_init_surface(&dri2_surf->base, disp, type, conf, attrib_list, true))
       goto cleanup_surface;
 
    if (type == EGL_WINDOW_BIT) {
@@ -389,6 +391,7 @@ droid_destroy_surface(_EGLDriver *drv, _EGLDisplay *disp, _EGLSurface *surf)
 
    dri2_dpy->core->destroyDrawable(dri2_surf->dri_drawable);
 
+   dri2_fini_surface(surf);
    free(dri2_surf);
 
    return EGL_TRUE;