summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorOwen Taylor <otaylor@redhat.com>2005-07-28 09:29:46 +0000
committerOwen Taylor <otaylor@redhat.com>2005-07-28 09:29:46 +0000
commitb9fe1b74665e528e6114bd833028a8f62ecfa869 (patch)
treef00a418b643d4257a246b23e5ec51032771ff7b3
parentd7699f0c072a6820007280a167b86a95adf8a54e (diff)
src/cairo-font.c src/cairoint.h: Define _cairo_font_face_nil. (cairo_font_face_reference, cairo_font_face_destroy cairo_font_face_set_user_data): Handle a nil font face. (cairo_font_face_status): New function.
src/cairo-ft-font.c (cairo_ft_font_face_create_for_pattern): src/cairo-ft-font.c (cairo_ft_font_face_create_for_ft_face): src/cairo-win32-font.c (cairo_win32_font_face_create_for_logfontw): Return _cairo_font_face_nil on out-of-memory. Check return of _cairo_simple_font_face_create(). Error out if font_face has a status. Handle a nil surface.
-rw-r--r--ChangeLog23
-rw-r--r--src/cairo-font.c57
-rw-r--r--src/cairo-ft-font.c26
-rw-r--r--src/cairo-gstate.c21
-rw-r--r--src/cairo-surface.c3
-rw-r--r--src/cairo-win32-font.c6
-rw-r--r--src/cairo.h3
-rw-r--r--src/cairoint.h3
8 files changed, 120 insertions, 22 deletions
diff --git a/ChangeLog b/ChangeLog
index 8470de91a..54dfbd48a 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,28 @@
2005-07-27 Owen Taylor <otaylor@redhat.com>
+ * src/cairo-font.c src/cairoint.h: Define _cairo_font_face_nil.
+ (cairo_font_face_reference, cairo_font_face_destroy
+ cairo_font_face_set_user_data): Handle a nil font face.
+ (cairo_font_face_status): New function.
+
+ * src/cairo-font.c (_cairo_simple_font_face_create)
+ src/cairo-ft-font.c (cairo_ft_font_face_create_for_pattern):
+ src/cairo-ft-font.c (cairo_ft_font_face_create_for_ft_face):
+ src/cairo-win32-font.c (cairo_win32_font_face_create_for_logfontw):
+ Return _cairo_font_face_nil on out-of-memory.
+
+ * src/cairo-gstate.c (_cairo_gstate_select_font_face)
+ * src/cairo-gstate.c (_cairo_gstate_ensure_font_face): Check return
+ of _cairo_simple_font_face_create().
+
+ * src/cairo-gstate.c (_cairo_gstate_set_font_face): Error out
+ if font_face has a status.
+
+ * src/cairo-surface.c (cairo_surface_set_user_data): Handle a nil
+ surface.
+
+2005-07-27 Owen Taylor <otaylor@redhat.com>
+
* test/Makefile.am (XFAIL_TESTS): Remove
text-antialias-none which is now fixed.
diff --git a/src/cairo-font.c b/src/cairo-font.c
index 8fc3b6872..9645f3df2 100644
--- a/src/cairo-font.c
+++ b/src/cairo-font.c
@@ -39,12 +39,25 @@
#include "cairoint.h"
+/* Forward declare so we can use it as an arbitrary backend for
+ * _cairo_font_face_nil.
+ */
+static const cairo_font_face_backend_t _cairo_simple_font_face_backend;
+
/* cairo_font_face_t */
+const cairo_font_face_t _cairo_font_face_nil = {
+ CAIRO_STATUS_NO_MEMORY, /* status */
+ -1, /* ref_count */
+ { 0, 0, 0, NULL }, /* user_data */
+ &_cairo_simple_font_face_backend
+};
+
void
_cairo_font_face_init (cairo_font_face_t *font_face,
const cairo_font_face_backend_t *backend)
{
+ font_face->status = CAIRO_STATUS_SUCCESS;
font_face->ref_count = 1;
font_face->backend = backend;
@@ -66,6 +79,9 @@ cairo_font_face_reference (cairo_font_face_t *font_face)
if (font_face == NULL)
return;
+ if (font_face->ref_count == (unsigned int)-1)
+ return;
+
font_face->ref_count++;
}
@@ -83,6 +99,9 @@ cairo_font_face_destroy (cairo_font_face_t *font_face)
if (font_face == NULL)
return;
+ if (font_face->ref_count == (unsigned int)-1)
+ return;
+
if (--(font_face->ref_count) > 0)
return;
@@ -101,6 +120,22 @@ cairo_font_face_destroy (cairo_font_face_t *font_face)
}
/**
+ * cairo_font_face_status:
+ * @surface: a #cairo_font_face_t
+ *
+ * Checks whether an error has previously occurred for this
+ * font face
+ *
+ * Return value: %CAIRO_STATUS_SUCCESS or another error such as
+ * %CAIRO_STATUS_NO_MEMORY.
+ **/
+cairo_status_t
+cairo_font_face_status (cairo_font_face_t *font_face)
+{
+ return font_face->status;
+}
+
+/**
* cairo_font_face_get_user_data:
* @font_face: a #cairo_font_face_t
* @key: the address of the #cairo_user_data_key_t the user data was
@@ -142,6 +177,9 @@ cairo_font_face_set_user_data (cairo_font_face_t *font_face,
void *user_data,
cairo_destroy_func_t destroy)
{
+ if (font_face->ref_count == -1)
+ return CAIRO_STATUS_NO_MEMORY;
+
return _cairo_user_data_array_set_data (&font_face->user_data,
key, user_data, destroy);
}
@@ -159,8 +197,6 @@ struct _cairo_simple_font_face {
cairo_font_weight_t weight;
};
-static const cairo_font_face_backend_t _cairo_simple_font_face_backend;
-
/* We maintain a global cache from family/weight/slant => cairo_font_face_t
* for cairo_simple_font_t. The primary purpose of this cache is to provide
* unique cairo_font_face_t values so that our cache from
@@ -406,15 +442,18 @@ _cairo_simple_font_face_create (const char *family,
cache = _get_global_simple_cache ();
if (cache == NULL) {
_unlock_global_simple_cache ();
- return NULL;
+ _cairo_error (CAIRO_STATUS_NO_MEMORY);
+ return (cairo_font_face_t *)&_cairo_font_face_nil;
}
status = _cairo_cache_lookup (cache, &key, (void **) &entry, &created_entry);
if (status == CAIRO_STATUS_SUCCESS && !created_entry)
cairo_font_face_reference (&entry->font_face->base);
_unlock_global_simple_cache ();
- if (status)
- return NULL;
+ if (status) {
+ _cairo_error (status);
+ return (cairo_font_face_t *)&_cairo_font_face_nil;
+ }
return &entry->font_face->base;
}
@@ -463,7 +502,8 @@ _cairo_scaled_font_set_error (cairo_scaled_font_t *scaled_font,
* Checks whether an error has previously occurred for this
* scaled_font.
*
- * Return value: %CAIRO_STATUS_SUCCESS or %CAIRO_STATUS_NULL_POINTER.
+ * Return value: %CAIRO_STATUS_SUCCESS or another error such as
+ * %CAIRO_STATUS_NO_MEMORY.
**/
cairo_status_t
cairo_scaled_font_status (cairo_scaled_font_t *scaled_font)
@@ -791,6 +831,9 @@ cairo_scaled_font_create (cairo_font_face_t *font_face,
cairo_cache_t *cache;
cairo_status_t status;
+ if (font_face->status)
+ return (cairo_scaled_font_t*) &_cairo_scaled_font_nil;
+
key.font_face = font_face;
key.font_matrix = font_matrix;
key.ctm = ctm;
@@ -810,7 +853,7 @@ cairo_scaled_font_create (cairo_font_face_t *font_face,
_unlock_global_font_cache ();
if (status) {
- _cairo_error (CAIRO_STATUS_NO_MEMORY);
+ _cairo_error (status);
return (cairo_scaled_font_t*) &_cairo_scaled_font_nil;
}
diff --git a/src/cairo-ft-font.c b/src/cairo-ft-font.c
index e1124afed..929ce58b7 100644
--- a/src/cairo-ft-font.c
+++ b/src/cairo-ft-font.c
@@ -2274,13 +2274,20 @@ cairo_ft_font_face_create_for_pattern (FcPattern *pattern)
cairo_font_face_t *font_face;
unscaled = _ft_unscaled_font_get_for_pattern (pattern);
- if (unscaled == NULL)
- return NULL;
+ if (unscaled == NULL) {
+ _cairo_error (CAIRO_STATUS_NO_MEMORY);
+ return (cairo_font_face_t *)&_cairo_font_face_nil;
+ }
font_face = _ft_font_face_create (unscaled, _get_pattern_load_flags (pattern));
_cairo_unscaled_font_destroy (&unscaled->base);
- return font_face;
+ if (font_face)
+ return font_face;
+ else {
+ _cairo_error (CAIRO_STATUS_NO_MEMORY);
+ return (cairo_font_face_t *)&_cairo_font_face_nil;
+ }
}
/**
@@ -2316,13 +2323,20 @@ cairo_ft_font_face_create_for_ft_face (FT_Face face,
cairo_font_face_t *font_face;
unscaled = _ft_unscaled_font_create_from_face (face);
- if (unscaled == NULL)
- return NULL;
+ if (unscaled == NULL) {
+ _cairo_error (CAIRO_STATUS_NO_MEMORY);
+ return (cairo_font_face_t *)&_cairo_font_face_nil;
+ }
font_face = _ft_font_face_create (unscaled, load_flags);
_cairo_unscaled_font_destroy (&unscaled->base);
- return font_face;
+ if (font_face) {
+ return font_face;
+ } else {
+ _cairo_error (CAIRO_STATUS_NO_MEMORY);
+ return (cairo_font_face_t *)&_cairo_font_face_nil;
+ }
}
/**
diff --git a/src/cairo-gstate.c b/src/cairo-gstate.c
index 43c4bcb0a..0cca756f3 100644
--- a/src/cairo-gstate.c
+++ b/src/cairo-gstate.c
@@ -1838,8 +1838,8 @@ _cairo_gstate_select_font_face (cairo_gstate_t *gstate,
cairo_font_face_t *font_face;
font_face = _cairo_simple_font_face_create (family, slant, weight);
- if (!font_face)
- return CAIRO_STATUS_NO_MEMORY;
+ if (font_face->status)
+ return font_face->status;
_cairo_gstate_set_font_face (gstate, font_face);
cairo_font_face_destroy (font_face);
@@ -1989,11 +1989,15 @@ static cairo_status_t
_cairo_gstate_ensure_font_face (cairo_gstate_t *gstate)
{
if (!gstate->font_face) {
- gstate->font_face = _cairo_simple_font_face_create (CAIRO_FONT_FAMILY_DEFAULT,
- CAIRO_FONT_SLANT_DEFAULT,
- CAIRO_FONT_WEIGHT_DEFAULT);
- if (!gstate->font_face)
- return CAIRO_STATUS_NO_MEMORY;
+ cairo_font_face_t *font_face;
+
+ font_face = _cairo_simple_font_face_create (CAIRO_FONT_FAMILY_DEFAULT,
+ CAIRO_FONT_SLANT_DEFAULT,
+ CAIRO_FONT_WEIGHT_DEFAULT);
+ if (font_face->status)
+ return font_face->status;
+ else
+ gstate->font_face = font_face;
}
return CAIRO_STATUS_SUCCESS;
@@ -2079,6 +2083,9 @@ cairo_status_t
_cairo_gstate_set_font_face (cairo_gstate_t *gstate,
cairo_font_face_t *font_face)
{
+ if (font_face->status)
+ return font_face->status;
+
if (font_face != gstate->font_face) {
if (gstate->font_face)
cairo_font_face_destroy (gstate->font_face);
diff --git a/src/cairo-surface.c b/src/cairo-surface.c
index 34967f2a1..59dfbad1c 100644
--- a/src/cairo-surface.c
+++ b/src/cairo-surface.c
@@ -338,6 +338,9 @@ cairo_surface_set_user_data (cairo_surface_t *surface,
void *user_data,
cairo_destroy_func_t destroy)
{
+ if (surface->ref_count == -1)
+ return CAIRO_STATUS_NO_MEMORY;
+
return _cairo_user_data_array_set_data (&surface->user_data,
key, user_data, destroy);
}
diff --git a/src/cairo-win32-font.c b/src/cairo-win32-font.c
index 1384d6622..9828ea5f3 100644
--- a/src/cairo-win32-font.c
+++ b/src/cairo-win32-font.c
@@ -1344,8 +1344,10 @@ cairo_win32_font_face_create_for_logfontw (LOGFONTW *logfont)
cairo_win32_font_face_t *font_face;
font_face = malloc (sizeof (cairo_win32_font_face_t));
- if (!font_face)
- return NULL;
+ if (!font_face) {
+ _cairo_error (CAIRO_STATUS_NO_MEMORY);
+ return (cairo_font_face_t *)&_cairo_font_face_nil;
+ }
font_face->logfont = *logfont;
diff --git a/src/cairo.h b/src/cairo.h
index 5252d2325..2f9bc2841 100644
--- a/src/cairo.h
+++ b/src/cairo.h
@@ -875,6 +875,9 @@ cairo_font_face_reference (cairo_font_face_t *font_face);
void
cairo_font_face_destroy (cairo_font_face_t *font_face);
+cairo_status_t
+cairo_font_face_status (cairo_font_face_t *font_face);
+
void *
cairo_font_face_get_user_data (cairo_font_face_t *font_face,
const cairo_user_data_key_t *key);
diff --git a/src/cairoint.h b/src/cairoint.h
index 9eca40e6d..d10812191 100644
--- a/src/cairoint.h
+++ b/src/cairoint.h
@@ -469,6 +469,7 @@ struct _cairo_scaled_font {
};
struct _cairo_font_face {
+ cairo_status_t status;
int ref_count;
cairo_user_data_array_t user_data;
const cairo_font_face_backend_t *backend;
@@ -1302,6 +1303,8 @@ cairo_private void
_cairo_scaled_font_set_error (cairo_scaled_font_t *scaled_font,
cairo_status_t status);
+extern const cairo_font_face_t _cairo_font_face_nil;
+
cairo_private void
_cairo_font_face_init (cairo_font_face_t *font_face,
const cairo_font_face_backend_t *backend);