From: Matthias Kramm Date: Thu, 25 Feb 2010 20:30:19 +0000 (-0800) Subject: fixed a memleak, made pdf device reorder bad unicode X-Git-Tag: version-0-9-1~133 X-Git-Url: http://git.asbjorn.biz/?p=swftools.git;a=commitdiff_plain;h=879464ce804e0c877db5f4b47fdbfee812f99731 fixed a memleak, made pdf device reorder bad unicode --- diff --git a/lib/gfxfont.c b/lib/gfxfont.c index dda20db..d7a8803 100644 --- a/lib/gfxfont.c +++ b/lib/gfxfont.c @@ -21,11 +21,13 @@ along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ +#include #include "../config.h" #include "gfxdevice.h" #include "gfxtools.h" #include "gfxfont.h" #include "ttf.h" +#include "mem.h" static int loadfont_scale = 64; static int full_unicode = 1; @@ -520,6 +522,75 @@ void gfxfont_free(gfxfont_t*font) free(font); } +static inline int invalid_unicode(int u) +{ + return (u<32 || (u>=0xe000 && u<0xf900)); +} +void gfxfont_fix_unicode(gfxfont_t*font) +{ + int t; + + /* find the current maximum unicode2glyph */ + int max = 0; + for(t=0;tnum_glyphs;t++) { + int u = font->glyphs[t].unicode; + if(u > max) + max = u; + } + char*used = rfx_calloc(max+1); + + /* now, remap all duplicates (and invalid characters) and + calculate the new maximum */ + int remap_pos=0; + max = 0; + for(t=0;tnum_glyphs;t++) { + int u = font->glyphs[t].unicode; + if(u>=0) { + if(used[u] || invalid_unicode(u)) { + u = font->glyphs[t].unicode = 0xe000 + remap_pos++; + } else { + used[u] = 1; + } + } + if(u > max) + max = u; + } + free(used); + + if(!font->unicode2glyph) { + /* (re)generate unicode2glyph-to-glyph mapping table by reverse mapping + the glyph unicode2glyph's indexes into the mapping table. For collisions, + we prefer the smaller unicode2glyph value.*/ + font->max_unicode = max+1; + font->unicode2glyph = malloc(sizeof(font->unicode2glyph[0])*(font->max_unicode)); + memset(font->unicode2glyph, -1, sizeof(font->unicode2glyph[0])*(font->max_unicode)); + + for(t=0;tnum_glyphs;t++) { + int u = font->glyphs[t].unicode; + if(u>=0) { + assert(font->unicode2glyph[u]<0); // we took care of duplicates, right? + font->unicode2glyph[u] = t; + } + } + } else { + /* add the new glyph indexes (most probably, that's only the remapped values + at 0xe000) to the unicode2glyph table. Notice: Unlike glyph2unicode, we don't + care about collisions in the unicode2glyph table */ + int new_max_unicode = max+1; + if(font->max_unicode < new_max_unicode) { + font->unicode2glyph = rfx_realloc(font->unicode2glyph, sizeof(font->unicode2glyph[0])*(font->max_unicode)); + memset(font->unicode2glyph+font->max_unicode, -1, sizeof(font->unicode2glyph[0])*(new_max_unicode - font->max_unicode)); + } + for(t=0;tnum_glyphs;t++) { + int u = font->glyphs[t].unicode; + if(u>=0 && font->unicode2glyph[u]<0) { + font->unicode2glyph[u] = t; + } + } + font->max_unicode = new_max_unicode; + } +} + ttf_t* gfxfont_to_ttf(gfxfont_t*font) { ttf_t*ttf = ttf_new(); @@ -595,7 +666,7 @@ ttf_t* gfxfont_to_ttf(gfxfont_t*font) dest->advance = src->advance*scale; int u = font->glyphs[t].unicode; - if(u<32 || (u>=0xe000 && u<0xf900)) { + if(invalid_unicode(u)) { u = 0xe000 + remap_pos++; } if(u > max_unicode) @@ -607,7 +678,7 @@ ttf_t* gfxfont_to_ttf(gfxfont_t*font) for(t=0;tnum_glyphs;t++) { gfxglyph_t*src = &font->glyphs[t]; int u = font->glyphs[t].unicode; - if(u<32 || (u>=0xe000 && u<0xf900)) { + if(invalid_unicode(u)) { u = 0xe000 + remap_pos++; } if(u>=0 && uunicode_size) @@ -617,7 +688,7 @@ ttf_t* gfxfont_to_ttf(gfxfont_t*font) if(font->unicode2glyph) { for(u=0;uunicode_size;u++) { int g = font->unicode2glyph[u]; - if(u<32 || (u>=0xe000 && u<0xf900)) + if(invalid_unicode(u)) continue; if(g>=0 && !ttf->unicode[u]) { ttf->unicode[u] = g+offset; @@ -638,5 +709,6 @@ void gfxfont_save(gfxfont_t*font, const char*filename) { ttf_t*ttf = gfxfont_to_ttf(font); ttf_save(ttf, filename); + ttf_destroy(ttf); } diff --git a/lib/gfxfont.h b/lib/gfxfont.h index 1058db6..f31d71f 100644 --- a/lib/gfxfont.h +++ b/lib/gfxfont.h @@ -34,6 +34,7 @@ extern "C" { still looks good. 1=normal, 0.5=double resolution etc. */ gfxfont_t* gfxfont_load(char*id, char*filename, unsigned int flags, double quality); void gfxfont_save(gfxfont_t*font, const char*filename); +void gfxfont_fix_unicode(gfxfont_t*font); void gfxfont_free(gfxfont_t*font); #ifdef __cplusplus diff --git a/lib/pdf/InfoOutputDev.cc b/lib/pdf/InfoOutputDev.cc index 7d7db0b..08a9cc3 100644 --- a/lib/pdf/InfoOutputDev.cc +++ b/lib/pdf/InfoOutputDev.cc @@ -17,6 +17,7 @@ #include "../log.h" #include "../types.h" #include "../q.h" +#include "../gfxfont.h" #include #include @@ -219,14 +220,8 @@ static gfxfont_t* createGfxFont(FontInfo*src) font->num_glyphs++; } } - font->unicode2glyph = (int*)malloc(sizeof(int)*font->max_unicode); - memset(font->unicode2glyph, -1, sizeof(int)*font->max_unicode); - for(t=0;tnum_glyphs;t++) { - if(font->glyphs[t].unicode>0 && font->glyphs[t].unicodemax_unicode) { - font->unicode2glyph[font->glyphs[t].unicode] = t; - } - } + gfxfont_fix_unicode(font); int kerning_size = 0; for(t=0;tnum_glyphs;t++) { diff --git a/lib/ttf.h b/lib/ttf.h index d37f745..21460c1 100644 --- a/lib/ttf.h +++ b/lib/ttf.h @@ -179,6 +179,7 @@ ttf_t*ttf_load(void*data, int length); ttf_table_t*ttf_addtable(ttf_t*ttf, U32 tag); void ttf_create_truetype_tables(ttf_t*ttf); void ttf_dump(ttf_t*ttf); +void ttf_destroy(ttf_t*ttf); void ttf_save(ttf_t*ttf, const char*filename); #endif