[cairo-commit] 13 commits - src/cairo-gl-glyphs.c src/cairo-gl-private.h src/cairo-gl-surface.c src/cairo.h src/cairo-image-surface.c src/cairo-recording-surface.c src/cairo-xcb-connection.c src/cairo-xcb-surface.c src/cairo-xcb-surface-render.c test/clear-source.c test/clip-image.c test/pthread-same-source.c

Chris Wilson ickle at kemper.freedesktop.org
Tue Mar 23 03:38:04 PDT 2010


 src/cairo-gl-glyphs.c          |   23 ++++++++++++-----------
 src/cairo-gl-private.h         |    7 ++++---
 src/cairo-gl-surface.c         |    4 ++++
 src/cairo-image-surface.c      |    9 ++++++---
 src/cairo-recording-surface.c  |   10 ++++------
 src/cairo-xcb-connection.c     |   12 ++++++++++++
 src/cairo-xcb-surface-render.c |   41 ++++++++++++++++++++++++++---------------
 src/cairo-xcb-surface.c        |   19 ++++++++++++-------
 src/cairo.h                    |    4 ++--
 test/clear-source.c            |   38 ++++++++++++++++++++++----------------
 test/clip-image.c              |    1 +
 test/pthread-same-source.c     |    6 ++++++
 12 files changed, 111 insertions(+), 63 deletions(-)

New commits:
commit 8a8c2f6c282c1822dc1a638c2258c8449b1d678b
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 10:34:06 2010 +0000

    cairo: Typos in docs.
    
    A couple of typos reported by Damien Carbonne.

diff --git a/src/cairo-recording-surface.c b/src/cairo-recording-surface.c
index 7f9c766..5f0a298 100644
--- a/src/cairo-recording-surface.c
+++ b/src/cairo-recording-surface.c
@@ -196,26 +196,22 @@ _cairo_recording_surface_finish (void *abstract_surface)
 	switch (command->header.type) {
 	case CAIRO_COMMAND_PAINT:
 	    _cairo_pattern_fini_snapshot (&command->paint.source.base);
-	    free (command);
 	    break;
 
 	case CAIRO_COMMAND_MASK:
 	    _cairo_pattern_fini_snapshot (&command->mask.source.base);
 	    _cairo_pattern_fini_snapshot (&command->mask.mask.base);
-	    free (command);
 	    break;
 
 	case CAIRO_COMMAND_STROKE:
 	    _cairo_pattern_fini_snapshot (&command->stroke.source.base);
 	    _cairo_path_fixed_fini (&command->stroke.path);
 	    _cairo_stroke_style_fini (&command->stroke.style);
-	    free (command);
 	    break;
 
 	case CAIRO_COMMAND_FILL:
 	    _cairo_pattern_fini_snapshot (&command->fill.source.base);
 	    _cairo_path_fixed_fini (&command->fill.path);
-	    free (command);
 	    break;
 
 	case CAIRO_COMMAND_SHOW_TEXT_GLYPHS:
@@ -224,16 +220,18 @@ _cairo_recording_surface_finish (void *abstract_surface)
 	    free (command->show_text_glyphs.glyphs);
 	    free (command->show_text_glyphs.clusters);
 	    cairo_scaled_font_destroy (command->show_text_glyphs.scaled_font);
-	    free (command);
 	    break;
 
 	default:
 	    ASSERT_NOT_REACHED;
 	}
+
+	_cairo_clip_fini (&command->header.clip);
+	free (command);
     }
 
     _cairo_array_fini (&recording_surface->commands);
-    _cairo_clip_reset (&recording_surface->clip);
+    _cairo_clip_fini (&recording_surface->clip);
 
     return CAIRO_STATUS_SUCCESS;
 }
diff --git a/src/cairo.h b/src/cairo.h
index 5a62f82..c1bf44a 100644
--- a/src/cairo.h
+++ b/src/cairo.h
@@ -155,7 +155,7 @@ typedef struct _cairo_surface cairo_surface_t;
  * cairo_xcb_device_create() creates a device that wraps the connection
  * to an X Windows System using the XCB library.
  *
