[Spice-devel] [PATCH 07/30] Turn image and palette cache into c style dynamic interface

Alexander Larsson alexl at redhat.com
Thu Feb 18 12:58:33 PST 2010


Instead of passing a bunch of function pointer and an opaque
pointer we make a real type and add a vtable pointer to it.
This means we can simplify all the canvas constructors, etc.
---
 client/canvas.cpp           |   30 -----------------
 client/canvas.h             |   74 ++++++++++++++++++++++++++++++++++++++----
 client/red_cairo_canvas.cpp |    5 +--
 client/red_gdi_canvas.cpp   |    6 +--
 client/red_gl_canvas.cpp    |    9 +----
 common/cairo_canvas.c       |   27 +++++-----------
 common/cairo_canvas.h       |   12 +++----
 common/canvas_base.c        |   45 ++++++++------------------
 common/canvas_base.h        |   36 +++++++++++++++-----
 common/gdi_canvas.c         |   22 +++---------
 common/gdi_canvas.h         |    6 +--
 common/gl_canvas.c          |   26 +++-----------
 common/gl_canvas.h          |   13 ++------
 server/red_worker.c         |   22 ++++++++-----
 14 files changed, 158 insertions(+), 175 deletions(-)

diff --git a/client/canvas.cpp b/client/canvas.cpp
index 04b0ce6..24ebd01 100644
--- a/client/canvas.cpp
+++ b/client/canvas.cpp
@@ -213,36 +213,6 @@ void Canvas::draw_stroke(SpiceMsgDisplayDrawStroke& stroke, int size)
     draw_stroke(&stroke.base.box, &stroke.base.clip, &stroke.data);
 }
 
-void Canvas::bits_cache_put(void *opaque, uint64_t id, cairo_surface_t *surface)
-{
-    PixmapCache* cache = static_cast<PixmapCache*>(opaque);
-    cache->add(id, surface);
-}
-
-cairo_surface_t* Canvas::bits_cache_get(void *opaque, uint64_t id)
-{
-    PixmapCache* cache = static_cast<PixmapCache*>(opaque);
-    return cache->get(id);
-}
-
-void Canvas::palette_cache_put(void *opaque, SpicePalette *palette)
-{
-    PaletteCache* cache = static_cast<PaletteCache*>(opaque);
-    AutoRef<CachedPalette> cached_palette(new CachedPalette(palette));
-    cache->add(palette->unique, *cached_palette);
-}
-
-SpicePalette* Canvas::palette_cache_get(void *opaque, uint64_t id)
-{
-    PaletteCache* cache = static_cast<PaletteCache*>(opaque);
-    return cache->get(id)->palette();
-}
-
-void Canvas::palette_cache_release(SpicePalette* palette)
-{
-    CachedPalette::unref(palette);
-}
-
 void Canvas::glz_decode(void *opaque, uint8_t *data, SpicePalette *plt, void *usr_data)
 {
     GlzDecoder* decoder = static_cast<GlzDecoder*>(opaque);
diff --git a/client/canvas.h b/client/canvas.h
index 84a654a..ac9a1f0 100644
--- a/client/canvas.h
+++ b/client/canvas.h
@@ -24,6 +24,7 @@
 #include <spice/protocol.h>
 #include "cache.hpp"
 #include "shared_cache.hpp"
+#include "canvas_base.h"
 #include "canvas_utils.h"
 #include "glz_decoded_image.h"
 #include "glz_decoder.h"
@@ -52,7 +53,35 @@ public:
     static const char* name() { return "pixmap";}
 };
 
-typedef SharedCache<cairo_surface_t, PixmapCacheTreat, 1024> PixmapCache;
+class SpiceImageCacheBase;
+
+typedef SharedCache<cairo_surface_t, PixmapCacheTreat, 1024, SpiceImageCacheBase> PixmapCache;
+
+class SpiceImageCacheBase {
+public:
+    SpiceImageCache base;
+
+    static void op_put(SpiceImageCache *c, uint64_t id, cairo_surface_t *surface)
+    {
+	PixmapCache* cache = reinterpret_cast<PixmapCache*>(c);
+	cache->add(id, surface);
+    }
+
+    static cairo_surface_t* op_get(SpiceImageCache *c, uint64_t id)
+    {
+	PixmapCache* cache = reinterpret_cast<PixmapCache*>(c);
+	return cache->get(id);
+    }
+
+    SpiceImageCacheBase()
+    {
+	static SpiceImageCacheOps cache_ops = {
+	    op_put,
+	    op_get
+	};
+	base.ops = &cache_ops;
+    }
+};
 
 class CachedPalette {
 public:
@@ -113,7 +142,43 @@ public:
     static const char* name() { return "palette";}
 };
 
-typedef Cache<CachedPalette, PaletteCacheTreat, 1024> PaletteCache;
+class SpicePaletteCacheBase;
+typedef Cache<CachedPalette, PaletteCacheTreat, 1024, SpicePaletteCacheBase> PaletteCache;
+
+class SpicePaletteCacheBase {
+public:
+    SpicePaletteCache base;
+
+    static void op_put(SpicePaletteCache *c, SpicePalette *palette)
+    {
+        PaletteCache* cache = reinterpret_cast<PaletteCache*>(c);
+        AutoRef<CachedPalette> cached_palette(new CachedPalette(palette));
+        cache->add(palette->unique, *cached_palette);
+    }
+
+    static SpicePalette* op_get(SpicePaletteCache *c, uint64_t id)
+    {
+        PaletteCache* cache = reinterpret_cast<PaletteCache*>(c);
+        return cache->get(id)->palette();
+    }
+
+    static void op_release (SpicePaletteCache *c,
+			    SpicePalette *palette)
+    {
+        CachedPalette::unref(palette);
+    }
+
+    SpicePaletteCacheBase()
+    {
+        static SpicePaletteCacheOps cache_ops = {
+            op_put,
+            op_get,
+            op_release
+        };
+        base.ops = &cache_ops;
+    }
+};
+
 
 /* Lz decoder related classes */
 
@@ -230,11 +295,6 @@ protected:
 
     PixmapCache& pixmap_cache() { return _pixmap_cache;}
     PaletteCache& palette_cache() { return _palette_cache;}
-    static void bits_cache_put(void *opaque, uint64_t id, cairo_surface_t *surface);
-    static cairo_surface_t* bits_cache_get(void *opaque, uint64_t id);
-    static void palette_cache_put(void *opaque, SpicePalette *palette);
-    static SpicePalette* palette_cache_get(void *opaque, uint64_t id);
-    static void palette_cache_release(SpicePalette* palette);
 
     GlzDecoder& glz_decoder() {return _glz_decoder;}
     static void glz_decode(void *opaque, uint8_t *data, SpicePalette *plt, void *usr_data);
