[Cogl] [PATCH 1/4] Add a vtable for the driver

Neil Roberts neil at linux.intel.com
Thu Mar 22 10:32:50 PDT 2012


Cogl already had a vtable for the texture driver. This ended up being
used for some things that are not strictly related to texturing such
as converting between pixel formats and GL enums. Some other functions
that are driver dependent such as updating the features were not
indirected through a vtable but instead switched directly by looking
at the ctx->driver enum value. This patch normalises to the two uses
by adding a separate vtable for driver functions not related to
texturing and moves the pixel format conversion functions to it from
the texture driver vtable. It also adds a context parameter to all of
the functions in the new driver vtable so that they won't have to rely
on the global context.
---
 cogl/Makefile.am                            |    1 +
 cogl/cogl-atlas.c                           |   18 +-
 cogl/cogl-context-private.h                 |    4 +-
 cogl/cogl-context.c                         |   31 ++--
 cogl/cogl-driver.h                          |   51 ++++++
 cogl/cogl-framebuffer.c                     |    9 +-
 cogl/cogl-private.h                         |    8 -
 cogl/cogl-texture-2d-sliced.c               |    9 +-
 cogl/cogl-texture-2d.c                      |   41 +++--
 cogl/cogl-texture-3d.c                      |   18 +-
 cogl/cogl-texture-driver.h                  |   19 +--
 cogl/cogl-texture-rectangle.c               |   41 +++--
 cogl/cogl-texture.c                         |   30 ++--
 cogl/driver/gl/cogl-gl.c                    |  240 ++++++++++++++++++++++++---
 cogl/driver/gl/cogl-texture-driver-gl.c     |  205 +----------------------
 cogl/driver/gles/cogl-gles.c                |  124 ++++++++++++++-
 cogl/driver/gles/cogl-texture-driver-gles.c |  119 +-------------
 17 files changed, 515 insertions(+), 453 deletions(-)
 create mode 100644 cogl/cogl-driver.h

diff --git a/cogl/Makefile.am b/cogl/Makefile.am
index 538fbf3..69cb5df 100644
--- a/cogl/Makefile.am
+++ b/cogl/Makefile.am
@@ -196,6 +196,7 @@ cogl_sources_c = \
 	$(srcdir)/cogl-display.h			\
 	$(srcdir)/cogl-display.c			\
 	$(srcdir)/cogl-internal.h			\
+	$(srcdir)/cogl-driver.h				\
 	$(srcdir)/cogl.c				\
 	$(srcdir)/cogl-object-private.h			\
 	$(srcdir)/cogl-object.h				\
diff --git a/cogl/cogl-atlas.c b/cogl/cogl-atlas.c
index bfa76dc..68f48c0 100644
--- a/cogl/cogl-atlas.c
+++ b/cogl/cogl-atlas.c
@@ -177,10 +177,11 @@ _cogl_atlas_get_initial_size (CoglPixelFormat format,
 
   _COGL_GET_CONTEXT (ctx, NO_RETVAL);
 
-  ctx->texture_driver->pixel_format_to_gl (format,
-                                           &gl_intformat,
-                                           NULL, /* gl_format */
-                                           &gl_type);
+  ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                          format,
+                                          &gl_intformat,
+                                          NULL, /* gl_format */
+                                          &gl_type);
 
   /* At least on Intel hardware, the texture size will be rounded up
      to at least 1MB so we might as well try to aim for that as an
@@ -217,10 +218,11 @@ _cogl_atlas_create_map (CoglPixelFormat          format,
 
   _COGL_GET_CONTEXT (ctx, NULL);
 
-  ctx->texture_driver->pixel_format_to_gl (format,
-                                           &gl_intformat,
-                                           NULL, /* gl_format */
-                                           &gl_type);
+  ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                          format,
+                                          &gl_intformat,
+                                          NULL, /* gl_format */
+                                          &gl_type);
 
   /* Keep trying increasingly larger atlases until we can fit all of
      the textures */
diff --git a/cogl/cogl-context-private.h b/cogl/cogl-context-private.h
index 6d92faf..a79672f 100644
--- a/cogl/cogl-context-private.h
+++ b/cogl/cogl-context-private.h
@@ -41,6 +41,7 @@
 #include "cogl-buffer-private.h"
 #include "cogl-bitmask.h"
 #include "cogl-atlas.h"
+#include "cogl-driver.h"
 #include "cogl-texture-driver.h"
 #include "cogl-pipeline-cache.h"
 #include "cogl-texture-2d.h"
@@ -62,7 +63,8 @@ struct _CoglContext
 
   CoglDriver driver;
 
-  /* vtable for the texture driver functions */
+  /* vtables for the driver functions */
+  const CoglDriverVtable *driver_vtable;
   const CoglTextureDriver *texture_driver;
 
   /* Features cache */
diff --git a/cogl/cogl-context.c b/cogl/cogl-context.c
index 8b1ea2b..8ed3103 100644
--- a/cogl/cogl-context.c
+++ b/cogl/cogl-context.c
@@ -61,9 +61,11 @@
 
 #ifdef HAVE_COGL_GL
 extern const CoglTextureDriver _cogl_texture_driver_gl;
+extern const CoglDriverVtable _cogl_driver_gl;
 #endif
 #if defined (HAVE_COGL_GLES) || defined (HAVE_COGL_GLES2)
 extern const CoglTextureDriver _cogl_texture_driver_gles;
+extern const CoglDriverVtable _cogl_driver_gles;
 #endif
 
 static void _cogl_context_free (CoglContext *context);
