mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-06-05 15:08:53 +00:00
eglglessink: Make the context current for the thread and unbind it again around every use
This fixes some crashes and leaking of our context into other OpenGL code on the same thread.
This commit is contained in:
parent
113253b292
commit
09b3518bae
1 changed files with 46 additions and 6 deletions
|
@ -376,6 +376,7 @@ static inline gboolean got_gl_error (const char *wtf);
|
||||||
static inline void show_egl_error (const char *wtf);
|
static inline void show_egl_error (const char *wtf);
|
||||||
static void gst_eglglessink_wipe_fmt (gpointer data);
|
static void gst_eglglessink_wipe_fmt (gpointer data);
|
||||||
static inline gboolean egl_init (GstEglGlesSink * eglglessink);
|
static inline gboolean egl_init (GstEglGlesSink * eglglessink);
|
||||||
|
static gboolean gst_eglglessink_context_make_current (GstEglGlesSink * eglglessink, gboolean bind);
|
||||||
|
|
||||||
static GstBufferClass *gsteglglessink_buffer_parent_class = NULL;
|
static GstBufferClass *gsteglglessink_buffer_parent_class = NULL;
|
||||||
#define GST_TYPE_EGLGLESBUFFER (gst_eglglesbuffer_get_type())
|
#define GST_TYPE_EGLGLESBUFFER (gst_eglglesbuffer_get_type())
|
||||||
|
@ -1041,6 +1042,9 @@ gst_eglglessink_stop (GstBaseSink * sink)
|
||||||
|
|
||||||
/* EGL/GLES2 cleanup */
|
/* EGL/GLES2 cleanup */
|
||||||
|
|
||||||
|
if (!gst_eglglessink_context_make_current (eglglessink, TRUE))
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
if (eglglessink->rendering_path == GST_EGLGLESSINK_RENDER_SLOW) {
|
if (eglglessink->rendering_path == GST_EGLGLESSINK_RENDER_SLOW) {
|
||||||
glUseProgram (0);
|
glUseProgram (0);
|
||||||
|
|
||||||
|
@ -1070,6 +1074,9 @@ gst_eglglessink_stop (GstBaseSink * sink)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!gst_eglglessink_context_make_current (eglglessink, FALSE))
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
if (eglglessink->eglglesctx->surface) {
|
if (eglglessink->eglglesctx->surface) {
|
||||||
eglDestroySurface (eglglessink->eglglesctx->display,
|
eglDestroySurface (eglglessink->eglglesctx->display,
|
||||||
eglglessink->eglglesctx->surface);
|
eglglessink->eglglesctx->surface);
|
||||||
|
@ -1433,6 +1440,32 @@ gst_eglglessink_update_surface_dimensions (GstEglGlesSink * eglglessink)
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
gst_eglglessink_context_make_current (GstEglGlesSink * eglglessink, gboolean bind)
|
||||||
|
{
|
||||||
|
g_assert (eglglessink->eglglesctx->display != NULL);
|
||||||
|
|
||||||
|
if (bind && eglglessink->eglglesctx->surface && eglglessink->eglglesctx->eglcontext) {
|
||||||
|
if (!eglMakeCurrent (eglglessink->eglglesctx->display,
|
||||||
|
eglglessink->eglglesctx->surface, eglglessink->eglglesctx->surface,
|
||||||
|
eglglessink->eglglesctx->eglcontext)) {
|
||||||
|
show_egl_error ("eglMakeCurrent");
|
||||||
|
GST_ERROR_OBJECT (eglglessink, "Couldn't bind context");
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (!eglMakeCurrent (eglglessink->eglglesctx->display,
|
||||||
|
EGL_NO_SURFACE, EGL_NO_SURFACE,
|
||||||
|
EGL_NO_CONTEXT)) {
|
||||||
|
show_egl_error ("eglMakeCurrent");
|
||||||
|
GST_ERROR_OBJECT (eglglessink, "Couldn't unbind context");
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
{
|
{
|
||||||
|
@ -1457,13 +1490,8 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
goto HANDLE_EGL_ERROR_LOCKED;
|
goto HANDLE_EGL_ERROR_LOCKED;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!eglMakeCurrent (eglglessink->eglglesctx->display,
|
if (!gst_eglglessink_context_make_current (eglglessink, TRUE))
|
||||||
eglglessink->eglglesctx->surface, eglglessink->eglglesctx->surface,
|
|
||||||
eglglessink->eglglesctx->eglcontext)) {
|
|
||||||
show_egl_error ("eglCreateWindowSurface");
|
|
||||||
GST_ERROR_OBJECT (eglglessink, "Couldn't bind surface/context");
|
|
||||||
goto HANDLE_EGL_ERROR_LOCKED;
|
goto HANDLE_EGL_ERROR_LOCKED;
|
||||||
}
|
|
||||||
|
|
||||||
/* Save surface dims */
|
/* Save surface dims */
|
||||||
gst_eglglessink_update_surface_dimensions (eglglessink);
|
gst_eglglessink_update_surface_dimensions (eglglessink);
|
||||||
|
@ -1864,6 +1892,9 @@ gst_eglglessink_render_and_display (GstEglGlesSink * eglglessink,
|
||||||
};
|
};
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
if (!gst_eglglessink_context_make_current (eglglessink, TRUE))
|
||||||
|
goto HANDLE_EGL_ERROR;
|
||||||
|
|
||||||
w = GST_VIDEO_SINK_WIDTH (eglglessink);
|
w = GST_VIDEO_SINK_WIDTH (eglglessink);
|
||||||
h = GST_VIDEO_SINK_HEIGHT (eglglessink);
|
h = GST_VIDEO_SINK_HEIGHT (eglglessink);
|
||||||
|
|
||||||
|
@ -2101,6 +2132,9 @@ gst_eglglessink_render_and_display (GstEglGlesSink * eglglessink,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!gst_eglglessink_context_make_current (eglglessink, FALSE))
|
||||||
|
goto HANDLE_EGL_ERROR;
|
||||||
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Succesfully rendered 1 frame");
|
GST_DEBUG_OBJECT (eglglessink, "Succesfully rendered 1 frame");
|
||||||
return GST_FLOW_OK;
|
return GST_FLOW_OK;
|
||||||
|
|
||||||
|
@ -2108,6 +2142,8 @@ HANDLE_EGL_ERROR:
|
||||||
GST_ERROR_OBJECT (eglglessink, "EGL call returned error %x", eglGetError ());
|
GST_ERROR_OBJECT (eglglessink, "EGL call returned error %x", eglGetError ());
|
||||||
HANDLE_ERROR:
|
HANDLE_ERROR:
|
||||||
GST_ERROR_OBJECT (eglglessink, "Rendering disabled for this frame");
|
GST_ERROR_OBJECT (eglglessink, "Rendering disabled for this frame");
|
||||||
|
|
||||||
|
gst_eglglessink_context_make_current (eglglessink, FALSE);
|
||||||
return GST_FLOW_ERROR;
|
return GST_FLOW_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2304,6 +2340,9 @@ gst_eglglessink_setcaps (GstBaseSink * bsink, GstCaps * caps)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!gst_eglglessink_context_make_current (eglglessink, FALSE))
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
SUCCEED:
|
SUCCEED:
|
||||||
GST_INFO_OBJECT (eglglessink, "Setcaps succeed");
|
GST_INFO_OBJECT (eglglessink, "Setcaps succeed");
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
@ -2311,6 +2350,7 @@ SUCCEED:
|
||||||
/* Errors */
|
/* Errors */
|
||||||
HANDLE_ERROR:
|
HANDLE_ERROR:
|
||||||
GST_ERROR_OBJECT (eglglessink, "Setcaps failed");
|
GST_ERROR_OBJECT (eglglessink, "Setcaps failed");
|
||||||
|
gst_eglglessink_context_make_current (eglglessink, FALSE);
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue