summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/egl/drivers/dri2/egl_dri2.c85
1 files changed, 76 insertions, 9 deletions
diff --git a/src/egl/drivers/dri2/egl_dri2.c b/src/egl/drivers/dri2/egl_dri2.c
index b43e91130c0..04d698e81c8 100644
--- a/src/egl/drivers/dri2/egl_dri2.c
+++ b/src/egl/drivers/dri2/egl_dri2.c
@@ -58,15 +58,16 @@ struct dri2_egl_driver
struct dri2_egl_display
{
- xcb_connection_t *conn;
- int dri2_major;
- int dri2_minor;
- __DRIscreen *dri_screen;
- void *driver;
- __DRIcoreExtension *core;
- __DRIdri2Extension *dri2;
- __DRI2flushExtension *flush;
- int fd;
+ xcb_connection_t *conn;
+ int dri2_major;
+ int dri2_minor;
+ __DRIscreen *dri_screen;
+ void *driver;
+ __DRIcoreExtension *core;
+ __DRIdri2Extension *dri2;
+ __DRI2flushExtension *flush;
+ __DRItexBufferExtension *tex_buffer;
+ int fd;
__DRIdri2LoaderExtension loader_extension;
const __DRIextension *extensions[2];
@@ -389,6 +390,7 @@ static struct dri2_extension_match dri2_driver_extensions[] = {
static struct dri2_extension_match dri2_core_extensions[] = {
{ __DRI2_FLUSH, 1, offsetof(struct dri2_egl_display, flush) },
+ { __DRI_TEX_BUFFER, 2, offsetof(struct dri2_egl_display, tex_buffer) },
{ NULL }
};
@@ -964,6 +966,69 @@ dri2_copy_buffers(_EGLDriver *drv, _EGLDisplay *disp, _EGLSurface *surf,
return EGL_TRUE;
}
+static EGLBoolean
+dri2_bind_tex_image(_EGLDriver *drv,
+ _EGLDisplay *disp, _EGLSurface *surf, EGLint buffer)
+{
+ struct dri2_egl_display *dri2_dpy = dri2_egl_display(disp);
+ struct dri2_egl_surface *dri2_surf = dri2_egl_surface(surf);
+ struct dri2_egl_context *dri2_ctx;
+ _EGLContext *ctx;
+ GLint format, target;
+
+ ctx = _eglGetCurrentContext();
+ dri2_ctx = dri2_egl_context(ctx);
+
+ if (buffer != EGL_BACK_BUFFER) {
+ _eglError(EGL_BAD_PARAMETER, "eglBindTexImage");
+ return EGL_FALSE;
+ }
+
+ /* We allow binding pixmaps too... Not conformat, but we can do it
+ * for free and it's useful for X compositors. Supposedly there's
+ * a EGL_NOKIA_texture_from_pixmap extension that allows that, but
+ * I couldn't find it at this time. */
+ if (dri2_surf->base.Type & (EGL_PBUFFER_BIT | EGL_PIXMAP_BIT) == 0) {
+ _eglError(EGL_BAD_SURFACE, "eglBindTexImage");
+ return EGL_FALSE;
+ }
+
+ switch (dri2_surf->base.TextureFormat) {
+ case EGL_TEXTURE_RGB:
+ format = __DRI_TEXTURE_FORMAT_RGB;
+ break;
+ case EGL_TEXTURE_RGBA:
+ format = __DRI_TEXTURE_FORMAT_RGBA;
+ break;
+ default:
+ _eglError(EGL_BAD_MATCH, "eglBindTexImage");
+ return EGL_FALSE;
+ }
+
+ switch (dri2_surf->base.TextureTarget) {
+ case EGL_TEXTURE_2D:
+ target = GL_TEXTURE_2D;
+ break;
+ default:
+ _eglError(EGL_BAD_PARAMETER, "eglBindTexImage");
+ return EGL_FALSE;
+ }
+
+ (*dri2_dpy->tex_buffer->setTexBuffer2)(dri2_ctx->dri_context,
+ target, format,
+ dri2_surf->dri_drawable);
+
+ return dri2_surf->base.BoundToTexture = EGL_TRUE;
+}
+
+static EGLBoolean
+dri2_release_tex_image(_EGLDriver *drv,
+ _EGLDisplay *disp, _EGLSurface *surf, EGLint buffer)
+{
+ return EGL_TRUE;
+}
+
+
/**
* This is the main entrypoint into the driver, called by libEGL.
* Create a new _EGLDriver object and init its dispatch table.
@@ -991,6 +1056,8 @@ _eglMain(const char *args)
dri2_drv->base.API.WaitClient = dri2_wait_client;
dri2_drv->base.API.WaitNative = dri2_wait_native;
dri2_drv->base.API.CopyBuffers = dri2_copy_buffers;
+ dri2_drv->base.API.BindTexImage = dri2_bind_tex_image;
+ dri2_drv->base.API.ReleaseTexImage = dri2_release_tex_image;
dri2_drv->base.Name = "DRI2";
dri2_drv->base.Unload = dri2_unload;