- * The type of a surface can be queried with cairo_device_get_type().
+ * The type of a device can be queried with cairo_device_get_type().
  *
  * Memory management of #cairo_device_t is done with
  * cairo_device_reference() and cairo_device_destroy().
@@ -2617,7 +2617,7 @@ cairo_public cairo_region_t *
 cairo_region_copy (const cairo_region_t *original);
 
 cairo_public cairo_region_t *
-cairo_region_reference (cairo_region_t *);
+cairo_region_reference (cairo_region_t *region);
 
 cairo_public void
 cairo_region_destroy (cairo_region_t *region);
commit 4c55c87478a2595569f9c1f13657c3d309f31407
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 10:05:35 2010 +0000

    image: Free traps after conversion from boxes.

diff --git a/src/cairo-image-surface.c b/src/cairo-image-surface.c
index f866ae6..099cacf 100644
--- a/src/cairo-image-surface.c
+++ b/src/cairo-image-surface.c
@@ -2851,9 +2851,12 @@ _clip_and_composite_boxes (cairo_image_surface_t *dst,
     info.num_traps = traps.num_traps;
     info.traps = traps.traps;
     info.antialias = antialias;
-    return _clip_and_composite (dst, op, src,
-				_composite_traps, &info,
-				extents, clip);
+    status =  _clip_and_composite (dst, op, src,
+				   _composite_traps, &info,
+				   extents, clip);
+
+    _cairo_traps_fini (&traps);
+    return status;
 }
 
 static cairo_bool_t
commit 07f7bddc30157fed8f9dced00fef44a2307b4b01
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 10:05:35 2010 +0000

    xcb: Free traps after conversion from boxes.

diff --git a/src/cairo-xcb-surface-render.c b/src/cairo-xcb-surface-render.c
index 971c473..8e0d0d9 100644
--- a/src/cairo-xcb-surface-render.c
+++ b/src/cairo-xcb-surface-render.c
@@ -2612,9 +2612,12 @@ _clip_and_composite_boxes (cairo_xcb_surface_t *dst,
 	return status;
 
     info.antialias = antialias;
-    return _clip_and_composite (dst, op, src,
-				_composite_traps, &info,
-				extents, clip);
+    status = _clip_and_composite (dst, op, src,
+				  _composite_traps, &info,
+				  extents, clip);
+
+    _cairo_traps_fini (&info.traps);
+    return status;
 }
 
 static cairo_bool_t
commit 181403fb534d0216123043bcd3ee6cff60e1e6fd
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 09:38:59 2010 +0000

    test/clear-source: Free source after use.

diff --git a/test/clear-source.c b/test/clear-source.c
index 36f46b3..cf9867c 100644
--- a/test/clear-source.c
+++ b/test/clear-source.c
@@ -42,23 +42,26 @@ create_surface (cairo_t *target, cairo_content_t content, surface_type_t type)
     cairo_t *cr;
 
     surface = cairo_surface_create_similar (cairo_get_target (target),
-                                            content,
-                                            SIZE, SIZE);
+					    content,
+					    SIZE, SIZE);
 
     if (type == CLEAR)
-        return surface;
+	return surface;
 
     cr = cairo_create (surface);
+    cairo_surface_destroy (surface);
+
     cairo_set_source_rgb (cr, 0.75, 0, 0);
     cairo_paint (cr);
-    cairo_destroy (cr);
 
     if (type == PAINTED)
-        return surface;
+	goto DONE;
 
-    cr = cairo_create (surface);
     cairo_set_operator (cr, CAIRO_OPERATOR_CLEAR);
     cairo_paint (cr);
+
+DONE:
+    surface = cairo_surface_reference (cairo_get_target (cr));
     cairo_destroy (cr);
 
     return surface;