diff --git a/client/red_cairo_canvas.cpp b/client/red_cairo_canvas.cpp
index 08880ea..80a89b7 100644
--- a/client/red_cairo_canvas.cpp
+++ b/client/red_cairo_canvas.cpp
@@ -99,9 +99,8 @@ void CCanvas::set_mode(int width, int height, int depth, RedWindow *win)
         THROW("create cairo failed, %s", cairo_status_to_string(cairo_status(cairo)));
     }
     if (!(_canvas = canvas_create(cairo, depth,
-                                  &pixmap_cache(), bits_cache_put, bits_cache_get,
-                                  &palette_cache(), palette_cache_put, palette_cache_get,
-                                  palette_cache_release,
+                                  &pixmap_cache().base,
+                                  &palette_cache().base,
                                   &glz_decoder(),
                                   glz_decode))) {
         THROW("create canvas failed");
diff --git a/client/red_gdi_canvas.cpp b/client/red_gdi_canvas.cpp
index 8e50a06..3dd33d2 100644
--- a/client/red_gdi_canvas.cpp
+++ b/client/red_gdi_canvas.cpp
@@ -81,10 +81,8 @@ void GDICanvas::set_mode(int width, int height, int depth)
     create_pixmap(width, height);
     if (!(_canvas = gdi_canvas_create(_pixmap->get_dc(),
                                       &_pixmap->get_mutex(),
-                                      depth, &pixmap_cache(), bits_cache_put,
-                                      bits_cache_get, &palette_cache(),
-                                      palette_cache_put, palette_cache_get,
-                                      palette_cache_release,
+                                      depth, &pixmap_cache().base,
+				      &palette_cache().base,
                                       &glz_decoder(),
                                       glz_decode))) {
         THROW("create canvas failed");
diff --git a/client/red_gl_canvas.cpp b/client/red_gl_canvas.cpp
index 830de03..43bf424 100644
--- a/client/red_gl_canvas.cpp
+++ b/client/red_gl_canvas.cpp
@@ -87,13 +87,8 @@ void GCanvas::set_mode(int width, int height, int depth, RedWindow *win,
 
     create_pixmap(width, height, win, rendertype);
     if (!(_canvas = gl_canvas_create(NULL, width, height, depth,
-                                     &pixmap_cache(),
-                                     bits_cache_put,
-                                     bits_cache_get,
-                                     &palette_cache(),
-                                     palette_cache_put,
-                                     palette_cache_get,
-                                     palette_cache_release,
+                                     &pixmap_cache().base,
+                                     &palette_cache().base,
                                      &glz_decoder(),
                                      glz_decode))) {
         THROW("create canvas failed");
diff --git a/common/cairo_canvas.c b/common/cairo_canvas.c
index 4f3c780..51069dd 100644
--- a/common/cairo_canvas.c
+++ b/common/cairo_canvas.c
@@ -438,7 +438,7 @@ static cairo_surface_t *canvas_get_invers_image(CairoCanvas *canvas, SPICE_ADDRE
     }
 #endif
     case SPICE_IMAGE_TYPE_FROM_CACHE:
-        surface = canvas->base.bits_cache_get(canvas->base.bits_cache_opaque, descriptor->id);
+        surface = canvas->base.bits_cache->ops->get(canvas->base.bits_cache, descriptor->id);
         break;
     case SPICE_IMAGE_TYPE_BITMAP: {
         SpiceBitmapImage *bitmap = (SpiceBitmapImage *)descriptor;
@@ -465,7 +465,7 @@ static cairo_surface_t *canvas_get_invers_image(CairoCanvas *canvas, SPICE_ADDRE
     }
 
     if (cache_me) {
-        canvas->base.bits_cache_put(canvas->base.bits_cache_opaque, descriptor->id, surface);
+        canvas->base.bits_cache->ops->put(canvas->base.bits_cache, descriptor->id, surface);
     }
 
     invers = canvas_handle_inverse_user_data(surface);
@@ -1596,15 +1596,11 @@ static int need_init = 1;
 
 #ifdef CAIRO_CANVAS_CACHE
 CairoCanvas *canvas_create(cairo_t *cairo, int bits,
-                           void *bits_cache_opaque,
-                           bits_cache_put_fn_t bits_cache_put, bits_cache_get_fn_t bits_cache_get,
-                           void *palette_cache_opaque, palette_cache_put_fn_t palette_cache_put,
-                           palette_cache_get_fn_t palette_cache_get,
-                           palette_cache_release_fn_t palette_cache_release
+                           SpiceImageCache *bits_cache,
+                           SpicePaletteCache *palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
 CairoCanvas *canvas_create(cairo_t *cairo, int bits,
-                           void *bits_cache_opaque,
-                           bits_cache_put_fn_t bits_cache_put, bits_cache_get_fn_t bits_cache_get
+                           SpiceImageCache *bits_cache
 #else
 CairoCanvas *canvas_create(cairo_t *cairo, int bits
 #endif
@@ -1626,18 +1622,11 @@ CairoCanvas *canvas_create(cairo_t *cairo, int bits
     memset(canvas, 0, sizeof(CairoCanvas));
 #ifdef CAIRO_CANVAS_CACHE
     init_ok = canvas_base_init(&canvas->base, bits,
-                               bits_cache_opaque,
-                               bits_cache_put,
-                               bits_cache_get,
-                               palette_cache_opaque,
-                               palette_cache_put,
-                               palette_cache_get,
-                               palette_cache_release
+                               bits_cache,
+                               palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
     init_ok = canvas_base_init(&canvas->base, bits,
-                               bits_cache_opaque,
-                               bits_cache_put,
-                               bits_cache_get
+                               bits_cache
 #else
     init_ok = canvas_base_init(&canvas->base, bits
 #endif
diff --git a/common/cairo_canvas.h b/common/cairo_canvas.h
index bf6ff90..485cf24 100644
--- a/common/cairo_canvas.h
+++ b/common/cairo_canvas.h
@@ -62,14 +62,12 @@ void canvas_set_access_params(CairoCanvas *canvas, unsigned long base, unsigned
 cairo_t *canvas_get_cairo(CairoCanvas *canvas);
 
 #ifdef CAIRO_CANVAS_CACHE
-CairoCanvas *canvas_create(cairo_t *cairo, int bits, void *bits_cache_opaque,
-                           bits_cache_put_fn_t bits_cache_put, bits_cache_get_fn_t bits_cache_get,
-                           void *palette_cache_opaque, palette_cache_put_fn_t palette_cache_put,
-                           palette_cache_get_fn_t palette_cache_get,
-                           palette_cache_release_fn_t palette_cache_release
+CairoCanvas *canvas_create(cairo_t *cairo, int bits,
+			   SpiceImageCache *bits_cache,
+			   SpicePaletteCache *palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
-CairoCanvas *canvas_create(cairo_t *cairo, int bits, void *bits_cache_opaque,
-                           bits_cache_put_fn_t bits_cache_put, bits_cache_get_fn_t bits_cache_get
+CairoCanvas *canvas_create(cairo_t *cairo, int bits,
+			   SpiceImageCache *bits_cache
 #else
 CairoCanvas *canvas_create(cairo_t *cairo, int bits
 #endif
diff --git a/common/canvas_base.c b/common/canvas_base.c
index ebb9846..0ddbaf4 100644
--- a/common/canvas_base.c
+++ b/common/canvas_base.c
@@ -171,15 +171,10 @@ typedef struct CanvasBase {
 #endif
 
 #if defined(CAIRO_CANVAS_CACHE) || defined(CAIRO_CANVAS_IMAGE_CACHE)
-    void *bits_cache_opaque;
-    bits_cache_put_fn_t bits_cache_put;
-    bits_cache_get_fn_t bits_cache_get;
+    SpiceImageCache *bits_cache;
 #endif
 #ifdef CAIRO_CANVAS_CACHE
-    void *palette_cache_opaque;
-    palette_cache_put_fn_t palette_cache_put;
-    palette_cache_get_fn_t palette_cache_get;
-    palette_cache_release_fn_t palette_cache_release;
+    SpicePaletteCache *palette_cache;
 #endif
 #ifdef WIN32
     HDC dc;
@@ -535,13 +530,13 @@ static inline SpicePalette *canvas_get_palett(CanvasBase *canvas, SPICE_ADDRESS
     }
 
     if (flags & SPICE_BITMAP_FLAGS_PAL_FROM_CACHE) {
-        palette = canvas->palette_cache_get(canvas->palette_cache_opaque, base_palette);
+        palette = canvas->palette_cache->ops->get(canvas->palette_cache, base_palette);
     } else if (flags & SPICE_BITMAP_FLAGS_PAL_CACHE_ME) {
         palette = (SpicePalette *)SPICE_GET_ADDRESS(base_palette);
         access_test(canvas, palette, sizeof(SpicePalette));
         access_test(canvas, palette, sizeof(SpicePalette) + palette->num_ents * sizeof(uint32_t));
         canvas_localize_palette(canvas, palette);
-        canvas->palette_cache_put(canvas->palette_cache_opaque, palette);
+        canvas->palette_cache->ops->put(canvas->palette_cache, palette);
     } else {
         palette = (SpicePalette *)SPICE_GET_ADDRESS(base_palette);
         canvas_localize_palette(canvas, palette);
@@ -716,7 +711,7 @@ static cairo_surface_t *canvas_get_bits(CanvasBase *canvas, SpiceBitmap *bitmap)
     surface = canvas_bitmap_to_surface(canvas, bitmap, palette);
 
     if (palette && (bitmap->flags & SPICE_BITMAP_FLAGS_PAL_FROM_CACHE)) {
-        canvas->palette_cache_release(palette);
+        canvas->palette_cache->ops->release(canvas->palette_cache, palette);
     }
 
     return surface;
@@ -851,7 +846,7 @@ static cairo_surface_t *canvas_get_image(CanvasBase *canvas, SPICE_ADDRESS addr)
     }
 #endif
     case SPICE_IMAGE_TYPE_FROM_CACHE:
-        return canvas->bits_cache_get(canvas->bits_cache_opaque, descriptor->id);
+        return canvas->bits_cache->ops->get(canvas->bits_cache, descriptor->id);
     case SPICE_IMAGE_TYPE_BITMAP: {
         SpiceBitmapImage *bitmap = (SpiceBitmapImage *)descriptor;
         access_test(canvas, descriptor, sizeof(SpiceBitmapImage));
@@ -863,7 +858,7 @@ static cairo_surface_t *canvas_get_image(CanvasBase *canvas, SPICE_ADDRESS addr)
     }
 
     if (descriptor->flags & SPICE_IMAGE_FLAGS_CACHE_ME) {
-        canvas->bits_cache_put(canvas->bits_cache_opaque, descriptor->id, surface);
+        canvas->bits_cache->ops->put(canvas->bits_cache, descriptor->id, surface);
 #ifdef DEBUG_DUMP_SURFACE
         dump_surface(surface, 1);
 #endif
@@ -1163,7 +1158,7 @@ static cairo_surface_t *canvas_get_mask(CanvasBase *canvas, SpiceQMask *mask)
     }
 #if defined(CAIRO_CANVAS_CACHE) || defined(CAIRO_CANVAS_IMAGE_CACHE)
     case SPICE_IMAGE_TYPE_FROM_CACHE:
-        surface = canvas->bits_cache_get(canvas->bits_cache_opaque, descriptor->id);
+        surface = canvas->bits_cache->ops->get(canvas->bits_cache, descriptor->id);
         is_invers = 0;
         break;
 #endif
@@ -1173,7 +1168,7 @@ static cairo_surface_t *canvas_get_mask(CanvasBase *canvas, SpiceQMask *mask)
 
 #if defined(CAIRO_CANVAS_CACHE) || defined(CAIRO_CANVAS_IMAGE_CACHE)
     if (cache_me) {
-        canvas->bits_cache_put(canvas->bits_cache_opaque, descriptor->id, surface);
+        canvas->bits_cache->ops->put(canvas->bits_cache, descriptor->id, surface);
     }
 
     if (need_invers && !is_invers) { // surface is in cache
@@ -1570,18 +1565,11 @@ static void canvas_base_destroy(CanvasBase *canvas)
 
 #ifdef CAIRO_CANVAS_CACHE
 static int canvas_base_init(CanvasBase *canvas, int depth,
-                            void *bits_cache_opaque,
-                            bits_cache_put_fn_t bits_cache_put,
-                            bits_cache_get_fn_t bits_cache_get,
-                            void *palette_cache_opaque,
-                            palette_cache_put_fn_t palette_cache_put,
-                            palette_cache_get_fn_t palette_cache_get,
-                            palette_cache_release_fn_t palette_cache_release
+                            SpiceImageCache *bits_cache,
+                            SpicePaletteCache *palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
 static int canvas_base_init(CanvasBase *canvas, int depth,
-                            void *bits_cache_opaque,
-                            bits_cache_put_fn_t bits_cache_put,
-                            bits_cache_get_fn_t bits_cache_get
+                            SpiceImageCache *bits_cache
 #else
 static int canvas_base_init(CanvasBase *canvas, int depth
 #endif
@@ -1637,15 +1625,10 @@ static int canvas_base_init(CanvasBase *canvas, int depth
 
 
 #if defined(CAIRO_CANVAS_CACHE) || defined(CAIRO_CANVAS_IMAGE_CACHE)
-    canvas->bits_cache_opaque = bits_cache_opaque;
-    canvas->bits_cache_put = bits_cache_put;
-    canvas->bits_cache_get = bits_cache_get;
+    canvas->bits_cache = bits_cache;
 #endif
 #ifdef CAIRO_CANVAS_CACHE
-    canvas->palette_cache_opaque = palette_cache_opaque;
-    canvas->palette_cache_put = palette_cache_put;
-    canvas->palette_cache_get = palette_cache_get;
-    canvas->palette_cache_release = palette_cache_release;
+    canvas->palette_cache = palette_cache;
 #endif
 
 #ifdef WIN32
diff --git a/common/canvas_base.h b/common/canvas_base.h
index 15cf869..cc75087 100644
--- a/common/canvas_base.h
+++ b/common/canvas_base.h
@@ -24,15 +24,33 @@
 #include "lz.h"
 #include <spice/draw.h>
 
-#if defined(CAIRO_CANVAS_CACHE) || defined(CAIRO_CANVAS_IMAGE_CACHE)
-typedef void (*bits_cache_put_fn_t)(void *bits_cache_opaque, uint64_t id, cairo_surface_t *surface);
-typedef cairo_surface_t *(*bits_cache_get_fn_t)(void *bits_cache_opaque, uint64_t id);
-#endif
-#ifdef CAIRO_CANVAS_CACHE
-typedef void (*palette_cache_put_fn_t)(void *palette_cache_opaque, SpicePalette *palette);
-typedef SpicePalette *(*palette_cache_get_fn_t)(void *palette_cache_opaque, uint64_t id);
-typedef void (*palette_cache_release_fn_t)(SpicePalette *palette);
-#endif
+typedef struct _SpiceImageCache SpiceImageCache;
+typedef struct _SpicePaletteCache SpicePaletteCache;
+
+typedef struct {
+    void (*put)(SpiceImageCache *cache,
+                uint64_t id,
+                cairo_surface_t *surface);
+    cairo_surface_t *(*get)(SpiceImageCache *cache,
+                            uint64_t id);
+} SpiceImageCacheOps;
+
+struct _SpiceImageCache {
+  SpiceImageCacheOps *ops;
+};
+
+typedef struct {
+    void (*put)(SpicePaletteCache *cache,
+                SpicePalette *palette);
+    SpicePalette *(*get)(SpicePaletteCache *cache,
+                         uint64_t id);
+    void (*release)(SpicePaletteCache *cache,
+                    SpicePalette *palette);
+} SpicePaletteCacheOps;
+
+struct _SpicePaletteCache {
+  SpicePaletteCacheOps *ops;
+};
 
 typedef void (*glz_decode_fn_t)(void *glz_decoder_opaque, uint8_t *data,
                                 SpicePalette *plt, void *usr_data);
diff --git a/common/gdi_canvas.c b/common/gdi_canvas.c
index df5ae64..be351b5 100644
--- a/common/gdi_canvas.c
+++ b/common/gdi_canvas.c
@@ -1695,14 +1695,11 @@ static int need_init = 1;
 
 #ifdef CAIRO_CANVAS_CACHE
 GdiCanvas *gdi_canvas_create(HDC dc, Mutex* lock, int bits, void *bits_cache_opaque,
-                             bits_cache_put_fn_t bits_cache_put, bits_cache_get_fn_t bits_cache_get,
-                             void *palette_cache_opaque, palette_cache_put_fn_t palette_cache_put,
-                             palette_cache_get_fn_t palette_cache_get,
-                             palette_cache_release_fn_t palette_cache_release
+                             SpiceImageCache *bits_cache,
+                             SpicePaletteCache *palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
 GdiCanvas *gdi_canvas_create(HDC dc, int bits,
-                             void *bits_cache_opaque,
-                             bits_cache_put_fn_t bits_cache_put, bits_cache_get_fn_t bits_cache_get
+                             SpiceImageCache *bits_cache
 #else
 GdiCanvas *gdi_canvas_create(HDC dc, int bits
 #endif
@@ -1720,18 +1717,11 @@ GdiCanvas *gdi_canvas_create(HDC dc, int bits
     memset(canvas, 0, sizeof(GdiCanvas));
 #ifdef CAIRO_CANVAS_CACHE
     init_ok = canvas_base_init(&canvas->base, bits,
-                               bits_cache_opaque,
-                               bits_cache_put,
-                               bits_cache_get,
-                               palette_cache_opaque,
-                               palette_cache_put,
-                               palette_cache_get,
-                               palette_cache_release
+                               bits_cache,
+                               palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
     init_ok = gdi_canvas_base_init(&canvas->base, bits,
-                                   bits_cache_opaque,
-                                   bits_cache_put,
-                                   bits_cache_get
+                                   bits_cache
 #else
     init_ok = gdi_canvas_base_init(&canvas->base, bits
 #endif
diff --git a/common/gdi_canvas.h b/common/gdi_canvas.h
index 8ba3f20..36aae59 100644
--- a/common/gdi_canvas.h
+++ b/common/gdi_canvas.h
@@ -59,10 +59,8 @@ void gdi_canvas_set_access_params(GdiCanvas *canvas, unsigned long base, unsigne
 
 
 GdiCanvas *gdi_canvas_create(HDC dc, class Mutex *lock, int bits, void *bits_cache_opaque,
-                             bits_cache_put_fn_t bits_cache_put, bits_cache_get_fn_t bits_cache_get,
-                             void *palette_cache_opaque, palette_cache_put_fn_t palette_cache_put,
-                             palette_cache_get_fn_t palette_cache_get,
-                             palette_cache_release_fn_t palette_cache_release,
+                             SpiceImageCache *bits_cache,
+                             SpicePaletteCache *palette_cache
                              void *glz_decoder_opaque,
                              glz_decode_fn_t glz_decode);
 
diff --git a/common/gl_canvas.c b/common/gl_canvas.c
index fd1a2c9..d7f2889 100644
--- a/common/gl_canvas.c
+++ b/common/gl_canvas.c
@@ -786,18 +786,11 @@ static int need_init = 1;
 
 #ifdef CAIRO_CANVAS_CACHE
 GLCanvas *gl_canvas_create(void *usr_data, int width, int height, int depth,
-                           void *bits_cache_opaque,
-                           bits_cache_put_fn_t bits_cache_put,
-                           bits_cache_get_fn_t bits_cache_get,
-                           void *palette_cache_opaque,
-                           palette_cache_put_fn_t palette_cache_put,
-                           palette_cache_get_fn_t palette_cache_get,
-                           palette_cache_release_fn_t palette_cache_release
+			   SpiceImageCache *bits_cache,
+			   SpicePaletteCache *palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
 GLCanvas *gl_canvas_create(void *usr_data, int width, int height, int depth,
-                           void *bits_cache_opaque,
-                           bits_cache_put_fn_t bits_cache_put,
-                           bits_cache_get_fn_t bits_cache_get
+			   SpiceImageCache *bits_cache
 #else
 GLCanvas *gl_canvas_create(void *usr_data, int width, int height, int depth
 #endif
@@ -825,18 +818,11 @@ GLCanvas *gl_canvas_create(void *usr_data, int width, int height, int depth
     canvas->private_data = NULL;
 #ifdef CAIRO_CANVAS_CACHE
     init_ok = canvas_base_init(&canvas->base, depth,
-                               bits_cache_opaque,
-                               bits_cache_put,
-                               bits_cache_get,
-                               palette_cache_opaque,
-                               palette_cache_put,
-                               palette_cache_get,
-                               palette_cache_release
+                               bits_cache,
+                               palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
     init_ok = canvas_base_init(&canvas->base, depth,
-                               bits_cache_opaque,
-                               bits_cache_put,
-                               bits_cache_get
+                               bits_cache
 #else
     init_ok = canvas_base_init(&canvas->base, depth
 #endif
diff --git a/common/gl_canvas.h b/common/gl_canvas.h
index 442c9f4..3f885a0 100644
--- a/common/gl_canvas.h
+++ b/common/gl_canvas.h
@@ -55,18 +55,11 @@ void *gl_canvas_get_usr_data(GLCanvas *canvas);
 
 #ifdef CAIRO_CANVAS_CACHE
 GLCanvas *gl_canvas_create(void *usr_data, int width, int height, int depth,
-                           void *bits_cache_opaque,
-                           bits_cache_put_fn_t bits_cache_put,
-                           bits_cache_get_fn_t bits_cache_get,
-                           void *palette_cache_opaque,
-                           palette_cache_put_fn_t palette_cache_put,
-                           palette_cache_get_fn_t palette_cache_get,
-                           palette_cache_release_fn_t palette_cache_release
+			   SpiceImageCache *bits_cache,
+			   SpicePaletteCache *palette_cache
 #elif defined(CAIRO_CANVAS_IMAGE_CACHE)
 GLCanvas *gl_canvas_create(void *usr_data, int width, int height, int depth,
-                           void *bits_cache_opaque,
-                           bits_cache_put_fn_t bits_cache_put,
-                           bits_cache_get_fn_t bits_cache_get
+			   SpiceImageCache *bits_cache
 #else
 GLCanvas *gl_canvas_create(void *usr_data, int width, int height, int depth
 #endif
diff --git a/server/red_worker.c b/server/red_worker.c
index 2b50b9f..85964ce 100644
--- a/server/red_worker.c
+++ b/server/red_worker.c
@@ -728,6 +728,7 @@ typedef struct ImageCacheItem {
 #define IMAGE_CACHE_HASH_SIZE 1024
 
 typedef struct ImageCache {
+    SpiceImageCache base;
     ImageCacheItem *hash_table[IMAGE_CACHE_HASH_SIZE];
     Ring lru;
 #ifdef IMAGE_CACHE_AGE
@@ -3898,9 +3899,9 @@ static void image_cache_remove(ImageCache *cache, ImageCacheItem *item)
 
 #define IMAGE_CACHE_MAX_ITEMS 2
 
-static void image_cache_put(void *opaque, uint64_t id, cairo_surface_t *surface)
+static void image_cache_put(SpiceImageCache *spice_cache, uint64_t id, cairo_surface_t *surface)
 {
-    ImageCache *cache = (ImageCache *)opaque;
+    ImageCache *cache = (ImageCache *)spice_cache;
     ImageCacheItem *item;
 
 #ifndef IMAGE_CACHE_AGE
@@ -3929,9 +3930,9 @@ static void image_cache_put(void *opaque, uint64_t id, cairo_surface_t *surface)
     ring_add(&cache->lru, &item->lru_link);
 }
 
-static cairo_surface_t *image_cache_get(void *opaque, uint64_t id)
+static cairo_surface_t *image_cache_get(SpiceImageCache *spice_cache, uint64_t id)
 {
-    ImageCache *cache = (ImageCache *)opaque;
+    ImageCache *cache = (ImageCache *)spice_cache;
 
     ImageCacheItem *item = image_cache_find(cache, id);
     if (!item) {
@@ -3942,6 +3943,12 @@ static cairo_surface_t *image_cache_get(void *opaque, uint64_t id)
 
 static void image_cache_init(ImageCache *cache)
 {
+    static SpiceImageCacheOps image_cache_ops = {
+        image_cache_put,
+        image_cache_get,
+    };
+
+    cache->base.ops = &image_cache_ops;
     memset(cache->hash_table, 0, sizeof(cache->hash_table));
     ring_init(&cache->lru);
 #ifdef IMAGE_CACHE_AGE
@@ -7488,7 +7495,7 @@ static CairoCanvas *create_cairo_context(RedWorker *worker, uint32_t width, uint
                   cairo_status_to_string(cairo_status(cairo)));
     }
 
-    return canvas_create(cairo, depth, &worker->image_cache, image_cache_put, image_cache_get,
+    return canvas_create(cairo, depth, &worker->image_cache.base,
                          worker, cb_get_virt_preload_group, worker,
                          cb_validate_virt_preload_group);
 }
@@ -7550,9 +7557,8 @@ static GLCanvas *create_ogl_context_common(RedWorker *worker, OGLCtx *ctx, uint3
     GLCanvas *canvas;
 
     oglctx_make_current(ctx);
-    if (!(canvas = gl_canvas_create(ctx, width, height, depth, &worker->image_cache,
-                                    image_cache_put, image_cache_get, worker,
-                                    cb_get_virt_preload_group,
+    if (!(canvas = gl_canvas_create(ctx, width, height, depth, &worker->image_cache.base,
+                                    worker, cb_get_virt_preload_group,
                                     worker, cb_validate_virt_preload_group))) {
         return NULL;
     }
-- 
1.6.6



More information about the Spice-devel mailing list