@@ -203,18 +205,11 @@ cogl_context_new (CoglDisplay *display,
      lot throughout Cogl */
   context->driver = display->renderer->driver;
 
-  winsys = _cogl_context_get_winsys (context);
-  if (!winsys->context_init (context, error))
-    {
-      cogl_object_unref (display);
-      g_free (context);
-      return NULL;
-    }
-
   switch (context->driver)
     {
 #ifdef HAVE_COGL_GL
     case COGL_DRIVER_GL:
+      context->driver_vtable = &_cogl_driver_gl;
       context->texture_driver = &_cogl_texture_driver_gl;
       break;
 #endif
@@ -222,6 +217,7 @@ cogl_context_new (CoglDisplay *display,
 #if defined (HAVE_COGL_GLES) || defined (HAVE_COGL_GLES2)
     case COGL_DRIVER_GLES1:
     case COGL_DRIVER_GLES2:
+      context->driver_vtable = &_cogl_driver_gles;
       context->texture_driver = &_cogl_texture_driver_gles;
       break;
 #endif
@@ -230,6 +226,14 @@ cogl_context_new (CoglDisplay *display,
       g_assert_not_reached ();
     }
 
+  winsys = _cogl_context_get_winsys (context);
+  if (!winsys->context_init (context, error))
+    {
+      cogl_object_unref (display);
+      g_free (context);
+      return NULL;
+    }
+
   context->attribute_name_states_hash =
     g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_free);
   context->attribute_name_index_map = NULL;
@@ -578,16 +582,7 @@ gboolean
 _cogl_context_update_features (CoglContext *context,
                                GError **error)
 {
-#ifdef HAVE_COGL_GL
-  if (context->driver == COGL_DRIVER_GL)
-    return _cogl_gl_update_features (context, error);
-#endif
-
-#if defined(HAVE_COGL_GLES) || defined(HAVE_COGL_GLES2)
-  return _cogl_gles_update_features (context, error);
-#endif
-
-  g_assert_not_reached ();
+  return context->driver_vtable->update_features (context, error);
 }
 
 void
diff --git a/cogl/cogl-driver.h b/cogl/cogl-driver.h
new file mode 100644
index 0000000..b68e37a
--- /dev/null
+++ b/cogl/cogl-driver.h
@@ -0,0 +1,51 @@
+/*
+ * Cogl
+ *
+ * An object oriented GL/GLES Abstraction/Utility Layer
+ *
+ * Copyright (C) 2012 Intel Corporation.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library. If not, see <http://www.gnu.org/licenses/>.
+ *
+ *
+ */
+
+#ifndef __COGL_DRIVER_H
+#define __COGL_DRIVER_H
+
+#include "cogl-context.h"
+
+typedef struct _CoglDriverVtable CoglDriverVtable;
+
+struct _CoglDriverVtable
+{
+  gboolean
+  (* pixel_format_from_gl_internal) (CoglContext *context,
+                                     GLenum gl_int_format,
+                                     CoglPixelFormat *out_format);
+
+  CoglPixelFormat
+  (* pixel_format_to_gl) (CoglContext *context,
+                          CoglPixelFormat format,
+                          GLenum *out_glintformat,
+                          GLenum *out_glformat,
+                          GLenum *out_gltype);
+
+  gboolean
+  (* update_features) (CoglContext *context,
+                       GError **error);
+};
+
+#endif /* __COGL_DRIVER_H */
+
diff --git a/cogl/cogl-framebuffer.c b/cogl/cogl-framebuffer.c
index 74d595f..647b61d 100644
--- a/cogl/cogl-framebuffer.c
+++ b/cogl/cogl-framebuffer.c
@@ -2005,10 +2005,11 @@ cogl_framebuffer_read_pixels_into_bitmap (CoglFramebuffer *framebuffer,
 
   format = cogl_bitmap_get_format (bitmap);
 
-  required_format = ctx->texture_driver->pixel_format_to_gl (format,
-                                                             &gl_intformat,
-                                                             &gl_format,
-                                                             &gl_type);
+  required_format = ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                                            format,
+                                                            &gl_intformat,
+                                                            &gl_format,
+                                                            &gl_type);
 
   /* NB: All offscreen rendering is done upside down so there is no need
    * to flip in this case... */
diff --git a/cogl/cogl-private.h b/cogl/cogl-private.h
index 6130c11..0985ec8 100644
--- a/cogl/cogl-private.h
+++ b/cogl/cogl-private.h
@@ -31,14 +31,6 @@
 G_BEGIN_DECLS
 
 gboolean
-_cogl_gl_update_features (CoglContext *context,
-                          GError **error);
-
-gboolean
-_cogl_gles_update_features (CoglContext *context,
-                            GError **error);
-
-gboolean
 _cogl_check_extension (const char *name, const char *ext);
 
 void
diff --git a/cogl/cogl-texture-2d-sliced.c b/cogl/cogl-texture-2d-sliced.c
index 836caaf..7150d2b 100644
--- a/cogl/cogl-texture-2d-sliced.c
+++ b/cogl/cogl-texture-2d-sliced.c
@@ -639,10 +639,11 @@ _cogl_texture_2d_sliced_slices_create (CoglContext *ctx,
       slices_for_size = _cogl_pot_slices_for_size;
     }
 
-  ctx->texture_driver->pixel_format_to_gl (format,
-                                           &gl_intformat,
-                                           NULL,
-                                           &gl_type);
+  ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                          format,
+                                          &gl_intformat,
+                                          NULL,
+                                          &gl_type);
 
   /* Negative number means no slicing forced by the user */
   if (tex_2ds->max_waste <= -1)
diff --git a/cogl/cogl-texture-2d.c b/cogl/cogl-texture-2d.c
index dad1eac..cd0d522 100644
--- a/cogl/cogl-texture-2d.c
+++ b/cogl/cogl-texture-2d.c
@@ -120,10 +120,11 @@ _cogl_texture_2d_can_create (unsigned int width,
        !_cogl_util_is_pot (height)))
     return FALSE;
 
-  ctx->texture_driver->pixel_format_to_gl (internal_format,
-                                           &gl_intformat,
-                                           NULL,
-                                           &gl_type);
+  ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                          internal_format,
+                                          &gl_intformat,
+                                          NULL,
+                                          &gl_type);
 
   /* Check that the driver can create a texture with that size */
   if (!ctx->texture_driver->size_supported (GL_TEXTURE_2D,
@@ -192,10 +193,11 @@ cogl_texture_2d_new_with_size (CoglContext *ctx,
       return NULL;
     }
 
-  internal_format = ctx->texture_driver->pixel_format_to_gl (internal_format,
-                                                             &gl_intformat,
-                                                             &gl_format,
-                                                             &gl_type);
+  internal_format = ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                                            internal_format,
+                                                            &gl_intformat,
+                                                            &gl_format,
+                                                            &gl_type);
 
   tex_2d = _cogl_texture_2d_create_base (width, height, COGL_TEXTURE_NONE,
                                          internal_format);
@@ -382,8 +384,9 @@ cogl_texture_2d_new_from_foreign (CoglContext *ctx,
 
       /* If we can query GL for the actual pixel format then we'll ignore
          the passed in format and use that. */
-      if (!ctx->texture_driver->pixel_format_from_gl_internal (gl_int_format,
-                                                               &format))
+      if (!ctx->driver_vtable->pixel_format_from_gl_internal (ctx,
+                                                              gl_int_format,
+                                                              &format))
         return COGL_INVALID_HANDLE;
     }
   else
@@ -391,10 +394,11 @@ cogl_texture_2d_new_from_foreign (CoglContext *ctx,
     {
       /* Otherwise we'll assume we can derive the GL format from the
          passed in format */
-      ctx->texture_driver->pixel_format_to_gl (format,
-                                               &gl_int_format,
-                                               NULL,
-                                               NULL);
+      ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                              format,
+                                              &gl_int_format,
+                                              NULL,
+                                              NULL);
     }
 
   /* Note: We always trust the given width and height without querying
@@ -812,10 +816,11 @@ _cogl_texture_2d_get_data (CoglTexture     *tex,
 
   bpp = _cogl_pixel_format_get_bytes_per_pixel (format);
 
-  ctx->texture_driver->pixel_format_to_gl (format,
-                                           NULL, /* internal format */
-                                           &gl_format,
-                                           &gl_type);
+  ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                          format,
+                                          NULL, /* internal format */
+                                          &gl_format,
+                                          &gl_type);
 
   ctx->texture_driver->prep_gl_for_pixels_download (rowstride, bpp);
 
diff --git a/cogl/cogl-texture-3d.c b/cogl/cogl-texture-3d.c
index 8662d5a..e33c248 100644
--- a/cogl/cogl-texture-3d.c
+++ b/cogl/cogl-texture-3d.c
@@ -167,10 +167,11 @@ _cogl_texture_3d_can_create (CoglContext *ctx,
       return FALSE;
     }
 
-  ctx->texture_driver->pixel_format_to_gl (internal_format,
-                                           &gl_intformat,
-                                           NULL,
-                                           &gl_type);
+  ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                          internal_format,
+                                          &gl_intformat,
+                                          NULL,
+                                          &gl_type);
 
   /* Check that the driver can create a texture with that size */
   if (!ctx->texture_driver->size_supported_3d (GL_TEXTURE_3D,
@@ -213,10 +214,11 @@ cogl_texture_3d_new_with_size (CoglContext *ctx,
                                     error))
     return NULL;
 
-  internal_format = ctx->texture_driver->pixel_format_to_gl (internal_format,
-                                                             &gl_intformat,
-                                                             &gl_format,
-                                                             &gl_type);
+  internal_format = ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                                            internal_format,
+                                                            &gl_intformat,
+                                                            &gl_format,
+                                                            &gl_type);
 
   tex_3d = _cogl_texture_3d_create_base (ctx,
                                          width, height, depth,
diff --git a/cogl/cogl-texture-driver.h b/cogl/cogl-texture-driver.h
index 6cbc3af..07ccdf8 100644
--- a/cogl/cogl-texture-driver.h
+++ b/cogl/cogl-texture-driver.h
@@ -161,22 +161,6 @@ struct _CoglTextureDriver
                                    const GLfloat *transparent_color);
 
   /*
-   * XXX: this should live in cogl/{gl,gles}/cogl.c
-   */
-  gboolean
-  (* pixel_format_from_gl_internal) (GLenum            gl_int_format,
-                                     CoglPixelFormat  *out_format);
-
-  /*
-   * XXX: this should live in cogl/{gl,gles}/cogl.c
-   */
-  CoglPixelFormat
-  (* pixel_format_to_gl) (CoglPixelFormat  format,
-                          GLenum          *out_glintformat,
-                          GLenum          *out_glformat,
-                          GLenum          *out_gltype);
-
-  /*
    * It may depend on the driver as to what texture targets may be used when
    * creating a foreign texture. E.g. OpenGL supports ARB_texture_rectangle
    * but GLES doesn't
@@ -199,7 +183,8 @@ struct _CoglTextureDriver
    * destination has another format.
    */
   CoglPixelFormat
-  (* find_best_gl_get_data_format) (CoglPixelFormat  format,
+  (* find_best_gl_get_data_format) (CoglContext     *context,
+                                    CoglPixelFormat  format,
                                     GLenum          *closest_gl_format,
                                     GLenum          *closest_gl_type);
 };
diff --git a/cogl/cogl-texture-rectangle.c b/cogl/cogl-texture-rectangle.c
index b906f58..a7c4ae2 100644
--- a/cogl/cogl-texture-rectangle.c
+++ b/cogl/cogl-texture-rectangle.c
@@ -128,10 +128,11 @@ _cogl_texture_rectangle_can_create (unsigned int width,
       return FALSE;
     }
 
-  ctx->texture_driver->pixel_format_to_gl (internal_format,
-                                           &gl_intformat,
-                                           NULL,
-                                           &gl_type);
+  ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                          internal_format,
+                                          &gl_intformat,
+                                          NULL,
+                                          &gl_type);
 
   /* Check that the driver can create a texture with that size */
   if (!ctx->texture_driver->size_supported (GL_TEXTURE_RECTANGLE_ARB,
@@ -196,10 +197,11 @@ cogl_texture_rectangle_new_with_size (CoglContext *ctx,
                                            internal_format, error))
     return NULL;
 
-  internal_format = ctx->texture_driver->pixel_format_to_gl (internal_format,
-                                                             &gl_intformat,
-                                                             &gl_format,
-                                                             &gl_type);
+  internal_format = ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                                            internal_format,
+                                                            &gl_intformat,
+                                                            &gl_format,
+                                                            &gl_type);
 
   tex_rect = _cogl_texture_rectangle_create_base (width, height,
                                                   internal_format);
@@ -320,8 +322,9 @@ _cogl_texture_rectangle_new_from_foreign (GLuint gl_handle,
 
       /* If we can query GL for the actual pixel format then we'll ignore
          the passed in format and use that. */
-      if (!ctx->texture_driver->pixel_format_from_gl_internal (gl_int_format,
-                                                               &format))
+      if (!ctx->driver_vtable->pixel_format_from_gl_internal (ctx,
+                                                              gl_int_format,
+                                                              &format))
         return NULL;
     }
   else
@@ -329,10 +332,11 @@ _cogl_texture_rectangle_new_from_foreign (GLuint gl_handle,
     {
       /* Otherwise we'll assume we can derive the GL format from the
          passed in format */
-      ctx->texture_driver->pixel_format_to_gl (format,
-                                               &gl_int_format,
-                                               NULL,
-                                               NULL);
+      ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                              format,
+                                              &gl_int_format,
+                                              NULL,
+                                              NULL);
     }
 
   /* Note: We always trust the given width and height without querying
@@ -532,10 +536,11 @@ _cogl_texture_rectangle_get_data (CoglTexture     *tex,
 
   bpp = _cogl_pixel_format_get_bytes_per_pixel (format);
 
-  ctx->texture_driver->pixel_format_to_gl (format,
-                                           NULL, /* internal format */
-                                           &gl_format,
-                                           &gl_type);
+  ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                          format,
+                                          NULL, /* internal format */
+                                          &gl_format,
+                                          &gl_type);
 
   ctx->texture_driver->prep_gl_for_pixels_download (rowstride, bpp);
 