@@ -117,28 +120,29 @@ glyphs (cairo_t *cr, cairo_surface_t *surface)
 
 typedef void (* operation_t) (cairo_t *cr, cairo_surface_t *surface);
 static operation_t operations[] = {
-  paint,
-  fill,
-  stroke,
-  mask,
-  mask_self,
-  glyphs
+    paint,
+    fill,
+    stroke,
+    mask,
+    mask_self,
+    glyphs
 };
 
-static cairo_test_status_t
+    static cairo_test_status_t
 draw (cairo_t *cr, int width, int height)
 {
     cairo_content_t contents[] = { CAIRO_CONTENT_COLOR_ALPHA, CAIRO_CONTENT_COLOR, CAIRO_CONTENT_ALPHA };
     unsigned int content, type, ops;
-    cairo_surface_t *surface;
 
     cairo_set_source_rgb (cr, 0.5, 0.5, 0.5);
     cairo_paint (cr);
     cairo_translate (cr, SPACE, SPACE);
 
     for (type = 0; type <= PAINTED; type++) {
-        for (content = 0; content < ARRAY_LENGTH (contents); content++) {
-            surface = create_surface (cr, contents[content], type);
+	for (content = 0; content < ARRAY_LENGTH (contents); content++) {
+	    cairo_surface_t *surface;
+
+	    surface = create_surface (cr, contents[content], type);
 
             cairo_save (cr);
             for (ops = 0; ops < ARRAY_LENGTH (operations); ops++) {
@@ -149,6 +153,8 @@ draw (cairo_t *cr, int width, int height)
             }
             cairo_restore (cr);
             cairo_translate (cr, SIZE + SPACE, 0);
+
+	    cairo_surface_destroy (surface);
         }
     }
 
commit 35432e37c264e1ace764b4a1393d9b8579eb52c0
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 09:35:51 2010 +0000

    xcb: Destroy reference to clip surface after use.

diff --git a/src/cairo-xcb-surface-render.c b/src/cairo-xcb-surface-render.c
index fe72b5d..971c473 100644
--- a/src/cairo-xcb-surface-render.c
+++ b/src/cairo-xcb-surface-render.c
@@ -2564,6 +2564,9 @@ _composite_boxes (cairo_xcb_surface_t *dst,
 	status = _render_composite_boxes (dst, op, src,
 					  need_clip_mask ? &mask.base : NULL,
 					  &extents->bounded, boxes);
+
+	if (need_clip_mask)
+	    _cairo_pattern_fini (&mask.base);
     }
 
     if (status == CAIRO_STATUS_SUCCESS && ! extents->is_bounded) {
commit 98e3dfbb899f0228fc9987a56af93b012989a27a
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 09:35:31 2010 +0000

    xcb: Relinquish the xcb connection on finish.

diff --git a/src/cairo-xcb-connection.c b/src/cairo-xcb-connection.c
index 33ba458..e0e6862 100644
--- a/src/cairo-xcb-connection.c
+++ b/src/cairo-xcb-connection.c
@@ -539,6 +539,13 @@ _device_finish (void *device)
 	_cairo_xcb_screen_finish (screen);
     }
 
+    if (connection->has_socket) {
+	/* Send a request so that xcb takes the socket from us, preventing
+	 * a later use-after-free on shutdown of the connection.
+	 */
+	xcb_no_operation (connection->xcb_connection);
+    }
+
     if (was_cached)
 	cairo_device_destroy (device);
 }
commit 638cae3bdeaf0b10d1fd59a519f5d7a05c5b179c
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 08:25:13 2010 +0000

    xcb: Fix leak of clip rectangle during show-glyphs.

diff --git a/src/cairo-xcb-surface-render.c b/src/cairo-xcb-surface-render.c
index c4a8852..fe72b5d 100644
--- a/src/cairo-xcb-surface-render.c
+++ b/src/cairo-xcb-surface-render.c
@@ -4394,15 +4394,12 @@ _cairo_xcb_surface_render_glyphs (cairo_xcb_surface_t	*surface,
 
     if (clip != NULL) {
 	clip = _cairo_clip_init_copy (&local_clip, clip);
-	have_clip = TRUE;
-    }
-
-    if (clip != NULL && extents.is_bounded) {
-	clip = _cairo_clip_init_copy (&local_clip, clip);
-	status = _cairo_clip_rectangle (clip, &extents.bounded);
-	if (unlikely (status)) {
-	    _cairo_clip_fini (&local_clip);
-	    return status;
+	if (extents.is_bounded) {
+	    status = _cairo_clip_rectangle (clip, &extents.bounded);
+	    if (unlikely (status)) {
+		_cairo_clip_fini (&local_clip);
+		return status;
+	    }
 	}
 	have_clip = TRUE;
     }
commit 1d4ad787747b5c92c3b062afde5b98c72ac4cc95
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 08:20:49 2010 +0000

    test/pthread-same-source: Free source after use.

diff --git a/test/pthread-same-source.c b/test/pthread-same-source.c
index 570c91d..50102d9 100644
--- a/test/pthread-same-source.c
+++ b/test/pthread-same-source.c
@@ -92,11 +92,15 @@ create_source (cairo_surface_t *similar)
                                            2, 2);
 
     cr = cairo_create (source);
+    cairo_surface_destroy (source);
+
     for (i = 0; i < 4; i++) {
       cairo_set_source_rgb (cr, colors[i][0], colors[i][1], colors[i][2]);
       cairo_rectangle (cr, i % 2, i / 2, 1, 1);
       cairo_fill (cr);
     }
+
+    source = cairo_surface_reference (cairo_get_target (cr));
     cairo_destroy (cr);
 
     return source;
@@ -128,6 +132,8 @@ draw (cairo_t *cr, int width, int height)
         }
     }
 
