diff options
author | Chris Wilson <chris@chris-wilson.co.uk> | 2009-09-01 23:12:43 +0100 |
---|---|---|
committer | Chris Wilson <chris@chris-wilson.co.uk> | 2009-09-01 23:12:43 +0100 |
commit | 7d1eb259f93d3f2f2e754b2b8b90cb88359b477d (patch) | |
tree | b608289649a97f6d0088246c1e09abb9fc1ad17b | |
parent | b8ddd66cf6e0d16383580c3c3398343f577b89fd (diff) |
[xlib] Make xlib_display_t private and rename xlib_screen_info_t
The issue Joonas was trying to solve was the unwanted inclusion of
the inlines via cairo-freelist-private.h. Unwittingly he included
cairoint.h from cairo-xlib-private.h instead, a far more heinous crime as
that causes the boilerplate to try to use the hidden, private symbols.
Instead we resolve this issue by making the cairo_xlib_display_t structure
private to cairo-xlib-display.c and provide functions to manipulate the
abstract data type. Whilst in the vicinity, we rename
cairo_xlib_screen_info_t to cairo_xlib_screen_t for consistency and
cleanliness.
-rw-r--r-- | src/cairo-xlib-display.c | 126 | ||||
-rw-r--r-- | src/cairo-xlib-private.h | 88 | ||||
-rw-r--r-- | src/cairo-xlib-screen.c | 155 | ||||
-rw-r--r-- | src/cairo-xlib-surface-private.h | 3 | ||||
-rw-r--r-- | src/cairo-xlib-surface.c | 173 |
5 files changed, 339 insertions, 206 deletions
diff --git a/src/cairo-xlib-display.c b/src/cairo-xlib-display.c index d05bfedd..0c0ce61c 100644 --- a/src/cairo-xlib-display.c +++ b/src/cairo-xlib-display.c @@ -38,8 +38,32 @@ #include "cairo-xlib-private.h" #include "cairo-xlib-xrender-private.h" +#include "cairo-freelist-private.h" + #include <X11/Xlibint.h> /* For XESetCloseDisplay */ +struct _cairo_xlib_display { + cairo_xlib_display_t *next; + cairo_reference_count_t ref_count; + cairo_mutex_t mutex; + + Display *display; + cairo_xlib_screen_t *screens; + + int render_major; + int render_minor; + XRenderPictFormat *cached_xrender_formats[CAIRO_FORMAT_A1 + 1]; + + cairo_xlib_job_t *workqueue; + cairo_freelist_t wq_freelist; + + cairo_xlib_hook_t *close_display_hooks; + unsigned int buggy_gradients :1; + unsigned int buggy_pad_reflect :1; + unsigned int buggy_repeat :1; + unsigned int closed :1; +}; + typedef int (*cairo_xlib_error_func_t) (Display *display, XErrorEvent *event); @@ -71,14 +95,14 @@ _cairo_xlib_remove_close_display_hook_internal (cairo_xlib_display_t *display, static void _cairo_xlib_call_close_display_hooks (cairo_xlib_display_t *display) { - cairo_xlib_screen_info_t *screen; + cairo_xlib_screen_t *screen; cairo_xlib_hook_t *hook; /* call all registered shutdown routines */ CAIRO_MUTEX_LOCK (display->mutex); for (screen = display->screens; screen != NULL; screen = screen->next) - _cairo_xlib_screen_info_close_display (screen); + _cairo_xlib_screen_close_display (screen); while (TRUE) { hook = display->close_display_hooks; @@ -99,7 +123,7 @@ _cairo_xlib_call_close_display_hooks (cairo_xlib_display_t *display) static void _cairo_xlib_display_discard_screens (cairo_xlib_display_t *display) { - cairo_xlib_screen_info_t *screens; + cairo_xlib_screen_t *screens; CAIRO_MUTEX_LOCK (display->mutex); screens = display->screens; @@ -107,10 +131,10 @@ _cairo_xlib_display_discard_screens (cairo_xlib_display_t *display) CAIRO_MUTEX_UNLOCK (display->mutex); while (screens != NULL) { - cairo_xlib_screen_info_t *screen = screens; + cairo_xlib_screen_t *screen = screens; screens = screen->next; - _cairo_xlib_screen_info_destroy (screen); + _cairo_xlib_screen_destroy (screen); } } @@ -559,3 +583,95 @@ _cairo_xlib_display_get_xrender_format (cairo_xlib_display_t *display, return xrender_format; } + +Display * +_cairo_xlib_display_get_dpy (cairo_xlib_display_t *display) +{ + return display->display; +} + +void +_cairo_xlib_display_remove_screen (cairo_xlib_display_t *display, + cairo_xlib_screen_t *screen) +{ + cairo_xlib_screen_t **prev; + cairo_xlib_screen_t *list; + + CAIRO_MUTEX_LOCK (display->mutex); + for (prev = &display->screens; (list = *prev); prev = &list->next) { + if (list == screen) { + *prev = screen->next; + break; + } + } + CAIRO_MUTEX_UNLOCK (display->mutex); +} + +cairo_status_t +_cairo_xlib_display_get_screen (cairo_xlib_display_t *display, + Screen *screen, + cairo_xlib_screen_t **out) +{ + cairo_xlib_screen_t *info = NULL, **prev; + + CAIRO_MUTEX_LOCK (display->mutex); + if (display->closed) { + CAIRO_MUTEX_UNLOCK (display->mutex); + return _cairo_error (CAIRO_STATUS_SURFACE_FINISHED); + } + + for (prev = &display->screens; (info = *prev); prev = &(*prev)->next) { + if (info->screen == screen) { + /* + * MRU the list + */ + if (prev != &display->screens) { + *prev = info->next; + info->next = display->screens; + display->screens = info; + } + break; + } + } + CAIRO_MUTEX_UNLOCK (display->mutex); + + *out = info; + return CAIRO_STATUS_SUCCESS; +} + + +void +_cairo_xlib_display_add_screen (cairo_xlib_display_t *display, + cairo_xlib_screen_t *screen) +{ + CAIRO_MUTEX_LOCK (display->mutex); + screen->next = display->screens; + display->screens = screen; + CAIRO_MUTEX_UNLOCK (display->mutex); +} + +void +_cairo_xlib_display_get_xrender_version (cairo_xlib_display_t *display, + int *major, int *minor) +{ + *major = display->render_major; + *minor = display->render_minor; +} + +cairo_bool_t +_cairo_xlib_display_has_repeat (cairo_xlib_display_t *display) +{ + return ! display->buggy_repeat; +} + +cairo_bool_t +_cairo_xlib_display_has_reflect (cairo_xlib_display_t *display) +{ + return ! display->buggy_pad_reflect; +} + +cairo_bool_t +_cairo_xlib_display_has_gradients (cairo_xlib_display_t *display) +{ + return ! display->buggy_gradients; +} diff --git a/src/cairo-xlib-private.h b/src/cairo-xlib-private.h index b980b074..e92bb942 100644 --- a/src/cairo-xlib-private.h +++ b/src/cairo-xlib-private.h @@ -41,11 +41,13 @@ #include "cairo-xlib-xrender-private.h" #include "cairo-compiler-private.h" -#include "cairo-freelist-private.h" #include "cairo-mutex-private.h" #include "cairo-reference-count-private.h" +#include "cairo-types-private.h" typedef struct _cairo_xlib_display cairo_xlib_display_t; +typedef struct _cairo_xlib_screen cairo_xlib_screen_t; + typedef struct _cairo_xlib_hook cairo_xlib_hook_t; typedef struct _cairo_xlib_job cairo_xlib_job_t; typedef void (*cairo_xlib_notify_func) (Display *, void *); @@ -56,28 +58,6 @@ struct _cairo_xlib_hook { void (*func) (cairo_xlib_display_t *display, void *data); }; -struct _cairo_xlib_display { - cairo_xlib_display_t *next; - cairo_reference_count_t ref_count; - cairo_mutex_t mutex; - - Display *display; - cairo_xlib_screen_info_t *screens; - - int render_major; - int render_minor; - XRenderPictFormat *cached_xrender_formats[CAIRO_FORMAT_A1 + 1]; - - cairo_xlib_job_t *workqueue; - cairo_freelist_t wq_freelist; - - cairo_xlib_hook_t *close_display_hooks; - unsigned int buggy_gradients :1; - unsigned int buggy_pad_reflect :1; - unsigned int buggy_repeat :1; - unsigned int closed :1; -}; - /* size of color cube */ #define CUBE_SIZE 6 /* size of gray ramp */ @@ -92,8 +72,8 @@ typedef struct _cairo_xlib_visual_info { uint8_t gray8_to_pseudocolor[256]; } cairo_xlib_visual_info_t; -struct _cairo_xlib_screen_info { - cairo_xlib_screen_info_t *next; +struct _cairo_xlib_screen { + cairo_xlib_screen_t *next; cairo_reference_count_t ref_count; cairo_mutex_t mutex; @@ -115,10 +95,33 @@ _cairo_xlib_display_get (Display *display, cairo_xlib_display_t **out); cairo_private cairo_xlib_display_t * _cairo_xlib_display_reference (cairo_xlib_display_t *info); + cairo_private void _cairo_xlib_display_destroy (cairo_xlib_display_t *info); cairo_private void +_cairo_xlib_display_lock (cairo_xlib_display_t *display); + +cairo_private void +_cairo_xlib_display_unlock (cairo_xlib_display_t *display); + +cairo_private Display * +_cairo_xlib_display_get_dpy (cairo_xlib_display_t *info); + +cairo_private void +_cairo_xlib_display_add_screen (cairo_xlib_display_t *display, + cairo_xlib_screen_t *screen); + +cairo_private cairo_status_t +_cairo_xlib_display_get_screen (cairo_xlib_display_t *display, + Screen *screen, + cairo_xlib_screen_t **out); + +cairo_private void +_cairo_xlib_display_remove_screen (cairo_xlib_display_t *display, + cairo_xlib_screen_t *screen); + +cairo_private void _cairo_xlib_add_close_display_hook (cairo_xlib_display_t *display, cairo_xlib_hook_t *hook); cairo_private void @@ -136,40 +139,53 @@ _cairo_xlib_display_queue_resource (cairo_xlib_display_t *display, cairo_private void _cairo_xlib_display_notify (cairo_xlib_display_t *display); +cairo_private void +_cairo_xlib_display_get_xrender_version (cairo_xlib_display_t *display, + int *major, int *minor); + +cairo_private cairo_bool_t +_cairo_xlib_display_has_repeat (cairo_xlib_display_t *display); + +cairo_private cairo_bool_t +_cairo_xlib_display_has_reflect (cairo_xlib_display_t *display); + +cairo_private cairo_bool_t +_cairo_xlib_display_has_gradients (cairo_xlib_display_t *display); + cairo_private XRenderPictFormat * _cairo_xlib_display_get_xrender_format (cairo_xlib_display_t *display, cairo_format_t format); cairo_private cairo_status_t -_cairo_xlib_screen_info_get (cairo_xlib_display_t *display, - Screen *screen, - cairo_xlib_screen_info_t **out); +_cairo_xlib_screen_get (Display *dpy, + Screen *screen, + cairo_xlib_screen_t **out); -cairo_private cairo_xlib_screen_info_t * -_cairo_xlib_screen_info_reference (cairo_xlib_screen_info_t *info); +cairo_private cairo_xlib_screen_t * +_cairo_xlib_screen_reference (cairo_xlib_screen_t *info); cairo_private void -_cairo_xlib_screen_info_destroy (cairo_xlib_screen_info_t *info); +_cairo_xlib_screen_destroy (cairo_xlib_screen_t *info); cairo_private void -_cairo_xlib_screen_info_close_display (cairo_xlib_screen_info_t *info); +_cairo_xlib_screen_close_display (cairo_xlib_screen_t *info); cairo_private GC -_cairo_xlib_screen_get_gc (cairo_xlib_screen_info_t *info, +_cairo_xlib_screen_get_gc (cairo_xlib_screen_t *info, unsigned int depth, Drawable drawable, unsigned int *need_reset); cairo_private void -_cairo_xlib_screen_put_gc (cairo_xlib_screen_info_t *info, +_cairo_xlib_screen_put_gc (cairo_xlib_screen_t *info, unsigned int depth, GC gc, cairo_bool_t reset_clip); cairo_private cairo_font_options_t * -_cairo_xlib_screen_get_font_options (cairo_xlib_screen_info_t *info); +_cairo_xlib_screen_get_font_options (cairo_xlib_screen_t *info); cairo_private cairo_status_t -_cairo_xlib_screen_get_visual_info (cairo_xlib_screen_info_t *info, +_cairo_xlib_screen_get_visual_info (cairo_xlib_screen_t *info, Visual *visual, cairo_xlib_visual_info_t **out); diff --git a/src/cairo-xlib-screen.c b/src/cairo-xlib-screen.c index e491a333..38e64af3 100644 --- a/src/cairo-xlib-screen.c +++ b/src/cairo-xlib-screen.c @@ -144,7 +144,7 @@ get_integer_default (Display *dpy, static void _cairo_xlib_init_screen_font_options (Display *dpy, - cairo_xlib_screen_info_t *info) + cairo_xlib_screen_t *info) { cairo_bool_t xft_hinting; cairo_bool_t xft_antialias; @@ -254,8 +254,8 @@ _cairo_xlib_init_screen_font_options (Display *dpy, cairo_font_options_set_hint_metrics (&info->font_options, CAIRO_HINT_METRICS_ON); } -cairo_xlib_screen_info_t * -_cairo_xlib_screen_info_reference (cairo_xlib_screen_info_t *info) +cairo_xlib_screen_t * +_cairo_xlib_screen_reference (cairo_xlib_screen_t *info) { assert (CAIRO_REFERENCE_COUNT_HAS_REFERENCE (&info->ref_count)); @@ -265,7 +265,7 @@ _cairo_xlib_screen_info_reference (cairo_xlib_screen_info_t *info) } void -_cairo_xlib_screen_info_close_display (cairo_xlib_screen_info_t *info) +_cairo_xlib_screen_close_display (cairo_xlib_screen_t *info) { cairo_xlib_visual_info_t **visuals; Display *dpy; @@ -273,7 +273,7 @@ _cairo_xlib_screen_info_close_display (cairo_xlib_screen_info_t *info) CAIRO_MUTEX_LOCK (info->mutex); - dpy = info->display->display; + dpy = _cairo_xlib_display_get_dpy (info->display); #if HAS_ATOMIC_OPS do { @@ -297,26 +297,16 @@ _cairo_xlib_screen_info_close_display (cairo_xlib_screen_info_t *info) } void -_cairo_xlib_screen_info_destroy (cairo_xlib_screen_info_t *info) +_cairo_xlib_screen_destroy (cairo_xlib_screen_t *info) { - cairo_xlib_screen_info_t **prev; - cairo_xlib_screen_info_t *list; - assert (CAIRO_REFERENCE_COUNT_HAS_REFERENCE (&info->ref_count)); if (! _cairo_reference_count_dec_and_test (&info->ref_count)) return; - CAIRO_MUTEX_LOCK (info->display->mutex); - for (prev = &info->display->screens; (list = *prev); prev = &list->next) { - if (list == info) { - *prev = info->next; - break; - } - } - CAIRO_MUTEX_UNLOCK (info->display->mutex); + _cairo_xlib_display_remove_screen (info->display, info); - _cairo_xlib_screen_info_close_display (info); + _cairo_xlib_screen_close_display (info); _cairo_xlib_display_destroy (info->display); @@ -328,77 +318,68 @@ _cairo_xlib_screen_info_destroy (cairo_xlib_screen_info_t *info) } cairo_status_t -_cairo_xlib_screen_info_get (cairo_xlib_display_t *display, - Screen *screen, - cairo_xlib_screen_info_t **out) +_cairo_xlib_screen_get (Display *dpy, + Screen *screen, + cairo_xlib_screen_t **out) { - cairo_xlib_screen_info_t *info = NULL, **prev; + cairo_xlib_display_t *display; + cairo_xlib_screen_t *info; + cairo_status_t status; - CAIRO_MUTEX_LOCK (display->mutex); - if (display->closed) { - CAIRO_MUTEX_UNLOCK (display->mutex); - return _cairo_error (CAIRO_STATUS_SURFACE_FINISHED); + status = _cairo_xlib_display_get (dpy, &display); + if (likely (status == CAIRO_STATUS_SUCCESS)) + status = _cairo_xlib_display_get_screen (display, screen, &info); + if (unlikely (status)) + goto CLEANUP_DISPLAY; + + if (info != NULL) { + *out = _cairo_xlib_screen_reference (info); + goto CLEANUP_DISPLAY; } - for (prev = &display->screens; (info = *prev); prev = &(*prev)->next) { - if (info->screen == screen) { - /* - * MRU the list - */ - if (prev != &display->screens) { - *prev = info->next; - info->next = display->screens; - display->screens = info; - } - break; - } + info = malloc (sizeof (cairo_xlib_screen_t)); + if (unlikely (info == NULL)) { + status = _cairo_error (CAIRO_STATUS_NO_MEMORY); + goto CLEANUP_DISPLAY; } - CAIRO_MUTEX_UNLOCK (display->mutex); - if (info != NULL) { - info = _cairo_xlib_screen_info_reference (info); - } else { - info = malloc (sizeof (cairo_xlib_screen_info_t)); - if (unlikely (info == NULL)) - return _cairo_error (CAIRO_STATUS_NO_MEMORY); - - CAIRO_REFERENCE_COUNT_INIT (&info->ref_count, 2); /* Add one for display cache */ - CAIRO_MUTEX_INIT (info->mutex); - info->display = _cairo_xlib_display_reference (display); - info->screen = screen; - info->has_render = FALSE; - info->has_font_options = FALSE; - info->gc_depths = 0; - memset (info->gc, 0, sizeof (info->gc)); - - _cairo_array_init (&info->visuals, - sizeof (cairo_xlib_visual_info_t*)); - - if (screen) { - Display *dpy = display->display; - int event_base, error_base; - - info->has_render = (XRenderQueryExtension (dpy, &event_base, &error_base) && - (XRenderFindVisualFormat (dpy, DefaultVisual (dpy, DefaultScreen (dpy))) != 0)); - } + CAIRO_REFERENCE_COUNT_INIT (&info->ref_count, 2); /* Add one for display cache */ + CAIRO_MUTEX_INIT (info->mutex); + info->display = display; + info->screen = screen; + info->has_render = FALSE; + info->has_font_options = FALSE; + info->gc_depths = 0; + memset (info->gc, 0, sizeof (info->gc)); + + _cairo_array_init (&info->visuals, + sizeof (cairo_xlib_visual_info_t*)); - /* Small window of opportunity for two screen infos for the same - * Screen - just wastes a little bit of memory but should not cause - * any corruption. - */ - CAIRO_MUTEX_LOCK (display->mutex); - info->next = display->screens; - display->screens = info; - CAIRO_MUTEX_UNLOCK (display->mutex); + if (screen) { + int event_base, error_base; + + info->has_render = + XRenderQueryExtension (dpy, &event_base, &error_base) && + (XRenderFindVisualFormat (dpy, DefaultVisual (dpy, DefaultScreen (dpy))) != 0); } + /* Small window of opportunity for two screen infos for the same + * Screen - just wastes a little bit of memory but should not cause + * any corruption. + */ + _cairo_xlib_display_add_screen (display, info); + *out = info; return CAIRO_STATUS_SUCCESS; + + CLEANUP_DISPLAY: + _cairo_xlib_display_destroy (display); + return status; } #if HAS_ATOMIC_OPS GC -_cairo_xlib_screen_get_gc (cairo_xlib_screen_info_t *info, +_cairo_xlib_screen_get_gc (cairo_xlib_screen_t *info, unsigned int depth, Drawable drawable, unsigned int *dirty) @@ -438,12 +419,13 @@ _cairo_xlib_screen_get_gc (cairo_xlib_screen_info_t *info, } gcv.graphics_exposures = False; - return XCreateGC (info->display->display, drawable, + return XCreateGC (_cairo_xlib_display_get_dpy (info->display), + drawable, GCGraphicsExposures, &gcv); } void -_cairo_xlib_screen_put_gc (cairo_xlib_screen_info_t *info, +_cairo_xlib_screen_put_gc (cairo_xlib_screen_t *info, unsigned int depth, GC gc, cairo_bool_t reset_clip) @@ -485,7 +467,7 @@ out: } #else GC -_cairo_xlib_screen_get_gc (cairo_xlib_screen_info_t *info, +_cairo_xlib_screen_get_gc (cairo_xlib_screen_t *info, unsigned int depth, Drawable drawable, unsigned int *dirty) @@ -510,7 +492,8 @@ _cairo_xlib_screen_get_gc (cairo_xlib_screen_info_t *info, XGCValues gcv; gcv.graphics_exposures = False; - gc = XCreateGC (info->display->display, drawable, + gc = XCreateGC (_cairo_xlib_display_get_dpy (info->display), + drawable, GCGraphicsExposures, &gcv); } @@ -518,7 +501,7 @@ _cairo_xlib_screen_get_gc (cairo_xlib_screen_info_t *info, } void -_cairo_xlib_screen_put_gc (cairo_xlib_screen_info_t *info, +_cairo_xlib_screen_put_gc (cairo_xlib_screen_t *info, unsigned int depth, GC gc, cairo_bool_t reset_clip) @@ -557,11 +540,11 @@ _cairo_xlib_screen_put_gc (cairo_xlib_screen_info_t *info, #endif cairo_status_t -_cairo_xlib_screen_get_visual_info (cairo_xlib_screen_info_t *info, +_cairo_xlib_screen_get_visual_info (cairo_xlib_screen_t *info, Visual *visual, cairo_xlib_visual_info_t **out) { - Display *dpy = info->display->display; + Display *dpy = _cairo_xlib_display_get_dpy (info->display); cairo_xlib_visual_info_t **visuals, *ret = NULL; cairo_status_t status; int i, n_visuals; @@ -617,19 +600,19 @@ _cairo_xlib_screen_get_visual_info (cairo_xlib_screen_info_t *info, } cairo_font_options_t * -_cairo_xlib_screen_get_font_options (cairo_xlib_screen_info_t *info) +_cairo_xlib_screen_get_font_options (cairo_xlib_screen_t *info) { if (info->has_font_options) return &info->font_options; CAIRO_MUTEX_LOCK (info->mutex); if (! info->has_font_options) { - Display *dpy = info->display->display; - _cairo_font_options_init_default (&info->font_options); - if (info->screen != NULL) - _cairo_xlib_init_screen_font_options (dpy, info); + if (info->screen != NULL) { + _cairo_xlib_init_screen_font_options (_cairo_xlib_display_get_dpy (info->display), + info); + } info->has_font_options = TRUE; } diff --git a/src/cairo-xlib-surface-private.h b/src/cairo-xlib-surface-private.h index cb97650b..b3cbe045 100644 --- a/src/cairo-xlib-surface-private.h +++ b/src/cairo-xlib-surface-private.h @@ -46,12 +46,11 @@ struct _cairo_xlib_surface { Display *dpy; cairo_xlib_display_t *display; - cairo_xlib_screen_info_t *screen_info; + cairo_xlib_screen_t *screen; cairo_xlib_hook_t close_display_hook; GC gc; Drawable drawable; - Screen *screen; cairo_bool_t owns_pixmap; Visual *visual; diff --git a/src/cairo-xlib-surface.c b/src/cairo-xlib-surface.c index 65b8a694..b53f4dec 100644 --- a/src/cairo-xlib-surface.c +++ b/src/cairo-xlib-surface.c @@ -74,9 +74,8 @@ typedef int (*cairo_xlib_error_func_t) (Display *display, XErrorEvent *event); static cairo_surface_t * -_cairo_xlib_surface_create_internal (Display *dpy, +_cairo_xlib_surface_create_internal (cairo_xlib_screen_t *screen, Drawable drawable, - Screen *screen, Visual *visual, XRenderPictFormat *xrender_format, int width, @@ -249,8 +248,8 @@ _cairo_xlib_surface_create_similar_with_format (void *abstract_src, xrender_format->depth); surface = (cairo_xlib_surface_t *) - _cairo_xlib_surface_create_internal (dpy, pix, - src->screen, NULL, + _cairo_xlib_surface_create_internal (src->screen, pix, + NULL, xrender_format, width, height, xrender_format->depth); @@ -327,8 +326,8 @@ _cairo_xlib_surface_create_similar (void *abstract_src, xrender_format->depth); surface = (cairo_xlib_surface_t *) - _cairo_xlib_surface_create_internal (src->dpy, pix, - src->screen, src->visual, + _cairo_xlib_surface_create_internal (src->screen, pix, + src->visual, xrender_format, width, height, xrender_format->depth); @@ -382,7 +381,7 @@ _cairo_xlib_surface_finish (void *abstract_surface) } if (surface->gc != NULL) { - _cairo_xlib_screen_put_gc (surface->screen_info, + _cairo_xlib_screen_put_gc (surface->screen, surface->depth, surface->gc, surface->gc_has_clip_rects); @@ -392,17 +391,15 @@ _cairo_xlib_surface_finish (void *abstract_surface) if (surface->clip_rects != surface->embedded_clip_rects) free (surface->clip_rects); - if (surface->screen_info != NULL) - _cairo_xlib_screen_info_destroy (surface->screen_info); - - if (surface->display != NULL) { + if (surface->dpy != NULL) { _cairo_xlib_remove_close_display_hook (surface->display, &surface->close_display_hook); - _cairo_xlib_display_destroy (surface->display); + surface->dpy = NULL; } + _cairo_xlib_screen_destroy (surface->screen); + cairo_region_destroy (surface->clip_region); - surface->dpy = NULL; return status; } @@ -857,7 +854,7 @@ _get_image_surface (cairo_xlib_surface_t *surface, } else { format = CAIRO_FORMAT_RGB24; - status = _cairo_xlib_screen_get_visual_info (surface->screen_info, + status = _cairo_xlib_screen_get_visual_info (surface->screen, surface->visual, &visual_info); if (unlikely (status)) @@ -984,7 +981,7 @@ _cairo_xlib_surface_ensure_gc (cairo_xlib_surface_t *surface, { if (surface->gc == NULL) { - surface->gc = _cairo_xlib_screen_get_gc (surface->screen_info, + surface->gc = _cairo_xlib_screen_get_gc (surface->screen, surface->depth, surface->drawable, &surface->clip_dirty); @@ -1017,7 +1014,7 @@ _cairo_xlib_surface_maybe_put_gc (cairo_xlib_surface_t *surface) if (surface->gc_has_clip_rects) return; - _cairo_xlib_screen_put_gc (surface->screen_info, + _cairo_xlib_screen_put_gc (surface->screen, surface->depth, surface->gc, FALSE); @@ -1117,7 +1114,7 @@ _draw_image_surface (cairo_xlib_surface_t *surface, _characterize_field (surface->g_mask, &o_g_width, &o_g_shift); _characterize_field (surface->b_mask, &o_b_width, &o_b_shift); } else { - status = _cairo_xlib_screen_get_visual_info (surface->screen_info, + status = _cairo_xlib_screen_get_visual_info (surface->screen, surface->visual, &visual_info); if (unlikely (status)) @@ -1289,7 +1286,7 @@ static inline cairo_bool_t _cairo_xlib_surface_same_screen (cairo_xlib_surface_t *dst, cairo_xlib_surface_t *src) { - return dst->screen_info == src->screen_info; + return dst->screen == src->screen; } static cairo_status_t @@ -1400,9 +1397,9 @@ _cairo_xlib_surface_create_solid_pattern_surface (void *abstrac other->depth); surface = (cairo_xlib_surface_t *) - _cairo_xlib_surface_create_internal (other->dpy, + _cairo_xlib_surface_create_internal (other->screen, pixmap, - other->screen, other->visual, + other->visual, other->xrender_format, width, height, other->depth); @@ -2010,9 +2007,9 @@ _cairo_xlib_surface_acquire_pattern_surface (cairo_xlib_surface_t *dst, CAIRO_FORMAT_ARGB32); surface = (cairo_xlib_surface_t *) - _cairo_xlib_surface_create_internal (dst->dpy, None, - dst->screen, NULL, - format, 0, 0, 32); + _cairo_xlib_surface_create_internal (dst->screen, None, + NULL, format, + 0, 0, 32); if (unlikely (surface->base.status)) { XRenderFreePicture (dst->dpy, picture); return surface->base.status; @@ -2744,7 +2741,7 @@ _cairo_xlib_surface_get_font_options (void *abstract_surface, { cairo_xlib_surface_t *surface = abstract_surface; - *options = *_cairo_xlib_screen_get_font_options (surface->screen_info); + *options = *_cairo_xlib_screen_get_font_options (surface->screen); } static void @@ -2870,19 +2867,15 @@ _cairo_xlib_surface_detach_display (cairo_xlib_display_t *display, void *data) } static cairo_surface_t * -_cairo_xlib_surface_create_internal (Display *dpy, - Drawable drawable, - Screen *screen, - Visual *visual, - XRenderPictFormat *xrender_format, - int width, - int height, - int depth) +_cairo_xlib_surface_create_internal (cairo_xlib_screen_t *screen, + Drawable drawable, + Visual *visual, + XRenderPictFormat *xrender_format, + int width, + int height, + int depth) { cairo_xlib_surface_t *surface; - cairo_xlib_display_t *display; - cairo_xlib_screen_info_t *screen_info; - cairo_status_t status; CAIRO_MUTEX_INITIALIZE (); @@ -2891,14 +2884,15 @@ _cairo_xlib_surface_create_internal (Display *dpy, /* XXX find matching visual for core/dithering fallbacks? */ } else if (visual) { + Screen *scr = screen->screen; int j, k; /* This is ugly, but we have to walk over all visuals * for the display to find the correct depth. */ depth = 0; - for (j = 0; j < screen->ndepths; j++) { - Depth *d = &screen->depths[j]; + for (j = 0; j < scr->ndepths; j++) { + Depth *d = &scr->depths[j]; for (k = 0; k < d->nvisuals; k++) { if (&d->visuals[k] == visual) { depth = d->depth; @@ -2913,36 +2907,27 @@ _cairo_xlib_surface_create_internal (Display *dpy, if (depth == 0) return _cairo_surface_create_in_error (_cairo_error (CAIRO_STATUS_INVALID_VISUAL)); - status = _cairo_xlib_display_get (dpy, &display); - if (unlikely (status)) - return _cairo_surface_create_in_error (status); - - status = _cairo_xlib_screen_info_get (display, screen, &screen_info); - if (unlikely (status)) { - _cairo_xlib_display_destroy (display); - return _cairo_surface_create_in_error (status); - } - surface = malloc (sizeof (cairo_xlib_surface_t)); - if (unlikely (surface == NULL)) { - _cairo_xlib_screen_info_destroy (screen_info); - _cairo_xlib_display_destroy (display); + if (unlikely (surface == NULL)) return _cairo_surface_create_in_error (_cairo_error (CAIRO_STATUS_NO_MEMORY)); - } + + surface->dpy = _cairo_xlib_display_get_dpy (screen->display); /* initialize and hook into the CloseDisplay callback */ surface->close_display_hook.func = _cairo_xlib_surface_detach_display; - _cairo_xlib_add_close_display_hook (display, &surface->close_display_hook); + _cairo_xlib_add_close_display_hook (screen->display, + &surface->close_display_hook); - surface->render_major = display->render_major; - surface->render_minor = display->render_minor; + _cairo_xlib_display_get_xrender_version (screen->display, + &surface->render_major, + &surface->render_minor); if (CAIRO_SURFACE_RENDER_HAS_CREATE_PICTURE (surface)) { if (!xrender_format) { if (visual) { - xrender_format = XRenderFindVisualFormat (dpy, visual); + xrender_format = XRenderFindVisualFormat (surface->dpy, visual); } else if (depth == 1) { xrender_format = - _cairo_xlib_display_get_xrender_format (display, + _cairo_xlib_display_get_xrender_format (screen->display, CAIRO_FORMAT_A1); } } @@ -2959,29 +2944,27 @@ _cairo_xlib_surface_create_internal (Display *dpy, _cairo_surface_init (&surface->base, &cairo_xlib_surface_backend, _xrender_format_to_content (xrender_format)); - surface->dpy = dpy; - surface->display = display; - surface->screen_info = screen_info; + surface->screen = _cairo_xlib_screen_reference (screen); + surface->display = screen->display; surface->gc = NULL; surface->drawable = drawable; - surface->screen = screen; surface->owns_pixmap = FALSE; surface->use_pixmap = 0; surface->width = width; surface->height = height; - surface->buggy_repeat = screen_info->display->buggy_repeat; + surface->buggy_repeat = ! _cairo_xlib_display_has_repeat (surface->display); if (! CAIRO_SURFACE_RENDER_HAS_FILL_RECTANGLES (surface)) { /* so we can use the XTile fallback */ surface->buggy_repeat = TRUE; } - surface->buggy_pad_reflect = screen_info->display->buggy_pad_reflect; + surface->buggy_pad_reflect = ! _cairo_xlib_display_has_reflect (surface->display); if (! CAIRO_SURFACE_RENDER_HAS_EXTENDED_REPEAT (surface)) surface->buggy_pad_reflect = TRUE; - surface->buggy_gradients = screen_info->display->buggy_gradients; + surface->buggy_gradients = ! _cairo_xlib_display_has_gradients (surface->display); if (! CAIRO_SURFACE_RENDER_HAS_GRADIENTS (surface)) surface->buggy_gradients = TRUE; @@ -3095,13 +3078,25 @@ cairo_xlib_surface_create (Display *dpy, int width, int height) { - Screen *screen = _cairo_xlib_screen_from_visual (dpy, visual); + Screen *scr; + cairo_xlib_screen_t *screen; + cairo_surface_t *surface; + cairo_status_t status; - if (screen == NULL) + scr = _cairo_xlib_screen_from_visual (dpy, visual); + if (scr == NULL) return _cairo_surface_create_in_error (_cairo_error (CAIRO_STATUS_INVALID_VISUAL)); - return _cairo_xlib_surface_create_internal (dpy, drawable, screen, - visual, NULL, width, height, 0); + status = _cairo_xlib_screen_get (dpy, scr, &screen); + if (unlikely (status)) + return _cairo_surface_create_in_error (status); + + surface = _cairo_xlib_surface_create_internal (screen, drawable, + visual, NULL, + width, height, 0); + _cairo_xlib_screen_destroy (screen); + + return surface; } slim_hidden_def (cairo_xlib_surface_create); @@ -3121,12 +3116,24 @@ slim_hidden_def (cairo_xlib_surface_create); cairo_surface_t * cairo_xlib_surface_create_for_bitmap (Display *dpy, Pixmap bitmap, - Screen *screen, + Screen *scr, int width, int height) { - return _cairo_xlib_surface_create_internal (dpy, bitmap, screen, - NULL, NULL, width, height, 1); + cairo_xlib_screen_t *screen; + cairo_surface_t *surface; + cairo_status_t status; + + status = _cairo_xlib_screen_get (dpy, scr, &screen); + if (unlikely (status)) + return _cairo_surface_create_in_error (status); + + surface = _cairo_xlib_surface_create_internal (screen, bitmap, + NULL, NULL, + width, height, 1); + _cairo_xlib_screen_destroy (screen); + + return surface; } #if CAIRO_HAS_XLIB_XRENDER_SURFACE @@ -3153,13 +3160,25 @@ cairo_xlib_surface_create_for_bitmap (Display *dpy, cairo_surface_t * cairo_xlib_surface_create_with_xrender_format (Display *dpy, Drawable drawable, - Screen *screen, + Screen *scr, XRenderPictFormat *format, int width, int height) { - return _cairo_xlib_surface_create_internal (dpy, drawable, screen, - NULL, format, width, height, 0); + cairo_xlib_screen_t *screen; + cairo_surface_t *surface; + cairo_status_t status; + + status = _cairo_xlib_screen_get (dpy, scr, &screen); + if (unlikely (status)) + return _cairo_surface_create_in_error (status); + + surface = _cairo_xlib_surface_create_internal (screen, drawable, + NULL, format, + width, height, 0); + _cairo_xlib_screen_destroy (screen); + + return surface; } slim_hidden_def (cairo_xlib_surface_create_with_xrender_format); @@ -3358,7 +3377,7 @@ cairo_xlib_surface_get_screen (cairo_surface_t *abstract_surface) return NULL; } - return surface->screen; + return surface->screen->screen; } /** @@ -3504,7 +3523,7 @@ _cairo_xlib_surface_remove_scaled_font (cairo_xlib_display_t *display, Display *dpy; int i; - dpy = display->display; + dpy = _cairo_xlib_display_get_dpy (display); for (i = 0; i < NUM_GLYPHSETS; i++) { cairo_xlib_font_glyphset_info_t *glyphset_info; @@ -3706,8 +3725,8 @@ _cairo_xlib_scaled_font_get_glyphset_info_for_format (cairo_scaled_font_t *scale glyphset_info->xrender_format = _cairo_xlib_display_get_xrender_format (display, glyphset_info->format); - glyphset_info->glyphset = XRenderCreateGlyphSet (display->display, - glyphset_info->xrender_format); + glyphset_info->glyphset = XRenderCreateGlyphSet (_cairo_xlib_display_get_dpy (display), + glyphset_info->xrender_format); } return glyphset_info; |