diff --git a/cogl/cogl-texture.c b/cogl/cogl-texture.c
index 6b08ec5..27cbb64 100644
--- a/cogl/cogl-texture.c
+++ b/cogl/cogl-texture.c
@@ -212,24 +212,27 @@ _cogl_texture_prepare_for_upload (CoglBitmap      *src_bmp,
       /* Use the source format from the src bitmap type and the internal
          format from the dst format type so that GL can do the
          conversion */
-      ctx->texture_driver->pixel_format_to_gl (src_format,
-                                               NULL, /* internal format */
-                                               out_glformat,
-                                               out_gltype);
-      ctx->texture_driver->pixel_format_to_gl (dst_format,
-                                               out_glintformat,
-                                               NULL,
-                                               NULL);
+      ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                              src_format,
+                                              NULL, /* internal format */
+                                              out_glformat,
+                                              out_gltype);
+      ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                              dst_format,
+                                              out_glintformat,
+                                              NULL,
+                                              NULL);
 
     }
   else
     {
       CoglPixelFormat closest_format;
 
-      closest_format = ctx->texture_driver->pixel_format_to_gl (dst_format,
-                                                                out_glintformat,
-                                                                out_glformat,
-                                                                out_gltype);
+      closest_format = ctx->driver_vtable->pixel_format_to_gl (ctx,
+                                                               dst_format,
+                                                               out_glintformat,
+                                                               out_glformat,
+                                                               out_gltype);
 
       if (closest_format != src_format)
         dst_bmp = _cogl_bitmap_convert (src_bmp, closest_format);
@@ -1148,7 +1151,8 @@ cogl_texture_get_data (CoglTexture     *texture,
     return byte_size;
 
   closest_format =
-    ctx->texture_driver->find_best_gl_get_data_format (format,
+    ctx->texture_driver->find_best_gl_get_data_format (ctx,
+                                                       format,
                                                        &closest_gl_format,
                                                        &closest_gl_type);
 
diff --git a/cogl/driver/gl/cogl-gl.c b/cogl/driver/gl/cogl-gl.c
index b35ddbe..6d39033 100644
--- a/cogl/driver/gl/cogl-gl.c
+++ b/cogl/driver/gl/cogl-gl.c
@@ -34,13 +34,199 @@
 #include "cogl-renderer-private.h"
 
 static gboolean
-_cogl_get_gl_version (int *major_out, int *minor_out)
+_cogl_driver_pixel_format_from_gl_internal (CoglContext *context,
+                                            GLenum gl_int_format,
+                                            CoglPixelFormat *out_format)
+{
+  /* It doesn't really matter we convert to exact same
+     format (some have no cogl match anyway) since format
+     is re-matched against cogl when getting or setting
+     texture image data.
+  */
+
+  switch (gl_int_format)
+    {
+    case GL_ALPHA: case GL_ALPHA4: case GL_ALPHA8:
+    case GL_ALPHA12: case GL_ALPHA16:
+
+      *out_format = COGL_PIXEL_FORMAT_A_8;
+      return TRUE;
+
+    case GL_LUMINANCE: case GL_LUMINANCE4: case GL_LUMINANCE8:
+    case GL_LUMINANCE12: case GL_LUMINANCE16:
+
+      *out_format = COGL_PIXEL_FORMAT_G_8;
+      return TRUE;
+
+    case GL_RGB: case GL_RGB4: case GL_RGB5: case GL_RGB8:
+    case GL_RGB10: case GL_RGB12: case GL_RGB16: case GL_R3_G3_B2:
+
+      *out_format = COGL_PIXEL_FORMAT_RGB_888;
+      return TRUE;
+
+    case GL_RGBA: case GL_RGBA2: case GL_RGBA4: case GL_RGB5_A1:
+    case GL_RGBA8: case GL_RGB10_A2: case GL_RGBA12: case GL_RGBA16:
+
+      *out_format = COGL_PIXEL_FORMAT_RGBA_8888;
+      return TRUE;
+    }
+
+  return FALSE;
+}
+
+static CoglPixelFormat
+_cogl_driver_pixel_format_to_gl (CoglContext *context,
+                                 CoglPixelFormat  format,
+                                 GLenum *out_glintformat,
+                                 GLenum *out_glformat,
+                                 GLenum *out_gltype)
+{
+  CoglPixelFormat required_format;
+  GLenum glintformat;
+  GLenum glformat = 0;
+  GLenum gltype;
+
+  required_format = format;
+
+  /* Find GL equivalents */
+  switch (format)
+    {
+    case COGL_PIXEL_FORMAT_A_8:
+      glintformat = GL_ALPHA;
+      glformat = GL_ALPHA;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+    case COGL_PIXEL_FORMAT_G_8:
+      glintformat = GL_LUMINANCE;
+      glformat = GL_LUMINANCE;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+
+    case COGL_PIXEL_FORMAT_RGB_888:
+      glintformat = GL_RGB;
+      glformat = GL_RGB;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+    case COGL_PIXEL_FORMAT_BGR_888:
+      glintformat = GL_RGB;
+      glformat = GL_BGR;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+    case COGL_PIXEL_FORMAT_RGBA_8888:
+    case COGL_PIXEL_FORMAT_RGBA_8888_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+    case COGL_PIXEL_FORMAT_BGRA_8888:
+    case COGL_PIXEL_FORMAT_BGRA_8888_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_BGRA;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+
+      /* The following two types of channel ordering
+       * have no GL equivalent unless defined using
+       * system word byte ordering */
+    case COGL_PIXEL_FORMAT_ARGB_8888:
+    case COGL_PIXEL_FORMAT_ARGB_8888_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_BGRA;
+#if G_BYTE_ORDER == G_LITTLE_ENDIAN
+      gltype = GL_UNSIGNED_INT_8_8_8_8;
+#else
+      gltype = GL_UNSIGNED_INT_8_8_8_8_REV;
+#endif
+      break;
+
+    case COGL_PIXEL_FORMAT_ABGR_8888:
+    case COGL_PIXEL_FORMAT_ABGR_8888_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+#if G_BYTE_ORDER == G_LITTLE_ENDIAN
+      gltype = GL_UNSIGNED_INT_8_8_8_8;
+#else
+      gltype = GL_UNSIGNED_INT_8_8_8_8_REV;
+#endif
+      break;
+
+    case COGL_PIXEL_FORMAT_RGBA_1010102:
+    case COGL_PIXEL_FORMAT_RGBA_1010102_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+      gltype = GL_UNSIGNED_INT_10_10_10_2;
+      break;
+
+    case COGL_PIXEL_FORMAT_BGRA_1010102:
+    case COGL_PIXEL_FORMAT_BGRA_1010102_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_BGRA;
+      gltype = GL_UNSIGNED_INT_10_10_10_2;
+      break;
+
+    case COGL_PIXEL_FORMAT_ABGR_2101010:
+    case COGL_PIXEL_FORMAT_ABGR_2101010_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+      gltype = GL_UNSIGNED_INT_2_10_10_10_REV;
+      break;
+
+    case COGL_PIXEL_FORMAT_ARGB_2101010:
+    case COGL_PIXEL_FORMAT_ARGB_2101010_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_BGRA;
+      gltype = GL_UNSIGNED_INT_2_10_10_10_REV;
+      break;
+
+      /* The following three types of channel ordering
+       * are always defined using system word byte
+       * ordering (even according to GLES spec) */
+    case COGL_PIXEL_FORMAT_RGB_565:
+      glintformat = GL_RGB;
+      glformat = GL_RGB;
+      gltype = GL_UNSIGNED_SHORT_5_6_5;
+      break;
+    case COGL_PIXEL_FORMAT_RGBA_4444:
+    case COGL_PIXEL_FORMAT_RGBA_4444_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+      gltype = GL_UNSIGNED_SHORT_4_4_4_4;
+      break;
+    case COGL_PIXEL_FORMAT_RGBA_5551:
+    case COGL_PIXEL_FORMAT_RGBA_5551_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+      gltype = GL_UNSIGNED_SHORT_5_5_5_1;
+      break;
+
+    case COGL_PIXEL_FORMAT_ANY:
+    case COGL_PIXEL_FORMAT_YUV:
+      g_assert_not_reached ();
+      break;
+    }
+
+  /* All of the pixel formats are handled above so if this hits then
+     we've been given an invalid pixel format */
+  g_assert (glformat != 0);
+
+  if (out_glintformat != NULL)
+    *out_glintformat = glintformat;
+  if (out_glformat != NULL)
+    *out_glformat = glformat;
+  if (out_gltype != NULL)
+    *out_gltype = gltype;
+
+  return required_format;
+}
+
+static gboolean
+_cogl_get_gl_version (CoglContext *ctx,
+                      int *major_out,
+                      int *minor_out)
 {
   const char *version_string, *major_end, *minor_end;
   int major = 0, minor = 0;
 
-  _COGL_GET_CONTEXT (ctx, FALSE);
-
   /* Get the OpenGL version number */
   if ((version_string = (const char *) ctx->glGetString (GL_VERSION)) == NULL)
     return FALSE;
@@ -77,7 +263,7 @@ check_gl_version (CoglContext *ctx,
   int major, minor;
   const char *gl_extensions;
 
-  if (!_cogl_get_gl_version (&major, &minor))
+  if (!_cogl_get_gl_version (ctx, &major, &minor))
     {
       g_set_error (error,
                    COGL_DRIVER_ERROR,
@@ -119,9 +305,9 @@ check_gl_version (CoglContext *ctx,
   return TRUE;
 }
 
-gboolean
-_cogl_gl_update_features (CoglContext *context,
-                          GError **error)
+static gboolean
+_cogl_driver_update_features (CoglContext *ctx,
+                              GError **error)
 {
   CoglPrivateFeatureFlags private_flags = 0;
   CoglFeatureFlags flags = 0;
@@ -130,16 +316,14 @@ _cogl_gl_update_features (CoglContext *context,
   int num_stencil_bits = 0;
   int gl_major = 0, gl_minor = 0;
 
-  _COGL_GET_CONTEXT (ctx, FALSE);
-
   /* We have to special case getting the pointer to the glGetString
      function because we need to use it to determine what functions we
      can expect */
-  context->glGetString =
-    (void *) _cogl_renderer_get_proc_address (context->display->renderer,
+  ctx->glGetString =
+    (void *) _cogl_renderer_get_proc_address (ctx->display->renderer,
                                               "glGetString");
 
-  if (!check_gl_version (context, error))
+  if (!check_gl_version (ctx, error))
     return FALSE;
 
   COGL_NOTE (WINSYS,
@@ -153,7 +337,7 @@ _cogl_gl_update_features (CoglContext *context,
              ctx->glGetString (GL_VERSION),
              ctx->glGetString (GL_EXTENSIONS));
 
-  _cogl_get_gl_version (&gl_major, &gl_minor);
+  _cogl_get_gl_version (ctx, &gl_major, &gl_minor);
 
   flags = (COGL_FEATURE_TEXTURE_READ_PIXELS
            | COGL_FEATURE_UNSIGNED_INT_INDICES
@@ -167,7 +351,7 @@ _cogl_gl_update_features (CoglContext *context,
 
   gl_extensions = (const char *)ctx->glGetString (GL_EXTENSIONS);
 
-  _cogl_feature_check_ext_functions (context,
+  _cogl_feature_check_ext_functions (ctx,
                                      gl_major,
                                      gl_minor,
                                      gl_extensions);
@@ -200,16 +384,16 @@ _cogl_gl_update_features (CoglContext *context,
   if (max_clip_planes >= 4)
     private_flags |= COGL_PRIVATE_FEATURE_FOUR_CLIP_PLANES;
 
-  if (context->glGenRenderbuffers)
+  if (ctx->glGenRenderbuffers)
     {
       flags |= COGL_FEATURE_OFFSCREEN;
       COGL_FLAGS_SET (ctx->features, COGL_FEATURE_ID_OFFSCREEN, TRUE);
     }
 
-  if (context->glBlitFramebuffer)
+  if (ctx->glBlitFramebuffer)
     private_flags |= COGL_PRIVATE_FEATURE_OFFSCREEN_BLIT;
 
-  if (context->glRenderbufferStorageMultisampleIMG)
+  if (ctx->glRenderbufferStorageMultisampleIMG)
     {
       flags |= COGL_FEATURE_OFFSCREEN_MULTISAMPLE;
       COGL_FLAGS_SET (ctx->features,
@@ -227,19 +411,19 @@ _cogl_gl_update_features (CoglContext *context,
       COGL_FLAGS_SET (ctx->features, COGL_FEATURE_ID_POINT_SPRITE, TRUE);
     }
 
-  if (context->glGenPrograms)
+  if (ctx->glGenPrograms)
     {
       flags |= COGL_FEATURE_SHADERS_ARBFP;
       COGL_FLAGS_SET (ctx->features, COGL_FEATURE_ID_ARBFP, TRUE);
     }
 
-  if (context->glCreateProgram)
+  if (ctx->glCreateProgram)
     {
       flags |= COGL_FEATURE_SHADERS_GLSL;
       COGL_FLAGS_SET (ctx->features, COGL_FEATURE_ID_GLSL, TRUE);
     }
 
-  if (context->glGenBuffers)
+  if (ctx->glGenBuffers)
     {
       private_flags |= COGL_PRIVATE_FEATURE_VBOS;
       flags |= (COGL_FEATURE_MAP_BUFFER_FOR_READ |
@@ -257,21 +441,29 @@ _cogl_gl_update_features (CoglContext *context,
                       COGL_FEATURE_ID_TEXTURE_RECTANGLE, TRUE);
     }
 
-  if (context->glTexImage3D)
+  if (ctx->glTexImage3D)
     {
       flags |= COGL_FEATURE_TEXTURE_3D;
       COGL_FLAGS_SET (ctx->features, COGL_FEATURE_ID_TEXTURE_3D, TRUE);
     }
 
-  if (context->glEGLImageTargetTexture2D)
+  if (ctx->glEGLImageTargetTexture2D)
     private_flags |= COGL_PRIVATE_FEATURE_TEXTURE_2D_FROM_EGL_IMAGE;
 
   if (_cogl_check_extension ("GL_EXT_packed_depth_stencil", gl_extensions))
     private_flags |= COGL_PRIVATE_FEATURE_EXT_PACKED_DEPTH_STENCIL;
 
   /* Cache features */
-  context->private_feature_flags |= private_flags;
-  context->feature_flags |= flags;
+  ctx->private_feature_flags |= private_flags;
+  ctx->feature_flags |= flags;
 
   return TRUE;
 }
+
+const CoglDriverVtable
+_cogl_driver_gl =
+  {
+    _cogl_driver_pixel_format_from_gl_internal,
+    _cogl_driver_pixel_format_to_gl,
+    _cogl_driver_update_features
+  };
diff --git a/cogl/driver/gl/cogl-texture-driver-gl.c b/cogl/driver/gl/cogl-texture-driver-gl.c
index 83d47ae..373fade 100644
--- a/cogl/driver/gl/cogl-texture-driver-gl.c
+++ b/cogl/driver/gl/cogl-texture-driver-gl.c
@@ -353,190 +353,6 @@ _cogl_texture_driver_try_setting_gl_border_color (
 }
 
 static gboolean
-_cogl_texture_driver_pixel_format_from_gl_internal (GLenum gl_int_format,
-                                                    CoglPixelFormat  *out_format)
-{
-  /* It doesn't really matter we convert to exact same
-     format (some have no cogl match anyway) since format
-     is re-matched against cogl when getting or setting
-     texture image data.
-  */
-
-  switch (gl_int_format)
-    {
-    case GL_ALPHA: case GL_ALPHA4: case GL_ALPHA8:
-    case GL_ALPHA12: case GL_ALPHA16:
-
-      *out_format = COGL_PIXEL_FORMAT_A_8;
-      return TRUE;
-
-    case GL_LUMINANCE: case GL_LUMINANCE4: case GL_LUMINANCE8:
-    case GL_LUMINANCE12: case GL_LUMINANCE16:
-
-      *out_format = COGL_PIXEL_FORMAT_G_8;
-      return TRUE;
-
-    case GL_RGB: case GL_RGB4: case GL_RGB5: case GL_RGB8:
-    case GL_RGB10: case GL_RGB12: case GL_RGB16: case GL_R3_G3_B2:
-
-      *out_format = COGL_PIXEL_FORMAT_RGB_888;
-      return TRUE;
-
-    case GL_RGBA: case GL_RGBA2: case GL_RGBA4: case GL_RGB5_A1:
-    case GL_RGBA8: case GL_RGB10_A2: case GL_RGBA12: case GL_RGBA16:
-
-      *out_format = COGL_PIXEL_FORMAT_RGBA_8888;
-      return TRUE;
-    }
-
-  return FALSE;
-}
-
-static CoglPixelFormat
-_cogl_texture_driver_pixel_format_to_gl (CoglPixelFormat  format,
-                                         GLenum          *out_glintformat,
-                                         GLenum          *out_glformat,
-                                         GLenum          *out_gltype)
-{
-  CoglPixelFormat required_format;
-  GLenum glintformat;
-  GLenum glformat = 0;
-  GLenum gltype;
-
-  required_format = format;
-
-  /* Find GL equivalents */
-  switch (format)
-    {
-    case COGL_PIXEL_FORMAT_A_8:
-      glintformat = GL_ALPHA;
-      glformat = GL_ALPHA;
-      gltype = GL_UNSIGNED_BYTE;
-      break;
-    case COGL_PIXEL_FORMAT_G_8:
-      glintformat = GL_LUMINANCE;
-      glformat = GL_LUMINANCE;
-      gltype = GL_UNSIGNED_BYTE;
-      break;
-
-    case COGL_PIXEL_FORMAT_RGB_888:
-      glintformat = GL_RGB;
-      glformat = GL_RGB;
-      gltype = GL_UNSIGNED_BYTE;
-      break;
-    case COGL_PIXEL_FORMAT_BGR_888:
-      glintformat = GL_RGB;
-      glformat = GL_BGR;
-      gltype = GL_UNSIGNED_BYTE;
-      break;
-    case COGL_PIXEL_FORMAT_RGBA_8888:
-    case COGL_PIXEL_FORMAT_RGBA_8888_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-      gltype = GL_UNSIGNED_BYTE;
-      break;
-    case COGL_PIXEL_FORMAT_BGRA_8888:
-    case COGL_PIXEL_FORMAT_BGRA_8888_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_BGRA;
-      gltype = GL_UNSIGNED_BYTE;
-      break;
-
-      /* The following two types of channel ordering
-       * have no GL equivalent unless defined using
-       * system word byte ordering */
-    case COGL_PIXEL_FORMAT_ARGB_8888:
-    case COGL_PIXEL_FORMAT_ARGB_8888_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_BGRA;
-#if G_BYTE_ORDER == G_LITTLE_ENDIAN
-      gltype = GL_UNSIGNED_INT_8_8_8_8;
-#else
-      gltype = GL_UNSIGNED_INT_8_8_8_8_REV;
-#endif
-      break;
-
-    case COGL_PIXEL_FORMAT_ABGR_8888:
-    case COGL_PIXEL_FORMAT_ABGR_8888_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-#if G_BYTE_ORDER == G_LITTLE_ENDIAN
-      gltype = GL_UNSIGNED_INT_8_8_8_8;
-#else
-      gltype = GL_UNSIGNED_INT_8_8_8_8_REV;
-#endif
-      break;
-
-    case COGL_PIXEL_FORMAT_RGBA_1010102:
-    case COGL_PIXEL_FORMAT_RGBA_1010102_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-      gltype = GL_UNSIGNED_INT_10_10_10_2;
-      break;
-
-    case COGL_PIXEL_FORMAT_BGRA_1010102:
-    case COGL_PIXEL_FORMAT_BGRA_1010102_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_BGRA;
-      gltype = GL_UNSIGNED_INT_10_10_10_2;
-      break;
-
-    case COGL_PIXEL_FORMAT_ABGR_2101010:
-    case COGL_PIXEL_FORMAT_ABGR_2101010_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-      gltype = GL_UNSIGNED_INT_2_10_10_10_REV;
-      break;
-
-    case COGL_PIXEL_FORMAT_ARGB_2101010:
-    case COGL_PIXEL_FORMAT_ARGB_2101010_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_BGRA;
-      gltype = GL_UNSIGNED_INT_2_10_10_10_REV;
-      break;
-
-      /* The following three types of channel ordering
-       * are always defined using system word byte
-       * ordering (even according to GLES spec) */
-    case COGL_PIXEL_FORMAT_RGB_565:
-      glintformat = GL_RGB;
-      glformat = GL_RGB;
-      gltype = GL_UNSIGNED_SHORT_5_6_5;
-      break;
-    case COGL_PIXEL_FORMAT_RGBA_4444:
-    case COGL_PIXEL_FORMAT_RGBA_4444_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-      gltype = GL_UNSIGNED_SHORT_4_4_4_4;
-      break;
-    case COGL_PIXEL_FORMAT_RGBA_5551:
-    case COGL_PIXEL_FORMAT_RGBA_5551_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-      gltype = GL_UNSIGNED_SHORT_5_5_5_1;
-      break;
-
-    case COGL_PIXEL_FORMAT_ANY:
-    case COGL_PIXEL_FORMAT_YUV:
-      g_assert_not_reached ();
-      break;
-    }
-
-  /* All of the pixel formats are handled above so if this hits then
-     we've been given an invalid pixel format */
-  g_assert (glformat != 0);
-
-  if (out_glintformat != NULL)
-    *out_glintformat = glintformat;
-  if (out_glformat != NULL)
-    *out_glformat = glformat;
-  if (out_gltype != NULL)
-    *out_gltype = gltype;
-
-  return required_format;
-}
-
-static gboolean
 _cogl_texture_driver_allows_foreign_gl_target (GLenum gl_target)
 {
   /* GL_ARB_texture_rectangle textures are supported if they are
@@ -561,16 +377,17 @@ _cogl_texture_driver_gl_generate_mipmaps (GLenum gl_target)
 }
 
 static CoglPixelFormat
-_cogl_texture_driver_find_best_gl_get_data_format (
-                                             CoglPixelFormat  format,
-                                             GLenum          *closest_gl_format,
-                                             GLenum          *closest_gl_type)
+_cogl_texture_driver_find_best_gl_get_data_format
+                                            (CoglContext *context,
+                                             CoglPixelFormat format,
+                                             GLenum *closest_gl_format,
+                                             GLenum *closest_gl_type)
 {
-  /* Find closest format that's supported by GL */
-  return _cogl_texture_driver_pixel_format_to_gl (format,
-                                                  NULL, /* don't need */
-                                                  closest_gl_format,
-                                                  closest_gl_type);
+  return context->driver_vtable->pixel_format_to_gl (context,
+                                                     format,
+                                                     NULL, /* don't need */
+                                                     closest_gl_format,
+                                                     closest_gl_type);
 }
 
 const CoglTextureDriver
@@ -586,8 +403,6 @@ _cogl_texture_driver_gl =
     _cogl_texture_driver_size_supported,
     _cogl_texture_driver_size_supported_3d,
     _cogl_texture_driver_try_setting_gl_border_color,
-    _cogl_texture_driver_pixel_format_from_gl_internal,
-    _cogl_texture_driver_pixel_format_to_gl,
     _cogl_texture_driver_allows_foreign_gl_target,
     _cogl_texture_driver_gl_generate_mipmaps,
     _cogl_texture_driver_find_best_gl_get_data_format
diff --git a/cogl/driver/gles/cogl-gles.c b/cogl/driver/gles/cogl-gles.c
index 8087ae0..d4c5968 100644
--- a/cogl/driver/gles/cogl-gles.c
+++ b/cogl/driver/gles/cogl-gles.c
@@ -33,9 +33,119 @@
 #include "cogl-renderer-private.h"
 #include "cogl-private.h"
 
-gboolean
-_cogl_gles_update_features (CoglContext *context,
-                            GError **error)
+static gboolean
+_cogl_driver_pixel_format_from_gl_internal (CoglContext *context,
+                                            GLenum gl_int_format,
+                                            CoglPixelFormat *out_format)
+{
+  return TRUE;
+}
+
+static CoglPixelFormat
+_cogl_driver_pixel_format_to_gl (CoglContext *context,
+                                 CoglPixelFormat  format,
+                                 GLenum *out_glintformat,
+                                 GLenum *out_glformat,
+                                 GLenum *out_gltype)
+{
+  CoglPixelFormat required_format;
+  GLenum glintformat;
+  GLenum glformat = 0;
+  GLenum gltype;
+
+  required_format = format;
+
+  /* Find GL equivalents */
+  switch (format)
+    {
+    case COGL_PIXEL_FORMAT_A_8:
+      glintformat = GL_ALPHA;
+      glformat = GL_ALPHA;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+    case COGL_PIXEL_FORMAT_G_8:
+      glintformat = GL_LUMINANCE;
+      glformat = GL_LUMINANCE;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+
+      /* Just one 24-bit ordering supported */
+    case COGL_PIXEL_FORMAT_RGB_888:
+    case COGL_PIXEL_FORMAT_BGR_888:
+      glintformat = GL_RGB;
+      glformat = GL_RGB;
+      gltype = GL_UNSIGNED_BYTE;
+      required_format = COGL_PIXEL_FORMAT_RGB_888;
+      break;
+
+      /* Just one 32-bit ordering supported */
+    case COGL_PIXEL_FORMAT_RGBA_8888:
+    case COGL_PIXEL_FORMAT_RGBA_8888_PRE:
+    case COGL_PIXEL_FORMAT_BGRA_8888:
+    case COGL_PIXEL_FORMAT_BGRA_8888_PRE:
+    case COGL_PIXEL_FORMAT_ARGB_8888:
+    case COGL_PIXEL_FORMAT_ARGB_8888_PRE:
+    case COGL_PIXEL_FORMAT_ABGR_8888:
+    case COGL_PIXEL_FORMAT_ABGR_8888_PRE:
+    case COGL_PIXEL_FORMAT_RGBA_1010102:
+    case COGL_PIXEL_FORMAT_RGBA_1010102_PRE:
+    case COGL_PIXEL_FORMAT_BGRA_1010102:
+    case COGL_PIXEL_FORMAT_BGRA_1010102_PRE:
+    case COGL_PIXEL_FORMAT_ABGR_2101010:
+    case COGL_PIXEL_FORMAT_ABGR_2101010_PRE:
+    case COGL_PIXEL_FORMAT_ARGB_2101010:
+    case COGL_PIXEL_FORMAT_ARGB_2101010_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+      gltype = GL_UNSIGNED_BYTE;
+      required_format = COGL_PIXEL_FORMAT_RGBA_8888;
+      required_format |= (format & COGL_PREMULT_BIT);
+      break;
+
+      /* The following three types of channel ordering
+       * are always defined using system word byte
+       * ordering (even according to GLES spec) */
+    case COGL_PIXEL_FORMAT_RGB_565:
+      glintformat = GL_RGB;
+      glformat = GL_RGB;
+      gltype = GL_UNSIGNED_SHORT_5_6_5;
+      break;
+    case COGL_PIXEL_FORMAT_RGBA_4444:
+    case COGL_PIXEL_FORMAT_RGBA_4444_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+      gltype = GL_UNSIGNED_SHORT_4_4_4_4;
+      break;
+    case COGL_PIXEL_FORMAT_RGBA_5551:
+    case COGL_PIXEL_FORMAT_RGBA_5551_PRE:
+      glintformat = GL_RGBA;
+      glformat = GL_RGBA;
+      gltype = GL_UNSIGNED_SHORT_5_5_5_1;
+      break;
+
+    case COGL_PIXEL_FORMAT_ANY:
+    case COGL_PIXEL_FORMAT_YUV:
+      g_assert_not_reached ();
+      break;
+    }
+
+  /* All of the pixel formats are handled above so if this hits then
+     we've been given an invalid pixel format */
+  g_assert (glformat != 0);
+
+  if (out_glintformat != NULL)
+    *out_glintformat = glintformat;
+  if (out_glformat != NULL)
+    *out_glformat = glformat;
+  if (out_gltype != NULL)
+    *out_gltype = gltype;
+
+  return required_format;
+}
+
+static gboolean
+_cogl_driver_update_features (CoglContext *context,
+                              GError **error)
 {
   CoglPrivateFeatureFlags private_flags = 0;
   CoglFeatureFlags flags = 0;
@@ -172,3 +282,11 @@ _cogl_gles_update_features (CoglContext *context,
 
   return TRUE;
 }
+
+const CoglDriverVtable
+_cogl_driver_gles =
+  {
+    _cogl_driver_pixel_format_from_gl_internal,
+    _cogl_driver_pixel_format_to_gl,
+    _cogl_driver_update_features
+  };
diff --git a/cogl/driver/gles/cogl-texture-driver-gles.c b/cogl/driver/gles/cogl-texture-driver-gles.c
index 2bc596b..ad1c248 100644
--- a/cogl/driver/gles/cogl-texture-driver-gles.c
+++ b/cogl/driver/gles/cogl-texture-driver-gles.c
@@ -390,114 +390,6 @@ _cogl_texture_driver_try_setting_gl_border_color (
 }
 
 static gboolean
-_cogl_texture_driver_pixel_format_from_gl_internal (GLenum gl_int_format,
-                                                    CoglPixelFormat *out_format)
-{
-  return TRUE;
-}
-
-static CoglPixelFormat
-_cogl_texture_driver_pixel_format_to_gl (CoglPixelFormat  format,
-                                         GLenum          *out_glintformat,
-                                         GLenum          *out_glformat,
-                                         GLenum          *out_gltype)
-{
-  CoglPixelFormat required_format;
-  GLenum glintformat;
-  GLenum glformat = 0;
-  GLenum gltype;
-
-  required_format = format;
-
-  /* Find GL equivalents */
-  switch (format)
-    {
-    case COGL_PIXEL_FORMAT_A_8:
-      glintformat = GL_ALPHA;
-      glformat = GL_ALPHA;
-      gltype = GL_UNSIGNED_BYTE;
-      break;
-    case COGL_PIXEL_FORMAT_G_8:
-      glintformat = GL_LUMINANCE;
-      glformat = GL_LUMINANCE;
-      gltype = GL_UNSIGNED_BYTE;
-      break;
-
-      /* Just one 24-bit ordering supported */
-    case COGL_PIXEL_FORMAT_RGB_888:
-    case COGL_PIXEL_FORMAT_BGR_888:
-      glintformat = GL_RGB;
-      glformat = GL_RGB;
-      gltype = GL_UNSIGNED_BYTE;
-      required_format = COGL_PIXEL_FORMAT_RGB_888;
-      break;
-
-      /* Just one 32-bit ordering supported */
-    case COGL_PIXEL_FORMAT_RGBA_8888:
-    case COGL_PIXEL_FORMAT_RGBA_8888_PRE:
-    case COGL_PIXEL_FORMAT_BGRA_8888:
-    case COGL_PIXEL_FORMAT_BGRA_8888_PRE:
-    case COGL_PIXEL_FORMAT_ARGB_8888:
-    case COGL_PIXEL_FORMAT_ARGB_8888_PRE:
-    case COGL_PIXEL_FORMAT_ABGR_8888:
-    case COGL_PIXEL_FORMAT_ABGR_8888_PRE:
-    case COGL_PIXEL_FORMAT_RGBA_1010102:
-    case COGL_PIXEL_FORMAT_RGBA_1010102_PRE:
-    case COGL_PIXEL_FORMAT_BGRA_1010102:
-    case COGL_PIXEL_FORMAT_BGRA_1010102_PRE:
-    case COGL_PIXEL_FORMAT_ABGR_2101010:
-    case COGL_PIXEL_FORMAT_ABGR_2101010_PRE:
-    case COGL_PIXEL_FORMAT_ARGB_2101010:
-    case COGL_PIXEL_FORMAT_ARGB_2101010_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-      gltype = GL_UNSIGNED_BYTE;
-      required_format = COGL_PIXEL_FORMAT_RGBA_8888;
-      required_format |= (format & COGL_PREMULT_BIT);
-      break;
-
-      /* The following three types of channel ordering
-       * are always defined using system word byte
-       * ordering (even according to GLES spec) */
-    case COGL_PIXEL_FORMAT_RGB_565:
-      glintformat = GL_RGB;
-      glformat = GL_RGB;
-      gltype = GL_UNSIGNED_SHORT_5_6_5;
-      break;
-    case COGL_PIXEL_FORMAT_RGBA_4444:
-    case COGL_PIXEL_FORMAT_RGBA_4444_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-      gltype = GL_UNSIGNED_SHORT_4_4_4_4;
-      break;
-    case COGL_PIXEL_FORMAT_RGBA_5551:
-    case COGL_PIXEL_FORMAT_RGBA_5551_PRE:
-      glintformat = GL_RGBA;
-      glformat = GL_RGBA;
-      gltype = GL_UNSIGNED_SHORT_5_5_5_1;
-      break;
-
-    case COGL_PIXEL_FORMAT_ANY:
-    case COGL_PIXEL_FORMAT_YUV:
-      g_assert_not_reached ();
-      break;
-    }
-
-  /* All of the pixel formats are handled above so if this hits then
-     we've been given an invalid pixel format */
-  g_assert (glformat != 0);
-
-  if (out_glintformat != NULL)
-    *out_glintformat = glintformat;
-  if (out_glformat != NULL)
-    *out_glformat = glformat;
-  if (out_gltype != NULL)
-    *out_gltype = gltype;
-
-  return required_format;
-}
-
-static gboolean
 _cogl_texture_driver_allows_foreign_gl_target (GLenum gl_target)
 {
   /* Allow 2-dimensional textures only */
@@ -516,10 +408,11 @@ _cogl_texture_driver_gl_generate_mipmaps (GLenum gl_target)
 }
 
 static CoglPixelFormat
-_cogl_texture_driver_find_best_gl_get_data_format (
-                                             CoglPixelFormat  format,
-                                             GLenum          *closest_gl_format,
-                                             GLenum          *closest_gl_type)
+_cogl_texture_driver_find_best_gl_get_data_format
+                                            (CoglContext *context,
+                                             CoglPixelFormat format,
+                                             GLenum *closest_gl_format,
+                                             GLenum *closest_gl_type)
 {
   /* Find closest format that's supported by GL
      (Can't use _cogl_pixel_format_to_gl since available formats
@@ -542,8 +435,6 @@ _cogl_texture_driver_gles =
     _cogl_texture_driver_size_supported,
     _cogl_texture_driver_size_supported_3d,
     _cogl_texture_driver_try_setting_gl_border_color,
-    _cogl_texture_driver_pixel_format_from_gl_internal,
-    _cogl_texture_driver_pixel_format_to_gl,
     _cogl_texture_driver_allows_foreign_gl_target,
     _cogl_texture_driver_gl_generate_mipmaps,
     _cogl_texture_driver_find_best_gl_get_data_format
-- 
1.7.3.16.g9464b



More information about the Cogl mailing list