+    cairo_surface_destroy (source);
+
     cairo_set_source_rgb (cr, 0.5, 0.5, 0.5);
     cairo_paint (cr);
 
commit bfc027ac6d05f489d0d26110c225d2871be0971c
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Tue Mar 23 08:16:57 2010 +0000

    test/clip-image: Free image after use.

diff --git a/test/clip-image.c b/test/clip-image.c
index e3c8809..68ed142 100644
--- a/test/clip-image.c
+++ b/test/clip-image.c
@@ -41,6 +41,7 @@ draw (cairo_t *cr, int width, int height)
 
     image = cairo_test_create_surface_from_png (ctx, png_filename);
     cairo_set_source_surface (cr, image, 0, 0);
+    cairo_surface_destroy (image);
 
     /* simple clip */
     cairo_save (cr);
commit e214f09d633093ce9b2ca0bffce10bc68a6e30b0
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Mon Mar 22 22:20:58 2010 +0000

    xcb: Consume the implicit reference for the cached connection on finish

diff --git a/src/cairo-xcb-connection.c b/src/cairo-xcb-connection.c
index 18ccd4a..33ba458 100644
--- a/src/cairo-xcb-connection.c
+++ b/src/cairo-xcb-connection.c
@@ -512,11 +512,13 @@ static void
 _device_finish (void *device)
 {
     cairo_xcb_connection_t *connection = device;
+    cairo_bool_t was_cached = FALSE;
 
     if (! cairo_list_is_empty (&connection->link)) {
 	CAIRO_MUTEX_LOCK (_cairo_xcb_connections_mutex);
 	cairo_list_del (&connection->link);
 	CAIRO_MUTEX_UNLOCK (_cairo_xcb_connections_mutex);
+	was_cached = TRUE;
     }
 
     while (! cairo_list_is_empty (&connection->fonts)) {
@@ -536,6 +538,9 @@ _device_finish (void *device)
 					 link);
 	_cairo_xcb_screen_finish (screen);
     }
+
+    if (was_cached)
+	cairo_device_destroy (device);
 }
 
 static void
