summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorUli Schlachter <psychon@znc.in>2011-07-02 23:00:24 +0200
committerUli Schlachter <psychon@znc.in>2011-07-02 23:00:24 +0200
commit9e4c73a40d6eb72a5110936ab310acbaef99baa8 (patch)
treeb965fe1f860bcd2fb646e4cbaf7233a3604c84bd
parent880566e14b335ddb5bf1c768f6ca4f02b2dd2add (diff)
xlib-xcb: Fix some use-after-free
Also, this now sets surface->xcb to NULL after the dereference. Segfaults are way more prominent anyway. :-) All the backend callbacks shouldn't need any checks since the public entry point already checks for finished surfaces. Only the public functions in xlib-xcb need to do checks for finished surfaces. Signed-off-by: Uli Schlachter <psychon@znc.in>
-rw-r--r--src/cairo-xlib-xcb-surface.c17
1 files changed, 17 insertions, 0 deletions
diff --git a/src/cairo-xlib-xcb-surface.c b/src/cairo-xlib-xcb-surface.c
index 0462e037..07c27358 100644
--- a/src/cairo-xlib-xcb-surface.c
+++ b/src/cairo-xlib-xcb-surface.c
@@ -80,6 +80,7 @@ _cairo_xlib_xcb_surface_finish (void *abstract_surface)
cairo_surface_finish (&surface->xcb->base);
status = surface->xcb->base.status;
cairo_surface_destroy (&surface->xcb->base);
+ surface->xcb = NULL;
return status;
}
@@ -483,6 +484,10 @@ cairo_xlib_surface_get_drawable (cairo_surface_t *abstract_surface)
{
cairo_xlib_xcb_surface_t *surface = (cairo_xlib_xcb_surface_t *) abstract_surface;
+ if (unlikely (abstract_surface->finished)) {
+ _cairo_error_throw (CAIRO_STATUS_SURFACE_FINISHED);
+ return 0;
+ }
if (surface->base.type != CAIRO_SURFACE_TYPE_XLIB) {
_cairo_error_throw (CAIRO_STATUS_SURFACE_TYPE_MISMATCH);
return 0;
@@ -528,6 +533,10 @@ cairo_xlib_surface_get_depth (cairo_surface_t *abstract_surface)
{
cairo_xlib_xcb_surface_t *surface = (cairo_xlib_xcb_surface_t *) abstract_surface;
+ if (unlikely (abstract_surface->finished)) {
+ _cairo_error_throw (CAIRO_STATUS_SURFACE_FINISHED);
+ return 0;
+ }
if (surface->base.type != CAIRO_SURFACE_TYPE_XLIB) {
_cairo_error_throw (CAIRO_STATUS_SURFACE_TYPE_MISMATCH);
return 0;
@@ -547,6 +556,10 @@ cairo_xlib_surface_get_width (cairo_surface_t *abstract_surface)
{
cairo_xlib_xcb_surface_t *surface = (cairo_xlib_xcb_surface_t *) abstract_surface;
+ if (unlikely (abstract_surface->finished)) {
+ _cairo_error_throw (CAIRO_STATUS_SURFACE_FINISHED);
+ return 0;
+ }
if (surface->base.type != CAIRO_SURFACE_TYPE_XLIB) {
_cairo_error_throw (CAIRO_STATUS_SURFACE_TYPE_MISMATCH);
return 0;
@@ -566,6 +579,10 @@ cairo_xlib_surface_get_height (cairo_surface_t *abstract_surface)
{
cairo_xlib_xcb_surface_t *surface = (cairo_xlib_xcb_surface_t *) abstract_surface;
+ if (unlikely (abstract_surface->finished)) {
+ _cairo_error_throw (CAIRO_STATUS_SURFACE_FINISHED);
+ return 0;
+ }
if (surface->base.type != CAIRO_SURFACE_TYPE_XLIB) {
_cairo_error_throw (CAIRO_STATUS_SURFACE_TYPE_MISMATCH);
return 0;