diff --git a/ChangeLog b/ChangeLog index 5fd2b378c..0c9493708 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,27 @@ +2003-10-30 Carl Worth + + * configure.in (CAIRO_VERSION): Bumped version to 0.1.9 for change + in argument list of cairo_ft_font_create. + + * src/cairo_ft_font.c: A set of changes to eliminate the static + FT_Library field, (which could introduce nasty problems with + respect to threading). With the new code, each font created with + the toy API will own its own FT_Library. Meanwhile, + cairo_ft_font_create now accepts an FT_Library parameter. + + * src/cairo_ft_font.c: Add ft_library field so that fonts that own + their own FT_Library can also clean it up. Eliminate static + FT_Library and _init_cairo_ft_lib. + (cairo_ft_font_create): Now accepts an FT_Library argument. + (_cairo_ft_font_create): Create an FT_Library owned by this font, + (this only happens as part of the "toy API") + (_cairo_ft_font_destroy): Clean up ft_font->ft_library if + necessary. + (cairo_ft_font_create_for_ft_face): Initialize ft_library and + owns_ft_library. + + * src/cairo.h: Add FT_Library parameter to cairo_ft_font_create. + 2003-10-30 Carl Worth * cairo_font: A few cleanups to eliminate a memory leak. diff --git a/configure.in b/configure.in index cf8c68c27..e403780b9 100644 --- a/configure.in +++ b/configure.in @@ -3,7 +3,7 @@ AC_INIT(src/cairo.h) dnl =========================================================================== # Package version number, (as distinct from shared library version) -CAIRO_VERSION=0.1.8 +CAIRO_VERSION=0.1.9 # libtool shared library version diff --git a/src/cairo-ft-font.c b/src/cairo-ft-font.c index 35d30b1b9..d0dde6cba 100644 --- a/src/cairo-ft-font.c +++ b/src/cairo-ft-font.c @@ -28,9 +28,14 @@ #include typedef struct { - cairo_font_t base; + cairo_font_t base; + + FT_Library ft_library; + int owns_ft_library; + FT_Face face; - int owner_of_face_p; + int owns_face; + FcPattern *pattern; } cairo_ft_font_t; @@ -42,35 +47,18 @@ typedef struct { #define DOUBLE_FROM_16_16(t) (((double)((t) >> 16)) \ + ((double)((t) & 0xFFFF) / 65535.0)) -static FT_Library _cairo_ft_lib = NULL; -static int -_init_cairo_ft_lib (void) -{ - if (_cairo_ft_lib != NULL) - return 1; - - if (FT_Init_FreeType (&_cairo_ft_lib) == 0 - && _cairo_ft_lib != NULL) - return 1; - - return 0; -} - /* implement the platform-specific interface */ cairo_font_t * -cairo_ft_font_create (FcPattern *pattern) +cairo_ft_font_create (FT_Library ft_library, FcPattern *pattern) { cairo_ft_font_t *f = NULL; char *filename = NULL; FT_Face face = NULL; - int own_face = 0; + int owns_face = 0; FcPattern *resolved = NULL; FcResult result = FcResultMatch; - if (!_init_cairo_ft_lib ()) - return NULL; - FcConfigSubstitute (0, pattern, FcMatchPattern); FcDefaultSubstitute (pattern); @@ -89,11 +77,11 @@ cairo_ft_font_create (FcPattern *pattern) /* otherwise it had better have a filename */ int open_res = 0; - own_face = 1; + owns_face = 1; result = FcPatternGetString (resolved, FC_FILE, 0, (FcChar8 **)(&filename)); if (result == FcResultMatch) - open_res = FT_New_Face (_cairo_ft_lib, filename, 0, &face); + open_res = FT_New_Face (ft_library, filename, 0, &face); if (face == NULL) return NULL; @@ -103,7 +91,10 @@ cairo_ft_font_create (FcPattern *pattern) if (f != NULL) f->pattern = FcPatternDuplicate (resolved); - f->owner_of_face_p = own_face; + f->ft_library = ft_library; + f->owns_ft_library = 0; + + f->owns_face = owns_face; FcPatternDestroy (resolved); return (cairo_font_t *) f; @@ -141,6 +132,8 @@ _cairo_ft_font_create (char *family, FcPattern * pat = NULL; int fcslant; int fcweight; + FT_Library ft_library; + FT_Error error; pat = FcPatternCreate (); if (pat == NULL) @@ -175,9 +168,17 @@ _cairo_ft_font_create (char *family, FcPatternAddInteger (pat, FC_SLANT, fcslant); FcPatternAddInteger (pat, FC_WEIGHT, fcweight); - font = cairo_ft_font_create (pat); + error = FT_Init_FreeType (&ft_library); + if (error) { + FcPatternDestroy (pat); + return NULL; + } + + font = cairo_ft_font_create (ft_library, pat); ft_font = (cairo_ft_font_t *) font; + ft_font->owns_ft_library = 1; + FT_Set_Char_Size (ft_font->face, DOUBLE_TO_26_6 (1.0), DOUBLE_TO_26_6 (1.0), @@ -216,12 +217,15 @@ _cairo_ft_font_destroy (cairo_font_t *font) ft_font = (cairo_ft_font_t *)font; - if (ft_font->face != NULL && ft_font->owner_of_face_p) + if (ft_font->face != NULL && ft_font->owns_face) FT_Done_Face (ft_font->face); if (ft_font->pattern != NULL) FcPatternDestroy (ft_font->pattern); + if (ft_font->ft_library && ft_font->owns_ft_library) + FT_Done_FreeType (ft_font->ft_library); + free (ft_font); } @@ -584,8 +588,12 @@ cairo_ft_font_create_for_ft_face (FT_Face face) _cairo_font_init (&f->base, &cairo_ft_font_backend); + f->ft_library = NULL; + f->owns_ft_library = 0; + f->face = face; - f->owner_of_face_p = 0; + f->owns_face = 0; + return (cairo_font_t *) f; } diff --git a/src/cairo.h b/src/cairo.h index 488adcb69..bee0325b2 100644 --- a/src/cairo.h +++ b/src/cairo.h @@ -433,7 +433,7 @@ cairo_font_current_transform (cairo_font_t *font, #include extern cairo_font_t * __external_linkage -cairo_ft_font_create (FcPattern *pattern); +cairo_ft_font_create (FT_Library ft_library, FcPattern *pattern); extern cairo_font_t * __external_linkage cairo_ft_font_create_for_ft_face (FT_Face face); diff --git a/src/cairo_ft_font.c b/src/cairo_ft_font.c index 35d30b1b9..d0dde6cba 100644 --- a/src/cairo_ft_font.c +++ b/src/cairo_ft_font.c @@ -28,9 +28,14 @@ #include typedef struct { - cairo_font_t base; + cairo_font_t base; + + FT_Library ft_library; + int owns_ft_library; + FT_Face face; - int owner_of_face_p; + int owns_face; + FcPattern *pattern; } cairo_ft_font_t; @@ -42,35 +47,18 @@ typedef struct { #define DOUBLE_FROM_16_16(t) (((double)((t) >> 16)) \ + ((double)((t) & 0xFFFF) / 65535.0)) -static FT_Library _cairo_ft_lib = NULL; -static int -_init_cairo_ft_lib (void) -{ - if (_cairo_ft_lib != NULL) - return 1; - - if (FT_Init_FreeType (&_cairo_ft_lib) == 0 - && _cairo_ft_lib != NULL) - return 1; - - return 0; -} - /* implement the platform-specific interface */ cairo_font_t * -cairo_ft_font_create (FcPattern *pattern) +cairo_ft_font_create (FT_Library ft_library, FcPattern *pattern) { cairo_ft_font_t *f = NULL; char *filename = NULL; FT_Face face = NULL; - int own_face = 0; + int owns_face = 0; FcPattern *resolved = NULL; FcResult result = FcResultMatch; - if (!_init_cairo_ft_lib ()) - return NULL; - FcConfigSubstitute (0, pattern, FcMatchPattern); FcDefaultSubstitute (pattern); @@ -89,11 +77,11 @@ cairo_ft_font_create (FcPattern *pattern) /* otherwise it had better have a filename */ int open_res = 0; - own_face = 1; + owns_face = 1; result = FcPatternGetString (resolved, FC_FILE, 0, (FcChar8 **)(&filename)); if (result == FcResultMatch) - open_res = FT_New_Face (_cairo_ft_lib, filename, 0, &face); + open_res = FT_New_Face (ft_library, filename, 0, &face); if (face == NULL) return NULL; @@ -103,7 +91,10 @@ cairo_ft_font_create (FcPattern *pattern) if (f != NULL) f->pattern = FcPatternDuplicate (resolved); - f->owner_of_face_p = own_face; + f->ft_library = ft_library; + f->owns_ft_library = 0; + + f->owns_face = owns_face; FcPatternDestroy (resolved); return (cairo_font_t *) f; @@ -141,6 +132,8 @@ _cairo_ft_font_create (char *family, FcPattern * pat = NULL; int fcslant; int fcweight; + FT_Library ft_library; + FT_Error error; pat = FcPatternCreate (); if (pat == NULL) @@ -175,9 +168,17 @@ _cairo_ft_font_create (char *family, FcPatternAddInteger (pat, FC_SLANT, fcslant); FcPatternAddInteger (pat, FC_WEIGHT, fcweight); - font = cairo_ft_font_create (pat); + error = FT_Init_FreeType (&ft_library); + if (error) { + FcPatternDestroy (pat); + return NULL; + } + + font = cairo_ft_font_create (ft_library, pat); ft_font = (cairo_ft_font_t *) font; + ft_font->owns_ft_library = 1; + FT_Set_Char_Size (ft_font->face, DOUBLE_TO_26_6 (1.0), DOUBLE_TO_26_6 (1.0), @@ -216,12 +217,15 @@ _cairo_ft_font_destroy (cairo_font_t *font) ft_font = (cairo_ft_font_t *)font; - if (ft_font->face != NULL && ft_font->owner_of_face_p) + if (ft_font->face != NULL && ft_font->owns_face) FT_Done_Face (ft_font->face); if (ft_font->pattern != NULL) FcPatternDestroy (ft_font->pattern); + if (ft_font->ft_library && ft_font->owns_ft_library) + FT_Done_FreeType (ft_font->ft_library); + free (ft_font); } @@ -584,8 +588,12 @@ cairo_ft_font_create_for_ft_face (FT_Face face) _cairo_font_init (&f->base, &cairo_ft_font_backend); + f->ft_library = NULL; + f->owns_ft_library = 0; + f->face = face; - f->owner_of_face_p = 0; + f->owns_face = 0; + return (cairo_font_t *) f; }