commit c235543bdfd8b1495cb7ae8f2a82b6267c4d9b84
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Mon Mar 22 22:15:44 2010 +0000

    xcb: Destroy reference to local source picture in show-glyphs.

diff --git a/src/cairo-xcb-surface-render.c b/src/cairo-xcb-surface-render.c
index 45d1015..c4a8852 100644
--- a/src/cairo-xcb-surface-render.c
+++ b/src/cairo-xcb-surface-render.c
@@ -4236,16 +4236,20 @@ _composite_glyphs (void				*closure,
 						 glyph_index,
 						 CAIRO_SCALED_GLYPH_INFO_METRICS,
 						 &scaled_glyph);
-	    if (unlikely (status))
+	    if (unlikely (status)) {
+		cairo_surface_destroy (&src->base);
 		return status;
+	    }
 
 	    /* Send unseen glyphs to the server */
 	    if (_cairo_xcb_scaled_glyph_get_glyphset_info (scaled_glyph) == NULL) {
 		status = _cairo_xcb_surface_add_glyph (dst->connection,
 						       info->font,
 						       &scaled_glyph);
-		if (unlikely (status))
+		if (unlikely (status)) {
+		    cairo_surface_destroy (&src->base);
 		    return status;
+		}
 	    }
 
 	    glyph_cache[cache_index] = scaled_glyph;
@@ -4304,8 +4308,10 @@ _composite_glyphs (void				*closure,
 					 info->glyphs, i,
 					 old_width, request_size,
 					 glyphset_info);
-	    if (unlikely (status))
+	    if (unlikely (status)) {
+		cairo_surface_destroy (&src->base);
 		return status;
+	    }
 
 	    info->glyphs += i;
 	    info->num_glyphs -= i;
@@ -4348,6 +4354,8 @@ _composite_glyphs (void				*closure,
 				     glyphset_info);
     }
 
+    cairo_surface_destroy (&src->base);
+
     return status;
 }
 
commit c42cdd2c9d883ef359ac57b65eba4ed15441181d
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Mon Mar 22 20:14:09 2010 +0000

    xcb: Gracefully destroy any lingering fallback during finish.
    
    A fallback should never persist beyond the flush into the finish, but
    yet one remains in test/clip-shapes-unaligned-rectangles. For the time
    been, simply clean up the rogue surface.

diff --git a/src/cairo-xcb-surface.c b/src/cairo-xcb-surface.c
index 82c3114..5f91ef6 100644
--- a/src/cairo-xcb-surface.c
+++ b/src/cairo-xcb-surface.c
@@ -257,7 +257,10 @@ _cairo_xcb_surface_finish (void *abstract_surface)
     cairo_xcb_surface_t *surface = abstract_surface;
     cairo_status_t status;
 
-    assert (surface->fallback == NULL);
+    if (surface->fallback != NULL) {
+	cairo_surface_finish (surface->fallback);
+	cairo_surface_destroy (surface->fallback);
+    }
 
     cairo_list_del (&surface->link);
 
@@ -683,7 +686,7 @@ static cairo_status_t
 _cairo_xcb_surface_flush (void *abstract_surface)
 {
     cairo_xcb_surface_t *surface = abstract_surface;
-    cairo_status_t status = CAIRO_STATUS_SUCCESS;
+    cairo_status_t status;
 
     if (surface->drm != NULL && ! surface->marked_dirty)
 	return surface->drm->backend->flush (surface->drm);
@@ -691,12 +694,14 @@ _cairo_xcb_surface_flush (void *abstract_surface)
     if (likely (surface->fallback == NULL))
 	return CAIRO_STATUS_SUCCESS;
 
-    if (! surface->base.finished) {
-	status = _put_image (surface,
-			     (cairo_image_surface_t *) surface->fallback);
+    status = surface->base.status;
+    if (status == CAIRO_STATUS_SUCCESS && ! surface->base.finished) {
+	status = cairo_surface_status (surface->fallback);
 
-	if (status == CAIRO_STATUS_SUCCESS)
-	    status = cairo_surface_status (surface->fallback);
+	if (status == CAIRO_STATUS_SUCCESS) {
+	    status = _put_image (surface,
+				 (cairo_image_surface_t *) surface->fallback);
+	}
 
 	if (status == CAIRO_STATUS_SUCCESS) {
 	    status = _cairo_surface_attach_snapshot (&surface->base,
commit fd96aa3de2218dcc6671636f35a24738e3cae996
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Mon Mar 22 19:07:31 2010 +0000

    gl: Hook in glyph cache finalisation.

diff --git a/src/cairo-gl-glyphs.c b/src/cairo-gl-glyphs.c
index 58e7838..6485af6 100644
--- a/src/cairo-gl-glyphs.c
+++ b/src/cairo-gl-glyphs.c
@@ -892,17 +892,6 @@ EMPTY:
 }
 
 void
-_cairo_gl_glyph_cache_fini (cairo_gl_glyph_cache_t *cache)
-{
-    if (cache->tex == 0)
-	return;
-
-    glDeleteTextures (1, &cache->tex);
-
-    _cairo_rtree_fini (&cache->rtree);
-}
-
-void
 _cairo_gl_glyph_cache_init (cairo_gl_glyph_cache_t *cache)
 {
     cache->tex = 0;
@@ -915,3 +904,15 @@ _cairo_gl_glyph_cache_init (cairo_gl_glyph_cache_t *cache)
 		       NULL);
 }
 
+void
+_cairo_gl_glyph_cache_fini (cairo_gl_context_t *ctx,
+			    cairo_gl_glyph_cache_t *cache)
+{
+    _cairo_rtree_fini (&cache->rtree);
+
+    if (cache->tex) {
+	/* XXX Is this safe? */
+	glDeleteTextures (1, &cache->tex);
+    }
+}
+
diff --git a/src/cairo-gl-private.h b/src/cairo-gl-private.h
index d309388..cfb563b 100644
--- a/src/cairo-gl-private.h
+++ b/src/cairo-gl-private.h
@@ -280,6 +280,10 @@ _cairo_gl_surface_scaled_glyph_fini (cairo_scaled_glyph_t *scaled_glyph,
 cairo_private void
 _cairo_gl_glyph_cache_init (cairo_gl_glyph_cache_t *cache);
 
+cairo_private void
+_cairo_gl_glyph_cache_fini (cairo_gl_context_t *ctx,
+			    cairo_gl_glyph_cache_t *cache);
+
 cairo_private cairo_int_status_t
 _cairo_gl_surface_show_glyphs (void			*abstract_dst,
 			       cairo_operator_t		 op,
@@ -290,9 +294,6 @@ _cairo_gl_surface_show_glyphs (void			*abstract_dst,
 			       cairo_clip_t		*clip,
 			       int			*remaining_glyphs);
 
-cairo_private void
-_cairo_gl_glyph_cache_fini (cairo_gl_glyph_cache_t *cache);
-
 static inline int
 _cairo_gl_y_flip (cairo_gl_surface_t *surface, int y)
 {
diff --git a/src/cairo-gl-surface.c b/src/cairo-gl-surface.c
index 5222791..708bf34 100644
--- a/src/cairo-gl-surface.c
+++ b/src/cairo-gl-surface.c
@@ -72,6 +72,7 @@ _gl_destroy (void *device)
 {
     cairo_gl_context_t *ctx = device;
     cairo_scaled_font_t *scaled_font, *next_scaled_font;
+    int n;
 
     ctx->destroy (ctx);
 
@@ -84,6 +85,9 @@ _gl_destroy (void *device)
 	_cairo_scaled_font_revoke_ownership (scaled_font);
     }
 
+    for (n = 0; n < ARRAY_LENGTH (ctx->glyph_cache); n++)
+	_cairo_gl_glyph_cache_fini (ctx, &ctx->glyph_cache[n]);
+
     free (ctx);
 }
 


More information about the cairo-commit mailing list