diff options
Diffstat (limited to 'Build/source/texk/web2c/luatexdir/font')
27 files changed, 12738 insertions, 11302 deletions
diff --git a/Build/source/texk/web2c/luatexdir/font/dofont.c b/Build/source/texk/web2c/luatexdir/font/dofont.c index fbe44c29ba9..14d785b8a9f 100644 --- a/Build/source/texk/web2c/luatexdir/font/dofont.c +++ b/Build/source/texk/web2c/luatexdir/font/dofont.c @@ -1,183 +1,186 @@ -/* -Copyright (c) 1996-2006 Taco Hoekwater <taco@luatex.org> +/* dofont.c + + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -This file is part of LuaTeX. + This file is part of LuaTeX. -LuaTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -LuaTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -You should have received a copy of the GNU General Public License -along with LuaTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -$Id: dofont.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" #include "luatex-api.h" +static const char _svn_version[] = + "$Id: dofont.c 2086 2009-03-22 15:32:08Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/dofont.c $"; + #define TIMERS 0 #if TIMERS -#include <sys/time.h> +# include <sys/time.h> #endif /* a bit more interfacing is needed for proper error reporting */ -static char * -font_error_message (pointer u, char *nom, scaled s) { - char *str = xmalloc(256); - char *c = makecstring(zget_cs_text(u)); - char *extra = "metric data not found or bad"; - if (s>=0 ) { - snprintf(str,255,"Font \\%s=%s at %gpt not loadable: %s", c, nom, (double)s/65536, extra); - } else if (s!=-1000) { - snprintf(str,255,"Font \\%s=%s scaled %d not loadable: %s", c, nom, (int)(-s), extra); - } else { - snprintf(str,255,"Font \\%s=%s not loadable: %s", c, nom, extra); - } - return str; +static char *font_error_message(pointer u, char *nom, scaled s) +{ + char *str = xmalloc(256); + char *c = makecstring(zget_cs_text(u)); + char *extra = "metric data not found or bad"; + if (s >= 0) { + snprintf(str, 255, "Font \\%s=%s at %gpt not loadable: %s", c, nom, + (double) s / 65536, extra); + } else if (s != -1000) { + snprintf(str, 255, "Font \\%s=%s scaled %d not loadable: %s", c, nom, + (int) (-s), extra); + } else { + snprintf(str, 255, "Font \\%s=%s not loadable: %s", c, nom, extra); + } + return str; } static int -do_define_font (integer f, char *cnom, char *caire, scaled s, integer natural_dir) { +do_define_font(integer f, char *cnom, char *caire, scaled s, + integer natural_dir) +{ - boolean res; /* was the callback successful? */ - integer callback_id; - char *cnam; + boolean res; /* was the callback successful? */ + integer callback_id; + char *cnam; #if TIMERS struct timeval tva; struct timeval tvb; double tvdiff; #endif - int r; - res = 0; - - callback_id=callback_defined(define_font_callback); - if (callback_id>0) { - if (caire == NULL || strlen(caire)==0) { - cnam = xstrdup(cnom); - } else { - cnam = xmalloc(strlen(cnom)+strlen(caire)+2); - sprintf(cnam,"%s/%s",caire,cnom); - } + int r; + res = 0; + + callback_id = callback_defined(define_font_callback); + if (callback_id > 0) { + if (caire == NULL || strlen(caire) == 0) { + cnam = xstrdup(cnom); + } else { + cnam = xmalloc(strlen(cnom) + strlen(caire) + 2); + sprintf(cnam, "%s/%s", caire, cnom); + } #if TIMERS - gettimeofday(&tva,NULL); + gettimeofday(&tva, NULL); #endif - callback_id = run_and_save_callback(callback_id,"Sdd->",cnam,s,f); + callback_id = run_and_save_callback(callback_id, "Sdd->", cnam, s, f); #if TIMERS - gettimeofday(&tvb,NULL); - tvdiff = tvb.tv_sec*1000000.0; - tvdiff += (double)tvb.tv_usec; - tvdiff -= (tva.tv_sec*1000000.0); - tvdiff -= (double)tva.tv_usec; - tvdiff /= 1000000; - fprintf(stdout,"\ncallback('define_font',%s,%i): %f seconds\n", cnam,f,tvdiff); + gettimeofday(&tvb, NULL); + tvdiff = tvb.tv_sec * 1000000.0; + tvdiff += (double) tvb.tv_usec; + tvdiff -= (tva.tv_sec * 1000000.0); + tvdiff -= (double) tva.tv_usec; + tvdiff /= 1000000; + fprintf(stdout, "\ncallback('define_font',%s,%i): %f seconds\n", cnam, + f, tvdiff); #endif - free(cnam); - if (callback_id>0) { /* success */ - luaL_checkstack(Luas[0],1,"out of stack space"); - lua_rawgeti(Luas[0],LUA_REGISTRYINDEX, callback_id); - if (lua_istable(Luas[0],-1)) { + free(cnam); + if (callback_id > 0) { /* success */ + luaL_checkstack(Luas, 1, "out of stack space"); + lua_rawgeti(Luas, LUA_REGISTRYINDEX, callback_id); + if (lua_istable(Luas, -1)) { #if TIMERS - gettimeofday(&tva,NULL); + gettimeofday(&tva, NULL); #endif - res = font_from_lua(Luas[0],f); - destroy_saved_callback (callback_id); + res = font_from_lua(Luas, f); + destroy_saved_callback(callback_id); #if TIMERS - gettimeofday(&tvb,NULL); - tvdiff = tvb.tv_sec*1000000.0; - tvdiff += (double)tvb.tv_usec; - tvdiff -= (tva.tv_sec*1000000.0); - tvdiff -= (double)tva.tv_usec; - tvdiff /= 1000000; - fprintf(stdout,"font_from_lua(%s,%i): %f seconds\n", font_name(f),f,tvdiff); + gettimeofday(&tvb, NULL); + tvdiff = tvb.tv_sec * 1000000.0; + tvdiff += (double) tvb.tv_usec; + tvdiff -= (tva.tv_sec * 1000000.0); + tvdiff -= (double) tva.tv_usec; + tvdiff /= 1000000; + fprintf(stdout, "font_from_lua(%s,%i): %f seconds\n", + font_name(f), f, tvdiff); #endif - lua_pop(Luas[0],1); - } else if (lua_isnumber(Luas[0],-1)) { - r = lua_tonumber(Luas[0],-1); - destroy_saved_callback (callback_id); - delete_font(f); - lua_pop(Luas[0],1); - return r; - } else { - lua_pop(Luas[0],1); - delete_font(f); - return 0; - } + /* lua_pop(Luas, 1); *//* done by font_from_lua */ + } else if (lua_isnumber(Luas, -1)) { + r = lua_tonumber(Luas, -1); + destroy_saved_callback(callback_id); + delete_font(f); + lua_pop(Luas, 1); + return r; + } else { + lua_pop(Luas, 1); + delete_font(f); + return 0; + } + } + } else { + res = read_tfm_info(f, cnom, caire, s); + if (res) { + set_hyphen_char(f, get_default_hyphen_char()); + set_skew_char(f, get_default_skew_char()); + } } - } else { - res = read_tfm_info(f,cnom,caire,s); if (res) { - set_hyphen_char(f,get_default_hyphen_char()); - set_skew_char(f,get_default_skew_char()); + if (font_type(f) != virtual_font_type) { /* implies lua */ + do_vf(f); + set_font_natural_dir(f, natural_dir); + } + return f; + } else { + delete_font(f); + return 0; } - } - if (res) { - do_vf(f); - set_font_natural_dir(f,natural_dir); - return f; - } else { - delete_font(f); - return 0; - } } -int -read_font_info(pointer u, strnumber nom, strnumber aire, scaled s, - integer natural_dir) { - integer f; - char *cnom, *caire = NULL; - char *msg; - cnom = xstrdup(makecstring(nom)); - if (aire != 0) - caire = xstrdup(makecstring(aire)); - - f = new_font(); - if ((f = do_define_font(f, cnom,caire,s,natural_dir))) { - if (caire != NULL) free(caire); - free(cnom); - return f; - } else { - char *help[] = {"I wasn't able to read the size data for this font,", - "so I will ignore the font specification.", - "[Wizards can fix TFM files using TFtoPL/PLtoTF.]", - "You might try inserting a different font spec;", - "e.g., type `I\font<same font id>=<substitute font name>'.", - NULL } ; - if(!get_suppress_fontnotfound_error()) { - msg = font_error_message(u, cnom, s); - tex_error(msg,help); - free(msg); - } - if (caire != NULL) free(caire); - free(cnom); - return 0; - } +int read_font_info(pointer u, strnumber nom, scaled s, integer natural_dir) +{ + integer f; + char *cnom; + char *msg; + cnom = xstrdup(makecstring(nom)); + + f = new_font(); + if ((f = do_define_font(f, cnom, NULL, s, natural_dir))) { + free(cnom); + return f; + } else { + char *help[] = { "I wasn't able to read the size data for this font,", + "so I will ignore the font specification.", + "[Wizards can fix TFM files using TFtoPL/PLtoTF.]", + "You might try inserting a different font spec;", + "e.g., type `I\font<same font id>=<substitute font name>'.", + NULL + }; + if (!get_suppress_fontnotfound_error()) { + msg = font_error_message(u, cnom, s); + tex_error(msg, help); + free(msg); + } + free(cnom); + return 0; + } } /* TODO This function is a placeholder. There can easily appears holes in the |font_tables| array, and we could attempt to reuse those */ -int -find_font_id (char *nom, char *aire, scaled s) { - integer f; - f = new_font(); - if ((f = do_define_font(f, nom, aire,s,-1))) { - return f; - } else { - return 0; - } +int find_font_id(char *nom, char *aire, scaled s) +{ + integer f; + f = new_font(); + if ((f = do_define_font(f, nom, aire, s, -1))) { + return f; + } else { + return 0; + } } - diff --git a/Build/source/texk/web2c/luatexdir/font/luafont.c b/Build/source/texk/web2c/luatexdir/font/luafont.c index 4a2eda1f41c..d9fd6273b06 100644 --- a/Build/source/texk/web2c/luatexdir/font/luafont.c +++ b/Build/source/texk/web2c/luatexdir/font/luafont.c @@ -1,316 +1,477 @@ +/* luafont.c + + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> + + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "luatex-api.h" #include <ptexlib.h> #include "nodes.h" +static const char _svn_version[] = + "$Id: luafont.c 2086 2009-03-22 15:32:08Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/luafont.c $"; + #define noVERBOSE #define SAVE_REF 1 -char *font_type_strings[] = {"unknown","virtual","real", NULL}; -char *font_format_strings[] = {"unknown","type1","type3","truetype", "opentype", NULL}; -char *font_embedding_strings[] = {"unknown","no","subset", "full", NULL}; -char *ligature_type_strings[] = {"=:", "=:|", "|=:", "|=:|", "", "=:|>", "|=:>", "|=:|>", "", "", "", "|=:|>>", NULL }; +char *font_type_strings[] = { "unknown", "virtual", "real", NULL }; +char *font_format_strings[] = + { "unknown", "type1", "type3", "truetype", "opentype", NULL }; +char *font_embedding_strings[] = { "unknown", "no", "subset", "full", NULL }; +char *ligature_type_strings[] = + { "=:", "=:|", "|=:", "|=:|", "", "=:|>", "|=:>", "|=:|>", "", "", "", + "|=:|>>", NULL +}; + +const char *MATH_param_names[] = { + "nil", + "ScriptPercentScaleDown", + "ScriptScriptPercentScaleDown", + "DelimitedSubFormulaMinHeight", + "DisplayOperatorMinHeight", + "MathLeading", + "AxisHeight", + "AccentBaseHeight", + "FlattenedAccentBaseHeight", + "SubscriptShiftDown", + "SubscriptTopMax", + "SubscriptBaselineDropMin", + "SuperscriptShiftUp", + "SuperscriptShiftUpCramped", + "SuperscriptBottomMin", + "SuperscriptBaselineDropMax", + "SubSuperscriptGapMin", + "SuperscriptBottomMaxWithSubscript", + "SpaceAfterScript", + "UpperLimitGapMin", + "UpperLimitBaselineRiseMin", + "LowerLimitGapMin", + "LowerLimitBaselineDropMin", + "StackTopShiftUp", + "StackTopDisplayStyleShiftUp", + "StackBottomShiftDown", + "StackBottomDisplayStyleShiftDown", + "StackGapMin", + "StackDisplayStyleGapMin", + "StretchStackTopShiftUp", + "StretchStackBottomShiftDown", + "StretchStackGapAboveMin", + "StretchStackGapBelowMin", + "FractionNumeratorShiftUp", + "FractionNumeratorDisplayStyleShiftUp", + "FractionDenominatorShiftDown", + "FractionDenominatorDisplayStyleShiftDown", + "FractionNumeratorGapMin", + "FractionNumeratorDisplayStyleGapMin", + "FractionRuleThickness", + "FractionDenominatorGapMin", + "FractionDenominatorDisplayStyleGapMin", + "SkewedFractionHorizontalGap", + "SkewedFractionVerticalGap", + "OverbarVerticalGap", + "OverbarRuleThickness", + "OverbarExtraAscender", + "UnderbarVerticalGap", + "UnderbarRuleThickness", + "UnderbarExtraDescender", + "RadicalVerticalGap", + "RadicalDisplayStyleVerticalGap", + "RadicalRuleThickness", + "RadicalExtraAscender", + "RadicalKernBeforeDegree", + "RadicalKernAfterDegree", + "RadicalDegreeBottomRaisePercent", + "MinConnectorOverlap", + NULL, +}; + +static void dump_intfield(lua_State * L, char *n, int c) +{ + lua_pushstring(L, n); + lua_pushnumber(L, c); + lua_rawset(L, -3); +} -void -font_char_to_lua (lua_State *L, internalfontnumber f, charinfo *co) { - int i; - liginfo *l; - kerninfo *ki; - - lua_createtable(L,0,10); - - lua_pushstring(L,"width"); - lua_pushnumber(L,get_charinfo_width(co)); - lua_rawset(L,-3); - - lua_pushstring(L,"height"); - lua_pushnumber(L,get_charinfo_height(co)); - lua_rawset(L,-3); - - lua_pushstring(L,"depth"); - lua_pushnumber(L,get_charinfo_depth(co)); - lua_rawset(L,-3); - - lua_pushstring(L,"italic"); - lua_pushnumber(L,get_charinfo_italic(co)); - lua_rawset(L,-3); - - if (get_charinfo_ef(co)!=0) { - lua_pushstring(L,"expansion_factor"); - lua_pushnumber(L,get_charinfo_ef(co)); - lua_rawset(L,-3); - } - - if (get_charinfo_lp(co)!=0) { - lua_pushstring(L,"left_protruding"); - lua_pushnumber(L,get_charinfo_lp(co)); - lua_rawset(L,-3); - } - - if (get_charinfo_lp(co)!=0) { - lua_pushstring(L,"right_protruding"); - lua_pushnumber(L,get_charinfo_rp(co)); - lua_rawset(L,-3); - } - - - if (font_encodingbytes(f) == 2 ) { - lua_pushstring(L,"index"); - lua_pushnumber(L,get_charinfo_index(co)); - lua_rawset(L,-3); - } - - if (get_charinfo_name(co)!=NULL) { - lua_pushstring(L,"name"); - lua_pushstring(L,get_charinfo_name(co)); - lua_rawset(L,-3); - } - - if (get_charinfo_tounicode(co)!=NULL) { - lua_pushstring(L,"tounicode"); - lua_pushstring(L,get_charinfo_tounicode(co)); - lua_rawset(L,-3); - } - - if (get_charinfo_tag(co) == list_tag) { - lua_pushstring(L,"next"); - lua_pushnumber(L,get_charinfo_remainder(co)); - lua_rawset(L,-3); - } - - lua_pushstring(L,"used"); - lua_pushboolean(L,(get_charinfo_used(co) ? true : false)); - lua_rawset(L,-3); - - if (get_charinfo_tag(co) == ext_tag) { - lua_pushstring(L,"extensible"); - lua_createtable(L,0,4); - lua_pushnumber(L,get_charinfo_extensible(co,EXT_TOP)); - lua_setfield(L,-2,"top"); - lua_pushnumber(L,get_charinfo_extensible(co,EXT_BOT)); - lua_setfield(L,-2,"bot"); - lua_pushnumber(L,get_charinfo_extensible(co,EXT_MID)); - lua_setfield(L,-2,"mid"); - lua_pushnumber(L,get_charinfo_extensible(co,EXT_REP)); - lua_setfield(L,-2,"rep"); - lua_rawset(L,-3); - } - ki = get_charinfo_kerns(co); - if (ki != NULL) { - lua_pushstring(L,"kerns"); - lua_createtable(L,10,1); - for (i=0;!kern_end(ki[i]);i++) { - if (kern_char(ki[i]) == right_boundarychar) { - lua_pushstring(L,"right_boundary"); - } else { - lua_pushnumber(L,kern_char(ki[i])); - } - lua_pushnumber(L,kern_kern(ki[i])); - lua_rawset(L,-3); - } - lua_rawset(L,-3); - } - l = get_charinfo_ligatures(co); - if (l!=NULL) { - lua_pushstring(L,"ligatures"); - lua_createtable(L,10,1); - for (i=0;!lig_end(l[i]);i++) { - if (lig_char(l[i]) == right_boundarychar) { - lua_pushstring(L,"right_boundary"); - } else { - lua_pushnumber(L,lig_char(l[i])); - } - lua_createtable(L,0,2); - lua_pushstring(L,"type"); - lua_pushnumber(L,lig_type(l[i])); - lua_rawset(L,-3); - lua_pushstring(L,"char"); - lua_pushnumber(L,lig_replacement(l[i])); - lua_rawset(L,-3); - lua_rawset(L,-3); - } - lua_rawset(L,-3); - } + + +void font_char_to_lua(lua_State * L, internalfontnumber f, charinfo * co) +{ + int i; + liginfo *l; + kerninfo *ki; + + lua_createtable(L, 0, 10); + + lua_pushstring(L, "width"); + lua_pushnumber(L, get_charinfo_width(co)); + lua_rawset(L, -3); + + lua_pushstring(L, "height"); + lua_pushnumber(L, get_charinfo_height(co)); + lua_rawset(L, -3); + + lua_pushstring(L, "depth"); + lua_pushnumber(L, get_charinfo_depth(co)); + lua_rawset(L, -3); + + lua_pushstring(L, "italic"); + lua_pushnumber(L, get_charinfo_italic(co)); + lua_rawset(L, -3); + + lua_pushstring(L, "top_accent"); + lua_pushnumber(L, get_charinfo_top_accent(co)); + lua_rawset(L, -3); + + lua_pushstring(L, "bot_accent"); + lua_pushnumber(L, get_charinfo_bot_accent(co)); + lua_rawset(L, -3); + + + if (get_charinfo_ef(co) != 0) { + lua_pushstring(L, "expansion_factor"); + lua_pushnumber(L, get_charinfo_ef(co)); + lua_rawset(L, -3); + } + + if (get_charinfo_lp(co) != 0) { + lua_pushstring(L, "left_protruding"); + lua_pushnumber(L, get_charinfo_lp(co)); + lua_rawset(L, -3); + } + + if (get_charinfo_lp(co) != 0) { + lua_pushstring(L, "right_protruding"); + lua_pushnumber(L, get_charinfo_rp(co)); + lua_rawset(L, -3); + } + + + if (font_encodingbytes(f) == 2) { + lua_pushstring(L, "index"); + lua_pushnumber(L, get_charinfo_index(co)); + lua_rawset(L, -3); + } + + if (get_charinfo_name(co) != NULL) { + lua_pushstring(L, "name"); + lua_pushstring(L, get_charinfo_name(co)); + lua_rawset(L, -3); + } + + if (get_charinfo_tounicode(co) != NULL) { + lua_pushstring(L, "tounicode"); + lua_pushstring(L, get_charinfo_tounicode(co)); + lua_rawset(L, -3); + } + + if (get_charinfo_tag(co) == list_tag) { + lua_pushstring(L, "next"); + lua_pushnumber(L, get_charinfo_remainder(co)); + lua_rawset(L, -3); + } + + lua_pushstring(L, "used"); + lua_pushboolean(L, (get_charinfo_used(co) ? true : false)); + lua_rawset(L, -3); + + if (get_charinfo_tag(co) == ext_tag) { + extinfo *h; + h = get_charinfo_hor_variants(co); + if (h != NULL) { + int i = 1; + lua_newtable(L); + while (h != NULL) { + lua_createtable(L, 0, 5); + dump_intfield(L, "glyph", h->glyph); + dump_intfield(L, "extender", h->extender); + dump_intfield(L, "start", h->start_overlap); + dump_intfield(L, "end", h->end_overlap); + dump_intfield(L, "advance", h->advance); + lua_rawseti(L, -2, i); + i++; + h = h->next; + } + lua_setfield(L, -2, "horiz_variants"); + } + h = get_charinfo_vert_variants(co); + if (h != NULL) { + int i = 1; + lua_newtable(L); + while (h != NULL) { + lua_createtable(L, 0, 5); + dump_intfield(L, "glyph", h->glyph); + dump_intfield(L, "extender", h->extender); + dump_intfield(L, "start", h->start_overlap); + dump_intfield(L, "end", h->end_overlap); + dump_intfield(L, "advance", h->advance); + lua_rawseti(L, -2, i); + i++; + h = h->next; + } + lua_setfield(L, -2, "vert_variants"); + } + } + ki = get_charinfo_kerns(co); + if (ki != NULL) { + lua_pushstring(L, "kerns"); + lua_createtable(L, 10, 1); + for (i = 0; !kern_end(ki[i]); i++) { + if (kern_char(ki[i]) == right_boundarychar) { + lua_pushstring(L, "right_boundary"); + } else { + lua_pushnumber(L, kern_char(ki[i])); + } + lua_pushnumber(L, kern_kern(ki[i])); + lua_rawset(L, -3); + } + lua_rawset(L, -3); + } + l = get_charinfo_ligatures(co); + if (l != NULL) { + lua_pushstring(L, "ligatures"); + lua_createtable(L, 10, 1); + for (i = 0; !lig_end(l[i]); i++) { + if (lig_char(l[i]) == right_boundarychar) { + lua_pushstring(L, "right_boundary"); + } else { + lua_pushnumber(L, lig_char(l[i])); + } + lua_createtable(L, 0, 2); + lua_pushstring(L, "type"); + lua_pushnumber(L, lig_type(l[i])); + lua_rawset(L, -3); + lua_pushstring(L, "char"); + lua_pushnumber(L, lig_replacement(l[i])); + lua_rawset(L, -3); + lua_rawset(L, -3); + } + lua_rawset(L, -3); + } } -static void -write_lua_parameters (lua_State *L, int f) { - int k; - lua_newtable(L); - for (k=1;k<=font_params(f);k++) { - lua_pushnumber(L,font_param(f,k)); - switch (k) { - case slant_code: lua_setfield(L,-2,"slant"); break; - case space_code: lua_setfield(L,-2,"space"); break; - case space_stretch_code: lua_setfield(L,-2,"space_stretch"); break; - case space_shrink_code: lua_setfield(L,-2,"space_shrink"); break; - case x_height_code: lua_setfield(L,-2,"x_height"); break; - case quad_code: lua_setfield(L,-2,"quad"); break; - case extra_space_code: lua_setfield(L,-2,"extra_space"); break; - default: - lua_rawseti(L,-2,k); - } - } - lua_setfield(L,-2,"parameters"); +static void write_lua_parameters(lua_State * L, int f) +{ + int k; + lua_newtable(L); + for (k = 1; k <= font_params(f); k++) { + lua_pushnumber(L, font_param(f, k)); + switch (k) { + case slant_code: + lua_setfield(L, -2, "slant"); + break; + case space_code: + lua_setfield(L, -2, "space"); + break; + case space_stretch_code: + lua_setfield(L, -2, "space_stretch"); + break; + case space_shrink_code: + lua_setfield(L, -2, "space_shrink"); + break; + case x_height_code: + lua_setfield(L, -2, "x_height"); + break; + case quad_code: + lua_setfield(L, -2, "quad"); + break; + case extra_space_code: + lua_setfield(L, -2, "extra_space"); + break; + default: + lua_rawseti(L, -2, k); + } + } + lua_setfield(L, -2, "parameters"); } -int -font_to_lua (lua_State *L, int f) { - int k; - charinfo *co; - if (font_cache_id(f)) { - /* fetch the table from the registry if it was - saved there by font_from_lua() */ - lua_rawgeti(L,LUA_REGISTRYINDEX,font_cache_id(f)); - /* fontdimens can be changed from tex code */ - write_lua_parameters(L,f); +static void write_lua_math_parameters(lua_State * L, int f) +{ + int k; + lua_newtable(L); + for (k = 1; k < font_math_params(f); k++) { + lua_pushnumber(L, font_math_param(f, k)); + if (k <= MATH_param_max) { + lua_setfield(L, -2, MATH_param_names[k]); + } else { + lua_rawseti(L, -2, k); + } + } + lua_setfield(L, -2, "MathConstants"); +} + + + +int font_to_lua(lua_State * L, int f) +{ + int k; + charinfo *co; + if (font_cache_id(f)) { + /* fetch the table from the registry if it was + saved there by font_from_lua() */ + lua_rawgeti(L, LUA_REGISTRYINDEX, font_cache_id(f)); + /* fontdimens can be changed from tex code */ + write_lua_parameters(L, f); + return 1; + } + + lua_newtable(L); + lua_pushstring(L, font_name(f)); + lua_setfield(L, -2, "name"); + if (font_area(f) != NULL) { + lua_pushstring(L, font_area(f)); + lua_setfield(L, -2, "area"); + } + if (font_filename(f) != NULL) { + lua_pushstring(L, font_filename(f)); + lua_setfield(L, -2, "filename"); + } + if (font_fullname(f) != NULL) { + lua_pushstring(L, font_fullname(f)); + lua_setfield(L, -2, "fullname"); + } + if (font_encodingname(f) != NULL) { + lua_pushstring(L, font_encodingname(f)); + lua_setfield(L, -2, "encodingname"); + } + + lua_pushboolean(L, (font_used(f) ? true : false)); + lua_setfield(L, -2, "used"); + + + lua_pushstring(L, font_type_strings[font_type(f)]); + lua_setfield(L, -2, "type"); + lua_pushstring(L, font_format_strings[font_format(f)]); + lua_setfield(L, -2, "format"); + lua_pushstring(L, font_embedding_strings[font_embedding(f)]); + lua_setfield(L, -2, "embedding"); + + lua_pushnumber(L, font_size(f)); + lua_setfield(L, -2, "size"); + lua_pushnumber(L, font_dsize(f)); + lua_setfield(L, -2, "designsize"); + lua_pushnumber(L, font_checksum(f)); + lua_setfield(L, -2, "checksum"); + lua_pushnumber(L, font_slant(f)); + lua_setfield(L, -2, "slant"); + lua_pushnumber(L, font_extend(f)); + lua_setfield(L, -2, "extend"); + lua_pushnumber(L, font_natural_dir(f)); + lua_setfield(L, -2, "direction"); + lua_pushnumber(L, font_encodingbytes(f)); + lua_setfield(L, -2, "encodingbytes"); + lua_pushnumber(L, font_tounicode(f)); + lua_setfield(L, -2, "tounicode"); + + /* pdf parameters */ + /* skip the first four for now, that are very much interal */ + /* + if (pdf_font_size(f) != 0) { + lua_pushnumber(L,pdf_font_size(f)); + lua_setfield(L,-2,"pdf_size"); + } + if (pdf_font_num(f) != 0) { + lua_pushnumber(L,pdf_font_num(f)); + lua_setfield(L,-2,"pdf_num"); + } + if (pdf_font_blink(f) != 0) { + lua_pushnumber(L,pdf_font_blink(f)); + lua_setfield(L,-2,"pdf_blink"); + } + if (pdf_font_elink(f) != 0) { + lua_pushnumber(L,pdf_font_elink(f)); + lua_setfield(L,-2,"pdf_elink"); + } + */ + /* the next one is read only */ + if (pdf_font_expand_ratio(f) != 0) { + lua_pushnumber(L, pdf_font_expand_ratio(f)); + lua_setfield(L, -2, "expand_ratio"); + } + if (pdf_font_shrink(f) != 0) { + lua_pushnumber(L, pdf_font_shrink(f)); + lua_setfield(L, -2, "shrink"); + } + if (pdf_font_stretch(f) != 0) { + lua_pushnumber(L, pdf_font_stretch(f)); + lua_setfield(L, -2, "stretch"); + } + if (pdf_font_step(f) != 0) { + lua_pushnumber(L, pdf_font_step(f)); + lua_setfield(L, -2, "step"); + } + if (pdf_font_auto_expand(f) != 0) { + lua_pushboolean(L, pdf_font_auto_expand(f)); + lua_setfield(L, -2, "auto_expand"); + } + if (pdf_font_attr(f) != 0) { + lua_pushstring(L, makecstring(pdf_font_attr(f))); + lua_setfield(L, -2, "attributes"); + } + + /* params */ + write_lua_parameters(L, f); + write_lua_math_parameters(L, f); + + /* chars */ + lua_createtable(L, font_tables[f]->charinfo_size, 0); /* all characters */ + + if (has_left_boundary(f)) { + co = get_charinfo(f, left_boundarychar); + font_char_to_lua(L, f, co); + lua_setfield(L, -2, "left_boundary"); + } + if (has_right_boundary(f)) { + co = get_charinfo(f, right_boundarychar); + font_char_to_lua(L, f, co); + lua_setfield(L, -2, "right_boundary"); + } + + for (k = font_bc(f); k <= font_ec(f); k++) { + if (char_exists(f, k)) { + lua_pushnumber(L, k); + co = get_charinfo(f, k); + font_char_to_lua(L, f, co); + lua_rawset(L, -3); + } + } + lua_setfield(L, -2, "characters"); return 1; - } - - lua_newtable(L); - lua_pushstring(L,font_name(f)); - lua_setfield(L,-2,"name"); - if(font_area(f)!=NULL) { - lua_pushstring(L,font_area(f)); - lua_setfield(L,-2,"area"); - } - if(font_filename(f)!=NULL) { - lua_pushstring(L,font_filename(f)); - lua_setfield(L,-2,"filename"); - } - if(font_fullname(f)!=NULL) { - lua_pushstring(L,font_fullname(f)); - lua_setfield(L,-2,"fullname"); - } - if(font_encodingname(f)!=NULL) { - lua_pushstring(L,font_encodingname(f)); - lua_setfield(L,-2,"encodingname"); - } - - lua_pushboolean(L,(font_used(f) ? true : false)); - lua_setfield(L,-2,"used"); - - - lua_pushstring(L,font_type_strings[font_type(f)]); - lua_setfield(L,-2,"type"); - lua_pushstring(L,font_format_strings[font_format(f)]); - lua_setfield(L,-2,"format"); - lua_pushstring(L,font_embedding_strings[font_embedding(f)]); - lua_setfield(L,-2,"embedding"); - - lua_pushnumber(L,font_size(f)); - lua_setfield(L,-2,"size"); - lua_pushnumber(L,font_dsize(f)); - lua_setfield(L,-2,"designsize"); - lua_pushnumber(L,font_checksum(f)); - lua_setfield(L,-2,"checksum"); - lua_pushnumber(L,font_slant(f)); - lua_setfield(L,-2,"slant"); - lua_pushnumber(L,font_extend(f)); - lua_setfield(L,-2,"extend"); - lua_pushnumber(L,font_natural_dir(f)); - lua_setfield(L,-2,"direction"); - lua_pushnumber(L,font_encodingbytes(f)); - lua_setfield(L,-2,"encodingbytes"); - lua_pushnumber(L,font_tounicode(f)); - lua_setfield(L,-2,"tounicode"); - - /* pdf parameters */ - /* skip the first four for now, that are very much interal */ - /* - if (pdf_font_size(f) != 0) { - lua_pushnumber(L,pdf_font_size(f)); - lua_setfield(L,-2,"pdf_size"); - } - if (pdf_font_num(f) != 0) { - lua_pushnumber(L,pdf_font_num(f)); - lua_setfield(L,-2,"pdf_num"); - } - if (pdf_font_blink(f) != 0) { - lua_pushnumber(L,pdf_font_blink(f)); - lua_setfield(L,-2,"pdf_blink"); - } - if (pdf_font_elink(f) != 0) { - lua_pushnumber(L,pdf_font_elink(f)); - lua_setfield(L,-2,"pdf_elink"); - } - */ - /* the next one is read only */ - if (pdf_font_expand_ratio(f) != 0) { - lua_pushnumber(L,pdf_font_expand_ratio(f)); - lua_setfield(L,-2,"expand_ratio"); - } - if (pdf_font_shrink(f) != 0) { - lua_pushnumber(L,pdf_font_shrink(f)); - lua_setfield(L,-2,"shrink"); - } - if (pdf_font_stretch(f) != 0) { - lua_pushnumber(L,pdf_font_stretch(f)); - lua_setfield(L,-2,"stretch"); - } - if (pdf_font_step(f) != 0) { - lua_pushnumber(L,pdf_font_step(f)); - lua_setfield(L,-2,"step"); - } - if (pdf_font_auto_expand(f) != 0) { - lua_pushboolean(L,pdf_font_auto_expand(f)); - lua_setfield(L,-2,"auto_expand"); - } - if (pdf_font_attr(f) != 0) { - lua_pushstring(L,makecstring(pdf_font_attr(f))); - lua_setfield(L,-2,"attributes"); - } - - /* params */ - write_lua_parameters(L,f); - - /* chars */ - lua_createtable(L,font_tables[f]->charinfo_size,0); /* all characters */ - - if (has_left_boundary(f)) { - co = get_charinfo(f,left_boundarychar); - font_char_to_lua(L,f,co); - lua_setfield(L,-2,"left_boundary"); - } - if (has_right_boundary(f)) { - co = get_charinfo(f,right_boundarychar); - font_char_to_lua(L,f,co); - lua_setfield(L,-2,"right_boundary"); - } - - for (k=font_bc(f);k<=font_ec(f);k++) { - if (char_exists(f,k)) { - lua_pushnumber(L,k); - co = get_charinfo(f,k); - font_char_to_lua(L,f,co); - lua_rawset(L,-3); - } - } - lua_setfield(L,-2,"characters"); - return 1; } -static int -count_hash_items (lua_State *L, int name_index){ - int n = -1; - lua_rawgeti(L,LUA_REGISTRYINDEX,name_index); - lua_rawget(L,-2); - if (!lua_isnil(L,-1)) { - if (lua_istable(L,-1)) { - n = 0; - /* now find the number */ - lua_pushnil(L); /* first key */ - while (lua_next(L, -2) != 0) { - n++; - lua_pop(L,1); - } - } - } - lua_pop(L,1); - return n; +static int count_hash_items(lua_State * L, int name_index) +{ + int n = -1; + lua_rawgeti(L, LUA_REGISTRYINDEX, name_index); + lua_rawget(L, -2); + if (!lua_isnil(L, -1)) { + if (lua_istable(L, -1)) { + n = 0; + /* now find the number */ + lua_pushnil(L); /* first key */ + while (lua_next(L, -2) != 0) { + n++; + lua_pop(L, 1); + } + } + } + lua_pop(L, 1); + return n; } #define streq(a,b) (strcmp(a,b)==0) @@ -321,130 +482,130 @@ count_hash_items (lua_State *L, int name_index){ append_packet((l&0xFF000000)>>24); \ append_packet((l&0x00FF0000)>>16); \ append_packet((l&0x0000FF00)>>8); \ - append_packet((l&0x000000FF)); } + append_packet((l&0x000000FF)); } /* */ #define lua_roundnumber(a,b) (int)floor((double)lua_tonumber(L,-1)+0.5) -static int -numeric_field (lua_State *L, char *name, int dflt) { - int i = dflt; - lua_pushstring(L,name); - lua_rawget(L,-2); - if (lua_isnumber(L,-1)) { - i = lua_roundnumber(L,-1); - } - lua_pop(L,1); - return i; +static int numeric_field(lua_State * L, char *name, int dflt) +{ + int i = dflt; + lua_pushstring(L, name); + lua_rawget(L, -2); + if (lua_isnumber(L, -1)) { + i = lua_roundnumber(L, -1); + } + lua_pop(L, 1); + return i; } -static int -n_numeric_field (lua_State *L, int name_index, int dflt) { - register int i = dflt; - lua_rawgeti(L,LUA_REGISTRYINDEX, name_index); /* fetch the stringptr */ - lua_rawget(L,-2); - if (lua_type(L,-1)==LUA_TNUMBER) { - i = lua_roundnumber(L,-1); - } - lua_pop(L,1); - return i; +static int n_numeric_field(lua_State * L, int name_index, int dflt) +{ + register int i = dflt; + lua_rawgeti(L, LUA_REGISTRYINDEX, name_index); /* fetch the stringptr */ + lua_rawget(L, -2); + if (lua_type(L, -1) == LUA_TNUMBER) { + i = lua_roundnumber(L, -1); + } + lua_pop(L, 1); + return i; } -static int -enum_field (lua_State *L, char *name, int dflt, char **values) { - int k; - char *s; - int i = dflt; - lua_pushstring(L,name); - lua_rawget(L,-2); - if (lua_isnumber(L,-1)) { - i = lua_tonumber(L,-1); - } else if (lua_isstring(L,-1)) { - s = (char *)lua_tostring(L,-1); - k = 0; - while (values[k] != NULL) { - if (strcmp(values[k],s) == 0) { - i = k; - break; - } - k++; - } - } - lua_pop(L,1); - return i; +static int enum_field(lua_State * L, char *name, int dflt, char **values) +{ + int k; + char *s; + int i = dflt; + lua_pushstring(L, name); + lua_rawget(L, -2); + if (lua_isnumber(L, -1)) { + i = lua_tonumber(L, -1); + } else if (lua_isstring(L, -1)) { + s = (char *) lua_tostring(L, -1); + k = 0; + while (values[k] != NULL) { + if (strcmp(values[k], s) == 0) { + i = k; + break; + } + k++; + } + } + lua_pop(L, 1); + return i; } -static int -boolean_field (lua_State *L, char *name, int dflt) { - int i = dflt; - lua_pushstring(L,name); - lua_rawget(L,-2); - if (lua_isboolean(L,-1)) { - i = lua_toboolean(L,-1); - } - lua_pop(L,1); - return i; +static int boolean_field(lua_State * L, char *name, int dflt) +{ + int i = dflt; + lua_pushstring(L, name); + lua_rawget(L, -2); + if (lua_isboolean(L, -1)) { + i = lua_toboolean(L, -1); + } + lua_pop(L, 1); + return i; } -static int -n_boolean_field (lua_State *L, int name_index, int dflt) { - int i = dflt; - lua_rawgeti(L,LUA_REGISTRYINDEX, name_index); /* fetch the stringptr */ - lua_rawget(L,-2); - if (lua_isboolean(L,-1)) { - i = lua_toboolean(L,-1); - } - lua_pop(L,1); - return i; +static int n_boolean_field(lua_State * L, int name_index, int dflt) +{ + int i = dflt; + lua_rawgeti(L, LUA_REGISTRYINDEX, name_index); /* fetch the stringptr */ + lua_rawget(L, -2); + if (lua_isboolean(L, -1)) { + i = lua_toboolean(L, -1); + } + lua_pop(L, 1); + return i; } -static char * -string_field (lua_State *L, char *name, char *dflt) { - char *i; - lua_pushstring(L,name); - lua_rawget(L,-2); - if (lua_isstring(L,-1)) { - i = xstrdup(lua_tostring(L,-1)); - } else if (dflt==NULL) { - i = NULL; - } else { - i = xstrdup(dflt); - } - lua_pop(L,1); - return i; +static char *string_field(lua_State * L, char *name, char *dflt) +{ + char *i; + lua_pushstring(L, name); + lua_rawget(L, -2); + if (lua_isstring(L, -1)) { + i = xstrdup(lua_tostring(L, -1)); + } else if (dflt == NULL) { + i = NULL; + } else { + i = xstrdup(dflt); + } + lua_pop(L, 1); + return i; } -static char * -n_string_field (lua_State *L, int name_index, char *dflt) { - char *i; - lua_rawgeti(L,LUA_REGISTRYINDEX, name_index); /* fetch the stringptr */ - lua_rawget(L,-2); - if (lua_isstring(L,-1)) { - i = xstrdup(lua_tostring(L,-1)); - } else if (dflt==NULL) { - i = NULL; - } else { - i = xstrdup(dflt); - } - lua_pop(L,1); - return i; +static char *n_string_field(lua_State * L, int name_index, char *dflt) +{ + char *i; + lua_rawgeti(L, LUA_REGISTRYINDEX, name_index); /* fetch the stringptr */ + lua_rawget(L, -2); + if (lua_isstring(L, -1)) { + i = xstrdup(lua_tostring(L, -1)); + } else if (dflt == NULL) { + i = NULL; + } else { + i = xstrdup(dflt); + } + lua_pop(L, 1); + return i; } -#define init_luaS_index(a) do { \ - lua_pushliteral(L,#a); \ - luaS_##a##_ptr = (char *)lua_tostring(L,-1); \ - luaS_##a##_index = luaL_ref (L,LUA_REGISTRYINDEX); \ +#define init_luaS_index(a) do { \ + lua_pushliteral(L,#a); \ + luaS_##a##_ptr = (char *)lua_tostring(L,-1); \ + luaS_##a##_index = luaL_ref (L,LUA_REGISTRYINDEX); \ } while (0) -#define make_luaS_index(a) \ - static int luaS_##a##_index = 0; \ +#define make_luaS_index(a) \ + static int luaS_##a##_index = 0; \ static char * luaS_##a##_ptr = NULL -#define luaS_index(a) luaS_##a##_index +#define luaS_index(a) luaS_##a##_index #define luaS_ptr_eq(a,b) (a==luaS_##b##_ptr) @@ -452,13 +613,15 @@ make_luaS_index(width); make_luaS_index(height); make_luaS_index(depth); make_luaS_index(italic); +make_luaS_index(top_accent); +make_luaS_index(bot_accent); make_luaS_index(index); make_luaS_index(left_protruding); make_luaS_index(right_protruding); make_luaS_index(expansion_factor); -make_luaS_index(top); -make_luaS_index(bot); -make_luaS_index(rep); +make_luaS_index(top); +make_luaS_index(bot); +make_luaS_index(rep); make_luaS_index(mid); make_luaS_index(next); make_luaS_index(used); @@ -475,6 +638,7 @@ make_luaS_index(right); make_luaS_index(node); make_luaS_index(down); make_luaS_index(special); +make_luaS_index(image); make_luaS_index(slant); make_luaS_index(space); make_luaS_index(space_stretch); @@ -487,455 +651,634 @@ make_luaS_index(right_boundary); make_luaS_index(kerns); make_luaS_index(ligatures); make_luaS_index(fonts); - -void init_font_string_pointers (lua_State *L) { - init_luaS_index(width); - init_luaS_index(height); - init_luaS_index(depth); - init_luaS_index(italic); - init_luaS_index(index); - init_luaS_index(left_protruding); - init_luaS_index(right_protruding); - init_luaS_index(expansion_factor); - init_luaS_index(top); - init_luaS_index(bot); - init_luaS_index(rep); - init_luaS_index(mid); - init_luaS_index(next); - init_luaS_index(used); - init_luaS_index(name); - init_luaS_index(tounicode); - init_luaS_index(font); - init_luaS_index(char); - init_luaS_index(slot); - init_luaS_index(comment); - init_luaS_index(push); - init_luaS_index(pop); - init_luaS_index(rule); - init_luaS_index(right); - init_luaS_index(node); - init_luaS_index(down); - init_luaS_index(special); - - init_luaS_index(slant); - init_luaS_index(space); - init_luaS_index(space_stretch); - init_luaS_index(space_shrink); - init_luaS_index(x_height); - init_luaS_index(quad); - init_luaS_index(extra_space); - - init_luaS_index(left_boundary); - init_luaS_index(right_boundary); - init_luaS_index(kerns); - init_luaS_index(ligatures); - init_luaS_index(fonts); +make_luaS_index(extender); +make_luaS_index(start); +make_luaS_index(end); +make_luaS_index(advance); +make_luaS_index(glyph); + +void init_font_string_pointers(lua_State * L) +{ + init_luaS_index(width); + init_luaS_index(height); + init_luaS_index(depth); + init_luaS_index(italic); + init_luaS_index(top_accent); + init_luaS_index(bot_accent); + init_luaS_index(index); + init_luaS_index(left_protruding); + init_luaS_index(right_protruding); + init_luaS_index(expansion_factor); + init_luaS_index(top); + init_luaS_index(bot); + init_luaS_index(rep); + init_luaS_index(mid); + init_luaS_index(next); + init_luaS_index(used); + init_luaS_index(name); + init_luaS_index(tounicode); + init_luaS_index(font); + init_luaS_index(char); + init_luaS_index(slot); + init_luaS_index(comment); + init_luaS_index(push); + init_luaS_index(pop); + init_luaS_index(rule); + init_luaS_index(right); + init_luaS_index(node); + init_luaS_index(down); + init_luaS_index(special); + init_luaS_index(image); + + init_luaS_index(slant); + init_luaS_index(space); + init_luaS_index(space_stretch); + init_luaS_index(space_shrink); + init_luaS_index(x_height); + init_luaS_index(quad); + init_luaS_index(extra_space); + + init_luaS_index(left_boundary); + init_luaS_index(right_boundary); + init_luaS_index(kerns); + init_luaS_index(ligatures); + init_luaS_index(fonts); + + init_luaS_index(extender); + init_luaS_index(start); + init_luaS_index(end); + init_luaS_index(advance); + init_luaS_index(glyph); } -static int -count_char_packet_bytes (lua_State *L) { - register int i; - register int l = 0; - int ff = 0; - for (i=1;i<=lua_objlen(L,-1);i++) { - lua_rawgeti(L,-1,i); - if (lua_istable(L,-1)) { - lua_rawgeti(L,-1,1); - if (lua_isstring(L,-1)) { - char *s = (char *)lua_tostring(L,-1); - if (luaS_ptr_eq(s,font)) { l+= 5; ff =1; } - else if (luaS_ptr_eq(s,char)) { if (ff==0) { l+=5; } l += 5; ff = 1; } - else if (luaS_ptr_eq(s,slot)) { l += 10; ff = 1;} - else if (luaS_ptr_eq(s,comment)) { ; } - else if (luaS_ptr_eq(s,push) || - luaS_ptr_eq(s,pop)) { l++; } - else if (luaS_ptr_eq(s,rule)) { l+=9; } - else if (luaS_ptr_eq(s,right) || - luaS_ptr_eq(s,node) || - luaS_ptr_eq(s,down)) { l+=5; } - else if (luaS_ptr_eq(s,special)) { - size_t len; - lua_rawgeti(L,-2,2); - (void)lua_tolstring(L,-1,&len); - lua_pop(L,1); - if (len>0) { l = l + 5 + len; } +static int count_char_packet_bytes(lua_State * L) +{ + register int i; + register int l = 0; + int ff = 0; + for (i = 1; i <= (int) lua_objlen(L, -1); i++) { + lua_rawgeti(L, -1, i); + if (lua_istable(L, -1)) { + lua_rawgeti(L, -1, 1); + if (lua_isstring(L, -1)) { + char *s = (char *) lua_tostring(L, -1); + if (luaS_ptr_eq(s, font)) { + l += 5; + ff = 1; + } else if (luaS_ptr_eq(s, char)) { + if (ff == 0) { + l += 5; + } + l += 5; + ff = 1; + } else if (luaS_ptr_eq(s, slot)) { + l += 10; + ff = 1; + } else if (luaS_ptr_eq(s, comment)) {; + } else if (luaS_ptr_eq(s, push) || luaS_ptr_eq(s, pop)) { + l++; + } else if (luaS_ptr_eq(s, rule)) { + l += 9; + } else if (luaS_ptr_eq(s, right) || + luaS_ptr_eq(s, node) || luaS_ptr_eq(s, down)) { + l += 5; + } else if (luaS_ptr_eq(s, special)) { + size_t len; + lua_rawgeti(L, -2, 2); + (void) lua_tolstring(L, -1, &len); + lua_pop(L, 1); + if (len > 0) { + l = l + 5 + len; + } + } else if (luaS_ptr_eq(s, image)) { + l += 5; + } else { + fprintf(stdout, "unknown packet command %s!\n", s); + } + } else { + fprintf(stdout, "no packet command!\n"); + } + lua_pop(L, 1); /* command name */ } - else { fprintf(stdout,"unknown packet command %s!\n",s); } - } else { - fprintf(stdout,"no packet command!\n"); - } - lua_pop(L,1); /* command name */ - } - lua_pop(L,1); /* item */ - } - return l; + lua_pop(L, 1); /* item */ + } + return l; } -scaled -sp_to_dvi (halfword sp, halfword atsize) { - double result, mult; - mult = (double)(atsize>>16); - result = (sp << 4); - return floor (result/mult ); +scaled sp_to_dvi(halfword sp, halfword atsize) +{ + double result, mult; + mult = (double) (atsize / 65536.0); + result = (double) (sp * 16.0); + return floor(result / mult); } static void -read_char_packets (lua_State *L, integer *l_fonts, charinfo *co, int atsize) { - int i, n, m; - size_t l; - int cmd; - char *s; - real_eight_bits *cpackets; - int ff = 0; - int np = 0; - int max_f = 0; - int pc = count_char_packet_bytes (L); - if (pc<=0) - return; - assert(l_fonts != NULL); - assert(l_fonts[1] != 0); - while (l_fonts[(max_f+1)]!=0) - max_f++; - - cpackets = xmalloc(pc+1); - for (i=1;i<=lua_objlen(L,-1);i++) { - lua_rawgeti(L,-1,i); - if (lua_istable(L,-1)) { - /* fetch the command code */ - lua_rawgeti(L,-1,1); - if (lua_isstring(L,-1)) { - s = (char *)lua_tostring(L,-1); - cmd = 0; - if (luaS_ptr_eq(s,font)) { - cmd = packet_font_code; - } else if (luaS_ptr_eq(s,char)) { - cmd = packet_char_code; - if (ff==0) { - append_packet(packet_font_code); - ff = l_fonts[1]; - do_store_four(ff); - } - } else if (luaS_ptr_eq(s,slot)) { - cmd = packet_nop_code; - lua_rawgeti(L,-2,2); n = lua_tointeger(L,-1); - ff = (n>max_f ? l_fonts[1] : l_fonts[n]); - lua_rawgeti(L,-3,3); n = lua_tointeger(L,-1); - lua_pop(L,2); - append_packet(packet_font_code); - do_store_four(ff); - append_packet(packet_char_code); - do_store_four(n); - } - else if (luaS_ptr_eq(s,comment)) { cmd = packet_nop_code; } - else if (luaS_ptr_eq(s,node)) { cmd = packet_node_code; } - else if (luaS_ptr_eq(s,push)) { cmd = packet_push_code; } - else if (luaS_ptr_eq(s,pop)) { cmd = packet_pop_code; } - else if (luaS_ptr_eq(s,rule)) { cmd = packet_rule_code; } - else if (luaS_ptr_eq(s,right)) { cmd = packet_right_code; } - else if (luaS_ptr_eq(s,down)) { cmd = packet_down_code; } - else if (luaS_ptr_eq(s,special)) { cmd = packet_special_code; } - - switch(cmd) { - case packet_push_code: - case packet_pop_code: - append_packet(cmd); - break; - case packet_font_code: - append_packet(cmd); - lua_rawgeti(L,-2,2); - n = lua_tointeger(L,-1); - ff = (n>max_f ? l_fonts[1] : l_fonts[n]); - do_store_four(ff); - lua_pop(L,1); - break; - case packet_node_code: - append_packet(cmd); - lua_rawgeti(L,-2,2); - n = copy_node_list(nodelist_from_lua(L)); - do_store_four(n); - lua_pop(L,1); - break; - case packet_char_code: - append_packet(cmd); - lua_rawgeti(L,-2,2); - n = lua_tointeger(L,-1); - do_store_four(n); - lua_pop(L,1); - break; - case packet_right_code: - case packet_down_code: - append_packet(cmd); - lua_rawgeti(L,-2,2); - n = lua_tointeger(L,-1); - do_store_four(sp_to_dvi(n,atsize)); - lua_pop(L,1); - break; - case packet_rule_code: - append_packet(cmd); - lua_rawgeti(L,-2,2); - n = lua_tointeger(L,-1); - do_store_four(sp_to_dvi(n,atsize)); - lua_rawgeti(L,-3,3); - n = lua_tointeger(L,-1); - do_store_four(sp_to_dvi(n,atsize)); - lua_pop(L,2); - break; - case packet_special_code: - append_packet(cmd); - lua_rawgeti(L,-2,2); - s = (char *)lua_tolstring(L,-1,&l); - if (l>0) { - do_store_four(l); - m = (int)l; - while(m>0) { - n = *s++; - m--; - append_packet(n); +read_char_packets(lua_State * L, integer * l_fonts, charinfo * co, int atsize) +{ + int i, n, m; + size_t l; + int cmd; + char *s; + real_eight_bits *cpackets; + int ff = 0; + int np = 0; + int max_f = 0; + int pc = count_char_packet_bytes(L); + if (pc <= 0) + return; + assert(l_fonts != NULL); + assert(l_fonts[1] != 0); + while (l_fonts[(max_f + 1)] != 0) + max_f++; + + cpackets = xmalloc(pc + 1); + for (i = 1; i <= (int) lua_objlen(L, -1); i++) { + lua_rawgeti(L, -1, i); + if (lua_istable(L, -1)) { + /* fetch the command code */ + lua_rawgeti(L, -1, 1); + if (lua_isstring(L, -1)) { + s = (char *) lua_tostring(L, -1); + cmd = 0; + if (luaS_ptr_eq(s, font)) { + cmd = packet_font_code; + } else if (luaS_ptr_eq(s, char)) { + cmd = packet_char_code; + if (ff == 0) { + append_packet(packet_font_code); + ff = l_fonts[1]; + do_store_four(ff); + } + } else if (luaS_ptr_eq(s, slot)) { + cmd = packet_nop_code; + lua_rawgeti(L, -2, 2); + n = lua_tointeger(L, -1); + ff = (n > max_f ? l_fonts[1] : l_fonts[n]); + lua_rawgeti(L, -3, 3); + n = lua_tointeger(L, -1); + lua_pop(L, 2); + append_packet(packet_font_code); + do_store_four(ff); + append_packet(packet_char_code); + do_store_four(n); + } else if (luaS_ptr_eq(s, comment)) { + cmd = packet_nop_code; + } else if (luaS_ptr_eq(s, node)) { + cmd = packet_node_code; + } else if (luaS_ptr_eq(s, push)) { + cmd = packet_push_code; + } else if (luaS_ptr_eq(s, pop)) { + cmd = packet_pop_code; + } else if (luaS_ptr_eq(s, rule)) { + cmd = packet_rule_code; + } else if (luaS_ptr_eq(s, right)) { + cmd = packet_right_code; + } else if (luaS_ptr_eq(s, down)) { + cmd = packet_down_code; + } else if (luaS_ptr_eq(s, special)) { + cmd = packet_special_code; + } else if (luaS_ptr_eq(s, image)) { + cmd = packet_image_code; + } + + switch (cmd) { + case packet_push_code: + case packet_pop_code: + append_packet(cmd); + break; + case packet_font_code: + append_packet(cmd); + lua_rawgeti(L, -2, 2); + n = lua_tointeger(L, -1); + ff = (n > max_f ? l_fonts[1] : l_fonts[n]); + do_store_four(ff); + lua_pop(L, 1); + break; + case packet_node_code: + append_packet(cmd); + lua_rawgeti(L, -2, 2); + n = copy_node_list(nodelist_from_lua(L)); + do_store_four(n); + lua_pop(L, 1); + break; + case packet_char_code: + append_packet(cmd); + lua_rawgeti(L, -2, 2); + n = lua_tointeger(L, -1); + do_store_four(n); + lua_pop(L, 1); + break; + case packet_right_code: + case packet_down_code: + append_packet(cmd); + lua_rawgeti(L, -2, 2); + n = lua_tointeger(L, -1); + do_store_four(sp_to_dvi(n, atsize)); + lua_pop(L, 1); + break; + case packet_rule_code: + append_packet(cmd); + lua_rawgeti(L, -2, 2); + n = lua_tointeger(L, -1); + do_store_four(sp_to_dvi(n, atsize)); + lua_rawgeti(L, -3, 3); + n = lua_tointeger(L, -1); + do_store_four(sp_to_dvi(n, atsize)); + lua_pop(L, 2); + break; + case packet_special_code: + append_packet(cmd); + lua_rawgeti(L, -2, 2); + s = (char *) lua_tolstring(L, -1, &l); + if (l > 0) { + do_store_four(l); + m = (int) l; + while (m > 0) { + n = *s++; + m--; + append_packet(n); + } + } + lua_pop(L, 1); + break; + case packet_image_code: + append_packet(cmd); + lua_rawgeti(L, -2, 2); /* img/imgtable? ... */ + if (lua_istable(L, -1)) { /* imgtable ... */ + lua_getglobal(L, "img"); /* imglib imgtable ... */ + lua_pushstring(L, "new"); /* `new' imglib imgtable ... */ + lua_gettable(L, -2); /* f imglib imgtable ... */ + lua_insert(L, -3); /* imglib imgtable f ... */ + lua_pop(L, 1); /* imgtable f ... */ + lua_call(L, 1, 1); + } /* img ... */ + luaL_checkudata(L, -1, TYPE_IMG); /* img ... --- just typecheck */ + n = luaL_ref(L, LUA_GLOBALSINDEX); /* ... */ + do_store_four(n); + break; + case packet_nop_code: + break; + default: + fprintf(stdout, + "Unknown char packet code %s (char %d in font %s)\n", + s, (int) c, font_name(f)); + } } - } - lua_pop(L,1); - break; - case packet_nop_code: - break; - default: - fprintf(stdout,"Unknown char packet code %s (char %d in font %s)\n",s,(int)c,font_name(f)); + lua_pop(L, 1); /* command code */ + } else { + fprintf(stdout, + "Found a `commands' item that is not a table (char %d in font %s)\n", + (int) c, font_name(f)); } - } - lua_pop(L,1); /* command code */ - } else { - fprintf(stdout,"Found a `commands' item that is not a table (char %d in font %s)\n",(int)c,font_name(f)); + lua_pop(L, 1); /* command table */ } - lua_pop(L,1); /* command table */ - } - append_packet(packet_end_code); - set_charinfo_packets(co,cpackets); - return; + append_packet(packet_end_code); + set_charinfo_packets(co, cpackets); + return; } -static void -read_lua_cidinfo (lua_State *L, int f) { - int i; - char *s; - lua_getfield(L,-1,"cidinfo"); - if (lua_istable(L,-1)) { - i = numeric_field(L,"version",0); - set_font_cidversion(f,i); - i = numeric_field(L,"supplement",0); - set_font_cidsupplement(f,i); - s = string_field(L,"registry","Adobe"); /* Adobe-Identity-0 */ - set_font_cidregistry(f,s); - s = string_field(L,"ordering","Identity"); - set_font_cidordering(f,s); - } - lua_pop(L,1); +static void read_lua_cidinfo(lua_State * L, int f) +{ + int i; + char *s; + lua_getfield(L, -1, "cidinfo"); + if (lua_istable(L, -1)) { + i = numeric_field(L, "version", 0); + set_font_cidversion(f, i); + i = numeric_field(L, "supplement", 0); + set_font_cidsupplement(f, i); + s = string_field(L, "registry", "Adobe"); /* Adobe-Identity-0 */ + set_font_cidregistry(f, s); + s = string_field(L, "ordering", "Identity"); + set_font_cidordering(f, s); + } + lua_pop(L, 1); } -static void -read_lua_parameters (lua_State *L, int f) { - int i, n; - char *s; - lua_getfield(L,-1,"parameters"); - if (lua_istable(L,-1)) { - /* the number of parameters is the max(IntegerKeys(L)),7) */ - n = 7; - lua_pushnil(L); /* first key */ - while (lua_next(L, -2) != 0) { - if (lua_isnumber(L,-2)) { - i = lua_tonumber(L,-2); - if (i > n) n = i; - } - lua_pop(L,1); /* pop value */ - } - if (n>7) set_font_params(f,n); - /* sometimes it is handy to have all integer keys */ - for (i=1;i<=7;i++) { - lua_rawgeti(L,-1,i); - if (lua_isnumber(L,-1)) { - n = lua_roundnumber(L,-1); - set_font_param(f,i, n); - } - lua_pop(L,1); - } - lua_pushnil(L); /* first key */ - while (lua_next(L, -2) != 0) { - if (lua_isnumber(L,-2)) { - i = lua_tointeger(L,-2); - if (i>=8) { - n = (lua_isnumber(L,-1) ? lua_roundnumber(L,-1) : 0); - set_font_param(f,i, n); +static void read_lua_parameters(lua_State * L, int f) +{ + int i, n; + char *s; + lua_getfield(L, -1, "parameters"); + if (lua_istable(L, -1)) { + /* the number of parameters is the max(IntegerKeys(L)),7) */ + n = 7; + lua_pushnil(L); /* first key */ + while (lua_next(L, -2) != 0) { + if (lua_isnumber(L, -2)) { + i = lua_tonumber(L, -2); + if (i > n) + n = i; + } + lua_pop(L, 1); /* pop value */ } - } else if (lua_isstring(L,-2)) { - s = (char *)lua_tostring(L,-2); - n = (lua_isnumber(L,-1) ? lua_roundnumber(L,-1) : 0); - if (luaS_ptr_eq(s,slant)) { set_font_param(f,slant_code,n); } - else if (luaS_ptr_eq(s,space)) { set_font_param(f,space_code,n); } - else if (luaS_ptr_eq(s,space_stretch)) { set_font_param(f,space_stretch_code,n); } - else if (luaS_ptr_eq(s,space_shrink)) { set_font_param(f,space_shrink_code,n); } - else if (luaS_ptr_eq(s,x_height)) { set_font_param(f,x_height_code,n); } - else if (luaS_ptr_eq(s,quad)) { set_font_param(f,quad_code,n); } - else if (luaS_ptr_eq(s,extra_space)) { set_font_param(f,extra_space_code,n); } - } - lua_pop(L,1); - } - } - lua_pop(L,1); + if (n > 7) + set_font_params(f, n); + /* sometimes it is handy to have all integer keys */ + for (i = 1; i <= 7; i++) { + lua_rawgeti(L, -1, i); + if (lua_isnumber(L, -1)) { + n = lua_roundnumber(L, -1); + set_font_param(f, i, n); + } + lua_pop(L, 1); + } + lua_pushnil(L); /* first key */ + while (lua_next(L, -2) != 0) { + if (lua_isnumber(L, -2)) { + i = lua_tointeger(L, -2); + if (i >= 8) { + n = (lua_isnumber(L, -1) ? lua_roundnumber(L, -1) : 0); + set_font_param(f, i, n); + } + } else if (lua_isstring(L, -2)) { + s = (char *) lua_tostring(L, -2); + n = (lua_isnumber(L, -1) ? lua_roundnumber(L, -1) : 0); + if (luaS_ptr_eq(s, slant)) { + set_font_param(f, slant_code, n); + } else if (luaS_ptr_eq(s, space)) { + set_font_param(f, space_code, n); + } else if (luaS_ptr_eq(s, space_stretch)) { + set_font_param(f, space_stretch_code, n); + } else if (luaS_ptr_eq(s, space_shrink)) { + set_font_param(f, space_shrink_code, n); + } else if (luaS_ptr_eq(s, x_height)) { + set_font_param(f, x_height_code, n); + } else if (luaS_ptr_eq(s, quad)) { + set_font_param(f, quad_code, n); + } else if (luaS_ptr_eq(s, extra_space)) { + set_font_param(f, extra_space_code, n); + } + } + lua_pop(L, 1); + } + } + lua_pop(L, 1); } - -void -font_char_from_lua (lua_State *L, internal_font_number f, integer i, integer *l_fonts) { - int k,r,t; - charinfo *co; - kerninfo *ckerns; - liginfo *cligs; - scaled j; - char *s; - int nl = 0; /* number of ligature table items */ - int nk = 0; /* number of kern table items */ - int ctr = 0; - int atsize = font_size(f); - if (lua_istable(L,-1)) { - co = get_charinfo(f,i); - set_charinfo_tag (co,0); - j = n_numeric_field(L,luaS_width_index,0); set_charinfo_width (co,j); - j = n_numeric_field(L,luaS_height_index,0); set_charinfo_height (co,j); - j = n_numeric_field(L,luaS_depth_index,0); set_charinfo_depth (co,j); - j = n_numeric_field(L,luaS_italic_index,0); set_charinfo_italic (co,j); - j = n_numeric_field(L,luaS_index_index,0); set_charinfo_index(co,j); - j = n_numeric_field(L,luaS_expansion_factor_index,0); set_charinfo_ef(co,j); - j = n_numeric_field(L,luaS_left_protruding_index,0); set_charinfo_lp(co,j); - j = n_numeric_field(L,luaS_right_protruding_index,0); set_charinfo_rp(co,j); - k = n_boolean_field(L,luaS_used_index,0); set_charinfo_used(co,k); - s = n_string_field (L,luaS_name_index,NULL); set_charinfo_name(co,s); - s = n_string_field (L,luaS_tounicode_index,NULL); set_charinfo_tounicode(co,s); - k = n_numeric_field(L,luaS_next_index,-1); - if (k>=0) { - set_charinfo_tag (co,list_tag); - set_charinfo_remainder (co,k); - } - lua_getfield(L,-1,"extensible"); - if (lua_istable(L,-1)){ - int top, bot,mid, rep; - top = n_numeric_field(L,luaS_top_index,0); - bot = n_numeric_field(L,luaS_bot_index,0); - mid = n_numeric_field(L,luaS_mid_index,0); - rep = n_numeric_field(L,luaS_rep_index,0); - if (top != 0 || bot != 0 || mid != 0 || rep != 0) { - set_charinfo_tag (co,ext_tag); - set_charinfo_extensible (co,top,bot,mid,rep); - } else { - pdftex_warn("lua-loaded font %s char [%d] has an invalid extensible field!",font_name(f),(int)i); - } - } - lua_pop(L,1); - - nk = count_hash_items(L,luaS_index(kerns)); - if (nk>0) { - ckerns = xcalloc((nk+1),sizeof(kerninfo)); - lua_rawgeti(L,LUA_REGISTRYINDEX,luaS_index(kerns)); - lua_rawget(L,-2); - if (lua_istable(L,-1)) { /* there are kerns */ - ctr = 0; + +static void read_lua_math_parameters(lua_State * L, int f) +{ + int i = 0, n = 0; + lua_getfield(L, -1, "MathConstants"); + if (lua_istable(L, -1)) { lua_pushnil(L); while (lua_next(L, -2) != 0) { - k = non_boundarychar; - if (lua_isnumber(L,-2)) { - k = lua_tonumber(L,-2); /* adjacent char */ - if (k<0) - k = non_boundarychar; - } else if (lua_isstring(L,-2)) { - s = (char *)lua_tostring(L,-2); - if (luaS_ptr_eq(s,right_boundary)) { - k = right_boundarychar; - if (!has_right_boundary(f)) - set_right_boundary(f,get_charinfo(f,right_boundarychar)); + if (lua_isnumber(L, -2)) { + i = lua_tonumber(L, -2); + } else if (lua_isstring(L, -2)) { + i = luaL_checkoption(L, -2, NULL, MATH_param_names); + } + n = lua_tonumber(L, -1); + if (i != 0) { + set_font_math_param(f, i, n); } - } - j = lua_roundnumber(L,-1); /* movement */ - if (k!=non_boundarychar) { - set_kern_item(ckerns[ctr],k,j); - ctr++; - } else { - pdftex_warn("lua-loaded font %s char [%d] has an invalid kern field!",font_name(f),(int)i); - } - lua_pop(L,1); + lua_pop(L, 1); /* pop value */ } - /* guard against empty tables */ - if (ctr>0) { - set_kern_item(ckerns[ctr],end_kern,0); - set_charinfo_kerns(co,ckerns); - } else { - pdftex_warn("lua-loaded font %s char [%d] has an invalid kerns field!",font_name(f),(int)i); + } + lua_pop(L, 1); +} + + +void +font_char_from_lua(lua_State * L, internal_font_number f, integer i, + integer * l_fonts) +{ + int k, r, t; + charinfo *co; + kerninfo *ckerns; + liginfo *cligs; + scaled j; + char *s; + int nl = 0; /* number of ligature table items */ + int nk = 0; /* number of kern table items */ + int ctr = 0; + int atsize = font_size(f); + if (lua_istable(L, -1)) { + co = get_charinfo(f, i); + set_charinfo_tag(co, 0); + j = n_numeric_field(L, luaS_width_index, 0); + set_charinfo_width(co, j); + j = n_numeric_field(L, luaS_height_index, 0); + set_charinfo_height(co, j); + j = n_numeric_field(L, luaS_depth_index, 0); + set_charinfo_depth(co, j); + j = n_numeric_field(L, luaS_italic_index, 0); + set_charinfo_italic(co, j); + j = n_numeric_field(L, luaS_top_accent_index, 0); + set_charinfo_top_accent(co, j); + j = n_numeric_field(L, luaS_bot_accent_index, 0); + set_charinfo_bot_accent(co, j); + j = n_numeric_field(L, luaS_index_index, 0); + set_charinfo_index(co, j); + j = n_numeric_field(L, luaS_expansion_factor_index, 0); + set_charinfo_ef(co, j); + j = n_numeric_field(L, luaS_left_protruding_index, 0); + set_charinfo_lp(co, j); + j = n_numeric_field(L, luaS_right_protruding_index, 0); + set_charinfo_rp(co, j); + k = n_boolean_field(L, luaS_used_index, 0); + set_charinfo_used(co, k); + s = n_string_field(L, luaS_name_index, NULL); + set_charinfo_name(co, s); + s = n_string_field(L, luaS_tounicode_index, NULL); + set_charinfo_tounicode(co, s); + k = n_numeric_field(L, luaS_next_index, -1); + if (k >= 0) { + set_charinfo_tag(co, list_tag); + set_charinfo_remainder(co, k); } - } - lua_pop(L,1); - } - - /* packet commands */ - lua_getfield(L,-1,"commands"); - if (lua_istable(L,-1)){ - lua_pushnil(L); /* first key */ - if (lua_next(L, -2) != 0) { - lua_pop(L,2); - read_char_packets(L,(integer *)l_fonts,co,atsize); - } - } - lua_pop(L,1); - - /* ligatures */ - nl = count_hash_items(L,luaS_index(ligatures)); - - if (nl>0) { - cligs = xcalloc((nl+1),sizeof(liginfo)); - lua_rawgeti(L,LUA_REGISTRYINDEX,luaS_index(ligatures)); - lua_rawget(L,-2); - if (lua_istable(L,-1)){/* do ligs */ - ctr = 0; - lua_pushnil(L); - while (lua_next(L, -2) != 0) { - k = non_boundarychar; - if (lua_isnumber(L,-2)) { - k = lua_tonumber(L,-2); /* adjacent char */ - if (k<0) { - k = non_boundarychar; + lua_getfield(L, -1, "extensible"); + if (lua_istable(L, -1)) { + int top, bot, mid, rep; + top = n_numeric_field(L, luaS_top_index, 0); + bot = n_numeric_field(L, luaS_bot_index, 0); + mid = n_numeric_field(L, luaS_mid_index, 0); + rep = n_numeric_field(L, luaS_rep_index, 0); + if (top != 0 || bot != 0 || mid != 0 || rep != 0) { + set_charinfo_tag(co, ext_tag); + set_charinfo_extensible(co, top, bot, mid, rep); + } else { + pdftex_warn + ("lua-loaded font %s char [U+%X] has an invalid extensible field!", + font_name(f), (int) i); } - } else if (lua_isstring(L,-2)) { - s = (char *)lua_tostring(L,-2); - if (luaS_ptr_eq(s,right_boundary)) { - k = right_boundarychar; - if (!has_right_boundary(f)) - set_right_boundary(f,get_charinfo(f,right_boundarychar)); + } + lua_pop(L, 1); + + lua_getfield(L, -1, "horiz_variants"); + if (lua_istable(L, -1)) { + int glyph, startconnect, endconnect, advance, extender; + extinfo *h; + set_charinfo_tag(co, ext_tag); + set_charinfo_hor_variants(co, NULL); + for (k = 1;; k++) { + lua_rawgeti(L, -1, k); + if (lua_istable(L, -1)) { + glyph = n_numeric_field(L, luaS_glyph_index, 0); + extender = n_numeric_field(L, luaS_extender_index, 0); + startconnect = n_numeric_field(L, luaS_start_index, 0); + endconnect = n_numeric_field(L, luaS_end_index, 0); + advance = n_numeric_field(L, luaS_advance_index, 0); + h = new_variant(glyph, startconnect, endconnect, advance, + extender); + add_charinfo_hor_variant(co, h); + lua_pop(L, 1); + } else { + lua_pop(L, 1); + break; + } } - } - r = -1; - if (lua_istable(L,-1)) { - r = n_numeric_field(L,luaS_char_index,-1); /* ligature */ - } - if (r != -1 && k != non_boundarychar) { - t = enum_field(L,"type",0,ligature_type_strings); - set_ligature_item(cligs[ctr],(t*2)+1,k,r); - ctr++; - } else { - pdftex_warn("lua-loaded font %s char [%d] has an invalid ligature field!",font_name(f),(int)i); - } - lua_pop(L,1); /* iterator value */ - } - /* guard against empty tables */ - if (ctr>0) { - set_ligature_item(cligs[ctr],0,end_ligature,0); - set_charinfo_ligatures(co,cligs); - } else { - pdftex_warn("lua-loaded font %s char [%d] has an invalid ligatures field!",font_name(f),(int)i); } - } - lua_pop(L,1); /* ligatures table */ + lua_pop(L, 1); + + + lua_getfield(L, -1, "vert_variants"); + if (lua_istable(L, -1)) { + int glyph, startconnect, endconnect, advance, extender; + extinfo *h; + set_charinfo_tag(co, ext_tag); + set_charinfo_vert_variants(co, NULL); + for (k = 1;; k++) { + lua_rawgeti(L, -1, k); + if (lua_istable(L, -1)) { + glyph = n_numeric_field(L, luaS_glyph_index, 0); + extender = n_numeric_field(L, luaS_extender_index, 0); + startconnect = n_numeric_field(L, luaS_start_index, 0); + endconnect = n_numeric_field(L, luaS_end_index, 0); + advance = n_numeric_field(L, luaS_advance_index, 0); + h = new_variant(glyph, startconnect, endconnect, advance, + extender); + add_charinfo_vert_variant(co, h); + lua_pop(L, 1); + } else { + lua_pop(L, 1); + break; + } + } + } + lua_pop(L, 1); + + nk = count_hash_items(L, luaS_index(kerns)); + if (nk > 0) { + ckerns = xcalloc((nk + 1), sizeof(kerninfo)); + lua_rawgeti(L, LUA_REGISTRYINDEX, luaS_index(kerns)); + lua_rawget(L, -2); + if (lua_istable(L, -1)) { /* there are kerns */ + ctr = 0; + lua_pushnil(L); + while (lua_next(L, -2) != 0) { + k = non_boundarychar; + if (lua_isnumber(L, -2)) { + k = lua_tonumber(L, -2); /* adjacent char */ + if (k < 0) + k = non_boundarychar; + } else if (lua_isstring(L, -2)) { + s = (char *) lua_tostring(L, -2); + if (luaS_ptr_eq(s, right_boundary)) { + k = right_boundarychar; + if (!has_right_boundary(f)) + set_right_boundary(f, + get_charinfo(f, + right_boundarychar)); + } + } + j = lua_roundnumber(L, -1); /* movement */ + if (k != non_boundarychar) { + set_kern_item(ckerns[ctr], k, j); + ctr++; + } else { + pdftex_warn + ("lua-loaded font %s char [U+%X] has an invalid kern field!", + font_name(f), (int) i); + } + lua_pop(L, 1); + } + /* guard against empty tables */ + if (ctr > 0) { + set_kern_item(ckerns[ctr], end_kern, 0); + set_charinfo_kerns(co, ckerns); + } else { + pdftex_warn + ("lua-loaded font %s char [U+%X] has an invalid kerns field!", + font_name(f), (int) i); + } + } + lua_pop(L, 1); + } + + /* packet commands */ + lua_getfield(L, -1, "commands"); + if (lua_istable(L, -1)) { + lua_pushnil(L); /* first key */ + if (lua_next(L, -2) != 0) { + lua_pop(L, 2); + read_char_packets(L, (integer *) l_fonts, co, atsize); + } + } + lua_pop(L, 1); + + /* ligatures */ + nl = count_hash_items(L, luaS_index(ligatures)); + + if (nl > 0) { + cligs = xcalloc((nl + 1), sizeof(liginfo)); + lua_rawgeti(L, LUA_REGISTRYINDEX, luaS_index(ligatures)); + lua_rawget(L, -2); + if (lua_istable(L, -1)) { /* do ligs */ + ctr = 0; + lua_pushnil(L); + while (lua_next(L, -2) != 0) { + k = non_boundarychar; + if (lua_isnumber(L, -2)) { + k = lua_tonumber(L, -2); /* adjacent char */ + if (k < 0) { + k = non_boundarychar; + } + } else if (lua_isstring(L, -2)) { + s = (char *) lua_tostring(L, -2); + if (luaS_ptr_eq(s, right_boundary)) { + k = right_boundarychar; + if (!has_right_boundary(f)) + set_right_boundary(f, + get_charinfo(f, + right_boundarychar)); + } + } + r = -1; + if (lua_istable(L, -1)) { + r = n_numeric_field(L, luaS_char_index, -1); /* ligature */ + } + if (r != -1 && k != non_boundarychar) { + t = enum_field(L, "type", 0, ligature_type_strings); + set_ligature_item(cligs[ctr], (t * 2) + 1, k, r); + ctr++; + } else { + pdftex_warn + ("lua-loaded font %s char [U+%X] has an invalid ligature field!", + font_name(f), (int) i); + } + lua_pop(L, 1); /* iterator value */ + } + /* guard against empty tables */ + if (ctr > 0) { + set_ligature_item(cligs[ctr], 0, end_ligature, 0); + set_charinfo_ligatures(co, cligs); + } else { + pdftex_warn + ("lua-loaded font %s char [U+%X] has an invalid ligatures field!", + font_name(f), (int) i); + } + } + lua_pop(L, 1); /* ligatures table */ + } } - } } @@ -943,203 +1286,247 @@ font_char_from_lua (lua_State *L, internal_font_number f, integer i, integer *l_ /* The caller has to fix the state of the lua stack when there is an error! */ -int -font_from_lua (lua_State *L, int f) { - int i,n,r,t; - int s_top; /* lua stack top */ - int bc; /* first char index */ - int ec; /* last char index */ - char *s; - integer *l_fonts = NULL; - /* the table is at stack index -1 */ - - if (luaS_width_index==0) - init_font_string_pointers(L); - - s = string_field(L,"area",""); set_font_area(f,s); - s = string_field(L,"filename",NULL); set_font_filename(f,s); - s = string_field(L,"encodingname",NULL); set_font_encodingname(f,s); - - s = string_field(L,"name",NULL); set_font_name(f,s); - s = string_field(L,"fullname",font_name(f)); set_font_fullname(f,s); - - if (s==NULL) { - pdftex_fail("lua-loaded font [%d] has no name!",f); - return false; - } - - i = numeric_field(L,"designsize",655360); set_font_dsize(f,i); - i = numeric_field(L,"size",font_dsize(f)); set_font_size(f,i); - i = numeric_field(L,"checksum",0); set_font_checksum(f,i); - i = numeric_field(L,"direction",0); set_font_natural_dir(f,i); - i = numeric_field(L,"encodingbytes",0); set_font_encodingbytes(f,i); - i = numeric_field(L,"tounicode",0); set_font_tounicode(f,i); - - i = numeric_field(L,"extend",0); - if (i<-2000) i = -2000; if (i>2000) i = 2000; if (i==1000) i = 0; - set_font_extend(f,i); - i = numeric_field(L,"slant",0); - if (i<-1000) i = -1000; if (i>1000) i = 1000; - set_font_slant(f,i); - - i = numeric_field(L,"hyphenchar",get_default_hyphen_char()); set_hyphen_char(f,i); - i = numeric_field(L,"skewchar",get_default_skew_char()); set_skew_char(f,i); - i = boolean_field(L,"used",0); set_font_used(f,i); - - s = string_field (L,"attributes",NULL); - if (s!=NULL && strlen(s)>0) { - i = maketexstring(s); - set_pdf_font_attr(f,i); - } - - i = enum_field(L,"type", unknown_font_type,font_type_strings); set_font_type(f,i); - i = enum_field(L,"format", unknown_format, font_format_strings); set_font_format(f,i); - i = enum_field(L,"embedding",unknown_embedding,font_embedding_strings); set_font_embedding(f,i); - if (font_encodingbytes(f)==0 && - (font_format(f)==opentype_format || font_format(f)==truetype_format)) { - set_font_encodingbytes(f,2); - } - - /* now fetch the base fonts, if needed */ - n = count_hash_items(L,luaS_index(fonts)); - if (n>0) { - l_fonts = xmalloc((n+2)*sizeof(integer)); - memset (l_fonts,0,(n+2)*sizeof(integer)); - lua_rawgeti(L,LUA_REGISTRYINDEX,luaS_index(fonts)); - lua_rawget(L,-2); - for (i=1;i<=n;i++) { - lua_rawgeti(L,-1,i); - if (lua_istable(L,-1)) { - lua_getfield(L,-1,"id"); - if (lua_isnumber(L,-1)) { - l_fonts[i] = lua_tonumber(L,-1); - lua_pop(L,2); /* pop id and entry */ - continue; - } - lua_pop(L,1); /* pop id */ - }; - s = NULL; - if (lua_istable(L,-1)) { - lua_getfield(L,-1,"name"); - if (lua_isstring(L,-1)) { - s = (char *)lua_tostring(L,-1); - } - lua_pop(L,1); /* pop name */ - } - if (s!= NULL) { - lua_getfield(L,-1,"size"); - t = (lua_isnumber(L,-1) ? lua_roundnumber(L,-1) : -1000); - lua_pop(L,1); - - /* TODO: the stack is messed up, otherwise this - * explicit resizing would not be needed - */ - s_top = lua_gettop(L); - l_fonts[i] = find_font_id(s,"",t); - lua_settop(L,s_top); - } else { - pdftex_fail("Invalid local font in font %s!\n", font_name(f)); - } - lua_pop(L,1); /* pop list entry */ - } - lua_pop(L,1); /* pop list entry */ - } else { - if(font_type(f) == virtual_font_type) { - pdftex_fail("Invalid local fonts in font %s!\n", font_name(f)); - } else { - l_fonts = xmalloc(3*sizeof(integer)); - l_fonts[0] = 0; - l_fonts[1] = f; - l_fonts[2] = 0; - } - } - - /* parameters */ - read_lua_parameters(L,f); - read_lua_cidinfo(L,f); - - /* characters */ - lua_getfield(L,-1,"characters"); - if (lua_istable(L,-1)) { - /* find the array size values */ - ec = 0; bc = -1; - lua_pushnil(L); /* first key */ - while (lua_next(L, -2) != 0) { - if (lua_isnumber(L,-2)) { - i = lua_tointeger(L,-2); - if (i>=0) { - if (lua_istable(L,-1)) { - if (i>ec) ec = i; - if (bc<0) bc = i; - if (bc>=0 && i<bc) bc = i; - } +int font_from_lua(lua_State * L, int f) +{ + int i, n, r, t; + int s_top; /* lua stack top */ + int bc; /* first char index */ + int ec; /* last char index */ + char *s; + integer *l_fonts = NULL; + /* the table is at stack index -1 */ + + if (luaS_width_index == 0) + init_font_string_pointers(L); + + s = string_field(L, "area", ""); + set_font_area(f, s); + s = string_field(L, "filename", NULL); + set_font_filename(f, s); + s = string_field(L, "encodingname", NULL); + set_font_encodingname(f, s); + + s = string_field(L, "name", NULL); + set_font_name(f, s); + s = string_field(L, "fullname", font_name(f)); + set_font_fullname(f, s); + + if (s == NULL) { + pdftex_fail("lua-loaded font [%d] has no name!", f); + return false; + } + + i = numeric_field(L, "designsize", 655360); + set_font_dsize(f, i); + i = numeric_field(L, "size", font_dsize(f)); + set_font_size(f, i); + i = numeric_field(L, "checksum", 0); + set_font_checksum(f, i); + i = numeric_field(L, "direction", 0); + set_font_natural_dir(f, i); + i = numeric_field(L, "encodingbytes", 0); + set_font_encodingbytes(f, i); + i = numeric_field(L, "tounicode", 0); + set_font_tounicode(f, i); + + i = numeric_field(L, "extend", 0); + if (i < -2000) + i = -2000; + if (i > 2000) + i = 2000; + if (i == 1000) + i = 0; + set_font_extend(f, i); + i = numeric_field(L, "slant", 0); + if (i < -1000) + i = -1000; + if (i > 1000) + i = 1000; + set_font_slant(f, i); + + i = numeric_field(L, "hyphenchar", get_default_hyphen_char()); + set_hyphen_char(f, i); + i = numeric_field(L, "skewchar", get_default_skew_char()); + set_skew_char(f, i); + i = boolean_field(L, "used", 0); + set_font_used(f, i); + + s = string_field(L, "attributes", NULL); + if (s != NULL && strlen(s) > 0) { + i = maketexstring(s); + set_pdf_font_attr(f, i); + } + + i = enum_field(L, "type", unknown_font_type, font_type_strings); + set_font_type(f, i); + i = enum_field(L, "format", unknown_format, font_format_strings); + set_font_format(f, i); + i = enum_field(L, "embedding", unknown_embedding, font_embedding_strings); + set_font_embedding(f, i); + if (font_encodingbytes(f) == 0 && + (font_format(f) == opentype_format + || font_format(f) == truetype_format)) { + set_font_encodingbytes(f, 2); + } + + /* now fetch the base fonts, if needed */ + n = count_hash_items(L, luaS_index(fonts)); + if (n > 0) { + l_fonts = xmalloc((n + 2) * sizeof(integer)); + memset(l_fonts, 0, (n + 2) * sizeof(integer)); + lua_rawgeti(L, LUA_REGISTRYINDEX, luaS_index(fonts)); + lua_rawget(L, -2); + for (i = 1; i <= n; i++) { + lua_rawgeti(L, -1, i); + if (lua_istable(L, -1)) { + lua_getfield(L, -1, "id"); + if (lua_isnumber(L, -1)) { + l_fonts[i] = lua_tonumber(L, -1); + lua_pop(L, 2); /* pop id and entry */ + continue; + } + lua_pop(L, 1); /* pop id */ + }; + s = NULL; + if (lua_istable(L, -1)) { + lua_getfield(L, -1, "name"); + if (lua_isstring(L, -1)) { + s = (char *) lua_tostring(L, -1); + } + lua_pop(L, 1); /* pop name */ + } + if (s != NULL) { + lua_getfield(L, -1, "size"); + t = (lua_isnumber(L, -1) ? lua_roundnumber(L, -1) : -1000); + lua_pop(L, 1); + + /* TODO: the stack is messed up, otherwise this + * explicit resizing would not be needed + */ + s_top = lua_gettop(L); + if (strcmp(font_name(f), s) == 0) + l_fonts[i] = f; + else + l_fonts[i] = find_font_id(s, "", t); + lua_settop(L, s_top); + } else { + pdftex_fail("Invalid local font in font %s!\n", font_name(f)); + } + lua_pop(L, 1); /* pop list entry */ } - } - lua_pop(L, 1); - } - - if (bc != -1) { - /* fprintf(stdout,"defined a font at %d with %d-%d\n",f,bc,ec); */ - set_font_bc(f,bc); - set_font_ec(f,ec); - lua_pushnil(L); /* first key */ - while (lua_next(L, -2) != 0) { - if (lua_isnumber(L,-2)) { - i = lua_tonumber(L,-2); - if (i>=0) { - font_char_from_lua(L,f, i, l_fonts); - } - } else if (lua_isstring(L,-2)) { - s = (char *)lua_tostring(L,-2); - if (luaS_ptr_eq(s,left_boundary)) { - font_char_from_lua(L,f, left_boundarychar, l_fonts); - } else if (luaS_ptr_eq(s,right_boundary)) { - font_char_from_lua(L,f, right_boundarychar, l_fonts); - } + lua_pop(L, 1); /* pop list entry */ + } else { + if (font_type(f) == virtual_font_type) { + pdftex_fail("Invalid local fonts in font %s!\n", font_name(f)); + } else { + l_fonts = xmalloc(3 * sizeof(integer)); + l_fonts[0] = 0; + l_fonts[1] = f; + l_fonts[2] = 0; } - lua_pop(L, 1); - } - lua_pop(L, 1); - - /* handle font expansion last: the |copy_font| routine is called eventually, - and that needs to know |bc| and |ec|. */ - if (font_type(f)!=virtual_font_type) { - int fstep = numeric_field(L,"step",0); - if (fstep<0) fstep = 0; - if (fstep>100) fstep = 100; - if (fstep!=0) { - int fshrink = numeric_field(L,"shrink",0); - int fstretch = numeric_field(L,"stretch",0); - int fexpand = boolean_field(L,"auto_expand",0); - if (fshrink<0) fshrink = 0; - if (fshrink>500) fshrink = 500; - fshrink -= (fshrink % fstep); - if (fshrink<0) fshrink = 0; - if (fstretch<0) fstretch = 0; - if (fstretch>1000) fstretch = 1000; - fstretch -= (fstretch % fstep); - if (fstretch<0) fstretch = 0; - set_expand_params(f, fexpand, fstretch, fshrink, fstep, 0); - } - } - - } else { /* jikes, no characters */ - pdftex_warn("lua-loaded font [%d] (%s) has no characters!",f, font_name(f)); } + /* parameters */ + read_lua_parameters(L, f); + read_lua_math_parameters(L, f); + read_lua_cidinfo(L, f); + + /* characters */ + lua_getfield(L, -1, "characters"); + if (lua_istable(L, -1)) { + /* find the array size values */ + ec = 0; + bc = -1; + lua_pushnil(L); /* first key */ + while (lua_next(L, -2) != 0) { + if (lua_isnumber(L, -2)) { + i = lua_tointeger(L, -2); + if (i >= 0) { + if (lua_istable(L, -1)) { + if (i > ec) + ec = i; + if (bc < 0) + bc = i; + if (bc >= 0 && i < bc) + bc = i; + } + } + } + lua_pop(L, 1); + } + + if (bc != -1) { + /* fprintf(stdout,"defined a font at %d with %d-%d\n",f,bc,ec); */ + set_font_bc(f, bc); + set_font_ec(f, ec); + lua_pushnil(L); /* first key */ + while (lua_next(L, -2) != 0) { + if (lua_isnumber(L, -2)) { + i = lua_tonumber(L, -2); + if (i >= 0) { + font_char_from_lua(L, f, i, l_fonts); + } + } else if (lua_isstring(L, -2)) { + s = (char *) lua_tostring(L, -2); + if (luaS_ptr_eq(s, left_boundary)) { + font_char_from_lua(L, f, left_boundarychar, l_fonts); + } else if (luaS_ptr_eq(s, right_boundary)) { + font_char_from_lua(L, f, right_boundarychar, l_fonts); + } + } + lua_pop(L, 1); + } + lua_pop(L, 1); + + /* handle font expansion last: the |copy_font| routine is called eventually, + and that needs to know |bc| and |ec|. */ + if (font_type(f) != virtual_font_type) { + int fstep = numeric_field(L, "step", 0); + if (fstep < 0) + fstep = 0; + if (fstep > 100) + fstep = 100; + if (fstep != 0) { + int fshrink = numeric_field(L, "shrink", 0); + int fstretch = numeric_field(L, "stretch", 0); + int fexpand = boolean_field(L, "auto_expand", 0); + if (fshrink < 0) + fshrink = 0; + if (fshrink > 500) + fshrink = 500; + fshrink -= (fshrink % fstep); + if (fshrink < 0) + fshrink = 0; + if (fstretch < 0) + fstretch = 0; + if (fstretch > 1000) + fstretch = 1000; + fstretch -= (fstretch % fstep); + if (fstretch < 0) + fstretch = 0; + set_expand_params(f, fexpand, fstretch, fshrink, fstep, 0); + } + } + + } else { /* jikes, no characters */ + pdftex_warn("lua-loaded font [%d] (%s) has no characters!", f, + font_name(f)); + } + #if SAVE_REF - r = luaL_ref(Luas[0],LUA_REGISTRYINDEX); /* pops the table */ - set_font_cache_id(f,r); + r = luaL_ref(Luas, LUA_REGISTRYINDEX); /* pops the table */ + set_font_cache_id(f, r); #else - lua_pop(Luas[0],1); + lua_pop(Luas, 1); #endif - } else { /* jikes, no characters */ - pdftex_warn("lua-loaded font [%d] (%s) has no character table!",f, font_name(f)); - } + } else { /* jikes, no characters */ + pdftex_warn("lua-loaded font [%d] (%s) has no character table!", f, + font_name(f)); + } - if (l_fonts!=NULL) - free(l_fonts); - return true; + if (l_fonts != NULL) + free(l_fonts); + return true; } /* ==================================================================== @@ -1151,393 +1538,423 @@ font_from_lua (lua_State *L, int f) { #define assert_disc(a) \ assert(pre_break(a)!=null); /* expect head_node */ \ - assert(type(pre_break(a))==nesting_node); \ + assert(type(pre_break(a))==nesting_node); \ assert((vlink_pre_break(a)==null && tlink_pre_break(a)==null) || tail_of_list(vlink_pre_break(a))==tlink_pre_break(a)); \ assert(post_break(a)!=null); /* expect head_node */ \ - assert(type(post_break(a))==nesting_node); \ + assert(type(post_break(a))==nesting_node); \ assert((vlink_post_break(a)==null && tlink_post_break(a)==null) || tail_of_list(vlink_post_break(a))==tlink_post_break(a)); \ - assert(no_break(a)!=null); /* expect head_node */ \ - assert(type(no_break(a))==nesting_node); \ - assert((vlink_no_break(a)==null && tlink_no_break(a)==null) || tail_of_list(vlink_no_break(a))==tlink_no_break(a)); - -static void -nesting_append (halfword nest, halfword newn) { - halfword tail = tlink(nest); - assert(alink(nest)==null); - assert(vlink(newn)==null); - assert(alink(newn)==null); - if (tail==null) { - assert(vlink(nest)==null); - couple_nodes(nest,newn); - } else { - assert(vlink(tail)==null); - assert(tail_of_list(vlink(nest))==tail); - couple_nodes(tail,newn); - } - tlink(nest) = newn; + assert(no_break(a)!=null); /* expect head_node */ \ + assert(type(no_break(a))==nesting_node); \ + assert((vlink_no_break(a)==null && tlink_no_break(a)==null) || tail_of_list(vlink_no_break(a))==tlink_no_break(a)); + +static void nesting_append(halfword nest, halfword newn) +{ + halfword tail = tlink(nest); + assert(alink(nest) == null); + assert(vlink(newn) == null); + assert(alink(newn) == null); + if (tail == null) { + assert(vlink(nest) == null); + couple_nodes(nest, newn); + } else { + assert(vlink(tail) == null); + assert(tail_of_list(vlink(nest)) == tail); + couple_nodes(tail, newn); + } + tlink(nest) = newn; } -static void -nesting_prepend (halfword nest, halfword newn) { - halfword head = vlink(nest); - assert(alink(nest)==null); - assert(vlink(newn)==null); - assert(alink(newn)==null); - couple_nodes(nest,newn); - if (head==null) { - assert(tlink(nest)==null); - tlink(nest) = newn; - } else { - assert(alink(head)==nest); - assert(tail_of_list(head)==tlink(nest)); - couple_nodes(newn,head); - } +static void nesting_prepend(halfword nest, halfword newn) +{ + halfword head = vlink(nest); + assert(alink(nest) == null); + assert(vlink(newn) == null); + assert(alink(newn) == null); + couple_nodes(nest, newn); + if (head == null) { + assert(tlink(nest) == null); + tlink(nest) = newn; + } else { + assert(alink(head) == nest); + assert(tail_of_list(head) == tlink(nest)); + couple_nodes(newn, head); + } } -static int -test_ligature( liginfo *lig, halfword left, halfword right ) { - if (type(left)!=glyph_node) - return 0; - assert(type(right)==glyph_node); - if (font(left)!=font(right)) return 0; - if (is_ghost(left) || is_ghost(right)) return 0; - *lig = get_ligature(font(left),character(left),character(right)); - if (is_valid_ligature(*lig)) { - return 1; - } - return 0; +static int test_ligature(liginfo * lig, halfword left, halfword right) +{ + if (type(left) != glyph_node) + return 0; + assert(type(right) == glyph_node); + if (font(left) != font(right)) + return 0; + if (is_ghost(left) || is_ghost(right)) + return 0; + *lig = get_ligature(font(left), character(left), character(right)); + if (is_valid_ligature(*lig)) { + return 1; + } + return 0; } -static int -try_ligature(halfword *frst, halfword fwd) { - halfword cur = *frst; - liginfo lig; - if (test_ligature(&lig,cur,fwd)) { - int move_after = (lig_type(lig) & 0x0C)>>2; - int keep_right = ((lig_type(lig) & 0x01) != 0); - int keep_left = ((lig_type(lig) & 0x02) != 0); - halfword newgl = raw_glyph_node(); - font(newgl) = font(cur); - character(newgl) = lig_replacement(lig); - set_is_ligature(newgl); - - /* below might not be correct in contrived border case. - * but we use it only for debugging, so ... */ - if (character(cur)<0) { - set_is_leftboundary(newgl); - } - if (character(fwd)<0) { - set_is_rightboundary(newgl); - } - if (character(cur)<0) { - if (character(fwd)<0) { - build_attribute_list(newgl); - } else { - add_node_attr_ref(node_attr(fwd)); - node_attr(newgl) = node_attr(fwd); - } - } else { - add_node_attr_ref(node_attr(cur)); - node_attr(newgl) = node_attr(cur); - } - - /* TODO/FIXME if this ligature is consists of another ligature - * we should add it's lig_ptr to the new glyphs lig_ptr (and - * cleanup the no longer needed node) LOW PRIORITY */ - /* left side */ - if (keep_left) { - halfword new_first = copy_node(cur); - lig_ptr(newgl) = new_first; - couple_nodes(cur,newgl); - if (move_after) { - move_after--; - cur = newgl; - } - } else { - halfword prev = alink(cur); - uncouple_node(cur); - lig_ptr(newgl) = cur; - assert(prev!=null); - couple_nodes(prev,newgl); - cur = newgl; /* as cur has disappeared */ - } - /* right side */ - if (keep_right) { - halfword new_second = copy_node(fwd); - /* correct, because we _know_ lig_ptr points to _one_ node */ - couple_nodes(lig_ptr(newgl),new_second); - couple_nodes(newgl,fwd); - if (move_after) { - move_after--; - cur = fwd; - } - } else { - halfword next = vlink(fwd); - uncouple_node(fwd); - /* correct, because we _know_ lig_ptr points to _one_ node */ - couple_nodes(lig_ptr(newgl),fwd); - if (next!=null) {couple_nodes(newgl,next);} - } +static int try_ligature(halfword * frst, halfword fwd) +{ + halfword cur = *frst; + liginfo lig; + if (test_ligature(&lig, cur, fwd)) { + int move_after = (lig_type(lig) & 0x0C) >> 2; + int keep_right = ((lig_type(lig) & 0x01) != 0); + int keep_left = ((lig_type(lig) & 0x02) != 0); + halfword newgl = raw_glyph_node(); + font(newgl) = font(cur); + character(newgl) = lig_replacement(lig); + set_is_ligature(newgl); + + /* below might not be correct in contrived border case. + * but we use it only for debugging, so ... */ + if (character(cur) < 0) { + set_is_leftboundary(newgl); + } + if (character(fwd) < 0) { + set_is_rightboundary(newgl); + } + if (character(cur) < 0) { + if (character(fwd) < 0) { + build_attribute_list(newgl); + } else { + add_node_attr_ref(node_attr(fwd)); + node_attr(newgl) = node_attr(fwd); + } + } else { + add_node_attr_ref(node_attr(cur)); + node_attr(newgl) = node_attr(cur); + } - /* check and return */ - /* assert(move_after==0);*/ - *frst = cur; - return 1; - } - return 0; + /* TODO/FIXME if this ligature is consists of another ligature + * we should add it's lig_ptr to the new glyphs lig_ptr (and + * cleanup the no longer needed node) LOW PRIORITY */ + /* left side */ + if (keep_left) { + halfword new_first = copy_node(cur); + lig_ptr(newgl) = new_first; + couple_nodes(cur, newgl); + if (move_after) { + move_after--; + cur = newgl; + } + } else { + halfword prev = alink(cur); + uncouple_node(cur); + lig_ptr(newgl) = cur; + assert(prev != null); + couple_nodes(prev, newgl); + cur = newgl; /* as cur has disappeared */ + } + /* right side */ + if (keep_right) { + halfword new_second = copy_node(fwd); + /* correct, because we _know_ lig_ptr points to _one_ node */ + couple_nodes(lig_ptr(newgl), new_second); + couple_nodes(newgl, fwd); + if (move_after) { + move_after--; + cur = fwd; + } + } else { + halfword next = vlink(fwd); + uncouple_node(fwd); + /* correct, because we _know_ lig_ptr points to _one_ node */ + couple_nodes(lig_ptr(newgl), fwd); + if (next != null) { + couple_nodes(newgl, next); + } + } + + /* check and return */ + /* assert(move_after==0); */ + *frst = cur; + return 1; + } + return 0; } /* there shouldn't be any ligatures here - we only add them at the end of * xxx_break in a DISC-1 - DISC-2 situation and we stop processing DISC-1 * (we continue with DISC-1's post_ and no_break */ -static halfword -handle_lig_nest(halfword root, halfword cur) { - if (cur==null) return root; - while (vlink(cur)!=null) { - halfword fwd = vlink(cur); - if (type(cur)==glyph_node && type(fwd)==glyph_node && - font(cur)==font(fwd) && try_ligature(&cur,fwd)) continue; - cur = vlink(cur); - assert(vlink(alink(cur))==cur); - } - tlink(root) = cur; - return root; +static halfword handle_lig_nest(halfword root, halfword cur) +{ + if (cur == null) + return root; + while (vlink(cur) != null) { + halfword fwd = vlink(cur); + if (type(cur) == glyph_node && type(fwd) == glyph_node && + font(cur) == font(fwd) && try_ligature(&cur, fwd)) + continue; + cur = vlink(cur); + assert(vlink(alink(cur)) == cur); + } + tlink(root) = cur; + return root; } -static halfword -handle_lig_word(halfword cur) { - halfword right=null; - - if (type(cur)==whatsit_node && subtype(cur)==cancel_boundary_node) { - halfword prev= alink(cur); - halfword fwd = vlink(cur); -/* uncouple_node(cur); */ /* not needed, it is freed */ - flush_node(cur); - if (fwd==null) { - vlink(prev) = fwd; - return prev; - } - couple_nodes(prev,fwd); - if (type(fwd)!=glyph_node) return prev; - cur = fwd; - } else if (has_left_boundary(font(cur))) { - halfword prev= alink(cur); - halfword p = new_glyph(font(cur),left_boundarychar); - couple_nodes(prev,p); - couple_nodes(p,cur); - cur = p; - } - if (has_right_boundary(font(cur))) { - right = new_glyph(font(cur),right_boundarychar); - } - - while (1) { - /* A glyph followed by ... */ - if (type(cur)==glyph_node) { - halfword fwd = vlink(cur); - if (fwd==null) { /* last character of paragraph */ - if (right==null) break; - couple_nodes(cur,right); - right = null; - continue; - } - assert(alink(fwd)==cur); - if (type(fwd)==glyph_node) { /* GLYPH - GLYPH */ - if (font(cur)!=font(fwd)) break; - if (try_ligature(&cur,fwd)) continue; - } else if (type(fwd)==disc_node) { /* GLYPH - DISC */ - - /* if a{bx}{}{y} and a+b=>B convert to {Bx}{}{ay} */ - halfword pre = vlink_pre_break(fwd); - halfword nob = vlink_no_break(fwd); - halfword next, tail; - liginfo lig; - assert_disc(fwd); - /* Check on: a{b?}{?}{?} and a+b=>B : {B?}{?}{a?}*/ - /* Check on: a{?}{?}{b?} and a+b=>B : {a?}{?}{B?} */ - if ( (pre!=null && type(pre)==glyph_node && test_ligature(&lig,cur,pre)) - || (nob!=null && type(nob)==glyph_node && test_ligature(&lig,cur,nob))) { - /* move cur from before disc, to skipped part */ - halfword prev = alink(cur); - assert(vlink(prev)==cur); - uncouple_node(cur); - couple_nodes(prev,fwd); - nesting_prepend(no_break(fwd),cur); - /* now ligature the pre_break */ - nesting_prepend(pre_break(fwd),copy_node(cur)); - /* As we have removed cur, we need to start again ... */ - cur = prev; - } - /* Check on: a{?}{?}{}b and a+b=>B : {a?}{?b}{B}*/ - next = vlink(fwd); - if (nob==null && next != null && type(next)==glyph_node - && test_ligature(&lig,cur,next)) { - /* move cur from before disc to no_break part */ - halfword prev = alink(cur); - assert(alink(next)==fwd); - assert(vlink(prev)==cur); - uncouple_node(cur); - couple_nodes(prev,fwd); - couple_nodes(no_break(fwd),cur); /* we _know_ it's empty */ - /* now copy cur the pre_break */ - nesting_prepend(pre_break(fwd),copy_node(cur)); - /* move next from after disc to no_break part */ - tail = vlink(next); - uncouple_node(next); - try_couple_nodes(fwd,tail); - couple_nodes(cur,next); /* we _know_ this works */ - tlink(no_break(fwd)) = next; /* and make sure the list is correct */ - /* now copy next to the post_break */ - nesting_append(post_break(fwd),copy_node(next)); - /* As we have removed cur, we need to start again ... */ - cur = prev; - } - /* we are finished with the pre_break */ - handle_lig_nest(pre_break(fwd),vlink_pre_break(fwd)); - } else if (type(fwd)==whatsit_node && subtype(fwd)==cancel_boundary_node) { - halfword next = vlink(fwd); - try_couple_nodes(cur,next); - flush_node(fwd); - if (right!=null) { - flush_node(right); /* Shame, didn't need it */ - /* right = null; */ /* no need, we're going to leave the loop anyway */ +static halfword handle_lig_word(halfword cur) +{ + halfword right = null; + + if (type(cur) == whatsit_node && subtype(cur) == cancel_boundary_node) { + halfword prev = alink(cur); + halfword fwd = vlink(cur); + /* uncouple_node(cur); *//* not needed, it is freed */ + flush_node(cur); + if (fwd == null) { + vlink(prev) = fwd; + return prev; } - break; - } else { /* fwd is something unknown */ - if (right==null) break; - couple_nodes(cur,right); - couple_nodes(right,fwd); - right = null; - continue; - } - /* A discretionary followed by ... */ - } else if (type(cur)==disc_node) { - assert_disc(cur); - /* If {?}{x}{?} or {?}{?}{y} then ... */ - if (vlink_no_break(cur)!=null || vlink_post_break(cur)!=null) { - halfword fwd; - halfword lists[511]; /* max 8 levels */ - - int i, max_depth=0; - lists[max_depth++] = handle_lig_nest(post_break(cur),vlink_post_break(cur)); - lists[max_depth++] = handle_lig_nest(no_break(cur),vlink_no_break(cur)); - while (1) { - if ((fwd = vlink(cur))==null) return cur; - if ( type(fwd)==glyph_node) { - halfword next; - for (i=0; i<max_depth; i++) { - liginfo lig; - halfword tail = tlink(lists[i]); - if ( tail!=null && test_ligature(&lig,tail,fwd)) - goto add_glyph_to_all; + couple_nodes(prev, fwd); + if (type(fwd) != glyph_node) + return prev; + cur = fwd; + } else if (has_left_boundary(font(cur))) { + halfword prev = alink(cur); + halfword p = new_glyph(font(cur), left_boundarychar); + couple_nodes(prev, p); + couple_nodes(p, cur); + cur = p; + } + if (has_right_boundary(font(cur))) { + right = new_glyph(font(cur), right_boundarychar); + } + + while (1) { + /* A glyph followed by ... */ + if (type(cur) == glyph_node) { + halfword fwd = vlink(cur); + if (fwd == null) { /* last character of paragraph */ + if (right == null) + break; + /* --\par prohibits use of couple_nodes here */ + try_couple_nodes(cur, right); + right = null; + continue; } - /* if we get here, nothing had a ligature, so we stop */ - break; -add_glyph_to_all: - for (i=0; i<max_depth; i++) { - halfword copy = copy_node(fwd); - halfword tail = tlink(lists[i]); - nesting_append(lists[i],copy); - if (tail==null) continue; /* first character - never a ligature */ - handle_lig_nest(lists[i],tail); + assert(alink(fwd) == cur); + if (type(fwd) == glyph_node) { /* GLYPH - GLYPH */ + if (font(cur) != font(fwd)) + break; + if (try_ligature(&cur, fwd)) + continue; + } else if (type(fwd) == disc_node) { /* GLYPH - DISC */ + + /* if a{bx}{}{y} and a+b=>B convert to {Bx}{}{ay} */ + halfword pre = vlink_pre_break(fwd); + halfword nob = vlink_no_break(fwd); + halfword next, tail; + liginfo lig; + assert_disc(fwd); + /* Check on: a{b?}{?}{?} and a+b=>B : {B?}{?}{a?} */ + /* Check on: a{?}{?}{b?} and a+b=>B : {a?}{?}{B?} */ + if ((pre != null && type(pre) == glyph_node + && test_ligature(&lig, cur, pre)) + || (nob != null && type(nob) == glyph_node + && test_ligature(&lig, cur, nob))) { + /* move cur from before disc, to skipped part */ + halfword prev = alink(cur); + assert(vlink(prev) == cur); + uncouple_node(cur); + couple_nodes(prev, fwd); + nesting_prepend(no_break(fwd), cur); + /* now ligature the pre_break */ + nesting_prepend(pre_break(fwd), copy_node(cur)); + /* As we have removed cur, we need to start again ... */ + cur = prev; + } + /* Check on: a{?}{?}{}b and a+b=>B : {a?}{?b}{B} */ + next = vlink(fwd); + if (nob == null && next != null && type(next) == glyph_node + && test_ligature(&lig, cur, next)) { + /* move cur from before disc to no_break part */ + halfword prev = alink(cur); + assert(alink(next) == fwd); + assert(vlink(prev) == cur); + uncouple_node(cur); + couple_nodes(prev, fwd); + couple_nodes(no_break(fwd), cur); /* we _know_ it's empty */ + /* now copy cur the pre_break */ + nesting_prepend(pre_break(fwd), copy_node(cur)); + /* move next from after disc to no_break part */ + tail = vlink(next); + uncouple_node(next); + try_couple_nodes(fwd, tail); + couple_nodes(cur, next); /* we _know_ this works */ + tlink(no_break(fwd)) = next; /* and make sure the list is correct */ + /* now copy next to the post_break */ + nesting_append(post_break(fwd), copy_node(next)); + /* As we have removed cur, we need to start again ... */ + cur = prev; + } + /* we are finished with the pre_break */ + handle_lig_nest(pre_break(fwd), vlink_pre_break(fwd)); + } else if (type(fwd) == whatsit_node + && subtype(fwd) == cancel_boundary_node) { + halfword next = vlink(fwd); + try_couple_nodes(cur, next); + flush_node(fwd); + if (right != null) { + flush_node(right); /* Shame, didn't need it */ + /* right = null; *//* no need, we're going to leave the loop anyway */ + } + break; + } else { /* fwd is something unknown */ + if (right == null) + break; + couple_nodes(cur, right); + couple_nodes(right, fwd); + right = null; + continue; } - next = vlink(fwd); - uncouple_node(fwd); - try_couple_nodes(cur,next); - flush_node(fwd); - } else if ( type(fwd)==disc_node) { - halfword next; - /* MAGIC WARNING - * A disc followed by a disc can have different kernings - * depending on which path is choosen, and it is impossible to - * store the possible kernings: fe {}{A}{W} {V}{}{A} - * So we _always_ add discs so only a simple path remains. */ - int m=max_depth; /* as max_depth changes in this loop */ - for (i=0; i<m; i++) { - halfword copy = copy_node(fwd); - halfword tail = tlink(lists[i]); - if (tail!=null) { - halfword prev = alink(tail); - assert(alink(tail)!=null); - uncouple_node(tail); - vlink(prev) = null; - if (prev==lists[i]) { - tlink(prev) = null; - } else { - tlink(lists[i]) = prev; + /* A discretionary followed by ... */ + } else if (type(cur) == disc_node) { + assert_disc(cur); + /* If {?}{x}{?} or {?}{?}{y} then ... */ + if (vlink_no_break(cur) != null || vlink_post_break(cur) != null) { + halfword fwd; + halfword lists[511]; /* max 8 levels */ + + int i, max_depth = 0; + lists[max_depth++] = + handle_lig_nest(post_break(cur), vlink_post_break(cur)); + lists[max_depth++] = + handle_lig_nest(no_break(cur), vlink_no_break(cur)); + while (1) { + if ((fwd = vlink(cur)) == null) + return cur; + if (type(fwd) == glyph_node) { + halfword next; + for (i = 0; i < max_depth; i++) { + liginfo lig; + halfword tail = tlink(lists[i]); + if (tail != null && test_ligature(&lig, tail, fwd)) + goto add_glyph_to_all; + } + /* if we get here, nothing had a ligature, so we stop */ + break; + add_glyph_to_all: + for (i = 0; i < max_depth; i++) { + halfword copy = copy_node(fwd); + halfword tail = tlink(lists[i]); + nesting_append(lists[i], copy); + if (tail == null) + continue; /* first character - never a ligature */ + handle_lig_nest(lists[i], tail); + } + next = vlink(fwd); + uncouple_node(fwd); + try_couple_nodes(cur, next); + flush_node(fwd); + } else if (type(fwd) == disc_node) { + halfword next; + /* MAGIC WARNING + * A disc followed by a disc can have different kernings + * depending on which path is choosen, and it is impossible to + * store the possible kernings: fe {}{A}{W} {V}{}{A} + * So we _always_ add discs so only a simple path remains. */ + int m = max_depth; /* as max_depth changes in this loop */ + for (i = 0; i < m; i++) { + halfword copy = copy_node(fwd); + halfword tail = tlink(lists[i]); + if (tail != null) { + halfword prev = alink(tail); + assert(alink(tail) != null); + uncouple_node(tail); + vlink(prev) = null; + if (prev == lists[i]) { + tlink(prev) = null; + } else { + tlink(lists[i]) = prev; + } + nesting_prepend(pre_break(copy), tail); + nesting_prepend(no_break(copy), + copy_node(tail)); + } + nesting_append(lists[i], copy); + handle_lig_nest(pre_break(copy), + vlink_pre_break(copy)); + assert(max_depth < 256); + lists[max_depth++] = + handle_lig_nest(no_break(copy), + vlink_no_break(copy)); + lists[i] = + handle_lig_nest(post_break(copy), + vlink_post_break(copy)); + } + next = vlink(fwd); + uncouple_node(fwd); + try_couple_nodes(cur, next); + flush_node(fwd); + } else { + return cur; + } } - nesting_prepend(pre_break(copy),tail); - nesting_prepend(no_break(copy),copy_node(tail)); - } - nesting_append(lists[i],copy); - handle_lig_nest(pre_break(copy),vlink_pre_break(copy)); - assert(max_depth<256); - lists[max_depth++] = handle_lig_nest(no_break(copy),vlink_no_break(copy)); - lists[i] = handle_lig_nest(post_break(copy),vlink_post_break(copy)); } - next = vlink(fwd); - uncouple_node(fwd); - try_couple_nodes(cur,next); - flush_node(fwd); - } else { + } else { /* NO GLYPH NOR DISC */ + /* fprintf(stdout,"This is a %d node\n",type(cur)); */ + /* assert(0); *//* TODO howcome there can be a glue here? */ return cur; - } } - } - } else { /* NO GLYPH NOR DISC */ - /* fprintf(stdout,"This is a %d node\n",type(cur));*/ - /* assert(0);*/ /* TODO howcome there can be a glue here? */ - return cur; - } - /* step-to-next-node */ - { - halfword prev = cur; - cur = vlink(cur); - assert(cur!=null); - assert(alink(cur)==prev); - /* alink(cur) = prev;*/ - } - } - - return cur; + /* step-to-next-node */ + { + halfword prev = cur; + /* --\par allows vlink(cur) to be null */ + cur = vlink(cur); + if (cur != null) { + assert(alink(cur) == prev); + } + } + } + + return cur; } /* return = new tail, head should be a dummy */ -halfword -handle_ligaturing(halfword head, halfword tail) { - halfword save_tail ; /* trick to allow explicit node==null tests */ - halfword cur, prev; +halfword handle_ligaturing(halfword head, halfword tail) +{ + halfword save_tail; /* trick to allow explicit node==null tests */ + halfword cur, prev; - if (vlink(head)==null) - return tail; - save_tail = vlink(tail); - vlink(tail) = null; - - /* if (fix_node_lists) */ - fix_node_list(head); - - prev = head; - cur = vlink(prev); - - while (cur!=null) { - if ( type(cur)==glyph_node || - (type(cur)==whatsit_node && subtype(cur)==cancel_boundary_node)) { - cur = handle_lig_word(cur); - } - prev = cur; - cur = vlink(cur); - assert(cur==null||alink(cur) == prev); - } - if (valid_node(save_tail)) { - try_couple_nodes(prev,save_tail); - } - return prev; + if (vlink(head) == null) + return tail; + save_tail = vlink(tail); + vlink(tail) = null; + + /* if (fix_node_lists) */ + fix_node_list(head); + + prev = head; + cur = vlink(prev); + + while (cur != null) { + if (type(cur) == glyph_node || + (type(cur) == whatsit_node + && subtype(cur) == cancel_boundary_node)) { + cur = handle_lig_word(cur); + } + prev = cur; + cur = vlink(cur); + assert(cur == null || alink(cur) == prev); + } + if (prev == null) + prev = tail; + + if (valid_node(save_tail)) { + try_couple_nodes(prev, save_tail); + } + return prev; } @@ -1547,124 +1964,128 @@ handle_ligaturing(halfword head, halfword tail) { * * ==================================================================== */ -static void -add_kern_before(halfword left, halfword right) { - if ((!is_rightghost(right)) && - font(left)==font(right) && - has_kern(font(left),character(left))) { - int k = get_kern(font(left),character(left),character(right)); - if (k!=0) { - halfword kern = new_kern(k); - halfword prev = alink(right); - assert(vlink(prev)==right); - couple_nodes(prev,kern); - couple_nodes(kern,right); - } - } +static void add_kern_before(halfword left, halfword right) +{ + if ((!is_rightghost(right)) && + font(left) == font(right) && has_kern(font(left), character(left))) { + int k = raw_get_kern(font(left), character(left), character(right)); + if (k != 0) { + halfword kern = new_kern(k); + halfword prev = alink(right); + assert(vlink(prev) == right); + couple_nodes(prev, kern); + couple_nodes(kern, right); + } + } } -static void -add_kern_after(halfword left, halfword right, halfword aft) { - if ((!is_rightghost(right)) && - font(left)==font(right) && - has_kern(font(left),character(left))) { - int k = get_kern(font(left),character(left),character(right)); - if (k!=0) { - halfword kern = new_kern(k); - halfword next = vlink(aft); - assert(next==null||alink(next)==aft); - couple_nodes(aft,kern); - try_couple_nodes(kern,next); - } - } +static void add_kern_after(halfword left, halfword right, halfword aft) +{ + if ((!is_rightghost(right)) && + font(left) == font(right) && has_kern(font(left), character(left))) { + int k = raw_get_kern(font(left), character(left), character(right)); + if (k != 0) { + halfword kern = new_kern(k); + halfword next = vlink(aft); + assert(next == null || alink(next) == aft); + couple_nodes(aft, kern); + try_couple_nodes(kern, next); + } + } } static void -do_handle_kerning (halfword root, halfword init_left, halfword init_right) { - halfword cur = vlink(root); - halfword left = null; - assert(init_left==null || type(init_left)==glyph_node); - assert(init_right==null || type(init_right)==glyph_node); - if (cur==null) { - if (init_left!=null && init_right!=null) { - add_kern_after(init_left,init_right,root); - tlink(root)=vlink(root); +do_handle_kerning(halfword root, halfword init_left, halfword init_right) +{ + halfword cur = vlink(root); + halfword left = null; + assert(init_left == null || type(init_left) == glyph_node); + assert(init_right == null || type(init_right) == glyph_node); + if (cur == null) { + if (init_left != null && init_right != null) { + add_kern_after(init_left, init_right, root); + tlink(root) = vlink(root); + } + return; } - return; - } - if (type(cur)==glyph_node) { - set_is_glyph(cur); - if (init_left!=null) - add_kern_before(init_left,cur); - left = cur; - } - while ((cur=vlink(cur))!=null) { - if (type(cur)==glyph_node) { - set_is_glyph(cur); - if (left != null) { - add_kern_before(left,cur); - if (character(left)<0 || is_ghost(left)) { - halfword prev = alink(left); - couple_nodes(prev,cur); - flush_node(left); + if (type(cur) == glyph_node) { + set_is_glyph(cur); + if (init_left != null) + add_kern_before(init_left, cur); + left = cur; + } + while ((cur = vlink(cur)) != null) { + if (type(cur) == glyph_node) { + set_is_glyph(cur); + if (left != null) { + add_kern_before(left, cur); + if (character(left) < 0 || is_ghost(left)) { + halfword prev = alink(left); + couple_nodes(prev, cur); + flush_node(left); + } + } + left = cur; + } else { + if (type(cur) == disc_node) { + halfword right = + type(vlink(cur)) == glyph_node ? vlink(cur) : null; + do_handle_kerning(pre_break(cur), left, null); + do_handle_kerning(post_break(cur), null, right); + if (vlink_post_break(cur) != null) + tlink_post_break(cur) = tail_of_list(vlink_post_break(cur)); + do_handle_kerning(no_break(cur), left, right); + if (vlink_no_break(cur) != null) + tlink_no_break(cur) = tail_of_list(vlink_no_break(cur)); /* needed? */ + } + if (left != null) { + if (character(left) < 0 || is_ghost(left)) { + halfword prev = alink(left); + couple_nodes(prev, cur); + flush_node(left); + } + left = null; + } } - } - left = cur; - } else { - if (type(cur)==disc_node) { - halfword right= type(vlink(cur))==glyph_node ? vlink(cur) : null; - do_handle_kerning(pre_break(cur),left,null); - do_handle_kerning(post_break(cur),null,right); - do_handle_kerning(no_break(cur),left,right); - } - if (left != null) { - if (character(left)<0 || is_ghost(left)) { - halfword prev = alink(left); - couple_nodes(prev,cur); - flush_node(left); + } + if (left != null) { + if (init_right != null) + add_kern_after(left, init_right, left); + if (character(left) < 0 || is_ghost(left)) { + halfword prev = alink(left); + halfword next = vlink(left); + if (next != null) { + couple_nodes(prev, next); + tlink(root) = next; + assert(vlink(next) == null); + assert(type(next) == kern_node); + } else if (prev != root) { + vlink(prev) = null; + tlink(root) = prev; + } else { + vlink(root) = null; + tlink(root) = null; + } + flush_node(left); } - left = null; - } - } - } - if (left!=null) { - if (init_right!=null) - add_kern_after(left,init_right,left); - if (character(left)<0 || is_ghost(left)) { - halfword prev = alink(left); - halfword next = vlink(left); - if (next!=null) { - couple_nodes(prev,next); - tlink(root) = next; - assert(vlink(next)==null); - assert(type(next)==kern_node); - } else if (prev!=root) { - vlink(prev) = null; - tlink(root) = prev; - } else { - vlink(root) = null; - tlink(root) = null; - } - flush_node(left); - } - } + } } -halfword -handle_kerning (halfword head, halfword tail) { - halfword save_link; - save_link = vlink(tail); - vlink(tail) = null; - tlink(head) = tail; - do_handle_kerning(head,null,null); - tail = tlink(head); - if (valid_node(save_link)) { - try_couple_nodes(tail,save_link); - } - return tail; +halfword handle_kerning(halfword head, halfword tail) +{ + halfword save_link; + save_link = vlink(tail); + vlink(tail) = null; + tlink(head) = tail; + do_handle_kerning(head, null, null); + tail = tlink(head); + if (valid_node(save_link)) { + try_couple_nodes(tail, save_link); + } + return tail; } /* ==================================================================== @@ -1674,63 +2095,63 @@ handle_kerning (halfword head, halfword tail) { * ==================================================================== */ static halfword -run_lua_ligkern_callback (halfword head, halfword tail, int callback_id){ - lua_State *L = Luas[0]; - lua_rawgeti(L,LUA_REGISTRYINDEX,callback_callbacks_id); - lua_rawgeti(L,-1, callback_id); - if (!lua_isfunction(L,-1)) { - lua_pop(L,2); - return tail; - } - nodelist_to_lua(L,head); - nodelist_to_lua(L,tail); - if (lua_pcall(L,2,1,0) != 0) { - fprintf(stdout,"error: %s\n",lua_tostring(L,-1)); - lua_pop(L,2); - lua_error(L); +run_lua_ligkern_callback(halfword head, halfword tail, int callback_id) +{ + lua_State *L = Luas; + if (!get_callback(L, callback_id)) { + lua_pop(L, 2); + return tail; + } + nodelist_to_lua(L, head); + nodelist_to_lua(L, tail); + if (lua_pcall(L, 2, 1, 0) != 0) { + fprintf(stdout, "error: %s\n", lua_tostring(L, -1)); + lua_pop(L, 2); + lua_error(L); + return tail; + } + tail = nodelist_from_lua(L); + if (fix_node_lists) + fix_node_list(head); + lua_pop(L, 2); return tail; - } - tail = nodelist_from_lua(L); - if (fix_node_lists) - fix_node_list(head); - lua_pop(L,2); - return tail; } -halfword -new_ligkern(halfword head, halfword tail) { - int callback_id = 0; +halfword new_ligkern(halfword head, halfword tail) +{ + int callback_id = 0; - assert(head!=null); - if (vlink(head)==null) - return tail; + assert(head != null); + if (vlink(head) == null) + return tail; - callback_id = callback_defined(ligaturing_callback); - if (callback_id>0) { - tail = run_lua_ligkern_callback(head,tail,callback_id); - if (tail==null) tail = tail_of_list(head); - } else { - tail = handle_ligaturing(head,tail); - } - - callback_id = callback_defined(kerning_callback); - if (callback_id>0) { - tail = run_lua_ligkern_callback(head,tail,callback_id); - if (tail==null) tail = tail_of_list(head); - } else { - halfword nest = new_node(nesting_node,1); - halfword cur = vlink(head); - halfword aft = vlink(tail); - couple_nodes(nest,cur); - tlink(nest)=tail; - vlink(tail)=null; - do_handle_kerning(nest,null,null); - couple_nodes(head,vlink(nest)); - tail = tlink(nest); - try_couple_nodes(tail,aft); - flush_node(nest); - } - return tail; -} + callback_id = callback_defined(ligaturing_callback); + if (callback_id > 0) { + tail = run_lua_ligkern_callback(head, tail, callback_id); + if (tail == null) + tail = tail_of_list(head); + } else { + tail = handle_ligaturing(head, tail); + } + callback_id = callback_defined(kerning_callback); + if (callback_id > 0) { + tail = run_lua_ligkern_callback(head, tail, callback_id); + if (tail == null) + tail = tail_of_list(head); + } else { + halfword nest = new_node(nesting_node, 1); + halfword cur = vlink(head); + halfword aft = vlink(tail); + couple_nodes(nest, cur); + tlink(nest) = tail; + vlink(tail) = null; + do_handle_kerning(nest, null, null); + couple_nodes(head, vlink(nest)); + tail = tlink(nest); + try_couple_nodes(tail, aft); + flush_node(nest); + } + return tail; +} diff --git a/Build/source/texk/web2c/luatexdir/font/luatexfont.h b/Build/source/texk/web2c/luatexdir/font/luatexfont.h new file mode 100644 index 00000000000..ceee8bf69f3 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/font/luatexfont.h @@ -0,0 +1,67 @@ +/* luatexfont.h General font functions + + Copyright 2008 Taco Hoekwater <taco@luatex.org> + + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ + +/* $Id: luatexfont.h 1783 2009-01-18 12:51:01Z oneiros $ */ + +#ifndef LUATEXFONT_H +# define LUATEXFONT_H 1 + +# include "ptexlib.h" +# include "sfnt.h" + +/* texfont.c */ +extern charinfo *copy_charinfo(charinfo * ci); + +/* tounicode.c */ +extern integer write_cid_tounicode(fo_entry * fo, internalfontnumber f); + +/* vfpacket.c */ +extern void replace_packet_fonts(internal_font_number f, integer * old_fontid, + integer * new_fontid, int count); +extern integer *packet_local_fonts(internal_font_number f, integer * num); + +/* writeccf.c */ +extern void writetype1w(fd_entry * fd); + +/* writetype0.c */ +extern void writetype0(fd_entry * fd); + +/* writetype2.c */ +extern void writetype2(fd_entry * fd); +extern unsigned long cidtogid_obj; +extern pdf_obj *pdf_new_stream(void); +extern void pdf_add_stream(pdf_obj * stream, unsigned char *buf, long len); +extern void pdf_release_obj(pdf_obj * stream); + +/* writet3.c */ +extern FILE *t3_file; + +extern unsigned char *t3_buffer; +extern integer t3_size; +extern integer t3_curbyte; + +# define t3_read_file() readbinfile(t3_file,&t3_buffer,&t3_size) +# define t3_close() xfclose(t3_file, cur_file_name) +# define t3_getchar() t3_buffer[t3_curbyte++] +# define t3_eof() (t3_curbyte>t3_size) + +# define t3_prefix(s) (!strncmp(t3_line_array, s, strlen(s))) +# define t3_putchar(c) pdfout(c) + +#endif diff --git a/Build/source/texk/web2c/luatexdir/font/macnames.c b/Build/source/texk/web2c/luatexdir/font/macnames.c index 941f087ef56..ae7720cc8dd 100644 --- a/Build/source/texk/web2c/luatexdir/font/macnames.c +++ b/Build/source/texk/web2c/luatexdir/font/macnames.c @@ -1,24 +1,25 @@ -/* -Copyright (c) 1996-2002 Han The Thanh, <thanh@pdftex.org> +/* macnames.c + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -This file is part of pdfTeX. + This file is part of LuaTeX. -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ -$Id: macnames.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ +static const char __svn_version[] = + "$Id: macnames.c 1223 2008-05-02 13:39:55Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/macnames.c $"; const char notdef[] = ".notdef"; diff --git a/Build/source/texk/web2c/luatexdir/font/mapfile.c b/Build/source/texk/web2c/luatexdir/font/mapfile.c index 1c444e5c1d4..c97cdf59782 100644 --- a/Build/source/texk/web2c/luatexdir/font/mapfile.c +++ b/Build/source/texk/web2c/luatexdir/font/mapfile.c @@ -1,25 +1,22 @@ -/* -Copyright (c) 1996-2006 Han The Thanh, <thanh@pdftex.org> - -This file is part of pdfTeX. +/* mapfile.c + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + This file is part of LuaTeX. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -$Id: mapfile.c 1013 2008-02-14 00:09:02Z oneiros $ - -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include <math.h> #include "ptexlib.h" @@ -28,6 +25,9 @@ $Id: mapfile.c 1013 2008-02-14 00:09:02Z oneiros $ #include <string.h> #include "luatex-api.h" +static const char _svn_version[] = + "$Id: mapfile.c 1870 2009-02-19 10:03:13Z taco $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/mapfile.c $"; + #define FM_BUF_SIZE 1024 static FILE *fm_file; @@ -37,12 +37,12 @@ static integer fm_size = 0; static integer fm_curbyte = 0; #define fm_open() \ - open_input (&fm_file, kpse_fontmap_format, FOPEN_RBIN_MODE) + (fm_file = fopen((char *) nameoffile + 1, FOPEN_RBIN_MODE)) #define fm_read_file() \ readbinfile(fm_file,&fm_buffer,&fm_size) #define fm_close() xfclose(fm_file, cur_file_name) #define fm_getchar() fm_buffer[fm_curbyte++] -#define fm_eof() (fm_curbyte>=fm_size) +#define fm_eof() (fm_curbyte>fm_size) typedef enum { FM_DUPIGNORE, FM_REPLACE, FM_DELETE } updatemode; typedef enum { MAPFILE, MAPLINE } maptype; @@ -79,7 +79,7 @@ fm_entry *new_fm_entry(void) fm->tfm_name = NULL; fm->sfd_name = NULL; fm->ps_name = NULL; - fm->fd_flags = 4; + fm->fd_flags = FD_FLAGS_NOT_SET_IN_MAPLINE; fm->ff_name = NULL; fm->encname = NULL; fm->type = 0; @@ -102,23 +102,23 @@ void delete_fm_entry(fm_entry * fm) xfree(fm); } -static ff_entry *new_ff_entry (void) +static ff_entry *new_ff_entry(void) { ff_entry *ff; - ff = xtalloc (1, ff_entry); + ff = xtalloc(1, ff_entry); ff->ff_name = NULL; ff->ff_path = NULL; return ff; } -static void delete_ff_entry (ff_entry * ff) +static void delete_ff_entry(ff_entry * ff) { - xfree (ff->ff_name); - xfree (ff->ff_path); - xfree (ff); + xfree(ff->ff_name); + xfree(ff->ff_path); + xfree(ff); } -static fm_entry *dummy_fm_entry () +static fm_entry *dummy_fm_entry() { static const fm_entry const_fm_entry; return (fm_entry *) & const_fm_entry; @@ -133,10 +133,10 @@ struct avl_table *encname_tree = NULL; /* AVL sort fm_entry into tfm_tree by tfm_name */ -static int comp_fm_entry_tfm (const void *pa, const void *pb, void *p) +static int comp_fm_entry_tfm(const void *pa, const void *pb, void *p) { - return strcmp (((const fm_entry *) pa)->tfm_name, - ((const fm_entry *) pb)->tfm_name); + return strcmp(((const fm_entry *) pa)->tfm_name, + ((const fm_entry *) pb)->tfm_name); } /* AVL sort fm_entry into ps_tree by ps_name, slant, and extend */ @@ -155,13 +155,13 @@ static int comp_fm_entry_ps(const void *pa, const void *pb, void *p) /* AVL sort ff_entry into ff_tree by ff_name */ -static int comp_ff_entry (const void *pa, const void *pb, void *p) +static int comp_ff_entry(const void *pa, const void *pb, void *p) { - return strcmp (((const ff_entry *) pa)->ff_name, - ((const ff_entry *) pb)->ff_name); + return strcmp(((const ff_entry *) pa)->ff_name, + ((const ff_entry *) pb)->ff_name); } -static void create_avl_trees () +static void create_avl_trees() { assert(tfm_tree == NULL); tfm_tree = avl_create(comp_fm_entry_tfm, NULL, &avl_xallocator); @@ -354,9 +354,9 @@ int check_fm_entry(fm_entry * fm, boolean warn) } /**********************************************************************/ -/* returns true if s is one of the 14 std. font names; speed-trimmed. */ +/* returns the font number if s is one of the 14 std. font names, -1 otherwise; speed-trimmed. */ -boolean check_std_t1font(char *s) +int check_std_t1font(char *s) { static const char *std_t1font_names[] = { "Courier", /* 0:7 */ @@ -378,10 +378,12 @@ boolean check_std_t1font(char *s) { -1, -1, -1, -1, -1, -1, 8, 0, -1, 4, 10, 9, -1, -1, 5, 2, 12, 6, -1, 3, -1, 7 }; - const size_t n = strlen(s); + size_t n; int k = -1; + assert(s != NULL); + n = strlen(s); if (n > 21) - return false; + return -1; if (n == 12) { /* three names have length 12 */ switch (*s) { case 'C': @@ -394,15 +396,16 @@ boolean check_std_t1font(char *s) k = 13; /* ZapfDingbats */ break; default: - return false; + return -1; } } else k = index[n]; if (k > -1 && !strcmp(std_t1font_names[k], s)) - return true; - return false; + return k; + return -1; }; + /**********************************************************************/ static void fm_scan_line() @@ -415,11 +418,17 @@ static void fm_scan_line() switch (mitem->type) { case MAPFILE: p = fm_line; - do { - c = fm_getchar(); - append_char_to_buf(c, p, fm_line, FM_BUF_SIZE); + while (!fm_eof()) { + if (fm_curbyte == fm_size) { + fm_curbyte++; + c = 10; + } else { + c = fm_getchar(); + } + append_char_to_buf(c, p, fm_line, FM_BUF_SIZE); + if (c == 10) + break; } - while (c != 10 && !fm_eof()); *(--p) = '\0'; r = fm_line; break; @@ -532,9 +541,9 @@ static void fm_scan_line() } } done: - if (fm->ps_name != NULL && check_std_t1font(fm->ps_name)) + if (fm->ps_name != NULL && (check_std_t1font(fm->ps_name) >= 0)) set_std_t1font(fm); - if (is_fontfile(fm)) { + if (is_fontfile(fm) && strlen(fm_fontfile(fm)) > 3) { if (strcasecmp(strend(fm_fontfile(fm)) - 4, ".ttf") == 0) set_truetype(fm); else if (strcasecmp(strend(fm_fontfile(fm)) - 4, ".otf") == 0) @@ -560,83 +569,95 @@ static void fm_scan_line() /**********************************************************************/ -void fm_read_info () +void fm_read_info() { int callback_id; int file_opened = 0; - char *ftemp = NULL; + char *ftemp = NULL; if (tfm_tree == NULL) - create_avl_trees (); + create_avl_trees(); if (mitem->line == NULL) /* nothing to do */ return; mitem->lineno = 1; switch (mitem->type) { case MAPFILE: - set_cur_file_name (mitem->line); - if (fm_buffer!=NULL) { - xfree(fm_buffer); - fm_buffer=NULL; - } - fm_curbyte=0; - fm_size=0; - callback_id=callback_defined(find_map_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->S",(char *)(nameoffile+1),&ftemp)) { - if(ftemp!=NULL&&strlen(ftemp)) { - free(nameoffile); - namelength = strlen(ftemp); - nameoffile = xmalloc(namelength+2); - strcpy((char *)(nameoffile+1),ftemp); - free(ftemp); - } - } - } - callback_id=callback_defined(read_map_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->bSd",(char *)(nameoffile+1), - &file_opened, &fm_buffer,&fm_size)) { - if(file_opened) { - if (fm_size>0) { - cur_file_name = (char *) nameoffile + 1; - if (tracefilenames) - tex_printf ("{%s", cur_file_name); - while (!fm_eof ()) { - fm_scan_line (); - mitem->lineno++; - } - if (tracefilenames) - tex_printf ("}"); - fm_file = NULL; - } - } else { - pdftex_warn ("cannot open font map file"); - } - } else { - pdftex_warn ("cannot open font map file"); - } - } else { - if (!fm_open ()) { - pdftex_warn ("cannot open font map file"); - } else { - fm_read_file(); - cur_file_name = (char *) nameoffile + 1; - tex_printf ("{%s", cur_file_name); - while (!fm_eof ()) { - fm_scan_line (); - mitem->lineno++; - } - fm_close (); - tex_printf ("}"); - fm_file = NULL; - } - } - break; + set_cur_file_name(mitem->line); + if (fm_buffer != NULL) { + xfree(fm_buffer); + fm_buffer = NULL; + } + fm_curbyte = 0; + fm_size = 0; + callback_id = callback_defined(find_map_file_callback); + if (callback_id > 0) { + if (run_callback + (callback_id, "S->S", (char *) (nameoffile + 1), &ftemp)) { + if (ftemp != NULL && strlen(ftemp)) { + free(nameoffile); + namelength = strlen(ftemp); + nameoffile = xmalloc(namelength + 2); + strcpy((char *) (nameoffile + 1), ftemp); + free(ftemp); + } + } + } else { + ftemp = + kpse_find_file((char *) (nameoffile + 1), kpse_fontmap_format, + 0); + if (ftemp != NULL) { + free(nameoffile); + namelength = strlen(ftemp); + nameoffile = xmalloc(namelength + 2); + strcpy((char *) (nameoffile + 1), ftemp); + free(ftemp); + } + } + callback_id = callback_defined(read_map_file_callback); + if (callback_id > 0) { + if (run_callback(callback_id, "S->bSd", (char *) (nameoffile + 1), + &file_opened, &fm_buffer, &fm_size)) { + if (file_opened) { + if (fm_size > 0) { + cur_file_name = (char *) nameoffile + 1; + if (tracefilenames) + tex_printf("{%s", cur_file_name); + while (!fm_eof()) { + fm_scan_line(); + mitem->lineno++; + } + if (tracefilenames) + tex_printf("}"); + fm_file = NULL; + } + } else { + pdftex_warn("cannot open font map file"); + } + } else { + pdftex_warn("cannot open font map file"); + } + } else { + if (!fm_open()) { + pdftex_warn("cannot open font map file"); + } else { + fm_read_file(); + cur_file_name = (char *) nameoffile + 1; + tex_printf("{%s", cur_file_name); + while (!fm_eof()) { + fm_scan_line(); + mitem->lineno++; + } + fm_close(); + tex_printf("}"); + fm_file = NULL; + } + } + break; case MAPLINE: - cur_file_name = NULL; /* makes pdftex_warn() shorter */ - fm_scan_line (); - break; + cur_file_name = NULL; /* makes pdftex_warn() shorter */ + fm_scan_line(); + break; default: - assert (0); + assert(0); } mitem->line = NULL; /* done with this line */ cur_file_name = NULL; @@ -667,10 +688,10 @@ static fm_entry_ptr fmlookup(internalfontnumber f) boolean hasfmentry(internalfontnumber f) { - if (font_map(f) == NULL) - set_font_map(f, (fm_entry_ptr) fmlookup(f)); - assert(font_map(f) != NULL); - return font_map(f) != (fm_entry_ptr) dummy_fm_entry(); + if (font_map(f) == NULL) + set_font_map(f, (fm_entry_ptr) fmlookup(f)); + assert(font_map(f) != NULL); + return font_map(f) != (fm_entry_ptr) dummy_fm_entry(); } /* check whether a map entry is valid for font replacement */ @@ -859,7 +880,7 @@ void pdf_init_map_file(string map_name) mitem = xtalloc(1, mapitem); mitem->mode = FM_DUPIGNORE; mitem->type = MAPFILE; - mitem->line = xstrdup(map_name); + mitem->line = map_name; } @@ -881,7 +902,7 @@ ff_entry *check_ff_exist(char *ff_name, boolean is_tt) ff_entry tmp; void **aa; int callback_id; - char *filepath=NULL; + char *filepath = NULL; assert(ff_name != NULL); tmp.ff_name = ff_name; @@ -890,27 +911,26 @@ ff_entry *check_ff_exist(char *ff_name, boolean is_tt) ff = new_ff_entry(); ff->ff_name = xstrdup(ff_name); if (is_tt) { - callback_id=callback_defined(find_truetype_file_callback); - if (callback_id>0) { - run_callback(callback_id,"S->S",ff_name,&filepath); - if (filepath && strlen(filepath)==0) - filepath=NULL; - ff->ff_path = filepath; - } else { - ff->ff_path = kpse_find_file (ff_name, kpse_truetype_format, 0); - } - } - else { - callback_id=callback_defined(find_type1_file_callback); - if (callback_id>0) { - run_callback(callback_id,"S->S",ff_name,&filepath); - if (filepath && strlen(filepath)==0) - filepath=NULL; - ff->ff_path = filepath; - } else { - ff->ff_path = kpse_find_file (ff_name, kpse_type1_format, 0); - } - } + callback_id = callback_defined(find_truetype_file_callback); + if (callback_id > 0) { + run_callback(callback_id, "S->S", ff_name, &filepath); + if (filepath && strlen(filepath) == 0) + filepath = NULL; + ff->ff_path = filepath; + } else { + ff->ff_path = kpse_find_file(ff_name, kpse_truetype_format, 0); + } + } else { + callback_id = callback_defined(find_type1_file_callback); + if (callback_id > 0) { + run_callback(callback_id, "S->S", ff_name, &filepath); + if (filepath && strlen(filepath) == 0) + filepath = NULL; + ff->ff_path = filepath; + } else { + ff->ff_path = kpse_find_file(ff_name, kpse_type1_format, 0); + } + } aa = avl_probe(ff_tree, ff); assert(aa != NULL); } diff --git a/Build/source/texk/web2c/luatexdir/font/pkin.c b/Build/source/texk/web2c/luatexdir/font/pkin.c index 5067d6dbd66..99f64f29c11 100644 --- a/Build/source/texk/web2c/luatexdir/font/pkin.c +++ b/Build/source/texk/web2c/luatexdir/font/pkin.c @@ -1,24 +1,22 @@ -/* -Copyright (c) 1996-2002 Han The Thanh, <thanh@pdftex.org> - -This file is part of pdfTeX. +/* pkin.c + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + This file is part of LuaTeX. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -$Id: pkin.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ /* * NAME @@ -44,25 +42,21 @@ $Id: pkin.c 1013 2008-02-14 00:09:02Z oneiros $ */ #include "ptexlib.h" +#include "luatexfont.h" + +static const char _svn_version[] = + "$Id: pkin.c 1712 2009-01-02 10:54:55Z taco $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/pkin.c $"; /* * Now we have some routines to get stuff from the pk file. pkbyte returns * the next byte from the pk file. */ - -/* -static FILE *pkfile ; -*/ - -extern FILE *t3_file; -#define pkfile t3_file - static shalfword pkbyte(void) { register shalfword i; - - if ((i = xgetc(pkfile)) == EOF) + i = t3_getchar(); + if (t3_eof()) pdftex_fail("unexpected eof in pk file"); return (i); } diff --git a/Build/source/texk/web2c/luatexdir/font/sfnt.c b/Build/source/texk/web2c/luatexdir/font/sfnt.c index 95453a531a0..b705ef7240b 100644 --- a/Build/source/texk/web2c/luatexdir/font/sfnt.c +++ b/Build/source/texk/web2c/luatexdir/font/sfnt.c @@ -1,114 +1,110 @@ -/* $Header: /home/cvsroot/dvipdfmx/src/sfnt.c,v 1.12 2004/09/11 14:50:29 hirata Exp $ +/* sfnt.c - This is dvipdfmx, an eXtended version of dvipdfm by Mark A. Wicks. + Copyright 2002 by Jin-Hwan Cho and Shunsaku Hirata, + the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> - Copyright (C) 2002 by Jin-Hwan Cho and Shunsaku Hirata, - the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. -*/ + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ /* Based on dvipdfmx-0.13.2c */ #if HAVE_CONFIG_H -#include "config.h" -#endif /* HAVE_CONFIG_H_ */ +# include "config.h" +#endif /* HAVE_CONFIG_H_ */ #include <string.h> #ifndef pdfTeX -#include "system.h" +# include "system.h" -#include "error.h" -#include "mem.h" -#include "mfileio.h" +# include "error.h" +# include "mem.h" +# include "mfileio.h" #else -extern void pdftex_fail (const char *fmt, ...); /* utils.c */ +# include "ptexlib.h" #endif #include "sfnt.h" +static const char _svn_version[] = + "$Id: sfnt.c 1592 2008-11-28 13:23:51Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/sfnt.c $"; + #ifdef XETEX -UNSIGNED_BYTE -ft_unsigned_byte(sfnt* f) +UNSIGNED_BYTE ft_unsigned_byte(sfnt * f) { - unsigned char byte; - unsigned long length = 1; - - if (FT_Load_Sfnt_Table(f->ft_face, 0, f->loc, &byte, &length) != 0) - TT_ERROR("sfnt: Freetype failure..."); - f->loc += 1; - - return byte; + unsigned char byte; + unsigned long length = 1; + + if (FT_Load_Sfnt_Table(f->ft_face, 0, f->loc, &byte, &length) != 0) + TT_ERROR("sfnt: Freetype failure..."); + f->loc += 1; + + return byte; } -SIGNED_BYTE -ft_signed_byte(sfnt* f) +SIGNED_BYTE ft_signed_byte(sfnt * f) { - int b = ft_unsigned_byte(f); - if (b >= 0x80) - b -= 0x100; - return (SIGNED_BYTE)b; + int b = ft_unsigned_byte(f); + if (b >= 0x80) + b -= 0x100; + return (SIGNED_BYTE) b; } -UNSIGNED_PAIR -ft_unsigned_pair(sfnt* f) +UNSIGNED_PAIR ft_unsigned_pair(sfnt * f) { - unsigned char buf[2]; - unsigned long length = 2; - - if (FT_Load_Sfnt_Table(f->ft_face, 0, f->loc, buf, &length) != 0) - TT_ERROR("sfnt: Freetype failure..."); - f->loc += 2; - - return (UNSIGNED_PAIR)((unsigned)buf[0] << 8) + buf[1]; + unsigned char buf[2]; + unsigned long length = 2; + + if (FT_Load_Sfnt_Table(f->ft_face, 0, f->loc, buf, &length) != 0) + TT_ERROR("sfnt: Freetype failure..."); + f->loc += 2; + + return (UNSIGNED_PAIR) ((unsigned) buf[0] << 8) + buf[1]; } -SIGNED_PAIR -ft_signed_pair(sfnt* f) +SIGNED_PAIR ft_signed_pair(sfnt * f) { - int p = ft_unsigned_pair(f); - if (p >= 0x8000U) - p -= 0x10000U; - - return (SIGNED_PAIR)p; + int p = ft_unsigned_pair(f); + if (p >= 0x8000U) + p -= 0x10000U; + + return (SIGNED_PAIR) p; } -UNSIGNED_QUAD -ft_unsigned_quad(sfnt* f) +UNSIGNED_QUAD ft_unsigned_quad(sfnt * f) { - unsigned char buf[4]; - unsigned long length = 4; + unsigned char buf[4]; + unsigned long length = 4; - if (FT_Load_Sfnt_Table(f->ft_face, 0, f->loc, buf, &length) != 0) - TT_ERROR("sfnt: Freetype failure..."); - f->loc += 4; + if (FT_Load_Sfnt_Table(f->ft_face, 0, f->loc, buf, &length) != 0) + TT_ERROR("sfnt: Freetype failure..."); + f->loc += 4; - return ((unsigned long)buf[0] << 24) + ((unsigned long)buf[1] << 16) - + ((unsigned long)buf[2] << 8) + (unsigned long)buf[3]; + return ((unsigned long) buf[0] << 24) + ((unsigned long) buf[1] << 16) + + ((unsigned long) buf[2] << 8) + (unsigned long) buf[3]; } -unsigned long -ft_read(unsigned char* buf, unsigned long len, sfnt* f) +unsigned long ft_read(unsigned char *buf, unsigned long len, sfnt * f) { - unsigned long length = len; - if (FT_Load_Sfnt_Table(f->ft_face, 0, f->loc, buf, &length) != 0) - TT_ERROR("sfnt: Freetype failure..."); - f->loc += len; + unsigned long length = len; + if (FT_Load_Sfnt_Table(f->ft_face, 0, f->loc, buf, &length) != 0) + TT_ERROR("sfnt: Freetype failure..."); + f->loc += len; - return length; + return length; } #endif @@ -122,398 +118,381 @@ ft_read(unsigned char* buf, unsigned long len, sfnt* f) * `ttcf': TrueType Collection */ #define SFNT_TRUETYPE 0x00010000UL -#define SFNT_MAC_TRUE 0x74727565UL +#define SFNT_MAC_TRUE 0x74727565UL #define SFNT_OPENTYPE 0x00010000UL #define SFNT_POSTSCRIPT 0x4f54544fUL #define SFNT_TTC 0x74746366UL #ifdef XETEX -sfnt * -sfnt_open (FT_Face face, int accept_types) +sfnt *sfnt_open(FT_Face face, int accept_types) { - sfnt *sfont; - ULONG type; - - if (!face || !FT_IS_SFNT(face)) - return NULL; - - sfont = NEW(1, sfnt); - sfont->ft_face = face; - sfont->loc = 0; - sfont->type = 0; - - type = sfnt_get_ulong(sfont); - - if (type == SFNT_TRUETYPE || type == SFNT_MAC_TRUE) { - sfont->type = SFNT_TYPE_TRUETYPE; - } else if (type == SFNT_OPENTYPE) { - sfont->type = SFNT_TYPE_OPENTYPE; - } else if (type == SFNT_POSTSCRIPT) { - sfont->type = SFNT_TYPE_POSTSCRIPT; - } else if (type == SFNT_TTC) { - sfont->type = SFNT_TYPE_TTC; - } - - if ((sfont->type & accept_types) == 0) { - RELEASE(sfont); - return NULL; - } - - sfont->loc = 0; - - sfont->directory = NULL; - - return sfont; + sfnt *sfont; + ULONG type; + + if (!face || !FT_IS_SFNT(face)) + return NULL; + + sfont = NEW(1, sfnt); + sfont->ft_face = face; + sfont->loc = 0; + sfont->type = 0; + + type = sfnt_get_ulong(sfont); + + if (type == SFNT_TRUETYPE || type == SFNT_MAC_TRUE) { + sfont->type = SFNT_TYPE_TRUETYPE; + } else if (type == SFNT_OPENTYPE) { + sfont->type = SFNT_TYPE_OPENTYPE; + } else if (type == SFNT_POSTSCRIPT) { + sfont->type = SFNT_TYPE_POSTSCRIPT; + } else if (type == SFNT_TTC) { + sfont->type = SFNT_TYPE_TTC; + } + + if ((sfont->type & accept_types) == 0) { + RELEASE(sfont); + return NULL; + } + + sfont->loc = 0; + + sfont->directory = NULL; + + return sfont; } -#else /* not XETEX */ -#ifdef pdfTeX -sfnt * -sfnt_open (unsigned char *buffer, integer buflen) +#else /* not XETEX */ +# ifdef pdfTeX +sfnt *sfnt_open(unsigned char *buffer, integer buflen) { - sfnt *sfont; - ULONG type; - - sfont = xmalloc(sizeof(sfnt)); - sfont->loc = 0; - sfont->buffer = buffer; - sfont->buflen = buflen; - - type = sfnt_get_ulong(sfont); - - if (type == SFNT_TRUETYPE || type == SFNT_MAC_TRUE) { - sfont->type = SFNT_TYPE_TRUETYPE; - } else if (type == SFNT_OPENTYPE) { - sfont->type = SFNT_TYPE_OPENTYPE; - } else if (type == SFNT_POSTSCRIPT) { - sfont->type = SFNT_TYPE_POSTSCRIPT; - } else if (type == SFNT_TTC) { - sfont->type = SFNT_TYPE_TTC; - } - - sfont->loc=0; - sfont->directory = NULL; - return sfont; + sfnt *sfont; + ULONG type; + + sfont = xmalloc(sizeof(sfnt)); + sfont->loc = 0; + sfont->buffer = buffer; + sfont->buflen = buflen; + + type = sfnt_get_ulong(sfont); + + if (type == SFNT_TRUETYPE || type == SFNT_MAC_TRUE) { + sfont->type = SFNT_TYPE_TRUETYPE; + } else if (type == SFNT_OPENTYPE) { + sfont->type = SFNT_TYPE_OPENTYPE; + } else if (type == SFNT_POSTSCRIPT) { + sfont->type = SFNT_TYPE_POSTSCRIPT; + } else if (type == SFNT_TTC) { + sfont->type = SFNT_TYPE_TTC; + } + + sfont->loc = 0; + sfont->directory = NULL; + return sfont; } -#else -sfnt * -sfnt_open (FILE *fp) +# else +sfnt *sfnt_open(FILE * fp) { - sfnt *sfont; - ULONG type; + sfnt *sfont; + ULONG type; - ASSERT(fp); + ASSERT(fp); - rewind(fp); + rewind(fp); - sfont = NEW(1, sfnt); + sfont = NEW(1, sfnt); - sfont->stream = fp; + sfont->stream = fp; - type = sfnt_get_ulong(sfont); + type = sfnt_get_ulong(sfont); - if (type == SFNT_TRUETYPE || type == SFNT_MAC_TRUE) { - sfont->type = SFNT_TYPE_TRUETYPE; - } else if (type == SFNT_OPENTYPE) { - sfont->type = SFNT_TYPE_OPENTYPE; - } else if (type == SFNT_POSTSCRIPT) { - sfont->type = SFNT_TYPE_POSTSCRIPT; - } else if (type == SFNT_TTC) { - sfont->type = SFNT_TYPE_TTC; - } + if (type == SFNT_TRUETYPE || type == SFNT_MAC_TRUE) { + sfont->type = SFNT_TYPE_TRUETYPE; + } else if (type == SFNT_OPENTYPE) { + sfont->type = SFNT_TYPE_OPENTYPE; + } else if (type == SFNT_POSTSCRIPT) { + sfont->type = SFNT_TYPE_POSTSCRIPT; + } else if (type == SFNT_TTC) { + sfont->type = SFNT_TYPE_TTC; + } - rewind(sfont->stream); + rewind(sfont->stream); - sfont->directory = NULL; + sfont->directory = NULL; - return sfont; + return sfont; } -#endif +# endif #endif -static void -release_directory (struct sfnt_table_directory *td) +static void release_directory(struct sfnt_table_directory *td) { - long i; - - if (td) { - if (td->tables) { - for (i = 0; i < td->num_tables; i++) { - if (td->tables[i].data) - RELEASE(td->tables[i].data); - } - RELEASE(td->tables); + long i; + + if (td) { + if (td->tables) { + for (i = 0; i < td->num_tables; i++) { + if (td->tables[i].data) + RELEASE(td->tables[i].data); + } + RELEASE(td->tables); + } + if (td->flags) + RELEASE(td->flags); + RELEASE(td); } - if (td->flags) - RELEASE(td->flags); - RELEASE(td); - } - return; + return; } -void -sfnt_close (sfnt *sfont) +void sfnt_close(sfnt * sfont) { - if (sfont) { - if (sfont->directory) - release_directory(sfont->directory); - RELEASE(sfont); - } + if (sfont) { + if (sfont->directory) + release_directory(sfont->directory); + RELEASE(sfont); + } - return; + return; } -int -put_big_endian (void *s, LONG q, int n) +int put_big_endian(void *s, LONG q, int n) { - int i; - char *p; + int i; + char *p; - p = (char *) s; - for (i = n - 1; i >= 0; i--) { - p[i] = (char) (q & 0xff); - q >>= 8; - } + p = (char *) s; + for (i = n - 1; i >= 0; i--) { + p[i] = (char) (q & 0xff); + q >>= 8; + } - return n; + return n; } /* Convert four-byte number to big endianess * in a machine independent way. */ -static void -convert_tag (char *tag, unsigned long u_tag) +static void convert_tag(char *tag, unsigned long u_tag) { - int i; + int i; - for (i = 3; i >= 0; i--) { - tag[i] = (char) (u_tag % 256); - u_tag /= 256; - } + for (i = 3; i >= 0; i--) { + tag[i] = (char) (u_tag % 256); + u_tag /= 256; + } - return; + return; } /* * Computes the max power of 2 <= n */ -static unsigned -max2floor (unsigned n) +static unsigned max2floor(unsigned n) { - int val = 1; + int val = 1; - while (n > 1) { - n /= 2; - val *= 2; - } + while (n > 1) { + n /= 2; + val *= 2; + } - return val; + return val; } /* * Computes the log2 of the max power of 2 <= n */ -static unsigned -log2floor (unsigned n) +static unsigned log2floor(unsigned n) { - unsigned val = 0; + unsigned val = 0; - while (n > 1) { - n /= 2; - val++; - } + while (n > 1) { + n /= 2; + val++; + } - return val; + return val; } -static ULONG -sfnt_calc_checksum(void *data, ULONG length) +static ULONG sfnt_calc_checksum(void *data, ULONG length) { - ULONG chksum = 0; - BYTE *p, *endptr; - int count = 0; - - p = (BYTE *) data; - endptr = p + length; - while (p < endptr) { - chksum += (p[0] << (8 * ( 3 - count))); - count = ((count + 1) & 3); - p++; - } - - return chksum; + ULONG chksum = 0; + BYTE *p, *endptr; + int count = 0; + + p = (BYTE *) data; + endptr = p + length; + while (p < endptr) { + chksum += (p[0] << (8 * (3 - count))); + count = ((count + 1) & 3); + p++; + } + + return chksum; } -static int -find_table_index (struct sfnt_table_directory *td, const char *tag) +static int find_table_index(struct sfnt_table_directory *td, const char *tag) { - int idx; + int idx; - if (!td) - return -1; + if (!td) + return -1; - for (idx = 0; idx < td->num_tables; idx++) { - if (!memcmp(td->tables[idx].tag, tag, 4)) - return idx; - } + for (idx = 0; idx < td->num_tables; idx++) { + if (!memcmp(td->tables[idx].tag, tag, 4)) + return idx; + } - return -1; + return -1; } -void -sfnt_set_table (sfnt *sfont, const char *tag, void *data, ULONG length) +void sfnt_set_table(sfnt * sfont, const char *tag, void *data, ULONG length) { - struct sfnt_table_directory *td; - int idx; + struct sfnt_table_directory *td; + int idx; - ASSERT(sfont); + ASSERT(sfont); - td = sfont->directory; - idx = find_table_index(td, tag); + td = sfont->directory; + idx = find_table_index(td, tag); - if (idx < 0) { - idx = td->num_tables; - td->num_tables++; - td->tables = RENEW(td->tables, td->num_tables, struct sfnt_table); - memcpy(td->tables[idx].tag, tag, 4); - } + if (idx < 0) { + idx = td->num_tables; + td->num_tables++; + td->tables = RENEW(td->tables, td->num_tables, struct sfnt_table); + memcpy(td->tables[idx].tag, tag, 4); + } - td->tables[idx].check_sum = sfnt_calc_checksum(data, length); - td->tables[idx].offset = 0L; - td->tables[idx].length = length; - td->tables[idx].data = data; + td->tables[idx].check_sum = sfnt_calc_checksum(data, length); + td->tables[idx].offset = 0L; + td->tables[idx].length = length; + td->tables[idx].data = data; - return; + return; } -ULONG -sfnt_find_table_len (sfnt *sfont, const char *tag) +ULONG sfnt_find_table_len(sfnt * sfont, const char *tag) { - ULONG length; - struct sfnt_table_directory *td; - int idx; - - ASSERT(sfont && tag); - - td = sfont->directory; - idx = find_table_index(td, tag); - if (idx < 0) - length = 0; - else { - length = td->tables[idx].length; - } + ULONG length; + struct sfnt_table_directory *td; + int idx; + + ASSERT(sfont && tag); + + td = sfont->directory; + idx = find_table_index(td, tag); + if (idx < 0) + length = 0; + else { + length = td->tables[idx].length; + } - return length; + return length; } -ULONG -sfnt_find_table_pos (sfnt *sfont, const char *tag) +ULONG sfnt_find_table_pos(sfnt * sfont, const char *tag) { - ULONG offset; - struct sfnt_table_directory *td; - int idx; - - ASSERT(sfont && tag); - - td = sfont->directory; - idx = find_table_index(td, tag); - if (idx < 0) - offset = 0; - else { - offset = td->tables[idx].offset; - } + ULONG offset; + struct sfnt_table_directory *td; + int idx; + + ASSERT(sfont && tag); + + td = sfont->directory; + idx = find_table_index(td, tag); + if (idx < 0) + offset = 0; + else { + offset = td->tables[idx].offset; + } - return offset; + return offset; } -ULONG -sfnt_locate_table (sfnt *sfont, const char *tag) +ULONG sfnt_locate_table(sfnt * sfont, const char *tag) { - ULONG offset; + ULONG offset; - ASSERT(sfont && tag); + ASSERT(sfont && tag); - offset = sfnt_find_table_pos(sfont, tag); - if (offset == 0) - TT_ERROR("sfnt: table not found..."); + offset = sfnt_find_table_pos(sfont, tag); + if (offset == 0) + TT_ERROR("sfnt: table not found..."); - sfnt_seek_set(sfont, offset); + sfnt_seek_set(sfont, offset); - return offset; + return offset; } -int -sfnt_read_table_directory (sfnt *sfont, ULONG offset) +int sfnt_read_table_directory(sfnt * sfont, ULONG offset) { - struct sfnt_table_directory *td; - unsigned long i, u_tag; + struct sfnt_table_directory *td; + unsigned long i, u_tag; - ASSERT(sfont); + ASSERT(sfont); - if (sfont->directory) - release_directory(sfont->directory); - sfont->directory = td = NEW (1, struct sfnt_table_directory); + if (sfont->directory) + release_directory(sfont->directory); + sfont->directory = td = NEW(1, struct sfnt_table_directory); #ifdef XETEX - ASSERT(sfont->ft_face); + ASSERT(sfont->ft_face); #elif defined(pdfTeX) - ASSERT(sfont->buffer); + ASSERT(sfont->buffer); #else - ASSERT(sfont->stream); + ASSERT(sfont->stream); #endif - sfnt_seek_set(sfont, offset); + sfnt_seek_set(sfont, offset); - td->version = sfnt_get_ulong(sfont); - td->num_tables = sfnt_get_ushort(sfont); - td->search_range = sfnt_get_ushort(sfont); - td->entry_selector = sfnt_get_ushort(sfont); - td->range_shift = sfnt_get_ushort(sfont); + td->version = sfnt_get_ulong(sfont); + td->num_tables = sfnt_get_ushort(sfont); + td->search_range = sfnt_get_ushort(sfont); + td->entry_selector = sfnt_get_ushort(sfont); + td->range_shift = sfnt_get_ushort(sfont); - td->flags = NEW(td->num_tables, char); - td->tables = NEW(td->num_tables, struct sfnt_table); + td->flags = NEW(td->num_tables, char); + td->tables = NEW(td->num_tables, struct sfnt_table); - for (i = 0; i < td->num_tables; i++) { - u_tag = sfnt_get_ulong(sfont); + for (i = 0; i < td->num_tables; i++) { + u_tag = sfnt_get_ulong(sfont); - convert_tag(td->tables[i].tag, u_tag); - td->tables[i].check_sum = sfnt_get_ulong(sfont); - td->tables[i].offset = sfnt_get_ulong(sfont); - td->tables[i].length = sfnt_get_ulong(sfont); - td->tables[i].data = NULL; + convert_tag(td->tables[i].tag, u_tag); + td->tables[i].check_sum = sfnt_get_ulong(sfont); + td->tables[i].offset = sfnt_get_ulong(sfont); + td->tables[i].length = sfnt_get_ulong(sfont); + td->tables[i].data = NULL; - td->flags[i] = 0; - } + td->flags[i] = 0; + } - td->num_kept_tables = 0; + td->num_kept_tables = 0; - return 0; + return 0; } -int -sfnt_require_table (sfnt *sfont, const char *tag, int must_exist) +int sfnt_require_table(sfnt * sfont, const char *tag, int must_exist) { - struct sfnt_table_directory *td; - int idx; - - ASSERT(sfont && sfont->directory); - - td = sfont->directory; - idx = find_table_index(td, tag); - if (idx < 0) { - if (must_exist) - return -1; - } else { - td->flags[idx] |= SFNT_TABLE_REQUIRED; - td->num_kept_tables++; - } - - return 0; + struct sfnt_table_directory *td; + int idx; + + ASSERT(sfont && sfont->directory); + + td = sfont->directory; + idx = find_table_index(td, tag); + if (idx < 0) { + if (must_exist) + return -1; + } else { + td->flags[idx] |= SFNT_TABLE_REQUIRED; + td->num_kept_tables++; + } + + return 0; } #ifndef pdfTeX -#include "pdfobj.h" +# include "pdfobj.h" #endif /* @@ -528,120 +507,115 @@ sfnt_require_table (sfnt *sfont, const char *tag, int must_exist) */ #ifdef pdfTeX -extern pdf_obj *pdf_new_stream(void); -extern void pdf_add_stream(pdf_obj *, unsigned char *, long); -extern void pdf_release_obj(pdf_obj *); -#undef MIN -#define MIN(a, b) (((a) < (b)) ? (a) : (b)) -#define STREAM_COMPRESS +# include "luatexfont.h" +# undef MIN +# define MIN(a, b) (((a) < (b)) ? (a) : (b)) +# define STREAM_COMPRESS #endif -static unsigned char wbuf[1024], padbytes[4] = {0, 0, 0, 0}; +static unsigned char wbuf[1024], padbytes[4] = { 0, 0, 0, 0 }; -pdf_obj * -sfnt_create_FontFile_stream (sfnt *sfont) +pdf_obj *sfnt_create_FontFile_stream(sfnt * sfont) { - pdf_obj *stream; + pdf_obj *stream; #ifndef pdfTeX - pdf_obj *stream_dict; + pdf_obj *stream_dict; #endif - struct sfnt_table_directory *td; - long offset, nb_read, length; - int i, sr; - char *p; - - ASSERT(sfont && sfont->directory); - - stream = pdf_new_stream(STREAM_COMPRESS); - - td = sfont->directory; - - /* Header */ - p = (char *) wbuf; - p += sfnt_put_ulong (p, td->version); - p += sfnt_put_ushort(p, td->num_kept_tables); - sr = max2floor(td->num_kept_tables) * 16; - p += sfnt_put_ushort(p, sr); - p += sfnt_put_ushort(p, log2floor(td->num_kept_tables)); - p += sfnt_put_ushort(p, td->num_kept_tables * 16 - sr); - - pdf_add_stream(stream, wbuf, 12); - - /* - * Compute start of actual tables (after headers). - */ - offset = 12 + 16 * td->num_kept_tables; - for (i = 0; i < td->num_tables; i++) { - /* This table must exist in FontFile */ - if (td->flags[i] & SFNT_TABLE_REQUIRED) { - if ((offset % 4) != 0) { - offset += 4 - (offset % 4); - } - - p = (char *) wbuf; - memcpy(p, td->tables[i].tag, 4); - p += 4; - p += sfnt_put_ulong(p, td->tables[i].check_sum); - p += sfnt_put_ulong(p, offset); - p += sfnt_put_ulong(p, td->tables[i].length); - pdf_add_stream(stream, wbuf, 16); - - offset += td->tables[i].length; + struct sfnt_table_directory *td; + long offset, nb_read, length; + int i, sr; + char *p; + + ASSERT(sfont && sfont->directory); + + stream = pdf_new_stream(STREAM_COMPRESS); + + td = sfont->directory; + + /* Header */ + p = (char *) wbuf; + p += sfnt_put_ulong(p, td->version); + p += sfnt_put_ushort(p, td->num_kept_tables); + sr = max2floor(td->num_kept_tables) * 16; + p += sfnt_put_ushort(p, sr); + p += sfnt_put_ushort(p, log2floor(td->num_kept_tables)); + p += sfnt_put_ushort(p, td->num_kept_tables * 16 - sr); + + pdf_add_stream(stream, wbuf, 12); + + /* + * Compute start of actual tables (after headers). + */ + offset = 12 + 16 * td->num_kept_tables; + for (i = 0; i < td->num_tables; i++) { + /* This table must exist in FontFile */ + if (td->flags[i] & SFNT_TABLE_REQUIRED) { + if ((offset % 4) != 0) { + offset += 4 - (offset % 4); + } + + p = (char *) wbuf; + memcpy(p, td->tables[i].tag, 4); + p += 4; + p += sfnt_put_ulong(p, td->tables[i].check_sum); + p += sfnt_put_ulong(p, offset); + p += sfnt_put_ulong(p, td->tables[i].length); + pdf_add_stream(stream, wbuf, 16); + + offset += td->tables[i].length; + } } - } - - offset = 12 + 16 * td->num_kept_tables; - for (i = 0; i < td->num_tables; i++) { - if (td->flags[i] & SFNT_TABLE_REQUIRED) { - if ((offset % 4) != 0) { - length = 4 - (offset % 4); - pdf_add_stream(stream, padbytes, length); - offset += length; - } - if (!td->tables[i].data) { + + offset = 12 + 16 * td->num_kept_tables; + for (i = 0; i < td->num_tables; i++) { + if (td->flags[i] & SFNT_TABLE_REQUIRED) { + if ((offset % 4) != 0) { + length = 4 - (offset % 4); + pdf_add_stream(stream, padbytes, length); + offset += length; + } + if (!td->tables[i].data) { #ifdef XETEX - if (!sfont->ft_face) + if (!sfont->ft_face) #elif defined(pdfTeX) - if (!sfont->buffer) + if (!sfont->buffer) #else - if (!sfont->stream) + if (!sfont->stream) #endif - { - pdf_release_obj(stream); - TT_ERROR("Font file not opened or already closed..."); - return NULL; - } - - length = td->tables[i].length; - sfnt_seek_set(sfont, td->tables[i].offset); - while (length > 0) { - nb_read = sfnt_read(wbuf, MIN(length, 1024), sfont); - if (nb_read < 0) { - pdf_release_obj(stream); - TT_ERROR("Reading file failed..."); - return NULL; - } else if (nb_read > 0) { - pdf_add_stream(stream, wbuf, nb_read); - } - length -= nb_read; - } - } else { - pdf_add_stream(stream, - (unsigned char *)td->tables[i].data, - td->tables[i].length); - RELEASE(td->tables[i].data); - td->tables[i].data = NULL; - } - /* Set offset for next table */ - offset += td->tables[i].length; + { + pdf_release_obj(stream); + TT_ERROR("Font file not opened or already closed..."); + return NULL; + } + + length = td->tables[i].length; + sfnt_seek_set(sfont, td->tables[i].offset); + while (length > 0) { + nb_read = sfnt_read(wbuf, MIN(length, 1024), sfont); + if (nb_read < 0) { + pdf_release_obj(stream); + TT_ERROR("Reading file failed..."); + return NULL; + } else if (nb_read > 0) { + pdf_add_stream(stream, wbuf, nb_read); + } + length -= nb_read; + } + } else { + pdf_add_stream(stream, + (unsigned char *) td->tables[i].data, + td->tables[i].length); + RELEASE(td->tables[i].data); + td->tables[i].data = NULL; + } + /* Set offset for next table */ + offset += td->tables[i].length; + } } - } #ifndef pdfTeX - stream_dict = pdf_stream_dict(stream); - pdf_add_dict(stream_dict, - pdf_new_name("Length1"), - pdf_new_number(offset)); + stream_dict = pdf_stream_dict(stream); + pdf_add_dict(stream_dict, pdf_new_name("Length1"), pdf_new_number(offset)); #endif - return stream; + return stream; } diff --git a/Build/source/texk/web2c/luatexdir/font/sfnt.h b/Build/source/texk/web2c/luatexdir/font/sfnt.h index 8db54dd9c39..87b373730be 100644 --- a/Build/source/texk/web2c/luatexdir/font/sfnt.h +++ b/Build/source/texk/web2c/luatexdir/font/sfnt.h @@ -1,197 +1,194 @@ -/* $Header: /home/cvsroot/dvipdfmx/src/sfnt.h,v 1.9 2004/09/11 14:50:29 hirata Exp $ +/* sfnt.h - This is dvipdfmx, an eXtended version of dvipdfm by Mark A. Wicks. + Copyright 2002 by Jin-Hwan Cho and Shunsaku Hirata, + the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> - Copyright (C) 2002 by Jin-Hwan Cho and Shunsaku Hirata, - the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. -*/ + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ + +/* $Id: sfnt.h 1223 2008-05-02 13:39:55Z oneiros $ */ #ifndef _SFNT_H_ -#define _SFNT_H_ +# define _SFNT_H_ -#if HAVE_CONFIG_H -#include "config.h" -#endif /* HAVE_CONFIG_H_ */ +# if HAVE_CONFIG_H +# include "config.h" +# endif /* HAVE_CONFIG_H_ */ -#ifndef pdfTeX -#include "mfileio.h" -#include "numbers.h" -#include "pdfobj.h" -#endif +# ifndef pdfTeX +# include "mfileio.h" +# include "numbers.h" +# include "pdfobj.h" +# endif -#ifdef XETEX -#include "ft2build.h" -#include FT_FREETYPE_H -#include FT_TRUETYPE_TABLES_H -#endif +# ifdef XETEX +# include "ft2build.h" +# include FT_FREETYPE_H +# include FT_TRUETYPE_TABLES_H +# endif /* Data Types as described in Apple's TTRefMan */ -typedef unsigned char BYTE; -typedef signed char ICHAR; +typedef unsigned char BYTE; +typedef signed char ICHAR; typedef unsigned short USHORT; -typedef signed short SHORT; -typedef unsigned long ULONG; -typedef signed long LONG; -typedef unsigned long Fixed; /* 16.16-bit signed fixed-point number */ -typedef short FWord; +typedef signed short SHORT; +typedef unsigned long ULONG; +typedef signed long LONG; +typedef unsigned long Fixed; /* 16.16-bit signed fixed-point number */ +typedef short FWord; typedef unsigned short uFWord; -typedef short F2Dot14; /* 16-bit signed fixed number with the low - 14 bits representing fraction. */ - -struct sfnt_table -{ - /* table header */ - char tag[4]; - ULONG check_sum; - ULONG offset; - ULONG length; - char *data; /* table data */ +typedef short F2Dot14; /* 16-bit signed fixed number with the low + 14 bits representing fraction. */ + +struct sfnt_table { + /* table header */ + char tag[4]; + ULONG check_sum; + ULONG offset; + ULONG length; + char *data; /* table data */ }; -#define SFNT_TABLE_REQUIRED (1 << 0) - -struct sfnt_table_directory -{ - ULONG version; /* Fixed for Win */ - USHORT num_tables; - USHORT search_range; - USHORT entry_selector; - USHORT range_shift; - USHORT num_kept_tables; /* number of kept tables */ - char *flags; /* keep or omit */ - struct sfnt_table *tables; +# define SFNT_TABLE_REQUIRED (1 << 0) + +struct sfnt_table_directory { + ULONG version; /* Fixed for Win */ + USHORT num_tables; + USHORT search_range; + USHORT entry_selector; + USHORT range_shift; + USHORT num_kept_tables; /* number of kept tables */ + char *flags; /* keep or omit */ + struct sfnt_table *tables; }; /* sfnt resource */ -#define SFNT_TYPE_TRUETYPE (1 << 0) -#define SFNT_TYPE_OPENTYPE (1 << 1) -#define SFNT_TYPE_POSTSCRIPT (1 << 2) -#define SFNT_TYPE_TTC (1 << 4) - -typedef struct -{ - int type; - struct sfnt_table_directory *directory; -#ifdef XETEX - FT_Face ft_face; - long loc; -#elif defined(pdfTeX) - BYTE *buffer; - long buflen; - long loc; -#else - FILE *stream; -#endif +# define SFNT_TYPE_TRUETYPE (1 << 0) +# define SFNT_TYPE_OPENTYPE (1 << 1) +# define SFNT_TYPE_POSTSCRIPT (1 << 2) +# define SFNT_TYPE_TTC (1 << 4) + +typedef struct { + int type; + struct sfnt_table_directory *directory; +# ifdef XETEX + FT_Face ft_face; + long loc; +# elif defined(pdfTeX) + BYTE *buffer; + long buflen; + long loc; +# else + FILE *stream; +# endif } sfnt; /* Convert sfnt "fixed" type to double */ -#define fixed(a) ((double)((a)%0x10000L)/(double)(0x10000L) + \ +# define fixed(a) ((double)((a)%0x10000L)/(double)(0x10000L) + \ (a)/0x10000L - (((a)/0x10000L > 0x7fffL) ? 0x10000L : 0)) -#ifdef XETEX -UNSIGNED_BYTE ft_unsigned_byte(sfnt* f); -SIGNED_BYTE ft_signed_byte(sfnt* f); -UNSIGNED_PAIR ft_unsigned_pair(sfnt* f); -SIGNED_PAIR ft_signed_pair(sfnt* f); -UNSIGNED_QUAD ft_unsigned_quad(sfnt* f); -unsigned long ft_read(unsigned char* buf, unsigned long len, sfnt* f); - -#define sfnt_get_byte(s) ((BYTE) ft_unsigned_byte(s)) -#define sfnt_get_char(s) ((ICHAR) ft_signed_byte (s)) -#define sfnt_get_ushort(s) ((USHORT) ft_unsigned_pair(s)) -#define sfnt_get_short(s) ((SHORT) ft_signed_pair (s)) -#define sfnt_get_ulong(s) ((ULONG) ft_unsigned_quad(s)) -#define sfnt_get_long(s) ((LONG) ft_signed_quad (s)) - -#define sfnt_seek_set(s,o) (s)->loc = (o) -#define sfnt_read(b,l,s) ft_read((b), (l), (s)) -#elif defined(pdfTeX) -BYTE get_unsigned_byte(sfnt* f); -ICHAR get_signed_byte(sfnt* f); -USHORT get_unsigned_pair(sfnt* f); -SHORT get_signed_pair(sfnt* f); -ULONG get_unsigned_quad(sfnt* f); -int do_sfnt_read (unsigned char *dest, int len, sfnt *f); - -#define sfnt_get_byte(s) ((BYTE) get_unsigned_byte(s)) -#define sfnt_get_char(s) ((ICHAR) get_signed_byte (s)) -#define sfnt_get_ushort(s) ((USHORT) get_unsigned_pair(s)) -#define sfnt_get_short(s) ((SHORT) get_signed_pair (s)) -#define sfnt_get_ulong(s) ((ULONG) get_unsigned_quad(s)) -#define sfnt_get_long(s) ((LONG) get_signed_quad (s)) - -#define sfnt_seek_set(s,o) (s)->loc = (o) -#define sfnt_read(b,l,s) do_sfnt_read((b), (l), (s)) -#else +# ifdef XETEX +UNSIGNED_BYTE ft_unsigned_byte(sfnt * f); +SIGNED_BYTE ft_signed_byte(sfnt * f); +UNSIGNED_PAIR ft_unsigned_pair(sfnt * f); +SIGNED_PAIR ft_signed_pair(sfnt * f); +UNSIGNED_QUAD ft_unsigned_quad(sfnt * f); +unsigned long ft_read(unsigned char *buf, unsigned long len, sfnt * f); + +# define sfnt_get_byte(s) ((BYTE) ft_unsigned_byte(s)) +# define sfnt_get_char(s) ((ICHAR) ft_signed_byte (s)) +# define sfnt_get_ushort(s) ((USHORT) ft_unsigned_pair(s)) +# define sfnt_get_short(s) ((SHORT) ft_signed_pair (s)) +# define sfnt_get_ulong(s) ((ULONG) ft_unsigned_quad(s)) +# define sfnt_get_long(s) ((LONG) ft_signed_quad (s)) + +# define sfnt_seek_set(s,o) (s)->loc = (o) +# define sfnt_read(b,l,s) ft_read((b), (l), (s)) +# elif defined(pdfTeX) +BYTE get_unsigned_byte(sfnt * f); +ICHAR get_signed_byte(sfnt * f); +USHORT get_unsigned_pair(sfnt * f); +SHORT get_signed_pair(sfnt * f); +ULONG get_unsigned_quad(sfnt * f); +int do_sfnt_read(unsigned char *dest, int len, sfnt * f); + +# define sfnt_get_byte(s) ((BYTE) get_unsigned_byte(s)) +# define sfnt_get_char(s) ((ICHAR) get_signed_byte (s)) +# define sfnt_get_ushort(s) ((USHORT) get_unsigned_pair(s)) +# define sfnt_get_short(s) ((SHORT) get_signed_pair (s)) +# define sfnt_get_ulong(s) ((ULONG) get_unsigned_quad(s)) +# define sfnt_get_long(s) ((LONG) get_signed_quad (s)) + +# define sfnt_seek_set(s,o) (s)->loc = (o) +# define sfnt_read(b,l,s) do_sfnt_read((b), (l), (s)) +# else /* get_***_*** from numbers.h */ -#define sfnt_get_byte(s) ((BYTE) get_unsigned_byte((s)->stream)) -#define sfnt_get_char(s) ((ICHAR) get_signed_byte ((s)->stream)) -#define sfnt_get_ushort(s) ((USHORT) get_unsigned_pair((s)->stream)) -#define sfnt_get_short(s) ((SHORT) get_signed_pair ((s)->stream)) -#define sfnt_get_ulong(s) ((ULONG) get_unsigned_quad((s)->stream)) -#define sfnt_get_long(s) ((LONG) get_signed_quad ((s)->stream)) - -#define sfnt_seek_set(s,o) seek_absolute((s)->stream, (o)) -#define sfnt_read(b,l,s) fread((b), 1, (l), (s)->stream) -#endif - -extern int put_big_endian (void *s, LONG q, int n); - -#define sfnt_put_ushort(s,v) put_big_endian((s), v, 2); -#define sfnt_put_short(s,v) put_big_endian((s), v, 2); -#define sfnt_put_ulong(s,v) put_big_endian((s), v, 4); -#define sfnt_put_long(s,v) put_big_endian((s), v, 4); - -#ifdef XETEX -extern sfnt *sfnt_open (FT_Face face, int accept_types); -#elif defined(pdfTeX) -extern sfnt *sfnt_open (unsigned char *buffer, integer buflen); -#else -extern sfnt *sfnt_open (FILE *fp); -#endif -extern void sfnt_close (sfnt *sfont); +# define sfnt_get_byte(s) ((BYTE) get_unsigned_byte((s)->stream)) +# define sfnt_get_char(s) ((ICHAR) get_signed_byte ((s)->stream)) +# define sfnt_get_ushort(s) ((USHORT) get_unsigned_pair((s)->stream)) +# define sfnt_get_short(s) ((SHORT) get_signed_pair ((s)->stream)) +# define sfnt_get_ulong(s) ((ULONG) get_unsigned_quad((s)->stream)) +# define sfnt_get_long(s) ((LONG) get_signed_quad ((s)->stream)) + +# define sfnt_seek_set(s,o) seek_absolute((s)->stream, (o)) +# define sfnt_read(b,l,s) fread((b), 1, (l), (s)->stream) +# endif + +extern int put_big_endian(void *s, LONG q, int n); + +# define sfnt_put_ushort(s,v) put_big_endian((s), v, 2); +# define sfnt_put_short(s,v) put_big_endian((s), v, 2); +# define sfnt_put_ulong(s,v) put_big_endian((s), v, 4); +# define sfnt_put_long(s,v) put_big_endian((s), v, 4); + +# ifdef XETEX +extern sfnt *sfnt_open(FT_Face face, int accept_types); +# elif defined(pdfTeX) +extern sfnt *sfnt_open(unsigned char *buffer, integer buflen); +# else +extern sfnt *sfnt_open(FILE * fp); +# endif +extern void sfnt_close(sfnt * sfont); /* table directory */ -extern int sfnt_read_table_directory (sfnt *sfont, ULONG offset); -extern ULONG sfnt_find_table_len (sfnt *sfont, const char *tag); -extern ULONG sfnt_find_table_pos (sfnt *sfont, const char *tag); -extern ULONG sfnt_locate_table (sfnt *sfont, const char *tag); - -extern void sfnt_set_table (sfnt *sfont, - const char *tag, void *data, ULONG length); -extern int sfnt_require_table (sfnt *sfont, const char *tag, int must_exist); - -#ifdef pdfTeX -typedef struct -{ - ULONG length; - BYTE *data; +extern int sfnt_read_table_directory(sfnt * sfont, ULONG offset); +extern ULONG sfnt_find_table_len(sfnt * sfont, const char *tag); +extern ULONG sfnt_find_table_pos(sfnt * sfont, const char *tag); +extern ULONG sfnt_locate_table(sfnt * sfont, const char *tag); + +extern void sfnt_set_table(sfnt * sfont, + const char *tag, void *data, ULONG length); +extern int sfnt_require_table(sfnt * sfont, const char *tag, int must_exist); + +# ifdef pdfTeX +typedef struct { + ULONG length; + BYTE *data; } pdf_obj; -#define ASSERT(a) assert(a) -#define RELEASE(a) free(a) -#define NEW(a,b) xmalloc((a)*sizeof(b)) -#define RENEW(a,b,c) xrealloc(a, ((b)*sizeof(c))) -#define TT_ERROR pdftex_fail -#define WARN printf +# define ASSERT(a) assert(a) +# define RELEASE(a) free(a) +# define NEW(a,b) xmalloc((a)*sizeof(b)) +# define RENEW(a,b,c) xrealloc(a, ((b)*sizeof(c))) +# define TT_ERROR pdftex_fail +# define WARN printf -#endif +# endif -extern pdf_obj *sfnt_create_FontFile_stream (sfnt *sfont); +extern pdf_obj *sfnt_create_FontFile_stream(sfnt * sfont); -#endif /* _SFNT_H_ */ +#endif /* _SFNT_H_ */ diff --git a/Build/source/texk/web2c/luatexdir/font/subfont.c b/Build/source/texk/web2c/luatexdir/font/subfont.c index 836985c10fd..fecd5ed7857 100644 --- a/Build/source/texk/web2c/luatexdir/font/subfont.c +++ b/Build/source/texk/web2c/luatexdir/font/subfont.c @@ -1,26 +1,29 @@ -/* -Copyright (c) 2005-2006 Han The Thanh, <thanh@pdftex.org> +/* subfont.c + + Copyright 2005-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -This file is part of pdfTeX. + This file is part of LuaTeX. -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" #include <string.h> +static const char _svn_version[] = + "$Id: subfont.c 1783 2009-01-18 12:51:01Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/subfont.c $"; + static struct avl_table *sfd_tree = NULL; static unsigned char *sfd_buffer = NULL; @@ -30,7 +33,7 @@ static integer sfd_curbyte = 0; #define SFD_BUF_SIZE SMALL_BUF_SIZE #define sfd_close() xfclose(sfd_file, cur_file_name) -#define sfd_open() open_input(&sfd_file, kpse_sfd_format, FOPEN_RBIN_MODE) +#define sfd_open() (sfd_file = fopen((char *) nameoffile + 1, FOPEN_RBIN_MODE)) #define sfd_read_file() readbinfile(sfd_file,&sfd_buffer,&sfd_size) #define sfd_getchar() sfd_buffer[sfd_curbyte++] @@ -40,11 +43,11 @@ static integer sfd_curbyte = 0; static FILE *sfd_file; static char sfd_line[SFD_BUF_SIZE]; -static subfont_entry *new_subfont_entry (void) +static subfont_entry *new_subfont_entry(void) { int i; subfont_entry *subfont; - subfont = xtalloc (1, subfont_entry); + subfont = xtalloc(1, subfont_entry); subfont->infix = NULL; for (i = 0; i < 256; ++i) subfont->charcodes[i] = -1; /* unassigned */ @@ -52,16 +55,16 @@ static subfont_entry *new_subfont_entry (void) return subfont; } -static sfd_entry *new_sfd_entry (void) +static sfd_entry *new_sfd_entry(void) { sfd_entry *sfd; - sfd = xtalloc (1, sfd_entry); + sfd = xtalloc(1, sfd_entry); sfd->name = NULL; sfd->subfont = NULL; return sfd; } -static void destroy_sfd_entry (void *pa, void *pb) +static void destroy_sfd_entry(void *pa, void *pb) { subfont_entry *p, *q; sfd_entry *sfd; @@ -69,132 +72,139 @@ static void destroy_sfd_entry (void *pa, void *pb) p = sfd->subfont; while (p != NULL) { q = p->next; - xfree (p->infix); - xfree (p); + xfree(p->infix); + xfree(p); p = q; } - xfree (sfd->name); + xfree(sfd->name); } -static int comp_sfd_entry (const void *pa, const void *pb, void *p) +static int comp_sfd_entry(const void *pa, const void *pb, void *p) { - return strcmp (((const sfd_entry *) pa)->name, - ((const sfd_entry *) pb)->name); + return strcmp(((const sfd_entry *) pa)->name, + ((const sfd_entry *) pb)->name); } -void sfd_free (void) +void sfd_free(void) { if (sfd_tree != NULL) - avl_destroy (sfd_tree, destroy_sfd_entry); + avl_destroy(sfd_tree, destroy_sfd_entry); } -static void sfd_getline (boolean expect_eof) +static void sfd_getline(boolean expect_eof) { char *p; int c; restart: - if (sfd_eof ()) { + if (sfd_eof()) { if (expect_eof) return; else - pdftex_fail ("unexpected end of file"); + pdftex_fail("unexpected end of file"); } p = sfd_line; do { - c = sfd_getchar (); - append_char_to_buf (c, p, sfd_line, SFD_BUF_SIZE); + c = sfd_getchar(); + append_char_to_buf(c, p, sfd_line, SFD_BUF_SIZE); } while (c != 10 && !sfd_eof()); - append_eol (p, sfd_line, SFD_BUF_SIZE); + append_eol(p, sfd_line, SFD_BUF_SIZE); if (p - sfd_line < 2 || *sfd_line == '#') goto restart; } -static sfd_entry *read_sfd (char *sfd_name) +static sfd_entry *read_sfd(char *sfd_name) { void **aa; sfd_entry *sfd, tmp_sfd; subfont_entry *sf; - char *ftemp = NULL; + char *ftemp = NULL; char buf[SMALL_BUF_SIZE], *p; long int i, j, k; int n; - int callback_id=0; - int file_opened=0; + int callback_id = 0; + int file_opened = 0; /* check whether this sfd has been read */ tmp_sfd.name = sfd_name; if (sfd_tree == NULL) { - sfd_tree = avl_create (comp_sfd_entry, NULL, &avl_xallocator); - assert (sfd_tree != NULL); + sfd_tree = avl_create(comp_sfd_entry, NULL, &avl_xallocator); + assert(sfd_tree != NULL); } - sfd = (sfd_entry *) avl_find (sfd_tree, &tmp_sfd); + sfd = (sfd_entry *) avl_find(sfd_tree, &tmp_sfd); if (sfd != NULL) return sfd; - set_cur_file_name (sfd_name); - if (sfd_buffer!=NULL) { - xfree(sfd_buffer); - sfd_buffer=NULL; + set_cur_file_name(sfd_name); + if (sfd_buffer != NULL) { + xfree(sfd_buffer); + sfd_buffer = NULL; } - sfd_curbyte=0; - sfd_size=0; + sfd_curbyte = 0; + sfd_size = 0; - callback_id=callback_defined(find_sfd_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->S",cur_file_name,&ftemp)) { - if(ftemp!=NULL&&strlen(ftemp)) { - if (cur_file_name) - free(cur_file_name); - cur_file_name = xstrdup(ftemp); - free(ftemp); - } - } - } - callback_id=callback_defined(read_sfd_file_callback); - if (callback_id>0) { - if(! (run_callback(callback_id,"S->bSd",cur_file_name, - &file_opened, &sfd_buffer,&sfd_size) && - file_opened && - sfd_size>0 ) ) { - pdftex_warn ("cannot open SFD file for reading"); - cur_file_name = NULL; - return NULL; - } - sfd_read_file(); - sfd_close(); + callback_id = callback_defined(find_sfd_file_callback); + if (callback_id > 0) { + if (run_callback(callback_id, "S->S", cur_file_name, &ftemp)) { + if (ftemp != NULL && strlen(ftemp)) { + if (cur_file_name) + free(cur_file_name); + cur_file_name = xstrdup(ftemp); + free(ftemp); + } + } + } else { + cur_file_name = kpse_find_file(cur_file_name, kpse_sfd_format, 0); + } + callback_id = callback_defined(read_sfd_file_callback); + if (callback_id > 0) { + if (!(run_callback(callback_id, "S->bSd", cur_file_name, + &file_opened, &sfd_buffer, &sfd_size) && + file_opened && sfd_size > 0)) { + pdftex_warn("cannot open SFD file for reading"); + cur_file_name = NULL; + return NULL; + } + } else { + if (!sfd_open()) { + pdftex_warn("cannot open SFD file for reading"); + cur_file_name = NULL; + return NULL; + } + sfd_read_file(); + sfd_close(); } - tex_printf ("{"); - tex_printf (cur_file_name); - sfd = new_sfd_entry (); - sfd->name = xstrdup (sfd_name); - while (!sfd_eof ()) { - sfd_getline (true); + tex_printf("{"); + tex_printf("%s", cur_file_name); + sfd = new_sfd_entry(); + sfd->name = xstrdup(sfd_name); + while (!sfd_eof()) { + sfd_getline(true); if (*sfd_line == 10) /* empty line indicating eof */ break; - sf = new_subfont_entry (); + sf = new_subfont_entry(); sf->next = sfd->subfont; sfd->subfont = sf; - sscanf (sfd_line, "%s %n", buf, &n); - sf->infix = xstrdup (buf); + sscanf(sfd_line, "%s %n", buf, &n); + sf->infix = xstrdup(buf); p = sfd_line + n; /* skip to the next word */ k = 0; read_ranges: for (;;) { if (*p == '\\') { /* continue on next line */ - sfd_getline (false); + sfd_getline(false); p = sfd_line; goto read_ranges; } else if (*p == 0) /* end of subfont */ break; - if (sscanf (p, " %li %n", &i, &n) == 0) - pdftex_fail ("invalid token:\n%s", p); + if (sscanf(p, " %li %n", &i, &n) == 0) + pdftex_fail("invalid token:\n%s", p); p += n; if (*p == ':') { /* offset */ k = i; p++; } else if (*p == '_') { /* range */ - if (sscanf (p + 1, " %li %n", &j, &n) == 0) - pdftex_fail ("invalid token:\n%s", p); + if (sscanf(p + 1, " %li %n", &j, &n) == 0) + pdftex_fail("invalid token:\n%s", p); if (i > j || k + (j - i) > 255) - pdftex_fail ("invalid range:\n%s", p); + pdftex_fail("invalid range:\n%s", p); while (i <= j) sf->charcodes[k++] = i++; p += n + 1; @@ -202,13 +212,13 @@ static sfd_entry *read_sfd (char *sfd_name) sf->charcodes[k++] = i; } } - tex_printf ("}"); - aa = avl_probe (sfd_tree, sfd); - assert (aa != NULL); + tex_printf("}"); + aa = avl_probe(sfd_tree, sfd); + assert(aa != NULL); return sfd; } -boolean handle_subfont_fm (fm_entry * fm, int mode) +boolean handle_subfont_fm(fm_entry * fm, int mode) { size_t l; char *p, *q, *r; @@ -216,28 +226,28 @@ boolean handle_subfont_fm (fm_entry * fm, int mode) subfont_entry *sf; fm_entry *fm2; char buf[SMALL_BUF_SIZE]; - assert (fm->tfm_name != NULL); + assert(fm->tfm_name != NULL); p = fm->tfm_name; - q = strchr (p, '@'); /* search for the first '@' */ + q = strchr(p, '@'); /* search for the first '@' */ if (q == NULL) return false; - r = strchr (q + 1, '@'); /* search for the second '@' */ + r = strchr(q + 1, '@'); /* search for the second '@' */ if (r == NULL) return false; if (q <= p || r <= q + 1 /* prefix or sfd name is empty */ - || r - p != strlen (p) - 1) /* or the second '@' is not the last char yet */ + || r - p != (int) strlen(p) - 1) /* or the second '@' is not the last char yet */ return false; l = r - (q + 1); /* length of sfd name */ - strncpy (buf, q + 1, l); + strncpy(buf, q + 1, l); buf[l] = 0; - check_buf(strlen(buf) + 4, SMALL_BUF_SIZE); - strcat (buf, ".sfd"); - sfd = read_sfd (buf); + check_buf(strlen(buf) + 4, SMALL_BUF_SIZE); + strcat(buf, ".sfd"); + sfd = read_sfd(buf); if (sfd == NULL) return false; /* at this point we know fm is a subfont */ - set_subfont (fm); - xfree (fm->ps_name); + set_subfont(fm); + xfree(fm->ps_name); fm->ps_name = NULL; /* set default values for PidEid */ if (fm->pid == -1) { @@ -246,19 +256,19 @@ boolean handle_subfont_fm (fm_entry * fm, int mode) } l = q - p; /* length of base tfm name (prefix) */ for (sf = sfd->subfont; sf != NULL; sf = sf->next) { - strncpy (buf, p, l); + strncpy(buf, p, l); buf[l] = 0; - strcat (buf, sf->infix); - fm2 = new_fm_entry (); - fm2->tfm_name = xstrdup (buf); - fm2->ff_name = xstrdup (fm->ff_name); + strcat(buf, sf->infix); + fm2 = new_fm_entry(); + fm2->tfm_name = xstrdup(buf); + fm2->ff_name = xstrdup(fm->ff_name); fm2->type = fm->type; fm2->pid = fm->pid; fm2->eid = fm->eid; fm2->subfont = sf; - if (avl_do_entry (fm2, mode) != 0) /* try to insert the entry */ - delete_fm_entry (fm2); /* delete it if failed */ + if (avl_do_entry(fm2, mode) != 0) /* try to insert the entry */ + delete_fm_entry(fm2); /* delete it if failed */ } - delete_fm_entry (fm); + delete_fm_entry(fm); return true; } diff --git a/Build/source/texk/web2c/luatexdir/font/texfont.c b/Build/source/texk/web2c/luatexdir/font/texfont.c index 150c2cba769..1daf6a5b56b 100644 --- a/Build/source/texk/web2c/luatexdir/font/texfont.c +++ b/Build/source/texk/web2c/luatexdir/font/texfont.c @@ -1,23 +1,21 @@ -/* - Copyright (c) 1996-2006 Taco Hoekwater <taco@luatex.org> - - This file is part of LuaTeX. - - LuaTeX is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - LuaTeX is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with LuaTeX; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - - $Id: texfont.c 1013 2008-02-14 00:09:02Z oneiros $ */ +/* texfont.c Main font API implementation for the pascal parts + + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> + + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ /* Main font API implementation for the pascal parts */ @@ -36,6 +34,9 @@ #include "ptexlib.h" #include "luatex-api.h" +static const char _svn_version[] = + "$Id: texfont.c 2064 2009-03-20 13:13:14Z taco $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/texfont.c $"; + #define proper_char_index(c) (c<=font_ec(f) && c>=font_bc(f)) #define dxfree(a,b) { xfree(a); a = b ; } #define do_realloc(a,b,d) a = xrealloc(a,(b)*sizeof(d)) @@ -45,1050 +46,1460 @@ texfont **font_tables = NULL; static integer font_arr_max = 0; static integer font_id_maxval = 0; -static void grow_font_table (integer id) { - int j; - if (id>=font_arr_max) { - font_bytes += (font_arr_max-id+8)*sizeof(texfont *); - font_tables = xrealloc(font_tables,(id+8)*sizeof(texfont *)); - j = 8; - while (j--) { - font_tables[id+j] = NULL; +extern extinfo *get_charinfo_vert_variants(charinfo * ci); +extern extinfo *get_charinfo_hor_variants(charinfo * ci); +extern void set_charinfo_hor_variants(charinfo * ci, extinfo * ext); +extern void set_charinfo_vert_variants(charinfo * ci, extinfo * ext); + +extern extinfo *copy_variants(extinfo * o); + + +static void grow_font_table(integer id) +{ + int j; + if (id >= font_arr_max) { + font_bytes += (font_arr_max - id + 8) * sizeof(texfont *); + font_tables = xrealloc(font_tables, (id + 8) * sizeof(texfont *)); + j = 8; + while (j--) { + font_tables[id + j] = NULL; + } + font_arr_max = id + 8; } - font_arr_max = id+8; - } } -integer -new_font_id (void) { - int i; - for (i=0;i<font_arr_max;i++) { - if (font_tables[i]==NULL) { - break; +integer new_font_id(void) +{ + int i; + for (i = 0; i < font_arr_max; i++) { + if (font_tables[i] == NULL) { + break; + } } - } - if (i>=font_arr_max) - grow_font_table (i); - if (i>font_id_maxval) + if (i >= font_arr_max) + grow_font_table(i); + if (i > font_id_maxval) + font_id_maxval = i; + return i; +} + +integer max_font_id(void) +{ + return font_id_maxval; +} + +void set_max_font_id(integer i) +{ font_id_maxval = i; - return i; -} - -integer -max_font_id (void) { - return font_id_maxval; -} - -void -set_max_font_id (integer i) { - font_id_maxval = i; -} - -integer -new_font (void) { - int k; - int id; - charinfo *ci; - id = new_font_id(); - font_bytes += sizeof(texfont); - /* most stuff is zero */ - font_tables[id] = xcalloc(1,sizeof(texfont)); - font_tables[id]->_font_name = NULL; - font_tables[id]->_font_area = NULL; - font_tables[id]->_font_filename = NULL; - font_tables[id]->_font_fullname = NULL; - font_tables[id]->_font_encodingname = NULL; - font_tables[id]->_font_cidregistry = NULL; - font_tables[id]->_font_cidordering = NULL; - font_tables[id]->_left_boundary = NULL; - font_tables[id]->_right_boundary = NULL; - font_tables[id]->_param_base = NULL; - - set_font_bc(id, 1); /* ec = 0 */ - set_hyphen_char(id,'-'); - set_skew_char(id,-1); - - /* allocate eight values including 0 */ - set_font_params(id,7); - for (k=0;k<=7;k++) { - set_font_param(id,k,0); - } - /* character info zero is reserved for notdef */ - font_tables[id]->characters = new_sa_tree(1, 0); /* stack size 1, default item value 0 */ +} - ci = xcalloc(1,sizeof(charinfo)); - set_charinfo_name(ci,xstrdup(".notdef")); - font_tables[id]->charinfo = ci; - font_tables[id]->charinfo_cache = NULL; +integer new_font(void) +{ + int k; + int id; + charinfo *ci; + id = new_font_id(); + font_bytes += sizeof(texfont); + /* most stuff is zero */ + font_tables[id] = xcalloc(1, sizeof(texfont)); + font_tables[id]->_font_name = NULL; + font_tables[id]->_font_area = NULL; + font_tables[id]->_font_filename = NULL; + font_tables[id]->_font_fullname = NULL; + font_tables[id]->_font_encodingname = NULL; + font_tables[id]->_font_cidregistry = NULL; + font_tables[id]->_font_cidordering = NULL; + font_tables[id]->_left_boundary = NULL; + font_tables[id]->_right_boundary = NULL; + font_tables[id]->_param_base = NULL; + font_tables[id]->_math_param_base = NULL; + + set_font_bc(id, 1); /* ec = 0 */ + set_hyphen_char(id, '-'); + set_skew_char(id, -1); + + /* allocate eight values including 0 */ + set_font_params(id, 7); + for (k = 0; k <= 7; k++) { + set_font_param(id, k, 0); + } + /* character info zero is reserved for notdef */ + font_tables[id]->characters = new_sa_tree(1, 0); /* stack size 1, default item value 0 */ + + ci = xcalloc(1, sizeof(charinfo)); + set_charinfo_name(ci, xstrdup(".notdef")); + font_tables[id]->charinfo = ci; + font_tables[id]->charinfo_cache = NULL; - return id; + return id; } #define Charinfo_count(a) font_tables[a]->charinfo_count #define Charinfo_size(a) font_tables[a]->charinfo_size #define Characters(a) font_tables[a]->characters -charinfo * -get_charinfo (internal_font_number f, integer c) { - sa_tree_item glyph; - charinfo *ci; - if (proper_char_index(c)) { - glyph = get_sa_item(Characters(f), c); - if (!glyph) { - /* this could be optimized using controlled growth */ - font_bytes += sizeof(charinfo); - glyph = ++font_tables[f]->charinfo_count; - do_realloc(font_tables[f]->charinfo, (glyph+1), charinfo); - memset (&(font_tables[f]->charinfo[glyph]),0,sizeof(charinfo)); - font_tables[f]->charinfo[glyph].ef = 1000; /* init */ - font_tables[f]->charinfo_size = glyph; - set_sa_item(font_tables[f]->characters, c, glyph, 1); /* 1= global */ - } - return &(font_tables[f]->charinfo[glyph]); - } else if (c == left_boundarychar) { - if (left_boundary(f)==NULL) { - ci = xcalloc(1,sizeof(charinfo)); - font_bytes += sizeof(charinfo); - set_left_boundary(f,ci); - } - return left_boundary(f); - } else if (c == right_boundarychar) { - if (right_boundary(f)==NULL) { - ci = xcalloc(1,sizeof(charinfo)); - font_bytes += sizeof(charinfo); - set_right_boundary(f,ci); - } - return right_boundary(f); - } - return &(font_tables[f]->charinfo[0]); +#define find_charinfo_id(f,c) get_sa_item(font_tables[f]->characters,c) + +charinfo *get_charinfo(internal_font_number f, integer c) +{ + sa_tree_item glyph; + charinfo *ci; + if (proper_char_index(c)) { + glyph = get_sa_item(Characters(f), c); + if (!glyph) { + /* this could be optimized using controlled growth */ + font_bytes += sizeof(charinfo); + glyph = ++font_tables[f]->charinfo_count; + do_realloc(font_tables[f]->charinfo, (glyph + 1), charinfo); + memset(&(font_tables[f]->charinfo[glyph]), 0, sizeof(charinfo)); + font_tables[f]->charinfo[glyph].ef = 1000; /* init */ + font_tables[f]->charinfo_size = glyph; + set_sa_item(font_tables[f]->characters, c, glyph, 1); /* 1= global */ + } + return &(font_tables[f]->charinfo[glyph]); + } else if (c == left_boundarychar) { + if (left_boundary(f) == NULL) { + ci = xcalloc(1, sizeof(charinfo)); + font_bytes += sizeof(charinfo); + set_left_boundary(f, ci); + } + return left_boundary(f); + } else if (c == right_boundarychar) { + if (right_boundary(f) == NULL) { + ci = xcalloc(1, sizeof(charinfo)); + font_bytes += sizeof(charinfo); + set_right_boundary(f, ci); + } + return right_boundary(f); + } + return &(font_tables[f]->charinfo[0]); +} + +void set_charinfo(internal_font_number f, integer c, charinfo * ci) +{ + sa_tree_item glyph; + if (proper_char_index(c)) { + glyph = get_sa_item(Characters(f), c); + if (glyph) { + font_tables[f]->charinfo[glyph] = *ci; + } else { + pdftex_fail("font: %s", "character insertion failed"); + } + } else if (c == left_boundarychar) { + set_left_boundary(f, ci); + } else if (c == right_boundarychar) { + set_right_boundary(f, ci); + } +} + + + +charinfo *copy_charinfo(charinfo * ci) +{ + int x; + kerninfo *kern; + liginfo *lig; + real_eight_bits *packet; + charinfo *co = NULL; + if (ci == NULL) + return NULL; + co = xmalloc(sizeof(charinfo)); + memcpy(co, ci, sizeof(charinfo)); + set_charinfo_used(co, false); + co->name = NULL; + co->tounicode = NULL; + co->packets = NULL; + co->ligatures = NULL; + co->kerns = NULL; + co->vert_variants = NULL; + co->hor_variants = NULL; + if (ci->name != NULL) { + co->name = xstrdup(ci->name); + } + if (ci->tounicode != NULL) { + co->tounicode = xstrdup(ci->tounicode); + } + /* kerns */ + if ((kern = get_charinfo_kerns(ci)) != NULL) { + x = 0; + while (!kern_end(kern[x])) { + x++; + } + x++; + co->kerns = xmalloc(x * sizeof(kerninfo)); + memcpy(co->kerns, ci->kerns, (x * sizeof(kerninfo))); + } + /* ligs */ + if ((lig = get_charinfo_ligatures(ci)) != NULL) { + x = 0; + while (!lig_end(lig[x])) { + x++; + } + x++; + co->ligatures = xmalloc(x * sizeof(liginfo)); + memcpy(co->ligatures, ci->ligatures, (x * sizeof(liginfo))); + } + /* packets */ + if ((packet = get_charinfo_packets(ci)) != NULL) { + x = vf_packet_bytes(ci); + co->packets = xmalloc(x); + memcpy(co->packets, ci->packets, x); + } + + /* horizontal and vertical extenders */ + if (get_charinfo_vert_variants(ci) != NULL) { + set_charinfo_vert_variants(co, + copy_variants(get_charinfo_vert_variants + (ci))); + } + if (get_charinfo_hor_variants(ci) != NULL) { + set_charinfo_hor_variants(co, + copy_variants(get_charinfo_hor_variants(ci))); + } + return co; +} + +charinfo *char_info(internal_font_number f, integer c) +{ + if (f > font_id_maxval) + return 0; + if (proper_char_index(c)) { + register int glyph = find_charinfo_id(f, c); + return &(font_tables[f]->charinfo[glyph]); + } else if (c == left_boundarychar && left_boundary(f) != NULL) { + return left_boundary(f); + } else if (c == right_boundarychar && right_boundary(f) != NULL) { + return right_boundary(f); + } + return &(font_tables[f]->charinfo[0]); +} + +charinfo_short char_info_short(internal_font_number f, integer c) +{ + charinfo_short s; + charinfo *i; + i = char_info(f, c); + s.ci_wd = i->width; + s.ci_dp = i->depth; + s.ci_ht = i->height; + return s; +} + +integer char_exists(internal_font_number f, integer c) +{ + if (f > font_id_maxval) + return 0; + if (proper_char_index(c)) { + return find_charinfo_id(f, c); + } else if ((c == left_boundarychar) && has_left_boundary(f)) { + return 1; + } else if ((c == right_boundarychar) && has_right_boundary(f)) { + return 1; + } + return 0; +} + +int lua_char_exists_callback(internal_font_number f, integer c) +{ + integer callback_id; + lua_State *L = Luas; + int ret = 0; + callback_id = callback_defined(char_exists_callback); + if (callback_id != 0) { + if (!get_callback(L, callback_id)) { + lua_pop(L, 2); + return 0; + } + lua_pushnumber(L, f); + lua_pushnumber(L, c); + if (lua_pcall(L, 2, 1, 0) != 0) { /* two args, 1 result */ + fprintf(stdout, "error: %s\n", lua_tostring(L, -1)); + lua_pop(L, 2); + error(); + } else { + ret = lua_toboolean(L, -1); + } + } + return ret; } -void -set_charinfo (internal_font_number f, integer c, charinfo *ci) { - sa_tree_item glyph; - if (proper_char_index(c)) { - glyph = get_sa_item(Characters(f), c); - if (glyph) { - font_tables[f]->charinfo[glyph] = *ci; + +extinfo *new_variant(int glyph, int startconnect, int endconnect, + int advance, int repeater) +{ + extinfo *ext; + ext = xmalloc(sizeof(extinfo)); + ext->next = NULL; + ext->glyph = glyph; + ext->start_overlap = startconnect; + ext->end_overlap = endconnect; + ext->advance = advance; + ext->extender = repeater; + return ext; +} + + +extinfo *copy_variant(extinfo * old) +{ + extinfo *ext; + ext = xmalloc(sizeof(extinfo)); + ext->next = NULL; + ext->glyph = old->glyph; + ext->start_overlap = old->start_overlap; + ext->end_overlap = old->end_overlap; + ext->advance = old->advance; + ext->extender = old->extender; + return ext; +} + +void dump_variant(extinfo * ext) +{ + dump_int(ext->glyph); + dump_int(ext->start_overlap); + dump_int(ext->end_overlap); + dump_int(ext->advance); + dump_int(ext->extender); + return; +} + + +extinfo *undump_variant(void) +{ + int x; + extinfo *ext; + undump_int(x); + if (x == 0) + return NULL; + ext = xmalloc(sizeof(extinfo)); + ext->next = NULL; + ext->glyph = x; + undump_int(x); + ext->start_overlap = x; + undump_int(x); + ext->end_overlap = x; + undump_int(x); + ext->advance = x; + undump_int(x); + ext->extender = x; + return ext; +} + +void add_charinfo_vert_variant(charinfo * ci, extinfo * ext) +{ + if (ci->vert_variants == NULL) { + ci->vert_variants = ext; } else { - pdftex_fail("font: %s","character insertion failed"); + extinfo *lst = ci->vert_variants; + while (lst->next != NULL) + lst = lst->next; + lst->next = ext; } - } else if (c == left_boundarychar) { - set_left_boundary(f,ci); - } else if (c == right_boundarychar) { - set_right_boundary(f,ci); - } + } +void add_charinfo_hor_variant(charinfo * ci, extinfo * ext) +{ + if (ci->hor_variants == NULL) { + ci->hor_variants = ext; + } else { + extinfo *lst = ci->hor_variants; + while (lst->next != NULL) + lst = lst->next; + lst->next = ext; + } +} -charinfo * -copy_charinfo (charinfo *ci) { - int x; - kerninfo *kern; - liginfo *lig; - real_eight_bits *packet; - charinfo *co = NULL; - if (ci==NULL) - return NULL; - co = xmalloc(sizeof(charinfo)); - memcpy(co,ci,sizeof(charinfo)); - set_charinfo_used(co,false); - co->name = NULL; - co->tounicode = NULL; - co->packets = NULL; - co->ligatures = NULL; - co->kerns = NULL; - co->extensible = NULL; - if (ci->name!=NULL) { - co->name = xstrdup(ci->name); - } - if (ci->tounicode!=NULL) { - co->tounicode = xstrdup(ci->tounicode); - } - /* kerns */ - if ((kern = get_charinfo_kerns(ci)) != NULL) { - x = 0; - while (!kern_end(kern[x])) { x++; } x++; - co->kerns = xmalloc (x*sizeof(kerninfo)); - memcpy(co->kerns,ci->kerns,(x*sizeof(kerninfo))); - } - /* ligs */ - if ((lig = get_charinfo_ligatures(ci)) != NULL) { - x = 0; - while (!lig_end(lig[x])) { x++; } x++; - co->ligatures = xmalloc (x*sizeof(liginfo)); - memcpy(co->ligatures,ci->ligatures,(x*sizeof(liginfo))); - } - /* packets */ - if ((packet = get_charinfo_packets(ci)) != NULL) { - x = vf_packet_bytes(ci); - co->packets = xmalloc (x); - memcpy(co->packets,ci->packets,x); - } - if (get_charinfo_tag(ci)==ext_tag) { - int top, bot, rep, mid; - top = get_charinfo_extensible(ci,EXT_TOP); - bot = get_charinfo_extensible(ci,EXT_BOT); - mid = get_charinfo_extensible(ci,EXT_MID); - rep = get_charinfo_extensible(ci,EXT_REP); - set_charinfo_extensible(co,top,bot,mid,rep); - } - return co; -} - -#if 0 -int -find_charinfo_id (internal_font_number f, integer c) { - register int g=0; - if (font_tables[f]->charinfo_cache==NULL) { - int i = (font_ec(f)+1)*sizeof(int); - font_tables[f]->charinfo_cache = xmalloc(i); - memset(font_tables[f]->charinfo_cache,0,i); - } else { - g = font_tables[f]->charinfo_cache[c]; - } - if (g==0) { - g = get_sa_item(font_tables[f]->characters, c); - font_tables[f]->charinfo_cache[c] = g; - } - return g; +extinfo *copy_variants(extinfo * o) +{ + extinfo *c, *t = NULL, *h = NULL; + while (o != NULL) { + c = copy_variant(o); + if (h == null) + h = c; + else + t->next = c; + t = c; + o = o->next; + } + + return h; } -#else -#define find_charinfo_id(f,c) get_sa_item(font_tables[f]->characters,c) -#endif - - -charinfo * -char_info (internal_font_number f, integer c) { - if (f>font_id_maxval) - return 0; - if (proper_char_index(c)) { - register int glyph = find_charinfo_id(f,c); - return &(font_tables[f]->charinfo[glyph]); - } else if (c == left_boundarychar && left_boundary(f)!=NULL) { - return left_boundary(f); - } else if (c == right_boundarychar && right_boundary(f)!=NULL) { - return right_boundary(f); - } - return &(font_tables[f]->charinfo[0]); -} - -charinfo_short -char_info_short (internal_font_number f, integer c) { - charinfo_short s; - charinfo *i; - i = char_info(f,c); - s.ci_wd = i->width; - s.ci_dp = i->depth; - s.ci_ht = i->height; - return s; -} - -integer -char_exists (internal_font_number f, integer c) { - if (f>font_id_maxval) - return 0; - if (proper_char_index(c)) { - return find_charinfo_id(f,c); - } else if ((c == left_boundarychar) && has_left_boundary(f)) { - return 1; - } else if ((c == right_boundarychar) && has_right_boundary(f)) { - return 1; - } - return 0; -} - -int -lua_char_exists_callback (internal_font_number f, integer c) { - integer callback_id ; - lua_State *L = Luas[0]; - int ret=0; - callback_id = callback_defined(char_exists_callback); - if (callback_id!=0) { - lua_rawgeti(L,LUA_REGISTRYINDEX,callback_callbacks_id); - lua_rawgeti(L,-1, callback_id); - if (!lua_isfunction(L,-1)) { - lua_pop(L,2); - return 0; - } - lua_pushnumber(L,f); - lua_pushnumber(L,c); - if (lua_pcall(L,2,1,0) != 0) { /* two args, 1 result */ - fprintf(stdout,"error: %s\n",lua_tostring(L,-1)); - lua_pop(L,2); - error(); - } else { - ret = lua_toboolean(L,-1); - } - } - return ret; -} - - -void set_charinfo_width (charinfo *ci, scaled val) { ci->width = val; } -void set_charinfo_height (charinfo *ci, scaled val) { ci->height = val; } -void set_charinfo_depth (charinfo *ci, scaled val) { ci->depth = val; } -void set_charinfo_italic (charinfo *ci, scaled val) { ci->italic = val; } -void set_charinfo_tag (charinfo *ci, scaled val) { ci->tag = val; } -void set_charinfo_remainder (charinfo *ci, scaled val) { ci->remainder = val; } -void set_charinfo_used (charinfo *ci, scaled val) { ci->used = val; } -void set_charinfo_index (charinfo *ci, scaled val) { ci->index = val; } -void set_charinfo_name (charinfo *ci, char *val) { dxfree(ci->name,val); } -void set_charinfo_tounicode (charinfo *ci, char *val) { dxfree(ci->tounicode,val); } -void set_charinfo_ligatures (charinfo *ci, liginfo *val) { dxfree(ci->ligatures,val); } -void set_charinfo_kerns (charinfo *ci, kerninfo *val) { dxfree(ci->kerns,val); } -void set_charinfo_packets (charinfo *ci, real_eight_bits *val){ dxfree(ci->packets,val); } -void set_charinfo_ef (charinfo *ci, scaled val) { ci->ef = val; } -void set_charinfo_lp (charinfo *ci, scaled val) { ci->lp = val; } -void set_charinfo_rp (charinfo *ci, scaled val) { ci->rp = val; } - - - -void set_charinfo_extensible (charinfo *ci, int top, int bot, int mid, int rep) { - if (top == 0 && bot == 0 && mid == 0 && rep == 0) { - if (ci->extensible != NULL) { - free(ci->extensible); - ci->extensible = NULL; - } - } else { - if (ci->extensible == NULL) { - ci->extensible = xmalloc(4*sizeof(integer)); - } - ci->extensible[EXT_TOP] = top; - ci->extensible[EXT_BOT] = bot; - ci->extensible[EXT_MID] = mid; - ci->extensible[EXT_REP] = rep; - } + + +void dump_charinfo_variants(extinfo * o) +{ + while (o != NULL) { + dump_variant(o); + o = o->next; + } + dump_int(0); + return; } - -scaled get_charinfo_width (charinfo *ci) { return ci->width; } -scaled get_charinfo_height (charinfo *ci) { return ci->height; } -scaled get_charinfo_depth (charinfo *ci) { return ci->depth; } -scaled get_charinfo_italic (charinfo *ci) { return ci->italic; } -char get_charinfo_tag (charinfo *ci) { return ci->tag; } -integer get_charinfo_remainder (charinfo *ci) { return ci->remainder; } -char get_charinfo_used (charinfo *ci) { return ci->used; } -integer get_charinfo_index (charinfo *ci) { return ci->index; } -char *get_charinfo_name (charinfo *ci) { return ci->name; } -char *get_charinfo_tounicode (charinfo *ci) { return ci->tounicode; } -liginfo *get_charinfo_ligatures (charinfo *ci) { return ci->ligatures; } -kerninfo *get_charinfo_kerns (charinfo *ci) { return ci->kerns; } -real_eight_bits *get_charinfo_packets (charinfo *ci) { return ci->packets; } -integer get_charinfo_ef (charinfo *ci) { return ci->ef; } -integer get_charinfo_rp (charinfo *ci) { return ci->rp; } -integer get_charinfo_lp (charinfo *ci) { return ci->lp; } -integer get_charinfo_extensible (charinfo *ci, int whch) { - int w = 0; - if (ci->extensible != NULL) - w = ci->extensible[whch]; - return w; +extinfo *undump_charinfo_variants(void) +{ + extinfo *c, *t, *h = NULL; + c = undump_variant(); + while (c != NULL) { + if (h == null) + h = c; + else + t->next = c; + t = c; + c = undump_variant(); + } + return h; } -integer ext_top (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - integer w = get_charinfo_extensible(ci,EXT_TOP); - /* fprintf(stdout,"top of char 0x%4x in font %s: %i\n",c,font_name(f),w);*/ - return w; -} -integer ext_bot (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - integer w = get_charinfo_extensible(ci,EXT_BOT); - /*fprintf(stdout,"bot of char 0x%4x in font %s: %i\n",c,font_name(f),w);*/ - return w; +void set_charinfo_width(charinfo * ci, scaled val) +{ + ci->width = val; } -integer ext_mid (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - integer w = get_charinfo_extensible(ci,EXT_MID); - /*fprintf(stdout,"mid of char 0x%4x in font %s: %i\n",c,font_name(f),w);*/ - return w; + +void set_charinfo_height(charinfo * ci, scaled val) +{ + ci->height = val; } -integer ext_rep (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - integer w = get_charinfo_extensible(ci,EXT_REP); - /*fprintf(stdout,"rep of char 0x%4x in font %s: %i\n",c,font_name(f),w);*/ - return w; + +void set_charinfo_depth(charinfo * ci, scaled val) +{ + ci->depth = val; } -scaled char_width (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - scaled w = get_charinfo_width(ci); - /*fprintf(stdout,"width of char 0x%x in font %s: %i\n",c,font_name(f),w);*/ - return w; -} - -scaled char_depth (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - scaled w = get_charinfo_depth(ci); - /*fprintf(stdout,"depth of char 0x%x in font %s: %i\n",c,font_name(f),w);*/ - return w; -} - -scaled char_height (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - scaled w = get_charinfo_height(ci); - /*fprintf(stdout,"height of char 0x%x in font %s: %i\n",c,font_name(f),w);*/ - return w; -} - -scaled char_italic (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_italic(ci); -} - -integer char_remainder (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_remainder(ci); -} - -char char_tag (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_tag(ci); -} - -char char_used (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_used(ci); -} - -char *char_name (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_name(ci); -} - -integer char_index (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_index(ci); -} - -liginfo * char_ligatures (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_ligatures(ci); -} - -kerninfo * char_kerns (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_kerns(ci); -} - -real_eight_bits * char_packets (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_packets(ci); -} - - -void -set_font_params(internal_font_number f, int b) { - int i; - i = font_params(f); - if (i!=b) { - font_bytes += (b-font_params(f))*sizeof(scaled); - do_realloc(param_base(f), (b+1), integer); - font_params(f) = b; - if (b>i) { - while (i<b) { - i++; - set_font_param(f,i,0); - } - } - } -} - - -integer -copy_font (integer f) { - int i; - charinfo *ci , *co; - integer k = new_font(); - memcpy(font_tables[k],font_tables[f],sizeof(texfont)); - - set_font_cache_id(k,0); - set_font_used(k,0); - set_font_touched(k,0); - - font_tables[k]->_font_name = NULL; - font_tables[k]->_font_filename = NULL; - font_tables[k]->_font_fullname = NULL; - font_tables[k]->_font_encodingname = NULL; - font_tables[k]->_font_area = NULL; - font_tables[k]->_font_cidregistry = NULL; - font_tables[k]->_font_cidordering = NULL; - font_tables[k]->_left_boundary = NULL; - font_tables[k]->_right_boundary = NULL; - - set_font_name(k,xstrdup(font_name(f))); - if (font_filename(f)!= NULL) - set_font_filename(k,xstrdup(font_filename(f))); - if (font_fullname(f)!= NULL) - set_font_fullname(k,xstrdup(font_fullname(f))); - if (font_encodingname(f)!= NULL) - set_font_encodingname(k,xstrdup(font_encodingname(f))); - if (font_area(f)!= NULL) - set_font_area(k,xstrdup(font_area(f))); - if (font_cidregistry(f)!= NULL) - set_font_cidregistry(k,xstrdup(font_cidregistry(f))); - if (font_cidordering(f)!= NULL) - set_font_cidordering(k,xstrdup(font_cidordering(f))); - - i = sizeof(*param_base(f))*font_params(f); - font_bytes += i; - param_base(k) = xmalloc (i); - memcpy(param_base(k),param_base(f), i); - - i = sizeof(charinfo)*(Charinfo_size(f)+1); - font_bytes += i; - font_tables[k]->charinfo = xmalloc(i); - memset(font_tables[k]->charinfo,0,i); - for(i=0;i<=Charinfo_size(k);i++) { - ci = copy_charinfo(&font_tables[f]->charinfo[i]); - font_tables[k]->charinfo[i] = *ci; - } - - if (left_boundary(f)!= NULL ) { - ci = copy_charinfo(left_boundary(f)); - set_charinfo(k,left_boundarychar,ci); - } +void set_charinfo_italic(charinfo * ci, scaled val) +{ + ci->italic = val; +} - if (right_boundary(f)!= NULL ) { - ci = copy_charinfo(right_boundary(f)); - set_charinfo(k,right_boundarychar,ci); - } - return k; -} - -void delete_font (integer f) { - int i; - charinfo *co; - assert(f>0); - if (font_tables[f]!=NULL) { - set_font_name(f,NULL); - set_font_filename(f,NULL); - set_font_fullname(f,NULL); - set_font_encodingname(f,NULL); - set_font_area(f,NULL); - set_font_cidregistry(f,NULL); - set_font_cidordering(f,NULL); - set_left_boundary(f,NULL); - set_right_boundary(f,NULL); - - for(i=font_bc(f); i<=font_ec(f); i++) { - if (char_exists(f,i)) { - co = char_info(f,i); - set_charinfo_name(co,NULL); - set_charinfo_tounicode(co,NULL); - set_charinfo_packets(co,NULL); - set_charinfo_ligatures(co,NULL); - set_charinfo_kerns(co,NULL); - set_charinfo_extensible(co,0,0,0,0); - } - } - /* free .notdef */ - set_charinfo_name(font_tables[f]->charinfo+0,NULL); - free(font_tables[f]->charinfo); - destroy_sa_tree(font_tables[f]->characters); - - free(param_base(f)); - free(font_tables[f]); - font_tables[f] = NULL; +void set_charinfo_top_accent(charinfo * ci, scaled val) +{ + ci->top_accent = val; +} + +void set_charinfo_bot_accent(charinfo * ci, scaled val) +{ + ci->bot_accent = val; +} + +void set_charinfo_tag(charinfo * ci, scaled val) +{ + ci->tag = val; +} + +void set_charinfo_remainder(charinfo * ci, scaled val) +{ + ci->remainder = val; +} + +void set_charinfo_used(charinfo * ci, scaled val) +{ + ci->used = val; +} - if (font_id_maxval==f) { - font_id_maxval--; +void set_charinfo_index(charinfo * ci, scaled val) +{ + ci->index = val; +} +void set_charinfo_name(charinfo * ci, char *val) +{ + dxfree(ci->name, val); +} +void set_charinfo_tounicode(charinfo * ci, char *val) +{ + dxfree(ci->tounicode, val); +} + +void set_charinfo_ligatures(charinfo * ci, liginfo * val) +{ + dxfree(ci->ligatures, val); +} + +void set_charinfo_kerns(charinfo * ci, kerninfo * val) +{ + dxfree(ci->kerns, val); +} + +void set_charinfo_packets(charinfo * ci, real_eight_bits * val) +{ + dxfree(ci->packets, val); +} + +void set_charinfo_ef(charinfo * ci, scaled val) +{ + ci->ef = val; +} + +void set_charinfo_lp(charinfo * ci, scaled val) +{ + ci->lp = val; +} + +void set_charinfo_rp(charinfo * ci, scaled val) +{ + ci->rp = val; +} + +void set_charinfo_vert_variants(charinfo * ci, extinfo * ext) +{ + extinfo *c, *lst; + if (ci->vert_variants != NULL) { + lst = ci->vert_variants; + while (lst != NULL) { + c = lst->next; + free(lst); + lst = c; + } } - } + ci->vert_variants = ext; +} + +void set_charinfo_hor_variants(charinfo * ci, extinfo * ext) +{ + extinfo *c, *lst; + if (ci->hor_variants != NULL) { + lst = ci->hor_variants; + while (lst != NULL) { + c = lst->next; + free(lst); + lst = c; + } + } + ci->hor_variants = ext; + +} + +/* In TeX, extensibles were fairly simple things. + This function squeezes a TFM extensible into the vertical extender structures. + |advance==0| is a special case for TFM fonts, because finding the proper + advance width during tfm reading can be tricky +*/ + +/* a small complication arises if |rep| is the only non-zero: it needs to be + doubled as a non-repeatable to avoid mayhem */ + +void set_charinfo_extensible(charinfo * ci, int top, int bot, int mid, int rep) +{ + extinfo *ext; + set_charinfo_vert_variants(ci, NULL); /* clear old */ + if (bot == 0 && top == 0 && mid == 0 && rep != 0) { + ext = new_variant(rep, 0, 0, 0, EXT_NORMAL); + add_charinfo_vert_variant(ci, ext); + ext = new_variant(rep, 0, 0, 0, EXT_REPEAT); + add_charinfo_vert_variant(ci, ext); + return; + } + if (bot != 0) { + ext = new_variant(bot, 0, 0, 0, EXT_NORMAL); + add_charinfo_vert_variant(ci, ext); + } + if (rep != 0) { + ext = new_variant(rep, 0, 0, 0, EXT_REPEAT); + add_charinfo_vert_variant(ci, ext); + } + if (mid != 0) { + ext = new_variant(mid, 0, 0, 0, EXT_NORMAL); + add_charinfo_vert_variant(ci, ext); + if (rep != 0) { + ext = new_variant(rep, 0, 0, 0, EXT_REPEAT); + add_charinfo_vert_variant(ci, ext); + } + } + if (top != 0) { + ext = new_variant(top, 0, 0, 0, EXT_NORMAL); + add_charinfo_vert_variant(ci, ext); + } +} + +scaled get_charinfo_width(charinfo * ci) +{ + return ci->width; +} + +scaled get_charinfo_height(charinfo * ci) +{ + return ci->height; +} + +scaled get_charinfo_depth(charinfo * ci) +{ + return ci->depth; +} + +scaled get_charinfo_italic(charinfo * ci) +{ + return ci->italic; +} + +scaled get_charinfo_top_accent(charinfo * ci) +{ + return ci->top_accent; +} + +scaled get_charinfo_bot_accent(charinfo * ci) +{ + return ci->bot_accent; +} + +char get_charinfo_tag(charinfo * ci) +{ + return ci->tag; +} + +integer get_charinfo_remainder(charinfo * ci) +{ + return ci->remainder; } -void -create_null_font (void) { - int i = new_font(); - assert(i==0); - set_font_name(i,xstrdup("nullfont")); - set_font_area(i,xstrdup("")); - set_font_touched(i,1); +char get_charinfo_used(charinfo * ci) +{ + return ci->used; } -boolean -is_valid_font (integer id) { - int ret=0; - if (id>=0 && id<=font_id_maxval && font_tables[id]!=NULL) - ret=1; - return ret; +integer get_charinfo_index(charinfo * ci) +{ + return ci->index; +} + +char *get_charinfo_name(charinfo * ci) +{ + return ci->name; +} + +char *get_charinfo_tounicode(charinfo * ci) +{ + return ci->tounicode; +} + +liginfo *get_charinfo_ligatures(charinfo * ci) +{ + return ci->ligatures; +} + +kerninfo *get_charinfo_kerns(charinfo * ci) +{ + return ci->kerns; +} + +real_eight_bits *get_charinfo_packets(charinfo * ci) +{ + return ci->packets; +} + +integer get_charinfo_ef(charinfo * ci) +{ + return ci->ef; +} + +integer get_charinfo_rp(charinfo * ci) +{ + return ci->rp; +} + +integer get_charinfo_lp(charinfo * ci) +{ + return ci->lp; +} + +extinfo *get_charinfo_vert_variants(charinfo * ci) +{ + extinfo *w = NULL; + if (ci->vert_variants != NULL) + w = ci->vert_variants; + return w; +} + +extinfo *get_charinfo_hor_variants(charinfo * ci) +{ + extinfo *w = NULL; + if (ci->hor_variants != NULL) + w = ci->hor_variants; + return w; +} + + +scaled char_width(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + scaled w = get_charinfo_width(ci); + /*fprintf(stdout,"width of char 0x%x in font %s: %i\n",c,font_name(f),w); */ + return w; +} + +scaled char_depth(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + scaled w = get_charinfo_depth(ci); + /*fprintf(stdout,"depth of char 0x%x in font %s: %i\n",c,font_name(f),w); */ + return w; +} + +scaled char_height(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + scaled w = get_charinfo_height(ci); + /*fprintf(stdout,"height of char 0x%x in font %s: %i\n",c,font_name(f),w); */ + return w; +} + +scaled char_italic(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_italic(ci); +} + +scaled char_top_accent(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_top_accent(ci); +} + +scaled char_bot_accent(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_bot_accent(ci); +} + + +integer char_remainder(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_remainder(ci); +} + +char char_tag(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_tag(ci); +} + +char char_used(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_used(ci); +} + +char *char_name(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_name(ci); +} + +integer char_index(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_index(ci); +} + +liginfo *char_ligatures(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_ligatures(ci); +} + +kerninfo *char_kerns(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_kerns(ci); +} + +real_eight_bits *char_packets(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_packets(ci); +} + + +void set_font_params(internal_font_number f, int b) +{ + int i; + i = font_params(f); + if (i != b) { + font_bytes += (b - font_params(f) + 1) * sizeof(scaled); + do_realloc(param_base(f), (b + 2), integer); + font_params(f) = b; + if (b > i) { + while (i < b) { + i++; + set_font_param(f, i, 0); + } + } + } +} + +void set_font_math_params(internal_font_number f, int b) +{ + int i; + i = font_math_params(f); + if (i != b) { + font_bytes += (b - font_math_params(f) + 1) * sizeof(scaled); + do_realloc(math_param_base(f), (b + 2), integer); + font_math_params(f) = b; + if (b > i) { + while (i < b) { + i++; + set_font_math_param(f, i, undefined_math_parameter); + } + } + } +} + + + +integer copy_font(integer f) +{ + int i; + charinfo *ci; + integer k = new_font(); + memcpy(font_tables[k], font_tables[f], sizeof(texfont)); + + set_font_cache_id(k, 0); + set_font_used(k, 0); + set_font_touched(k, 0); + + font_tables[k]->_font_name = NULL; + font_tables[k]->_font_filename = NULL; + font_tables[k]->_font_fullname = NULL; + font_tables[k]->_font_encodingname = NULL; + font_tables[k]->_font_area = NULL; + font_tables[k]->_font_cidregistry = NULL; + font_tables[k]->_font_cidordering = NULL; + font_tables[k]->_left_boundary = NULL; + font_tables[k]->_right_boundary = NULL; + + set_font_name(k, xstrdup(font_name(f))); + if (font_filename(f) != NULL) + set_font_filename(k, xstrdup(font_filename(f))); + if (font_fullname(f) != NULL) + set_font_fullname(k, xstrdup(font_fullname(f))); + if (font_encodingname(f) != NULL) + set_font_encodingname(k, xstrdup(font_encodingname(f))); + if (font_area(f) != NULL) + set_font_area(k, xstrdup(font_area(f))); + if (font_cidregistry(f) != NULL) + set_font_cidregistry(k, xstrdup(font_cidregistry(f))); + if (font_cidordering(f) != NULL) + set_font_cidordering(k, xstrdup(font_cidordering(f))); + + i = sizeof(*param_base(f)) * font_params(f); + font_bytes += i; + param_base(k) = xmalloc(i); + memcpy(param_base(k), param_base(f), i); + + if (font_math_params(f) > 0) { + i = sizeof(*math_param_base(f)) * font_math_params(f); + font_bytes += i; + math_param_base(k) = xmalloc(i); + memcpy(math_param_base(k), math_param_base(f), i); + } + + i = sizeof(charinfo) * (Charinfo_size(f) + 1); + font_bytes += i; + font_tables[k]->charinfo = xmalloc(i); + memset(font_tables[k]->charinfo, 0, i); + for (i = 0; i <= Charinfo_size(k); i++) { + ci = copy_charinfo(&font_tables[f]->charinfo[i]); + font_tables[k]->charinfo[i] = *ci; + } + + if (left_boundary(f) != NULL) { + ci = copy_charinfo(left_boundary(f)); + set_charinfo(k, left_boundarychar, ci); + } + + if (right_boundary(f) != NULL) { + ci = copy_charinfo(right_boundary(f)); + set_charinfo(k, right_boundarychar, ci); + } + return k; +} + +void delete_font(integer f) +{ + int i; + charinfo *co; + assert(f > 0); + if (font_tables[f] != NULL) { + set_font_name(f, NULL); + set_font_filename(f, NULL); + set_font_fullname(f, NULL); + set_font_encodingname(f, NULL); + set_font_area(f, NULL); + set_font_cidregistry(f, NULL); + set_font_cidordering(f, NULL); + set_left_boundary(f, NULL); + set_right_boundary(f, NULL); + + for (i = font_bc(f); i <= font_ec(f); i++) { + if (char_exists(f, i)) { + co = char_info(f, i); + set_charinfo_name(co, NULL); + set_charinfo_tounicode(co, NULL); + set_charinfo_packets(co, NULL); + set_charinfo_ligatures(co, NULL); + set_charinfo_kerns(co, NULL); + set_charinfo_vert_variants(co, NULL); + set_charinfo_hor_variants(co, NULL); + } + } + /* free .notdef */ + set_charinfo_name(font_tables[f]->charinfo + 0, NULL); + free(font_tables[f]->charinfo); + destroy_sa_tree(font_tables[f]->characters); + + free(param_base(f)); + if (math_param_base(f) != NULL) + free(math_param_base(f)); + free(font_tables[f]); + font_tables[f] = NULL; + + if (font_id_maxval == f) { + font_id_maxval--; + } + } +} + +void create_null_font(void) +{ + int i = new_font(); + assert(i == 0); + set_font_name(i, xstrdup("nullfont")); + set_font_area(i, xstrdup("")); + set_font_touched(i, 1); +} + +boolean is_valid_font(integer id) +{ + int ret = 0; + if (id >= 0 && id <= font_id_maxval && font_tables[id] != NULL) + ret = 1; + return ret; } /* return 1 == identical */ -boolean -cmp_font_name (integer id, strnumber t) { - char *tid , *tt; - if (!is_valid_font(id)) - return 0; - tt = makecstring(t); - tid = font_name(id); - if (tt == NULL && tid == NULL) +boolean cmp_font_name(integer id, strnumber t) +{ + char *tid, *tt; + if (!is_valid_font(id)) + return 0; + tt = makecstring(t); + tid = font_name(id); + if (tt == NULL && tid == NULL) + return 1; + if (tt == NULL || tid == NULL || strcmp(tid, tt) != 0) + return 0; return 1; - if (tt == NULL || tid == NULL || strcmp(tid,tt)!=0) - return 0; - return 1; -} - -boolean -cmp_font_area (integer id, strnumber t) { - char *tt = NULL; - char *tid = font_area(id); - if (t == 0) { - if (tid == NULL || strlen(tid)==0) - return 1; - else - return 0; - } - tt = makecstring(t); - if ((tt == NULL || strlen(tt)==0) && (tid == NULL || strlen(tid)==0)) +} + +boolean cmp_font_area(integer id, strnumber t) +{ + char *tt = NULL; + char *tid = font_area(id); + if (t == 0) { + if (tid == NULL || strlen(tid) == 0) + return 1; + else + return 0; + } + tt = makecstring(t); + if ((tt == NULL || strlen(tt) == 0) && (tid == NULL || strlen(tid) == 0)) + return 1; + if (tt == NULL || strcmp(tid, tt) != 0) + return 0; return 1; - if (tt == NULL || strcmp(tid,tt)!=0) - return 0; - return 1; } -static boolean -same_font_name (integer id, integer t) { - int ret = 0; - if (font_name(t) == NULL || - font_name(id) == NULL || - strcmp(font_name(t),font_name(id))!=0) { - ; - } else { - ret =1 ; - } - return ret; -} - -boolean -font_shareable (internal_font_number f, internal_font_number k) { - int ret = 0; - if (font_cidregistry(f) == NULL) { - if ( hasfmentry ( k ) - && ( font_map ( k ) == font_map ( f ) ) - && ( same_font_name ( k , f ) - || - ( pdf_font_auto_expand (f) - && ( pdf_font_blink (f) != 0 ) /* 0 = nullfont */ - && same_font_name ( k , pdf_font_blink (f) ) ) ) ) { - ret = 1; - } - } else { - if ((font_filename(k) != NULL && font_filename(f) != NULL && - strcmp(font_filename(k),font_filename(f)) == 0) - || - ( pdf_font_auto_expand (f) - && ( pdf_font_blink (f) != 0 ) /* 0 = nullfont */ - && same_font_name ( k , pdf_font_blink (f) ) ) ) { - ret = 1; +static boolean same_font_name(integer id, integer t) +{ + int ret = 0; + if (font_name(t) == NULL || + font_name(id) == NULL || strcmp(font_name(t), font_name(id)) != 0) { + ; + } else { + ret = 1; } - } - return ret; -} - -integer -test_no_ligatures (internal_font_number f) { - integer c; - for (c=font_bc(f);c<=font_ec(f);c++) { - if (has_lig(f,c)) /* char_exists(f,c) */ - return 0; - } - return 1; -} - -integer -get_tag_code (internal_font_number f, integer c) { - small_number i; - if (char_exists(f,c)) { - i = char_tag(f,c); - if (i==lig_tag) return 1; - else if (i==list_tag) return 2; - else if (i==ext_tag) return 4; - else return 0; - } - return -1; -} - -integer -get_lp_code (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_lp(ci); -} - -integer -get_rp_code (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_rp(ci); -} - -integer -get_ef_code (internal_font_number f, integer c) { - charinfo *ci = char_info(f,c); - return get_charinfo_ef(ci); -} - -void -set_tag_code (internal_font_number f, integer c, integer i) { - integer fixedi; - charinfo * co; - if (char_exists(f,c)) { - /* abs(fix_int(i-7,0)) */ - fixedi = - (i<-7 ? -7 : (i>0 ? 0 : i )) ; - co = char_info(f,c); - if (fixedi >= 4) { - if (char_tag(f,c) == ext_tag) - set_charinfo_tag(co,(char_tag(f,c)- ext_tag)); - fixedi = fixedi - 4; - } - if (fixedi >= 2) { - if (char_tag(f,c) == list_tag) - set_charinfo_tag(co,(char_tag(f,c)- list_tag)); - fixedi = fixedi - 2; - }; - if (fixedi >= 1) { - if (has_lig(f,c)) - set_charinfo_ligatures(co,NULL); - if (has_kern(f,c)) - set_charinfo_kerns(co,NULL); + return ret; +} + +boolean font_shareable(internal_font_number f, internal_font_number k) +{ + int ret = 0; + /* For some lua-loaded (for instance AFM) fonts, it is normal to have + a zero cidregistry, and such fonts do not have a fontmap entry yet + at this point, so the test shoulh use the other branch */ + if (font_cidregistry(f) == NULL && font_cidregistry(k) == NULL && + font_encodingbytes(f) != 2 && font_encodingbytes(k) != 2) { + if (hasfmentry(k) + && (font_map(k) == font_map(f)) + && (same_font_name(k, f) + || (pdf_font_auto_expand(f) + && (pdf_font_blink(f) != 0) /* 0 = nullfont */ + &&same_font_name(k, pdf_font_blink(f))))) { + ret = 1; + } + } else { + if ((font_filename(k) != NULL && font_filename(f) != NULL && + strcmp(font_filename(k), font_filename(f)) == 0) + || (pdf_font_auto_expand(f) + && (pdf_font_blink(f) != 0) /* 0 = nullfont */ + &&same_font_name(k, pdf_font_blink(f)))) { + ret = 1; + } } - } + return ret; } +integer test_no_ligatures(internal_font_number f) +{ + integer c; + for (c = font_bc(f); c <= font_ec(f); c++) { + if (has_lig(f, c)) /* char_exists(f,c) */ + return 0; + } + return 1; +} -void -set_lp_code(internal_font_number f, integer c, integer i) { - charinfo * co; - if (char_exists(f,c)) { - co = char_info(f,c); - set_charinfo_lp(co,i); - } +integer get_tag_code(internal_font_number f, integer c) +{ + small_number i; + if (char_exists(f, c)) { + i = char_tag(f, c); + if (i == lig_tag) + return 1; + else if (i == list_tag) + return 2; + else if (i == ext_tag) + return 4; + else + return 0; + } + return -1; } -void -set_rp_code(internal_font_number f, integer c, integer i) { - charinfo * co; - if (char_exists(f,c)) { - co = char_info(f,c); - set_charinfo_rp(co,i); - } +integer get_lp_code(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_lp(ci); } -void -set_ef_code(internal_font_number f, integer c, integer i) { - charinfo * co; - if (char_exists(f,c)) { - co = char_info(f,c); - set_charinfo_ef(co,i); - } +integer get_rp_code(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_rp(ci); } -void -set_no_ligatures (internal_font_number f) { - integer c; - charinfo * co; - - if (font_tables[f]->ligatures_disabled) - return; - - co = char_info(f,left_boundarychar); - set_charinfo_ligatures(co,NULL); - co = char_info(f,right_boundarychar); /* this is weird */ - set_charinfo_ligatures(co,NULL); - for (c=0;c<font_tables[f]->charinfo_count;c++) { - co = font_tables[f]->charinfo+c; - set_charinfo_ligatures(co,NULL); - } - font_tables[f]->ligatures_disabled =1; +integer get_ef_code(internal_font_number f, integer c) +{ + charinfo *ci = char_info(f, c); + return get_charinfo_ef(ci); +} + +void set_tag_code(internal_font_number f, integer c, integer i) +{ + integer fixedi; + charinfo *co; + if (char_exists(f, c)) { + /* abs(fix_int(i-7,0)) */ + fixedi = -(i < -7 ? -7 : (i > 0 ? 0 : i)); + co = char_info(f, c); + if (fixedi >= 4) { + if (char_tag(f, c) == ext_tag) + set_charinfo_tag(co, (char_tag(f, c) - ext_tag)); + fixedi = fixedi - 4; + } + if (fixedi >= 2) { + if (char_tag(f, c) == list_tag) + set_charinfo_tag(co, (char_tag(f, c) - list_tag)); + fixedi = fixedi - 2; + }; + if (fixedi >= 1) { + if (has_lig(f, c)) + set_charinfo_ligatures(co, NULL); + if (has_kern(f, c)) + set_charinfo_kerns(co, NULL); + } + } } -liginfo -get_ligature (internal_font_number f, integer lc, integer rc) { - liginfo t, u; - charinfo * co; - t.lig = 0; - t.type = 0; - t.adj = 0; - if (lc == non_boundarychar || rc == non_boundarychar || (!has_lig(f,lc)) ) + +void set_lp_code(internal_font_number f, integer c, integer i) +{ + charinfo *co; + if (char_exists(f, c)) { + co = char_info(f, c); + set_charinfo_lp(co, i); + } +} + +void set_rp_code(internal_font_number f, integer c, integer i) +{ + charinfo *co; + if (char_exists(f, c)) { + co = char_info(f, c); + set_charinfo_rp(co, i); + } +} + +void set_ef_code(internal_font_number f, integer c, integer i) +{ + charinfo *co; + if (char_exists(f, c)) { + co = char_info(f, c); + set_charinfo_ef(co, i); + } +} + +void set_no_ligatures(internal_font_number f) +{ + integer c; + charinfo *co; + + if (font_tables[f]->ligatures_disabled) + return; + + co = char_info(f, left_boundarychar); + set_charinfo_ligatures(co, NULL); + co = char_info(f, right_boundarychar); /* this is weird */ + set_charinfo_ligatures(co, NULL); + for (c = 0; c < font_tables[f]->charinfo_count; c++) { + co = font_tables[f]->charinfo + c; + set_charinfo_ligatures(co, NULL); + } + font_tables[f]->ligatures_disabled = 1; +} + +liginfo get_ligature(internal_font_number f, integer lc, integer rc) +{ + liginfo t, u; + charinfo *co; + t.lig = 0; + t.type = 0; + t.adj = 0; + if (lc == non_boundarychar || rc == non_boundarychar || (!has_lig(f, lc))) + return t; + k = 0; + co = char_info(f, lc); + while (1) { + u = charinfo_ligature(co, k); + if (lig_end(u)) + break; + if (lig_char(u) == rc) { + if (lig_disabled(u)) { + return t; + } else { + return u; + } + } + k++; + } return t; - k = 0; - co = char_info(f,lc); - while (1) { - u = charinfo_ligature(co,k); - if (lig_end(u)) - break; - if (lig_char(u) == rc) { - if (lig_disabled(u)) { - return t; - } else { - return u; - } - } - k++; - } - return t; } -scaled -get_kern(internal_font_number f, integer lc, integer rc) +scaled raw_get_kern(internal_font_number f, integer lc, integer rc) { - integer k; - kerninfo u; - charinfo * co; - if (lc == non_boundarychar || rc == non_boundarychar || (!has_kern(f,lc)) ) + integer k; + kerninfo u; + charinfo *co; + if (lc == non_boundarychar || rc == non_boundarychar) + return 0; + k = 0; + co = char_info(f, lc); + while (1) { + u = charinfo_kern(co, k); + if (kern_end(u)) + break; + if (kern_char(u) == rc) { + if (kern_disabled(u)) + return 0; + else + return kern_kern(u); + } + k++; + } return 0; - k = 0; - co = char_info(f,lc); - while (1) { - u = charinfo_kern(co,k); - if (kern_end(u)) - break; - if (kern_char(u) == rc) { - if (kern_disabled(u)) - return 0; - else - return kern_kern(u); - } - k++; - } - return 0; +} + + +scaled get_kern(internal_font_number f, integer lc, integer rc) +{ + if (lc == non_boundarychar || rc == non_boundarychar || (!has_kern(f, lc))) + return 0; + return raw_get_kern(f, lc, rc); } /* dumping and undumping fonts */ -#define dump_string(a) \ - if (a!=NULL) { \ - x = strlen(a)+1; \ - dump_int(x); dump_things(*a, x); \ - } else { \ - x = 0; dump_int(x); \ +#define dump_string(a) \ + if (a!=NULL) { \ + x = strlen(a)+1; \ + dump_int(x); dump_things(*a, x); \ + } else { \ + x = 0; dump_int(x); \ } -void -dump_charinfo (int f , int c) { - charinfo *co; - int x; - liginfo *lig; - kerninfo *kern; - - dump_int(c); - co = char_info(f,c); - set_charinfo_used(co,0); - dump_int(get_charinfo_width(co)); - dump_int(get_charinfo_height(co)); - dump_int(get_charinfo_depth(co)); - dump_int(get_charinfo_italic(co)); - dump_int(get_charinfo_tag(co)); - dump_int(get_charinfo_ef(co)); - dump_int(get_charinfo_rp(co)); - dump_int(get_charinfo_lp(co)); - dump_int(get_charinfo_remainder(co)); - dump_int(get_charinfo_used(co)); - dump_int(get_charinfo_index(co)); - dump_string(get_charinfo_name(co)); - dump_string(get_charinfo_tounicode(co)); - - /* ligatures */ - x = 0; - if ((lig = get_charinfo_ligatures(co)) != NULL) { - while (!lig_end(lig[x])) { x++; } - x++; - dump_int(x); dump_things(*lig, x); - } else { +void dump_charinfo(int f, int c) +{ + charinfo *co; + int x; + liginfo *lig; + kerninfo *kern; + dump_int(c); + co = char_info(f, c); + set_charinfo_used(co, 0); + dump_int(get_charinfo_width(co)); + dump_int(get_charinfo_height(co)); + dump_int(get_charinfo_depth(co)); + dump_int(get_charinfo_italic(co)); + dump_int(get_charinfo_top_accent(co)); + dump_int(get_charinfo_bot_accent(co)); + dump_int(get_charinfo_tag(co)); + dump_int(get_charinfo_ef(co)); + dump_int(get_charinfo_rp(co)); + dump_int(get_charinfo_lp(co)); + dump_int(get_charinfo_remainder(co)); + dump_int(get_charinfo_used(co)); + dump_int(get_charinfo_index(co)); + dump_string(get_charinfo_name(co)); + dump_string(get_charinfo_tounicode(co)); + + /* ligatures */ + x = 0; + if ((lig = get_charinfo_ligatures(co)) != NULL) { + while (!lig_end(lig[x])) { + x++; + } + x++; + dump_int(x); + dump_things(*lig, x); + } else { + dump_int(x); + } + /* kerns */ + x = 0; + if ((kern = get_charinfo_kerns(co)) != NULL) { + while (!kern_end(kern[x])) { + x++; + } + x++; + dump_int(x); + dump_things(*kern, x); + } else { + dump_int(x); + } + /* packets */ + x = vf_packet_bytes(co); dump_int(x); - } - /* kerns */ - x = 0; - if ((kern = get_charinfo_kerns(co)) != NULL) { - while (!kern_end(kern[x])) { x++; } - x++; - dump_int(x); dump_things(*kern, x); - } else { - dump_int(x); - } - /* packets */ - x= vf_packet_bytes(co); - dump_int(x); - if (x>0) { - dump_things(*get_charinfo_packets(co), x); - } + if (x > 0) { + dump_things(*get_charinfo_packets(co), x); + } - if (get_charinfo_tag(co)==ext_tag) { - x = get_charinfo_extensible(co,EXT_TOP); dump_int(x); - x = get_charinfo_extensible(co,EXT_BOT); dump_int(x); - x = get_charinfo_extensible(co,EXT_MID); dump_int(x); - x = get_charinfo_extensible(co,EXT_REP); dump_int(x); - } + if (get_charinfo_tag(co) == ext_tag) { + dump_charinfo_variants(get_charinfo_vert_variants(co)); + dump_charinfo_variants(get_charinfo_hor_variants(co)); + } } -void -dump_font (int f) { - int i,x; - - set_font_used(f,0); - font_tables[f]->charinfo_cache = NULL; - dump_things(*(font_tables[f]), 1); - dump_string(font_name(f)); - dump_string(font_area(f)); - dump_string(font_filename(f)); - dump_string(font_fullname(f)); - dump_string(font_encodingname(f)); - dump_string(font_cidregistry(f)); - dump_string(font_cidordering(f)); - - dump_things(*param_base(f),(font_params(f)+1)); - - if (has_left_boundary(f)) { - dump_int(1); dump_charinfo(f,left_boundarychar); - } else { - dump_int(0); - } - if (has_right_boundary(f)) { - dump_int(1); dump_charinfo(f,right_boundarychar); - } else { - dump_int(0); - } +void dump_font(int f) +{ + int i, x; + + set_font_used(f, 0); + font_tables[f]->charinfo_cache = NULL; + dump_things(*(font_tables[f]), 1); + dump_string(font_name(f)); + dump_string(font_area(f)); + dump_string(font_filename(f)); + dump_string(font_fullname(f)); + dump_string(font_encodingname(f)); + dump_string(font_cidregistry(f)); + dump_string(font_cidordering(f)); + + dump_things(*param_base(f), (font_params(f) + 1)); + + if (font_math_params(f) > 0) { + dump_things(*math_param_base(f), (font_math_params(f))); + } + if (has_left_boundary(f)) { + dump_int(1); + dump_charinfo(f, left_boundarychar); + } else { + dump_int(0); + } + if (has_right_boundary(f)) { + dump_int(1); + dump_charinfo(f, right_boundarychar); + } else { + dump_int(0); + } - for(i=font_bc(f); i<=font_ec(f); i++) { - if (char_exists(f,i)) { - dump_charinfo(f,i); + for (i = font_bc(f); i <= font_ec(f); i++) { + if (char_exists(f, i)) { + dump_charinfo(f, i); + } } - } } -int -undump_charinfo (int f) { - charinfo *co; - int x,i; - char *s = NULL; - liginfo *lig = NULL; - kerninfo *kern = NULL; - real_eight_bits *packet = NULL; - int top = 0, bot = 0, mid = 0, rep = 0; - - undump_int(i); - co = get_charinfo(f,i); - undump_int(x); set_charinfo_width(co,x); - undump_int(x); set_charinfo_height(co,x); - undump_int(x); set_charinfo_depth(co,x); - undump_int(x); set_charinfo_italic(co,x); - undump_int(x); set_charinfo_tag(co,x); - undump_int(x); set_charinfo_ef(co,x); - undump_int(x); set_charinfo_rp(co,x); - undump_int(x); set_charinfo_lp(co,x); - undump_int(x); set_charinfo_remainder(co,x); - undump_int(x); set_charinfo_used(co,x); - undump_int(x); set_charinfo_index(co,x); - - /* name */ - undump_int (x); - if (x>0) { - font_bytes += x; - s = xmalloc(x); - undump_things(*s,x); - } - set_charinfo_name(co,s); - - /* tounicode */ - undump_int (x); - if (x>0) { - font_bytes += x; - s = xmalloc(x); - undump_things(*s,x); - } - set_charinfo_tounicode(co,s); - - /* ligatures */ - undump_int (x); - if (x>0) { - font_bytes += x*sizeof(liginfo); - lig = xmalloc(x*sizeof(liginfo)); - undump_things(*lig,x); - } - set_charinfo_ligatures(co,lig); - - /* kerns */ - undump_int (x); - if (x>0) { - font_bytes += x*sizeof(kerninfo); - kern = xmalloc(x*sizeof(kerninfo)); - undump_things(*kern,x); - } - set_charinfo_kerns(co,kern); - - /* packets */ - undump_int (x); - if (x>0) { - font_bytes += x; - packet = xmalloc(x); - undump_things(*packet,x); - } - set_charinfo_packets(co,packet); - - if (get_charinfo_tag(co)==ext_tag) { - undump_int(top); - undump_int(bot); - undump_int(mid); - undump_int(rep); - set_charinfo_extensible(co,top,bot,mid,rep); - } - return i; +int undump_charinfo(int f) +{ + charinfo *co; + int x, i; + char *s = NULL; + liginfo *lig = NULL; + kerninfo *kern = NULL; + real_eight_bits *packet = NULL; + + undump_int(i); + co = get_charinfo(f, i); + undump_int(x); + set_charinfo_width(co, x); + undump_int(x); + set_charinfo_height(co, x); + undump_int(x); + set_charinfo_depth(co, x); + undump_int(x); + set_charinfo_italic(co, x); + undump_int(x); + set_charinfo_top_accent(co, x); + undump_int(x); + set_charinfo_bot_accent(co, x); + undump_int(x); + set_charinfo_tag(co, x); + undump_int(x); + set_charinfo_ef(co, x); + undump_int(x); + set_charinfo_rp(co, x); + undump_int(x); + set_charinfo_lp(co, x); + undump_int(x); + set_charinfo_remainder(co, x); + undump_int(x); + set_charinfo_used(co, x); + undump_int(x); + set_charinfo_index(co, x); + + /* name */ + undump_int(x); + if (x > 0) { + font_bytes += x; + s = xmalloc(x); + undump_things(*s, x); + } + set_charinfo_name(co, s); + /* tounicode */ + undump_int(x); + if (x > 0) { + font_bytes += x; + s = xmalloc(x); + undump_things(*s, x); + } + set_charinfo_tounicode(co, s); + /* ligatures */ + undump_int(x); + if (x > 0) { + font_bytes += x * sizeof(liginfo); + lig = xmalloc(x * sizeof(liginfo)); + undump_things(*lig, x); + } + set_charinfo_ligatures(co, lig); + /* kerns */ + undump_int(x); + if (x > 0) { + font_bytes += x * sizeof(kerninfo); + kern = xmalloc(x * sizeof(kerninfo)); + undump_things(*kern, x); + } + set_charinfo_kerns(co, kern); + + /* packets */ + undump_int(x); + if (x > 0) { + font_bytes += x; + packet = xmalloc(x); + undump_things(*packet, x); + } + set_charinfo_packets(co, packet); + + if (get_charinfo_tag(co) == ext_tag) { + set_charinfo_vert_variants(co, undump_charinfo_variants()); + set_charinfo_hor_variants(co, undump_charinfo_variants()); + } + return i; } -#define undump_font_string(a) undump_int (x); \ - if (x>0) { \ - font_bytes += x; \ - s = xmalloc(x); undump_things(*s,x); \ +#define undump_font_string(a) undump_int (x); \ + if (x>0) { \ + font_bytes += x; \ + s = xmalloc(x); undump_things(*s,x); \ a(f,s); } -void -undump_font(int f) -{ - int x, i; - texfont *tt; - charinfo *ci; - char *s; - grow_font_table (f); - font_tables[f] = NULL; - font_bytes += sizeof(texfont); - tt = xmalloc(sizeof(texfont)); - undump_things(*tt,1); - font_tables[f] = tt; - - undump_font_string(set_font_name); - undump_font_string(set_font_area); - undump_font_string(set_font_filename); - undump_font_string(set_font_fullname); - undump_font_string(set_font_encodingname); - undump_font_string(set_font_cidregistry); - undump_font_string(set_font_cidordering); - - i = sizeof(*param_base(f))*(font_params(f)+1); - font_bytes += i; - param_base(f) = xmalloc (i); - undump_things(*param_base(f), (font_params(f)+1)); - - font_tables[f]->_left_boundary = NULL; - undump_int(x); - if (x) { i = undump_charinfo(f); } /* left boundary */ - - font_tables[f]->_right_boundary = NULL; - undump_int(x); - if (x) { i = undump_charinfo(f); } /* right boundary */ - - - font_tables[f]->characters = new_sa_tree(1, 0); /* stack size 1, default item value 0 */ - ci = xcalloc(1,sizeof(charinfo)); - set_charinfo_name(ci,xstrdup(".notdef")); - font_tables[f]->charinfo = ci; - - i = font_bc(f); - while(i<font_ec(f)) { - i = undump_charinfo(f); - } -} +void undump_font(int f) +{ + int x, i; + texfont *tt; + charinfo *ci; + char *s; + grow_font_table(f); + font_tables[f] = NULL; + font_bytes += sizeof(texfont); + tt = xmalloc(sizeof(texfont)); + undump_things(*tt, 1); + /* these |char *| need resetting */ + tt->_font_name = NULL; + tt->_font_area = NULL; + tt->_font_filename = NULL; + tt->_font_fullname = NULL; + tt->_font_encodingname = NULL; + tt->_font_cidregistry = NULL; + tt->_font_cidordering = NULL; + font_tables[f] = tt; + + undump_font_string(set_font_name); + undump_font_string(set_font_area); + undump_font_string(set_font_filename); + undump_font_string(set_font_fullname); + undump_font_string(set_font_encodingname); + undump_font_string(set_font_cidregistry); + undump_font_string(set_font_cidordering); + + i = sizeof(*param_base(f)) * (font_params(f) + 1); + font_bytes += i; + param_base(f) = xmalloc(i); + undump_things(*param_base(f), (font_params(f) + 1)); + + if (font_math_params(f) > 0) { + i = sizeof(*math_param_base(f)) * (font_math_params(f) + 1); + font_bytes += i; + math_param_base(f) = xmalloc(i); + undump_things(*math_param_base(f), (font_math_params(f) + 1)); + } else { + math_param_base(f) = NULL; + } + font_tables[f]->_left_boundary = NULL; + undump_int(x); + if (x) { + i = undump_charinfo(f); + } + /* left boundary */ + font_tables[f]->_right_boundary = NULL; + undump_int(x); + if (x) { + i = undump_charinfo(f); + } + + /* right boundary */ + font_tables[f]->characters = new_sa_tree(1, 0); /* stack size 1, default item value 0 */ + ci = xcalloc(1, sizeof(charinfo)); + set_charinfo_name(ci, xstrdup(".notdef")); + font_tables[f]->charinfo = ci; + + i = font_bc(f); + while (i < font_ec(f)) { + i = undump_charinfo(f); + } +} diff --git a/Build/source/texk/web2c/luatexdir/font/texfont.h b/Build/source/texk/web2c/luatexdir/font/texfont.h index 21b79f1e876..f91d00dc2b1 100644 --- a/Build/source/texk/web2c/luatexdir/font/texfont.h +++ b/Build/source/texk/web2c/luatexdir/font/texfont.h @@ -1,23 +1,23 @@ -/* - Copyright (c) 1996-2006 Taco Hoekwater <taco@luatex.org> - - This file is part of LuaTeX. - - LuaTeX is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - LuaTeX is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with LuaTeX; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - - $Id: texfont.h 1117 2008-03-21 15:26:12Z hhenkel $ */ +/* texfont.h Main font API implementation for the pascal parts + + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> + + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ + +/* $Id: texfont.h 2057 2009-03-19 15:45:47Z taco $ */ /* Here we have the interface to LuaTeX's font system, as seen from the main pascal program. There is a companion list in luatex.defines to @@ -28,41 +28,53 @@ */ #ifndef TEXFONT_H -#define TEXFONT_H 1 +# define TEXFONT_H 1 -#include "luatexdir/managed-sa.h" +# include "luatexdir/managed-sa.h" -#define pointer halfword +# define pointer halfword typedef struct liginfo { - integer adj; - integer lig; - char type; + integer adj; + integer lig; + char type; } liginfo; typedef struct kerninfo { - integer adj; - scaled sc; + integer adj; + scaled sc; } kerninfo; +typedef struct extinfo { + struct extinfo *next; + int glyph; + int start_overlap; + int end_overlap; + int advance; + int extender; +} extinfo; + typedef struct charinfo { - char *name; /* postscript character name */ - liginfo *ligatures; /* ligature items */ - kerninfo *kerns; /* kern items */ - real_eight_bits *packets; /* virtual commands. */ - integer *extensible; /* extensible recipe (if any) */ - unsigned short index; /* CID index */ - integer remainder; /* spare value for odd items, could be union-ed with extensible */ - scaled width; /* width */ - scaled height; /* height */ - scaled depth; /* depth */ - scaled italic; /* italic correction */ - integer ef; /* font expansion factor */ - integer lp; /* left protruding factor */ - integer rp; /* right protruding factor */ - char tag ; /* list / ext taginfo */ - char used ; /* char is typeset ? */ - char *tounicode; /* unicode equivalent */ + char *name; /* postscript character name */ + liginfo *ligatures; /* ligature items */ + kerninfo *kerns; /* kern items */ + real_eight_bits *packets; /* virtual commands. */ + unsigned short index; /* CID index */ + integer remainder; /* spare value for odd items, could be union-ed with extensible */ + scaled width; /* width */ + scaled height; /* height */ + scaled depth; /* depth */ + scaled italic; /* italic correction */ + scaled top_accent; /* top accent alignment */ + scaled bot_accent; /* bot accent alignment */ + integer ef; /* font expansion factor */ + integer lp; /* left protruding factor */ + integer rp; /* right protruding factor */ + char tag; /* list / ext taginfo */ + char used; /* char is typeset ? */ + char *tounicode; /* unicode equivalent */ + extinfo *hor_variants; /* horizontal variants */ + extinfo *vert_variants; /* vertical variants */ } charinfo; @@ -71,94 +83,111 @@ typedef struct charinfo { at the same time. the structure |charinfo_short| is defined in web */ -#ifndef luaTeX +# ifndef luaTeX typedef struct charinfo_short { - scaled ci_wd; /* width */ - scaled ci_ht; /* height */ - scaled ci_dp; /* depth */ + scaled ci_wd; /* width */ + scaled ci_ht; /* height */ + scaled ci_dp; /* depth */ } charinfo_short; -#endif +# endif +# define EXT_NORMAL 0 +# define EXT_REPEAT 1 -extern charinfo_short char_info_short (internal_font_number f, integer c); +extern extinfo *get_charinfo_vert_variants(charinfo * ci); +extern extinfo *get_charinfo_hor_variants(charinfo * ci); +extern void set_charinfo_hor_variants(charinfo * ci, extinfo * ext); +extern void set_charinfo_vert_variants(charinfo * ci, extinfo * ext); +extern void add_charinfo_vert_variant(charinfo * ci, extinfo * ext); +extern void add_charinfo_hor_variant(charinfo * ci, extinfo * ext); + +extern extinfo *copy_variants(extinfo * o); + +extern extinfo *new_variant(int glyph, int startconnect, int endconnect, + int advance, int repeater); + +extern charinfo_short char_info_short(internal_font_number f, integer c); typedef struct texfont { - integer _font_size ; - integer _font_dsize ; - char * _font_name ; - char * _font_area ; - char * _font_filename ; - char * _font_fullname ; - char * _font_encodingname ; - char * _font_cidregistry ; - char * _font_cidordering ; - integer _font_cidversion ; - integer _font_cidsupplement ; - - integer _font_ec ; - integer _font_checksum ; /* internal information */ - char _font_used ; /* internal information */ - char _font_touched ; /* internal information */ - integer _font_cache_id ; /* internal information */ - char _font_encodingbytes ; /* 1 or 2 bytes */ - integer _font_slant ; /* a slant in ppt */ - integer _font_extend ; /* an extension in ppt, or 0 */ - char _font_tounicode ; /* 1 if info is present */ - fm_entry_ptr _font_map; - integer _font_type; - integer _font_format; - integer _font_embedding; - integer _font_bc ; - integer _hyphen_char ; - integer _skew_char ; - integer _font_natural_dir; - - charinfo *_left_boundary; - charinfo *_right_boundary; - - integer _font_params; - scaled *_param_base; - - sa_tree characters; - integer charinfo_count; - integer charinfo_size; - charinfo *charinfo; - int *charinfo_cache; - integer ligatures_disabled; - - integer _pdf_font_num; /* maps to a PDF resource ID */ - scaled _pdf_font_size; /* maps to a PDF font size */ - internal_font_number _pdf_font_blink; /* link to base font for expanded fonts */ - internal_font_number _pdf_font_elink; /* link to expanded fonts for base font */ - integer _pdf_font_expand_ratio; /* expansion ratio of a particular font */ - internal_font_number _pdf_font_shrink; /* font at limit of shrinking */ - internal_font_number _pdf_font_stretch; /* font at limit of stretching */ - integer _pdf_font_step; /* amount of one step of expansion */ - boolean _pdf_font_auto_expand; /* this font is auto-expanded? */ - str_number _pdf_font_attr; /* pointer to additional attributes */ + integer _font_size; + integer _font_dsize; + char *_font_name; + char *_font_area; + char *_font_filename; + char *_font_fullname; + char *_font_encodingname; + char *_font_cidregistry; + char *_font_cidordering; + integer _font_cidversion; + integer _font_cidsupplement; + + integer _font_ec; + unsigned _font_checksum; /* internal information */ + char _font_used; /* internal information */ + char _font_touched; /* internal information */ + integer _font_cache_id; /* internal information */ + char _font_encodingbytes; /* 1 or 2 bytes */ + integer _font_slant; /* a slant in ppt */ + integer _font_extend; /* an extension in ppt, or 0 */ + char _font_tounicode; /* 1 if info is present */ + fm_entry_ptr _font_map; + integer _font_type; + integer _font_format; + integer _font_embedding; + integer _font_bc; + integer _hyphen_char; + integer _skew_char; + integer _font_natural_dir; + + charinfo *_left_boundary; + charinfo *_right_boundary; + + integer _font_params; + scaled *_param_base; + + integer _font_math_params; + scaled *_math_param_base; + + sa_tree characters; + integer charinfo_count; + integer charinfo_size; + charinfo *charinfo; + int *charinfo_cache; + integer ligatures_disabled; + + integer _pdf_font_num; /* maps to a PDF resource ID */ + scaled _pdf_font_size; /* maps to a PDF font size */ + internal_font_number _pdf_font_blink; /* link to base font for expanded fonts */ + internal_font_number _pdf_font_elink; /* link to expanded fonts for base font */ + integer _pdf_font_expand_ratio; /* expansion ratio of a particular font */ + internal_font_number _pdf_font_shrink; /* font at limit of shrinking */ + internal_font_number _pdf_font_stretch; /* font at limit of stretching */ + integer _pdf_font_step; /* amount of one step of expansion */ + boolean _pdf_font_auto_expand; /* this font is auto-expanded? */ + str_number _pdf_font_attr; /* pointer to additional attributes */ } texfont; typedef enum { - unknown_font_type=0, /* new font (has not been used yet) */ - virtual_font_type, /* virtual font */ - real_font_type, /* real font */ + unknown_font_type = 0, /* new font (has not been used yet) */ + virtual_font_type, /* virtual font */ + real_font_type, /* real font */ } font_types; typedef enum { - unknown_format=0, - type1_format, - type3_format, - truetype_format, - opentype_format, + unknown_format = 0, + type1_format, + type3_format, + truetype_format, + opentype_format, } font_formats; typedef enum { - unknown_embedding=0, - no_embedding, - subset_embedding, - full_embedding, + unknown_embedding = 0, + no_embedding, + subset_embedding, + full_embedding, } font_embedding_option; extern char *font_type_strings[]; @@ -166,359 +195,391 @@ extern char *font_format_strings[]; extern char *font_embedding_strings[]; -#define font_checksum(a) font_tables[a]->_font_checksum -#define set_font_checksum(a,b) font_checksum(a) = b +# define font_checksum(a) font_tables[a]->_font_checksum +# define set_font_checksum(a,b) font_checksum(a) = b -#define font_check_0(a) ((font_tables[a]->_font_checksum&0xFF000000)>>24) -#define font_check_1(a) ((font_tables[a]->_font_checksum&0x00FF0000)>>16) -#define font_check_2(a) ((font_tables[a]->_font_checksum&0x0000FF00)>>8) -#define font_check_3(a) (font_tables[a]->_font_checksum&0x000000FF) +# define font_check_0(a) ((font_tables[a]->_font_checksum&0xFF000000)>>24) +# define font_check_1(a) ((font_tables[a]->_font_checksum&0x00FF0000)>>16) +# define font_check_2(a) ((font_tables[a]->_font_checksum&0x0000FF00)>>8) +# define font_check_3(a) (font_tables[a]->_font_checksum&0x000000FF) -#define font_size(a) font_tables[a]->_font_size -#define set_font_size(a,b) font_size(a) = b -#define font_dsize(a) font_tables[a]->_font_dsize -#define set_font_dsize(a,b) font_dsize(a) = b +# define font_size(a) font_tables[a]->_font_size +# define set_font_size(a,b) font_size(a) = b +# define font_dsize(a) font_tables[a]->_font_dsize +# define set_font_dsize(a,b) font_dsize(a) = b -#define font_name(a) font_tables[a]->_font_name -#define get_font_name(a) (unsigned char *)font_name(a) -#define set_font_name(f,b) font_name(f) = b -#define tex_font_name(a) maketexstring(font_name(a)) +# define font_name(a) font_tables[a]->_font_name +# define get_font_name(a) (unsigned char *)font_name(a) +# define set_font_name(f,b) font_name(f) = b +# define tex_font_name(a) maketexstring(font_name(a)) -boolean cmp_font_name (integer, strnumber); +boolean cmp_font_name(integer, strnumber); -#define font_area(a) font_tables[a]->_font_area -#define get_font_area(a) (unsigned char *)font_area(a) -#define set_font_area(f,b) font_area(f) = b -#define tex_font_area(a) maketexstring(font_area(a)) +# define font_area(a) font_tables[a]->_font_area +# define get_font_area(a) (unsigned char *)font_area(a) +# define set_font_area(f,b) font_area(f) = b +# define tex_font_area(a) maketexstring(font_area(a)) -boolean cmp_font_area (integer, strnumber); +boolean cmp_font_area(integer, strnumber); -#define font_reassign(a,b) { if (a!=NULL) free(a); a = b; } +# define font_reassign(a,b) { if (a!=NULL) free(a); a = b; } -#define font_filename(a) font_tables[a]->_font_filename -#define set_font_filename(f,b) font_reassign(font_filename(f),b) +# define font_filename(a) font_tables[a]->_font_filename +# define set_font_filename(f,b) font_reassign(font_filename(f),b) -#define font_fullname(a) font_tables[a]->_font_fullname -#define set_font_fullname(f,b) font_reassign(font_fullname(f),b) +# define font_fullname(a) font_tables[a]->_font_fullname +# define set_font_fullname(f,b) font_reassign(font_fullname(f),b) -#define font_encodingname(a) font_tables[a]->_font_encodingname -#define set_font_encodingname(f,b) font_reassign(font_encodingname(f),b) +# define font_encodingname(a) font_tables[a]->_font_encodingname +# define set_font_encodingname(f,b) font_reassign(font_encodingname(f),b) -boolean font_shareable(internal_font_number,internal_font_number); +boolean font_shareable(internal_font_number, internal_font_number); -#define cmp_font_filename(a,b) (!(font_filename(a)!=NULL || font_filename(b)!=NULL || \ +# define cmp_font_filename(a,b) (!(font_filename(a)!=NULL || font_filename(b)!=NULL || \ strcmp(font_filename(a),font_filename(b)))) -#define cmp_font_fullname(a,b) (!(font_fullname(a)!=NULL || font_fullname(b)!=NULL || \ +# define cmp_font_fullname(a,b) (!(font_fullname(a)!=NULL || font_fullname(b)!=NULL || \ strcmp(font_fullname(a),font_fullname(b)))) -#define cmp_font_encodingname(a,b) (!(font_encoding(a)!=NULL || font_encodingname(b)!=NULL || \ +# define cmp_font_encodingname(a,b) (!(font_encoding(a)!=NULL || font_encodingname(b)!=NULL || \ strcmp(font_encodingname(a),font_encodingname(b)))) -#define font_bc(a) font_tables[a]->_font_bc -#define set_font_bc(f,b) font_bc(f) = b +# define font_bc(a) font_tables[a]->_font_bc +# define set_font_bc(f,b) font_bc(f) = b -#define font_ec(a) font_tables[a]->_font_ec -#define set_font_ec(f,b) font_ec(f) = b +# define font_ec(a) font_tables[a]->_font_ec +# define set_font_ec(f,b) font_ec(f) = b -#define font_used(a) (font_tables[a]!=NULL && font_tables[a]->_font_used) -#define set_font_used(a,b) font_tables[a]->_font_used = b +# define font_used(a) (font_tables[a]!=NULL && font_tables[a]->_font_used) +# define set_font_used(a,b) font_tables[a]->_font_used = b -#define font_touched(a) font_tables[a]->_font_touched -#define set_font_touched(a,b) font_touched(a) = b - -#define font_type(a) font_tables[a]->_font_type -#define set_font_type(a,b) { /* fprintf(stdout,"set font type of %s to %i: %s\n",font_name(a),b,__FILE__); */ \ +# define font_touched(a) font_tables[a]->_font_touched +# define set_font_touched(a,b) font_touched(a) = b + +# define font_type(a) font_tables[a]->_font_type +# define set_font_type(a,b) { /* fprintf(stdout,"set font type of %s to %i: %s\n",font_name(a),b,__FILE__); */ \ font_type(a) = b; } -#define font_format(a) font_tables[a]->_font_format -#define font_format_name(a) font_format_strings[font_tables[a]->_font_format] -#define set_font_format(a,b) font_format(a) = b +# define font_format(a) font_tables[a]->_font_format +# define font_format_name(a) font_format_strings[font_tables[a]->_font_format] +# define set_font_format(a,b) font_format(a) = b -#define font_embedding(a) font_tables[a]->_font_embedding -#define set_font_embedding(a,b) font_embedding(a) = b +# define font_embedding(a) font_tables[a]->_font_embedding +# define set_font_embedding(a,b) font_embedding(a) = b -#define font_cidversion(a) font_tables[a]->_font_cidversion -#define set_font_cidversion(a,b) font_cidversion(a) = b +# define font_cidversion(a) font_tables[a]->_font_cidversion +# define set_font_cidversion(a,b) font_cidversion(a) = b -#define font_cidsupplement(a) font_tables[a]->_font_cidsupplement -#define set_font_cidsupplement(a,b) font_cidsupplement(a) = b +# define font_cidsupplement(a) font_tables[a]->_font_cidsupplement +# define set_font_cidsupplement(a,b) font_cidsupplement(a) = b -#define font_cidordering(a) font_tables[a]->_font_cidordering -#define set_font_cidordering(f,b) font_reassign(font_cidordering(f),b) +# define font_cidordering(a) font_tables[a]->_font_cidordering +# define set_font_cidordering(f,b) font_reassign(font_cidordering(f),b) -#define font_cidregistry(a) font_tables[a]->_font_cidregistry -#define set_font_cidregistry(f,b) font_reassign(font_cidregistry(f),b) +# define font_cidregistry(a) font_tables[a]->_font_cidregistry +# define set_font_cidregistry(f,b) font_reassign(font_cidregistry(f),b) -#define font_map(a) font_tables[a]->_font_map -#define set_font_map(a,b) font_map(a) = b +# define font_map(a) font_tables[a]->_font_map +# define set_font_map(a,b) font_map(a) = b -#define font_cache_id(a) font_tables[a]->_font_cache_id -#define set_font_cache_id(a,b) font_cache_id(a) = b +# define font_cache_id(a) font_tables[a]->_font_cache_id +# define set_font_cache_id(a,b) font_cache_id(a) = b -#define font_encodingbytes(a) font_tables[a]->_font_encodingbytes -#define set_font_encodingbytes(a,b) font_encodingbytes(a) = b +# define font_encodingbytes(a) font_tables[a]->_font_encodingbytes +# define set_font_encodingbytes(a,b) font_encodingbytes(a) = b -#define font_slant(a) font_tables[a]->_font_slant -#define set_font_slant(a,b) font_slant(a) = b +# define font_slant(a) font_tables[a]->_font_slant +# define set_font_slant(a,b) font_slant(a) = b -#define font_extend(a) font_tables[a]->_font_extend -#define set_font_extend(a,b) font_extend(a) = b +# define font_extend(a) font_tables[a]->_font_extend +# define set_font_extend(a,b) font_extend(a) = b -#define font_tounicode(a) font_tables[a]->_font_tounicode -#define set_font_tounicode(a,b) font_tounicode(a) = b +# define font_tounicode(a) font_tables[a]->_font_tounicode +# define set_font_tounicode(a,b) font_tounicode(a) = b -#define hyphen_char(a) font_tables[a]->_hyphen_char -#define set_hyphen_char(a,b) hyphen_char(a) = b +# define hyphen_char(a) font_tables[a]->_hyphen_char +# define set_hyphen_char(a,b) hyphen_char(a) = b -#define skew_char(a) font_tables[a]->_skew_char -#define set_skew_char(a,b) skew_char(a) = b +# define skew_char(a) font_tables[a]->_skew_char +# define set_skew_char(a,b) skew_char(a) = b -#define font_natural_dir(a) font_tables[a]->_font_natural_dir -#define set_font_natural_dir(a,b) font_natural_dir(a) = b +# define font_natural_dir(a) font_tables[a]->_font_natural_dir +# define set_font_natural_dir(a,b) font_natural_dir(a) = b -#define pdf_font_size(a) font_tables[a]->_pdf_font_size -#define set_pdf_font_size(a,b) pdf_font_size(a) = b +# define pdf_font_size(a) font_tables[a]->_pdf_font_size +# define set_pdf_font_size(a,b) pdf_font_size(a) = b -#define pdf_font_num(a) font_tables[a]->_pdf_font_num -#define set_pdf_font_num(a,b) pdf_font_num(a) = b +# define pdf_font_num(a) font_tables[a]->_pdf_font_num +# define set_pdf_font_num(a,b) pdf_font_num(a) = b -#define pdf_font_blink(a) font_tables[a]->_pdf_font_blink -#define set_pdf_font_blink(a,b) pdf_font_blink(a) = b +# define pdf_font_blink(a) font_tables[a]->_pdf_font_blink +# define set_pdf_font_blink(a,b) pdf_font_blink(a) = b -#define pdf_font_elink(a) font_tables[a]->_pdf_font_elink -#define set_pdf_font_elink(a,b) pdf_font_elink(a) = b +# define pdf_font_elink(a) font_tables[a]->_pdf_font_elink +# define set_pdf_font_elink(a,b) pdf_font_elink(a) = b -#define pdf_font_expand_ratio(a) font_tables[a]->_pdf_font_expand_ratio -#define set_pdf_font_expand_ratio(a,b) pdf_font_expand_ratio(a) = b +# define pdf_font_expand_ratio(a) font_tables[a]->_pdf_font_expand_ratio +# define set_pdf_font_expand_ratio(a,b) pdf_font_expand_ratio(a) = b -#define pdf_font_shrink(a) font_tables[a]->_pdf_font_shrink -#define set_pdf_font_shrink(a,b) pdf_font_shrink(a) = b +# define pdf_font_shrink(a) font_tables[a]->_pdf_font_shrink +# define set_pdf_font_shrink(a,b) pdf_font_shrink(a) = b -#define pdf_font_stretch(a) font_tables[a]->_pdf_font_stretch -#define set_pdf_font_stretch(a,b) pdf_font_stretch(a) = b +# define pdf_font_stretch(a) font_tables[a]->_pdf_font_stretch +# define set_pdf_font_stretch(a,b) pdf_font_stretch(a) = b -#define pdf_font_step(a) font_tables[a]->_pdf_font_step -#define set_pdf_font_step(a,b) pdf_font_step(a) = b +# define pdf_font_step(a) font_tables[a]->_pdf_font_step +# define set_pdf_font_step(a,b) pdf_font_step(a) = b -#define pdf_font_auto_expand(a) font_tables[a]->_pdf_font_auto_expand -#define set_pdf_font_auto_expand(a,b) pdf_font_auto_expand(a) = b +# define pdf_font_auto_expand(a) font_tables[a]->_pdf_font_auto_expand +# define set_pdf_font_auto_expand(a,b) pdf_font_auto_expand(a) = b -#define pdf_font_attr(a) font_tables[a]->_pdf_font_attr -#define set_pdf_font_attr(a,b) pdf_font_attr(a) = b +# define pdf_font_attr(a) font_tables[a]->_pdf_font_attr +# define set_pdf_font_attr(a,b) pdf_font_attr(a) = b -#define left_boundarychar -1 -#define right_boundarychar -2 -#define non_boundarychar -3 +# define left_boundarychar -1 +# define right_boundarychar -2 +# define non_boundarychar -3 -#define left_boundary(a) font_tables[a]->_left_boundary -#define has_left_boundary(a) (left_boundary(a)!=NULL) -#define set_left_boundary(a,b) font_reassign(left_boundary(a),b) +# define left_boundary(a) font_tables[a]->_left_boundary +# define has_left_boundary(a) (left_boundary(a)!=NULL) +# define set_left_boundary(a,b) font_reassign(left_boundary(a),b) -#define right_boundary(a) font_tables[a]->_right_boundary -#define has_right_boundary(a) (right_boundary(a)!=NULL) -#define set_right_boundary(a,b) font_reassign(right_boundary(a),b) +# define right_boundary(a) font_tables[a]->_right_boundary +# define has_right_boundary(a) (right_boundary(a)!=NULL) +# define set_right_boundary(a,b) font_reassign(right_boundary(a),b) -#define font_bchar(a) (right_boundary(a)!=NULL ? right_boundarychar : non_boundarychar) +# define font_bchar(a) (right_boundary(a)!=NULL ? right_boundarychar : non_boundarychar) /* font parameters */ -#define font_params(a) font_tables[a]->_font_params -#define param_base(a) font_tables[a]->_param_base -#define font_param(a,b) font_tables[a]->_param_base[b] +# define font_params(a) font_tables[a]->_font_params +# define param_base(a) font_tables[a]->_param_base +# define font_param(a,b) font_tables[a]->_param_base[b] extern void set_font_params(internal_font_number f, int b); -#define set_font_param(f,n,b) \ +# define set_font_param(f,n,b) \ { if (font_params(f)<n) set_font_params(f,n); \ font_param(f,n) = b; } + +# define font_math_params(a) font_tables[a]->_font_math_params +# define math_param_base(a) font_tables[a]->_math_param_base +# define font_math_param(a,b) font_tables[a]->_math_param_base[b] + +extern void set_font_math_params(internal_font_number f, int b); + +# define set_font_math_param(f,n,b) \ + { if (font_math_params(f)<n) set_font_math_params(f,n); \ + font_math_param(f,n) = b; } + /* Font parameters are sometimes referred to as |slant(f)|, |space(f)|, etc.*/ typedef enum { - slant_code = 1, - space_code = 2, - space_stretch_code = 3, - space_shrink_code = 4, - x_height_code = 5, - quad_code = 6, - extra_space_code = 7 } font_parameter_codes ; - -#define slant(f) font_param(f,slant_code) -#define space(f) font_param(f,space_code) -#define space_stretch(f) font_param(f,space_stretch_code) -#define space_shrink(f) font_param(f,space_shrink_code) -#define x_height(f) font_param(f,x_height_code) -#define quad(f) font_param(f,quad_code) -#define extra_space(f) font_param(f,extra_space_code) + slant_code = 1, + space_code = 2, + space_stretch_code = 3, + space_shrink_code = 4, + x_height_code = 5, + quad_code = 6, + extra_space_code = 7 +} font_parameter_codes; + +# define slant(f) font_param(f,slant_code) +# define space(f) font_param(f,space_code) +# define space_stretch(f) font_param(f,space_stretch_code) +# define space_shrink(f) font_param(f,space_shrink_code) +# define x_height(f) font_param(f,x_height_code) +# define quad(f) font_param(f,quad_code) +# define extra_space(f) font_param(f,extra_space_code) /* now for characters */ -extern charinfo *get_charinfo (internal_font_number f, integer c) ; -extern integer char_exists (internal_font_number f, integer c); -extern charinfo *char_info (internal_font_number f, integer c); - - -extern void set_charinfo_width (charinfo *ci, scaled val); -extern void set_charinfo_height (charinfo *ci, scaled val); -extern void set_charinfo_depth (charinfo *ci, scaled val); -extern void set_charinfo_italic (charinfo *ci, scaled val); -extern void set_charinfo_tag (charinfo *ci, scaled val); -extern void set_charinfo_remainder (charinfo *ci, scaled val); -extern void set_charinfo_used (charinfo *ci, scaled val); -extern void set_charinfo_index (charinfo *ci, scaled val); -extern void set_charinfo_name (charinfo *ci, char *val) ; -extern void set_charinfo_tounicode (charinfo *ci, char *val) ; -extern void set_charinfo_ligatures (charinfo *ci, liginfo *val); -extern void set_charinfo_kerns (charinfo *ci, kerninfo *val); -extern void set_charinfo_packets (charinfo *ci, real_eight_bits *val); -extern void set_charinfo_extensible (charinfo *ci, int a, int b, int c, int d); - -#define set_char_used(f,a,b) set_charinfo_used(get_charinfo(f,a),b) - -extern scaled get_charinfo_width (charinfo *ci); -extern scaled get_charinfo_height (charinfo *ci); -extern scaled get_charinfo_depth (charinfo *ci); -extern scaled get_charinfo_italic (charinfo *ci); -extern char get_charinfo_tag (charinfo *ci); -extern integer get_charinfo_remainder (charinfo *ci); -extern char get_charinfo_used (charinfo *ci); -extern integer get_charinfo_index (charinfo *ci); -extern char * get_charinfo_name (charinfo *ci) ; -extern char * get_charinfo_tounicode (charinfo *ci) ; -extern liginfo * get_charinfo_ligatures (charinfo *ci); -extern kerninfo *get_charinfo_kerns (charinfo *ci); -extern real_eight_bits *get_charinfo_packets (charinfo *ci); -extern integer get_charinfo_extensible (charinfo *ci, int which); - -extern integer ext_top (internal_font_number f, integer c); -extern integer ext_bot (internal_font_number f, integer c); -extern integer ext_rep (internal_font_number f, integer c); -extern integer ext_mid (internal_font_number f, integer c); - -#define set_ligature_item(f,b,c,d) { f.type = b; f.adj = c; f.lig = d; } - -#define set_kern_item(f,b,c) { f.adj = b; f.sc = c; } +extern charinfo *get_charinfo(internal_font_number f, integer c); +extern integer char_exists(internal_font_number f, integer c); +extern charinfo *char_info(internal_font_number f, integer c); + + +extern void set_charinfo_width(charinfo * ci, scaled val); +extern void set_charinfo_height(charinfo * ci, scaled val); +extern void set_charinfo_depth(charinfo * ci, scaled val); +extern void set_charinfo_italic(charinfo * ci, scaled val); +extern void set_charinfo_top_accent(charinfo * ci, scaled val); +extern void set_charinfo_bot_accent(charinfo * ci, scaled val); +extern void set_charinfo_tag(charinfo * ci, scaled val); +extern void set_charinfo_remainder(charinfo * ci, scaled val); +extern void set_charinfo_used(charinfo * ci, scaled val); +extern void set_charinfo_index(charinfo * ci, scaled val); +extern void set_charinfo_name(charinfo * ci, char *val); +extern void set_charinfo_tounicode(charinfo * ci, char *val); +extern void set_charinfo_ligatures(charinfo * ci, liginfo * val); +extern void set_charinfo_kerns(charinfo * ci, kerninfo * val); +extern void set_charinfo_packets(charinfo * ci, real_eight_bits * val); +extern void set_charinfo_extensible(charinfo * ci, int a, int b, int c, int d); +extern void set_charinfo_ef(charinfo * ci, scaled val); +extern void set_charinfo_lp(charinfo * ci, scaled val); +extern void set_charinfo_rp(charinfo * ci, scaled val); + +# define set_char_used(f,a,b) do { \ + if (char_exists(f,a)) \ + set_charinfo_used(char_info(f,a),b); \ + } while (0) + +extern scaled get_charinfo_width(charinfo * ci); +extern scaled get_charinfo_height(charinfo * ci); +extern scaled get_charinfo_depth(charinfo * ci); +extern scaled get_charinfo_italic(charinfo * ci); +extern scaled get_charinfo_top_accent(charinfo * ci); +extern scaled get_charinfo_bot_accent(charinfo * ci); +extern char get_charinfo_tag(charinfo * ci); +extern integer get_charinfo_remainder(charinfo * ci); +extern char get_charinfo_used(charinfo * ci); +extern integer get_charinfo_index(charinfo * ci); +extern char *get_charinfo_name(charinfo * ci); +extern char *get_charinfo_tounicode(charinfo * ci); +extern liginfo *get_charinfo_ligatures(charinfo * ci); +extern kerninfo *get_charinfo_kerns(charinfo * ci); +extern real_eight_bits *get_charinfo_packets(charinfo * ci); +extern integer get_charinfo_ef(charinfo * ci); +extern integer get_charinfo_rp(charinfo * ci); +extern integer get_charinfo_lp(charinfo * ci); +extern integer get_charinfo_extensible(charinfo * ci, int which); + +extern integer ext_top(internal_font_number f, integer c); +extern integer ext_bot(internal_font_number f, integer c); +extern integer ext_rep(internal_font_number f, integer c); +extern integer ext_mid(internal_font_number f, integer c); + +# define set_ligature_item(f,b,c,d) { f.type = b; f.adj = c; f.lig = d; } + +# define set_kern_item(f,b,c) { f.adj = b; f.sc = c; } /* character information */ -#define non_char 65536 /* a code that can't match a real character */ -#define non_address 0 /* a spurious |bchar_label| */ +# define non_char 65536 /* a code that can't match a real character */ +# define non_address 0 /* a spurious |bchar_label| */ /* character kerns and ligatures */ -#define end_kern 0x7FFFFF /* otherchar value meaning "stop" */ -#define ignored_kern 0x800000 /* otherchar value meaning "disabled" */ +# define end_kern 0x7FFFFF + /* otherchar value meaning "stop" */ +# define ignored_kern 0x800000 + /* otherchar value meaning "disabled" */ -#define charinfo_kern(b,c) b->kerns[c] +# define charinfo_kern(b,c) b->kerns[c] -#define kern_char(b) (b).adj -#define kern_kern(b) (b).sc -#define kern_end(b) ((b).adj == end_kern) -#define kern_disabled(b) ((b).adj > end_kern) +# define kern_char(b) (b).adj +# define kern_kern(b) (b).sc +# define kern_end(b) ((b).adj == end_kern) +# define kern_disabled(b) ((b).adj > end_kern) /* character ligatures */ -#define end_ligature 0x7FFFFF /* otherchar value meaning "stop" */ -#define ignored_ligature 0x800000 /* otherchar value meaning "disabled" */ - -#define charinfo_ligature(b,c) b->ligatures[c] - -#define is_valid_ligature(a) ((a).type!=0) -#define lig_type(a) ((a).type>>1) -#define lig_char(a) (a).adj -#define lig_replacement(a) (a).lig -#define lig_end(a) (lig_char(a) == end_ligature) -#define lig_disabled(a) (lig_char(a) > end_ligature) - -#define no_tag 0 /* vanilla character */ -#define lig_tag 1 /* character has a ligature/kerning program */ -#define list_tag 2 /* character has a successor in a charlist */ -#define ext_tag 3 /* character is extensible */ - -extern scaled char_height (internal_font_number f, integer c); -extern scaled char_width (internal_font_number f, integer c); -extern scaled char_depth (internal_font_number f, integer c); -extern scaled char_italic (internal_font_number f, integer c); - -extern liginfo * char_ligatures (internal_font_number f, integer c); -extern kerninfo * char_kerns (internal_font_number f, integer c); -extern real_eight_bits * char_packets (internal_font_number f, integer c); - -#define has_lig(f,b) (char_exists(f,b) &&( char_ligatures(f,b) != NULL)) -#define has_kern(f,b) (char_exists(f,b) && (char_kerns(f,b) != NULL)) -#define has_packet(f,b) (char_exists(f,b) && (char_packets(f,b) != NULL)) - -extern integer char_remainder (internal_font_number f, integer c); -extern char char_tag (internal_font_number f, integer c); -extern char char_used (internal_font_number f, integer c); -extern char * char_name (internal_font_number f, integer c); -extern integer char_index (internal_font_number f, integer c); - +# define end_ligature 0x7FFFFF /* otherchar value meaning "stop" */ +# define ignored_ligature 0x800000 /* otherchar value meaning "disabled" */ + +# define charinfo_ligature(b,c) b->ligatures[c] + +# define is_valid_ligature(a) ((a).type!=0) +# define lig_type(a) ((a).type>>1) +# define lig_char(a) (a).adj +# define lig_replacement(a) (a).lig +# define lig_end(a) (lig_char(a) == end_ligature) +# define lig_disabled(a) (lig_char(a) > end_ligature) + +# define no_tag 0 /* vanilla character */ +# define lig_tag 1 /* character has a ligature/kerning program */ +# define list_tag 2 /* character has a successor in a charlist */ +# define ext_tag 3 /* character is extensible */ + +extern scaled char_height(internal_font_number f, integer c); +extern scaled char_width(internal_font_number f, integer c); +extern scaled char_depth(internal_font_number f, integer c); +extern scaled char_italic(internal_font_number f, integer c); +extern scaled char_top_accent(internal_font_number f, integer c); +extern scaled char_bot_accent(internal_font_number f, integer c); + +extern liginfo *char_ligatures(internal_font_number f, integer c); +extern kerninfo *char_kerns(internal_font_number f, integer c); +extern real_eight_bits *char_packets(internal_font_number f, integer c); + +# define has_lig(f,b) (char_exists(f,b) &&( char_ligatures(f,b) != NULL)) +# define has_kern(f,b) (char_exists(f,b) && (char_kerns(f,b) != NULL)) +# define has_packet(f,b) (char_exists(f,b) && (char_packets(f,b) != NULL)) + +extern integer char_remainder(internal_font_number f, integer c); +extern char char_tag(internal_font_number f, integer c); +extern char char_used(internal_font_number f, integer c); +extern char *char_name(internal_font_number f, integer c); +extern integer char_index(internal_font_number f, integer c); + +scaled raw_get_kern(internalfontnumber f, integer lc, integer rc); scaled get_kern(internalfontnumber f, integer lc, integer rc); liginfo get_ligature(internalfontnumber f, integer lc, integer rc); -#define EXT_TOP 0 -#define EXT_BOT 1 -#define EXT_MID 2 -#define EXT_REP 3 +# define EXT_TOP 0 +# define EXT_BOT 1 +# define EXT_MID 2 +# define EXT_REP 3 extern texfont **font_tables; -integer new_font (void) ; -integer copy_font (integer id) ; -integer scale_font (integer id, integer atsize) ; -integer max_font_id (void); -void set_max_font_id (integer id); -integer new_font_id (void); -void create_null_font (void); +integer new_font(void); +integer copy_font(integer id); +integer scale_font(integer id, integer atsize); +integer max_font_id(void); +void set_max_font_id(integer id); +integer new_font_id(void); +void create_null_font(void); void delete_font(integer id); -boolean is_valid_font (integer id); +boolean is_valid_font(integer id); -void dump_font (int font_number); -void undump_font (int font_number); +void dump_font(int font_number); +void undump_font(int font_number); -integer test_no_ligatures (internal_font_number f) ; -void set_no_ligatures (internal_font_number f) ; +integer test_no_ligatures(internal_font_number f); +void set_no_ligatures(internal_font_number f); -extern integer get_tag_code (internal_font_number f, integer c); -extern integer get_lp_code (internal_font_number f, integer c); -extern integer get_rp_code (internal_font_number f, integer c); -extern integer get_ef_code (internal_font_number f, integer c); +extern integer get_tag_code(internal_font_number f, integer c); +extern integer get_lp_code(internal_font_number f, integer c); +extern integer get_rp_code(internal_font_number f, integer c); +extern integer get_ef_code(internal_font_number f, integer c); -extern void set_tag_code (internal_font_number f, integer c, integer i) ; -extern void set_lp_code(internal_font_number f, integer c, integer i) ; -extern void set_rp_code(internal_font_number f, integer c, integer i) ; -extern void set_ef_code(internal_font_number f, integer c, integer i) ; +extern void set_tag_code(internal_font_number f, integer c, integer i); +extern void set_lp_code(internal_font_number f, integer c, integer i); +extern void set_rp_code(internal_font_number f, integer c, integer i); +extern void set_ef_code(internal_font_number f, integer c, integer i); int read_tfm_info(internal_font_number f, char *nom, char *aire, scaled s); /* from dofont.c */ -extern int read_font_info (pointer u, strnumber nom, strnumber aire, scaled s, integer ndir); -extern int find_font_id (char *nom, char *aire, scaled s); +extern int read_font_info(pointer u, strnumber nom, scaled s, integer ndir); +extern int find_font_id(char *nom, char *aire, scaled s); /* for and from vfpacket.c */ -#define scan_special 3 /* look into special text */ /* this is a hack */ - -typedef enum { packet_char_code, - packet_font_code, - packet_pop_code, - packet_push_code, - packet_special_code, - packet_right_code, - packet_down_code, - packet_rule_code, - packet_node_code, - packet_nop_code, - packet_end_code } packet_command_codes; - -extern scaled sqxfw (scaled sq, integer fw); - -extern void do_vf_packet (internal_font_number vf_f, integer c); -extern int vf_packet_bytes (charinfo *co); +# define scan_special 3 /* look into special text */ /* this is a hack */ + +typedef enum { packet_char_code, + packet_font_code, + packet_pop_code, + packet_push_code, + packet_special_code, + packet_image_code, + packet_right_code, + packet_down_code, + packet_rule_code, + packet_node_code, + packet_nop_code, + packet_end_code +} packet_command_codes; + +extern scaled sqxfw(scaled sq, integer fw); + +extern void do_vf_packet(internal_font_number vf_f, integer c); +extern int vf_packet_bytes(charinfo * co); #endif diff --git a/Build/source/texk/web2c/luatexdir/font/tfmofm.c b/Build/source/texk/web2c/luatexdir/font/tfmofm.c index db82f94deba..36364ba6d44 100644 --- a/Build/source/texk/web2c/luatexdir/font/tfmofm.c +++ b/Build/source/texk/web2c/luatexdir/font/tfmofm.c @@ -1,34 +1,34 @@ -/* -Copyright (c) 1996-2006 Taco Hoekwater <taco@luatex.org> - -This file is part of LuaTeX. +/* tfmofm.c + + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -LuaTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + This file is part of LuaTeX. -LuaTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -You should have received a copy of the GNU General Public License -along with LuaTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -$Id: tfmofm.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" - #include "luatex-api.h" +#include "luatexfont.h" + +static const char _svn_version[] = + "$Id: tfmofm.c 2086 2009-03-22 15:32:08Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/tfmofm.c $"; /* Here are some macros that help process ligatures and kerns */ #define lig_kern_start(f,c) char_remainder(f,c) -#define stop_flag 128 /* value indicating `\.{STOP}' in a lig/kern program */ -#define kern_flag 128 /* op code for a kern step */ +#define stop_flag 128 /* value indicating `\.{STOP}' in a lig/kern program */ +#define kern_flag 128 /* op code for a kern step */ #define skip_byte(z) lig_kerns[z].b0 #define next_char(z) lig_kerns[z].b1 @@ -205,7 +205,7 @@ character does not exist in the font, since a character is valid if and only if it lies between |bc| and |ec| and has a nonzero |width_index|. */ - /* +/* @ \TeX\ checks the information of a \.{TFM} file for validity as the file is being read in, so that no further checks will be needed when typesetting is going on. The somewhat tedious subroutine that does this @@ -361,53 +361,54 @@ additional parameter information, which is explained later. */ -#define tfm_abort { font_tables[f]->_font_name = NULL; \ - font_tables[f]->_font_area = NULL; \ - xfree(tfm_buffer); xfree(kerns); \ - xfree(widths); xfree(heights); xfree(depths); \ - xfree(italics); xfree(extens); xfree(lig_kerns); \ - xfree(xligs); xfree(xkerns); \ - return 0; } +#define tfm_abort { font_tables[f]->_font_name = NULL; \ + font_tables[f]->_font_area = NULL; \ + xfree(tfm_buffer); xfree(kerns); \ + xfree(widths); xfree(heights); xfree(depths); \ + xfree(italics); xfree(extens); xfree(lig_kerns); \ + xfree(xligs); xfree(xkerns); \ + return 0; } -#define tfm_success { xfree(tfm_buffer); xfree(kerns); \ - xfree(widths); xfree(heights); xfree(depths); \ - xfree(italics); xfree(extens); xfree(lig_kerns); \ - xfree(xligs); xfree(xkerns); return 1; } +#define tfm_success { xfree(tfm_buffer); xfree(kerns); \ + xfree(widths); xfree(heights); xfree(depths); \ + xfree(italics); xfree(extens); xfree(lig_kerns); \ + xfree(xligs); xfree(xkerns); return 1; } int -open_tfm_file(char *nom, char *aire, unsigned char **tfm_buf, integer *tfm_siz) { - boolean res; /* was the callback successful? */ - boolean opened; /* was |tfm_file| successfully opened?*/ - integer callback_id; - FILE *tfm_file; - /* packfilename(nom,aire,getnullstr()); */ - if(nameoffile != NULL) - xfree(nameoffile); - nameoffile = malloc(strlen(nom)+2); - strcpy(stringcast(nameoffile+1),nom); - namelength = strlen(nom); - callback_id=callback_defined(read_font_file_callback); - if (callback_id>0) { - res = run_callback(callback_id,"S->bSd",stringcast(nameoffile+1), - &opened, tfm_buf, tfm_siz); - if (res && opened && (*tfm_siz>0)) { - return 1; - } +open_tfm_file(char *nom, char *aire, unsigned char **tfm_buf, integer * tfm_siz) +{ + boolean res; /* was the callback successful? */ + boolean opened; /* was |tfm_file| successfully opened? */ + integer callback_id; + FILE *tfm_file; + /* packfilename(nom,aire,getnullstr()); */ + if (nameoffile != NULL) + xfree(nameoffile); + nameoffile = malloc(strlen(nom) + 2); + strcpy(stringcast(nameoffile + 1), nom); + namelength = strlen(nom); + callback_id = callback_defined(read_font_file_callback); + if (callback_id > 0) { + res = run_callback(callback_id, "S->bSd", stringcast(nameoffile + 1), + &opened, tfm_buf, tfm_siz); + if (res && opened && (*tfm_siz > 0)) { + return 1; + } if (!opened) - return -1; - } else { - if (ofm_open_in(tfm_file)) { - res = read_tfm_file(tfm_file,tfm_buf,tfm_siz); - b_close(tfm_file); - if (res) { - return 1; - } + return -1; } else { - return -1; + if (ofm_open_in(tfm_file)) { + res = read_tfm_file(tfm_file, tfm_buf, tfm_siz); + b_close(tfm_file); + if (res) { + return 1; + } + } else { + return -1; + } } - } - return 0; + return 0; } @@ -441,47 +442,47 @@ open_tfm_file(char *nom, char *aire, unsigned char **tfm_buf, integer *tfm_siz) a=(a*256)+tfm_buffer[++tfm_byte]; } #define store_four_bytes(z) \ - { a=tfm_buffer[++tfm_byte]; \ - a=(a*256)+tfm_buffer[++tfm_byte]; \ - a=(a*256)+tfm_buffer[++tfm_byte]; \ - a=(a*256)+tfm_buffer[++tfm_byte]; \ + { a=tfm_buffer[++tfm_byte]; \ + a=(a*256)+tfm_buffer[++tfm_byte]; \ + a=(a*256)+tfm_buffer[++tfm_byte]; \ + a=(a*256)+tfm_buffer[++tfm_byte]; \ z = a; } #define store_char_info(z) \ { if (font_level!=-1) { \ - fget; read_sixteen_unsigned(a); \ - ci._width_index=a; \ - fget; read_sixteen_unsigned(b); \ - ci._height_index=b>>8; \ - ci._depth_index=b%256; \ - fget; read_sixteen_unsigned(c); \ - ci._italic_index=c>>8; \ - ci._tag=c%4; \ - fget; read_sixteen_unsigned(d); \ - ci._remainder=d; \ + fget; read_sixteen_unsigned(a); \ + ci._width_index=a; \ + fget; read_sixteen_unsigned(b); \ + ci._height_index=b>>8; \ + ci._depth_index=b%256; \ + fget; read_sixteen_unsigned(c); \ + ci._italic_index=c>>8; \ + ci._tag=c%4; \ + fget; read_sixteen_unsigned(d); \ + ci._remainder=d; \ } else { \ - a=tfm_buffer[++tfm_byte]; \ - ci._width_index=a; \ - b=tfm_buffer[++tfm_byte]; \ - ci._height_index=b>>4; \ - ci._depth_index=b%16; \ - c=tfm_buffer[++tfm_byte]; \ - ci._italic_index=c>>2; \ - ci._tag=c%4; \ - d=tfm_buffer[++tfm_byte]; \ - ci._remainder=d; \ + a=tfm_buffer[++tfm_byte]; \ + ci._width_index=a; \ + b=tfm_buffer[++tfm_byte]; \ + ci._height_index=b>>4; \ + ci._depth_index=b%16; \ + c=tfm_buffer[++tfm_byte]; \ + ci._italic_index=c>>2; \ + ci._tag=c%4; \ + d=tfm_buffer[++tfm_byte]; \ + ci._remainder=d; \ } } -#define read_four_quarters(q) \ +#define read_four_quarters(q) \ { if (font_level!=-1) { \ - fget; read_sixteen_unsigned(a); q.b0=a; \ - fget; read_sixteen_unsigned(b); q.b1=b; \ - fget; read_sixteen_unsigned(c); q.b2=c; \ - fget; read_sixteen_unsigned(d); q.b3=d; \ + fget; read_sixteen_unsigned(a); q.b0=a; \ + fget; read_sixteen_unsigned(b); q.b1=b; \ + fget; read_sixteen_unsigned(c); q.b2=c; \ + fget; read_sixteen_unsigned(d); q.b3=d; \ } else { \ - a=tfm_buffer[++tfm_byte]; q.b0=a; \ - b=tfm_buffer[++tfm_byte]; q.b1=b; \ - c=tfm_buffer[++tfm_byte]; q.b2=c; \ + a=tfm_buffer[++tfm_byte]; q.b0=a; \ + b=tfm_buffer[++tfm_byte]; q.b1=b; \ + c=tfm_buffer[++tfm_byte]; q.b2=c; \ d=tfm_buffer[++tfm_byte]; q.b3=d; \ } } @@ -507,499 +508,565 @@ open_tfm_file(char *nom, char *aire, unsigned char **tfm_buf, integer *tfm_siz) of \TeX\ between computers. */ -#define store_scaled(zz) \ +#define store_scaled(zz) \ { fget; a=fbyte; fget; b=fbyte; \ fget; c=fbyte; fget; d=fbyte; \ sw=(((((d*z)>>8)+(c*z))>>8)+(b*z)) / beta; \ - if (a==0) { zz=sw; } else if (a==255) { zz=sw-alpha; } else tfm_abort; \ + if (a==0) { zz=sw; } else if (a==255) { zz=sw-alpha; } else tfm_abort; \ } #define check_existence(z) \ { check_byte_range(z); \ - if (!char_exists(f,z)) tfm_abort; \ + if (!char_exists(f,z)) tfm_abort; \ } typedef struct tfmcharacterinfo { - integer _kern_index; - integer _lig_index; - integer _width_index; - integer _height_index; - integer _depth_index; - integer _italic_index; - integer _remainder; - unsigned char _tag ; + integer _kern_index; + integer _lig_index; + integer _width_index; + integer _height_index; + integer _depth_index; + integer _italic_index; + integer _remainder; + unsigned char _tag; } tfmcharacterinfo; -extern charinfo *copy_charinfo(charinfo *ci); - -int -read_tfm_info(internalfontnumber f, char *cnom, char *caire, scaled s) { - integer k; /* index into |font_info| */ - halfword lf,lh,bc,ec,nw,nh,nd,ni,nl,nk,ne,np,slh; /* sizes of subfiles */ - scaled *widths, *heights, *depths, *italics, *kerns; - halfword font_dir; - integer a,b,c,d; /* byte variables */ - integer i; /* counter */ - integer font_level,header_length; - integer nco,ncw,npc,nlw,neew; - tfmcharacterinfo ci; - charinfo *co; - four_quarters qw; - four_quarters *lig_kerns, *extens; - scaled sw; /* accumulators */ - integer bch_label; /* left boundary start location, or infinity */ - int bchar; /* :0..too_big_char; */ /* right boundary character, or |too_big_char| */ - integer first_two; - scaled z; /* the design size or the ``at'' size */ - integer alpha; - char beta; /* :1..16*/ - integer *xligs, *xkerns; /* aux. for ligkern processing */ - liginfo *cligs; - kerninfo *ckerns; - int fligs, fkerns; - char *tmpnam; - integer tfm_byte = 0; /* index into |tfm_buffer| */ - integer saved_tfm_byte = 0; /* saved index into |tfm_buffer| */ - unsigned char *tfm_buffer = NULL; /* byte buffer for tfm files */ - integer tfm_size = 0; /* total size of the tfm file */ - - widths=NULL; - heights=NULL; - depths = NULL; - italics = NULL; - kerns = NULL; - lig_kerns = NULL; - extens = NULL; - xkerns = NULL; - ckerns = NULL; - xligs = NULL; - cligs = NULL; - - font_dir = 0; - - memset(&ci,0,sizeof(tfmcharacterinfo)); - - if(open_tfm_file(cnom,caire,&tfm_buffer,&tfm_size)!=1) - tfm_abort; - - /* cnom can be an absolute filename, xbasename() fixes that. */ - - tmpnam=strdup(xbasename(cnom)); - if (strcmp(tmpnam+strlen(tmpnam)-4,".tfm")==0) { - *(tmpnam+strlen(tmpnam)-4) =0; - } - set_font_name(f,tmpnam); - set_font_area(f,xstrdup(caire)); /* perhaps it leaks, but it doesnt crash */ - - /* @<Read the {\.{TFM}} size fields@>; */ - nco=0; ncw=0; npc=0; - read_sixteen(first_two); - if (first_two!=0) { - font_level=-1; - lf=first_two; - fget; read_sixteen(lh); - fget; read_sixteen(bc); - fget; read_sixteen(ec); - if ((bc>ec+1)||(ec>255)) tfm_abort; - if (bc>255) { /* |bc=256| and |ec=255| */ - bc=1; ec=0; +int read_tfm_info(internalfontnumber f, char *cnom, char *caire, scaled s) +{ + integer k; /* index into |font_info| */ + halfword lf, lh, bc, ec, nw, nh, nd, ni, nl, nk, ne, np, slh; /* sizes of subfiles */ + scaled *widths, *heights, *depths, *italics, *kerns; + halfword font_dir; + integer a, b, c, d; /* byte variables */ + integer i; /* counter */ + integer font_level, header_length; + integer nco, ncw, npc, nlw, neew; + tfmcharacterinfo ci; + charinfo *co; + four_quarters qw; + four_quarters *lig_kerns, *extens; + scaled sw; /* accumulators */ + integer bch_label; /* left boundary start location, or infinity */ + int bchar; /* :0..too_big_char; *//* right boundary character, or |too_big_char| */ + integer first_two; + scaled z; /* the design size or the ``at'' size */ + integer alpha; + char beta; /* :1..16 */ + integer *xligs, *xkerns; /* aux. for ligkern processing */ + liginfo *cligs; + kerninfo *ckerns; + int fligs, fkerns; + char *tmpnam; + integer tfm_byte = 0; /* index into |tfm_buffer| */ + integer saved_tfm_byte = 0; /* saved index into |tfm_buffer| */ + unsigned char *tfm_buffer = NULL; /* byte buffer for tfm files */ + integer tfm_size = 0; /* total size of the tfm file */ + + widths = NULL; + heights = NULL; + depths = NULL; + italics = NULL; + kerns = NULL; + lig_kerns = NULL; + extens = NULL; + xkerns = NULL; + ckerns = NULL; + xligs = NULL; + cligs = NULL; + + font_dir = 0; + + memset(&ci, 0, sizeof(tfmcharacterinfo)); + + if (open_tfm_file(cnom, caire, &tfm_buffer, &tfm_size) != 1) + tfm_abort; + + /* cnom can be an absolute filename, xbasename() fixes that. */ + + tmpnam = strdup(xbasename(cnom)); + if (strcmp(tmpnam + strlen(tmpnam) - 4, ".tfm") == 0) { + *(tmpnam + strlen(tmpnam) - 4) = 0; + } + set_font_name(f, tmpnam); + set_font_area(f, NULL); + + /* @<Read the {\.{TFM}} size fields@>; */ + nco = 0; + ncw = 0; + npc = 0; + read_sixteen(first_two); + if (first_two != 0) { + font_level = -1; + lf = first_two; + fget; + read_sixteen(lh); + fget; + read_sixteen(bc); + fget; + read_sixteen(ec); + if ((bc > ec + 1) || (ec > 255)) + tfm_abort; + if (bc > 255) { /* |bc=256| and |ec=255| */ + bc = 1; + ec = 0; + }; + fget; + read_sixteen(nw); + fget; + read_sixteen(nh); + fget; + read_sixteen(nd); + fget; + read_sixteen(ni); + fget; + read_sixteen(nl); + fget; + read_sixteen(nk); + fget; + read_sixteen(ne); + fget; + read_sixteen(np); + header_length = 6; + ncw = (ec - bc + 1); + nlw = nl; + neew = ne; + } else { + fget; + read_sixteen(font_level); + if (font_level != 0) + tfm_abort; + read_thirtytwo(lf); + read_thirtytwo(lh); + read_thirtytwo(bc); + read_thirtytwo(ec); + if ((bc > ec + 1) || (ec > 65535)) + tfm_abort; + if (bc > 65535) { /* |bc=65536| and |ec=65535| */ + bc = 1; + ec = 0; + }; + read_thirtytwo(nw); + read_thirtytwo(nh); + read_thirtytwo(nd); + read_thirtytwo(ni); + read_thirtytwo(nl); + read_thirtytwo(nk); + read_thirtytwo(ne); + read_thirtytwo(np); + read_thirtytwo(font_dir); /* junk */ + nlw = 2 * nl; + neew = 2 * ne; + header_length = 14; + ncw = 2 * (ec - bc + 1); }; - fget; read_sixteen(nw); - fget; read_sixteen(nh); - fget; read_sixteen(nd); - fget; read_sixteen(ni); - fget; read_sixteen(nl); - fget; read_sixteen(nk); - fget; read_sixteen(ne); - fget; read_sixteen(np); - header_length=6; - ncw=(ec-bc+1); - nlw=nl; - neew=ne; - } else { - fget; read_sixteen(font_level); - if (font_level!=0) tfm_abort; - read_thirtytwo(lf); - read_thirtytwo(lh); - read_thirtytwo(bc); - read_thirtytwo(ec); - if ((bc>ec+1)||(ec>65535)) tfm_abort; - if (bc>65535) { /* |bc=65536| and |ec=65535| */ - bc=1; ec=0; + if (lf != + (header_length + lh + ncw + nw + nh + nd + ni + nlw + nk + neew + np)) + tfm_abort; + if ((nw == 0) || (nh == 0) || (nd == 0) || (ni == 0)) + tfm_abort; + + /* + We check to see that the \.{TFM} file doesn't end prematurely; but + no error message is given for files having more than |lf| words. + */ + if (lf * 4 > tfm_size) + tfm_abort; + + /* @<Use size fields to allocate font information@>; */ + + set_font_natural_dir(f, font_dir); + set_font_bc(f, bc); + set_font_ec(f, ec); + + /* read the arrays first */ + widths = xmalloc(nw * sizeof(scaled)); + heights = xmalloc(nh * sizeof(scaled)); + depths = xmalloc(nd * sizeof(scaled)); + italics = xmalloc(ni * sizeof(scaled)); + extens = xmalloc(ne * sizeof(four_quarters)); + lig_kerns = xmalloc(nl * sizeof(four_quarters)); + kerns = xmalloc(nk * sizeof(scaled)); + + /* @<Read the {\.{TFM}} header@>; */ + + /* Only the first two words of the header are needed by \TeX82. */ + slh = lh; + if (lh < 2) + tfm_abort; + store_four_bytes(font_checksum(f)); + fget; + read_sixteen(z); /* this rejects a negative design size */ + fget; + z = z * 256 + fbyte; + fget; + z = (z * 16) + (fbyte >> 4); + if (z < unity) + tfm_abort; + while (lh > 2) { + fget; + fget; + fget; + fget; + lh--; /* ignore the rest of the header */ }; - read_thirtytwo(nw); - read_thirtytwo(nh); - read_thirtytwo(nd); - read_thirtytwo(ni); - read_thirtytwo(nl); - read_thirtytwo(nk); - read_thirtytwo(ne); - read_thirtytwo(np); - read_thirtytwo(font_dir); /* junk */ - nlw=2*nl; - neew=2*ne; - header_length=14; - ncw=2*(ec-bc+1); - }; - if (lf!=(header_length+lh+ncw+nw+nh+nd+ni+nlw+nk+neew+np)) tfm_abort; - - /* @<Use size fields to allocate font information@>; */ - - set_font_natural_dir(f,font_dir); - set_font_bc(f,bc); - set_font_ec(f,ec); - - /* read the arrays first */ - widths = xmalloc(nw*sizeof(scaled)); - heights = xmalloc(nh*sizeof(scaled)); - depths = xmalloc(nd*sizeof(scaled)); - italics = xmalloc(ni*sizeof(scaled)); - extens = xmalloc(ne*sizeof(four_quarters)); - lig_kerns = xmalloc(nl*sizeof(four_quarters)); - kerns = xmalloc(nk*sizeof(scaled)); - - /* @<Read the {\.{TFM}} header@>; */ - - /* Only the first two words of the header are needed by \TeX82. */ - slh = lh; - if (lh<2) - tfm_abort; - store_four_bytes(font_checksum(f)); - fget; read_sixteen(z); /* this rejects a negative design size */ - fget; z=z*256+fbyte; fget; z=(z*16)+(fbyte>>4); - if (z<unity) tfm_abort; - while (lh>2) { - fget;fget;fget;fget; - lh--; /* ignore the rest of the header */ - }; - - /* read the arrays before the character info */ - - set_font_dsize(f,z); - if (s!=-1000) { - z = (s>=0 ? s : xn_over_d(z,-s,1000)); - } - set_font_size(f,z); - if (np>7) - set_font_params(f,np); + /* read the arrays before the character info */ - saved_tfm_byte = tfm_byte; - tfm_byte = (header_length+slh+ncw)*4 - 1; + set_font_dsize(f, z); + if (s != -1000) { + z = (s >= 0 ? s : xn_over_d(z, -s, 1000)); + } + set_font_size(f, z); - /* @<Replace |z| by $|z|^\prime$ and compute $\alpha,\beta$@>; */ + if (np > 7) + set_font_params(f, np); - alpha=16; - while (z>=040000000) { - z=z>>1; alpha=alpha+alpha; - }; - beta=256/alpha; alpha=alpha*z; + saved_tfm_byte = tfm_byte; + tfm_byte = (header_length + slh + ncw) * 4 - 1; - /* @<Read box dimensions@>; */ + /* @<Replace |z| by $|z|^\prime$ and compute $\alpha,\beta$@>; */ - for (k=0;k<nw;k++) { - store_scaled(sw); widths[k] = sw; - } - if (widths[0]!=0) /* \\{width}[0] must be zero */ - tfm_abort; - for (k=0;k<nh;k++) { - store_scaled(sw); heights[k] = sw; - } - if (heights[0]!=0) - tfm_abort; /* \\{height}[0] must be zero */ - for (k=0;k<nd;k++) { - store_scaled(sw); depths[k] = sw; - } - if (depths[0]!=0) - tfm_abort; /* \\{depth}[0] must be zero */ - for (k=0;k<ni;k++) { - store_scaled(sw); italics[k] = sw; - } - if (italics[0]!=0) - tfm_abort; /* \\{italic}[0] must be zero */ - - - /* @<Read ligature/kern program@>; */ - - bch_label=nl; /* infinity*/ - bchar=65536; - if (nl>0) { - for (k=0;k<nl;k++) { - read_four_quarters(qw); - lig_kerns[k] = qw; - if (a>128) { - if (256*c+d>=nl) tfm_abort; - if (a==255 && k==0) bchar=b; - } else { - /* if (b!=bchar) check_existence(b); */ - if (c<128) { - /* check_existence(d); */ /* check ligature */ - } else if (256*(c-128)+d>=nk) { - tfm_abort; /* check kern */ - } - if ((a<128) && (k-0+a+1>=nl)) tfm_abort; - }; + alpha = 16; + while (z >= 040000000) { + z = z >> 1; + alpha = alpha + alpha; }; - if (a==255) bch_label=256*c+d; - }; + beta = 256 / alpha; + alpha = alpha * z; - /* the actual kerns */ - for (k=0;k<nk;k++) { - store_scaled(sw); kerns[k] = sw; - } + /* @<Read box dimensions@>; */ - /* @<Read extensible character recipes@>; */ - for (k=0;k<ne;k++) { - read_four_quarters(qw); extens[k] = qw; - } + for (k = 0; k < nw; k++) { + store_scaled(sw); + widths[k] = sw; + } + if (widths[0] != 0) /* \\{width}[0] must be zero */ + tfm_abort; + for (k = 0; k < nh; k++) { + store_scaled(sw); + heights[k] = sw; + } + if (heights[0] != 0) + tfm_abort; /* \\{height}[0] must be zero */ + for (k = 0; k < nd; k++) { + store_scaled(sw); + depths[k] = sw; + } + if (depths[0] != 0) + tfm_abort; /* \\{depth}[0] must be zero */ + for (k = 0; k < ni; k++) { + store_scaled(sw); + italics[k] = sw; + } + if (italics[0] != 0) + tfm_abort; /* \\{italic}[0] must be zero */ + + + /* @<Read ligature/kern program@>; */ + + bch_label = nl; /* infinity */ + bchar = 65536; + if (nl > 0) { + for (k = 0; k < nl; k++) { + read_four_quarters(qw); + lig_kerns[k] = qw; + if (a > 128) { + if (256 * c + d >= nl) + tfm_abort; + if (a == 255 && k == 0) + bchar = b; + } else { + /* if (b!=bchar) check_existence(b); */ + if (c < 128) { + /* check_existence(d); *//* check ligature */ + } else if (256 * (c - 128) + d >= nk) { + tfm_abort; /* check kern */ + } + if ((a < 128) && (k - 0 + a + 1 >= nl)) + tfm_abort; + }; + }; + if (a == 255) + bch_label = 256 * c + d; + }; - /* @<Read font parameters@>; */ + /* the actual kerns */ + for (k = 0; k < nk; k++) { + store_scaled(sw); + kerns[k] = sw; + } - if (np>7) { - set_font_params(f,np); - } - for (k=1;k<=np;k++) { - if (k==1) { /* the |slant| parameter is a pure number */ - fget; sw=fbyte; - if (sw>127) sw=sw-256; - fget; sw=sw*256+fbyte; - fget; sw=sw*256+fbyte; - fget; sw=(sw*16)+(fbyte>>4); - set_font_param(f,k,sw); - } else { - store_scaled(font_param(f,k)); + /* @<Read extensible character recipes@>; */ + for (k = 0; k < ne; k++) { + read_four_quarters(qw); + extens[k] = qw; } - } - /* - We check to see that the \.{TFM} file doesn't end prematurely; but - no error message is given for files having more than |lf| words. - */ - - if (tfm_byte<tfm_size-1) tfm_abort; - - tfm_byte = saved_tfm_byte ; - - /* fix up the left boundary character */ - fligs = 0; - fkerns = 0; - if (bch_label != nl ) { - k = bch_label; - /* - if (skip_byte(k) > stop_flag) - k = lig_kern_restart(k); - */ - while (1) { - if (skip_byte(k) <= stop_flag) { - if(op_byte(k) >= kern_flag) { /* kern */ - fkerns++; - } else { /* lig */ - fligs++; - } - } - if (skip_byte(k) == 0) { - k++; - } else { - if (skip_byte(k) >= stop_flag) - break; - k += skip_byte(k) + 1; - } + /* @<Read font parameters@>; */ + + if (np > 7) { + set_font_params(f, np); } - } - if (fkerns >0 || fligs > 0) { - if (fligs>0) cligs = xcalloc((fligs+1),sizeof(liginfo)); - if (fkerns>0) ckerns = xcalloc((fkerns+1),sizeof(kerninfo)); + for (k = 1; k <= np; k++) { + if (k == 1) { /* the |slant| parameter is a pure number */ + fget; + sw = fbyte; + if (sw > 127) + sw = sw - 256; + fget; + sw = sw * 256 + fbyte; + fget; + sw = sw * 256 + fbyte; + fget; + sw = (sw * 16) + (fbyte >> 4); + set_font_param(f, k, sw); + } else { + store_scaled(font_param(f, k)); + } + } + + tfm_byte = saved_tfm_byte; + + /* fix up the left boundary character */ fligs = 0; fkerns = 0; - k = bch_label; - /* - if (skip_byte(k) > stop_flag) - k = lig_kern_restart(k); - */ - while (1) { - if (skip_byte(k) <= stop_flag) { - if(op_byte(k) >= kern_flag) { /* kern */ - set_kern_item(ckerns[fkerns],next_char(k),kerns[256*(op_byte(k)-128)+rem_byte(k)]); - fkerns++; - } else { /* lig */ - set_ligature_item(cligs[fligs],(op_byte(k)*2+1),next_char(k),rem_byte(k)); - fligs++; - } - } - if (skip_byte(k) == 0) { - k++; - } else { - if (skip_byte(k) >= stop_flag) - break; - k += skip_byte(k) + 1; - } + if (bch_label != nl) { + k = bch_label; + /* + if (skip_byte(k) > stop_flag) + k = lig_kern_restart(k); + */ + while (1) { + if (skip_byte(k) <= stop_flag) { + if (op_byte(k) >= kern_flag) { /* kern */ + fkerns++; + } else { /* lig */ + fligs++; + } + } + if (skip_byte(k) == 0) { + k++; + } else { + if (skip_byte(k) >= stop_flag) + break; + k += skip_byte(k) + 1; + } + } } - if (fkerns>0 || fligs>0){ - co = get_charinfo(f,left_boundarychar); - if (fkerns>0) { - set_kern_item(ckerns[fkerns],end_kern,0); - fkerns++; - set_charinfo_kerns(co,ckerns); - } - if (fligs>0){ - set_ligature_item(cligs[fligs],0,end_ligature,0); - fligs++; - set_charinfo_ligatures(co,cligs); - } - set_charinfo_remainder(co,0); + if (fkerns > 0 || fligs > 0) { + if (fligs > 0) + cligs = xcalloc((fligs + 1), sizeof(liginfo)); + if (fkerns > 0) + ckerns = xcalloc((fkerns + 1), sizeof(kerninfo)); + fligs = 0; + fkerns = 0; + k = bch_label; + /* + if (skip_byte(k) > stop_flag) + k = lig_kern_restart(k); + */ + while (1) { + if (skip_byte(k) <= stop_flag) { + if (op_byte(k) >= kern_flag) { /* kern */ + set_kern_item(ckerns[fkerns], next_char(k), + kerns[256 * (op_byte(k) - 128) + + rem_byte(k)]); + fkerns++; + } else { /* lig */ + set_ligature_item(cligs[fligs], (op_byte(k) * 2 + 1), + next_char(k), rem_byte(k)); + fligs++; + } + } + if (skip_byte(k) == 0) { + k++; + } else { + if (skip_byte(k) >= stop_flag) + break; + k += skip_byte(k) + 1; + } + } + if (fkerns > 0 || fligs > 0) { + co = get_charinfo(f, left_boundarychar); + if (fkerns > 0) { + set_kern_item(ckerns[fkerns], end_kern, 0); + fkerns++; + set_charinfo_kerns(co, ckerns); + } + if (fligs > 0) { + set_ligature_item(cligs[fligs], 0, end_ligature, 0); + fligs++; + set_charinfo_ligatures(co, cligs); + } + set_charinfo_remainder(co, 0); + } } - } - /* @<Read character data@>; */ - for (k=bc;k<=ec;k++) { - store_char_info(k); - if (ci._width_index==0) - continue; - if (ci._width_index>=nw||ci._height_index>=nh|| - ci._depth_index>=nd||ci._italic_index>=ni) tfm_abort; - d = ci._remainder; - switch (ci._tag) { - case lig_tag: if (d>=nl) tfm_abort; break; - case ext_tag: if (d>=ne) tfm_abort; break; - case list_tag: - /* We want to make sure that there is no cycle of characters linked together - by |list_tag| entries, since such a cycle would get \TeX\ into an endless - loop. If such a cycle exists, the routine here detects it when processing - the largest character code in the cycle. - */ - check_byte_range(d); - while (d<k) { /* current_character == k */ - if (char_tag(f,d)!=list_tag) - goto NOT_FOUND; /* not a cycle */ - d=char_remainder(f,d); /* next character on the list */ - }; - if (d==k) tfm_abort; /* yes, there's a cycle */ - NOT_FOUND: - break; - } - /* put it in the actual font */ - co = get_charinfo(f,k); - set_charinfo_index (co,k); - set_charinfo_tag (co,ci._tag); - if (ci._tag == ext_tag) { - set_charinfo_extensible(co, - extens[ci._remainder].b0, /* top */ - extens[ci._remainder].b2, /* bot */ - extens[ci._remainder].b1, /* mid */ - extens[ci._remainder].b3); /* rep */ - set_charinfo_remainder (co,0); - } else { - set_charinfo_remainder (co,ci._remainder); - } - set_charinfo_width (co,widths[ci._width_index]); - set_charinfo_height (co,heights[ci._height_index]); - set_charinfo_depth (co,depths[ci._depth_index]); - set_charinfo_italic (co,italics[ci._italic_index]); - }; - - /* first pass: count ligs and kerns */ - - xligs = xcalloc((ec+1),sizeof(integer)); - xkerns = xcalloc((ec+1),sizeof(integer)); - - for (i=bc;i<=ec;i++) { - if (char_tag(f,i) == lig_tag) { - k = lig_kern_start(f,i); - if (skip_byte(k) > stop_flag) - k = lig_kern_restart(k); - /* now k is the start index */ - while (1) { - if (skip_byte(k) <= stop_flag) { - if(op_byte(k) >= kern_flag) { /* kern */ - xkerns[i]++; - if (next_char(k) == bchar) - xkerns[i]++; - } else { /* lig */ - xligs[i]++; - if (next_char(k) == bchar) - xligs[i]++; - } - } - if (skip_byte(k) == 0) { - k++; - } else { - if (skip_byte(k) >= stop_flag) - break; - k += skip_byte(k) + 1; - } - } + /* @<Read character data@>; */ + for (k = bc; k <= ec; k++) { + store_char_info(k); + if (ci._width_index == 0) + continue; + if (ci._width_index >= nw || ci._height_index >= nh || + ci._depth_index >= nd || ci._italic_index >= ni) + tfm_abort; + d = ci._remainder; + switch (ci._tag) { + case lig_tag: + if (d >= nl) + tfm_abort; + break; + case ext_tag: + if (d >= ne) + tfm_abort; + break; + case list_tag: + /* We want to make sure that there is no cycle of characters linked together + by |list_tag| entries, since such a cycle would get \TeX\ into an endless + loop. If such a cycle exists, the routine here detects it when processing + the largest character code in the cycle. + */ + check_byte_range(d); + while (d < k) { /* current_character == k */ + if (char_tag(f, d) != list_tag) + goto NOT_FOUND; /* not a cycle */ + d = char_remainder(f, d); /* next character on the list */ + }; + if (d == k) + tfm_abort; /* yes, there's a cycle */ + NOT_FOUND: + break; + } + /* put it in the actual font */ + co = get_charinfo(f, k); + set_charinfo_index(co, k); + set_charinfo_tag(co, ci._tag); + if (ci._tag == ext_tag) { + set_charinfo_extensible(co, extens[ci._remainder].b0, /* top */ + extens[ci._remainder].b2, /* bot */ + extens[ci._remainder].b1, /* mid */ + extens[ci._remainder].b3); /* rep */ + set_charinfo_remainder(co, 0); + } else { + set_charinfo_remainder(co, ci._remainder); + } + set_charinfo_width(co, widths[ci._width_index]); + set_charinfo_height(co, heights[ci._height_index]); + set_charinfo_depth(co, depths[ci._depth_index]); + set_charinfo_italic(co, italics[ci._italic_index]); + }; + + /* first pass: count ligs and kerns */ + + xligs = xcalloc((ec + 1), sizeof(integer)); + xkerns = xcalloc((ec + 1), sizeof(integer)); + + for (i = bc; i <= ec; i++) { + if (char_tag(f, i) == lig_tag) { + k = lig_kern_start(f, i); + if (skip_byte(k) > stop_flag) + k = lig_kern_restart(k); + /* now k is the start index */ + while (1) { + if (skip_byte(k) <= stop_flag) { + if (op_byte(k) >= kern_flag) { /* kern */ + xkerns[i]++; + if (next_char(k) == bchar) + xkerns[i]++; + } else { /* lig */ + xligs[i]++; + if (next_char(k) == bchar) + xligs[i]++; + } + } + if (skip_byte(k) == 0) { + k++; + } else { + if (skip_byte(k) >= stop_flag) + break; + k += skip_byte(k) + 1; + } + } + } } - } - - cligs = NULL; - ckerns = NULL; - for (i=bc;i<=ec;i++) { - fligs = 0; - fkerns = 0; - if (char_tag(f,i) == lig_tag) { - k = lig_kern_start(f,i); - if (skip_byte(k) > stop_flag) - k = lig_kern_restart(k); - /* now k is the start index */ - if (xligs[i]>0) cligs = xcalloc((xligs[i]+1),sizeof(liginfo)); - if (xkerns[i]>0) ckerns = xcalloc((xkerns[i]+1),sizeof(kerninfo)); - while (1) { - if (skip_byte(k) <= stop_flag) { - if(op_byte(k) >= kern_flag) { /* kern */ - if (next_char(k) == bchar) { - set_kern_item(ckerns[fkerns],right_boundarychar,kerns[256*(op_byte(k)-128)+rem_byte(k)]); - fkerns++; - } - set_kern_item(ckerns[fkerns],next_char(k),kerns[256*(op_byte(k)-128)+rem_byte(k)]); - fkerns++; - } else { /* lig */ - if (next_char(k) == bchar) { - set_ligature_item(cligs[fligs],(op_byte(k)*2+1),right_boundarychar,rem_byte(k)); - fligs++; - } - set_ligature_item(cligs[fligs],(op_byte(k)*2+1),next_char(k),rem_byte(k)); - fligs++; - } - } - if (skip_byte(k) == 0) { - k++; - } else { - if (skip_byte(k) >= stop_flag) - break; - k += skip_byte(k) + 1; - } - } - if (fkerns>0 || fligs>0){ - co = get_charinfo(f,i); - if (fkerns>0) { - set_kern_item(ckerns[fkerns],end_kern,0); - fkerns++; - set_charinfo_kerns(co,ckerns); - } - if (fligs>0){ - set_ligature_item(cligs[fligs],0,end_ligature,0); - fligs++; - set_charinfo_ligatures(co,cligs); - } - set_charinfo_remainder(co,0); - } + cligs = NULL; + ckerns = NULL; + + for (i = bc; i <= ec; i++) { + fligs = 0; + fkerns = 0; + if (char_tag(f, i) == lig_tag) { + k = lig_kern_start(f, i); + if (skip_byte(k) > stop_flag) + k = lig_kern_restart(k); + /* now k is the start index */ + if (xligs[i] > 0) + cligs = xcalloc((xligs[i] + 1), sizeof(liginfo)); + if (xkerns[i] > 0) + ckerns = xcalloc((xkerns[i] + 1), sizeof(kerninfo)); + while (1) { + if (skip_byte(k) <= stop_flag) { + if (op_byte(k) >= kern_flag) { /* kern */ + if (next_char(k) == bchar) { + set_kern_item(ckerns[fkerns], right_boundarychar, + kerns[256 * (op_byte(k) - 128) + + rem_byte(k)]); + fkerns++; + } + set_kern_item(ckerns[fkerns], next_char(k), + kerns[256 * (op_byte(k) - 128) + + rem_byte(k)]); + fkerns++; + } else { /* lig */ + if (next_char(k) == bchar) { + set_ligature_item(cligs[fligs], + (op_byte(k) * 2 + 1), + right_boundarychar, rem_byte(k)); + fligs++; + } + set_ligature_item(cligs[fligs], (op_byte(k) * 2 + 1), + next_char(k), rem_byte(k)); + fligs++; + } + } + if (skip_byte(k) == 0) { + k++; + } else { + if (skip_byte(k) >= stop_flag) + break; + k += skip_byte(k) + 1; + } + } + if (fkerns > 0 || fligs > 0) { + co = get_charinfo(f, i); + if (fkerns > 0) { + set_kern_item(ckerns[fkerns], end_kern, 0); + fkerns++; + set_charinfo_kerns(co, ckerns); + } + if (fligs > 0) { + set_ligature_item(cligs[fligs], 0, end_ligature, 0); + fligs++; + set_charinfo_ligatures(co, cligs); + } + set_charinfo_remainder(co, 0); + } + } } - } - /* @<Make final adjustments and |goto done|@> */ + /* @<Make final adjustments and |goto done|@> */ - /* Now to wrap it up, we have checked all the necessary things about the \.{TFM} - file, and all we need to do is put the finishing touches on the data for - the new font. - */ + /* Now to wrap it up, we have checked all the necessary things about the \.{TFM} + file, and all we need to do is put the finishing touches on the data for + the new font. + */ - if (bchar!= 65536) { - co = copy_charinfo(char_info(f,bchar)); - set_right_boundary(f,co); - } + if (bchar != 65536) { + co = copy_charinfo(char_info(f, bchar)); + set_right_boundary(f, co); + } - tfm_success; + tfm_success; } - diff --git a/Build/source/texk/web2c/luatexdir/font/tounicode.c b/Build/source/texk/web2c/luatexdir/font/tounicode.c index ff86a8512e2..29ee8c9bd0b 100644 --- a/Build/source/texk/web2c/luatexdir/font/tounicode.c +++ b/Build/source/texk/web2c/luatexdir/font/tounicode.c @@ -1,25 +1,27 @@ -/* -Copyright (c) 2006 Han The Thanh, <thanh@pdftex.org> +/* tounicode.c + Copyright 2006 Han The Thanh, <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -This file is part of pdfTeX. + This file is part of LuaTeX. -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" +static const char _svn_version[] = + "$Id: tounicode.c 2029 2009-03-14 19:10:25Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/tounicode.c $"; + #define isXdigit(c) (isdigit(c) || ('A' <= (c) && (c) <= 'F')) #define UNI_UNDEF -1 #define UNI_STRING -2 /* string allocated by def_tounicode() */ @@ -289,17 +291,17 @@ static void set_glyph_unicode(char *s, glyph_unicode_entry * gp) } } -static void set_cid_glyph_unicode(long index, glyph_unicode_entry * gp, - internal_font_number f) { - char *s; - if (font_tounicode(f)) { - if ((s = get_charinfo_tounicode(char_info(f,index)))!=NULL) { +static void set_cid_glyph_unicode(long index, glyph_unicode_entry * gp, + internal_font_number f) +{ + char *s; + if (font_tounicode(f) && + (s = get_charinfo_tounicode(char_info(f, index))) != NULL) { gp->code = UNI_EXTRA_STRING; gp->unicode_seq = xstrdup(s); - } - } else { - gp->code = index; /* fallback */ - } + } else { + gp->code = index; /* fallback */ + } } @@ -314,7 +316,7 @@ integer write_tounicode(char **glyph_names, char *name) int bfchar_count, bfrange_count, subrange_count; assert(strlen(name) + strlen(builtin_suffix) < SMALL_BUF_SIZE); if (glyph_unicode_tree == NULL) { - pdftex_warn("no GlyphToUnicode entry has been inserted yet!"); + /*pdftex_warn("no GlyphToUnicode entry has been inserted yet!"); */ fixed_gen_tounicode = 0; return 0; } @@ -451,19 +453,21 @@ integer write_tounicode(char **glyph_names, char *name) return objnum; } -integer write_cid_tounicode(fo_entry * fo, internalfontnumber f) { +integer write_cid_tounicode(fo_entry * fo, internalfontnumber f) +{ int range_size[65537]; glyph_unicode_entry gtab[65537]; integer objnum; int i, j, k; int bfchar_count, bfrange_count, subrange_count; - char *buf; + char *buf; - assert(fo->fd->fontname); - buf = xmalloc(strlen(fo->fd->fontname)+8); - sprintf(buf,"%s-%s",(fo->fd->subset_tag!=NULL ? fo->fd->subset_tag : "UCS"), - fo->fd->fontname); + assert(fo->fd->fontname); + buf = xmalloc(strlen(fo->fd->fontname) + 8); + sprintf(buf, "%s-%s", + (fo->fd->subset_tag != NULL ? fo->fd->subset_tag : "UCS"), + fo->fd->fontname); objnum = pdf_new_objnum(); pdf_begin_dict(objnum, 0); @@ -486,25 +490,25 @@ integer write_cid_tounicode(fo_entry * fo, internalfontnumber f) { "/CMapName /TeX-Identity-%s def\n" "/CMapType 2 def\n" "1 begincodespacerange\n" - "<0000> <FFFF>\n" + "<0000> <FFFF>\n" "endcodespacerange\n", buf, buf, buf, buf, buf); - xfree(buf); + xfree(buf); /* set up gtab */ for (i = 0; i < 65537; ++i) { gtab[i].code = UNI_UNDEF; } - for (k = 1; k <= max_font_id(); k++) { - if (k == f || -f == pdf_font_num(k)) { - for (i = font_bc(k); i <= font_ec(k); i++) { - if (char_exists(k,i) && char_used(k,i)) { - j = char_index(k,i); - if (gtab[j].code == UNI_UNDEF) { - set_cid_glyph_unicode(i, >ab[j], f); - } - } - } - } - } + for (k = 1; k <= max_font_id(); k++) { + if (k == f || -f == pdf_font_num(k)) { + for (i = font_bc(k); i <= font_ec(k); i++) { + if (char_exists(k, i) && char_used(k, i)) { + j = char_index(k, i); + if (gtab[j].code == UNI_UNDEF) { + set_cid_glyph_unicode(i, >ab[j], f); + } + } + } + } + } /* set range_size */ for (i = 0; i < 65536;) { @@ -522,7 +526,7 @@ integer write_cid_tounicode(fo_entry * fo, internalfontnumber f) { /* at this point i is the last entry of the subrange */ i++; /* move i to the next entry */ range_size[j] = i - j; - } + } } /* calculate bfrange_count and bfchar_count */ diff --git a/Build/source/texk/web2c/luatexdir/font/tt_glyf.c b/Build/source/texk/web2c/luatexdir/font/tt_glyf.c index bf21e58c49a..b024897f82d 100644 --- a/Build/source/texk/web2c/luatexdir/font/tt_glyf.c +++ b/Build/source/texk/web2c/luatexdir/font/tt_glyf.c @@ -1,24 +1,23 @@ -/* $Header: /home/cvsroot/dvipdfmx/src/tt_glyf.c,v 1.2 2005/06/09 14:31:11 hirata Exp $ +/* tt_glyf.c - This is dvipdfmx, an eXtended version of dvipdfm by Mark A. Wicks. + Copyright 2002 by Jin-Hwan Cho and Shunsaku Hirata, + the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> - Copyright (C) 2002 by Jin-Hwan Cho and Shunsaku Hirata, - the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. -*/ + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ /* * Subsetting glyf, updating loca, hmtx, ... @@ -30,629 +29,623 @@ #include "sfnt.h" #include "tt_table.h" #include "tt_glyf.h" +#include "writettf.h" + +static const char _svn_version[] = + "$Id: tt_glyf.c 1592 2008-11-28 13:23:51Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/tt_glyf.c $"; #define NUM_GLYPH_LIMIT 65534 #define TABLE_DATA_ALLOC_SIZE 40960 #define GLYPH_ARRAY_ALLOC_SIZE 256 -static USHORT -find_empty_slot (struct tt_glyphs *g) +static USHORT find_empty_slot(struct tt_glyphs *g) { - USHORT gid; + USHORT gid; - ASSERT(g); + ASSERT(g); - for (gid = 0; gid < NUM_GLYPH_LIMIT; gid++) { - if (!(g->used_slot[gid/8] & (1 << (7 - (gid % 8))))) - break; - } - if (gid == NUM_GLYPH_LIMIT) - TT_ERROR("No empty glyph slot available."); + for (gid = 0; gid < NUM_GLYPH_LIMIT; gid++) { + if (!(g->used_slot[gid / 8] & (1 << (7 - (gid % 8))))) + break; + } + if (gid == NUM_GLYPH_LIMIT) + TT_ERROR("No empty glyph slot available."); - return gid; + return gid; } -USHORT -tt_find_glyph (struct tt_glyphs *g, USHORT gid) +USHORT tt_find_glyph(struct tt_glyphs * g, USHORT gid) { - USHORT idx, new_gid = 0; + USHORT idx, new_gid = 0; - ASSERT(g); + ASSERT(g); - for (idx = 0; idx < g->num_glyphs; idx++) { - if (gid == g->gd[idx].ogid) { - new_gid = g->gd[idx].gid; - break; + for (idx = 0; idx < g->num_glyphs; idx++) { + if (gid == g->gd[idx].ogid) { + new_gid = g->gd[idx].gid; + break; + } } - } - return new_gid; + return new_gid; } -USHORT -tt_get_index (struct tt_glyphs *g, USHORT gid) +USHORT tt_get_index(struct tt_glyphs * g, USHORT gid) { - USHORT idx; + USHORT idx; - ASSERT(g); + ASSERT(g); - for (idx = 0; idx < g->num_glyphs; idx++) { - if (gid == g->gd[idx].gid) - break; - } - if (idx == g->num_glyphs) - idx = 0; + for (idx = 0; idx < g->num_glyphs; idx++) { + if (gid == g->gd[idx].gid) + break; + } + if (idx == g->num_glyphs) + idx = 0; - return idx; + return idx; } -USHORT -tt_add_glyph (struct tt_glyphs *g, USHORT gid, USHORT new_gid) +USHORT tt_add_glyph(struct tt_glyphs * g, USHORT gid, USHORT new_gid) { - ASSERT(g); + ASSERT(g); - if (g->used_slot[new_gid/8] & (1 << (7 - (new_gid % 8)))) { - WARN("Slot %u already used.", new_gid); - } else { - if (g->num_glyphs+1 >= NUM_GLYPH_LIMIT) - TT_ERROR("Too many glyphs."); + if (g->used_slot[new_gid / 8] & (1 << (7 - (new_gid % 8)))) { + WARN("Slot %u already used.", new_gid); + } else { + if (g->num_glyphs + 1 >= NUM_GLYPH_LIMIT) + TT_ERROR("Too many glyphs."); + + if (g->num_glyphs >= g->max_glyphs) { + g->max_glyphs += GLYPH_ARRAY_ALLOC_SIZE; + g->gd = RENEW(g->gd, g->max_glyphs, struct tt_glyph_desc); + } + g->gd[g->num_glyphs].gid = new_gid; + g->gd[g->num_glyphs].ogid = gid; + g->gd[g->num_glyphs].length = 0; + g->gd[g->num_glyphs].data = NULL; + g->used_slot[new_gid / 8] |= (1 << (7 - (new_gid % 8))); + g->num_glyphs += 1; + } - if (g->num_glyphs >= g->max_glyphs) { - g->max_glyphs += GLYPH_ARRAY_ALLOC_SIZE; - g->gd = RENEW(g->gd, g->max_glyphs, struct tt_glyph_desc); + if (new_gid > g->last_gid) { + g->last_gid = new_gid; } - g->gd[g->num_glyphs].gid = new_gid; - g->gd[g->num_glyphs].ogid = gid; - g->gd[g->num_glyphs].length = 0; - g->gd[g->num_glyphs].data = NULL; - g->used_slot[new_gid/8] |= (1 << (7 - (new_gid % 8))); - g->num_glyphs += 1; - } - - if (new_gid > g->last_gid) { - g->last_gid = new_gid; - } - - return new_gid; + + return new_gid; } /* * Initialization */ -struct tt_glyphs * -tt_build_init (void) +struct tt_glyphs *tt_build_init(void) { - struct tt_glyphs *g; - - g = NEW(1, struct tt_glyphs); - - g->num_glyphs = 0; - g->max_glyphs = 0; - g->last_gid = 0; - g->emsize = 1; - g->default_advh = 0; - g->default_tsb = 0; - g->gd = NULL; - g->used_slot = NEW(8192, unsigned char); - memset(g->used_slot, 0, 8192); - tt_add_glyph(g, 0, 0); - - return g; + struct tt_glyphs *g; + + g = NEW(1, struct tt_glyphs); + + g->num_glyphs = 0; + g->max_glyphs = 0; + g->last_gid = 0; + g->emsize = 1; + g->default_advh = 0; + g->default_tsb = 0; + g->gd = NULL; + g->used_slot = NEW(8192, unsigned char); + memset(g->used_slot, 0, 8192); + tt_add_glyph(g, 0, 0); + + return g; } -void -tt_build_finish (struct tt_glyphs *g) +void tt_build_finish(struct tt_glyphs *g) { - if (g) { - if (g->gd) { - USHORT idx; - for (idx = 0; idx < g->num_glyphs; idx++) { - if (g->gd[idx].data) - RELEASE(g->gd[idx].data); - } - RELEASE(g->gd); + if (g) { + if (g->gd) { + USHORT idx; + for (idx = 0; idx < g->num_glyphs; idx++) { + if (g->gd[idx].data) + RELEASE(g->gd[idx].data); + } + RELEASE(g->gd); + } + if (g->used_slot) + RELEASE(g->used_slot); + RELEASE(g); } - if (g->used_slot) - RELEASE(g->used_slot); - RELEASE(g); - } } -static int -glyf_cmp (const void *v1, const void *v2) +static int glyf_cmp(const void *v1, const void *v2) { - int cmp = 0; - struct tt_glyph_desc *sv1, *sv2; - - sv1 = (struct tt_glyph_desc *) v1; - sv2 = (struct tt_glyph_desc *) v2; - - if (sv1->gid == sv2->gid) - cmp = 0; - else if (sv1->gid < sv2->gid) - cmp = -1; - else - cmp = 1; - - return cmp; + int cmp = 0; + struct tt_glyph_desc *sv1, *sv2; + + sv1 = (struct tt_glyph_desc *) v1; + sv2 = (struct tt_glyph_desc *) v2; + + if (sv1->gid == sv2->gid) + cmp = 0; + else if (sv1->gid < sv2->gid) + cmp = -1; + else + cmp = 1; + + return cmp; } -/* - * TrueType outline data. - */ -#define ARG_1_AND_2_ARE_WORDS (1 << 0) -#define ARGS_ARE_XY_VALUES (1 << 1) -#define ROUND_XY_TO_GRID (1 << 2) -#define WE_HAVE_A_SCALE (1 << 3) -#define RESERVED (1 << 4) -#define MORE_COMPONENT (1 << 5) -#define WE_HAVE_AN_X_AND_Y_SCALE (1 << 6) -#define WE_HAVE_A_TWO_BY_TWO (1 << 7) -#define WE_HAVE_INSTRUCTIONS (1 << 8) -#define USE_MY_METRICS (1 << 9) - -int -tt_build_tables (sfnt *sfont, struct tt_glyphs *g) +int tt_build_tables(sfnt * sfont, struct tt_glyphs *g) { - char *hmtx_table_data = NULL, *loca_table_data = NULL; - char *glyf_table_data = NULL; - ULONG hmtx_table_size, loca_table_size, glyf_table_size; - /* some information available from other TrueType table */ - struct tt_head_table *head = NULL; - struct tt_hhea_table *hhea = NULL; - struct tt_maxp_table *maxp = NULL; - struct tt_longMetrics *hmtx, *vmtx = NULL; - struct tt_os2__table *os2; - /* temp */ - ULONG *location, offset; - long i; - USHORT *w_stat; /* Estimate most frequently appeared width */ - - ASSERT(g); - - if (sfont->type != SFNT_TYPE_TRUETYPE && - sfont->type != SFNT_TYPE_TTC) - TT_ERROR("Invalid font type"); - - if (g->num_glyphs > NUM_GLYPH_LIMIT) - TT_ERROR("Too many glyphs."); - - /* - * Read head, hhea, maxp, loca: - * - * unitsPerEm --> head - * numHMetrics --> hhea - * indexToLocFormat --> head - * numGlyphs --> maxp - */ - head = tt_read_head_table(sfont); - hhea = tt_read_hhea_table(sfont); - maxp = tt_read_maxp_table(sfont); - - if (hhea->metricDataFormat != 0) - TT_ERROR("Unknown metricDataFormat."); - - g->emsize = head->unitsPerEm; - - sfnt_locate_table(sfont, "hmtx"); - hmtx = tt_read_longMetrics(sfont, maxp->numGlyphs, hhea->numberOfHMetrics); - - os2 = tt_read_os2__table(sfont); - if (os2) { - g->default_advh = os2->sTypoAscender - os2->sTypoDescender; - g->default_tsb = g->default_advh - os2->sTypoAscender; - } - - if (sfnt_find_table_pos(sfont, "vmtx") > 0) { - struct tt_vhea_table *vhea; - vhea = tt_read_vhea_table(sfont); - sfnt_locate_table(sfont, "vmtx"); - vmtx = tt_read_longMetrics(sfont, maxp->numGlyphs, vhea->numOfLongVerMetrics); - RELEASE(vhea); - } else { - vmtx = NULL; - } - - sfnt_locate_table(sfont, "loca"); - location = NEW(maxp->numGlyphs + 1, ULONG); - if (head->indexToLocFormat == 0) { - for (i = 0; i <= maxp->numGlyphs; i++) - location[i] = 2*((ULONG) sfnt_get_ushort(sfont)); - } else if (head->indexToLocFormat == 1) { - for (i = 0; i <= maxp->numGlyphs; i++) - location[i] = sfnt_get_ulong(sfont); - } else { - TT_ERROR("Unknown IndexToLocFormat."); - } - - w_stat = NEW(g->emsize+2, USHORT); - memset(w_stat, 0, sizeof(USHORT)*(g->emsize+2)); - /* - * Read glyf table. - */ - offset = sfnt_locate_table(sfont, "glyf"); - /* - * The num_glyphs may grow when composite glyph is found. - * A component of glyph refered by a composite glyph is appended - * to used_glyphs if it is not already registered in used_glyphs. - * Glyph programs of composite glyphs are modified so that it - * correctly refer to new gid of their components. - */ - for (i = 0; i < NUM_GLYPH_LIMIT; i++) { - USHORT gid; /* old gid */ - ULONG loc, len; - BYTE *p, *endptr; - SHORT number_of_contours; - - if (i >= g->num_glyphs) /* finished */ - break; - - gid = g->gd[i].ogid; - if (gid >= maxp->numGlyphs) - TT_ERROR("Invalid glyph index (gid %u)", gid); - - loc = location[gid]; - len = location[gid+1] - loc; - g->gd[i].advw = hmtx[gid].advance; - g->gd[i].lsb = hmtx[gid].sideBearing; - if (vmtx) { - g->gd[i].advh = vmtx[gid].advance; - g->gd[i].tsb = vmtx[gid].sideBearing; - } else { - g->gd[i].advh = g->default_advh; - g->gd[i].tsb = g->default_tsb; - } - g->gd[i].length = len; - g->gd[i].data = NULL; - if (g->gd[i].advw <= g->emsize) { - w_stat[g->gd[i].advw] += 1; - } else { - w_stat[g->emsize+1] += 1; /* larger than em */ - } + char *hmtx_table_data = NULL, *loca_table_data = NULL; + char *glyf_table_data = NULL; + ULONG hmtx_table_size, loca_table_size, glyf_table_size; + /* some information available from other TrueType table */ + struct tt_head_table *head = NULL; + struct tt_hhea_table *hhea = NULL; + struct tt_maxp_table *maxp = NULL; + struct tt_longMetrics *hmtx, *vmtx = NULL; + struct tt_os2__table *os2; + /* temp */ + ULONG *location, offset; + long i; + USHORT *w_stat; /* Estimate most frequently appeared width */ + + ASSERT(g); + + if (sfont->type != SFNT_TYPE_TRUETYPE && sfont->type != SFNT_TYPE_TTC) + TT_ERROR("Invalid font type"); + + if (g->num_glyphs > NUM_GLYPH_LIMIT) + TT_ERROR("Too many glyphs."); - if (len == 0) { /* Does not contains any data. */ - continue; - } else if (len < 10) { - TT_ERROR("Invalid TrueType glyph data (gid %u).", gid); - } + /* + * Read head, hhea, maxp, loca: + * + * unitsPerEm --> head + * numHMetrics --> hhea + * indexToLocFormat --> head + * numGlyphs --> maxp + */ + head = tt_read_head_table(sfont); + hhea = tt_read_hhea_table(sfont); + maxp = tt_read_maxp_table(sfont); - g->gd[i].data = p = NEW(len, BYTE); - endptr = p + len; + if (hhea->metricDataFormat != 0) + TT_ERROR("Unknown metricDataFormat."); - sfnt_seek_set(sfont, offset+loc); - number_of_contours = sfnt_get_short(sfont); - p += sfnt_put_short(p, number_of_contours); + g->emsize = head->unitsPerEm; - /* BoundingBox: FWord x 4 */ - g->gd[i].llx = sfnt_get_short(sfont); - g->gd[i].lly = sfnt_get_short(sfont); - g->gd[i].urx = sfnt_get_short(sfont); - g->gd[i].ury = sfnt_get_short(sfont); - /* _FIXME_ */ -#if 1 - if (!vmtx) /* vertOriginY == sTypeAscender */ - g->gd[i].tsb = g->default_advh - g->default_tsb - g->gd[i].ury; -#endif - p += sfnt_put_short(p, g->gd[i].llx); - p += sfnt_put_short(p, g->gd[i].lly); - p += sfnt_put_short(p, g->gd[i].urx); - p += sfnt_put_short(p, g->gd[i].ury); + sfnt_locate_table(sfont, "hmtx"); + hmtx = tt_read_longMetrics(sfont, maxp->numGlyphs, hhea->numberOfHMetrics); - /* Read evrything else. */ - sfnt_read(p, len - 10, sfont); - /* - * Fix GIDs of composite glyphs. - */ - if (number_of_contours < 0) { - USHORT flags, cgid, new_gid; /* flag, gid of a component */ - do { - if (p >= endptr) - TT_ERROR("Invalid TrueType glyph data (gid %u): %u bytes", gid, (unsigned int)len); - /* - * Flags and gid of component glyph are both USHORT. - */ - flags = ((*p) << 8)| *(p+1); - p += 2; - cgid = ((*p) << 8)| *(p+1); - if (cgid >= maxp->numGlyphs) { - TT_ERROR("Invalid gid (%u > %u) in composite glyph %u.", cgid, maxp->numGlyphs, gid); - } - new_gid = tt_find_glyph(g, cgid); - if (new_gid == 0) { - new_gid = tt_add_glyph(g, cgid, find_empty_slot(g)); - } - p += sfnt_put_ushort(p, new_gid); - /* - * Just skip remaining part. - */ - p += (flags & ARG_1_AND_2_ARE_WORDS) ? 4 : 2; - if (flags & WE_HAVE_A_SCALE) /* F2Dot14 */ - p += 2; - else if (flags & WE_HAVE_AN_X_AND_Y_SCALE) /* F2Dot14 x 2 */ - p += 4; - else if (flags & WE_HAVE_A_TWO_BY_TWO) /* F2Dot14 x 4 */ - p += 8; - } while (flags & MORE_COMPONENT); - /* - * TrueType instructions comes here: - * length_of_instruction (ushort) - * instruction (byte * length_of_instruction) - */ - } - } - RELEASE(location); - RELEASE(hmtx); - if (vmtx) - RELEASE(vmtx); - - { - int max_count = -1; - - g->dw = g->gd[0].advw; - for (i = 0; i < g->emsize + 1; i++) { - if (w_stat[i] > max_count) { - max_count = w_stat[i]; - g->dw = i; - } + os2 = tt_read_os2__table(sfont); + if (os2) { + g->default_advh = os2->sTypoAscender - os2->sTypoDescender; + g->default_tsb = g->default_advh - os2->sTypoAscender; + + /* dvipdfmx does this elsewhere! */ + fd_cur->font_dim[STEMV_CODE].val = + (os2->usWeightClass / 65) * (os2->usWeightClass / 65) + 50; } - } - RELEASE(w_stat); - - qsort(g->gd, g->num_glyphs, sizeof(struct tt_glyph_desc), glyf_cmp); - { - USHORT prev, last_advw; - char *p, *q; - int padlen, num_hm_known; - - glyf_table_size = 0UL; - num_hm_known = 0; - last_advw = g->gd[g->num_glyphs - 1].advw; - for (i = g->num_glyphs - 1; i >= 0; i--) { - padlen = (g->gd[i].length % 4) ? (4 - (g->gd[i].length % 4)) : 0; - glyf_table_size += g->gd[i].length + padlen; - if (!num_hm_known && last_advw != g->gd[i].advw) { - hhea->numberOfHMetrics = g->gd[i].gid + 2; - num_hm_known = 1; - } + + if (sfnt_find_table_pos(sfont, "vmtx") > 0) { + struct tt_vhea_table *vhea; + vhea = tt_read_vhea_table(sfont); + sfnt_locate_table(sfont, "vmtx"); + vmtx = + tt_read_longMetrics(sfont, maxp->numGlyphs, + vhea->numOfLongVerMetrics); + RELEASE(vhea); + } else { + vmtx = NULL; } - /* All advance widths are same. */ - if (!num_hm_known) { - hhea->numberOfHMetrics = 1; + + sfnt_locate_table(sfont, "loca"); + location = NEW(maxp->numGlyphs + 1, ULONG); + if (head->indexToLocFormat == 0) { + for (i = 0; i <= maxp->numGlyphs; i++) + location[i] = 2 * ((ULONG) sfnt_get_ushort(sfont)); + } else if (head->indexToLocFormat == 1) { + for (i = 0; i <= maxp->numGlyphs; i++) + location[i] = sfnt_get_ulong(sfont); + } else { + TT_ERROR("Unknown IndexToLocFormat."); } - hmtx_table_size = hhea->numberOfHMetrics * 2 + (g->last_gid + 1) * 2; + w_stat = NEW(g->emsize + 2, USHORT); + memset(w_stat, 0, sizeof(USHORT) * (g->emsize + 2)); /* - * Choosing short format does not always give good result - * when compressed. Sometimes increases size. + * Read glyf table. */ - if (glyf_table_size < 0x20000UL) { - head->indexToLocFormat = 0; - loca_table_size = (g->last_gid + 2)*2; - } else { - head->indexToLocFormat = 1; - loca_table_size = (g->last_gid + 2)*4; + offset = sfnt_locate_table(sfont, "glyf"); + /* + * The num_glyphs may grow when composite glyph is found. + * A component of glyph refered by a composite glyph is appended + * to used_glyphs if it is not already registered in used_glyphs. + * Glyph programs of composite glyphs are modified so that it + * correctly refer to new gid of their components. + */ + for (i = 0; i < NUM_GLYPH_LIMIT; i++) { + USHORT gid; /* old gid */ + ULONG loc, len; + BYTE *p, *endptr; + SHORT number_of_contours; + + if (i >= g->num_glyphs) /* finished */ + break; + + gid = g->gd[i].ogid; + if (gid >= maxp->numGlyphs) + TT_ERROR("Invalid glyph index (gid %u)", gid); + + loc = location[gid]; + len = location[gid + 1] - loc; + g->gd[i].advw = hmtx[gid].advance; + g->gd[i].lsb = hmtx[gid].sideBearing; + if (vmtx) { + g->gd[i].advh = vmtx[gid].advance; + g->gd[i].tsb = vmtx[gid].sideBearing; + } else { + g->gd[i].advh = g->default_advh; + g->gd[i].tsb = g->default_tsb; + } + g->gd[i].length = len; + g->gd[i].data = NULL; + if (g->gd[i].advw <= g->emsize) { + w_stat[g->gd[i].advw] += 1; + } else { + w_stat[g->emsize + 1] += 1; /* larger than em */ + } + + if (len == 0) { /* Does not contains any data. */ + continue; + } else if (len < 10) { + TT_ERROR("Invalid TrueType glyph data (gid %u).", gid); + } + + g->gd[i].data = p = NEW(len, BYTE); + endptr = p + len; + + sfnt_seek_set(sfont, offset + loc); + number_of_contours = sfnt_get_short(sfont); + p += sfnt_put_short(p, number_of_contours); + + /* BoundingBox: FWord x 4 */ + g->gd[i].llx = sfnt_get_short(sfont); + g->gd[i].lly = sfnt_get_short(sfont); + g->gd[i].urx = sfnt_get_short(sfont); + g->gd[i].ury = sfnt_get_short(sfont); + /* _FIXME_ */ +#if 1 + if (!vmtx) /* vertOriginY == sTypeAscender */ + g->gd[i].tsb = g->default_advh - g->default_tsb - g->gd[i].ury; +#endif + p += sfnt_put_short(p, g->gd[i].llx); + p += sfnt_put_short(p, g->gd[i].lly); + p += sfnt_put_short(p, g->gd[i].urx); + p += sfnt_put_short(p, g->gd[i].ury); + + /* Read evrything else. */ + sfnt_read(p, len - 10, sfont); + /* + * Fix GIDs of composite glyphs. + */ + if (number_of_contours < 0) { + USHORT flags, cgid, new_gid; /* flag, gid of a component */ + do { + if (p >= endptr) + TT_ERROR("Invalid TrueType glyph data (gid %u): %u bytes", + gid, (unsigned int) len); + /* + * Flags and gid of component glyph are both USHORT. + */ + flags = ((*p) << 8) | *(p + 1); + p += 2; + cgid = ((*p) << 8) | *(p + 1); + if (cgid >= maxp->numGlyphs) { + TT_ERROR("Invalid gid (%u > %u) in composite glyph %u.", + cgid, maxp->numGlyphs, gid); + } + new_gid = tt_find_glyph(g, cgid); + if (new_gid == 0) { + new_gid = tt_add_glyph(g, cgid, find_empty_slot(g)); + } + p += sfnt_put_ushort(p, new_gid); + /* + * Just skip remaining part. + */ + p += (flags & ARG_1_AND_2_ARE_WORDS) ? 4 : 2; + if (flags & WE_HAVE_A_SCALE) /* F2Dot14 */ + p += 2; + else if (flags & WE_HAVE_AN_X_AND_Y_SCALE) /* F2Dot14 x 2 */ + p += 4; + else if (flags & WE_HAVE_A_TWO_BY_TWO) /* F2Dot14 x 4 */ + p += 8; + } while (flags & MORE_COMPONENTS); + /* + * TrueType instructions comes here: + * length_of_instruction (ushort) + * instruction (byte * length_of_instruction) + */ + } } - - hmtx_table_data = p = NEW(hmtx_table_size, char); - loca_table_data = q = NEW(loca_table_size, char); - glyf_table_data = NEW(glyf_table_size, char); - - offset = 0UL; prev = 0; - for (i = 0; i < g->num_glyphs; i++) { - long gap, j; - gap = (long) g->gd[i].gid - prev - 1; - for (j = 1; j <= gap; j++) { - if (prev + j == hhea->numberOfHMetrics - 1) { - p += sfnt_put_ushort(p, last_advw); - } else if (prev + j < hhea->numberOfHMetrics) { - p += sfnt_put_ushort(p, 0); - } - p += sfnt_put_short (p, 0); - if (head->indexToLocFormat == 0) { - q += sfnt_put_ushort(q, (USHORT) (offset/2)); - } else { - q += sfnt_put_ulong(q, offset); - } - } - padlen = (g->gd[i].length % 4) ? (4 - (g->gd[i].length % 4)) : 0; - if (g->gd[i].gid < hhea->numberOfHMetrics) { - p += sfnt_put_ushort(p, g->gd[i].advw); - } - p += sfnt_put_short (p, g->gd[i].lsb); - if (head->indexToLocFormat == 0) { - q += sfnt_put_ushort(q, (USHORT) (offset/2)); - } else { - q += sfnt_put_ulong(q, offset); - } - memset(glyf_table_data + offset, 0, g->gd[i].length + padlen); - memcpy(glyf_table_data + offset, g->gd[i].data, g->gd[i].length); - offset += g->gd[i].length + padlen; - prev = g->gd[i].gid; - /* free data here since it consume much memory */ - RELEASE(g->gd[i].data); - g->gd[i].length = 0; g->gd[i].data = NULL; + RELEASE(location); + RELEASE(hmtx); + if (vmtx) + RELEASE(vmtx); + + { + int max_count = -1; + + g->dw = g->gd[0].advw; + for (i = 0; i < g->emsize + 1; i++) { + if (w_stat[i] > max_count) { + max_count = w_stat[i]; + g->dw = i; + } + } } - if (head->indexToLocFormat == 0) { - q += sfnt_put_ushort(q, (USHORT) (offset/2)); - } else { - q += sfnt_put_ulong(q, offset); + RELEASE(w_stat); + + qsort(g->gd, g->num_glyphs, sizeof(struct tt_glyph_desc), glyf_cmp); + { + USHORT prev, last_advw; + char *p, *q; + int padlen, num_hm_known; + + glyf_table_size = 0UL; + num_hm_known = 0; + last_advw = g->gd[g->num_glyphs - 1].advw; + for (i = g->num_glyphs - 1; i >= 0; i--) { + padlen = (g->gd[i].length % 4) ? (4 - (g->gd[i].length % 4)) : 0; + glyf_table_size += g->gd[i].length + padlen; + if (!num_hm_known && last_advw != g->gd[i].advw) { + hhea->numberOfHMetrics = g->gd[i].gid + 2; + num_hm_known = 1; + } + } + /* All advance widths are same. */ + if (!num_hm_known) { + hhea->numberOfHMetrics = 1; + } + hmtx_table_size = hhea->numberOfHMetrics * 2 + (g->last_gid + 1) * 2; + + /* + * Choosing short format does not always give good result + * when compressed. Sometimes increases size. + */ + if (glyf_table_size < 0x20000UL) { + head->indexToLocFormat = 0; + loca_table_size = (g->last_gid + 2) * 2; + } else { + head->indexToLocFormat = 1; + loca_table_size = (g->last_gid + 2) * 4; + } + + hmtx_table_data = p = NEW(hmtx_table_size, char); + loca_table_data = q = NEW(loca_table_size, char); + glyf_table_data = NEW(glyf_table_size, char); + + offset = 0UL; + prev = 0; + for (i = 0; i < g->num_glyphs; i++) { + long gap, j; + gap = (long) g->gd[i].gid - prev - 1; + for (j = 1; j <= gap; j++) { + if (prev + j == hhea->numberOfHMetrics - 1) { + p += sfnt_put_ushort(p, last_advw); + } else if (prev + j < hhea->numberOfHMetrics) { + p += sfnt_put_ushort(p, 0); + } + p += sfnt_put_short(p, 0); + if (head->indexToLocFormat == 0) { + q += sfnt_put_ushort(q, (USHORT) (offset / 2)); + } else { + q += sfnt_put_ulong(q, offset); + } + } + padlen = (g->gd[i].length % 4) ? (4 - (g->gd[i].length % 4)) : 0; + if (g->gd[i].gid < hhea->numberOfHMetrics) { + p += sfnt_put_ushort(p, g->gd[i].advw); + } + p += sfnt_put_short(p, g->gd[i].lsb); + if (head->indexToLocFormat == 0) { + q += sfnt_put_ushort(q, (USHORT) (offset / 2)); + } else { + q += sfnt_put_ulong(q, offset); + } + memset(glyf_table_data + offset, 0, g->gd[i].length + padlen); + memcpy(glyf_table_data + offset, g->gd[i].data, g->gd[i].length); + offset += g->gd[i].length + padlen; + prev = g->gd[i].gid; + /* free data here since it consume much memory */ + RELEASE(g->gd[i].data); + g->gd[i].length = 0; + g->gd[i].data = NULL; + } + if (head->indexToLocFormat == 0) { + q += sfnt_put_ushort(q, (USHORT) (offset / 2)); + } else { + q += sfnt_put_ulong(q, offset); + } + + sfnt_set_table(sfont, "hmtx", (char *) hmtx_table_data, + hmtx_table_size); + sfnt_set_table(sfont, "loca", (char *) loca_table_data, + loca_table_size); + sfnt_set_table(sfont, "glyf", (char *) glyf_table_data, + glyf_table_size); } - sfnt_set_table(sfont, "hmtx", (char *) hmtx_table_data, hmtx_table_size); - sfnt_set_table(sfont, "loca", (char *) loca_table_data, loca_table_size); - sfnt_set_table(sfont, "glyf", (char *) glyf_table_data, glyf_table_size); - } - - head->checkSumAdjustment = 0; - maxp->numGlyphs = g->last_gid + 1; - - /* TODO */ - sfnt_set_table(sfont, "maxp", tt_pack_maxp_table(maxp), TT_MAXP_TABLE_SIZE); - sfnt_set_table(sfont, "hhea", tt_pack_hhea_table(hhea), TT_HHEA_TABLE_SIZE); - sfnt_set_table(sfont, "head", tt_pack_head_table(head), TT_HEAD_TABLE_SIZE); - RELEASE(maxp); - RELEASE(hhea); - RELEASE(head); - if (os2) - RELEASE(os2); + head->checkSumAdjustment = 0; + maxp->numGlyphs = g->last_gid + 1; + + /* TODO */ + sfnt_set_table(sfont, "maxp", tt_pack_maxp_table(maxp), TT_MAXP_TABLE_SIZE); + sfnt_set_table(sfont, "hhea", tt_pack_hhea_table(hhea), TT_HHEA_TABLE_SIZE); + sfnt_set_table(sfont, "head", tt_pack_head_table(head), TT_HEAD_TABLE_SIZE); + RELEASE(maxp); + RELEASE(hhea); + RELEASE(head); + if (os2) + RELEASE(os2); - return 0; + return 0; } -int -tt_get_metrics (sfnt *sfont, struct tt_glyphs *g) +int tt_get_metrics(sfnt * sfont, struct tt_glyphs *g) { - struct tt_head_table *head = NULL; - struct tt_hhea_table *hhea = NULL; - struct tt_maxp_table *maxp = NULL; - struct tt_longMetrics *hmtx, *vmtx = NULL; - struct tt_os2__table *os2; - /* temp */ - ULONG *location, offset; - long i; - USHORT *w_stat; - - ASSERT(g); - - if (sfont == NULL || + struct tt_head_table *head = NULL; + struct tt_hhea_table *hhea = NULL; + struct tt_maxp_table *maxp = NULL; + struct tt_longMetrics *hmtx, *vmtx = NULL; + struct tt_os2__table *os2; + /* temp */ + ULONG *location, offset; + long i; + USHORT *w_stat; + + ASSERT(g); + + if (sfont == NULL || #ifdef XETEX - sfont->ft_face == NULL + sfont->ft_face == NULL #elif defined(pdfTeX) - sfont->buffer == NULL + sfont->buffer == NULL #else - sfont->stream == NULL + sfont->stream == NULL #endif - ) - TT_ERROR("File not opened."); - - if (sfont->type != SFNT_TYPE_TRUETYPE && - sfont->type != SFNT_TYPE_TTC) - TT_ERROR("Invalid font type"); - - /* - * Read head, hhea, maxp, loca: - * - * unitsPerEm --> head - * numHMetrics --> hhea - * indexToLocFormat --> head - * numGlyphs --> maxp - */ - head = tt_read_head_table(sfont); - hhea = tt_read_hhea_table(sfont); - maxp = tt_read_maxp_table(sfont); - - if (hhea->metricDataFormat != 0) - TT_ERROR("Unknown metricDataFormat."); - - g->emsize = head->unitsPerEm; - - sfnt_locate_table(sfont, "hmtx"); - hmtx = tt_read_longMetrics(sfont, maxp->numGlyphs, hhea->numberOfHMetrics); - - os2 = tt_read_os2__table(sfont); - g->default_advh = os2->sTypoAscender - os2->sTypoDescender; - g->default_tsb = g->default_advh - os2->sTypoAscender; - - if (sfnt_find_table_pos(sfont, "vmtx") > 0) { - struct tt_vhea_table *vhea; - vhea = tt_read_vhea_table(sfont); - sfnt_locate_table(sfont, "vmtx"); - vmtx = tt_read_longMetrics(sfont, maxp->numGlyphs, vhea->numOfLongVerMetrics); - RELEASE(vhea); - } else { - vmtx = NULL; - } - - sfnt_locate_table(sfont, "loca"); - location = NEW(maxp->numGlyphs + 1, ULONG); - if (head->indexToLocFormat == 0) { - for (i = 0; i <= maxp->numGlyphs; i++) - location[i] = 2*((ULONG) sfnt_get_ushort(sfont)); - } else if (head->indexToLocFormat == 1) { - for (i = 0; i <= maxp->numGlyphs; i++) - location[i] = sfnt_get_ulong(sfont); - } else { - TT_ERROR("Unknown IndexToLocFormat."); - } - - w_stat = NEW(g->emsize+2, USHORT); - memset(w_stat, 0, sizeof(USHORT)*(g->emsize+2)); - /* - * Read glyf table. - */ - offset = sfnt_locate_table(sfont, "glyf"); - for (i = 0; i < g->num_glyphs; i++) { - USHORT gid; /* old gid */ - ULONG loc, len; - SHORT number_of_contours; - - gid = g->gd[i].ogid; - if (gid >= maxp->numGlyphs) - TT_ERROR("Invalid glyph index (gid %u)", gid); - - loc = location[gid]; - len = location[gid+1] - loc; - g->gd[i].advw = hmtx[gid].advance; - g->gd[i].lsb = hmtx[gid].sideBearing; - if (vmtx) { - g->gd[i].advh = vmtx[gid].advance; - g->gd[i].tsb = vmtx[gid].sideBearing; + ) + TT_ERROR("File not opened."); + + if (sfont->type != SFNT_TYPE_TRUETYPE && sfont->type != SFNT_TYPE_TTC) + TT_ERROR("Invalid font type"); + + /* + * Read head, hhea, maxp, loca: + * + * unitsPerEm --> head + * numHMetrics --> hhea + * indexToLocFormat --> head + * numGlyphs --> maxp + */ + head = tt_read_head_table(sfont); + hhea = tt_read_hhea_table(sfont); + maxp = tt_read_maxp_table(sfont); + + if (hhea->metricDataFormat != 0) + TT_ERROR("Unknown metricDataFormat."); + + g->emsize = head->unitsPerEm; + + sfnt_locate_table(sfont, "hmtx"); + hmtx = tt_read_longMetrics(sfont, maxp->numGlyphs, hhea->numberOfHMetrics); + + os2 = tt_read_os2__table(sfont); + g->default_advh = os2->sTypoAscender - os2->sTypoDescender; + g->default_tsb = g->default_advh - os2->sTypoAscender; + + if (sfnt_find_table_pos(sfont, "vmtx") > 0) { + struct tt_vhea_table *vhea; + vhea = tt_read_vhea_table(sfont); + sfnt_locate_table(sfont, "vmtx"); + vmtx = + tt_read_longMetrics(sfont, maxp->numGlyphs, + vhea->numOfLongVerMetrics); + RELEASE(vhea); } else { - g->gd[i].advh = g->default_advh; - g->gd[i].tsb = g->default_tsb; + vmtx = NULL; } - g->gd[i].length = len; - g->gd[i].data = NULL; - if (g->gd[i].advw <= g->emsize) { - w_stat[g->gd[i].advw] += 1; + sfnt_locate_table(sfont, "loca"); + location = NEW(maxp->numGlyphs + 1, ULONG); + if (head->indexToLocFormat == 0) { + for (i = 0; i <= maxp->numGlyphs; i++) + location[i] = 2 * ((ULONG) sfnt_get_ushort(sfont)); + } else if (head->indexToLocFormat == 1) { + for (i = 0; i <= maxp->numGlyphs; i++) + location[i] = sfnt_get_ulong(sfont); } else { - w_stat[g->emsize+1] += 1; /* larger than em */ + TT_ERROR("Unknown IndexToLocFormat."); } - if (len == 0) { /* Does not contains any data. */ - continue; - } else if (len < 10) { - TT_ERROR("Invalid TrueType glyph data (gid %u).", gid); + w_stat = NEW(g->emsize + 2, USHORT); + memset(w_stat, 0, sizeof(USHORT) * (g->emsize + 2)); + /* + * Read glyf table. + */ + offset = sfnt_locate_table(sfont, "glyf"); + for (i = 0; i < g->num_glyphs; i++) { + USHORT gid; /* old gid */ + ULONG loc, len; + SHORT number_of_contours; + + gid = g->gd[i].ogid; + if (gid >= maxp->numGlyphs) + TT_ERROR("Invalid glyph index (gid %u)", gid); + + loc = location[gid]; + len = location[gid + 1] - loc; + g->gd[i].advw = hmtx[gid].advance; + g->gd[i].lsb = hmtx[gid].sideBearing; + if (vmtx) { + g->gd[i].advh = vmtx[gid].advance; + g->gd[i].tsb = vmtx[gid].sideBearing; + } else { + g->gd[i].advh = g->default_advh; + g->gd[i].tsb = g->default_tsb; + } + g->gd[i].length = len; + g->gd[i].data = NULL; + + if (g->gd[i].advw <= g->emsize) { + w_stat[g->gd[i].advw] += 1; + } else { + w_stat[g->emsize + 1] += 1; /* larger than em */ + } + + if (len == 0) { /* Does not contains any data. */ + continue; + } else if (len < 10) { + TT_ERROR("Invalid TrueType glyph data (gid %u).", gid); + } + + sfnt_seek_set(sfont, offset + loc); + number_of_contours = sfnt_get_short(sfont); + + /* BoundingBox: FWord x 4 */ + g->gd[i].llx = sfnt_get_short(sfont); + g->gd[i].lly = sfnt_get_short(sfont); + g->gd[i].urx = sfnt_get_short(sfont); + g->gd[i].ury = sfnt_get_short(sfont); + /* _FIXME_ */ +#if 1 + if (!vmtx) /* vertOriginY == sTypeAscender */ + g->gd[i].tsb = g->default_advh - g->default_tsb - g->gd[i].ury; +#endif } + RELEASE(location); + RELEASE(hmtx); + RELEASE(maxp); + RELEASE(hhea); + RELEASE(head); + RELEASE(os2); - sfnt_seek_set(sfont, offset+loc); - number_of_contours = sfnt_get_short(sfont); + if (vmtx) + RELEASE(vmtx); - /* BoundingBox: FWord x 4 */ - g->gd[i].llx = sfnt_get_short(sfont); - g->gd[i].lly = sfnt_get_short(sfont); - g->gd[i].urx = sfnt_get_short(sfont); - g->gd[i].ury = sfnt_get_short(sfont); - /* _FIXME_ */ -#if 1 - if (!vmtx) /* vertOriginY == sTypeAscender */ - g->gd[i].tsb = g->default_advh - g->default_tsb - g->gd[i].ury; -#endif - } - RELEASE(location); - RELEASE(hmtx); - RELEASE(maxp); - RELEASE(hhea); - RELEASE(head); - RELEASE(os2); - - if (vmtx) - RELEASE(vmtx); - - { - int max_count = -1; - - g->dw = g->gd[0].advw; - for (i = 0; i < g->emsize + 1; i++) { - if (w_stat[i] > max_count) { - max_count = w_stat[i]; - g->dw = i; - } + { + int max_count = -1; + + g->dw = g->gd[0].advw; + for (i = 0; i < g->emsize + 1; i++) { + if (w_stat[i] > max_count) { + max_count = w_stat[i]; + g->dw = i; + } + } } - } - RELEASE(w_stat); + RELEASE(w_stat); - return 0; + return 0; } diff --git a/Build/source/texk/web2c/luatexdir/font/tt_glyf.h b/Build/source/texk/web2c/luatexdir/font/tt_glyf.h index cf33af6733f..0ca8465c33d 100644 --- a/Build/source/texk/web2c/luatexdir/font/tt_glyf.h +++ b/Build/source/texk/web2c/luatexdir/font/tt_glyf.h @@ -1,60 +1,59 @@ -/* $Header: /home/cvsroot/dvipdfmx/src/tt_glyf.h,v 1.1 2004/09/11 14:50:29 hirata Exp $ +/* tt_glyf.h - This is dvipdfmx, an eXtended version of dvipdfm by Mark A. Wicks. + Copyright 2002 by Jin-Hwan Cho and Shunsaku Hirata, + the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> - Copyright (C) 2002 by Jin-Hwan Cho and Shunsaku Hirata, - the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. -*/ + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ + +/* $Id: tt_glyf.h 1223 2008-05-02 13:39:55Z oneiros $ */ #ifndef _TT_GLYF_H_ -#define _TT_GLYF_H_ - -struct tt_glyph_desc -{ - USHORT gid; - USHORT ogid; /* GID in original font */ - USHORT advw, advh; - SHORT lsb, tsb; - SHORT llx, lly, urx, ury; - ULONG length; - BYTE *data; +# define _TT_GLYF_H_ + +struct tt_glyph_desc { + USHORT gid; + USHORT ogid; /* GID in original font */ + USHORT advw, advh; + SHORT lsb, tsb; + SHORT llx, lly, urx, ury; + ULONG length; + BYTE *data; }; -struct tt_glyphs -{ - USHORT num_glyphs; - USHORT max_glyphs; - USHORT last_gid; - USHORT emsize; - USHORT dw; /* optimal value for DW */ - USHORT default_advh; /* default value */ - SHORT default_tsb; /* default value */ - struct tt_glyph_desc *gd; - unsigned char *used_slot; +struct tt_glyphs { + USHORT num_glyphs; + USHORT max_glyphs; + USHORT last_gid; + USHORT emsize; + USHORT dw; /* optimal value for DW */ + USHORT default_advh; /* default value */ + SHORT default_tsb; /* default value */ + struct tt_glyph_desc *gd; + unsigned char *used_slot; }; -extern struct tt_glyphs *tt_build_init (void); -extern void tt_build_finish (struct tt_glyphs *g); +extern struct tt_glyphs *tt_build_init(void); +extern void tt_build_finish(struct tt_glyphs *g); -extern USHORT tt_add_glyph (struct tt_glyphs *g, USHORT gid, USHORT new_gid); -extern USHORT tt_get_index (struct tt_glyphs *g, USHORT gid); -extern USHORT tt_find_glyph (struct tt_glyphs *g, USHORT gid); +extern USHORT tt_add_glyph(struct tt_glyphs *g, USHORT gid, USHORT new_gid); +extern USHORT tt_get_index(struct tt_glyphs *g, USHORT gid); +extern USHORT tt_find_glyph(struct tt_glyphs *g, USHORT gid); -extern int tt_build_tables (sfnt *sfont, struct tt_glyphs *g); -extern int tt_get_metrics (sfnt *sfont, struct tt_glyphs *g); +extern int tt_build_tables(sfnt * sfont, struct tt_glyphs *g); +extern int tt_get_metrics(sfnt * sfont, struct tt_glyphs *g); -#endif /* _TT_GLYF_H_ */ +#endif /* _TT_GLYF_H_ */ diff --git a/Build/source/texk/web2c/luatexdir/font/tt_table.c b/Build/source/texk/web2c/luatexdir/font/tt_table.c index 4f82552d9df..3df19723c2b 100644 --- a/Build/source/texk/web2c/luatexdir/font/tt_table.c +++ b/Build/source/texk/web2c/luatexdir/font/tt_table.c @@ -1,39 +1,41 @@ -/* $Header: /home/cvsroot/dvipdfmx/src/tt_table.c,v 1.7 2004/09/11 14:50:29 hirata Exp $ +/* tt_table.c - This is dvipdfmx, an eXtended version of dvipdfm by Mark A. Wicks. + Copyright 2002 by Jin-Hwan Cho and Shunsaku Hirata, + the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> - Copyright (C) 2002 by Jin-Hwan Cho and Shunsaku Hirata, - the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. -*/ + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include <stdio.h> #ifndef pdfTeX -#include "system.h" -#include "error.h" -#include "mem.h" -#include "mfileio.h" +# include "system.h" +# include "error.h" +# include "mem.h" +# include "mfileio.h" #else -extern void pdftex_fail (const char *fmt, ...); /* utils.c */ +# include "ptexlib.h" #endif #include "sfnt.h" #include "tt_table.h" +static const char _svn_version[] = + "$Id: tt_table.c 1588 2008-11-28 13:18:54Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/tt_table.c $"; + /* tables contains information refered by other tables maxp->numGlyphs, etc --> loca, etc @@ -42,269 +44,264 @@ extern void pdftex_fail (const char *fmt, ...); /* utils.c */ head->glyphDataFormat --> glyf */ -char *tt_pack_head_table (struct tt_head_table *table) +char *tt_pack_head_table(struct tt_head_table *table) { - int i; - char *p, *data; - - if (table == NULL) - TT_ERROR("passed NULL pointer\n"); - - p = data = NEW(TT_HEAD_TABLE_SIZE, char); - p += sfnt_put_ulong(p, table->version); - p += sfnt_put_ulong(p, table->fontRevision); - p += sfnt_put_ulong(p, table->checkSumAdjustment); - p += sfnt_put_ulong(p, table->magicNumber); - p += sfnt_put_ushort(p, table->flags); - p += sfnt_put_ushort(p, table->unitsPerEm); - for (i=0; i<8; i++) { - *(p++) = (table->created)[i]; - } - for (i=0; i<8; i++) { - *(p++) = (table->modified)[i]; - } - p += sfnt_put_short(p, table->xMin); - p += sfnt_put_short(p, table->yMin); - p += sfnt_put_short(p, table->xMax); - p += sfnt_put_short(p, table->yMax); - p += sfnt_put_ushort(p, table->macStyle); - p += sfnt_put_ushort(p, table->lowestRecPPEM); - p += sfnt_put_short(p, table->fontDirectionHint); - p += sfnt_put_short(p, table->indexToLocFormat); - p += sfnt_put_short(p, table->glyphDataFormat); - - return data; + int i; + char *p, *data; + + if (table == NULL) + TT_ERROR("passed NULL pointer\n"); + + p = data = NEW(TT_HEAD_TABLE_SIZE, char); + p += sfnt_put_ulong(p, table->version); + p += sfnt_put_ulong(p, table->fontRevision); + p += sfnt_put_ulong(p, table->checkSumAdjustment); + p += sfnt_put_ulong(p, table->magicNumber); + p += sfnt_put_ushort(p, table->flags); + p += sfnt_put_ushort(p, table->unitsPerEm); + for (i = 0; i < 8; i++) { + *(p++) = (table->created)[i]; + } + for (i = 0; i < 8; i++) { + *(p++) = (table->modified)[i]; + } + p += sfnt_put_short(p, table->xMin); + p += sfnt_put_short(p, table->yMin); + p += sfnt_put_short(p, table->xMax); + p += sfnt_put_short(p, table->yMax); + p += sfnt_put_ushort(p, table->macStyle); + p += sfnt_put_ushort(p, table->lowestRecPPEM); + p += sfnt_put_short(p, table->fontDirectionHint); + p += sfnt_put_short(p, table->indexToLocFormat); + p += sfnt_put_short(p, table->glyphDataFormat); + + return data; } -struct tt_head_table *tt_read_head_table (sfnt *sfont) +struct tt_head_table *tt_read_head_table(sfnt * sfont) { - int i; - struct tt_head_table *table = NULL; - - table = NEW(1, struct tt_head_table); - - sfnt_locate_table(sfont, "head"); - - table->version = sfnt_get_ulong(sfont); - table->fontRevision = sfnt_get_ulong(sfont); - table->checkSumAdjustment = sfnt_get_ulong(sfont); - table->magicNumber = sfnt_get_ulong(sfont); - table->flags = sfnt_get_ushort(sfont); - table->unitsPerEm = sfnt_get_ushort(sfont); - for (i=0; i<8; i++) { - (table->created)[i] = sfnt_get_byte (sfont); - } - for (i=0; i<8; i++) { - (table->modified)[i] = sfnt_get_byte (sfont); - } - table->xMin = sfnt_get_short(sfont); - table->yMin = sfnt_get_short(sfont); - table->xMax = sfnt_get_short(sfont); - table->yMax = sfnt_get_short(sfont); - table->macStyle = sfnt_get_short(sfont); - table->lowestRecPPEM = sfnt_get_short(sfont); - table->fontDirectionHint = sfnt_get_short(sfont); - table->indexToLocFormat = sfnt_get_short(sfont); - table->glyphDataFormat = sfnt_get_short(sfont); - - return table; + int i; + struct tt_head_table *table = NULL; + + table = NEW(1, struct tt_head_table); + + sfnt_locate_table(sfont, "head"); + + table->version = sfnt_get_ulong(sfont); + table->fontRevision = sfnt_get_ulong(sfont); + table->checkSumAdjustment = sfnt_get_ulong(sfont); + table->magicNumber = sfnt_get_ulong(sfont); + table->flags = sfnt_get_ushort(sfont); + table->unitsPerEm = sfnt_get_ushort(sfont); + for (i = 0; i < 8; i++) { + (table->created)[i] = sfnt_get_byte(sfont); + } + for (i = 0; i < 8; i++) { + (table->modified)[i] = sfnt_get_byte(sfont); + } + table->xMin = sfnt_get_short(sfont); + table->yMin = sfnt_get_short(sfont); + table->xMax = sfnt_get_short(sfont); + table->yMax = sfnt_get_short(sfont); + table->macStyle = sfnt_get_short(sfont); + table->lowestRecPPEM = sfnt_get_short(sfont); + table->fontDirectionHint = sfnt_get_short(sfont); + table->indexToLocFormat = sfnt_get_short(sfont); + table->glyphDataFormat = sfnt_get_short(sfont); + + return table; } -char *tt_pack_maxp_table (struct tt_maxp_table *table) +char *tt_pack_maxp_table(struct tt_maxp_table *table) { - char *p, *data; - - p = data = NEW(TT_MAXP_TABLE_SIZE, char); - p += sfnt_put_ulong(p, table->version); - p += sfnt_put_ushort(p, table->numGlyphs); - p += sfnt_put_ushort(p, table->maxPoints); - p += sfnt_put_ushort(p, table->maxContours); - p += sfnt_put_ushort(p, table->maxComponentPoints); - p += sfnt_put_ushort(p, table->maxComponentContours); - p += sfnt_put_ushort(p, table->maxZones); - p += sfnt_put_ushort(p, table->maxTwilightPoints); - p += sfnt_put_ushort(p, table->maxStorage); - p += sfnt_put_ushort(p, table->maxFunctionDefs); - p += sfnt_put_ushort(p, table->maxInstructionDefs); - p += sfnt_put_ushort(p, table->maxStackElements); - p += sfnt_put_ushort(p, table->maxSizeOfInstructions); - p += sfnt_put_ushort(p, table->maxComponentElements); - p += sfnt_put_ushort(p, table->maxComponentDepth); - - return data; + char *p, *data; + + p = data = NEW(TT_MAXP_TABLE_SIZE, char); + p += sfnt_put_ulong(p, table->version); + p += sfnt_put_ushort(p, table->numGlyphs); + p += sfnt_put_ushort(p, table->maxPoints); + p += sfnt_put_ushort(p, table->maxContours); + p += sfnt_put_ushort(p, table->maxComponentPoints); + p += sfnt_put_ushort(p, table->maxComponentContours); + p += sfnt_put_ushort(p, table->maxZones); + p += sfnt_put_ushort(p, table->maxTwilightPoints); + p += sfnt_put_ushort(p, table->maxStorage); + p += sfnt_put_ushort(p, table->maxFunctionDefs); + p += sfnt_put_ushort(p, table->maxInstructionDefs); + p += sfnt_put_ushort(p, table->maxStackElements); + p += sfnt_put_ushort(p, table->maxSizeOfInstructions); + p += sfnt_put_ushort(p, table->maxComponentElements); + p += sfnt_put_ushort(p, table->maxComponentDepth); + + return data; } -struct tt_maxp_table *tt_read_maxp_table (sfnt *sfont) +struct tt_maxp_table *tt_read_maxp_table(sfnt * sfont) { - struct tt_maxp_table *table = NULL; - - table = NEW(1, struct tt_maxp_table); - - sfnt_locate_table(sfont, "maxp"); - table->version = sfnt_get_ulong(sfont); - table->numGlyphs = sfnt_get_ushort(sfont); - table->maxPoints = sfnt_get_ushort(sfont); - table->maxContours = sfnt_get_ushort(sfont); - table->maxComponentPoints = sfnt_get_ushort(sfont); - table->maxComponentContours = sfnt_get_ushort(sfont); - table->maxZones = sfnt_get_ushort(sfont); - table->maxTwilightPoints = sfnt_get_ushort(sfont); - table->maxStorage = sfnt_get_ushort(sfont); - table->maxFunctionDefs = sfnt_get_ushort(sfont); - table->maxInstructionDefs = sfnt_get_ushort(sfont); - table->maxStackElements = sfnt_get_ushort(sfont); - table->maxSizeOfInstructions = sfnt_get_ushort(sfont); - table->maxComponentElements = sfnt_get_ushort(sfont); - table->maxComponentDepth = sfnt_get_ushort(sfont); - - return table; + struct tt_maxp_table *table = NULL; + + table = NEW(1, struct tt_maxp_table); + + sfnt_locate_table(sfont, "maxp"); + table->version = sfnt_get_ulong(sfont); + table->numGlyphs = sfnt_get_ushort(sfont); + table->maxPoints = sfnt_get_ushort(sfont); + table->maxContours = sfnt_get_ushort(sfont); + table->maxComponentPoints = sfnt_get_ushort(sfont); + table->maxComponentContours = sfnt_get_ushort(sfont); + table->maxZones = sfnt_get_ushort(sfont); + table->maxTwilightPoints = sfnt_get_ushort(sfont); + table->maxStorage = sfnt_get_ushort(sfont); + table->maxFunctionDefs = sfnt_get_ushort(sfont); + table->maxInstructionDefs = sfnt_get_ushort(sfont); + table->maxStackElements = sfnt_get_ushort(sfont); + table->maxSizeOfInstructions = sfnt_get_ushort(sfont); + table->maxComponentElements = sfnt_get_ushort(sfont); + table->maxComponentDepth = sfnt_get_ushort(sfont); + + return table; } -char *tt_pack_hhea_table (struct tt_hhea_table *table) +char *tt_pack_hhea_table(struct tt_hhea_table *table) { - int i; - char *p, *data; - - p = data = NEW(TT_HHEA_TABLE_SIZE, char); - p += sfnt_put_ulong(p, table->version); - p += sfnt_put_short(p, table->Ascender); - p += sfnt_put_short(p, table->Descender); - p += sfnt_put_short(p, table->LineGap); - p += sfnt_put_ushort(p, table->advanceWidthMax); - p += sfnt_put_short(p, table->minLeftSideBearing); - p += sfnt_put_short(p, table->minRightSideBearing); - p += sfnt_put_short(p, table->xMaxExtent); - p += sfnt_put_short(p, table->caretSlopeRise); - p += sfnt_put_short(p, table->caretSlopeRun); - for (i = 0; i < 5; i++) { - p += sfnt_put_short(p, table->reserved[i]); - } - p += sfnt_put_short(p, table->metricDataFormat); - p += sfnt_put_ushort(p, table->numberOfHMetrics); - - return data; + int i; + char *p, *data; + + p = data = NEW(TT_HHEA_TABLE_SIZE, char); + p += sfnt_put_ulong(p, table->version); + p += sfnt_put_short(p, table->Ascender); + p += sfnt_put_short(p, table->Descender); + p += sfnt_put_short(p, table->LineGap); + p += sfnt_put_ushort(p, table->advanceWidthMax); + p += sfnt_put_short(p, table->minLeftSideBearing); + p += sfnt_put_short(p, table->minRightSideBearing); + p += sfnt_put_short(p, table->xMaxExtent); + p += sfnt_put_short(p, table->caretSlopeRise); + p += sfnt_put_short(p, table->caretSlopeRun); + for (i = 0; i < 5; i++) { + p += sfnt_put_short(p, table->reserved[i]); + } + p += sfnt_put_short(p, table->metricDataFormat); + p += sfnt_put_ushort(p, table->numberOfHMetrics); + + return data; } -struct tt_hhea_table * -tt_read_hhea_table (sfnt *sfont) +struct tt_hhea_table *tt_read_hhea_table(sfnt * sfont) { - int i; - struct tt_hhea_table *table = NULL; - - table = NEW(1, struct tt_hhea_table); - - sfnt_locate_table(sfont, "hhea"); - table->version = sfnt_get_ulong(sfont); - table->Ascender = sfnt_get_short (sfont); - table->Descender = sfnt_get_short(sfont); - table->LineGap = sfnt_get_short(sfont); - table->advanceWidthMax = sfnt_get_ushort(sfont); - table->minLeftSideBearing = sfnt_get_short(sfont); - table->minRightSideBearing = sfnt_get_short(sfont); - table->xMaxExtent = sfnt_get_short(sfont); - table->caretSlopeRise = sfnt_get_short(sfont); - table->caretSlopeRun = sfnt_get_short(sfont); - for(i = 0; i < 5; i++) { - table->reserved[i] = sfnt_get_short(sfont); - } - table->metricDataFormat = sfnt_get_short(sfont); - if (table->metricDataFormat != 0) - TT_ERROR("unknown metricDaraFormat"); - table->numberOfHMetrics = sfnt_get_ushort(sfont); - - return table; + int i; + struct tt_hhea_table *table = NULL; + + table = NEW(1, struct tt_hhea_table); + + sfnt_locate_table(sfont, "hhea"); + table->version = sfnt_get_ulong(sfont); + table->Ascender = sfnt_get_short(sfont); + table->Descender = sfnt_get_short(sfont); + table->LineGap = sfnt_get_short(sfont); + table->advanceWidthMax = sfnt_get_ushort(sfont); + table->minLeftSideBearing = sfnt_get_short(sfont); + table->minRightSideBearing = sfnt_get_short(sfont); + table->xMaxExtent = sfnt_get_short(sfont); + table->caretSlopeRise = sfnt_get_short(sfont); + table->caretSlopeRun = sfnt_get_short(sfont); + for (i = 0; i < 5; i++) { + table->reserved[i] = sfnt_get_short(sfont); + } + table->metricDataFormat = sfnt_get_short(sfont); + if (table->metricDataFormat != 0) + TT_ERROR("unknown metricDaraFormat"); + table->numberOfHMetrics = sfnt_get_ushort(sfont); + + return table; } /* vhea */ -char * -tt_pack_vhea_table (struct tt_vhea_table *table) +char *tt_pack_vhea_table(struct tt_vhea_table *table) { - int i; - char *p, *data; - - p = data = NEW(TT_VHEA_TABLE_SIZE, char); - p += sfnt_put_ulong(p, table->version); - p += sfnt_put_short(p, table->vertTypoAscender); - p += sfnt_put_short(p, table->vertTypoDescender); - p += sfnt_put_short(p, table->vertTypoLineGap); - p += sfnt_put_short(p, table->advanceHeightMax); /* ushort ? */ - p += sfnt_put_short(p, table->minTopSideBearing); - p += sfnt_put_short(p, table->minBottomSideBearing); - p += sfnt_put_short(p, table->yMaxExtent); - p += sfnt_put_short(p, table->caretSlopeRise); - p += sfnt_put_short(p, table->caretSlopeRun); - p += sfnt_put_short(p, table->caretOffset); - for(i = 0; i < 5; i++) { - p += sfnt_put_short(p, table->reserved[i]); - } - p += sfnt_put_ushort(p, table->numOfLongVerMetrics); - - return data; -} + int i; + char *p, *data; + + p = data = NEW(TT_VHEA_TABLE_SIZE, char); + p += sfnt_put_ulong(p, table->version); + p += sfnt_put_short(p, table->vertTypoAscender); + p += sfnt_put_short(p, table->vertTypoDescender); + p += sfnt_put_short(p, table->vertTypoLineGap); + p += sfnt_put_short(p, table->advanceHeightMax); /* ushort ? */ + p += sfnt_put_short(p, table->minTopSideBearing); + p += sfnt_put_short(p, table->minBottomSideBearing); + p += sfnt_put_short(p, table->yMaxExtent); + p += sfnt_put_short(p, table->caretSlopeRise); + p += sfnt_put_short(p, table->caretSlopeRun); + p += sfnt_put_short(p, table->caretOffset); + for (i = 0; i < 5; i++) { + p += sfnt_put_short(p, table->reserved[i]); + } + p += sfnt_put_ushort(p, table->numOfLongVerMetrics); -struct tt_vhea_table *tt_read_vhea_table (sfnt *sfont) -{ - int i; - struct tt_vhea_table *table = NULL; - - table = NEW(1, struct tt_vhea_table); - - sfnt_locate_table(sfont, "vhea"); - table->version = sfnt_get_ulong(sfont); - table->vertTypoAscender = sfnt_get_short (sfont); - table->vertTypoDescender = sfnt_get_short(sfont); - table->vertTypoLineGap = sfnt_get_short(sfont); - table->advanceHeightMax = sfnt_get_short(sfont); /* ushort ? */ - table->minTopSideBearing = sfnt_get_short(sfont); - table->minBottomSideBearing = sfnt_get_short(sfont); - table->yMaxExtent = sfnt_get_short(sfont); - table->caretSlopeRise = sfnt_get_short(sfont); - table->caretSlopeRun = sfnt_get_short(sfont); - table->caretOffset = sfnt_get_short(sfont); - for(i=0;i<5;i++) { - (table->reserved)[i] = sfnt_get_short(sfont); - } - table->numOfLongVerMetrics = sfnt_get_ushort(sfont); - - return table; + return data; } - -struct tt_VORG_table * -tt_read_VORG_table (sfnt *sfont) +struct tt_vhea_table *tt_read_vhea_table(sfnt * sfont) { - struct tt_VORG_table *vorg; - ULONG offset; - USHORT i; - - offset = sfnt_find_table_pos(sfont, "VORG"); + int i; + struct tt_vhea_table *table = NULL; + + table = NEW(1, struct tt_vhea_table); + + sfnt_locate_table(sfont, "vhea"); + table->version = sfnt_get_ulong(sfont); + table->vertTypoAscender = sfnt_get_short(sfont); + table->vertTypoDescender = sfnt_get_short(sfont); + table->vertTypoLineGap = sfnt_get_short(sfont); + table->advanceHeightMax = sfnt_get_short(sfont); /* ushort ? */ + table->minTopSideBearing = sfnt_get_short(sfont); + table->minBottomSideBearing = sfnt_get_short(sfont); + table->yMaxExtent = sfnt_get_short(sfont); + table->caretSlopeRise = sfnt_get_short(sfont); + table->caretSlopeRun = sfnt_get_short(sfont); + table->caretOffset = sfnt_get_short(sfont); + for (i = 0; i < 5; i++) { + (table->reserved)[i] = sfnt_get_short(sfont); + } + table->numOfLongVerMetrics = sfnt_get_ushort(sfont); - if (offset > 0) { - vorg = NEW(1, struct tt_VORG_table); + return table; +} - sfnt_locate_table(sfont, "VORG"); - if (sfnt_get_ushort(sfont) != 1 || - sfnt_get_ushort(sfont) != 0) - TT_ERROR("Unsupported VORG version."); - vorg->defaultVertOriginY = sfnt_get_short(sfont); - vorg->numVertOriginYMetrics = sfnt_get_ushort(sfont); - vorg->vertOriginYMetrics = NEW(vorg->numVertOriginYMetrics, - struct tt_vertOriginYMetrics); - /* - * The vertOriginYMetrics array must be sorted in increasing - * glyphIndex order. - */ - for (i = 0; - i < vorg->numVertOriginYMetrics; i++) { - vorg->vertOriginYMetrics[i].glyphIndex = sfnt_get_ushort(sfont); - vorg->vertOriginYMetrics[i].vertOriginY = sfnt_get_short(sfont); +struct tt_VORG_table *tt_read_VORG_table(sfnt * sfont) +{ + struct tt_VORG_table *vorg; + ULONG offset; + USHORT i; + + offset = sfnt_find_table_pos(sfont, "VORG"); + + if (offset > 0) { + vorg = NEW(1, struct tt_VORG_table); + + sfnt_locate_table(sfont, "VORG"); + if (sfnt_get_ushort(sfont) != 1 || sfnt_get_ushort(sfont) != 0) + TT_ERROR("Unsupported VORG version."); + + vorg->defaultVertOriginY = sfnt_get_short(sfont); + vorg->numVertOriginYMetrics = sfnt_get_ushort(sfont); + vorg->vertOriginYMetrics = NEW(vorg->numVertOriginYMetrics, + struct tt_vertOriginYMetrics); + /* + * The vertOriginYMetrics array must be sorted in increasing + * glyphIndex order. + */ + for (i = 0; i < vorg->numVertOriginYMetrics; i++) { + vorg->vertOriginYMetrics[i].glyphIndex = sfnt_get_ushort(sfont); + vorg->vertOriginYMetrics[i].vertOriginY = sfnt_get_short(sfont); + } + } else { + vorg = NULL; } - } else { - vorg = NULL; - } - return vorg; + return vorg; } /* @@ -313,171 +310,167 @@ tt_read_VORG_table (sfnt *sfont) * Reading/writing hmtx and vmtx depend on other tables, maxp and hhea/vhea. */ -struct tt_longMetrics * -tt_read_longMetrics (sfnt *sfont, USHORT numGlyphs, USHORT numLongMetrics) +struct tt_longMetrics *tt_read_longMetrics(sfnt * sfont, USHORT numGlyphs, + USHORT numLongMetrics) { - struct tt_longMetrics *m; - USHORT gid, last_adv = 0; - - m = NEW(numGlyphs, struct tt_longMetrics); - for (gid = 0; gid < numGlyphs; gid++) { - if (gid < numLongMetrics) - last_adv = sfnt_get_ushort(sfont); - m[gid].sideBearing = sfnt_get_short(sfont); - m[gid].advance = last_adv; - } - - return m; + struct tt_longMetrics *m; + USHORT gid, last_adv = 0; + + m = NEW(numGlyphs, struct tt_longMetrics); + for (gid = 0; gid < numGlyphs; gid++) { + if (gid < numLongMetrics) + last_adv = sfnt_get_ushort(sfont); + m[gid].sideBearing = sfnt_get_short(sfont); + m[gid].advance = last_adv; + } + + return m; } /* OS/2 table */ /* this table may not exist */ -struct tt_os2__table * -tt_read_os2__table (sfnt *sfont) +struct tt_os2__table *tt_read_os2__table(sfnt * sfont) { - struct tt_os2__table *table = NULL; - int i; + struct tt_os2__table *table = NULL; + int i; + + if (sfnt_find_table_pos(sfont, "OS/2") == 0) + return NULL; + + sfnt_locate_table(sfont, "OS/2"); + + table = NEW(1, struct tt_os2__table); + + table->version = sfnt_get_ushort(sfont); + table->xAvgCharWidth = sfnt_get_short(sfont); + table->usWeightClass = sfnt_get_ushort(sfont); + table->usWidthClass = sfnt_get_ushort(sfont); + table->fsType = sfnt_get_short(sfont); + table->ySubscriptXSize = sfnt_get_short(sfont); + table->ySubscriptYSize = sfnt_get_short(sfont); + table->ySubscriptXOffset = sfnt_get_short(sfont); + table->ySubscriptYOffset = sfnt_get_short(sfont); + table->ySuperscriptXSize = sfnt_get_short(sfont); + table->ySuperscriptYSize = sfnt_get_short(sfont); + table->ySuperscriptXOffset = sfnt_get_short(sfont); + table->ySuperscriptYOffset = sfnt_get_short(sfont); + table->yStrikeoutSize = sfnt_get_short(sfont); + table->yStrikeoutPosition = sfnt_get_short(sfont); + table->sFamilyClass = sfnt_get_short(sfont); + for (i = 0; i < 10; i++) { + table->panose[i] = sfnt_get_byte(sfont); + } + table->ulUnicodeRange1 = sfnt_get_ulong(sfont); + table->ulUnicodeRange2 = sfnt_get_ulong(sfont); + table->ulUnicodeRange3 = sfnt_get_ulong(sfont); + table->ulUnicodeRange4 = sfnt_get_ulong(sfont); + for (i = 0; i < 4; i++) { + table->achVendID[i] = sfnt_get_char(sfont); + } + table->fsSelection = sfnt_get_ushort(sfont); + table->usFirstCharIndex = sfnt_get_ushort(sfont); + table->usLastCharIndex = sfnt_get_ushort(sfont); + table->sTypoAscender = sfnt_get_short(sfont); + table->sTypoDescender = sfnt_get_short(sfont); + table->sTypoLineGap = sfnt_get_short(sfont); + table->usWinAscent = sfnt_get_ushort(sfont); + table->usWinDescent = sfnt_get_ushort(sfont); + table->ulCodePageRange1 = sfnt_get_ulong(sfont); + table->ulCodePageRange2 = sfnt_get_ulong(sfont); + if (table->version == 0x0002) { + table->sxHeight = sfnt_get_short(sfont); + table->sCapHeight = sfnt_get_short(sfont); + table->usDefaultChar = sfnt_get_ushort(sfont); + table->usBreakChar = sfnt_get_ushort(sfont); + table->usMaxContext = sfnt_get_ushort(sfont); + } - if (sfnt_find_table_pos(sfont, "OS/2") == 0) - return NULL; - - sfnt_locate_table(sfont, "OS/2"); - - table = NEW(1, struct tt_os2__table); - - table->version = sfnt_get_ushort(sfont); - table->xAvgCharWidth = sfnt_get_short(sfont); - table->usWeightClass = sfnt_get_ushort(sfont); - table->usWidthClass = sfnt_get_ushort(sfont); - table->fsType = sfnt_get_short(sfont); - table->ySubscriptXSize = sfnt_get_short(sfont); - table->ySubscriptYSize = sfnt_get_short(sfont); - table->ySubscriptXOffset = sfnt_get_short(sfont); - table->ySubscriptYOffset = sfnt_get_short(sfont); - table->ySuperscriptXSize = sfnt_get_short(sfont); - table->ySuperscriptYSize = sfnt_get_short(sfont); - table->ySuperscriptXOffset = sfnt_get_short(sfont); - table->ySuperscriptYOffset = sfnt_get_short(sfont); - table->yStrikeoutSize = sfnt_get_short(sfont); - table->yStrikeoutPosition = sfnt_get_short(sfont); - table->sFamilyClass = sfnt_get_short(sfont); - for (i = 0; i < 10; i++) { - table->panose[i] = sfnt_get_byte(sfont); - } - table->ulUnicodeRange1 = sfnt_get_ulong(sfont); - table->ulUnicodeRange2 = sfnt_get_ulong(sfont); - table->ulUnicodeRange3 = sfnt_get_ulong(sfont); - table->ulUnicodeRange4 = sfnt_get_ulong(sfont); - for (i = 0; i < 4; i++) { - table->achVendID[i] = sfnt_get_char(sfont); - } - table->fsSelection = sfnt_get_ushort(sfont); - table->usFirstCharIndex = sfnt_get_ushort(sfont); - table->usLastCharIndex = sfnt_get_ushort(sfont); - table->sTypoAscender = sfnt_get_short(sfont); - table->sTypoDescender = sfnt_get_short(sfont); - table->sTypoLineGap = sfnt_get_short(sfont); - table->usWinAscent = sfnt_get_ushort(sfont); - table->usWinDescent = sfnt_get_ushort(sfont); - table->ulCodePageRange1 = sfnt_get_ulong(sfont); - table->ulCodePageRange2 = sfnt_get_ulong(sfont); - if (table->version == 0x0002) { - table->sxHeight = sfnt_get_short(sfont); - table->sCapHeight = sfnt_get_short(sfont); - table->usDefaultChar = sfnt_get_ushort(sfont); - table->usBreakChar = sfnt_get_ushort(sfont); - table->usMaxContext = sfnt_get_ushort(sfont); - } - - return table; + return table; } USHORT -tt_get_name (sfnt *sfont, char *dest, USHORT destlen, - USHORT plat_id, USHORT enco_id, - USHORT lang_id, USHORT name_id) +tt_get_name(sfnt * sfont, char *dest, USHORT destlen, + USHORT plat_id, USHORT enco_id, USHORT lang_id, USHORT name_id) { - USHORT length = 0; - USHORT num_names, string_offset; - ULONG name_offset; - int i; - - name_offset = sfnt_locate_table (sfont, "name"); - - if (sfnt_get_ushort(sfont)) - TT_ERROR ("Expecting zero"); - - num_names = sfnt_get_ushort(sfont); - string_offset = sfnt_get_ushort(sfont); - for (i=0;i<num_names;i++) { - USHORT p_id, e_id, n_id, l_id; - USHORT offset; - - p_id = sfnt_get_ushort(sfont); - e_id = sfnt_get_ushort(sfont); - l_id = sfnt_get_ushort(sfont); - n_id = sfnt_get_ushort(sfont); - length = sfnt_get_ushort(sfont); - offset = sfnt_get_ushort(sfont); - /* language ID value 0xffffu for `accept any language ID' */ - if ((p_id == plat_id) && (e_id == enco_id) && - (lang_id == 0xffffu || l_id == lang_id) && (n_id == name_id)) { - if (length > destlen - 1) { - fprintf(stderr, "\n** Notice: Name string too long. Truncating **\n"); - length = destlen - 1; - } - sfnt_seek_set (sfont, name_offset+string_offset+offset); - sfnt_read((unsigned char*)dest, length, sfont); - dest[length] = '\0'; - break; + USHORT length = 0; + USHORT num_names, string_offset; + ULONG name_offset; + int i; + + name_offset = sfnt_locate_table(sfont, "name"); + + if (sfnt_get_ushort(sfont)) + TT_ERROR("Expecting zero"); + + num_names = sfnt_get_ushort(sfont); + string_offset = sfnt_get_ushort(sfont); + for (i = 0; i < num_names; i++) { + USHORT p_id, e_id, n_id, l_id; + USHORT offset; + + p_id = sfnt_get_ushort(sfont); + e_id = sfnt_get_ushort(sfont); + l_id = sfnt_get_ushort(sfont); + n_id = sfnt_get_ushort(sfont); + length = sfnt_get_ushort(sfont); + offset = sfnt_get_ushort(sfont); + /* language ID value 0xffffu for `accept any language ID' */ + if ((p_id == plat_id) && (e_id == enco_id) && + (lang_id == 0xffffu || l_id == lang_id) && (n_id == name_id)) { + if (length > destlen - 1) { + fprintf(stderr, + "\n** Notice: Name string too long. Truncating **\n"); + length = destlen - 1; + } + sfnt_seek_set(sfont, name_offset + string_offset + offset); + sfnt_read((unsigned char *) dest, length, sfont); + dest[length] = '\0'; + break; + } + } + if (i == num_names) { + length = 0; } - } - if (i == num_names) { - length = 0; - } - return length; + return length; } -USHORT -tt_get_ps_fontname (sfnt *sfont, char *dest, USHORT destlen) +USHORT tt_get_ps_fontname(sfnt * sfont, char *dest, USHORT destlen) { - USHORT namelen = 0; + USHORT namelen = 0; #ifdef XETEX - const char* name = FT_Get_Postscript_Name(sfont->ft_face); + const char *name = FT_Get_Postscript_Name(sfont->ft_face); namelen = strlen(name); if (namelen > destlen - 1) { - strncpy(dest, name, destlen - 1); - dest[destlen] = 0; - } - else - strcpy(dest, name); + strncpy(dest, name, destlen - 1); + dest[destlen] = 0; + } else + strcpy(dest, name); #else - /* First try Mac-Roman PS name and then Win-Unicode PS name */ - if ((namelen = tt_get_name(sfont, dest, destlen, 1, 0, 0, 6)) != 0 || - (namelen = tt_get_name(sfont, dest, destlen, 3, 1, 0x409u, 6)) != 0 || - (namelen = tt_get_name(sfont, dest, destlen, 3, 5, 0x412u, 6)) != 0) - return namelen; + /* First try Mac-Roman PS name and then Win-Unicode PS name */ + if ((namelen = tt_get_name(sfont, dest, destlen, 1, 0, 0, 6)) != 0 || + (namelen = tt_get_name(sfont, dest, destlen, 3, 1, 0x409u, 6)) != 0 || + (namelen = tt_get_name(sfont, dest, destlen, 3, 5, 0x412u, 6)) != 0) + return namelen; - fprintf(stderr, "\n** Warning: No valid PostScript name available **\n"); - /* - Wrokaround for some bad TTfonts: - Language ID value 0xffffu for `accept any language ID' - */ - if ((namelen = tt_get_name(sfont, dest, destlen, 1, 0, 0xffffu, 6)) == 0) { + fprintf(stderr, "\n** Warning: No valid PostScript name available **\n"); /* - Finally falling back to Mac Roman name field. - Warning: Some bad Japanese TTfonts using SJIS encoded string in the - Mac Roman name field. - */ - namelen = tt_get_name(sfont, dest, destlen, 1, 0, 0, 1); - } - + Wrokaround for some bad TTfonts: + Language ID value 0xffffu for `accept any language ID' + */ + if ((namelen = tt_get_name(sfont, dest, destlen, 1, 0, 0xffffu, 6)) == 0) { + /* + Finally falling back to Mac Roman name field. + Warning: Some bad Japanese TTfonts using SJIS encoded string in the + Mac Roman name field. + */ + namelen = tt_get_name(sfont, dest, destlen, 1, 0, 0, 1); + } #endif - return namelen; + return namelen; } diff --git a/Build/source/texk/web2c/luatexdir/font/tt_table.h b/Build/source/texk/web2c/luatexdir/font/tt_table.h index ffb2c5b8f45..5dcd17d5b66 100644 --- a/Build/source/texk/web2c/luatexdir/font/tt_table.h +++ b/Build/source/texk/web2c/luatexdir/font/tt_table.h @@ -1,193 +1,189 @@ -/* $Header: /home/cvsroot/dvipdfmx/src/tt_table.h,v 1.6 2004/09/11 14:50:29 hirata Exp $ +/* tt_table.h - This is dvipdfmx, an eXtended version of dvipdfm by Mark A. Wicks. + Copyright 2002 by Jin-Hwan Cho and Shunsaku Hirata, + the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> - Copyright (C) 2002 by Jin-Hwan Cho and Shunsaku Hirata, - the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. -*/ + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ + +/* $Id: tt_table.h 1223 2008-05-02 13:39:55Z oneiros $ */ #ifndef _TT_TABLE_H_ -#define _TT_TABLE_H_ - -#include "sfnt.h" - -#define TT_HEAD_TABLE_SIZE 54UL -#define TT_MAXP_TABLE_SIZE 32UL -#define TT_HHEA_TABLE_SIZE 36UL -#define TT_VHEA_TABLE_SIZE 36UL - -struct tt_head_table -{ - Fixed version; - Fixed fontRevision; - ULONG checkSumAdjustment; - ULONG magicNumber; - USHORT flags; - USHORT unitsPerEm; - BYTE created[8]; - BYTE modified[8]; - FWord xMin, yMin, xMax, yMax; - USHORT macStyle; - USHORT lowestRecPPEM; - SHORT fontDirectionHint; - SHORT indexToLocFormat; - SHORT glyphDataFormat; +# define _TT_TABLE_H_ + +# include "sfnt.h" + +# define TT_HEAD_TABLE_SIZE 54UL +# define TT_MAXP_TABLE_SIZE 32UL +# define TT_HHEA_TABLE_SIZE 36UL +# define TT_VHEA_TABLE_SIZE 36UL + +struct tt_head_table { + Fixed version; + Fixed fontRevision; + ULONG checkSumAdjustment; + ULONG magicNumber; + USHORT flags; + USHORT unitsPerEm; + BYTE created[8]; + BYTE modified[8]; + FWord xMin, yMin, xMax, yMax; + USHORT macStyle; + USHORT lowestRecPPEM; + SHORT fontDirectionHint; + SHORT indexToLocFormat; + SHORT glyphDataFormat; }; -struct tt_hhea_table -{ - Fixed version; - FWord Ascender; - FWord Descender; - FWord LineGap; - uFWord advanceWidthMax; - FWord minLeftSideBearing; - FWord minRightSideBearing; - FWord xMaxExtent; - SHORT caretSlopeRise; - SHORT caretSlopeRun; - SHORT reserved[5]; /* set to 0 */ - SHORT metricDataFormat; - USHORT numberOfHMetrics; +struct tt_hhea_table { + Fixed version; + FWord Ascender; + FWord Descender; + FWord LineGap; + uFWord advanceWidthMax; + FWord minLeftSideBearing; + FWord minRightSideBearing; + FWord xMaxExtent; + SHORT caretSlopeRise; + SHORT caretSlopeRun; + SHORT reserved[5]; /* set to 0 */ + SHORT metricDataFormat; + USHORT numberOfHMetrics; }; -struct tt_vhea_table -{ - Fixed version; - SHORT vertTypoAscender; /* v.1.1 name */ - SHORT vertTypoDescender; /* v.1.1 name */ - SHORT vertTypoLineGap; /* v.1.1 name */ - SHORT advanceHeightMax; - SHORT minTopSideBearing; - SHORT minBottomSideBearing; - SHORT yMaxExtent; - SHORT caretSlopeRise; - SHORT caretSlopeRun; - SHORT caretOffset; - SHORT reserved[5]; /* set to 0 */ - USHORT numOfLongVerMetrics; +struct tt_vhea_table { + Fixed version; + SHORT vertTypoAscender; /* v.1.1 name */ + SHORT vertTypoDescender; /* v.1.1 name */ + SHORT vertTypoLineGap; /* v.1.1 name */ + SHORT advanceHeightMax; + SHORT minTopSideBearing; + SHORT minBottomSideBearing; + SHORT yMaxExtent; + SHORT caretSlopeRise; + SHORT caretSlopeRun; + SHORT caretOffset; + SHORT reserved[5]; /* set to 0 */ + USHORT numOfLongVerMetrics; }; -struct tt_maxp_table -{ - Fixed version; - USHORT numGlyphs; - USHORT maxPoints; - USHORT maxContours; - USHORT maxComponentPoints; - USHORT maxComponentContours; - USHORT maxZones; - USHORT maxTwilightPoints; - USHORT maxStorage; - USHORT maxFunctionDefs; - USHORT maxInstructionDefs; - USHORT maxStackElements; - USHORT maxSizeOfInstructions; - USHORT maxComponentElements; - USHORT maxComponentDepth; +struct tt_maxp_table { + Fixed version; + USHORT numGlyphs; + USHORT maxPoints; + USHORT maxContours; + USHORT maxComponentPoints; + USHORT maxComponentContours; + USHORT maxZones; + USHORT maxTwilightPoints; + USHORT maxStorage; + USHORT maxFunctionDefs; + USHORT maxInstructionDefs; + USHORT maxStackElements; + USHORT maxSizeOfInstructions; + USHORT maxComponentElements; + USHORT maxComponentDepth; }; -struct tt_os2__table -{ - USHORT version; /* 0x0001 or 0x0002 */ - SHORT xAvgCharWidth; - USHORT usWeightClass; - USHORT usWidthClass; - SHORT fsType; /* if (faType & 0x08) editable_embedding */ - SHORT ySubscriptXSize; - SHORT ySubscriptYSize; - SHORT ySubscriptXOffset; - SHORT ySubscriptYOffset; - SHORT ySuperscriptXSize; - SHORT ySuperscriptYSize; - SHORT ySuperscriptXOffset; - SHORT ySuperscriptYOffset; - SHORT yStrikeoutSize; - SHORT yStrikeoutPosition; - SHORT sFamilyClass; - BYTE panose[10]; - ULONG ulUnicodeRange1; - ULONG ulUnicodeRange2; - ULONG ulUnicodeRange3; - ULONG ulUnicodeRange4; - ICHAR achVendID[4]; - USHORT fsSelection; - USHORT usFirstCharIndex; - USHORT usLastCharIndex; - SHORT sTypoAscender; /* TTF spec. from MS is wrong */ - SHORT sTypoDescender; /* TTF spec. from MS is wrong */ - SHORT sTypoLineGap; /* TTF spec. from MS is wrong */ - USHORT usWinAscent; - USHORT usWinDescent; - ULONG ulCodePageRange1; - ULONG ulCodePageRange2; - /* version 0x0002 */ - SHORT sxHeight; - SHORT sCapHeight; - USHORT usDefaultChar; - USHORT usBreakChar; - USHORT usMaxContext; +struct tt_os2__table { + USHORT version; /* 0x0001 or 0x0002 */ + SHORT xAvgCharWidth; + USHORT usWeightClass; + USHORT usWidthClass; + SHORT fsType; /* if (faType & 0x08) editable_embedding */ + SHORT ySubscriptXSize; + SHORT ySubscriptYSize; + SHORT ySubscriptXOffset; + SHORT ySubscriptYOffset; + SHORT ySuperscriptXSize; + SHORT ySuperscriptYSize; + SHORT ySuperscriptXOffset; + SHORT ySuperscriptYOffset; + SHORT yStrikeoutSize; + SHORT yStrikeoutPosition; + SHORT sFamilyClass; + BYTE panose[10]; + ULONG ulUnicodeRange1; + ULONG ulUnicodeRange2; + ULONG ulUnicodeRange3; + ULONG ulUnicodeRange4; + ICHAR achVendID[4]; + USHORT fsSelection; + USHORT usFirstCharIndex; + USHORT usLastCharIndex; + SHORT sTypoAscender; /* TTF spec. from MS is wrong */ + SHORT sTypoDescender; /* TTF spec. from MS is wrong */ + SHORT sTypoLineGap; /* TTF spec. from MS is wrong */ + USHORT usWinAscent; + USHORT usWinDescent; + ULONG ulCodePageRange1; + ULONG ulCodePageRange2; + /* version 0x0002 */ + SHORT sxHeight; + SHORT sCapHeight; + USHORT usDefaultChar; + USHORT usBreakChar; + USHORT usMaxContext; }; struct tt_vertOriginYMetrics { - USHORT glyphIndex; - SHORT vertOriginY; + USHORT glyphIndex; + SHORT vertOriginY; }; struct tt_VORG_table { - SHORT defaultVertOriginY; - USHORT numVertOriginYMetrics; - struct tt_vertOriginYMetrics *vertOriginYMetrics; + SHORT defaultVertOriginY; + USHORT numVertOriginYMetrics; + struct tt_vertOriginYMetrics *vertOriginYMetrics; }; /* hmtx and vmtx */ -struct tt_longMetrics -{ - USHORT advance; - SHORT sideBearing; +struct tt_longMetrics { + USHORT advance; + SHORT sideBearing; }; /* head, hhea, maxp */ -extern char *tt_pack_head_table (struct tt_head_table *table); -extern struct tt_head_table *tt_read_head_table (sfnt *sfont); -extern char *tt_pack_hhea_table (struct tt_hhea_table *table); -extern struct tt_hhea_table *tt_read_hhea_table (sfnt *sfont); -extern char *tt_pack_maxp_table (struct tt_maxp_table *table); -extern struct tt_maxp_table *tt_read_maxp_table (sfnt *sfont); +extern char *tt_pack_head_table(struct tt_head_table *table); +extern struct tt_head_table *tt_read_head_table(sfnt * sfont); +extern char *tt_pack_hhea_table(struct tt_hhea_table *table); +extern struct tt_hhea_table *tt_read_hhea_table(sfnt * sfont); +extern char *tt_pack_maxp_table(struct tt_maxp_table *table); +extern struct tt_maxp_table *tt_read_maxp_table(sfnt * sfont); /* vhea */ -extern char *tt_pack_vhea_table (struct tt_vhea_table *table); -extern struct tt_vhea_table *tt_read_vhea_table (sfnt *sfont); +extern char *tt_pack_vhea_table(struct tt_vhea_table *table); +extern struct tt_vhea_table *tt_read_vhea_table(sfnt * sfont); /* VORG */ -extern struct tt_VORG_table *tt_read_VORG_table (sfnt *sfont); +extern struct tt_VORG_table *tt_read_VORG_table(sfnt * sfont); /* hmtx and vmtx */ -extern struct tt_longMetrics *tt_read_longMetrics (sfnt *sfont, - USHORT numGlyphs, USHORT numLongMetrics); +extern struct tt_longMetrics *tt_read_longMetrics(sfnt * sfont, + USHORT numGlyphs, + USHORT numLongMetrics); /* OS/2 table */ -extern struct tt_os2__table *tt_read_os2__table (sfnt *sfont); +extern struct tt_os2__table *tt_read_os2__table(sfnt * sfont); /* name table */ -extern USHORT tt_get_name (sfnt *sfont, char *dest, USHORT destlen, - USHORT plat_id, USHORT enco_id, - USHORT lang_id, USHORT name_id); -extern USHORT tt_get_ps_fontname (sfnt *sfont, char *dest, USHORT destlen); +extern USHORT tt_get_name(sfnt * sfont, char *dest, USHORT destlen, + USHORT plat_id, USHORT enco_id, + USHORT lang_id, USHORT name_id); +extern USHORT tt_get_ps_fontname(sfnt * sfont, char *dest, USHORT destlen); -#endif /* _TT_TABLE_H_ */ +#endif /* _TT_TABLE_H_ */ diff --git a/Build/source/texk/web2c/luatexdir/font/vfovf.c b/Build/source/texk/web2c/luatexdir/font/vfovf.c index 61a0b76aaa4..fefcd16b756 100644 --- a/Build/source/texk/web2c/luatexdir/font/vfovf.c +++ b/Build/source/texk/web2c/luatexdir/font/vfovf.c @@ -1,113 +1,114 @@ -/* -Copyright (c) 1996-2006 Taco Hoekwater <taco@luatex.org> - -This file is part of LuaTeX. +/* vfovf.c + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -LuaTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + This file is part of LuaTeX. -LuaTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -You should have received a copy of the GNU General Public License -along with LuaTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -$Id: vfovf.c 1169 2008-04-15 14:57:56Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" - #include "luatex-api.h" +#include "luatexfont.h" + +static const char _svn_version[] = + "$Id: vfovf.c 2057 2009-03-19 15:45:47Z taco $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/vfovf.c $"; /* this is a hack! */ #define font_max 5000 -#define set_char_0 0 /* typeset character 0 and move right */ -#define set1 128 /* typeset a character and move right */ -#define set2 129 /* typeset a character and move right */ -#define set3 130 /* typeset a character and move right */ -#define set4 131 /* typeset a character and move right */ -#define set_rule 132 /* typeset a rule and move right */ -#define put1 133 /* typeset a character without moving */ -#define put2 134 /* typeset a character without moving */ -#define put3 135 /* typeset a character without moving */ -#define put4 136 /* typeset a character without moving */ -#define put_rule 137 /* typeset a rule */ -#define nop 138 /* no operation */ -#define bop 139 /* beginning of page */ -#define eop 140 /* ending of page */ -#define push 141 /* save the current positions */ -#define pop 142 /* restore previous positions */ -#define right1 143 /* move right */ -#define right2 144 /* move right */ -#define right3 145 /* move right */ -#define right4 146 /* move right, 4 bytes */ -#define w0 147 /* move right by |w| */ -#define w1 148 /* move right and set |w| */ -#define w2 149 /* move right and set |w| */ -#define w3 150 /* move right and set |w| */ -#define w4 151 /* move right and set |w| */ -#define x0 152 /* move right by |x| */ -#define x1 153 /* move right and set |x| */ -#define x2 154 /* move right and set |x| */ -#define x3 155 /* move right and set |x| */ -#define x4 156 /* move right and set |x| */ -#define down1 157 /* move down */ -#define down2 158 /* move down */ -#define down3 159 /* move down */ -#define down4 160 /* move down, 4 bytes */ -#define y0 161 /* move down by |y| */ -#define y1 162 /* move down and set |y| */ -#define y2 163 /* move down and set |y| */ -#define y3 164 /* move down and set |y| */ -#define y4 165 /* move down and set |y| */ -#define z0 166 /* move down by |z| */ -#define z1 167 /* move down and set |z| */ -#define z2 168 /* move down and set |z| */ -#define z3 169 /* move down and set |z| */ -#define z4 170 /* move down and set |z| */ -#define fnt_num_0 171 /* set current font to 0 */ -#define fnt1 235 /* set current font */ -#define fnt2 236 /* set current font */ -#define fnt3 237 /* set current font */ -#define fnt4 238 /* set current font */ -#define xxx1 239 /* extension to DVI primitives */ -#define xxx2 240 /* extension to DVI primitives */ -#define xxx3 241 /* extension to DVI primitives */ -#define xxx4 242 /* potentially long extension to DVI primitives */ -#define fnt_def1 243 /* define the meaning of a font number */ -#define pre 247 /* preamble */ -#define post 248 /* postamble beginning */ -#define post_post 249 /* postamble ending */ -#define yyy1 250 /* PDF literal text */ -#define yyy2 251 /* PDF literal text */ -#define yyy3 252 /* PDF literal text */ -#define yyy4 253 /* PDF literal text */ +#define set_char_0 0 /* typeset character 0 and move right */ +#define set1 128 /* typeset a character and move right */ +#define set2 129 /* typeset a character and move right */ +#define set3 130 /* typeset a character and move right */ +#define set4 131 /* typeset a character and move right */ +#define set_rule 132 /* typeset a rule and move right */ +#define put1 133 /* typeset a character without moving */ +#define put2 134 /* typeset a character without moving */ +#define put3 135 /* typeset a character without moving */ +#define put4 136 /* typeset a character without moving */ +#define put_rule 137 /* typeset a rule */ +#define nop 138 /* no operation */ +#define bop 139 /* beginning of page */ +#define eop 140 /* ending of page */ +#define push 141 /* save the current positions */ +#define pop 142 /* restore previous positions */ +#define right1 143 /* move right */ +#define right2 144 /* move right */ +#define right3 145 /* move right */ +#define right4 146 /* move right, 4 bytes */ +#define w0 147 /* move right by |w| */ +#define w1 148 /* move right and set |w| */ +#define w2 149 /* move right and set |w| */ +#define w3 150 /* move right and set |w| */ +#define w4 151 /* move right and set |w| */ +#define x0 152 /* move right by |x| */ +#define x1 153 /* move right and set |x| */ +#define x2 154 /* move right and set |x| */ +#define x3 155 /* move right and set |x| */ +#define x4 156 /* move right and set |x| */ +#define down1 157 /* move down */ +#define down2 158 /* move down */ +#define down3 159 /* move down */ +#define down4 160 /* move down, 4 bytes */ +#define y0 161 /* move down by |y| */ +#define y1 162 /* move down and set |y| */ +#define y2 163 /* move down and set |y| */ +#define y3 164 /* move down and set |y| */ +#define y4 165 /* move down and set |y| */ +#define z0 166 /* move down by |z| */ +#define z1 167 /* move down and set |z| */ +#define z2 168 /* move down and set |z| */ +#define z3 169 /* move down and set |z| */ +#define z4 170 /* move down and set |z| */ +#define fnt_num_0 171 /* set current font to 0 */ +#define fnt1 235 /* set current font */ +#define fnt2 236 /* set current font */ +#define fnt3 237 /* set current font */ +#define fnt4 238 /* set current font */ +#define xxx1 239 /* extension to DVI primitives */ +#define xxx2 240 /* extension to DVI primitives */ +#define xxx3 241 /* extension to DVI primitives */ +#define xxx4 242 /* potentially long extension to DVI primitives */ +#define fnt_def1 243 /* define the meaning of a font number */ +#define pre 247 /* preamble */ +#define post 248 /* postamble beginning */ +#define post_post 249 /* postamble ending */ +#define yyy1 250 /* PDF literal text */ +#define yyy2 251 /* PDF literal text */ +#define yyy3 252 /* PDF literal text */ +#define yyy4 253 /* PDF literal text */ #define null_font 0 -#define long_char 242 /* \.{VF} command for general character packet */ -#define vf_id 202 /* identifies \.{VF} files */ +#define long_char 242 /* \.{VF} command for general character packet */ +#define vf_id 202 /* identifies \.{VF} files */ /* go out \.{VF} processing with an error message */ -#define bad_vf(a) { xfree(vf_buffer); print_nlp(); \ - print_string("Error in processing VF font ("); \ - print_string(font_name(f)); \ - print_string(".vf): "); \ - print_string(a); \ - print_string(", virtual font will be ignored"); \ - print_ln(); return; } - -#define lua_bad_vf(a) { xfree(vf_buffer); \ - lua_settop(L,s_top); \ - lua_pushnil(L); \ - lua_pushstring(L,a); \ - return 2; } +#define bad_vf(a) { xfree(vf_buffer); print_nlp(); \ + print_string("Error in processing VF font ("); \ + print_string(font_name(f)); \ + print_string(".vf): "); \ + print_string(a); \ + print_string(", virtual font will be ignored"); \ + print_ln(); return; } + +#define lua_bad_vf(a) { xfree(vf_buffer); \ + lua_settop(L,s_top); \ + lua_pushnil(L); \ + lua_pushstring(L,a); \ + return 2; } #define tmp_b0 tmp_w.qqqq.b0 #define tmp_b1 tmp_w.qqqq.b1 @@ -115,9 +116,9 @@ $Id: vfovf.c 1169 2008-04-15 14:57:56Z oneiros $ #define tmp_b3 tmp_w.qqqq.b3 #define tmp_int tmp_w.cint -#define vf_stack_size 100 /* \.{DVI} files shouldn't |push| beyond this depth */ +#define vf_stack_size 100 /* \.{DVI} files shouldn't |push| beyond this depth */ -typedef unsigned char vf_stack_index ; /* an index into the stack */ +typedef unsigned char vf_stack_index; /* an index into the stack */ typedef struct vf_stack_record { scaled stack_w, stack_x, stack_y, stack_z; @@ -127,179 +128,201 @@ boolean auto_expand_vf(internal_font_number f); /* forward */ /* get a byte from\.{VF} file */ -#define vf_byte(a) { real_eight_bits vf_tmp_b; \ - if (vf_cur>=vf_size) { \ - pdftex_fail("unexpected eof on virtual font"); \ - } \ +#define vf_byte(a) { real_eight_bits vf_tmp_b; \ + if (vf_cur>=vf_size) { \ + pdftex_fail("unexpected eof on virtual font"); \ + } \ vf_tmp_b = vf_buffer[vf_cur++] ; a = vf_tmp_b; } -#define vf_replace_z() { \ - vf_alpha=16; \ - while (vf_z>=040000000) { \ - vf_z= vf_z / 2; \ - vf_alpha += vf_alpha; \ - } \ - vf_beta=256 / vf_alpha; \ +#define vf_replace_z() { \ + vf_alpha=16; \ + while (vf_z>=040000000) { \ + vf_z= vf_z / 2; \ + vf_alpha += vf_alpha; \ + } \ + vf_beta=256 / vf_alpha; \ vf_alpha=vf_alpha*vf_z; } /* read |k| bytes as an integer from \.{VF} file */ -#define vf_read(k,l) { integer itmp = 0, dtmp = k, jtmp = 0; \ - while (dtmp > 0) { \ - vf_byte(jtmp); \ - if ((dtmp==k) && jtmp>127) \ - jtmp = jtmp - 256; \ - itmp = itmp*256 + jtmp; \ - decr(dtmp); \ - } \ +#define vf_read(k,l) { integer itmp = 0, dtmp = k, jtmp = 0; \ + while (dtmp > 0) { \ + vf_byte(jtmp); \ + if ((dtmp==(integer)k) && jtmp>127) \ + jtmp = jtmp - 256; \ + itmp = itmp*256 + jtmp; \ + decr(dtmp); \ + } \ l = itmp; } -#define vf_read_u(k,l) { unsigned int dtmp=k, itmp = 0, jtmp = 0; \ - while (dtmp-- > 0) { \ - vf_byte(jtmp); \ - itmp = itmp*256 + jtmp; \ - } \ +#define vf_read_u(k,l) { unsigned int dtmp=k, itmp = 0, jtmp = 0; \ + while (dtmp-- > 0) { \ + vf_byte(jtmp); \ + itmp = itmp*256 + jtmp; \ + } \ l = itmp; } -void -pdf_check_vf_cur_val (void) { - internal_font_number f; - f = cur_val; - if (font_type(f) == virtual_font_type) - pdf_error(maketexstring("font"), maketexstring("command cannot be used with virtual font")); +void pdf_check_vf_cur_val(void) +{ + internal_font_number f; + f = cur_val; + if (font_type(f) == virtual_font_type) + pdf_error(maketexstring("font"), + maketexstring("command cannot be used with virtual font")); } static void -vf_local_font_warning(internal_font_number f, internal_font_number k, char *s, integer a, integer b) { - print_nlp(); - print_string(s); - print_string(" in local font "); - print_string(font_name(k)); - print_string(" ("); - print_int(b); - print_string(" != "); - print_int(a); - print_string(") in virtual font "); - print_string(font_name(f)); - print_string(".vf ignored."); +vf_local_font_warning(internal_font_number f, internal_font_number k, char *s, + integer a, integer b) +{ + print_nlp(); + print_string(s); + print_string(" in local font "); + print_string(font_name(k)); + print_string(" ("); + print_int(b); + print_string(" != "); + print_int(a); + print_string(") in virtual font "); + print_string(font_name(f)); + print_string(".vf ignored."); } /* process a local font in \.{VF} file */ -internal_font_number -vf_def_font(internal_font_number f,unsigned char *vf_buffer, integer *vf_cr) { +internal_font_number +vf_def_font(internal_font_number f, unsigned char *vf_buffer, integer * vf_cr) +{ internal_font_number k; str_number s; - scaled ds,fs; + scaled ds, fs; four_quarters cs; - memory_word tmp_w; /* accumulator */ + memory_word tmp_w; /* accumulator */ integer junk; unsigned long checksum; - cs.b0 = vf_buffer[(*vf_cr)]; - cs.b1 = vf_buffer[(*vf_cr)+1]; - cs.b2 = vf_buffer[(*vf_cr)+2]; - cs.b3 = vf_buffer[(*vf_cr)+3]; (*vf_cr)+=4; - checksum = cs.b0*256*256*256 + cs.b1*256*256 + cs.b2*256 + cs.b3; - k = vf_buffer[(*vf_cr)] ; (*vf_cr)++; - if (k>127) k-=256; - k = k*256+ vf_buffer[(*vf_cr)] ; (*vf_cr)++; - k = k*256+ vf_buffer[(*vf_cr)] ; (*vf_cr)++; - k = k*256+ vf_buffer[(*vf_cr)] ; (*vf_cr)++; + cs.b0 = vf_buffer[(*vf_cr)]; + cs.b1 = vf_buffer[(*vf_cr) + 1]; + cs.b2 = vf_buffer[(*vf_cr) + 2]; + cs.b3 = vf_buffer[(*vf_cr) + 3]; + (*vf_cr) += 4; + checksum = + cs.b0 * 256 * 256 * 256 + cs.b1 * 256 * 256 + cs.b2 * 256 + cs.b3; + k = vf_buffer[(*vf_cr)]; + (*vf_cr)++; + if (k > 127) + k -= 256; + k = k * 256 + vf_buffer[(*vf_cr)]; + (*vf_cr)++; + k = k * 256 + vf_buffer[(*vf_cr)]; + (*vf_cr)++; + k = k * 256 + vf_buffer[(*vf_cr)]; + (*vf_cr)++; fs = sqxfw(k, font_size(f)); - k = vf_buffer[(*vf_cr)] ; (*vf_cr)++; - if (k>127) k-=256; - k = k*256+ vf_buffer[(*vf_cr)] ; (*vf_cr)++; - k = k*256+ vf_buffer[(*vf_cr)] ; (*vf_cr)++; - k = k*256+ vf_buffer[(*vf_cr)] ; (*vf_cr)++; + k = vf_buffer[(*vf_cr)]; + (*vf_cr)++; + if (k > 127) + k -= 256; + k = k * 256 + vf_buffer[(*vf_cr)]; + (*vf_cr)++; + k = k * 256 + vf_buffer[(*vf_cr)]; + (*vf_cr)++; + k = k * 256 + vf_buffer[(*vf_cr)]; + (*vf_cr)++; ds = k / 16; - tmp_b0 = vf_buffer[(*vf_cr)] ; (*vf_cr)++; - tmp_b1 = vf_buffer[(*vf_cr)] ; (*vf_cr)++; + tmp_b0 = vf_buffer[(*vf_cr)]; + (*vf_cr)++; + tmp_b1 = vf_buffer[(*vf_cr)]; + (*vf_cr)++; while (tmp_b0 > 0) { - tmp_b0--; - (*vf_cr)++; /* skip the font path */ + tmp_b0--; + (*vf_cr)++; /* skip the font path */ } string_room(tmp_b1); while (tmp_b1 > 0) { - tmp_b1--; - junk = vf_buffer[(*vf_cr)] ; (*vf_cr)++; - append_pool_char(junk); + tmp_b1--; + junk = vf_buffer[(*vf_cr)]; + (*vf_cr)++; + append_pool_char(junk); } s = make_string(); k = tfm_lookup(s, fs); - if (k == null_font) - k = read_font_info(get_nullcs(), s, get_nullstr(), fs, -1); + if (k == null_font) + k = read_font_info(get_nullcs(), s, fs, -1); if (k != null_font) { - if (checksum!=0 && font_checksum(k)!=0 && checksum!= font_checksum(k)) - vf_local_font_warning(f, k, "checksum mismatch",checksum,font_checksum(k)); - if (ds != font_dsize(k)) - vf_local_font_warning(f, k, "design size mismatch",ds,font_dsize(k)); + if (checksum != 0 && font_checksum(k) != 0 + && checksum != font_checksum(k)) + vf_local_font_warning(f, k, "checksum mismatch", checksum, + font_checksum(k)); + if (ds != font_dsize(k)) + vf_local_font_warning(f, k, "design size mismatch", ds, + font_dsize(k)); } if (pdf_font_expand_ratio(f) != 0) - set_expand_params(k, pdf_font_auto_expand(f), - pdf_font_expand_ratio(pdf_font_stretch(f)), - -pdf_font_expand_ratio(pdf_font_shrink(f)), - pdf_font_step(f), pdf_font_expand_ratio(f)); + set_expand_params(k, pdf_font_auto_expand(f), + pdf_font_expand_ratio(pdf_font_stretch(f)), + -pdf_font_expand_ratio(pdf_font_shrink(f)), + pdf_font_step(f), pdf_font_expand_ratio(f)); return k; } -int -open_vf_file (char *fn, unsigned char **vbuffer, integer *vsize) { - boolean res; /* was the callback successful? */ - integer callback_id; - boolean file_read; /* was |vf_file| successfully read? */ - FILE *vf_file; - char *fnam = NULL; +int open_vf_file(char *fn, unsigned char **vbuffer, integer * vsize) +{ + boolean res; /* was the callback successful? */ + integer callback_id; + boolean file_read; /* was |vf_file| successfully read? */ + FILE *vf_file; + char *fnam = NULL; - namelength = strlen(fn); - nameoffile = xmalloc(namelength+2); - strcpy((char *)(nameoffile+1),fn); + namelength = strlen(fn); + nameoffile = xmalloc(namelength + 2); + strcpy((char *) (nameoffile + 1), fn); - callback_id=callback_defined(find_vf_file_callback); - if (callback_id>0) { - res = run_callback(callback_id,"S->S",fn, &fnam); - if (res && (fnam!=NULL) && (strlen(fnam)>0)) { - /* @<Fixup |nameoffile| after callback@>; */ - free(nameoffile); - namelength = strlen(fnam); - nameoffile = xmalloc(namelength+2); - strcpy((char *)(nameoffile+1),fnam); - } else { - return 0; - } - } - callback_id=callback_defined(read_vf_file_callback); - if (callback_id>0) { - file_read = false; - res = run_callback(callback_id,"S->bSd",stringcast(nameoffile+1), - &file_read, vbuffer,vsize); - if (res && file_read && (*vsize>0)) { - return 1; + callback_id = callback_defined(find_vf_file_callback); + if (callback_id > 0) { + res = run_callback(callback_id, "S->S", fn, &fnam); + if (res && (fnam != NULL) && (strlen(fnam) > 0)) { + /* @<Fixup |nameoffile| after callback@>; */ + free(nameoffile); + namelength = strlen(fnam); + nameoffile = xmalloc(namelength + 2); + strcpy((char *) (nameoffile + 1), fnam); + } else { + return 0; + } } - if (!file_read) - return 0; /* -1 */ - } else { - if (ovf_b_open_in(vf_file) || vf_b_open_in(vf_file)) { - res = read_vf_file(vf_file,vbuffer,vsize); - b_close(vf_file); - if (res) { - return 1; - } + callback_id = callback_defined(read_vf_file_callback); + if (callback_id > 0) { + file_read = false; + res = run_callback(callback_id, "S->bSd", stringcast(nameoffile + 1), + &file_read, vbuffer, vsize); + if (res && file_read && (*vsize > 0)) { + return 1; + } + if (!file_read) + return 0; /* -1 */ } else { - return 0; /* -1 */ + if (ovf_b_open_in(vf_file) || vf_b_open_in(vf_file)) { + res = read_vf_file(vf_file, vbuffer, vsize); + b_close(vf_file); + if (res) { + return 1; + } + } else { + return 0; /* -1 */ + } } - } - return 0; + return 0; } @@ -311,1039 +334,1281 @@ open_vf_file (char *fn, unsigned char **vbuffer, integer *vsize) { process font definitions in virtual font we call |vf_def_font|. */ -#define append_packet(k) vpackets[vf_np++] = k +#define append_packet(k) vpackets[vf_np++] = k /* life is easier if all internal font commands are fnt4 and all character commands are set4 or put4 */ -#define append_fnt_set(k) { \ - assert(k>0) ; \ - append_packet(packet_font_code); \ - append_four(k); } +#define append_fnt_set(k) { \ + assert(k>0) ; \ + append_packet(packet_font_code); \ + append_four(k); } -#define append_four(k) { \ - append_packet((k&0xFF000000)>>24); \ - append_packet((k&0x00FF0000)>>16); \ - append_packet((k&0x0000FF00)>>8); \ - append_packet((k&0x000000FF)); } +#define append_four(k) { \ + append_packet((k&0xFF000000)>>24); \ + append_packet((k&0x00FF0000)>>16); \ + append_packet((k&0x0000FF00)>>8); \ + append_packet((k&0x000000FF)); } /* some of these things happen twice, adding a define is simplest */ -#define test_checksum() { vf_byte(tmp_b0); vf_byte(tmp_b1); \ - vf_byte(tmp_b2); vf_byte(tmp_b3); \ +#define test_checksum() { vf_byte(tmp_b0); vf_byte(tmp_b1); \ + vf_byte(tmp_b2); vf_byte(tmp_b3); \ if (((tmp_b0 != 0) || (tmp_b1 != 0) || (tmp_b2 != 0) || (tmp_b3 != 0)) && \ - ((font_check_0(f) != 0) || (font_check_1(f) != 0) || \ - (font_check_2(f) != 0) || (font_check_3(f) != 0)) && \ - ((tmp_b0 != font_check_0(f)) || (tmp_b1 != font_check_1(f)) || \ - (tmp_b2 != font_check_2(f)) || (tmp_b3 != font_check_3(f)))) { \ - print_nlp(); \ - print_string("checksum mismatch in font "); \ - print_string(font_name(f)); \ + ((font_check_0(f) != 0) || (font_check_1(f) != 0) || \ + (font_check_2(f) != 0) || (font_check_3(f) != 0)) && \ + ((tmp_b0 != font_check_0(f)) || (tmp_b1 != font_check_1(f)) || \ + (tmp_b2 != font_check_2(f)) || (tmp_b3 != font_check_3(f)))) { \ + print_nlp(); \ + print_string("checksum mismatch in font "); \ + print_string(font_name(f)); \ print_string(".vf ignored "); } } -#define test_dsize() { int read_tmp; vf_read(4,read_tmp); \ - if ((read_tmp / 16) != font_dsize(f)) { \ - print_nlp(); \ - print_string("design size mismatch in font "); \ - print_string(font_name(f)); \ - print_string(".vf ignored"); \ +#define test_dsize() { int read_tmp; vf_read(4,read_tmp); \ + if ((read_tmp / 16) != font_dsize(f)) { \ + print_nlp(); \ + print_string("design size mismatch in font "); \ + print_string(font_name(f)); \ + print_string(".vf ignored"); \ } } -int count_packet_bytes (real_eight_bits *vf_buf, int cur_bute, int count) { - int k = 0; - int ff = 0; - int acc = 0; - unsigned int cmd = 0; - unsigned int d = 0; - while (k<count) { - cmd = vf_buf[cur_bute+k]; k++; - if ((cmd >= set_char_0) && (cmd < set1)) { - if (ff==0) { ff = 1; acc+=5; } - acc+=5; - } else if ((fnt_num_0 <= cmd) && (cmd <= fnt_num_0 + 63)) { - ff = 1; - acc+=5; - } else { - switch (cmd) { - case fnt1: acc+=5; k+=1; ff=1 ; break; - case fnt2: acc+=5; k+=2; ff=1 ; break; - case fnt3: acc+=5; k+=3; ff=1 ; break; - case fnt4: acc+=5; k+=4; ff=1 ; break; - case set_rule: acc+=9; k+=8; break; - case put_rule: acc+=11; k+=8; break; - case set1: acc+=5; k+=1; if (ff==0) { ff = 1; acc+=5; } break; - case set2: acc+=5; k+=2; if (ff==0) { ff = 1; acc+=5; } break; - case set3: acc+=5; k+=3; if (ff==0) { ff = 1; acc+=5; } break; - case set4: acc+=5; k+=4; if (ff==0) { ff = 1; acc+=5; } break; - case put1: acc+=7; k+=1; if (ff==0) { ff = 1; acc+=5; } break; - case put2: acc+=7; k+=2; if (ff==0) { ff = 1; acc+=5; } break; - case put3: acc+=7; k+=3; if (ff==0) { ff = 1; acc+=5; } break; - case put4: acc+=7; k+=4; if (ff==0) { ff = 1; acc+=5; } break; - case right1: acc+=5; k+=1; break; - case right2: acc+=5; k+=2; break; - case right3: acc+=5; k+=3; break; - case right4: acc+=5; k+=4; break; - case w1: acc+=5; k+=1; break; - case w2: acc+=5; k+=2; break; - case w3: acc+=5; k+=3; break; - case w4: acc+=5; k+=4; break; - case x1: acc+=5; k+=1; break; - case x2: acc+=5; k+=2; break; - case x3: acc+=5; k+=3; break; - case x4: acc+=5; k+=4; break; - case down1: acc+=5; k+=1; break; - case down2: acc+=5; k+=2; break; - case down3: acc+=5; k+=3; break; - case down4: acc+=5; k+=4; break; - case y1: acc+=5; k+=1; break; - case y2: acc+=5; k+=2; break; - case y3: acc+=5; k+=3; break; - case y4: acc+=5; k+=4; break; - case z1: acc+=5; k+=1; break; - case z2: acc+=5; k+=2; break; - case z3: acc+=5; k+=3; break; - case z4: acc+=5; k+=4; break; - case xxx1: - d = vf_buf[cur_bute+k]; k++; - k += d; acc += 5 + d; - break; - case xxx2: - d = vf_buf[cur_bute+k]; k++; - d = d*256 + vf_buf[cur_bute+k]; k++; - k += d; acc += 5 + d; - break; - case xxx3: - d = vf_buf[cur_bute+k]; k++; - d = d*256 + vf_buf[cur_bute+k]; k++; - d = d*256 + vf_buf[cur_bute+k]; k++; - k += d; acc += 5 + d; - break; - case xxx4: - d = vf_buf[cur_bute+k]; k++; - d = d*256 + vf_buf[cur_bute+k]; k++; - d = d*256 + vf_buf[cur_bute+k]; k++; - d = d*256 + vf_buf[cur_bute+k]; k++; - k += d; acc += 5 + d; - break; - case w0: acc+=5; break; - case x0: acc+=5; break; - case y0: acc+=5; break; - case z0: acc+=5; break; - case nop: break; - case push: acc+=1; break; - case pop: acc+=1; break; - } - } - } - return (acc+1); +int count_packet_bytes(real_eight_bits * vf_buf, int cur_bute, int count) +{ + int k = 0; + int ff = 0; + int acc = 0; + unsigned int cmd = 0; + unsigned int d = 0; + while (k < count) { + cmd = vf_buf[cur_bute + k]; + k++; + if (cmd < set1) { + if (ff == 0) { + ff = 1; + acc += 5; + } + acc += 5; + } else if ((fnt_num_0 <= cmd) && (cmd <= fnt_num_0 + 63)) { + ff = 1; + acc += 5; + } else { + switch (cmd) { + case fnt1: + acc += 5; + k += 1; + ff = 1; + break; + case fnt2: + acc += 5; + k += 2; + ff = 1; + break; + case fnt3: + acc += 5; + k += 3; + ff = 1; + break; + case fnt4: + acc += 5; + k += 4; + ff = 1; + break; + case set_rule: + acc += 9; + k += 8; + break; + case put_rule: + acc += 11; + k += 8; + break; + case set1: + acc += 5; + k += 1; + if (ff == 0) { + ff = 1; + acc += 5; + } + break; + case set2: + acc += 5; + k += 2; + if (ff == 0) { + ff = 1; + acc += 5; + } + break; + case set3: + acc += 5; + k += 3; + if (ff == 0) { + ff = 1; + acc += 5; + } + break; + case set4: + acc += 5; + k += 4; + if (ff == 0) { + ff = 1; + acc += 5; + } + break; + case put1: + acc += 7; + k += 1; + if (ff == 0) { + ff = 1; + acc += 5; + } + break; + case put2: + acc += 7; + k += 2; + if (ff == 0) { + ff = 1; + acc += 5; + } + break; + case put3: + acc += 7; + k += 3; + if (ff == 0) { + ff = 1; + acc += 5; + } + break; + case put4: + acc += 7; + k += 4; + if (ff == 0) { + ff = 1; + acc += 5; + } + break; + case right1: + acc += 5; + k += 1; + break; + case right2: + acc += 5; + k += 2; + break; + case right3: + acc += 5; + k += 3; + break; + case right4: + acc += 5; + k += 4; + break; + case w1: + acc += 5; + k += 1; + break; + case w2: + acc += 5; + k += 2; + break; + case w3: + acc += 5; + k += 3; + break; + case w4: + acc += 5; + k += 4; + break; + case x1: + acc += 5; + k += 1; + break; + case x2: + acc += 5; + k += 2; + break; + case x3: + acc += 5; + k += 3; + break; + case x4: + acc += 5; + k += 4; + break; + case down1: + acc += 5; + k += 1; + break; + case down2: + acc += 5; + k += 2; + break; + case down3: + acc += 5; + k += 3; + break; + case down4: + acc += 5; + k += 4; + break; + case y1: + acc += 5; + k += 1; + break; + case y2: + acc += 5; + k += 2; + break; + case y3: + acc += 5; + k += 3; + break; + case y4: + acc += 5; + k += 4; + break; + case z1: + acc += 5; + k += 1; + break; + case z2: + acc += 5; + k += 2; + break; + case z3: + acc += 5; + k += 3; + break; + case z4: + acc += 5; + k += 4; + break; + case xxx1: + d = vf_buf[cur_bute + k]; + k++; + k += d; + acc += 5 + d; + break; + case xxx2: + d = vf_buf[cur_bute + k]; + k++; + d = d * 256 + vf_buf[cur_bute + k]; + k++; + k += d; + acc += 5 + d; + break; + case xxx3: + d = vf_buf[cur_bute + k]; + k++; + d = d * 256 + vf_buf[cur_bute + k]; + k++; + d = d * 256 + vf_buf[cur_bute + k]; + k++; + k += d; + acc += 5 + d; + break; + case xxx4: + d = vf_buf[cur_bute + k]; + k++; + d = d * 256 + vf_buf[cur_bute + k]; + k++; + d = d * 256 + vf_buf[cur_bute + k]; + k++; + d = d * 256 + vf_buf[cur_bute + k]; + k++; + k += d; + acc += 5 + d; + break; + case w0: + acc += 5; + break; + case x0: + acc += 5; + break; + case y0: + acc += 5; + break; + case z0: + acc += 5; + break; + case nop: + break; + case push: + acc += 1; + break; + case pop: + acc += 1; + break; + } + } + } + return (acc + 1); } -void -do_vf(internal_font_number f) { - integer k, n, i; - unsigned cmd; - scaled x,y,w,z,h,v; - integer cc, cmd_length, packet_length; - charinfo *co; - scaled tfm_width; - integer save_cur_byte; - vf_stack_index stack_level; - integer vf_z; /* multiplier */ - integer vf_alpha; /* correction for negative values */ - char vf_beta; /* divisor */ - integer vf_np; - real_eight_bits *vpackets; - memory_word tmp_w; /* accumulator */ - vf_stack_record vf_stack[256]; - integer junk; - unsigned char *vf_buffer; - integer vf_size; - integer vf_cur; - integer *vf_local_fnts = NULL; /* external font ids */ - integer *vf_real_fnts = NULL; /* internal font ids */ - unsigned vf_nf = 0; /* local font counter */ - - if (font_type(f)!= unknown_font_type) - return; - set_font_type(f,real_font_type); - if (auto_expand_vf(f)) - return; /* auto-expanded virtual font */ - stack_level = 0; - /* @<Open |vf_file|, return if not found@>; */ - vf_cur=0; vf_buffer=NULL; vf_size=0; - if (!open_vf_file(font_name(f), &vf_buffer, &vf_size)) - return; - /* @<Process the preamble@>;@/ */ - set_font_type(f,virtual_font_type); - vf_byte(k); - if (k != pre) - bad_vf("PRE command expected"); - vf_byte(k); - if (k != vf_id) - bad_vf("wrong id byte"); - vf_byte(cmd_length); - for (k = 1;k<= cmd_length;k++) - vf_byte(junk); - test_checksum(); - test_dsize(); - /* update_terminal;*/ - vf_z = font_size(f); - vf_replace_z(); - /* @<Process the font definitions@>;@/ */ - /* scan forward to find the number of internal fonts */ - vf_nf = 0; - save_cur_byte = vf_cur; - vf_byte(cmd); - while ((cmd >= fnt_def1) && (cmd <= (fnt_def1 + 3))) { - vf_read((cmd - fnt_def1 + 1),junk); - vf_read(4,junk); - vf_read(4,junk); - vf_read(4,junk); +void do_vf(internal_font_number f) +{ + integer k, i; + unsigned cmd, n; + scaled x, y, w, z, h, v; + integer cc, cmd_length, packet_length; + charinfo *co; + scaled tfm_width; + integer save_cur_byte; + vf_stack_index stack_level; + integer vf_z; /* multiplier */ + integer vf_alpha; /* correction for negative values */ + char vf_beta; /* divisor */ + integer vf_np; + real_eight_bits *vpackets; + memory_word tmp_w; /* accumulator */ + vf_stack_record vf_stack[256]; + integer junk; + unsigned char *vf_buffer; + integer vf_size; + integer vf_cur; + integer *vf_local_fnts = NULL; /* external font ids */ + integer *vf_real_fnts = NULL; /* internal font ids */ + unsigned vf_nf = 0; /* local font counter */ + + if (font_type(f) != unknown_font_type) + return; + set_font_type(f, real_font_type); + if (auto_expand_vf(f)) + return; /* auto-expanded virtual font */ + stack_level = 0; + /* @<Open |vf_file|, return if not found@>; */ + vf_cur = 0; + vf_buffer = NULL; + vf_size = 0; + if (!open_vf_file(font_name(f), &vf_buffer, &vf_size)) + return; + /* @<Process the preamble@>;@/ */ + set_font_type(f, virtual_font_type); vf_byte(k); - vf_byte(junk); - k += junk; - while (k-- > 0) { vf_byte(junk); } - incr(vf_nf); - vf_byte(cmd); - } - vf_cur = save_cur_byte; - vf_byte(cmd); - /* malloc and fill the local font arrays */ - if (vf_nf>0) { - i = vf_nf*sizeof(integer); - vf_local_fnts= xmalloc(i); - memset(vf_local_fnts,0,i); - vf_real_fnts= xmalloc(i); - memset(vf_real_fnts,0,i); + if (k != pre) + bad_vf("PRE command expected"); + vf_byte(k); + if (k != vf_id) + bad_vf("wrong id byte"); + vf_byte(cmd_length); + for (k = 1; k <= cmd_length; k++) + vf_byte(junk); + test_checksum(); + test_dsize(); + /* update_terminal; */ + vf_z = font_size(f); + vf_replace_z(); + /* @<Process the font definitions@>;@/ */ + /* scan forward to find the number of internal fonts */ vf_nf = 0; + save_cur_byte = vf_cur; + vf_byte(cmd); while ((cmd >= fnt_def1) && (cmd <= (fnt_def1 + 3))) { - vf_read_u((cmd - fnt_def1 + 1),vf_local_fnts[vf_nf]); - vf_real_fnts[vf_nf] = vf_def_font(f, vf_buffer, &vf_cur); - incr(vf_nf); - vf_byte(cmd); + vf_read((cmd - fnt_def1 + 1), junk); + vf_read(4, junk); + vf_read(4, junk); + vf_read(4, junk); + vf_byte(k); + vf_byte(junk); + k += junk; + while (k-- > 0) { + vf_byte(junk); + } + incr(vf_nf); + vf_byte(cmd); + } + vf_cur = save_cur_byte; + vf_byte(cmd); + /* malloc and fill the local font arrays */ + if (vf_nf > 0) { + i = vf_nf * sizeof(integer); + vf_local_fnts = xmalloc(i); + memset(vf_local_fnts, 0, i); + vf_real_fnts = xmalloc(i); + memset(vf_real_fnts, 0, i); + vf_nf = 0; + while ((cmd >= fnt_def1) && (cmd <= (fnt_def1 + 3))) { + vf_read_u((cmd - fnt_def1 + 1), vf_local_fnts[vf_nf]); + vf_real_fnts[vf_nf] = vf_def_font(f, vf_buffer, &vf_cur); + incr(vf_nf); + vf_byte(cmd); + } } - } - while (cmd <= long_char) { - /* @<Build a character packet@>;@/ */ - vf_np = 0; - if (cmd == long_char) { - vf_read_u(4,packet_length); - vf_read_u(4,cc); - if (!char_exists(f,cc)) { - bad_vf("invalid character code"); - } - vf_read(4,k); - tfm_width = sqxfw(k, font_size(f)); - } else { - packet_length = cmd; - vf_byte(cc); - if (!char_exists(f,cc)) { - bad_vf("invalid character code"); - } - vf_read(3,k); - tfm_width = sqxfw(k, font_size(f)); + while (cmd <= long_char) { + /* @<Build a character packet@>;@/ */ + vf_np = 0; + if (cmd == long_char) { + vf_read_u(4, packet_length); + vf_read_u(4, cc); + if (!char_exists(f, cc)) { + bad_vf("invalid character code"); + } + vf_read(4, k); + tfm_width = sqxfw(k, font_size(f)); + } else { + packet_length = cmd; + vf_byte(cc); + if (!char_exists(f, cc)) { + bad_vf("invalid character code"); + } + vf_read(3, k); + tfm_width = sqxfw(k, font_size(f)); + } + if (packet_length < 0) + bad_vf("negative packet length"); + if (tfm_width != char_width(f, cc)) { + /* precisely 'one off' errors are rampant */ + if (abs(tfm_width - char_width(f, cc)) > 1) { + print_nlp(); + print_string("character width mismatch in font "); + print_string(font_name(f)); + print_string(".vf ignored"); + } + } + k = count_packet_bytes(vf_buffer, vf_cur, packet_length); + vpackets = xmalloc(k + 1); /* need one extra extra for packet_end */ + co = get_charinfo(f, cc); + k = 0; + w = 0; + x = 0; + y = 0; + z = 0; + while (packet_length > 0) { + vf_byte(cmd); + decr(packet_length); + + if (cmd < set1) { + if (k == 0) { + k = vf_real_fnts[0]; + append_fnt_set(k); + } + append_packet(packet_char_code); + append_four(cmd); + cmd_length = 0; + cmd = nop; + + } else if (((fnt_num_0 <= cmd) && (cmd <= fnt_num_0 + 63)) || + ((fnt1 <= cmd) && (cmd <= fnt1 + 3))) { + if (cmd >= fnt1) { + vf_read_u((cmd - fnt1 + 1), k); + packet_length -= (cmd - fnt1 + 1); + } else { + k = cmd - fnt_num_0; + } + + /* change from local to external font id */ + n = 0; + while ((n < vf_nf) && (vf_local_fnts[n] != k)) + n++; + if (n == vf_nf) + bad_vf("undefined local font"); + + k = vf_real_fnts[n]; + append_fnt_set(k); + cmd_length = 0; + cmd = nop; + } else { + switch (cmd) { + case set_rule: + vf_read(4, h); + vf_read(4, v); + append_packet(packet_rule_code); + append_four(h); + append_four(v); + packet_length -= 8; + break; + case put_rule: + vf_read(4, h); + vf_read(4, v); + append_packet(packet_push_code); + append_packet(packet_rule_code); + append_four(h); + append_four(v); + append_packet(packet_pop_code); + packet_length -= 8; + break; + case set1: + case set2: + case set3: + case set4: + if (k == 0) { + k = vf_real_fnts[0]; + append_fnt_set(k); + } + vf_read_u((cmd - set1 + 1), i); + append_packet(packet_char_code); + append_four(i); + packet_length -= (cmd - set1 + 1); + break; + case put1: + case put2: + case put3: + case put4: + if (k == 0) { + k = vf_real_fnts[0]; + append_fnt_set(k); + } + vf_read_u((cmd - put1 + 1), i); + append_packet(packet_push_code); + append_packet(packet_char_code); + append_four(i); + append_packet(packet_pop_code); + packet_length -= (cmd - put1 + 1); + break; + case right1: + case right2: + case right3: + case right4: + vf_read((cmd - right1 + 1), i); + append_packet(packet_right_code); + append_four(i); + packet_length -= (cmd - right1 + 1); + break; + case w1: + case w2: + case w3: + case w4: + vf_read((cmd - w1 + 1), w); + append_packet(packet_right_code); + append_four(w); + packet_length -= (cmd - w1 + 1); + break; + case x1: + case x2: + case x3: + case x4: + vf_read((cmd - x1 + 1), x); + append_packet(packet_right_code); + append_four(x); + packet_length -= (cmd - x1 + 1); + break; + case down1: + case down2: + case down3: + case down4: + vf_read((cmd - down1 + 1), i); + append_packet(packet_down_code); + append_four(i); + packet_length -= (cmd - down1 + 1); + break; + case y1: + case y2: + case y3: + case y4: + vf_read((cmd - y1 + 1), y); + append_packet(packet_down_code); + append_four(y); + packet_length -= (cmd - y1 + 1); + break; + case z1: + case z2: + case z3: + case z4: + vf_read((cmd - z1 + 1), z); + append_packet(packet_down_code); + append_four(z); + packet_length -= (cmd - z1 + 1); + break; + case xxx1: + case xxx2: + case xxx3: + case xxx4: + vf_read_u((cmd - xxx1 + 1), cmd_length); + packet_length -= (cmd - xxx1 + 1); + if (cmd_length <= 0) + bad_vf("special of negative length"); + packet_length -= cmd_length; + + append_packet(packet_special_code); + append_four(cmd_length); + while (cmd_length > 0) { + cmd_length--; + vf_byte(i); + append_packet(i); + } + break; + case w0: + append_packet(packet_right_code); + append_four(w); + break; + case x0: + append_packet(packet_right_code); + append_four(x); + break; + case y0: + append_packet(packet_down_code); + append_four(y); + break; + case z0: + append_packet(packet_down_code); + append_four(z); + break; + case nop: + break; + case push: + if (stack_level == vf_stack_size) { + overflow_string("virtual font stack size", + vf_stack_size); + } else { + vf_stack[stack_level].stack_w = w; + vf_stack[stack_level].stack_x = x; + vf_stack[stack_level].stack_y = y; + vf_stack[stack_level].stack_z = z; + incr(stack_level); + append_packet(packet_push_code); + } + break; + case pop: + if (stack_level == 0) { + bad_vf("more POPs than PUSHs in character"); + } else { + decr(stack_level); + w = vf_stack[stack_level].stack_w; + x = vf_stack[stack_level].stack_x; + y = vf_stack[stack_level].stack_y; + z = vf_stack[stack_level].stack_z; + append_packet(packet_pop_code); + } + break; + default: + bad_vf("improver DVI command"); + } + } + } + /* signal end of packet */ + append_packet(packet_end_code); + + if (stack_level != 0) + bad_vf("more PUSHs than POPs in character packet"); + if (packet_length != 0) + bad_vf("invalid packet length or DVI command in packet"); + /* @<Store the packet being built@>; */ + set_charinfo_packets(co, vpackets); + vf_byte(cmd); } - if (packet_length < 0) - bad_vf("negative packet length"); - if (tfm_width != char_width(f,cc)) { - /* precisely 'one off' errors are rampant */ - if (abs(tfm_width - char_width(f,cc))>1) { - print_nlp(); - print_string("character width mismatch in font "); - print_string(font_name(f)); - print_string(".vf ignored"); - } - } - k = count_packet_bytes(vf_buffer,vf_cur,packet_length); - vpackets = xmalloc(k+1); - co = get_charinfo(f,cc); - k = 0; - w = 0; x = 0; y = 0; z = 0; - while (packet_length > 0) { - vf_byte(cmd); - decr(packet_length); - - if ((cmd >= set_char_0) && (cmd < set1)) { - if (k == 0) { - k = vf_real_fnts[0]; - append_fnt_set(k); - } - append_packet(packet_char_code); - append_four(cmd); - cmd_length = 0; - cmd = nop; - - } else if (((fnt_num_0 <= cmd) && (cmd <= fnt_num_0 + 63)) || - ((fnt1 <= cmd) && (cmd <= fnt1 + 3))) { - if (cmd >= fnt1) { - vf_read_u((cmd - fnt1 + 1),k); - packet_length -= (cmd - fnt1 + 1); - } else { - k = cmd - fnt_num_0; - } - - /* change from local to external font id */ - n = 0; - while ((n < vf_nf) && (vf_local_fnts[n] != k)) - n++; - if (n==vf_nf) - bad_vf("undefined local font"); - - k = vf_real_fnts[n]; - append_fnt_set(k); - cmd_length = 0; - cmd = nop; - } else { - switch (cmd) { - case set_rule: - vf_read(4,h); vf_read(4,v); - append_packet(packet_rule_code); - append_four(h); - append_four(v); - packet_length -= 8; - break; - case put_rule: - vf_read(4,h); vf_read(4,v); - append_packet(packet_push_code); - append_packet(packet_rule_code); - append_four(h); - append_four(v); - append_packet(packet_pop_code); - packet_length -= 8; - break; - case set1: - case set2: - case set3: - case set4: - if (k == 0) { - k = vf_real_fnts[0]; - append_fnt_set(k); - } - vf_read_u((cmd - set1 + 1),i); - append_packet(packet_char_code); - append_four(i); - packet_length -= (cmd - set1 + 1); - break; - case put1: - case put2: - case put3: - case put4: - if (k == 0) { - k = vf_real_fnts[0]; - append_fnt_set(k); - } - vf_read_u((cmd - put1 + 1),i); - append_packet(packet_push_code); - append_packet(packet_char_code); - append_four(i); - append_packet(packet_pop_code); - packet_length -= (cmd - put1 + 1); - break; - case right1: - case right2: - case right3: - case right4: - vf_read((cmd - right1 + 1),i); - append_packet(packet_right_code); - append_four(i); - packet_length -= (cmd - right1 + 1); - break; - case w1: - case w2: - case w3: - case w4: - vf_read((cmd - w1 + 1),w); - append_packet(packet_right_code); - append_four(w); - packet_length -= (cmd - w1 + 1); - break; - case x1: - case x2: - case x3: - case x4: - vf_read((cmd - x1 + 1),x); - append_packet(packet_right_code); - append_four(x); - packet_length -= (cmd - x1 + 1); - break; - case down1: - case down2: - case down3: - case down4: - vf_read((cmd - down1 + 1),i); - append_packet(packet_down_code); - append_four(i); - packet_length -= (cmd - down1 + 1); - break; - case y1: - case y2: - case y3: - case y4: - vf_read((cmd - y1 + 1),y); - append_packet(packet_down_code); - append_four(y); - packet_length -= (cmd - y1 + 1); - break; - case z1: - case z2: - case z3: - case z4: - vf_read((cmd - z1 + 1),z); - append_packet(packet_down_code); - append_four(z); - packet_length -= (cmd - z1 + 1); - break; - case xxx1: - case xxx2: - case xxx3: - case xxx4: - vf_read_u((cmd - xxx1 + 1),cmd_length); - packet_length -= (cmd - xxx1 + 1); - if (cmd_length <= 0) - bad_vf("special of negative length"); - packet_length -= cmd_length; - - append_packet(packet_special_code); - append_four(cmd_length); - while (cmd_length > 0) { - cmd_length--; - vf_byte(i); - append_packet(i); - } - append_packet(0); - break; - case w0: - append_packet(packet_right_code); - append_four(w); - break; - case x0: - append_packet(packet_right_code); - append_four(x); - break; - case y0: - append_packet(packet_down_code); - append_four(y); - break; - case z0: - append_packet(packet_down_code); - append_four(z); - break; - case nop: - break; - case push: - if (stack_level == vf_stack_size) { - overflow_string("virtual font stack size", vf_stack_size); - } else { - vf_stack[stack_level].stack_w = w; - vf_stack[stack_level].stack_x = x; - vf_stack[stack_level].stack_y = y; - vf_stack[stack_level].stack_z = z; - incr(stack_level); - append_packet(packet_push_code); - } - break; - case pop: - if (stack_level == 0) { - bad_vf("more POPs than PUSHs in character"); - } else { - decr(stack_level); - w = vf_stack[stack_level].stack_w; - x = vf_stack[stack_level].stack_x; - y = vf_stack[stack_level].stack_y; - z = vf_stack[stack_level].stack_z; - append_packet(packet_pop_code); - } - break; - default: - bad_vf("improver DVI command"); - } - } - } - /* signal end of packet */ - append_packet(packet_end_code); - - if (stack_level != 0) - bad_vf("more PUSHs than POPs in character packet"); - if (packet_length != 0) - bad_vf("invalid packet length or DVI command in packet"); - /* @<Store the packet being built@>; */ - set_charinfo_packets(co,vpackets); - vf_byte(cmd); - } - if (cmd != post) - bad_vf("POST command expected"); + if (cmd != post) + bad_vf("POST command expected"); - xfree(vf_buffer); + xfree(vf_buffer); } -#define make_command0(N,K) { \ - lua_newtable(L); \ - lua_pushstring(L, N); \ - lua_rawseti(L,-2, 1); \ - lua_rawseti(L,-2, K); \ +#define make_command0(N,K) { \ + lua_newtable(L); \ + lua_pushstring(L, N); \ + lua_rawseti(L,-2, 1); \ + lua_rawseti(L,-2, K); \ K++; } -#define make_command1(N,V,K) { \ - lua_newtable(L); \ - lua_pushstring(L, N); \ - lua_rawseti(L,-2, 1); \ - lua_pushnumber(L, V); \ - lua_rawseti(L,-2, 2); \ - lua_rawseti(L,-2, K); \ +#define make_command1(N,V,K) { \ + lua_newtable(L); \ + lua_pushstring(L, N); \ + lua_rawseti(L,-2, 1); \ + lua_pushnumber(L, V); \ + lua_rawseti(L,-2, 2); \ + lua_rawseti(L,-2, K); \ K++; } -#define make_command2(N,V,W,K) { \ - lua_newtable(L); \ - lua_pushstring(L, N); \ - lua_rawseti(L,-2, 1); \ - lua_pushnumber(L, V); \ - lua_rawseti(L,-2, 2); \ - lua_pushnumber(L, W); \ - lua_rawseti(L,-2, 3); \ - lua_rawseti(L,-2, K); \ +#define make_command2(N,V,W,K) { \ + lua_newtable(L); \ + lua_pushstring(L, N); \ + lua_rawseti(L,-2, 1); \ + lua_pushnumber(L, V); \ + lua_rawseti(L,-2, 2); \ + lua_pushnumber(L, W); \ + lua_rawseti(L,-2, 3); \ + lua_rawseti(L,-2, K); \ K++; } -#define make_commands(N,S,V,K) { \ - lua_newtable(L); \ - lua_pushstring(L, N); \ - lua_rawseti(L,-2, 1); \ - lua_pushlstring(L, S, V); \ - lua_rawseti(L,-2, 2); \ - lua_rawseti(L,-2, K); \ +#define make_commands(N,S,V,K) { \ + lua_newtable(L); \ + lua_pushstring(L, N); \ + lua_rawseti(L,-2, 1); \ + lua_pushlstring(L, S, V); \ + lua_rawseti(L,-2, 2); \ + lua_rawseti(L,-2, K); \ K++; } -int -make_vf_table(lua_State *L, char *cnom, scaled atsize) { - integer cmd, k, i; - integer cc, cmd_length, packet_length; - scaled tfm_width; - vf_stack_index stack_level; - integer vf_z; /* multiplier */ - integer vf_alpha; /* correction for negative values */ - char vf_beta; /* divisor */ - char *s; - scaled h,v; - scaled w, x, y, z; - integer s_top; /* lua stack */ - integer vf_nf ; /* local font counter */ - scaled ds,fs; - four_quarters cs; - memory_word tmp_w; /* accumulator */ - vf_stack_record vf_stack[256]; - unsigned char *vf_buffer; - integer vf_size; - integer vf_cur; - - - stack_level = 0; - /* @<Open |vf_file|, return if not found@>; */ - vf_cur=0; vf_buffer=NULL; vf_size=0; - if (!open_vf_file(cnom, &vf_buffer, &vf_size)) { - lua_pushnil(L); - return 1; - } +int make_vf_table(lua_State * L, char *cnom, scaled atsize) +{ + integer cmd, k, i; + integer cc, cmd_length, packet_length; + scaled tfm_width; + vf_stack_index stack_level; + integer vf_z; /* multiplier */ + integer vf_alpha; /* correction for negative values */ + char vf_beta; /* divisor */ + char *s; + scaled h, v; + scaled w, x, y, z; + integer s_top; /* lua stack */ + integer vf_nf; /* local font counter */ + scaled ds, fs; + four_quarters cs; + memory_word tmp_w; /* accumulator */ + vf_stack_record vf_stack[256]; + unsigned char *vf_buffer; + integer vf_size; + integer vf_cur; + + + stack_level = 0; + /* @<Open |vf_file|, return if not found@>; */ + vf_cur = 0; + vf_buffer = NULL; + vf_size = 0; + if (!open_vf_file(cnom, &vf_buffer, &vf_size)) { + lua_pushnil(L); + return 1; + } + + /* start by creating a table */ + s_top = lua_gettop(L); + lua_newtable(L); + + /* @<Process the preamble@>;@/ */ + vf_byte(k); + if (k != pre) + lua_bad_vf("PRE command expected"); + vf_byte(k); + if (k != vf_id) + lua_bad_vf("wrong id byte"); + vf_byte(cmd_length); + + s = xmalloc(cmd_length); + for (k = 1; k <= cmd_length; k++) + vf_byte(s[(k - 1)]); - /* start by creating a table */ - s_top = lua_gettop(L); - lua_newtable(L); - - /* @<Process the preamble@>;@/ */ - vf_byte(k); - if (k != pre) - lua_bad_vf("PRE command expected"); - vf_byte(k); - if (k != vf_id) - lua_bad_vf("wrong id byte"); - vf_byte(cmd_length); - - s = xmalloc(cmd_length); - for (k = 1;k<= cmd_length;k++) - vf_byte(s[(k-1)]); - - lua_pushlstring(L,s,cmd_length); - free(s); - lua_setfield(L,-2,"header"); - - vf_byte(cs.b0); vf_byte(cs.b1); vf_byte(cs.b2); vf_byte(cs.b3); - lua_pushnumber(L, (unsigned long)(cs.b0<<24)+(cs.b1<<16)+(cs.b2<<8)+cs.b3 ); - lua_setfield(L,-2,"checksum"); - - vf_read(4,k); - ds = k /16; - lua_pushinteger(L,ds); - lua_setfield(L,-2,"designsize"); - - - lua_pushstring(L,cnom); - lua_setfield(L,-2,"name"); - - lua_pushinteger(L,atsize); - lua_setfield(L,-2,"size"); - - - /* update_terminal;*/ - vf_z = atsize; - vf_replace_z(); - /* @<Process the font definitions@>;@/ */ - vf_byte(cmd); - lua_newtable(L); - - i = 1; - while ((cmd >= fnt_def1) && (cmd <= fnt_def1 + 3)) { - - lua_newtable(L); - vf_read_u((cmd - fnt_def1 + 1),vf_nf); - vf_nf++; - /* checksum */ - vf_byte(cs.b0); vf_byte(cs.b1); vf_byte(cs.b2); vf_byte(cs.b3); - - vf_read(4,k); - fs = sqxfw(k, atsize); - lua_pushstring(L,"size"); - lua_pushnumber(L,fs); - lua_rawset(L,-3); - - vf_read(4,k); - ds = k / 16; /* dsize, not used */ - - vf_byte(tmp_b0); - vf_byte(tmp_b1); - while (tmp_b0 > 0) { tmp_b0--; vf_byte(k); } /* skip the font path */ - - s = xmalloc(tmp_b1+1); k = 0; - while (tmp_b1-- > 0) - vf_byte(s[k++]); - s[k]=0; - lua_pushstring(L,"name"); - lua_pushstring(L,xstrdup(s)); + lua_pushlstring(L, s, cmd_length); free(s); - lua_rawset(L,-3); - - lua_rawseti(L,-2,vf_nf); - i++; - vf_byte(cmd); - } + lua_setfield(L, -2, "header"); + + vf_byte(cs.b0); + vf_byte(cs.b1); + vf_byte(cs.b2); + vf_byte(cs.b3); + lua_pushnumber(L, + (unsigned long) (cs.b0 << 24) + (cs.b1 << 16) + + (cs.b2 << 8) + cs.b3); + lua_setfield(L, -2, "checksum"); + + vf_read(4, k); + ds = k / 16; + lua_pushinteger(L, ds); + lua_setfield(L, -2, "designsize"); - if (i>1) { - lua_setfield(L,-2,"fonts"); - } else { - lua_pop(L,1); - } - lua_newtable(L); /* 'characters' */ - while (cmd <= long_char) { - /* @<Build a character packet@>;@/ */ - if (cmd == long_char) { - vf_read_u(4,packet_length); - vf_read_u(4,cc); - vf_read(4,tfm_width); - } else { - packet_length = cmd; - vf_byte(cc); - vf_read(3,tfm_width); - } - if (packet_length < 0) - lua_bad_vf("negative packet length"); - - lua_newtable(L); /* for this character */ - - lua_pushnumber(L,tfm_width); - lua_setfield(L,-2,"width"); - - lua_newtable(L); /* for 'commands' */ - - k = 1; vf_nf = 0; - w = 0; x = 0; y = 0; z = 0; - while (packet_length > 0) { - vf_byte(cmd); - decr(packet_length); - - if ((cmd >= set_char_0) && (cmd < set1)) { - if (vf_nf == 0) { - vf_nf = 1; - make_command1("font",vf_nf,k); - } - make_command1("char",cmd,k); - - } else if (((fnt_num_0 <= cmd) && (cmd <= fnt_num_0 + 63)) || - ((fnt1 <= cmd) && (cmd <= fnt1 + 3))) { - if (cmd >= fnt1) { - vf_read_u((cmd - fnt1 + 1),vf_nf); vf_nf++; - packet_length -= (cmd - fnt1 + 1); - } else { - vf_nf = cmd - fnt_num_0 + 1; - } - make_command1("font",vf_nf,k); - } else { - switch (cmd) { - case set_rule: - vf_read(4,h); vf_read(4,v); - make_command2("rule",sqxfw(h,atsize),sqxfw(v,atsize),k); - packet_length -= 8; - break; - case put_rule: - vf_read(4,h); vf_read(4,v); - make_command0("push",k); - make_command2("rule",sqxfw(h,atsize),sqxfw(v,atsize),k); - make_command0("pop",k); - packet_length -= 8; - break; - case set1: - case set2: - case set3: - case set4: - if (vf_nf == 0) { - vf_nf = 1; - make_command1("font",vf_nf,k); - } - vf_read_u((cmd - set1 + 1),i); - make_command1("char",i,k); - packet_length -= (cmd - set1 + 1); - break; - case put1: - case put2: - case put3: - case put4: - if (vf_nf == 0) { - vf_nf = 1; - make_command1("font",vf_nf,k); - } - vf_read_u((cmd - put1 + 1),i); - make_command0("push",k); - make_command1("char",i,k); - make_command0("pop",k); - packet_length -= (cmd - put1 + 1); - break; - case right1: - case right2: - case right3: - case right4: - vf_read((cmd - right1 + 1),i); - make_command1("right",sqxfw(i,atsize),k); - packet_length -= (cmd - right1 + 1); - break; - case w1: - case w2: - case w3: - case w4: - vf_read((cmd - w1 + 1),w); - make_command1("right",sqxfw(w,atsize),k); - packet_length -= (cmd - w1 + 1); - break; - case x1: - case x2: - case x3: - case x4: - vf_read((cmd - x1 + 1),x); - make_command1("right",sqxfw(x,atsize),k); - packet_length -= (cmd - x1 + 1); - break; - case down1: - case down2: - case down3: - case down4: - vf_read((cmd - down1 + 1),i); - make_command1("down",sqxfw(i,atsize),k); - packet_length -= (cmd - down1 + 1); - break; - case y1: - case y2: - case y3: - case y4: - vf_read((cmd - y1 + 1),y); - make_command1("down",sqxfw(y,atsize),k); - packet_length -= (cmd - y1 + 1); - break; - case z1: - case z2: - case z3: - case z4: - vf_read((cmd - z1 + 1),z); - make_command1("down",sqxfw(z,atsize),k); - packet_length -= (cmd - z1 + 1); - break; - case xxx1: - case xxx2: - case xxx3: - case xxx4: - vf_read_u((cmd - xxx1 + 1),cmd_length); - packet_length -= (cmd - xxx1 + 1); - if (cmd_length <= 0) - lua_bad_vf("special of negative length"); - packet_length -= cmd_length; - - s = xmalloc(cmd_length+1); i = 0; - while (cmd_length > 0) { - cmd_length--; - vf_byte(s[i]); - i++; - } - s[i]=0; - make_commands("special",strdup(s),i,k); - free(s); - break; - case w0: - make_command1("right",sqxfw(w,atsize),k); - break; - case x0: - make_command1("right",sqxfw(x,atsize),k); - break; - case y0: - make_command1("down",sqxfw(y,atsize),k); - break; - case z0: - make_command1("down",sqxfw(z,atsize),k); - break; - case nop: - break; - case push: - if (stack_level == vf_stack_size) { - overflow_string("virtual font stack size", vf_stack_size); - } else { - vf_stack[stack_level].stack_w = w; - vf_stack[stack_level].stack_x = x; - vf_stack[stack_level].stack_y = y; - vf_stack[stack_level].stack_z = z; - incr(stack_level); - make_command0("push",k); - } - break; - case pop: - if (stack_level == 0) { - lua_bad_vf("more POPs than PUSHs in character"); - } else { - decr(stack_level); - w = vf_stack[stack_level].stack_w; - x = vf_stack[stack_level].stack_x; - y = vf_stack[stack_level].stack_y; - z = vf_stack[stack_level].stack_z; - make_command0("pop",k); - } - break; - default: - lua_bad_vf("improver DVI command"); - } - } - } - /* signal end of packet */ - lua_setfield(L,-2,"commands"); + lua_pushstring(L, cnom); + lua_setfield(L, -2, "name"); - if (stack_level != 0) - lua_bad_vf("more PUSHs than POPs in character packet"); - if (packet_length != 0) - lua_bad_vf("invalid packet length or DVI command in packet"); + lua_pushinteger(L, atsize); + lua_setfield(L, -2, "size"); - lua_rawseti(L,-2,cc); + /* update_terminal; */ + vf_z = atsize; + vf_replace_z(); + /* @<Process the font definitions@>;@/ */ vf_byte(cmd); - } - lua_setfield(L,-2,"characters"); + lua_newtable(L); + + i = 1; + while ((cmd >= fnt_def1) && (cmd <= fnt_def1 + 3)) { + + lua_newtable(L); + vf_read_u((cmd - fnt_def1 + 1), vf_nf); + vf_nf++; + /* checksum */ + vf_byte(cs.b0); + vf_byte(cs.b1); + vf_byte(cs.b2); + vf_byte(cs.b3); + + vf_read(4, k); + fs = sqxfw(k, atsize); + lua_pushstring(L, "size"); + lua_pushnumber(L, fs); + lua_rawset(L, -3); + + vf_read(4, k); + ds = k / 16; /* dsize, not used */ + + vf_byte(tmp_b0); + vf_byte(tmp_b1); + while (tmp_b0 > 0) { + tmp_b0--; + vf_byte(k); + } /* skip the font path */ + + s = xmalloc(tmp_b1 + 1); + k = 0; + while (tmp_b1-- > 0) + vf_byte(s[k++]); + s[k] = 0; + lua_pushstring(L, "name"); + lua_pushstring(L, xstrdup(s)); + free(s); + lua_rawset(L, -3); + + lua_rawseti(L, -2, vf_nf); + i++; + vf_byte(cmd); + } - if (cmd != post) - lua_bad_vf("POST command expected"); - xfree(vf_buffer); - return 1; -} + if (i > 1) { + lua_setfield(L, -2, "fonts"); + } else { + lua_pop(L, 1); + } + lua_newtable(L); /* 'characters' */ + while (cmd <= long_char) { + /* @<Build a character packet@>;@/ */ + if (cmd == long_char) { + vf_read_u(4, packet_length); + vf_read_u(4, cc); + vf_read(4, tfm_width); + } else { + packet_length = cmd; + vf_byte(cc); + vf_read(3, tfm_width); + } + if (packet_length < 0) + lua_bad_vf("negative packet length"); + + lua_newtable(L); /* for this character */ + + lua_pushnumber(L, tfm_width); + lua_setfield(L, -2, "width"); + + lua_newtable(L); /* for 'commands' */ + + k = 1; + vf_nf = 0; + w = 0; + x = 0; + y = 0; + z = 0; + while (packet_length > 0) { + vf_byte(cmd); + decr(packet_length); + + if ((cmd >= set_char_0) && (cmd < set1)) { + if (vf_nf == 0) { + vf_nf = 1; + make_command1("font", vf_nf, k); + } + make_command1("char", cmd, k); + + } else if (((fnt_num_0 <= cmd) && (cmd <= fnt_num_0 + 63)) || + ((fnt1 <= cmd) && (cmd <= fnt1 + 3))) { + if (cmd >= fnt1) { + vf_read_u((cmd - fnt1 + 1), vf_nf); + vf_nf++; + packet_length -= (cmd - fnt1 + 1); + } else { + vf_nf = cmd - fnt_num_0 + 1; + } + make_command1("font", vf_nf, k); + } else { + switch (cmd) { + case set_rule: + vf_read(4, h); + vf_read(4, v); + make_command2("rule", sqxfw(h, atsize), sqxfw(v, atsize), + k); + packet_length -= 8; + break; + case put_rule: + vf_read(4, h); + vf_read(4, v); + make_command0("push", k); + make_command2("rule", sqxfw(h, atsize), sqxfw(v, atsize), + k); + make_command0("pop", k); + packet_length -= 8; + break; + case set1: + case set2: + case set3: + case set4: + if (vf_nf == 0) { + vf_nf = 1; + make_command1("font", vf_nf, k); + } + vf_read_u((cmd - set1 + 1), i); + make_command1("char", i, k); + packet_length -= (cmd - set1 + 1); + break; + case put1: + case put2: + case put3: + case put4: + if (vf_nf == 0) { + vf_nf = 1; + make_command1("font", vf_nf, k); + } + vf_read_u((cmd - put1 + 1), i); + make_command0("push", k); + make_command1("char", i, k); + make_command0("pop", k); + packet_length -= (cmd - put1 + 1); + break; + case right1: + case right2: + case right3: + case right4: + vf_read((cmd - right1 + 1), i); + make_command1("right", sqxfw(i, atsize), k); + packet_length -= (cmd - right1 + 1); + break; + case w1: + case w2: + case w3: + case w4: + vf_read((cmd - w1 + 1), w); + make_command1("right", sqxfw(w, atsize), k); + packet_length -= (cmd - w1 + 1); + break; + case x1: + case x2: + case x3: + case x4: + vf_read((cmd - x1 + 1), x); + make_command1("right", sqxfw(x, atsize), k); + packet_length -= (cmd - x1 + 1); + break; + case down1: + case down2: + case down3: + case down4: + vf_read((cmd - down1 + 1), i); + make_command1("down", sqxfw(i, atsize), k); + packet_length -= (cmd - down1 + 1); + break; + case y1: + case y2: + case y3: + case y4: + vf_read((cmd - y1 + 1), y); + make_command1("down", sqxfw(y, atsize), k); + packet_length -= (cmd - y1 + 1); + break; + case z1: + case z2: + case z3: + case z4: + vf_read((cmd - z1 + 1), z); + make_command1("down", sqxfw(z, atsize), k); + packet_length -= (cmd - z1 + 1); + break; + case xxx1: + case xxx2: + case xxx3: + case xxx4: + vf_read_u((cmd - xxx1 + 1), cmd_length); + packet_length -= (cmd - xxx1 + 1); + if (cmd_length <= 0) + lua_bad_vf("special of negative length"); + packet_length -= cmd_length; + + s = xmalloc(cmd_length + 1); + i = 0; + while (cmd_length > 0) { + cmd_length--; + vf_byte(s[i]); + i++; + } + s[i] = 0; + make_commands("special", strdup(s), i, k); + free(s); + break; + case w0: + make_command1("right", sqxfw(w, atsize), k); + break; + case x0: + make_command1("right", sqxfw(x, atsize), k); + break; + case y0: + make_command1("down", sqxfw(y, atsize), k); + break; + case z0: + make_command1("down", sqxfw(z, atsize), k); + break; + case nop: + break; + case push: + if (stack_level == vf_stack_size) { + overflow_string("virtual font stack size", + vf_stack_size); + } else { + vf_stack[stack_level].stack_w = w; + vf_stack[stack_level].stack_x = x; + vf_stack[stack_level].stack_y = y; + vf_stack[stack_level].stack_z = z; + incr(stack_level); + make_command0("push", k); + } + break; + case pop: + if (stack_level == 0) { + lua_bad_vf("more POPs than PUSHs in character"); + } else { + decr(stack_level); + w = vf_stack[stack_level].stack_w; + x = vf_stack[stack_level].stack_x; + y = vf_stack[stack_level].stack_y; + z = vf_stack[stack_level].stack_z; + make_command0("pop", k); + } + break; + default: + lua_bad_vf("improver DVI command"); + } + } + } + /* signal end of packet */ + lua_setfield(L, -2, "commands"); + + if (stack_level != 0) + lua_bad_vf("more PUSHs than POPs in character packet"); + if (packet_length != 0) + lua_bad_vf("invalid packet length or DVI command in packet"); + + lua_rawseti(L, -2, cc); + + vf_byte(cmd); + } + lua_setfield(L, -2, "characters"); -extern void replace_packet_fonts(internal_font_number f, integer *old_fontid, integer *new_fontid, int count) ; -extern integer *packet_local_fonts(internal_font_number f, integer *num); -extern internal_font_number auto_expand_font (internal_font_number f, integer e) ; + if (cmd != post) + lua_bad_vf("POST command expected"); + xfree(vf_buffer); + return 1; +} /* This function is called from |do_vf|, and fixes up the virtual data inside an auto-expanded virtual font */ -boolean -auto_expand_vf(internal_font_number f) { - - internal_font_number bf; - integer e, k; - integer *vf_old_fonts, *vf_new_fonts; - integer num = 0; - - if ((! pdf_font_auto_expand(f)) || (pdf_font_blink(f) == null_font)) - return false ; /* not an auto-expanded font */ - bf = pdf_font_blink(f); - - if (font_type(bf) != virtual_font_type) - return false; /* not a virtual font */ - - e = pdf_font_expand_ratio(f); - - vf_old_fonts = packet_local_fonts(bf,&num); - if (num>0) { - vf_new_fonts = xmalloc(num*sizeof(integer)); - for (k=0;k<num;k++) { - vf_new_fonts[k] = auto_expand_font(vf_old_fonts[k], e); - copy_expand_params(vf_new_fonts[k], vf_old_fonts[k], e); +boolean auto_expand_vf(internal_font_number f) +{ + + internal_font_number bf; + integer e, k; + integer *vf_old_fonts, *vf_new_fonts; + integer num = 0; + + if ((!pdf_font_auto_expand(f)) || (pdf_font_blink(f) == null_font)) + return false; /* not an auto-expanded font */ + bf = pdf_font_blink(f); + + if (font_type(bf) != virtual_font_type) + return false; /* not a virtual font */ + + e = pdf_font_expand_ratio(f); + + vf_old_fonts = packet_local_fonts(bf, &num); + if (num > 0) { + vf_new_fonts = xmalloc(num * sizeof(integer)); + for (k = 0; k < num; k++) { + vf_new_fonts[k] = auto_expand_font(vf_old_fonts[k], e); + copy_expand_params(vf_new_fonts[k], vf_old_fonts[k], e); + } + replace_packet_fonts(f, vf_old_fonts, vf_new_fonts, num); + xfree(vf_new_fonts); + xfree(vf_old_fonts); } - replace_packet_fonts(f,vf_old_fonts,vf_new_fonts,num); - xfree(vf_new_fonts); - xfree(vf_old_fonts); - } - set_font_type(f,virtual_font_type); - return true; + set_font_type(f, virtual_font_type); + return true; } /* this function is not always safe, because it needs makecstring() */ -str_number -expand_font_name (internal_font_number f, integer e) { - int old_setting; - old_setting=selector; - selector=new_string; - print_string(font_name(f)); - if (e > 0) { - print_char('+'); - } - print_int(e); - selector=old_setting; - return make_string(); +str_number expand_font_name(internal_font_number f, integer e) +{ + int old_setting; + old_setting = selector; + selector = new_string; + print_string(font_name(f)); + if (e > 0) { + print_char('+'); + } + print_int(e); + selector = old_setting; + return make_string(); } -internal_font_number -auto_expand_font (internal_font_number f, integer e) { - internal_font_number k; - kerninfo *krn; - charinfo *co, *ci; - char *fn; - integer i; - scaled w; - k = copy_font(f); - i = strlen(font_name(f))+12; - fn = xmalloc(i); - snprintf(fn,i,"%s%s%d",font_name(f),(e>0 ? "+" : ""), (int)e); - set_font_name(k,fn); - for (i = font_bc(k);i<=font_ec(k);i++) { - if (char_exists(k,i)) { - co = get_charinfo(k,i); - w = round_xn_over_d(char_width(f,i), 1000 + e, 1000); - set_charinfo_width (co, w); - w = round_xn_over_d(char_italic(f,i), 1000 + e, 1000); - set_charinfo_italic(co, w); - krn = get_charinfo_kerns(co); - if (krn != NULL) { - while (!kern_end((*krn))) { - kern_kern(*krn) = round_xn_over_d(kern_kern(*krn), 1000 + e, 1000); - krn++; - } - } +internal_font_number auto_expand_font(internal_font_number f, integer e) +{ + internal_font_number k; + kerninfo *krn; + charinfo *co; + char *fn; + integer i; + scaled w; + k = copy_font(f); + i = strlen(font_name(f)) + 12; + fn = xmalloc(i); + snprintf(fn, i, "%s%s%d", font_name(f), (e > 0 ? "+" : ""), (int) e); + set_font_name(k, fn); + for (i = font_bc(k); i <= font_ec(k); i++) { + if (char_exists(k, i)) { + co = get_charinfo(k, i); + w = round_xn_over_d(char_width(f, i), 1000 + e, 1000); + set_charinfo_width(co, w); + w = round_xn_over_d(char_italic(f, i), 1000 + e, 1000); + set_charinfo_italic(co, w); + krn = get_charinfo_kerns(co); + if (krn != NULL) { + while (!kern_end((*krn))) { + kern_kern(*krn) = + round_xn_over_d(kern_kern(*krn), 1000 + e, 1000); + krn++; + } + } + } } - } - return k; + return k; } -void -vf_expand_local_fonts(internal_font_number f) { - internal_font_number lf; - integer k, num; - integer *vf_old_fonts; - pdfassert(font_type(f) == virtual_font_type); - num = 0; - vf_old_fonts = packet_local_fonts(f,&num); - if (num>0) { - for (k = 0;k<num;k++) { - lf = vf_old_fonts[k]; - set_expand_params(lf, pdf_font_auto_expand(f), - pdf_font_expand_ratio(pdf_font_stretch(f)), - -pdf_font_expand_ratio(pdf_font_shrink(f)), - pdf_font_step(f), pdf_font_expand_ratio(f)); - if (font_type(lf) == virtual_font_type) - vf_expand_local_fonts(lf); +void vf_expand_local_fonts(internal_font_number f) +{ + internal_font_number lf; + integer k, num; + integer *vf_old_fonts; + pdfassert(font_type(f) == virtual_font_type); + num = 0; + vf_old_fonts = packet_local_fonts(f, &num); + if (num > 0) { + for (k = 0; k < num; k++) { + lf = vf_old_fonts[k]; + set_expand_params(lf, pdf_font_auto_expand(f), + pdf_font_expand_ratio(pdf_font_stretch(f)), + -pdf_font_expand_ratio(pdf_font_shrink(f)), + pdf_font_step(f), pdf_font_expand_ratio(f)); + if (font_type(lf) == virtual_font_type) + vf_expand_local_fonts(lf); + } + xfree(vf_old_fonts); } - xfree(vf_old_fonts); - } } -internal_font_number -letter_space_font (halfword u, internal_font_number f, integer e) { - internal_font_number k; - scaled w, r; +internal_font_number +letter_space_font(halfword u, internal_font_number f, integer e) +{ + internal_font_number k; + scaled w, r; - char *new_font_name; - integer vf_z; - integer vf_alpha; - integer vf_beta; - memory_word tmp_w; /* accumulator */ + char *new_font_name; + integer vf_z; + integer vf_alpha; + integer vf_beta; + memory_word tmp_w; /* accumulator */ - /* read a new font and expand the character widths */ - k = read_font_info(u, tex_font_name(f), get_nullstr(), font_size(f), font_natural_dir(f)); - set_no_ligatures(k); /* disable ligatures for letter-spaced fonts */ + /* read a new font and expand the character widths */ + k = read_font_info(u, tex_font_name(f), font_size(f), font_natural_dir(f)); + set_no_ligatures(k); /* disable ligatures for letter-spaced fonts */ /* for (i = 0;i <= font_widths(k);i++) { set_font_width(k,i,font_width(f,i)+round_xn_over_d(quad(k), e, 1000)); } */ - /* append eg '+100ls' to font name */ - new_font_name = xmalloc(strlen(font_name(k)) + 8); /* |abs(e) <= 1000| */ - if (e > 0) { - sprintf(new_font_name,"%s+%ils",font_name(k),(int)e); - } else { - /* minus from %i */ - sprintf(new_font_name,"%s%ils",font_name(k),(int)e); - } - set_font_name(k, new_font_name); - - /* create the corresponding virtual font */ - set_font_type(k,virtual_font_type); - - vf_z = font_size(f); - vf_replace_z(); - w = round_xn_over_d(quad(f), e, 2000); - if (w > 0) { - tmp_b0 = 0; - } else { - tmp_b0 = 255; - w = vf_alpha + w; - } - r = w*vf_beta; - tmp_b1 = r / vf_z; - r = r % vf_z; - if (r == 0) { - tmp_b2 = 0; - } else { - r = r * 256; - tmp_b2 = r / vf_z; + /* append eg '+100ls' to font name */ + new_font_name = xmalloc(strlen(font_name(k)) + 8); /* |abs(e) <= 1000| */ + if (e > 0) { + sprintf(new_font_name, "%s+%ils", font_name(k), (int) e); + } else { + /* minus from %i */ + sprintf(new_font_name, "%s%ils", font_name(k), (int) e); + } + set_font_name(k, new_font_name); + + /* create the corresponding virtual font */ + set_font_type(k, virtual_font_type); + + vf_z = font_size(f); + vf_replace_z(); + w = round_xn_over_d(quad(f), e, 2000); + if (w > 0) { + tmp_b0 = 0; + } else { + tmp_b0 = 255; + w = vf_alpha + w; + } + r = w * vf_beta; + tmp_b1 = r / vf_z; r = r % vf_z; - } - if (r == 0) { - tmp_b3 = 0; - } else { - r = r * 256; - tmp_b3 = r / vf_z; - } - /* - vf_packet_base[k] = new_vf_packet(k); - - for (c=font_bc(k);c<=font_ec(k);c++) { - string_room(17); - append_fnt_set(f); - append_packet(right1 + 3); - append_packet(tmp_b0); - append_packet(tmp_b1); - append_packet(tmp_b2); - append_packet(tmp_b3); - - append_packet(set1); - append_packet(c); - - append_packet(right1 + 3); - append_packet(tmp_b0); - append_packet(tmp_b1); - append_packet(tmp_b2); - append_packet(tmp_b3); - s = make_string(); - store_packet(k, c, s); - flush_str(s); - } -*/ - return k; + if (r == 0) { + tmp_b2 = 0; + } else { + r = r * 256; + tmp_b2 = r / vf_z; + r = r % vf_z; + } + if (r == 0) { + tmp_b3 = 0; + } else { + r = r * 256; + tmp_b3 = r / vf_z; + } + /* + vf_packet_base[k] = new_vf_packet(k); + + for (c=font_bc(k);c<=font_ec(k);c++) { + string_room(17); + append_fnt_set(f); + append_packet(right1 + 3); + append_packet(tmp_b0); + append_packet(tmp_b1); + append_packet(tmp_b2); + append_packet(tmp_b3); + + append_packet(set1); + append_packet(c); + + append_packet(right1 + 3); + append_packet(tmp_b0); + append_packet(tmp_b1); + append_packet(tmp_b2); + append_packet(tmp_b3); + s = make_string(); + store_packet(k, c, s); + flush_str(s); + } + */ + return k; } +/* the fontname has [+-]\d+ls at the end */ + +boolean is_letterspaced_font(internal_font_number f) +{ + char *i, *j; + if (font_type(f) != virtual_font_type) + return false; + j = font_name(f); + i = j + strlen(j); + if ((*(i - 1) != 'l') || (*i != 's')) + return false; + i = i - 2; + while (i >= j) { + if ((*i < '0') || (*i > '9')) + break; + i--; + } + if (i < j) + return false; + if ((*i != '+') && (*i != '-')) + return false; + return true; +} +/* TODO */ + +internal_font_number copy_font_info(internal_font_number f) +{ + return copy_font(f); +} diff --git a/Build/source/texk/web2c/luatexdir/font/writecff.c b/Build/source/texk/web2c/luatexdir/font/writecff.c index 69c35c6950e..274c4ad1567 100644 --- a/Build/source/texk/web2c/luatexdir/font/writecff.c +++ b/Build/source/texk/web2c/luatexdir/font/writecff.c @@ -1,29 +1,29 @@ -/* -Copyright (c) 2007 Taco Hoekwater, taco@luatex.org - -This file is part of luaTeX. +/* writecff.c + + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -luaTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + This file is part of LuaTeX. -luaTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -You should have received a copy of the GNU General Public License -along with luaTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -$Id: writecff.c 1021 2008-02-14 10:24:34Z taco $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" #include "writecff.h" +static const char _svn_version[] = + "$Id: writecff.c 1592 2008-11-28 13:23:51Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/writecff.c $"; + #define get_offset(s,n) get_unsigned(s, (n)) #define get_card8(a) a->stream[a->offset++] #define get_card16(a) get_unsigned(a,2) @@ -37,12 +37,12 @@ $Id: writecff.c 1021 2008-02-14 10:24:34Z taco $ static char work_buffer[WORK_BUFFER_SIZE]; -static unsigned long get_unsigned (cff_font *cff, int n) +static unsigned long get_unsigned(cff_font * cff, int n) { - unsigned long v = 0; - while (n-- > 0) - v = v*256 + get_card8(cff); - return v; + unsigned long v = 0; + while (n-- > 0) + v = v * 256 + get_card8(cff); + return v; } #define CFF_ERROR pdftex_fail @@ -50,421 +50,454 @@ static unsigned long get_unsigned (cff_font *cff, int n) const char *const cff_stdstr[CFF_STDSTR_MAX] = { - ".notdef", "space", "exclam", "quotedbl", "numbersign", - "dollar", "percent", "ampersand", "quoteright", "parenleft", - "parenright", "asterisk", "plus", "comma", "hyphen", - "period", "slash", "zero", "one", "two", - "three", "four", "five", "six", "seven", - "eight", "nine", "colon", "semicolon", "less", - "equal", "greater", "question", "at", "A", - "B", "C", "D", "E", "F", - "G", "H", "I", "J", "K", - "L", "M", "N", "O", "P", - "Q", "R", "S", "T", "U", - "V", "W", "X", "Y", "Z", - "bracketleft", "backslash", "bracketright", "asciicircum", "underscore", - "quoteleft", "a", "b", "c", "d", - "e", "f", "g", "h", "i", - "j", "k", "l", "m", "n", - "o", "p", "q", "r", "s", - "t", "u", "v", "w", "x", - "y", "z", "braceleft", "bar", "braceright", - "asciitilde", "exclamdown", "cent", "sterling", "fraction", - "yen", "florin", "section", "currency", "quotesingle", - "quotedblleft", "guillemotleft", "guilsinglleft", "guilsinglright", "fi", - "fl", "endash", "dagger", "daggerdbl", "periodcentered", - "paragraph", "bullet", "quotesinglbase", "quotedblbase", "quotedblright", - "guillemotright", "ellipsis", "perthousand", "questiondown", "grave", - "acute", "circumflex", "tilde", "macron", "breve", - "dotaccent", "dieresis", "ring", "cedilla", "hungarumlaut", - "ogonek", "caron", "emdash", "AE", "ordfeminine", - "Lslash", "Oslash", "OE", "ordmasculine", "ae", - "dotlessi", "lslash", "oslash", "oe", "germandbls", - "onesuperior", "logicalnot", "mu", "trademark", "Eth", - "onehalf", "plusminus", "Thorn", "onequarter", "divide", - "brokenbar", "degree", "thorn", "threequarters", "twosuperior", - "registered", "minus", "eth", "multiply", "threesuperior", - "copyright", "Aacute", "Acircumflex", "Adieresis", "Agrave", - "Aring", "Atilde", "Ccedilla", "Eacute", "Ecircumflex", - "Edieresis", "Egrave", "Iacute", "Icircumflex", "Idieresis", - "Igrave", "Ntilde", "Oacute", "Ocircumflex", "Odieresis", - "Ograve", "Otilde", "Scaron", "Uacute", "Ucircumflex", - "Udieresis", "Ugrave", "Yacute", "Ydieresis", "Zcaron", - "aacute", "acircumflex", "adieresis", "agrave", "aring", - "atilde", "ccedilla", "eacute", "ecircumflex", "edieresis", - "egrave", "iacute", "icircumflex", "idieresis", "igrave", - "ntilde", "oacute", "ocircumflex", "odieresis", "ograve", - "otilde", "scaron", "uacute", "ucircumflex", "udieresis", - "ugrave", "yacute", "ydieresis", "zcaron", "exclamsmall", - "Hungarumlautsmall", "dollaroldstyle", "dollarsuperior", "ampersandsmall", "Acutesmall", - "parenleftsuperior", "parenrightsuperior", "twodotenleader", "onedotenleader", "zerooldstyle", - "oneoldstyle", "twooldstyle", "threeoldstyle", "fouroldstyle", "fiveoldstyle", - "sixoldstyle", "sevenoldstyle", "eightoldstyle", "nineoldstyle", "commasuperior", - "threequartersemdash", "periodsuperior", "questionsmall", "asuperior", "bsuperior", - "centsuperior", "dsuperior", "esuperior", "isuperior", "lsuperior", - "msuperior", "nsuperior", "osuperior", "rsuperior", "ssuperior", - "tsuperior", "ff", "ffi", "ffl", "parenleftinferior", - "parenrightinferior", "Circumflexsmall", "hyphensuperior", "Gravesmall", "Asmall", - "Bsmall", "Csmall", "Dsmall", "Esmall", "Fsmall", - "Gsmall", "Hsmall", "Ismall", "Jsmall", "Ksmall", - "Lsmall", "Msmall", "Nsmall", "Osmall", "Psmall", - "Qsmall", "Rsmall", "Ssmall", "Tsmall", "Usmall", - "Vsmall", "Wsmall", "Xsmall", "Ysmall", "Zsmall", - "colonmonetary", "onefitted", "rupiah", "Tildesmall", "exclamdownsmall", - "centoldstyle", "Lslashsmall", "Scaronsmall", "Zcaronsmall", "Dieresissmall", - "Brevesmall", "Caronsmall", "Dotaccentsmall", "Macronsmall", "figuredash", - "hypheninferior", "Ogoneksmall", "Ringsmall", "Cedillasmall", "questiondownsmall", - "oneeighth", "threeeighths", "fiveeighths", "seveneighths", "onethird", - "twothirds", "zerosuperior", "foursuperior", "fivesuperior", "sixsuperior", - "sevensuperior", "eightsuperior", "ninesuperior", "zeroinferior", "oneinferior", - "twoinferior", "threeinferior", "fourinferior", "fiveinferior", "sixinferior", - "seveninferior", "eightinferior", "nineinferior", "centinferior", "dollarinferior", - "periodinferior", "commainferior", "Agravesmall", "Aacutesmall", "Acircumflexsmall", - "Atildesmall", "Adieresissmall", "Aringsmall", "AEsmall", "Ccedillasmall", - "Egravesmall", "Eacutesmall", "Ecircumflexsmall", "Edieresissmall", "Igravesmall", - "Iacutesmall", "Icircumflexsmall", "Idieresissmall", "Ethsmall", "Ntildesmall", - "Ogravesmall", "Oacutesmall", "Ocircumflexsmall", "Otildesmall", "Odieresissmall", - "OEsmall", "Oslashsmall", "Ugravesmall", "Uacutesmall", "Ucircumflexsmall", - "Udieresissmall", "Yacutesmall", "Thornsmall", "Ydieresissmall", - "001.000", "001.001", "001.002", "001.003", - "Black", "Bold", "Book", "Light", "Medium", "Regular", "Roman", "Semibold" + ".notdef", "space", "exclam", "quotedbl", "numbersign", + "dollar", "percent", "ampersand", "quoteright", "parenleft", + "parenright", "asterisk", "plus", "comma", "hyphen", + "period", "slash", "zero", "one", "two", + "three", "four", "five", "six", "seven", + "eight", "nine", "colon", "semicolon", "less", + "equal", "greater", "question", "at", "A", + "B", "C", "D", "E", "F", + "G", "H", "I", "J", "K", + "L", "M", "N", "O", "P", + "Q", "R", "S", "T", "U", + "V", "W", "X", "Y", "Z", + "bracketleft", "backslash", "bracketright", "asciicircum", "underscore", + "quoteleft", "a", "b", "c", "d", + "e", "f", "g", "h", "i", + "j", "k", "l", "m", "n", + "o", "p", "q", "r", "s", + "t", "u", "v", "w", "x", + "y", "z", "braceleft", "bar", "braceright", + "asciitilde", "exclamdown", "cent", "sterling", "fraction", + "yen", "florin", "section", "currency", "quotesingle", + "quotedblleft", "guillemotleft", "guilsinglleft", "guilsinglright", "fi", + "fl", "endash", "dagger", "daggerdbl", "periodcentered", + "paragraph", "bullet", "quotesinglbase", "quotedblbase", "quotedblright", + "guillemotright", "ellipsis", "perthousand", "questiondown", "grave", + "acute", "circumflex", "tilde", "macron", "breve", + "dotaccent", "dieresis", "ring", "cedilla", "hungarumlaut", + "ogonek", "caron", "emdash", "AE", "ordfeminine", + "Lslash", "Oslash", "OE", "ordmasculine", "ae", + "dotlessi", "lslash", "oslash", "oe", "germandbls", + "onesuperior", "logicalnot", "mu", "trademark", "Eth", + "onehalf", "plusminus", "Thorn", "onequarter", "divide", + "brokenbar", "degree", "thorn", "threequarters", "twosuperior", + "registered", "minus", "eth", "multiply", "threesuperior", + "copyright", "Aacute", "Acircumflex", "Adieresis", "Agrave", + "Aring", "Atilde", "Ccedilla", "Eacute", "Ecircumflex", + "Edieresis", "Egrave", "Iacute", "Icircumflex", "Idieresis", + "Igrave", "Ntilde", "Oacute", "Ocircumflex", "Odieresis", + "Ograve", "Otilde", "Scaron", "Uacute", "Ucircumflex", + "Udieresis", "Ugrave", "Yacute", "Ydieresis", "Zcaron", + "aacute", "acircumflex", "adieresis", "agrave", "aring", + "atilde", "ccedilla", "eacute", "ecircumflex", "edieresis", + "egrave", "iacute", "icircumflex", "idieresis", "igrave", + "ntilde", "oacute", "ocircumflex", "odieresis", "ograve", + "otilde", "scaron", "uacute", "ucircumflex", "udieresis", + "ugrave", "yacute", "ydieresis", "zcaron", "exclamsmall", + "Hungarumlautsmall", "dollaroldstyle", "dollarsuperior", "ampersandsmall", + "Acutesmall", + "parenleftsuperior", "parenrightsuperior", "twodotenleader", + "onedotenleader", "zerooldstyle", + "oneoldstyle", "twooldstyle", "threeoldstyle", "fouroldstyle", + "fiveoldstyle", + "sixoldstyle", "sevenoldstyle", "eightoldstyle", "nineoldstyle", + "commasuperior", + "threequartersemdash", "periodsuperior", "questionsmall", "asuperior", + "bsuperior", + "centsuperior", "dsuperior", "esuperior", "isuperior", "lsuperior", + "msuperior", "nsuperior", "osuperior", "rsuperior", "ssuperior", + "tsuperior", "ff", "ffi", "ffl", "parenleftinferior", + "parenrightinferior", "Circumflexsmall", "hyphensuperior", "Gravesmall", + "Asmall", + "Bsmall", "Csmall", "Dsmall", "Esmall", "Fsmall", + "Gsmall", "Hsmall", "Ismall", "Jsmall", "Ksmall", + "Lsmall", "Msmall", "Nsmall", "Osmall", "Psmall", + "Qsmall", "Rsmall", "Ssmall", "Tsmall", "Usmall", + "Vsmall", "Wsmall", "Xsmall", "Ysmall", "Zsmall", + "colonmonetary", "onefitted", "rupiah", "Tildesmall", "exclamdownsmall", + "centoldstyle", "Lslashsmall", "Scaronsmall", "Zcaronsmall", + "Dieresissmall", + "Brevesmall", "Caronsmall", "Dotaccentsmall", "Macronsmall", "figuredash", + "hypheninferior", "Ogoneksmall", "Ringsmall", "Cedillasmall", + "questiondownsmall", + "oneeighth", "threeeighths", "fiveeighths", "seveneighths", "onethird", + "twothirds", "zerosuperior", "foursuperior", "fivesuperior", "sixsuperior", + "sevensuperior", "eightsuperior", "ninesuperior", "zeroinferior", + "oneinferior", + "twoinferior", "threeinferior", "fourinferior", "fiveinferior", + "sixinferior", + "seveninferior", "eightinferior", "nineinferior", "centinferior", + "dollarinferior", + "periodinferior", "commainferior", "Agravesmall", "Aacutesmall", + "Acircumflexsmall", + "Atildesmall", "Adieresissmall", "Aringsmall", "AEsmall", "Ccedillasmall", + "Egravesmall", "Eacutesmall", "Ecircumflexsmall", "Edieresissmall", + "Igravesmall", + "Iacutesmall", "Icircumflexsmall", "Idieresissmall", "Ethsmall", + "Ntildesmall", + "Ogravesmall", "Oacutesmall", "Ocircumflexsmall", "Otildesmall", + "Odieresissmall", + "OEsmall", "Oslashsmall", "Ugravesmall", "Uacutesmall", "Ucircumflexsmall", + "Udieresissmall", "Yacutesmall", "Thornsmall", "Ydieresissmall", + "001.000", "001.001", "001.002", "001.003", + "Black", "Bold", "Book", "Light", "Medium", "Regular", "Roman", "Semibold" }; /* Only read header part but not body */ -cff_index * -cff_get_index_header (cff_font *cff) +cff_index *cff_get_index_header(cff_font * cff) { - cff_index *idx; - card16 i, count; + cff_index *idx; + card16 i, count; - idx = xcalloc(1, sizeof(cff_index)); + idx = xcalloc(1, sizeof(cff_index)); - idx->count = count = get_card16(cff); - if (count > 0) { - idx->offsize = get_card8(cff); - if (idx->offsize < 1 || idx->offsize > 4) - CFF_ERROR("invalid offsize data"); + idx->count = count = get_card16(cff); + if (count > 0) { + idx->offsize = get_card8(cff); + if (idx->offsize < 1 || idx->offsize > 4) + CFF_ERROR("invalid offsize data"); - idx->offset = xcalloc(count+1, sizeof(l_offset)); - for (i=0;i<count+1;i++) { - (idx->offset)[i] = get_offset(cff, idx->offsize); - } + idx->offset = xcalloc(count + 1, sizeof(l_offset)); + for (i = 0; i < count + 1; i++) { + (idx->offset)[i] = get_offset(cff, idx->offsize); + } - if (idx->offset[0] != 1) - CFF_ERROR("cff_get_index(): invalid index data"); + if (idx->offset[0] != 1) + CFF_ERROR("cff_get_index(): invalid index data"); - idx->data = NULL; - } else { - idx->offsize = 0; - idx->offset = NULL; - idx->data = NULL; - } + idx->data = NULL; + } else { + idx->offsize = 0; + idx->offset = NULL; + idx->data = NULL; + } - return idx; + return idx; } -cff_index * -cff_get_index (cff_font *cff) +cff_index *cff_get_index(cff_font * cff) { - cff_index *idx; - card16 i, count; - long length; + cff_index *idx; + card16 i, count; + long length; - idx = xcalloc(1,sizeof(cff_index)); + idx = xcalloc(1, sizeof(cff_index)); - idx->count = count = get_card16(cff); - if (count > 0) { - idx->offsize = get_card8(cff); - if (idx->offsize < 1 || idx->offsize > 4) - CFF_ERROR("invalid offsize data"); + idx->count = count = get_card16(cff); + if (count > 0) { + idx->offsize = get_card8(cff); + if (idx->offsize < 1 || idx->offsize > 4) + CFF_ERROR("invalid offsize data"); - idx->offset = xcalloc((count + 1),sizeof(l_offset)); - for (i = 0 ; i < count + 1; i++) { - idx->offset[i] = get_offset(cff, idx->offsize); - } + idx->offset = xcalloc((count + 1), sizeof(l_offset)); + for (i = 0; i < count + 1; i++) { + idx->offset[i] = get_offset(cff, idx->offsize); + } - if (idx->offset[0] != 1) - CFF_ERROR("Invalid CFF Index offset data"); + if (idx->offset[0] != 1) + CFF_ERROR("Invalid CFF Index offset data"); - length = idx->offset[count] - idx->offset[0]; + length = idx->offset[count] - idx->offset[0]; - idx->data = xcalloc(length,sizeof(card8)); - memcpy(idx->data,&cff->stream[cff->offset],length); - cff->offset += length; + idx->data = xcalloc(length, sizeof(card8)); + memcpy(idx->data, &cff->stream[cff->offset], length); + cff->offset += length; - } else { - idx->offsize = 0; - idx->offset = NULL; - idx->data = NULL; - } - return idx; + } else { + idx->offsize = 0; + idx->offset = NULL; + idx->data = NULL; + } + return idx; } -long -cff_pack_index (cff_index *idx, card8 *dest, long destlen) +long cff_pack_index(cff_index * idx, card8 * dest, long destlen) { - long len = 0; - unsigned long datalen; - card16 i; + long len = 0; + unsigned long datalen; + card16 i; - if (idx->count < 1) { - if (destlen < 2) - CFF_ERROR("Not enough space available..."); - memset(dest, 0, 2); - return 2; - } + if (idx->count < 1) { + if (destlen < 2) + CFF_ERROR("Not enough space available..."); + memset(dest, 0, 2); + return 2; + } - len = cff_index_size(idx); - datalen = idx->offset[idx->count] - 1; + len = cff_index_size(idx); + datalen = idx->offset[idx->count] - 1; - if (destlen < len) - CFF_ERROR("Not enough space available..."); + if (destlen < len) + CFF_ERROR("Not enough space available..."); - *(dest++) = (idx->count >> 8) & 0xff; - *(dest++) = idx->count & 0xff; + *(dest++) = (idx->count >> 8) & 0xff; + *(dest++) = idx->count & 0xff; - if (datalen < 0xffUL) { - idx->offsize = 1; - *(dest++) = 1; - for (i = 0; i <= idx->count; i++) { - *(dest++) = (card8) (idx->offset[i] & 0xff); - } - } else if (datalen < 0xffffUL) { - idx->offsize = 2; - *(dest++) = 2; - for (i = 0; i <= idx->count; i++) { - *(dest++) = (card8) ((idx->offset[i] >> 8) & 0xff); - *(dest++) = (card8) ( idx->offset[i] & 0xff); - } - } else if (datalen < 0xffffffUL) { - idx->offsize = 3; - *(dest++) = 3; - for (i = 0; i <= idx->count; i++) { - *(dest++) = (card8)((idx->offset[i] >> 16) & 0xff); - *(dest++) = (card8)((idx->offset[i] >> 8) & 0xff); - *(dest++) = (card8)(idx->offset[i] & 0xff); - } - } else { - idx->offsize = 4; - *(dest++) = 4; - for (i = 0; i <= idx->count; i++) { - *(dest++) = (card8)((idx->offset[i] >> 24) & 0xff); - *(dest++) = (card8)((idx->offset[i] >> 16) & 0xff); - *(dest++) = (card8)((idx->offset[i] >> 8) & 0xff); - *(dest++) = (card8)(idx->offset[i] & 0xff); + if (datalen < 0xffUL) { + idx->offsize = 1; + *(dest++) = 1; + for (i = 0; i <= idx->count; i++) { + *(dest++) = (card8) (idx->offset[i] & 0xff); + } + } else if (datalen < 0xffffUL) { + idx->offsize = 2; + *(dest++) = 2; + for (i = 0; i <= idx->count; i++) { + *(dest++) = (card8) ((idx->offset[i] >> 8) & 0xff); + *(dest++) = (card8) (idx->offset[i] & 0xff); + } + } else if (datalen < 0xffffffUL) { + idx->offsize = 3; + *(dest++) = 3; + for (i = 0; i <= idx->count; i++) { + *(dest++) = (card8) ((idx->offset[i] >> 16) & 0xff); + *(dest++) = (card8) ((idx->offset[i] >> 8) & 0xff); + *(dest++) = (card8) (idx->offset[i] & 0xff); + } + } else { + idx->offsize = 4; + *(dest++) = 4; + for (i = 0; i <= idx->count; i++) { + *(dest++) = (card8) ((idx->offset[i] >> 24) & 0xff); + *(dest++) = (card8) ((idx->offset[i] >> 16) & 0xff); + *(dest++) = (card8) ((idx->offset[i] >> 8) & 0xff); + *(dest++) = (card8) (idx->offset[i] & 0xff); + } } - } - memmove(dest, idx->data, idx->offset[idx->count] - 1); + memmove(dest, idx->data, idx->offset[idx->count] - 1); - return len; + return len; } -long -cff_index_size (cff_index *idx) +long cff_index_size(cff_index * idx) { - if (idx->count > 0) { - l_offset datalen; - - datalen = idx->offset[idx->count] - 1; - if (datalen < 0xffUL) { - idx->offsize = 1; - } else if (datalen < 0xffffUL) { - idx->offsize = 2; - } else if (datalen < 0xffffffUL) { - idx->offsize = 3; + if (idx->count > 0) { + l_offset datalen; + + datalen = idx->offset[idx->count] - 1; + if (datalen < 0xffUL) { + idx->offsize = 1; + } else if (datalen < 0xffffUL) { + idx->offsize = 2; + } else if (datalen < 0xffffffUL) { + idx->offsize = 3; + } else { + idx->offsize = 4; + } + return (3 + (idx->offsize) * (idx->count + 1) + datalen); } else { - idx->offsize = 4; + return 2; } - return (3 + (idx->offsize)*(idx->count + 1) + datalen); - } else { - return 2; - } } -cff_index *cff_new_index (card16 count) +cff_index *cff_new_index(card16 count) { - cff_index *idx; + cff_index *idx; - idx = xcalloc(1, sizeof(cff_index)); - idx->count = count; - idx->offsize = 0; + idx = xcalloc(1, sizeof(cff_index)); + idx->count = count; + idx->offsize = 0; - if (count > 0) { - idx->offset = xcalloc(count + 1, sizeof(l_offset)); - (idx->offset)[0] = 1; - } else { - idx->offset = NULL; - } - idx->data = NULL; + if (count > 0) { + idx->offset = xcalloc(count + 1, sizeof(l_offset)); + (idx->offset)[0] = 1; + } else { + idx->offset = NULL; + } + idx->data = NULL; - return idx; + return idx; } -void cff_release_index (cff_index *idx) +void cff_release_index(cff_index * idx) { - if (idx) { - xfree(idx->data); - xfree(idx->offset); - xfree(idx); - } + if (idx) { + xfree(idx->data); + xfree(idx->offset); + xfree(idx); + } } -void cff_release_dict (cff_dict *dict) +void cff_release_dict(cff_dict * dict) { - if (dict) { - if (dict->entries) { - int i; - for (i=0;i<dict->count;i++) { - xfree((dict->entries)[i].values); - } - xfree(dict->entries); - } - xfree(dict); - } + if (dict) { + if (dict->entries) { + int i; + for (i = 0; i < dict->count; i++) { + xfree((dict->entries)[i].values); + } + xfree(dict->entries); + } + xfree(dict); + } } -void cff_release_encoding (cff_encoding *encoding) +void cff_release_encoding(cff_encoding * encoding) { - if (encoding) { - switch (encoding->format & (~0x80)) { - case 0: xfree(encoding->data.codes); break; - case 1: xfree(encoding->data.range1); break; - default: CFF_ERROR("Unknown Encoding format."); + if (encoding) { + switch (encoding->format & (~0x80)) { + case 0: + xfree(encoding->data.codes); + break; + case 1: + xfree(encoding->data.range1); + break; + default: + CFF_ERROR("Unknown Encoding format."); + } + if (encoding->format & 0x80) + xfree(encoding->supp); + xfree(encoding); } - if (encoding->format & 0x80) - xfree(encoding->supp); - xfree(encoding); - } } -void -cff_release_charsets (cff_charsets *charset) +void cff_release_charsets(cff_charsets * charset) { - if (charset) { - switch (charset->format) { - case 0: xfree(charset->data.glyphs); break; - case 1: xfree(charset->data.range1); break; - case 2: xfree(charset->data.range2); break; - default: break; + if (charset) { + switch (charset->format) { + case 0: + xfree(charset->data.glyphs); + break; + case 1: + xfree(charset->data.range1); + break; + case 2: + xfree(charset->data.range2); + break; + default: + break; + } + xfree(charset); } - xfree(charset); - } } -void cff_release_fdselect (cff_fdselect *fdselect) +void cff_release_fdselect(cff_fdselect * fdselect) { - if (fdselect) { - if (fdselect->format == 0) { xfree(fdselect->data.fds); } - else if (fdselect->format == 3) { xfree(fdselect->data.ranges); } - xfree(fdselect); - } + if (fdselect) { + if (fdselect->format == 0) { + xfree(fdselect->data.fds); + } else if (fdselect->format == 3) { + xfree(fdselect->data.ranges); + } + xfree(fdselect); + } } -void -cff_close (cff_font *cff) +void cff_close(cff_font * cff) { - card16 i; - - if (cff) { - if (cff->fontname) xfree(cff->fontname); - if (cff->name) cff_release_index(cff->name); - if (cff->topdict) cff_release_dict(cff->topdict); - if (cff->string) cff_release_index(cff->string); - if (cff->gsubr) cff_release_index(cff->gsubr); - if (cff->encoding) cff_release_encoding(cff->encoding); - if (cff->charsets) cff_release_charsets(cff->charsets); - if (cff->fdselect) cff_release_fdselect(cff->fdselect); - if (cff->cstrings) cff_release_index(cff->cstrings); - if (cff->fdarray) { - for (i=0;i<cff->num_fds;i++) { - if (cff->fdarray[i]) cff_release_dict(cff->fdarray[i]); - } - xfree(cff->fdarray); - } - if (cff->private) { - for (i=0;i<cff->num_fds;i++) { - if (cff->private[i]) cff_release_dict(cff->private[i]); - } - xfree(cff->private); - } - if (cff->subrs) { - for (i=0;i<cff->num_fds;i++) { - if (cff->subrs[i]) cff_release_index(cff->subrs[i]); - } - xfree(cff->subrs); - } - if (cff->_string) - cff_release_index(cff->_string); - xfree(cff); - } + card16 i; + + if (cff) { + if (cff->fontname) + xfree(cff->fontname); + if (cff->name) + cff_release_index(cff->name); + if (cff->topdict) + cff_release_dict(cff->topdict); + if (cff->string) + cff_release_index(cff->string); + if (cff->gsubr) + cff_release_index(cff->gsubr); + if (cff->encoding) + cff_release_encoding(cff->encoding); + if (cff->charsets) + cff_release_charsets(cff->charsets); + if (cff->fdselect) + cff_release_fdselect(cff->fdselect); + if (cff->cstrings) + cff_release_index(cff->cstrings); + if (cff->fdarray) { + for (i = 0; i < cff->num_fds; i++) { + if (cff->fdarray[i]) + cff_release_dict(cff->fdarray[i]); + } + xfree(cff->fdarray); + } + if (cff->private) { + for (i = 0; i < cff->num_fds; i++) { + if (cff->private[i]) + cff_release_dict(cff->private[i]); + } + xfree(cff->private); + } + if (cff->subrs) { + for (i = 0; i < cff->num_fds; i++) { + if (cff->subrs[i]) + cff_release_index(cff->subrs[i]); + } + xfree(cff->subrs); + } + if (cff->_string) + cff_release_index(cff->_string); + xfree(cff); + } - return; + return; } -char * -cff_get_name (cff_font *cff) +char *cff_get_name(cff_font * cff) { - char *fontname; - l_offset len; - cff_index *idx; + char *fontname; + l_offset len; + cff_index *idx; - idx = cff->name; - len = idx->offset[cff->index + 1] - idx->offset[cff->index]; - fontname = xmalloc((len + 1)*sizeof(char)); - memcpy(fontname, idx->data + idx->offset[cff->index] - 1, len); - fontname[len] = '\0'; + idx = cff->name; + len = idx->offset[cff->index + 1] - idx->offset[cff->index]; + fontname = xmalloc((len + 1) * sizeof(char)); + memcpy(fontname, idx->data + idx->offset[cff->index] - 1, len); + fontname[len] = '\0'; - return fontname; + return fontname; } -long -cff_set_name (cff_font *cff, char *name) +long cff_set_name(cff_font * cff, char *name) { - cff_index *idx; + cff_index *idx; - if (strlen(name) > 127) - CFF_ERROR("FontName string length too large..."); + if (strlen(name) > 127) + CFF_ERROR("FontName string length too large..."); - if (cff->name) - cff_release_index(cff->name); + if (cff->name) + cff_release_index(cff->name); - cff->name = idx = xcalloc(1, sizeof(cff_index)); - idx->count = 1; - idx->offsize = 1; - idx->offset = xmalloc(2*sizeof(l_offset)); - (idx->offset)[0] = 1; - (idx->offset)[1] = strlen(name) + 1; - idx->data = xcalloc(strlen(name), sizeof(card8)); - memmove(idx->data, name, strlen(name)); /* no trailing '\0' */ + cff->name = idx = xcalloc(1, sizeof(cff_index)); + idx->count = 1; + idx->offsize = 1; + idx->offset = xmalloc(2 * sizeof(l_offset)); + (idx->offset)[0] = 1; + (idx->offset)[1] = strlen(name) + 1; + idx->data = xcalloc(strlen(name), sizeof(card8)); + memmove(idx->data, name, strlen(name)); /* no trailing '\0' */ - return 5 + strlen(name); + return 5 + strlen(name); } -long -cff_put_header (cff_font *cff, card8 *dest, long destlen) +long cff_put_header(cff_font * cff, card8 * dest, long destlen) { - if (destlen < 4) - CFF_ERROR("Not enough space available..."); - - *(dest++) = cff->header_major; - *(dest++) = cff->header_minor; - *(dest++) = 4; /* Additional data in between header and - * Name INDEX ignored. - */ - /* We will set all offset (0) to four-byte integer. */ - *(dest++) = 4; - cff->header_offsize = 4; - - return 4; + if (destlen < 4) + CFF_ERROR("Not enough space available..."); + + *(dest++) = cff->header_major; + *(dest++) = cff->header_minor; + *(dest++) = 4; /* Additional data in between header and + * Name INDEX ignored. + */ + /* We will set all offset (0) to four-byte integer. */ + *(dest++) = 4; + cff->header_offsize = 4; + + return 4; } #define CFF_PARSE_OK 0 @@ -475,15 +508,15 @@ cff_put_header (cff_font *cff, card8 *dest, long destlen) #define DICT_ENTRY_MAX 16 -cff_dict *cff_new_dict (void) +cff_dict *cff_new_dict(void) { - cff_dict *dict; + cff_dict *dict; - dict = xcalloc(1, sizeof(cff_dict)); - dict->max = DICT_ENTRY_MAX; - dict->count = 0; - dict->entries = xcalloc(dict->max, sizeof(cff_dict_entry)); - return dict; + dict = xcalloc(1, sizeof(cff_dict)); + dict->max = DICT_ENTRY_MAX; + dict->count = 0; + dict->entries = xcalloc(dict->max, sizeof(cff_dict_entry)); + return dict; } /* @@ -500,7 +533,7 @@ cff_dict *cff_new_dict (void) */ #define CFF_DICT_STACK_LIMIT 64 -static int stack_top = 0; +static int stack_top = 0; static double arg_stack[CFF_DICT_STACK_LIMIT]; /* @@ -513,231 +546,239 @@ static double arg_stack[CFF_DICT_STACK_LIMIT]; #define CFF_LAST_DICT_OP (CFF_LAST_DICT_OP1 + CFF_LAST_DICT_OP2) static struct { - const char *opname; - int argtype; + const char *opname; + int argtype; } dict_operator[CFF_LAST_DICT_OP] = { - {"version", CFF_TYPE_SID}, - {"Notice", CFF_TYPE_SID}, - {"FullName", CFF_TYPE_SID}, - {"FamilyName", CFF_TYPE_SID}, - {"Weight", CFF_TYPE_SID}, - {"FontBBox", CFF_TYPE_ARRAY}, - {"BlueValues", CFF_TYPE_DELTA}, - {"OtherBlues", CFF_TYPE_DELTA}, - {"FamilyBlues", CFF_TYPE_DELTA}, - {"FamilyOtherBlues", CFF_TYPE_DELTA}, - {"StdHW", CFF_TYPE_NUMBER}, - {"StdVW", CFF_TYPE_NUMBER}, - {NULL, -1}, /* first byte of two-byte operator */ - /* Top */ - {"UniqueID", CFF_TYPE_NUMBER}, - {"XUID", CFF_TYPE_ARRAY}, - {"charset", CFF_TYPE_OFFSET}, - {"Encoding", CFF_TYPE_OFFSET}, - {"CharStrings", CFF_TYPE_OFFSET}, - {"Private", CFF_TYPE_SZOFF}, /* two numbers (size and offset) */ - /* Private */ - {"Subrs", CFF_TYPE_OFFSET}, - {"defaultWidthX", CFF_TYPE_NUMBER}, - {"nominalWidthX", CFF_TYPE_NUMBER}, - /* Operator 2 */ - {"Copyright", CFF_TYPE_SID}, - {"IsFixedPitch", CFF_TYPE_BOOLEAN}, - {"ItalicAngle", CFF_TYPE_NUMBER}, - {"UnderlinePosition", CFF_TYPE_NUMBER}, - {"UnderlineThickness", CFF_TYPE_NUMBER}, - {"PaintType", CFF_TYPE_NUMBER}, - {"CharstringType", CFF_TYPE_NUMBER}, - {"FontMatrix", CFF_TYPE_ARRAY}, - {"StrokeWidth", CFF_TYPE_NUMBER}, - {"BlueScale", CFF_TYPE_NUMBER}, - {"BlueShift", CFF_TYPE_NUMBER}, - {"BlueFuzz", CFF_TYPE_NUMBER}, - {"StemSnapH", CFF_TYPE_DELTA}, - {"StemSnapV", CFF_TYPE_DELTA}, - {"ForceBold", CFF_TYPE_BOOLEAN}, - {NULL, -1}, - {NULL, -1}, - {"LanguageGroup", CFF_TYPE_NUMBER}, - {"ExpansionFactor", CFF_TYPE_NUMBER}, - {"InitialRandomSeed", CFF_TYPE_NUMBER}, - {"SyntheticBase", CFF_TYPE_NUMBER}, - {"PostScript", CFF_TYPE_SID}, - {"BaseFontName", CFF_TYPE_SID}, - {"BaseFontBlend", CFF_TYPE_DELTA}, /* MMaster ? */ - {NULL, -1}, - {NULL, -1}, - {NULL, -1}, - {NULL, -1}, - {NULL, -1}, - {NULL, -1}, - /* CID-Keyed font */ - {"ROS", CFF_TYPE_ROS}, /* SID SID number */ - {"CIDFontVersion", CFF_TYPE_NUMBER}, - {"CIDFontRevision", CFF_TYPE_NUMBER}, - {"CIDFontType", CFF_TYPE_NUMBER}, - {"CIDCount", CFF_TYPE_NUMBER}, - {"UIDBase", CFF_TYPE_NUMBER}, - {"FDArray", CFF_TYPE_OFFSET}, - {"FDSelect", CFF_TYPE_OFFSET}, - {"FontName", CFF_TYPE_SID}, -}; + { + "version", CFF_TYPE_SID}, { + "Notice", CFF_TYPE_SID}, { + "FullName", CFF_TYPE_SID}, { + "FamilyName", CFF_TYPE_SID}, { + "Weight", CFF_TYPE_SID}, { + "FontBBox", CFF_TYPE_ARRAY}, { + "BlueValues", CFF_TYPE_DELTA}, { + "OtherBlues", CFF_TYPE_DELTA}, { + "FamilyBlues", CFF_TYPE_DELTA}, { + "FamilyOtherBlues", CFF_TYPE_DELTA}, { + "StdHW", CFF_TYPE_NUMBER}, { + "StdVW", CFF_TYPE_NUMBER}, { + NULL, -1}, /* first byte of two-byte operator */ + /* Top */ + { + "UniqueID", CFF_TYPE_NUMBER}, { + "XUID", CFF_TYPE_ARRAY}, { + "charset", CFF_TYPE_OFFSET}, { + "Encoding", CFF_TYPE_OFFSET}, { + "CharStrings", CFF_TYPE_OFFSET}, { + "Private", CFF_TYPE_SZOFF}, /* two numbers (size and offset) */ + /* Private */ + { + "Subrs", CFF_TYPE_OFFSET}, { + "defaultWidthX", CFF_TYPE_NUMBER}, { + "nominalWidthX", CFF_TYPE_NUMBER}, + /* Operator 2 */ + { + "Copyright", CFF_TYPE_SID}, { + "IsFixedPitch", CFF_TYPE_BOOLEAN}, { + "ItalicAngle", CFF_TYPE_NUMBER}, { + "UnderlinePosition", CFF_TYPE_NUMBER}, { + "UnderlineThickness", CFF_TYPE_NUMBER}, { + "PaintType", CFF_TYPE_NUMBER}, { + "CharstringType", CFF_TYPE_NUMBER}, { + "FontMatrix", CFF_TYPE_ARRAY}, { + "StrokeWidth", CFF_TYPE_NUMBER}, { + "BlueScale", CFF_TYPE_NUMBER}, { + "BlueShift", CFF_TYPE_NUMBER}, { + "BlueFuzz", CFF_TYPE_NUMBER}, { + "StemSnapH", CFF_TYPE_DELTA}, { + "StemSnapV", CFF_TYPE_DELTA}, { + "ForceBold", CFF_TYPE_BOOLEAN}, { + NULL, -1}, { + NULL, -1}, { + "LanguageGroup", CFF_TYPE_NUMBER}, { + "ExpansionFactor", CFF_TYPE_NUMBER}, { + "InitialRandomSeed", CFF_TYPE_NUMBER}, { + "SyntheticBase", CFF_TYPE_NUMBER}, { + "PostScript", CFF_TYPE_SID}, { + "BaseFontName", CFF_TYPE_SID}, { + "BaseFontBlend", CFF_TYPE_DELTA}, /* MMaster ? */ + { + NULL, -1}, { + NULL, -1}, { + NULL, -1}, { + NULL, -1}, { + NULL, -1}, { + NULL, -1}, + /* CID-Keyed font */ + { + "ROS", CFF_TYPE_ROS}, /* SID SID number */ + { + "CIDFontVersion", CFF_TYPE_NUMBER}, { + "CIDFontRevision", CFF_TYPE_NUMBER}, { + "CIDFontType", CFF_TYPE_NUMBER}, { + "CIDCount", CFF_TYPE_NUMBER}, { + "UIDBase", CFF_TYPE_NUMBER}, { + "FDArray", CFF_TYPE_OFFSET}, { + "FDSelect", CFF_TYPE_OFFSET}, { +"FontName", CFF_TYPE_SID},}; /* Parse DICT data */ -static double get_integer (card8 **data, card8 *endptr, int *status) +static double get_integer(card8 ** data, card8 * endptr, int *status) { - long result = 0; - card8 b0, b1, b2; - - b0 = *(*data)++; - if (b0 == 28 && *data < endptr - 2) { /* shortint */ - b1 = *(*data)++; - b2 = *(*data)++; - result = b1*256+b2; - if (result > 0x7fffL) - result -= 0x10000L; - } else if (b0 == 29 && *data < endptr - 4) { /* longint */ - int i; - result = *(*data)++; - if (result > 0x7f) - result -= 0x100; - for (i=0;i<3;i++) { - result = result*256+(**data); - *data += 1; - } - } else if (b0 >= 32 && b0 <= 246) { /* int (1) */ - result = b0 - 139; - } else if (b0 >= 247 && b0 <= 250) { /* int (2) */ - b1 = *(*data)++; - result = (b0-247)*256+b1+108; - } else if (b0 >= 251 && b0 <= 254) { - b1 = *(*data)++; - result = -(b0-251)*256-b1-108; - } else { - *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; - } + long result = 0; + card8 b0, b1, b2; + + b0 = *(*data)++; + if (b0 == 28 && *data < endptr - 2) { /* shortint */ + b1 = *(*data)++; + b2 = *(*data)++; + result = b1 * 256 + b2; + if (result > 0x7fffL) + result -= 0x10000L; + } else if (b0 == 29 && *data < endptr - 4) { /* longint */ + int i; + result = *(*data)++; + if (result > 0x7f) + result -= 0x100; + for (i = 0; i < 3; i++) { + result = result * 256 + (**data); + *data += 1; + } + } else if (b0 >= 32 && b0 <= 246) { /* int (1) */ + result = b0 - 139; + } else if (b0 >= 247 && b0 <= 250) { /* int (2) */ + b1 = *(*data)++; + result = (b0 - 247) * 256 + b1 + 108; + } else if (b0 >= 251 && b0 <= 254) { + b1 = *(*data)++; + result = -(b0 - 251) * 256 - b1 - 108; + } else { + *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; + } - return (double) result; + return (double) result; } /* Simply uses strtod */ -static double get_real(card8 **data, card8 *endptr, int *status) +static double get_real(card8 ** data, card8 * endptr, int *status) { - double result = 0.0; - int nibble = 0, pos = 0; - int len = 0, fail = 0; - - if (**data != 30 || *data >= endptr -1) { - *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; - return 0.0; - } - - *data += 1; /* skip first byte (30) */ - - pos = 0; - while ((! fail) && len < WORK_BUFFER_SIZE - 2 && *data < endptr) { - /* get nibble */ - if (pos % 2) { - nibble = **data & 0x0f; - *data += 1; + double result = 0.0; + int nibble = 0, pos = 0; + int len = 0, fail = 0; + + if (**data != 30 || *data >= endptr - 1) { + *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; + return 0.0; + } + + *data += 1; /* skip first byte (30) */ + + pos = 0; + while ((!fail) && len < WORK_BUFFER_SIZE - 2 && *data < endptr) { + /* get nibble */ + if (pos % 2) { + nibble = **data & 0x0f; + *data += 1; + } else { + nibble = (**data >> 4) & 0x0f; + } + if (nibble >= 0x00 && nibble <= 0x09) { + work_buffer[len++] = nibble + '0'; + } else if (nibble == 0x0a) { /* . */ + work_buffer[len++] = '.'; + } else if (nibble == 0x0b || nibble == 0x0c) { /* E, E- */ + work_buffer[len++] = 'e'; + if (nibble == 0x0c) + work_buffer[len++] = '-'; + } else if (nibble == 0x0e) { /* `-' */ + work_buffer[len++] = '-'; + } else if (nibble == 0x0d) { /* skip */ + /* do nothing */ + } else if (nibble == 0x0f) { /* end */ + work_buffer[len++] = '\0'; + if (((pos % 2) == 0) && (**data != 0xff)) { + fail = 1; + } + break; + } else { /* invalid */ + fail = 1; + } + pos++; + } + + /* returned values */ + if (fail || nibble != 0x0f) { + *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; } else { - nibble = (**data >> 4) & 0x0f; - } - if (nibble >= 0x00 && nibble <= 0x09) { - work_buffer[len++] = nibble + '0'; - } else if (nibble == 0x0a) { /* . */ - work_buffer[len++] = '.'; - } else if (nibble == 0x0b || nibble == 0x0c) { /* E, E- */ - work_buffer[len++] = 'e'; - if (nibble == 0x0c) - work_buffer[len++] = '-'; - } else if (nibble == 0x0e) { /* `-' */ - work_buffer[len++] = '-'; - } else if (nibble == 0x0d) { /* skip */ - /* do nothing */ - } else if (nibble == 0x0f) { /* end */ - work_buffer[len++] = '\0'; - if (((pos % 2) == 0) && (**data != 0xff)) { - fail = 1; - } - break; - } else { /* invalid */ - fail = 1; - } - pos++; - } - - /* returned values */ - if (fail || nibble != 0x0f) { - *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; - } else { - char *s; - result = strtod(work_buffer, &s); - if (*s != 0 || errno == ERANGE) { - *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; + char *s; + result = strtod(work_buffer, &s); + if (*s != 0 || errno == ERANGE) { + *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; + } } - } - return result; + return result; } /* operators */ -static void add_dict (cff_dict *dict, - card8 **data, card8 *endptr, int *status) +static void add_dict(cff_dict * dict, + card8 ** data, card8 * endptr, int *status) { - int id, argtype; + int id, argtype; + + id = **data; + if (id == 0x0c) { + *data += 1; + if (*data >= endptr || + (id = **data + CFF_LAST_DICT_OP1) >= CFF_LAST_DICT_OP) { + *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; + return; + } + } else if (id >= CFF_LAST_DICT_OP1) { + *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; + return; + } + + argtype = dict_operator[id].argtype; + if (dict_operator[id].opname == NULL || argtype < 0) { + *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; + return; + } else if (stack_top < 1) { + *status = CFF_CFF_ERROR_STACK_UNDERFLOW; + return; + } + + if (dict->count >= dict->max) { + dict->max += DICT_ENTRY_MAX; + /* not zeroed! */ + dict->entries = + xrealloc(dict->entries, dict->max * sizeof(cff_dict_entry)); + } + + (dict->entries)[dict->count].id = id; + (dict->entries)[dict->count].key = (char *) dict_operator[id].opname; + if (argtype == CFF_TYPE_NUMBER || + argtype == CFF_TYPE_BOOLEAN || + argtype == CFF_TYPE_SID || argtype == CFF_TYPE_OFFSET) { + stack_top--; + (dict->entries)[dict->count].count = 1; + (dict->entries)[dict->count].values = xcalloc(1, sizeof(double)); + (dict->entries)[dict->count].values[0] = arg_stack[stack_top]; + } else { + (dict->entries)[dict->count].count = stack_top; + (dict->entries)[dict->count].values = + xcalloc(stack_top, sizeof(double)); + while (stack_top > 0) { + stack_top--; + (dict->entries)[dict->count].values[stack_top] = + arg_stack[stack_top]; + } + } - id = **data; - if (id == 0x0c) { + dict->count += 1; *data += 1; - if (*data >= endptr || - (id = **data + CFF_LAST_DICT_OP1) >= CFF_LAST_DICT_OP) { - *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; - return; - } - } else if (id >= CFF_LAST_DICT_OP1) { - *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; - return; - } - argtype = dict_operator[id].argtype; - if (dict_operator[id].opname == NULL || argtype < 0) { - *status = CFF_CFF_ERROR_PARSE_CFF_ERROR; return; - } else if (stack_top < 1) { - *status = CFF_CFF_ERROR_STACK_UNDERFLOW; - return; - } - - if (dict->count >= dict->max) { - dict->max += DICT_ENTRY_MAX; - /* not zeroed! */ - dict->entries = xrealloc(dict->entries, dict->max*sizeof(cff_dict_entry)); - } - - (dict->entries)[dict->count].id = id; - (dict->entries)[dict->count].key = (char *) dict_operator[id].opname; - if (argtype == CFF_TYPE_NUMBER || - argtype == CFF_TYPE_BOOLEAN || - argtype == CFF_TYPE_SID || - argtype == CFF_TYPE_OFFSET) { - stack_top--; - (dict->entries)[dict->count].count = 1; - (dict->entries)[dict->count].values = xcalloc(1, sizeof(double)); - (dict->entries)[dict->count].values[0] = arg_stack[stack_top]; - } else { - (dict->entries)[dict->count].count = stack_top; - (dict->entries)[dict->count].values = xcalloc(stack_top, sizeof(double)); - while (stack_top > 0) { - stack_top--; - (dict->entries)[dict->count].values[stack_top] = arg_stack[stack_top]; - } - } - - dict->count += 1; - *data += 1; - - return; } /* @@ -745,370 +786,370 @@ static void add_dict (cff_dict *dict, * Private: two numbers, size and offset * ROS : three numbers, SID, SID, and a number */ -cff_dict *cff_dict_unpack (card8 *data, card8 *endptr) +cff_dict *cff_dict_unpack(card8 * data, card8 * endptr) { - cff_dict *dict; - int status = CFF_PARSE_OK; - - stack_top = 0; - - dict = cff_new_dict(); - while (data < endptr && status == CFF_PARSE_OK) { - if (*data < 22) { /* operator */ - add_dict(dict, &data, endptr, &status); - } else if (*data == 30) { /* real - First byte of a sequence (variable) */ - if (stack_top < CFF_DICT_STACK_LIMIT) { - arg_stack[stack_top] = get_real(&data, endptr, &status); - stack_top++; - } else { - status = CFF_CFF_ERROR_STACK_OVERFLOW; - } - } else if (*data == 255 || (*data >= 22 && *data <= 27)) { /* reserved */ - data++; - } else { /* everything else are integer */ - if (stack_top < CFF_DICT_STACK_LIMIT) { - arg_stack[stack_top] = get_integer(&data, endptr, &status); - stack_top++; - } else { - status = CFF_CFF_ERROR_STACK_OVERFLOW; - } - } - } + cff_dict *dict; + int status = CFF_PARSE_OK; - if (status != CFF_PARSE_OK) { - pdftex_fail("Parsing CFF DICT failed. (error=%d)", status); - } else if (stack_top != 0) { - WARN("Garbage in CFF DICT data."); stack_top = 0; - } - return dict; + dict = cff_new_dict(); + while (data < endptr && status == CFF_PARSE_OK) { + if (*data < 22) { /* operator */ + add_dict(dict, &data, endptr, &status); + } else if (*data == 30) { /* real - First byte of a sequence (variable) */ + if (stack_top < CFF_DICT_STACK_LIMIT) { + arg_stack[stack_top] = get_real(&data, endptr, &status); + stack_top++; + } else { + status = CFF_CFF_ERROR_STACK_OVERFLOW; + } + } else if (*data == 255 || (*data >= 22 && *data <= 27)) { /* reserved */ + data++; + } else { /* everything else are integer */ + if (stack_top < CFF_DICT_STACK_LIMIT) { + arg_stack[stack_top] = get_integer(&data, endptr, &status); + stack_top++; + } else { + status = CFF_CFF_ERROR_STACK_OVERFLOW; + } + } + } + + if (status != CFF_PARSE_OK) { + pdftex_fail("Parsing CFF DICT failed. (error=%d)", status); + } else if (stack_top != 0) { + WARN("Garbage in CFF DICT data."); + stack_top = 0; + } + + return dict; } -int cff_dict_known (cff_dict *dict, const char *key) +int cff_dict_known(cff_dict * dict, const char *key) { - int i; + int i; - for (i = 0; i < dict->count; i++) { - if (key && strcmp(key, (dict->entries)[i].key) == 0 - && (dict->entries)[i].count > 0) - return 1; - } + for (i = 0; i < dict->count; i++) { + if (key && strcmp(key, (dict->entries)[i].key) == 0 + && (dict->entries)[i].count > 0) + return 1; + } - return 0; + return 0; } -double cff_dict_get (cff_dict *dict, const char *key, int idx) +double cff_dict_get(cff_dict * dict, const char *key, int idx) { - double value = 0.0; - int i; + double value = 0.0; + int i; - assert(key && dict); + assert(key && dict); - for (i = 0; i < dict->count; i++) { - if (strcmp(key, (dict->entries)[i].key) == 0) { - if ((dict->entries)[i].count > idx) - value = (dict->entries)[i].values[idx]; - else - pdftex_fail("Invalid index number."); - break; + for (i = 0; i < dict->count; i++) { + if (strcmp(key, (dict->entries)[i].key) == 0) { + if ((dict->entries)[i].count > idx) + value = (dict->entries)[i].values[idx]; + else + pdftex_fail("Invalid index number."); + break; + } } - } - if (i == dict->count) - pdftex_fail("DICT entry \"%s\" not found.", key); + if (i == dict->count) + pdftex_fail("DICT entry \"%s\" not found.", key); - return value; + return value; } -card8 cff_fdselect_lookup (cff_font *cff, card16 gid) +card8 cff_fdselect_lookup(cff_font * cff, card16 gid) { - card8 fd = 0xff; - cff_fdselect *fdsel; - - if (cff->fdselect == NULL) - CFF_ERROR("in cff_fdselect_lookup(): FDSelect not available"); - - fdsel = cff->fdselect; - - if (gid >= cff->num_glyphs) - CFF_ERROR("in cff_fdselect_lookup(): Invalid glyph index"); - - switch (fdsel->format) { - case 0: - fd = fdsel->data.fds[gid]; - break; - case 3: - { - if (gid == 0) { - fd = (fdsel->data).ranges[0].fd; - } else { - card16 i; - for (i=1;i<(fdsel->num_entries);i++) { - if (gid < (fdsel->data).ranges[i].first) - break; - } - fd = (fdsel->data).ranges[i-1].fd; - } - } - break; - default: - CFF_ERROR("in cff_fdselect_lookup(): Invalid FDSelect format"); - break; - } - - if (fd >= cff->num_fds) - CFF_ERROR("in cff_fdselect_lookup(): Invalid Font DICT index"); - - return fd; + card8 fd = 0xff; + cff_fdselect *fdsel; + + if (cff->fdselect == NULL) + CFF_ERROR("in cff_fdselect_lookup(): FDSelect not available"); + + fdsel = cff->fdselect; + + if (gid >= cff->num_glyphs) + CFF_ERROR("in cff_fdselect_lookup(): Invalid glyph index"); + + switch (fdsel->format) { + case 0: + fd = fdsel->data.fds[gid]; + break; + case 3: + { + if (gid == 0) { + fd = (fdsel->data).ranges[0].fd; + } else { + card16 i; + for (i = 1; i < (fdsel->num_entries); i++) { + if (gid < (fdsel->data).ranges[i].first) + break; + } + fd = (fdsel->data).ranges[i - 1].fd; + } + } + break; + default: + CFF_ERROR("in cff_fdselect_lookup(): Invalid FDSelect format"); + break; + } + + if (fd >= cff->num_fds) + CFF_ERROR("in cff_fdselect_lookup(): Invalid Font DICT index"); + + return fd; } -long cff_read_subrs (cff_font *cff) +long cff_read_subrs(cff_font * cff) { - long len = 0; - long offset; - int i; - - - if ((cff->flag & FONTTYPE_CIDFONT) && cff->fdselect == NULL) { - cff_read_fdselect(cff); - } - - if ((cff->flag & FONTTYPE_CIDFONT) && cff->fdarray == NULL) { - cff_read_fdarray(cff); - } + long len = 0; + long offset; + int i; - if (cff->private == NULL) - cff_read_private(cff); - if (cff->gsubr == NULL) { - cff->offset = cff->gsubr_offset; - cff->gsubr = cff_get_index(cff); - } - - cff->subrs = xcalloc(cff->num_fds, sizeof(cff_index *)); - if (cff->flag & FONTTYPE_CIDFONT) { - for (i=0;i<cff->num_fds;i++) { - if (cff->private[i] == NULL || - !cff_dict_known(cff->private[i], "Subrs")) { - (cff->subrs)[i] = NULL; - } else { - offset = (long) cff_dict_get(cff->fdarray[i], "Private", 1); - offset += (long) cff_dict_get(cff->private[i], "Subrs", 0); - cff->offset = offset; - (cff->subrs)[i] = cff_get_index(cff); - len += cff_index_size((cff->subrs)[i]); - } - } - } else { - if (cff->private[0] == NULL || - !cff_dict_known(cff->private[0], "Subrs")) { - (cff->subrs)[0] = NULL; - } else { - offset = (long) cff_dict_get(cff->topdict, "Private", 1); - offset += (long) cff_dict_get(cff->private[0], "Subrs", 0); - cff->offset = offset; - (cff->subrs)[0] = cff_get_index(cff); - len += cff_index_size((cff->subrs)[0]); + if ((cff->flag & FONTTYPE_CIDFONT) && cff->fdselect == NULL) { + cff_read_fdselect(cff); } - } - - return len; -} - - -long cff_read_fdarray (cff_font *cff) -{ - long len = 0; - cff_index *idx; - long offset, size; - card16 i; - if (cff->topdict == NULL) - CFF_ERROR("in cff_read_fdarray(): Top DICT not found"); + if ((cff->flag & FONTTYPE_CIDFONT) && cff->fdarray == NULL) { + cff_read_fdarray(cff); + } - if (!(cff->flag & FONTTYPE_CIDFONT)) - return 0; + if (cff->private == NULL) + cff_read_private(cff); - /* must exist */ - offset = (long) cff_dict_get(cff->topdict, "FDArray", 0); - cff->offset = offset; - idx = cff_get_index(cff); - cff->num_fds = (card8)idx->count; - cff->fdarray = xcalloc(idx->count, sizeof(cff_dict *)); - for (i=0;i<idx->count;i++) { - card8 *data = idx->data + (idx->offset)[i] - 1; - size = (idx->offset)[i+1] - (idx->offset)[i]; - if (size > 0) { - (cff->fdarray)[i] = cff_dict_unpack(data, data+size); - } else { - (cff->fdarray)[i] = NULL; + if (cff->gsubr == NULL) { + cff->offset = cff->gsubr_offset; + cff->gsubr = cff_get_index(cff); } - } - len = cff_index_size(idx); - cff_release_index(idx); - return len; + cff->subrs = xcalloc(cff->num_fds, sizeof(cff_index *)); + if (cff->flag & FONTTYPE_CIDFONT) { + for (i = 0; i < cff->num_fds; i++) { + if (cff->private[i] == NULL || + !cff_dict_known(cff->private[i], "Subrs")) { + (cff->subrs)[i] = NULL; + } else { + offset = (long) cff_dict_get(cff->fdarray[i], "Private", 1); + offset += (long) cff_dict_get(cff->private[i], "Subrs", 0); + cff->offset = offset; + (cff->subrs)[i] = cff_get_index(cff); + len += cff_index_size((cff->subrs)[i]); + } + } + } else { + if (cff->private[0] == NULL || + !cff_dict_known(cff->private[0], "Subrs")) { + (cff->subrs)[0] = NULL; + } else { + offset = (long) cff_dict_get(cff->topdict, "Private", 1); + offset += (long) cff_dict_get(cff->private[0], "Subrs", 0); + cff->offset = offset; + (cff->subrs)[0] = cff_get_index(cff); + len += cff_index_size((cff->subrs)[0]); + } + } + + return len; } -long cff_read_private (cff_font *cff) +long cff_read_fdarray(cff_font * cff) { - long len = 0; - card8 *data; - long offset, size; + long len = 0; + cff_index *idx; + long offset, size; + card16 i; + + if (cff->topdict == NULL) + CFF_ERROR("in cff_read_fdarray(): Top DICT not found"); + + if (!(cff->flag & FONTTYPE_CIDFONT)) + return 0; + + /* must exist */ + offset = (long) cff_dict_get(cff->topdict, "FDArray", 0); + cff->offset = offset; + idx = cff_get_index(cff); + cff->num_fds = (card8) idx->count; + cff->fdarray = xcalloc(idx->count, sizeof(cff_dict *)); + for (i = 0; i < idx->count; i++) { + card8 *data = idx->data + (idx->offset)[i] - 1; + size = (idx->offset)[i + 1] - (idx->offset)[i]; + if (size > 0) { + (cff->fdarray)[i] = cff_dict_unpack(data, data + size); + } else { + (cff->fdarray)[i] = NULL; + } + } + len = cff_index_size(idx); + cff_release_index(idx); + + return len; +} - if (cff->flag & FONTTYPE_CIDFONT) { - int i; - if (cff->fdarray == NULL) - cff_read_fdarray(cff); - - cff->private = xcalloc(cff->num_fds, sizeof(cff_dict *)); - for (i=0;i<cff->num_fds;i++) { - if (cff->fdarray[i] != NULL && - cff_dict_known(cff->fdarray[i], "Private") && - (size = (long) cff_dict_get(cff->fdarray[i], "Private", 0)) - > 0) { - offset = (long) cff_dict_get(cff->fdarray[i], "Private", 1); - cff->offset = offset; - data = xcalloc(size, sizeof(card8)); - memcpy(data,&cff->stream[cff->offset],size); - cff->offset = size; - (cff->private)[i] = cff_dict_unpack(data, data+size); - xfree(data); - len += size; - } else { - (cff->private)[i] = NULL; - } - } - } else { - cff->num_fds = 1; - cff->private = xcalloc(1, sizeof(cff_dict *)); - if (cff_dict_known(cff->topdict, "Private") && - (size = (long) cff_dict_get(cff->topdict, "Private", 0)) > 0) { - offset = (long) cff_dict_get(cff->topdict, "Private", 1); - cff->offset = offset; - data = xcalloc(size, sizeof(card8)); - memcpy(data,&cff->stream[cff->offset],size); - cff->offset = size; - cff->private[0] = cff_dict_unpack(data, data+size); - xfree(data); - len += size; +long cff_read_private(cff_font * cff) +{ + long len = 0; + card8 *data; + long offset, size; + + if (cff->flag & FONTTYPE_CIDFONT) { + int i; + + if (cff->fdarray == NULL) + cff_read_fdarray(cff); + + cff->private = xcalloc(cff->num_fds, sizeof(cff_dict *)); + for (i = 0; i < cff->num_fds; i++) { + if (cff->fdarray[i] != NULL && + cff_dict_known(cff->fdarray[i], "Private") && + (size = (long) cff_dict_get(cff->fdarray[i], "Private", 0)) + > 0) { + offset = (long) cff_dict_get(cff->fdarray[i], "Private", 1); + cff->offset = offset; + data = xcalloc(size, sizeof(card8)); + memcpy(data, &cff->stream[cff->offset], size); + cff->offset = size; + (cff->private)[i] = cff_dict_unpack(data, data + size); + xfree(data); + len += size; + } else { + (cff->private)[i] = NULL; + } + } } else { - (cff->private)[0] = NULL; - len = 0; - } - } - - return len; + cff->num_fds = 1; + cff->private = xcalloc(1, sizeof(cff_dict *)); + if (cff_dict_known(cff->topdict, "Private") && + (size = (long) cff_dict_get(cff->topdict, "Private", 0)) > 0) { + offset = (long) cff_dict_get(cff->topdict, "Private", 1); + cff->offset = offset; + data = xcalloc(size, sizeof(card8)); + memcpy(data, &cff->stream[cff->offset], size); + cff->offset = size; + cff->private[0] = cff_dict_unpack(data, data + size); + xfree(data); + len += size; + } else { + (cff->private)[0] = NULL; + len = 0; + } + } + + return len; } -cff_font *read_cff (unsigned char *buf,long buflength, int n) +cff_font *read_cff(unsigned char *buf, long buflength, int n) { - cff_font *cff; - cff_index *idx; - long offset ; + cff_font *cff; + cff_index *idx; + long offset; - cff = xcalloc(1,sizeof(cff_font)); + cff = xcalloc(1, sizeof(cff_font)); - cff->stream = buf; - cff->stream_size = buflength; - cff->index = n; + cff->stream = buf; + cff->stream_size = buflength; + cff->index = n; - cff->header_major = get_card8(cff); - cff->header_minor = get_card8(cff); - cff->header_hdr_size = get_card8(cff); - cff->header_offsize = get_card8(cff); - if (cff->header_offsize < 1 || cff->header_offsize > 4) { - WARN("invalid offsize data"); - cff_close(cff); - return NULL; - } - if (cff->header_major > 1) { - pdftex_warn("CFF major version %u not supported.",cff->header_major); - cff_close(cff); - return NULL; - } - cff->offset = cff->header_hdr_size; - - /* Name INDEX */ - idx = cff_get_index(cff); - if (n > idx->count - 1) { - pdftex_warn("Invalid CFF fontset index number."); - cff_close(cff); - return NULL; - } + cff->header_major = get_card8(cff); + cff->header_minor = get_card8(cff); + cff->header_hdr_size = get_card8(cff); + cff->header_offsize = get_card8(cff); + if (cff->header_offsize < 1 || cff->header_offsize > 4) { + WARN("invalid offsize data"); + cff_close(cff); + return NULL; + } + if (cff->header_major > 1) { + pdftex_warn("CFF major version %u not supported.", cff->header_major); + cff_close(cff); + return NULL; + } + cff->offset = cff->header_hdr_size; - cff->name = idx; + /* Name INDEX */ + idx = cff_get_index(cff); + if (n > idx->count - 1) { + pdftex_warn("Invalid CFF fontset index number."); + cff_close(cff); + return NULL; + } - cff->fontname = cff_get_name(cff); + cff->name = idx; - /* Top DICT INDEX */ - idx = cff_get_index(cff); - if (n > idx->count - 1) { - WARN("CFF Top DICT not exist..."); - cff_close(cff); - return NULL; - } - cff->topdict = cff_dict_unpack(idx->data + idx->offset[n] - 1, - idx->data + idx->offset[n + 1] - 1); - if (!cff->topdict) { - WARN("Parsing CFF Top DICT data failed..."); - cff_close(cff); - return NULL; - } - cff_release_index(idx); + cff->fontname = cff_get_name(cff); - if (cff_dict_known(cff->topdict, "CharstringType") && - cff_dict_get(cff->topdict, "CharstringType", 0) != 2) { - WARN("Only Type 2 Charstrings supported..."); - cff_close(cff); - return NULL; - } + /* Top DICT INDEX */ + idx = cff_get_index(cff); + if (n > idx->count - 1) { + WARN("CFF Top DICT not exist..."); + cff_close(cff); + return NULL; + } + cff->topdict = cff_dict_unpack(idx->data + idx->offset[n] - 1, + idx->data + idx->offset[n + 1] - 1); + if (!cff->topdict) { + WARN("Parsing CFF Top DICT data failed..."); + cff_close(cff); + return NULL; + } + cff_release_index(idx); - if (cff_dict_known(cff->topdict, "SyntheticBase")) { - WARN("CFF Synthetic font not supported."); - cff_close(cff); - return NULL; - } + if (cff_dict_known(cff->topdict, "CharstringType") && + cff_dict_get(cff->topdict, "CharstringType", 0) != 2) { + WARN("Only Type 2 Charstrings supported..."); + cff_close(cff); + return NULL; + } - /* String INDEX */ - cff->string = cff_get_index(cff); + if (cff_dict_known(cff->topdict, "SyntheticBase")) { + WARN("CFF Synthetic font not supported."); + cff_close(cff); + return NULL; + } - /* offset to GSubr */ - cff->gsubr_offset = cff->offset; + /* String INDEX */ + cff->string = cff_get_index(cff); - /* Number of glyphs */ - offset = (long) cff_dict_get(cff->topdict, "CharStrings", 0); - cff->offset = offset; - cff->num_glyphs = get_card16(cff); + /* offset to GSubr */ + cff->gsubr_offset = cff->offset; - /* Check for font type */ - if (cff_dict_known(cff->topdict, "ROS")) { - cff->flag |= FONTTYPE_CIDFONT; - } else { - cff->flag |= FONTTYPE_FONT; - } + /* Number of glyphs */ + offset = (long) cff_dict_get(cff->topdict, "CharStrings", 0); + cff->offset = offset; + cff->num_glyphs = get_card16(cff); - /* Check for encoding */ - if (cff_dict_known(cff->topdict, "Encoding")) { - offset = (long) cff_dict_get(cff->topdict, "Encoding", 0); - if (offset == 0) { /* predefined */ - cff->flag |= ENCODING_STANDARD; - } else if (offset == 1) { - cff->flag |= ENCODING_EXPERT; + /* Check for font type */ + if (cff_dict_known(cff->topdict, "ROS")) { + cff->flag |= FONTTYPE_CIDFONT; + } else { + cff->flag |= FONTTYPE_FONT; } - } else { - cff->flag |= ENCODING_STANDARD; - } - cff->offset = cff->gsubr_offset; /* seek back to GSubr */ + /* Check for encoding */ + if (cff_dict_known(cff->topdict, "Encoding")) { + offset = (long) cff_dict_get(cff->topdict, "Encoding", 0); + if (offset == 0) { /* predefined */ + cff->flag |= ENCODING_STANDARD; + } else if (offset == 1) { + cff->flag |= ENCODING_EXPERT; + } + } else { + cff->flag |= ENCODING_STANDARD; + } + + cff->offset = cff->gsubr_offset; /* seek back to GSubr */ - return cff; + return cff; } /* write a cff for opentype */ @@ -1116,610 +1157,610 @@ cff_font *read_cff (unsigned char *buf,long buflength, int n) /* Pack DICT data */ -static long pack_integer (card8 *dest, long destlen, long value) +static long pack_integer(card8 * dest, long destlen, long value) { - long len = 0; - - if (value >= -107 && value <= 107) { - if (destlen < 1) - CFF_ERROR("Buffer overflow."); - dest[0] = (value + 139) & 0xff; - len = 1; - } else if (value >= 108 && value <= 1131) { - if (destlen < 2) - CFF_ERROR("Buffer overflow."); - value = 0xf700u + value - 108; - dest[0] = (value >> 8) & 0xff; - dest[1] = value & 0xff; - len = 2; - } else if (value >= -1131 && value <= -108) { - if (destlen < 2) - CFF_ERROR("Buffer overflow."); - value = 0xfb00u - value - 108; - dest[0] = (value >> 8) & 0xff; - dest[1] = value & 0xff; - len = 2; - } else if (value >= -32768 && value <= 32767) { /* shortint */ - if (destlen < 3) - CFF_ERROR("Buffer overflow."); - dest[0] = 28; - dest[1] = (value >> 8) & 0xff; - dest[2] = value & 0xff; - len = 3; - } else { /* longint */ - if (destlen < 5) - CFF_ERROR("Buffer overflow."); - dest[0] = 29; - dest[1] = (value >> 24) & 0xff; - dest[2] = (value >> 16) & 0xff; - dest[3] = (value >> 8) & 0xff; - dest[4] = value & 0xff; - len = 5; - } - return len; + long len = 0; + + if (value >= -107 && value <= 107) { + if (destlen < 1) + CFF_ERROR("Buffer overflow."); + dest[0] = (value + 139) & 0xff; + len = 1; + } else if (value >= 108 && value <= 1131) { + if (destlen < 2) + CFF_ERROR("Buffer overflow."); + value = 0xf700u + value - 108; + dest[0] = (value >> 8) & 0xff; + dest[1] = value & 0xff; + len = 2; + } else if (value >= -1131 && value <= -108) { + if (destlen < 2) + CFF_ERROR("Buffer overflow."); + value = 0xfb00u - value - 108; + dest[0] = (value >> 8) & 0xff; + dest[1] = value & 0xff; + len = 2; + } else if (value >= -32768 && value <= 32767) { /* shortint */ + if (destlen < 3) + CFF_ERROR("Buffer overflow."); + dest[0] = 28; + dest[1] = (value >> 8) & 0xff; + dest[2] = value & 0xff; + len = 3; + } else { /* longint */ + if (destlen < 5) + CFF_ERROR("Buffer overflow."); + dest[0] = 29; + dest[1] = (value >> 24) & 0xff; + dest[2] = (value >> 16) & 0xff; + dest[3] = (value >> 8) & 0xff; + dest[4] = value & 0xff; + len = 5; + } + return len; } -static long pack_real (card8 *dest, long destlen, double value) +static long pack_real(card8 * dest, long destlen, double value) { - long e; - int i = 0, pos = 2; + long e; + int i = 0, pos = 2; #define CFF_REAL_MAX_LEN 17 - if (destlen < 2) - CFF_ERROR("Buffer overflow."); - - dest[0] = 30; - - if (value == 0.0) { - dest[1] = 0x0f; - return 2; - } - - if (value < 0.0) { - dest[1] = 0xe0; - value *= -1.0; - pos++; - } - - e = 0; - if (value >= 10.0) { - while (value >= 10.0) { - value /= 10.0; - e++; - } - } else if (value < 1.0) { - while (value < 1.0) { - value *= 10.0; - e--; - } - } - - sprintf(work_buffer, "%1.14g", value); - for (i=0;i<CFF_REAL_MAX_LEN;i++) { - unsigned char ch = 0; - if (work_buffer[i] == '\0') { - break; - } else if (work_buffer[i] == '.') { - ch = 0x0a; - } else if (work_buffer[i] >= '0' && work_buffer[i] <= '9') { - ch = work_buffer[i] - '0'; - } else { - CFF_ERROR("Invalid character."); - } - - if (destlen < pos/2 + 1) - CFF_ERROR("Buffer overflow."); - - if (pos % 2) { - dest[pos/2] += ch; - } else { - dest[pos/2] = (ch << 4); + if (destlen < 2) + CFF_ERROR("Buffer overflow."); + + dest[0] = 30; + + if (value == 0.0) { + dest[1] = 0x0f; + return 2; + } + + if (value < 0.0) { + dest[1] = 0xe0; + value *= -1.0; + pos++; + } + + e = 0; + if (value >= 10.0) { + while (value >= 10.0) { + value /= 10.0; + e++; + } + } else if (value < 1.0) { + while (value < 1.0) { + value *= 10.0; + e--; + } + } + + sprintf(work_buffer, "%1.14g", value); + for (i = 0; i < CFF_REAL_MAX_LEN; i++) { + unsigned char ch = 0; + if (work_buffer[i] == '\0') { + break; + } else if (work_buffer[i] == '.') { + ch = 0x0a; + } else if (work_buffer[i] >= '0' && work_buffer[i] <= '9') { + ch = work_buffer[i] - '0'; + } else { + CFF_ERROR("Invalid character."); + } + + if (destlen < pos / 2 + 1) + CFF_ERROR("Buffer overflow."); + + if (pos % 2) { + dest[pos / 2] += ch; + } else { + dest[pos / 2] = (ch << 4); + } + pos++; + } + + if (e > 0) { + if (pos % 2) { + dest[pos / 2] += 0x0b; + } else { + if (destlen < pos / 2 + 1) + CFF_ERROR("Buffer overflow."); + dest[pos / 2] = 0xb0; + } + pos++; + } else if (e < 0) { + if (pos % 2) { + dest[pos / 2] += 0x0c; + } else { + if (destlen < pos / 2 + 1) + CFF_ERROR("Buffer overflow."); + dest[pos / 2] = 0xc0; + } + e *= -1; + pos++; + } + + if (e != 0) { + sprintf(work_buffer, "%ld", e); + for (i = 0; i < CFF_REAL_MAX_LEN; i++) { + unsigned char ch = 0; + if (work_buffer[i] == '\0') { + break; + } else if (work_buffer[i] == '.') { + ch = 0x0a; + } else if (work_buffer[i] >= '0' && work_buffer[i] <= '9') { + ch = work_buffer[i] - '0'; + } else { + CFF_ERROR("Invalid character."); + } + + if (destlen < pos / 2 + 1) + CFF_ERROR("Buffer overflow."); + + if (pos % 2) { + dest[pos / 2] += ch; + } else { + dest[pos / 2] = (ch << 4); + } + pos++; + } } - pos++; - } - if (e > 0) { - if (pos % 2) { - dest[pos/2] += 0x0b; - } else { - if (destlen < pos/2 + 1) - CFF_ERROR("Buffer overflow."); - dest[pos/2] = 0xb0; - } - pos++; - } else if (e < 0) { if (pos % 2) { - dest[pos/2] += 0x0c; + dest[pos / 2] += 0x0f; + pos++; } else { - if (destlen < pos/2 + 1) - CFF_ERROR("Buffer overflow."); - dest[pos/2] = 0xc0; - } - e *= -1; - pos++; - } - - if (e != 0) { - sprintf(work_buffer, "%ld", e); - for (i=0;i<CFF_REAL_MAX_LEN;i++) { - unsigned char ch = 0; - if (work_buffer[i] == '\0') { - break; - } else if (work_buffer[i] == '.') { - ch = 0x0a; - } else if (work_buffer[i] >= '0' && work_buffer[i] <= '9') { - ch = work_buffer[i] - '0'; - } else { - CFF_ERROR("Invalid character."); - } - - if (destlen < pos/2 + 1) - CFF_ERROR("Buffer overflow."); - - if (pos % 2) { - dest[pos/2] += ch; - } else { - dest[pos/2] = (ch << 4); - } - pos++; + if (destlen < pos / 2 + 1) + CFF_ERROR("Buffer overflow."); + dest[pos / 2] = 0xff; + pos += 2; } - } - - if (pos % 2) { - dest[pos/2] += 0x0f; - pos++; - } else { - if (destlen < pos/2 + 1) - CFF_ERROR("Buffer overflow."); - dest[pos/2] = 0xff; - pos += 2; - } - return pos/2; + return pos / 2; } -static long cff_dict_put_number (double value, - card8 *dest, long destlen, - int type) +static long cff_dict_put_number(double value, + card8 * dest, long destlen, int type) { - long len = 0; - double nearint; - - nearint = floor(value+0.5); - /* set offset to longint */ - if (type == CFF_TYPE_OFFSET) { - long lvalue; - - lvalue = (long) value; - if (destlen < 5) - CFF_ERROR("Buffer overflow."); - dest[0] = 29; - dest[1] = (lvalue >> 24) & 0xff; - dest[2] = (lvalue >> 16) & 0xff; - dest[3] = (lvalue >> 8) & 0xff; - dest[4] = lvalue & 0xff; - len = 5; - } else if (value > CFF_INT_MAX || value < CFF_INT_MIN || - (fabs(value - nearint) > 1.0e-5)) { /* real */ - len = pack_real(dest, destlen, value); - } else { /* integer */ - len = pack_integer(dest, destlen, (long) nearint); - } - - return len; + long len = 0; + double nearint; + + nearint = floor(value + 0.5); + /* set offset to longint */ + if (type == CFF_TYPE_OFFSET) { + long lvalue; + + lvalue = (long) value; + if (destlen < 5) + CFF_ERROR("Buffer overflow."); + dest[0] = 29; + dest[1] = (lvalue >> 24) & 0xff; + dest[2] = (lvalue >> 16) & 0xff; + dest[3] = (lvalue >> 8) & 0xff; + dest[4] = lvalue & 0xff; + len = 5; + } else if (value > CFF_INT_MAX || value < CFF_INT_MIN || (fabs(value - nearint) > 1.0e-5)) { /* real */ + len = pack_real(dest, destlen, value); + } else { /* integer */ + len = pack_integer(dest, destlen, (long) nearint); + } + + return len; } -static long -put_dict_entry (cff_dict_entry *de, - card8 *dest, long destlen) +static long put_dict_entry(cff_dict_entry * de, card8 * dest, long destlen) { - long len = 0; - int i, type, id; - - if (de->count > 0) { - id = de->id; - if (dict_operator[id].argtype == CFF_TYPE_OFFSET || - dict_operator[id].argtype == CFF_TYPE_SZOFF) { - type = CFF_TYPE_OFFSET; - } else { - type = CFF_TYPE_NUMBER; - } - for (i = 0; i < de->count; i++) { - len += cff_dict_put_number(de->values[i], - dest+len, - destlen-len, type); - } - if (id >= 0 && id < CFF_LAST_DICT_OP1) { - if (len + 1 > destlen) - CFF_ERROR("Buffer overflow."); - dest[len++] = id; - } else if (id >= 0 && id < CFF_LAST_DICT_OP) { - if (len + 2 > destlen) - CFF_ERROR("in cff_dict_pack(): Buffer overflow"); - dest[len++] = 12; - dest[len++] = id - CFF_LAST_DICT_OP1; - } else { - CFF_ERROR("Invalid CFF DICT operator ID."); - } - } - - return len; + long len = 0; + int i, type, id; + + if (de->count > 0) { + id = de->id; + if (dict_operator[id].argtype == CFF_TYPE_OFFSET || + dict_operator[id].argtype == CFF_TYPE_SZOFF) { + type = CFF_TYPE_OFFSET; + } else { + type = CFF_TYPE_NUMBER; + } + for (i = 0; i < de->count; i++) { + len += cff_dict_put_number(de->values[i], + dest + len, destlen - len, type); + } + if (id >= 0 && id < CFF_LAST_DICT_OP1) { + if (len + 1 > destlen) + CFF_ERROR("Buffer overflow."); + dest[len++] = id; + } else if (id >= 0 && id < CFF_LAST_DICT_OP) { + if (len + 2 > destlen) + CFF_ERROR("in cff_dict_pack(): Buffer overflow"); + dest[len++] = 12; + dest[len++] = id - CFF_LAST_DICT_OP1; + } else { + CFF_ERROR("Invalid CFF DICT operator ID."); + } + } + + return len; } -long cff_dict_pack (cff_dict *dict, card8 *dest, long destlen) +long cff_dict_pack(cff_dict * dict, card8 * dest, long destlen) { - long len = 0; - int i; + long len = 0; + int i; - for (i = 0; i < dict->count; i++) { - if (!strcmp(dict->entries[i].key, "ROS")) { - len += put_dict_entry(&dict->entries[i], dest, destlen); - break; + for (i = 0; i < dict->count; i++) { + if (!strcmp(dict->entries[i].key, "ROS")) { + len += put_dict_entry(&dict->entries[i], dest, destlen); + break; + } } - } - for (i = 0; i < dict->count; i++) { - if (strcmp(dict->entries[i].key, "ROS")) { - len += put_dict_entry(&dict->entries[i], dest+len, destlen-len); + for (i = 0; i < dict->count; i++) { + if (strcmp(dict->entries[i].key, "ROS")) { + len += put_dict_entry(&dict->entries[i], dest + len, destlen - len); + } } - } - return len; + return len; } -void cff_dict_add (cff_dict *dict, const char *key, int count) +void cff_dict_add(cff_dict * dict, const char *key, int count) { - int id, i; + int id, i; - for (id=0;id<CFF_LAST_DICT_OP;id++) { - if (key && dict_operator[id].opname && - strcmp(dict_operator[id].opname, key) == 0) - break; - } + for (id = 0; id < CFF_LAST_DICT_OP; id++) { + if (key && dict_operator[id].opname && + strcmp(dict_operator[id].opname, key) == 0) + break; + } - if (id == CFF_LAST_DICT_OP) - CFF_ERROR("Unknown CFF DICT operator."); + if (id == CFF_LAST_DICT_OP) + CFF_ERROR("Unknown CFF DICT operator."); - for (i=0;i<dict->count;i++) { - if ((dict->entries)[i].id == id) { - if ((dict->entries)[i].count != count) - CFF_ERROR("Inconsistent DICT argument number."); - return; + for (i = 0; i < dict->count; i++) { + if ((dict->entries)[i].id == id) { + if ((dict->entries)[i].count != count) + CFF_ERROR("Inconsistent DICT argument number."); + return; + } } - } - if (dict->count + 1 >= dict->max) { - dict->max += 8; - dict->entries = xrealloc(dict->entries, (dict->max)*sizeof(cff_dict_entry)); - } + if (dict->count + 1 >= dict->max) { + dict->max += 8; + dict->entries = + xrealloc(dict->entries, (dict->max) * sizeof(cff_dict_entry)); + } - (dict->entries)[dict->count].id = id; - (dict->entries)[dict->count].key = (char *) dict_operator[id].opname; - (dict->entries)[dict->count].count = count; - if (count > 0) { - (dict->entries)[dict->count].values = xcalloc(count, sizeof(double)); - memset((dict->entries)[dict->count].values, - 0, sizeof(double)*count); - } else { - (dict->entries)[dict->count].values = NULL; - } - dict->count += 1; + (dict->entries)[dict->count].id = id; + (dict->entries)[dict->count].key = (char *) dict_operator[id].opname; + (dict->entries)[dict->count].count = count; + if (count > 0) { + (dict->entries)[dict->count].values = xcalloc(count, sizeof(double)); + memset((dict->entries)[dict->count].values, 0, sizeof(double) * count); + } else { + (dict->entries)[dict->count].values = NULL; + } + dict->count += 1; - return; + return; } -void cff_dict_remove (cff_dict *dict, const char *key) +void cff_dict_remove(cff_dict * dict, const char *key) { - int i; - for (i = 0; i < dict->count; i++) { - if (key && strcmp(key, (dict->entries)[i].key) == 0) { - (dict->entries)[i].count = 0; - if ((dict->entries)[i].values) - xfree((dict->entries)[i].values); - (dict->entries)[i].values = NULL; + int i; + for (i = 0; i < dict->count; i++) { + if (key && strcmp(key, (dict->entries)[i].key) == 0) { + (dict->entries)[i].count = 0; + if ((dict->entries)[i].values) + xfree((dict->entries)[i].values); + (dict->entries)[i].values = NULL; + } } - } } -void cff_dict_set (cff_dict *dict, const char *key, int idx, double value) +void cff_dict_set(cff_dict * dict, const char *key, int idx, double value) { - int i; + int i; - assert(dict && key); + assert(dict && key); - for (i = 0 ; i < dict->count; i++) { - if (strcmp(key, (dict->entries)[i].key) == 0) { - if ((dict->entries)[i].count > idx) - (dict->entries)[i].values[idx] = value; - else - CFF_ERROR("Invalid index number."); - break; + for (i = 0; i < dict->count; i++) { + if (strcmp(key, (dict->entries)[i].key) == 0) { + if ((dict->entries)[i].count > idx) + (dict->entries)[i].values[idx] = value; + else + CFF_ERROR("Invalid index number."); + break; + } } - } - if (i == dict->count) - pdftex_fail("DICT entry \"%s\" not found.", key); + if (i == dict->count) + pdftex_fail("DICT entry \"%s\" not found.", key); } /* Strings */ -char *cff_get_string (cff_font *cff, s_SID id) +char *cff_get_string(cff_font * cff, s_SID id) { - char *result = NULL; - long len; - - if (id < CFF_STDSTR_MAX) { - len = strlen(cff_stdstr[id]); - result = xcalloc(len+1, sizeof(char)); - memcpy(result, cff_stdstr[id], len); - result[len] = '\0'; - } else if (cff && cff->string) { - cff_index *strings = cff->string; - id -= CFF_STDSTR_MAX; - if (id < strings->count) { - len = (strings->offset)[id+1] - (strings->offset)[id]; - result = xcalloc(len + 1, sizeof(char)); - memmove(result, strings->data + (strings->offset)[id] - 1, len); - result[len] = '\0'; - } - } - - return result; + char *result = NULL; + long len; + + if (id < CFF_STDSTR_MAX) { + len = strlen(cff_stdstr[id]); + result = xcalloc(len + 1, sizeof(char)); + memcpy(result, cff_stdstr[id], len); + result[len] = '\0'; + } else if (cff && cff->string) { + cff_index *strings = cff->string; + id -= CFF_STDSTR_MAX; + if (id < strings->count) { + len = (strings->offset)[id + 1] - (strings->offset)[id]; + result = xcalloc(len + 1, sizeof(char)); + memmove(result, strings->data + (strings->offset)[id] - 1, len); + result[len] = '\0'; + } + } + + return result; } -long cff_get_sid (cff_font *cff, char *str) +long cff_get_sid(cff_font * cff, char *str) { - card16 i; + card16 i; - if (!cff || !str) - return -1; + if (!cff || !str) + return -1; - /* I search String INDEX first. */ - if (cff && cff->string) { - cff_index *idx = cff->string; - for (i = 0; i < idx->count; i++) { - if (strlen(str) == (idx->offset)[i+1] - (idx->offset)[i] && - !memcmp(str, (idx->data)+(idx->offset)[i]-1, strlen(str))) - return (i + CFF_STDSTR_MAX); + /* I search String INDEX first. */ + if (cff && cff->string) { + cff_index *idx = cff->string; + for (i = 0; i < idx->count; i++) { + if (strlen(str) == (idx->offset)[i + 1] - (idx->offset)[i] && + !memcmp(str, (idx->data) + (idx->offset)[i] - 1, strlen(str))) + return (i + CFF_STDSTR_MAX); + } } - } - for (i = 0; i < CFF_STDSTR_MAX; i++) { - if (!strcmp(str, cff_stdstr[i])) - return i; - } + for (i = 0; i < CFF_STDSTR_MAX; i++) { + if (!strcmp(str, cff_stdstr[i])) + return i; + } - return -1; + return -1; } -void cff_update_string (cff_font *cff) +void cff_update_string(cff_font * cff) { - if (cff == NULL) - CFF_ERROR("CFF font not opened."); - - if (cff->string) - cff_release_index(cff->string); - cff->string = cff->_string; - cff->_string = NULL; + if (cff == NULL) + CFF_ERROR("CFF font not opened."); + + if (cff->string) + cff_release_index(cff->string); + cff->string = cff->_string; + cff->_string = NULL; } -s_SID cff_add_string (cff_font *cff, char *str) +s_SID cff_add_string(cff_font * cff, char *str) { - card16 idx; - cff_index *strings; - l_offset offset, size; - - if (cff == NULL) - CFF_ERROR("CFF font not opened."); - - if (cff->_string == NULL) - cff->_string = cff_new_index(0); - strings = cff->_string; - - for (idx = 0; idx < strings->count; idx++) { - size = strings->offset[idx+1] - strings->offset[idx]; - offset = strings->offset[idx]; - if (size == strlen(str) && - !memcmp(strings->data+offset-1, str, strlen(str))) - return (idx + CFF_STDSTR_MAX); - } - - for (idx = 0; idx < CFF_STDSTR_MAX; idx++) { - if (cff_stdstr[idx] && - !strcmp(cff_stdstr[idx], str)) - return idx; - } - offset = (strings->count > 0) ? strings->offset[strings->count] : 1; - strings->offset = xrealloc(strings->offset, (strings->count+2)*sizeof(l_offset)); - if (strings->count == 0) - strings->offset[0] = 1; - idx = strings->count; - strings->count += 1; - strings->offset[strings->count] = offset + strlen(str); - strings->data = xrealloc(strings->data, (offset+strlen(str)-1)*sizeof(card8)); - memcpy(strings->data+offset-1, str, strlen(str)); - - return (idx + CFF_STDSTR_MAX); + card16 idx; + cff_index *strings; + l_offset offset, size; + + if (cff == NULL) + CFF_ERROR("CFF font not opened."); + + if (cff->_string == NULL) + cff->_string = cff_new_index(0); + strings = cff->_string; + + for (idx = 0; idx < strings->count; idx++) { + size = strings->offset[idx + 1] - strings->offset[idx]; + offset = strings->offset[idx]; + if (size == strlen(str) && + !memcmp(strings->data + offset - 1, str, strlen(str))) + return (idx + CFF_STDSTR_MAX); + } + + for (idx = 0; idx < CFF_STDSTR_MAX; idx++) { + if (cff_stdstr[idx] && !strcmp(cff_stdstr[idx], str)) + return idx; + } + offset = (strings->count > 0) ? strings->offset[strings->count] : 1; + strings->offset = + xrealloc(strings->offset, (strings->count + 2) * sizeof(l_offset)); + if (strings->count == 0) + strings->offset[0] = 1; + idx = strings->count; + strings->count += 1; + strings->offset[strings->count] = offset + strlen(str); + strings->data = + xrealloc(strings->data, (offset + strlen(str) - 1) * sizeof(card8)); + memcpy(strings->data + offset - 1, str, strlen(str)); + + return (idx + CFF_STDSTR_MAX); } -void cff_dict_update (cff_dict *dict, cff_font *cff) +void cff_dict_update(cff_dict * dict, cff_font * cff) { - int i; - - for (i = 0;i < dict->count; i++) { - if ((dict->entries)[i].count > 0) { - char *str; - int id; - - id = (dict->entries)[i].id; - - if (dict_operator[id].argtype == CFF_TYPE_SID) { - str = cff_get_string(cff, (dict->entries)[i].values[0]); - (dict->entries)[i].values[0] = cff_add_string(cff, str); - xfree(str); - } else if (dict_operator[id].argtype == CFF_TYPE_ROS) { - str = cff_get_string(cff, (dict->entries)[i].values[0]); - (dict->entries)[i].values[0] = cff_add_string(cff, str); - xfree(str); - str = cff_get_string(cff, (dict->entries)[i].values[1]); - (dict->entries)[i].values[1] = cff_add_string(cff, str); - xfree(str); - } - + int i; + + for (i = 0; i < dict->count; i++) { + if ((dict->entries)[i].count > 0) { + char *str; + int id; + + id = (dict->entries)[i].id; + + if (dict_operator[id].argtype == CFF_TYPE_SID) { + str = cff_get_string(cff, (dict->entries)[i].values[0]); + (dict->entries)[i].values[0] = cff_add_string(cff, str); + xfree(str); + } else if (dict_operator[id].argtype == CFF_TYPE_ROS) { + str = cff_get_string(cff, (dict->entries)[i].values[0]); + (dict->entries)[i].values[0] = cff_add_string(cff, str); + xfree(str); + str = cff_get_string(cff, (dict->entries)[i].values[1]); + (dict->entries)[i].values[1] = cff_add_string(cff, str); + xfree(str); + } + + } } - } } /* charsets */ -long cff_read_charsets (cff_font *cff) +long cff_read_charsets(cff_font * cff) { - cff_charsets *charset; - long offset, length; - card16 count, i; + cff_charsets *charset; + long offset, length; + card16 count, i; - if (cff->topdict == NULL) - CFF_ERROR("Top DICT not available"); + if (cff->topdict == NULL) + CFF_ERROR("Top DICT not available"); - if (!cff_dict_known(cff->topdict, "charset")) { - cff->flag |= CHARSETS_ISOADOBE; - cff->charsets = NULL; - return 0; - } + if (!cff_dict_known(cff->topdict, "charset")) { + cff->flag |= CHARSETS_ISOADOBE; + cff->charsets = NULL; + return 0; + } - offset = (long) cff_dict_get(cff->topdict, "charset", 0); + offset = (long) cff_dict_get(cff->topdict, "charset", 0); - if (offset == 0) { /* predefined */ - cff->flag |= CHARSETS_ISOADOBE; - cff->charsets = NULL; - return 0; - } else if (offset == 1) { - cff->flag |= CHARSETS_EXPERT; - cff->charsets = NULL; - return 0; - } else if (offset == 2) { - cff->flag |= CHARSETS_EXPSUB; - cff->charsets = NULL; - return 0; - } + if (offset == 0) { /* predefined */ + cff->flag |= CHARSETS_ISOADOBE; + cff->charsets = NULL; + return 0; + } else if (offset == 1) { + cff->flag |= CHARSETS_EXPERT; + cff->charsets = NULL; + return 0; + } else if (offset == 2) { + cff->flag |= CHARSETS_EXPSUB; + cff->charsets = NULL; + return 0; + } - cff->offset = offset; - cff->charsets = charset = xcalloc(1, sizeof(cff_charsets)); - charset->format = get_card8(cff); - charset->num_entries = 0; - - count = cff->num_glyphs - 1; - length = 1; - - /* Not sure. Not well documented. */ - switch (charset->format) { - case 0: - charset->num_entries = cff->num_glyphs - 1; /* no .notdef */ - charset->data.glyphs = xcalloc(charset->num_entries, sizeof(s_SID)); - length += (charset->num_entries) * 2; - for (i=0;i<(charset->num_entries);i++) { - charset->data.glyphs[i] = get_card16(cff); - } - count = 0; - break; - case 1: - { - cff_range1 *ranges = NULL; - while (count > 0 && charset->num_entries < cff->num_glyphs) { - ranges = xrealloc(ranges, (charset->num_entries + 1)*sizeof(cff_range1)); - ranges[charset->num_entries].first = get_card16(cff); - ranges[charset->num_entries].n_left = get_card8(cff); - count -= ranges[charset->num_entries].n_left + 1; /* no-overrap */ - charset->num_entries += 1; - charset->data.range1 = ranges; - } - length += (charset->num_entries) * 3; - } - break; - case 2: - { - cff_range2 *ranges = NULL; - while (count > 0 && charset->num_entries < cff->num_glyphs) { - ranges = xrealloc(ranges, (charset->num_entries + 1)*sizeof(cff_range2)); - ranges[charset->num_entries].first = get_card16(cff); - ranges[charset->num_entries].n_left = get_card16(cff); - count -= ranges[charset->num_entries].n_left + 1; /* non-overrapping */ - charset->num_entries += 1; - } - charset->data.range2 = ranges; - length += (charset->num_entries) * 4; - } - break; - default: - xfree(charset); - CFF_ERROR("Unknown Charset format"); - break; - } + cff->offset = offset; + cff->charsets = charset = xcalloc(1, sizeof(cff_charsets)); + charset->format = get_card8(cff); + charset->num_entries = 0; - if (count > 0) - CFF_ERROR("Charset data possibly broken"); + count = cff->num_glyphs - 1; + length = 1; - return length; + /* Not sure. Not well documented. */ + switch (charset->format) { + case 0: + charset->num_entries = cff->num_glyphs - 1; /* no .notdef */ + charset->data.glyphs = xcalloc(charset->num_entries, sizeof(s_SID)); + length += (charset->num_entries) * 2; + for (i = 0; i < (charset->num_entries); i++) { + charset->data.glyphs[i] = get_card16(cff); + } + count = 0; + break; + case 1: + { + cff_range1 *ranges = NULL; + while (count > 0 && charset->num_entries < cff->num_glyphs) { + ranges = + xrealloc(ranges, + (charset->num_entries + 1) * sizeof(cff_range1)); + ranges[charset->num_entries].first = get_card16(cff); + ranges[charset->num_entries].n_left = get_card8(cff); + count -= ranges[charset->num_entries].n_left + 1; /* no-overrap */ + charset->num_entries += 1; + charset->data.range1 = ranges; + } + length += (charset->num_entries) * 3; + } + break; + case 2: + { + cff_range2 *ranges = NULL; + while (count > 0 && charset->num_entries < cff->num_glyphs) { + ranges = + xrealloc(ranges, + (charset->num_entries + 1) * sizeof(cff_range2)); + ranges[charset->num_entries].first = get_card16(cff); + ranges[charset->num_entries].n_left = get_card16(cff); + count -= ranges[charset->num_entries].n_left + 1; /* non-overrapping */ + charset->num_entries += 1; + } + charset->data.range2 = ranges; + length += (charset->num_entries) * 4; + } + break; + default: + xfree(charset); + CFF_ERROR("Unknown Charset format"); + break; + } + + if (count > 0) + CFF_ERROR("Charset data possibly broken"); + + return length; } -long cff_pack_charsets (cff_font *cff, card8 *dest, long destlen) +long cff_pack_charsets(cff_font * cff, card8 * dest, long destlen) { - long len = 0; - card16 i; - cff_charsets *charset; - - if (cff->flag & HAVE_STANDARD_CHARSETS || cff->charsets == NULL) - return 0; + long len = 0; + card16 i; + cff_charsets *charset; - if (destlen < 1) - CFF_ERROR("in cff_pack_charsets(): Buffer overflow"); + if (cff->flag & HAVE_STANDARD_CHARSETS || cff->charsets == NULL) + return 0; - charset = cff->charsets; + if (destlen < 1) + CFF_ERROR("in cff_pack_charsets(): Buffer overflow"); - dest[len++] = charset->format; - switch (charset->format) { - case 0: - if (destlen < len + (charset->num_entries)*2) - CFF_ERROR("in cff_pack_charsets(): Buffer overflow"); - for (i=0;i<(charset->num_entries);i++) { - s_SID sid = (charset->data).glyphs[i]; /* or CID */ - dest[len++] = (sid >> 8) & 0xff; - dest[len++] = sid & 0xff; - } - break; - case 1: - { - if (destlen < len + (charset->num_entries)*3) - CFF_ERROR("in cff_pack_charsets(): Buffer overflow"); - for (i=0;i<(charset->num_entries);i++) { - dest[len++] = ((charset->data).range1[i].first >> 8) & 0xff; - dest[len++] = (charset->data).range1[i].first & 0xff; - dest[len++] = (charset->data).range1[i].n_left; - } - } - break; - case 2: - { - if (destlen < len + (charset->num_entries)*4) - CFF_ERROR("in cff_pack_charsets(): Buffer overflow"); - for (i=0;i<(charset->num_entries);i++) { - dest[len++] = ((charset->data).range2[i].first >> 8) & 0xff; - dest[len++] = (charset->data).range2[i].first & 0xff; - dest[len++] = ((charset->data).range2[i].n_left >> 8) & 0xff; - dest[len++] = (charset->data).range2[i].n_left & 0xff; - } - } - break; - default: - CFF_ERROR("Unknown Charset format"); - break; - } + charset = cff->charsets; - return len; + dest[len++] = charset->format; + switch (charset->format) { + case 0: + if (destlen < len + (charset->num_entries) * 2) + CFF_ERROR("in cff_pack_charsets(): Buffer overflow"); + for (i = 0; i < (charset->num_entries); i++) { + s_SID sid = (charset->data).glyphs[i]; /* or CID */ + dest[len++] = (sid >> 8) & 0xff; + dest[len++] = sid & 0xff; + } + break; + case 1: + { + if (destlen < len + (charset->num_entries) * 3) + CFF_ERROR("in cff_pack_charsets(): Buffer overflow"); + for (i = 0; i < (charset->num_entries); i++) { + dest[len++] = ((charset->data).range1[i].first >> 8) & 0xff; + dest[len++] = (charset->data).range1[i].first & 0xff; + dest[len++] = (charset->data).range1[i].n_left; + } + } + break; + case 2: + { + if (destlen < len + (charset->num_entries) * 4) + CFF_ERROR("in cff_pack_charsets(): Buffer overflow"); + for (i = 0; i < (charset->num_entries); i++) { + dest[len++] = ((charset->data).range2[i].first >> 8) & 0xff; + dest[len++] = (charset->data).range2[i].first & 0xff; + dest[len++] = ((charset->data).range2[i].n_left >> 8) & 0xff; + dest[len++] = (charset->data).range2[i].n_left & 0xff; + } + } + break; + default: + CFF_ERROR("Unknown Charset format"); + break; + } + + return len; } @@ -1771,14 +1812,14 @@ static int status = CS_PARSE_CFF_ERROR; /* hintmask and cntrmask need number of stem zones */ static int num_stems = 0; -static int phase = 0; +static int phase = 0; /* subroutine nesting */ -static int cs2_nest = 0; +static int cs2_nest = 0; /* advance width */ -static int have_width = 0; -static double width = 0.0; +static int have_width = 0; +static double width = 0.0; /* * Standard Encoding Accented Characters: @@ -1787,11 +1828,11 @@ static double width = 0.0; */ #if 0 /* adx ady bchar achar endchar */ -static double seac[4] = {0.0, 0.0, 0.0, 0.0}; +static double seac[4] = { 0.0, 0.0, 0.0, 0.0 }; #endif /* Operand stack and Transient array */ -static int cs2_stack_top = 0; +static int cs2_stack_top = 0; static double cs2_arg_stack[CS_ARG_STACK_MAX]; static double trn_array[CS_TRANS_ARRAY_MAX]; @@ -1864,7 +1905,7 @@ static double trn_array[CS_TRANS_ARRAY_MAX]; /* RESERVED 19 */ #define cs_put 20 #define cs_get 21 -#define cs_ifelse 22 +#define cs_ifelse 22 #define cs_random 23 #define cs_mul 24 /* RESERVED 25 */ @@ -1884,60 +1925,59 @@ static double trn_array[CS_TRANS_ARRAY_MAX]; /* * clear_stack() put all operands sotred in operand stack to dest. */ -static void -clear_stack (card8 **dest, card8 *limit) +static void clear_stack(card8 ** dest, card8 * limit) { - int i; - - for (i = 0; i < cs2_stack_top; i++) { - double value; - long ivalue; - value = cs2_arg_stack[i]; - /* Nearest integer value */ - ivalue = (long) floor(value+0.5); - if (value >= 0x8000L || value <= (-0x8000L - 1)) { - /* - * This number cannot be represented as a single operand. - * We must use `a b mul ...' or `a c div' to represent large values. - */ - CFF_ERROR("Argument value too large. (This is bug)"); - } else if (fabs(value - ivalue) > 3.0e-5) { - /* 16.16-bit signed fixed value */ - DST_NEED(limit, *dest + 5); - *(*dest)++ = 255; - ivalue = (long) floor(value); /* mantissa */ - *(*dest)++ = (ivalue >> 8) & 0xff; - *(*dest)++ = ivalue & 0xff; - ivalue = (long)((value - ivalue) * 0x10000l); /* fraction */ - *(*dest)++ = (ivalue >> 8) & 0xff; - *(*dest)++ = ivalue & 0xff; - /* Everything else are integers. */ - } else if (ivalue >= -107 && ivalue <= 107) { - DST_NEED(limit, *dest + 1); - *(*dest)++ = ivalue + 139; - } else if (ivalue >= 108 && ivalue <= 1131) { - DST_NEED(limit, *dest + 2); - ivalue = 0xf700u + ivalue - 108; - *(*dest)++ = (ivalue >> 8) & 0xff; - *(*dest)++ = ivalue & 0xff; - } else if (ivalue >= -1131 && ivalue <= -108) { - DST_NEED(limit, *dest + 2); - ivalue = 0xfb00u - ivalue - 108; - *(*dest)++ = (ivalue >> 8) & 0xff; - *(*dest)++ = ivalue & 0xff; - } else if (ivalue >= -32768 && ivalue <= 32767) { /* shortint */ - DST_NEED(limit, *dest + 3); - *(*dest)++ = 28; - *(*dest)++ = (ivalue >> 8) & 0xff; - *(*dest)++ = (ivalue) & 0xff; - } else { /* Shouldn't come here */ - CFF_ERROR("Unexpected error."); - } - } + int i; - cs2_stack_top = 0; /* clear stack */ + for (i = 0; i < cs2_stack_top; i++) { + double value; + long ivalue; + value = cs2_arg_stack[i]; + /* Nearest integer value */ + ivalue = (long) floor(value + 0.5); + if (value >= 0x8000L || value <= (-0x8000L - 1)) { + /* + * This number cannot be represented as a single operand. + * We must use `a b mul ...' or `a c div' to represent large values. + */ + CFF_ERROR("Argument value too large. (This is bug)"); + } else if (fabs(value - ivalue) > 3.0e-5) { + /* 16.16-bit signed fixed value */ + DST_NEED(limit, *dest + 5); + *(*dest)++ = 255; + ivalue = (long) floor(value); /* mantissa */ + *(*dest)++ = (ivalue >> 8) & 0xff; + *(*dest)++ = ivalue & 0xff; + ivalue = (long) ((value - ivalue) * 0x10000l); /* fraction */ + *(*dest)++ = (ivalue >> 8) & 0xff; + *(*dest)++ = ivalue & 0xff; + /* Everything else are integers. */ + } else if (ivalue >= -107 && ivalue <= 107) { + DST_NEED(limit, *dest + 1); + *(*dest)++ = ivalue + 139; + } else if (ivalue >= 108 && ivalue <= 1131) { + DST_NEED(limit, *dest + 2); + ivalue = 0xf700u + ivalue - 108; + *(*dest)++ = (ivalue >> 8) & 0xff; + *(*dest)++ = ivalue & 0xff; + } else if (ivalue >= -1131 && ivalue <= -108) { + DST_NEED(limit, *dest + 2); + ivalue = 0xfb00u - ivalue - 108; + *(*dest)++ = (ivalue >> 8) & 0xff; + *(*dest)++ = ivalue & 0xff; + } else if (ivalue >= -32768 && ivalue <= 32767) { /* shortint */ + DST_NEED(limit, *dest + 3); + *(*dest)++ = 28; + *(*dest)++ = (ivalue >> 8) & 0xff; + *(*dest)++ = (ivalue) & 0xff; + } else { /* Shouldn't come here */ + CFF_ERROR("Unexpected error."); + } + } + + cs2_stack_top = 0; /* clear stack */ - return; + return; } /* @@ -1951,122 +1991,122 @@ clear_stack (card8 **dest, card8 *limit) */ static void -do_operator1 (card8 **dest, card8 *limit, card8 **data, card8 *endptr) +do_operator1(card8 ** dest, card8 * limit, card8 ** data, card8 * endptr) { - card8 op = **data; - - *data += 1; - - switch (op) { - case cs_hstemhm: - case cs_vstemhm: - /* charstring may have hintmask if above operator have seen */ - case cs_hstem: - case cs_vstem: - if (phase == 0 && (cs2_stack_top % 2)) { - have_width = 1; - width = cs2_arg_stack[0]; - } - num_stems += cs2_stack_top/2; - clear_stack(dest, limit); - DST_NEED(limit, *dest + 1); - *(*dest)++ = op; - phase = 1; - break; - case cs_hintmask: - case cs_cntrmask: - if (phase < 2) { - if (phase == 0 && (cs2_stack_top % 2)) { - have_width = 1; - width = cs2_arg_stack[0]; - } - num_stems += cs2_stack_top/2; - } - clear_stack(dest, limit); - DST_NEED(limit, *dest + 1); - *(*dest)++ = op; - if (num_stems > 0) { - int masklen = (num_stems + 7) / 8; - DST_NEED(limit, *dest + masklen); - SRC_NEED(endptr, *data + masklen); - memmove(*dest, *data, masklen); - *data += masklen; - *dest += masklen; - } - phase = 2; - break; - case cs_rmoveto: - if (phase == 0 && (cs2_stack_top % 2)) { - have_width = 1; - width = cs2_arg_stack[0]; - } - clear_stack(dest, limit); - DST_NEED(limit, *dest + 1); - *(*dest)++ = op; - phase = 2; - break; - case cs_hmoveto: - case cs_vmoveto: - if (phase == 0 && (cs2_stack_top % 2) == 0) { - have_width = 1; - width = cs2_arg_stack[0]; - } - clear_stack(dest, limit); - DST_NEED(limit, *dest + 1); - *(*dest)++ = op; - phase = 2; - break; - case cs_endchar: - if (cs2_stack_top == 1) { - have_width = 1; - width = cs2_arg_stack[0]; - clear_stack(dest, limit); - } else if (cs2_stack_top == 4 || cs2_stack_top == 5) { - WARN("\"seac\" character deprecated in Type 2 charstring."); - status = CS_PARSE_CFF_ERROR; - return; - } else if (cs2_stack_top > 0) { - WARN("Operand stack not empty."); - } - DST_NEED(limit, *dest + 1); - *(*dest)++ = op; - status = CS_CHAR_END; - break; - /* above oprators are candidate for first stack-clearing operator */ - case cs_rlineto: - case cs_hlineto: - case cs_vlineto: - case cs_rrcurveto: - case cs_rcurveline: - case cs_rlinecurve: - case cs_vvcurveto: - case cs_hhcurveto: - case cs_vhcurveto: - case cs_hvcurveto: - if (phase < 2) { - WARN("Broken Type 2 charstring."); - status = CS_PARSE_CFF_ERROR; - return; - } - clear_stack(dest, limit); - DST_NEED(limit, *dest + 1); - *(*dest)++ = op; - break; - /* all operotors above are stack-clearing operator */ - /* no output */ - case cs_return: - case cs_callgsubr: - case cs_callsubr: - CFF_ERROR("Unexpected call(g)subr/return"); - break; - default: - /* no-op ? */ - WARN("%s: Unknown charstring operator: 0x%02x", CS_TYPE2_DEBUG_STR, op); - status = CS_PARSE_CFF_ERROR; - break; - } + card8 op = **data; + + *data += 1; + + switch (op) { + case cs_hstemhm: + case cs_vstemhm: + /* charstring may have hintmask if above operator have seen */ + case cs_hstem: + case cs_vstem: + if (phase == 0 && (cs2_stack_top % 2)) { + have_width = 1; + width = cs2_arg_stack[0]; + } + num_stems += cs2_stack_top / 2; + clear_stack(dest, limit); + DST_NEED(limit, *dest + 1); + *(*dest)++ = op; + phase = 1; + break; + case cs_hintmask: + case cs_cntrmask: + if (phase < 2) { + if (phase == 0 && (cs2_stack_top % 2)) { + have_width = 1; + width = cs2_arg_stack[0]; + } + num_stems += cs2_stack_top / 2; + } + clear_stack(dest, limit); + DST_NEED(limit, *dest + 1); + *(*dest)++ = op; + if (num_stems > 0) { + int masklen = (num_stems + 7) / 8; + DST_NEED(limit, *dest + masklen); + SRC_NEED(endptr, *data + masklen); + memmove(*dest, *data, masklen); + *data += masklen; + *dest += masklen; + } + phase = 2; + break; + case cs_rmoveto: + if (phase == 0 && (cs2_stack_top % 2)) { + have_width = 1; + width = cs2_arg_stack[0]; + } + clear_stack(dest, limit); + DST_NEED(limit, *dest + 1); + *(*dest)++ = op; + phase = 2; + break; + case cs_hmoveto: + case cs_vmoveto: + if (phase == 0 && (cs2_stack_top % 2) == 0) { + have_width = 1; + width = cs2_arg_stack[0]; + } + clear_stack(dest, limit); + DST_NEED(limit, *dest + 1); + *(*dest)++ = op; + phase = 2; + break; + case cs_endchar: + if (cs2_stack_top == 1) { + have_width = 1; + width = cs2_arg_stack[0]; + clear_stack(dest, limit); + } else if (cs2_stack_top == 4 || cs2_stack_top == 5) { + WARN("\"seac\" character deprecated in Type 2 charstring."); + status = CS_PARSE_CFF_ERROR; + return; + } else if (cs2_stack_top > 0) { + WARN("Operand stack not empty."); + } + DST_NEED(limit, *dest + 1); + *(*dest)++ = op; + status = CS_CHAR_END; + break; + /* above oprators are candidate for first stack-clearing operator */ + case cs_rlineto: + case cs_hlineto: + case cs_vlineto: + case cs_rrcurveto: + case cs_rcurveline: + case cs_rlinecurve: + case cs_vvcurveto: + case cs_hhcurveto: + case cs_vhcurveto: + case cs_hvcurveto: + if (phase < 2) { + WARN("Broken Type 2 charstring."); + status = CS_PARSE_CFF_ERROR; + return; + } + clear_stack(dest, limit); + DST_NEED(limit, *dest + 1); + *(*dest)++ = op; + break; + /* all operotors above are stack-clearing operator */ + /* no output */ + case cs_return: + case cs_callgsubr: + case cs_callsubr: + CFF_ERROR("Unexpected call(g)subr/return"); + break; + default: + /* no-op ? */ + WARN("%s: Unknown charstring operator: 0x%02x", CS_TYPE2_DEBUG_STR, op); + status = CS_PARSE_CFF_ERROR; + break; + } - return; + return; } /* @@ -2077,272 +2117,276 @@ do_operator1 (card8 **dest, card8 *limit, card8 **data, card8 *endptr) * random: How random ? */ static void -do_operator2 (card8 **dest, card8 *limit, card8 **data, card8 *endptr) +do_operator2(card8 ** dest, card8 * limit, card8 ** data, card8 * endptr) { - card8 op; + card8 op; - *data += 1; + *data += 1; - SRC_NEED(endptr, *data + 1); + SRC_NEED(endptr, *data + 1); - op = **data; - *data += 1; + op = **data; + *data += 1; - switch(op) { - case cs_dotsection: /* deprecated */ - WARN("Operator \"dotsection\" deprecated in Type 2 charstring."); - status = CS_PARSE_CFF_ERROR; - return; - break; - case cs_hflex: - case cs_flex: - case cs_hflex1: - case cs_flex1: - if (phase < 2) { - WARN("%s: Broken Type 2 charstring.", CS_TYPE2_DEBUG_STR); - status = CS_PARSE_CFF_ERROR; - return; - } - clear_stack(dest, limit); - DST_NEED(limit, *dest + 2); - *(*dest)++ = cs_escape; - *(*dest)++ = op; - break; - /* all operator above are stack-clearing */ - /* no output */ - case cs_and: - NEED(cs2_stack_top, 2); - cs2_stack_top--; - if (cs2_arg_stack[cs2_stack_top] && cs2_arg_stack[cs2_stack_top-1]) { - cs2_arg_stack[cs2_stack_top-1] = 1.0; - } else { - cs2_arg_stack[cs2_stack_top-1] = 0.0; - } - break; - case cs_or: - NEED(cs2_stack_top, 2); - cs2_stack_top--; - if (cs2_arg_stack[cs2_stack_top] || cs2_arg_stack[cs2_stack_top-1]) { - cs2_arg_stack[cs2_stack_top-1] = 1.0; - } else { - cs2_arg_stack[cs2_stack_top-1] = 0.0; - } - break; - case cs_not: - NEED(cs2_stack_top, 1); - if (cs2_arg_stack[cs2_stack_top-1]) { - cs2_arg_stack[cs2_stack_top-1] = 0.0; - } else { - cs2_arg_stack[cs2_stack_top-1] = 1.0; - } - break; - case cs_abs: - NEED(cs2_stack_top, 1); - cs2_arg_stack[cs2_stack_top-1] = fabs(cs2_arg_stack[cs2_stack_top-1]); - break; - case cs_add: - NEED(cs2_stack_top, 2); - cs2_arg_stack[cs2_stack_top-2] += cs2_arg_stack[cs2_stack_top-1]; - cs2_stack_top--; - break; - case cs_sub: - NEED(cs2_stack_top, 2); - cs2_arg_stack[cs2_stack_top-2] -= cs2_arg_stack[cs2_stack_top-1]; - cs2_stack_top--; - break; - case cs_div: /* doesn't check overflow */ - NEED(cs2_stack_top, 2); - cs2_arg_stack[cs2_stack_top-2] /= cs2_arg_stack[cs2_stack_top-1]; - cs2_stack_top--; - break; - case cs_neg: - NEED(cs2_stack_top, 1); - cs2_arg_stack[cs2_stack_top-1] *= -1.0; - break; - case cs_eq: - NEED(cs2_stack_top, 2); - cs2_stack_top--; - if (cs2_arg_stack[cs2_stack_top] == cs2_arg_stack[cs2_stack_top-1]) { - cs2_arg_stack[cs2_stack_top-1] = 1.0; - } else { - cs2_arg_stack[cs2_stack_top-1] = 0.0; - } - break; - case cs_drop: - NEED(cs2_stack_top, 1); - cs2_stack_top--; - break; - case cs_put: - NEED(cs2_stack_top, 2); - { - int idx = (int)cs2_arg_stack[--cs2_stack_top]; - NEED(CS_TRANS_ARRAY_MAX, idx); - trn_array[idx] = cs2_arg_stack[--cs2_stack_top]; - } - break; - case cs_get: - NEED(cs2_stack_top, 1); - { - int idx = (int)cs2_arg_stack[cs2_stack_top-1]; - NEED(CS_TRANS_ARRAY_MAX, idx); - cs2_arg_stack[cs2_stack_top-1] = trn_array[idx]; - } - break; - case cs_ifelse: - NEED(cs2_stack_top, 4); - cs2_stack_top -= 3; - if (cs2_arg_stack[cs2_stack_top+1] > cs2_arg_stack[cs2_stack_top+2]) { - cs2_arg_stack[cs2_stack_top-1] = cs2_arg_stack[cs2_stack_top]; - } - break; - case cs_mul: - NEED(cs2_stack_top, 2); - cs2_arg_stack[cs2_stack_top-2] = cs2_arg_stack[cs2_stack_top-2] * cs2_arg_stack[cs2_stack_top-1]; - cs2_stack_top--; - break; - case cs_sqrt: - NEED(cs2_stack_top, 1); - cs2_arg_stack[cs2_stack_top-1] = sqrt(cs2_arg_stack[cs2_stack_top-1]); - break; - case cs_dup: - NEED(cs2_stack_top, 1); - NEED(CS_ARG_STACK_MAX, cs2_stack_top+1); - cs2_arg_stack[cs2_stack_top] = cs2_arg_stack[cs2_stack_top-1]; - cs2_stack_top++; - break; - case cs_exch: - NEED(cs2_stack_top, 2); - { - double save = cs2_arg_stack[cs2_stack_top-2]; - cs2_arg_stack[cs2_stack_top-2] = cs2_arg_stack[cs2_stack_top-1]; - cs2_arg_stack[cs2_stack_top-1] = save; + switch (op) { + case cs_dotsection: /* deprecated */ + WARN("Operator \"dotsection\" deprecated in Type 2 charstring."); + status = CS_PARSE_CFF_ERROR; + return; + break; + case cs_hflex: + case cs_flex: + case cs_hflex1: + case cs_flex1: + if (phase < 2) { + WARN("%s: Broken Type 2 charstring.", CS_TYPE2_DEBUG_STR); + status = CS_PARSE_CFF_ERROR; + return; + } + clear_stack(dest, limit); + DST_NEED(limit, *dest + 2); + *(*dest)++ = cs_escape; + *(*dest)++ = op; + break; + /* all operator above are stack-clearing */ + /* no output */ + case cs_and: + NEED(cs2_stack_top, 2); + cs2_stack_top--; + if (cs2_arg_stack[cs2_stack_top] && cs2_arg_stack[cs2_stack_top - 1]) { + cs2_arg_stack[cs2_stack_top - 1] = 1.0; + } else { + cs2_arg_stack[cs2_stack_top - 1] = 0.0; + } + break; + case cs_or: + NEED(cs2_stack_top, 2); + cs2_stack_top--; + if (cs2_arg_stack[cs2_stack_top] || cs2_arg_stack[cs2_stack_top - 1]) { + cs2_arg_stack[cs2_stack_top - 1] = 1.0; + } else { + cs2_arg_stack[cs2_stack_top - 1] = 0.0; + } + break; + case cs_not: + NEED(cs2_stack_top, 1); + if (cs2_arg_stack[cs2_stack_top - 1]) { + cs2_arg_stack[cs2_stack_top - 1] = 0.0; + } else { + cs2_arg_stack[cs2_stack_top - 1] = 1.0; + } + break; + case cs_abs: + NEED(cs2_stack_top, 1); + cs2_arg_stack[cs2_stack_top - 1] = + fabs(cs2_arg_stack[cs2_stack_top - 1]); + break; + case cs_add: + NEED(cs2_stack_top, 2); + cs2_arg_stack[cs2_stack_top - 2] += cs2_arg_stack[cs2_stack_top - 1]; + cs2_stack_top--; + break; + case cs_sub: + NEED(cs2_stack_top, 2); + cs2_arg_stack[cs2_stack_top - 2] -= cs2_arg_stack[cs2_stack_top - 1]; + cs2_stack_top--; + break; + case cs_div: /* doesn't check overflow */ + NEED(cs2_stack_top, 2); + cs2_arg_stack[cs2_stack_top - 2] /= cs2_arg_stack[cs2_stack_top - 1]; + cs2_stack_top--; + break; + case cs_neg: + NEED(cs2_stack_top, 1); + cs2_arg_stack[cs2_stack_top - 1] *= -1.0; + break; + case cs_eq: + NEED(cs2_stack_top, 2); + cs2_stack_top--; + if (cs2_arg_stack[cs2_stack_top] == cs2_arg_stack[cs2_stack_top - 1]) { + cs2_arg_stack[cs2_stack_top - 1] = 1.0; + } else { + cs2_arg_stack[cs2_stack_top - 1] = 0.0; + } + break; + case cs_drop: + NEED(cs2_stack_top, 1); + cs2_stack_top--; + break; + case cs_put: + NEED(cs2_stack_top, 2); + { + int idx = (int) cs2_arg_stack[--cs2_stack_top]; + NEED(CS_TRANS_ARRAY_MAX, idx); + trn_array[idx] = cs2_arg_stack[--cs2_stack_top]; + } + break; + case cs_get: + NEED(cs2_stack_top, 1); + { + int idx = (int) cs2_arg_stack[cs2_stack_top - 1]; + NEED(CS_TRANS_ARRAY_MAX, idx); + cs2_arg_stack[cs2_stack_top - 1] = trn_array[idx]; + } + break; + case cs_ifelse: + NEED(cs2_stack_top, 4); + cs2_stack_top -= 3; + if (cs2_arg_stack[cs2_stack_top + 1] > cs2_arg_stack[cs2_stack_top + 2]) { + cs2_arg_stack[cs2_stack_top - 1] = cs2_arg_stack[cs2_stack_top]; + } + break; + case cs_mul: + NEED(cs2_stack_top, 2); + cs2_arg_stack[cs2_stack_top - 2] = + cs2_arg_stack[cs2_stack_top - 2] * cs2_arg_stack[cs2_stack_top - 1]; + cs2_stack_top--; + break; + case cs_sqrt: + NEED(cs2_stack_top, 1); + cs2_arg_stack[cs2_stack_top - 1] = + sqrt(cs2_arg_stack[cs2_stack_top - 1]); + break; + case cs_dup: + NEED(cs2_stack_top, 1); + NEED(CS_ARG_STACK_MAX, cs2_stack_top + 1); + cs2_arg_stack[cs2_stack_top] = cs2_arg_stack[cs2_stack_top - 1]; + cs2_stack_top++; + break; + case cs_exch: + NEED(cs2_stack_top, 2); + { + double save = cs2_arg_stack[cs2_stack_top - 2]; + cs2_arg_stack[cs2_stack_top - 2] = cs2_arg_stack[cs2_stack_top - 1]; + cs2_arg_stack[cs2_stack_top - 1] = save; + } + break; + case cs_index: + NEED(cs2_stack_top, 2); /* need two arguments at least */ + { + int idx = (int) cs2_arg_stack[cs2_stack_top - 1]; + if (idx < 0) { + cs2_arg_stack[cs2_stack_top - 1] = + cs2_arg_stack[cs2_stack_top - 2]; + } else { + NEED(cs2_stack_top, idx + 2); + cs2_arg_stack[cs2_stack_top - 1] = + cs2_arg_stack[cs2_stack_top - idx - 2]; + } + } + break; + case cs_roll: + NEED(cs2_stack_top, 2); + { + int N, J; + J = (int) cs2_arg_stack[--cs2_stack_top]; + N = (int) cs2_arg_stack[--cs2_stack_top]; + NEED(cs2_stack_top, N); + if (J > 0) { + J = J % N; + while (J-- > 0) { + double save = cs2_arg_stack[cs2_stack_top - 1]; + int i = cs2_stack_top - 1; + while (i > cs2_stack_top - N) { + cs2_arg_stack[i] = cs2_arg_stack[i - 1]; + i--; + } + cs2_arg_stack[i] = save; + } + } else { + J = (-J) % N; + while (J-- > 0) { + double save = cs2_arg_stack[cs2_stack_top - N]; + int i = cs2_stack_top - N; + while (i < cs2_stack_top - 1) { + cs2_arg_stack[i] = cs2_arg_stack[i + 1]; + i++; + } + cs2_arg_stack[i] = save; + } + } + } + break; + case cs_random: + WARN("%s: Charstring operator \"random\" found.", CS_TYPE2_DEBUG_STR); + NEED(CS_ARG_STACK_MAX, cs2_stack_top + 1); + cs2_arg_stack[cs2_stack_top++] = 1.0; + break; + default: + /* no-op ? */ + WARN("%s: Unknown charstring operator: 0x0c%02x", CS_TYPE2_DEBUG_STR, + op); + status = CS_PARSE_CFF_ERROR; + break; } - break; - case cs_index: - NEED(cs2_stack_top, 2); /* need two arguments at least */ - { - int idx = (int)cs2_arg_stack[cs2_stack_top-1]; - if (idx < 0) { - cs2_arg_stack[cs2_stack_top-1] = cs2_arg_stack[cs2_stack_top-2]; - } else { - NEED(cs2_stack_top, idx+2); - cs2_arg_stack[cs2_stack_top-1] = cs2_arg_stack[cs2_stack_top-idx-2]; - } - } - break; - case cs_roll: - NEED(cs2_stack_top, 2); - { - int N, J; - J = (int)cs2_arg_stack[--cs2_stack_top]; - N = (int)cs2_arg_stack[--cs2_stack_top]; - NEED(cs2_stack_top, N); - if (J > 0) { - J = J % N; - while (J-- > 0) { - double save = cs2_arg_stack[cs2_stack_top-1]; - int i = cs2_stack_top - 1; - while (i > cs2_stack_top-N) { - cs2_arg_stack[i] = cs2_arg_stack[i-1]; - i--; - } - cs2_arg_stack[i] = save; - } - } else { - J = (-J) % N; - while (J-- > 0) { - double save = cs2_arg_stack[cs2_stack_top-N]; - int i = cs2_stack_top - N; - while (i < cs2_stack_top-1) { - cs2_arg_stack[i] = cs2_arg_stack[i+1]; - i++; - } - cs2_arg_stack[i] = save; - } - } - } - break; - case cs_random: - WARN("%s: Charstring operator \"random\" found.", CS_TYPE2_DEBUG_STR); - NEED(CS_ARG_STACK_MAX, cs2_stack_top+1); - cs2_arg_stack[cs2_stack_top++] = 1.0; - break; - default: - /* no-op ? */ - WARN("%s: Unknown charstring operator: 0x0c%02x", CS_TYPE2_DEBUG_STR, op); - status = CS_PARSE_CFF_ERROR; - break; - } - return; + return; } /* * integer: * exactly the same as the DICT encoding (except 29) */ -static void -cs2_get_integer (card8 **data, card8 *endptr) +static void cs2_get_integer(card8 ** data, card8 * endptr) { - long result = 0; - card8 b0 = **data, b1, b2; - - *data += 1; - - if (b0 == 28) { /* shortint */ - SRC_NEED(endptr, *data + 2); - b1 = **data; - b2 = *(*data+1); - result = b1*256+b2; - if (result > 0x7fff) - result -= 0x10000L; - *data += 2; - } else if (b0 >= 32 && b0 <= 246) { /* int (1) */ - result = b0 - 139; - } else if (b0 >= 247 && b0 <= 250) { /* int (2) */ - SRC_NEED(endptr, *data + 1); - b1 = **data; - result = (b0-247)*256+b1+108; - *data += 1; - } else if (b0 >= 251 && b0 <= 254) { - SRC_NEED(endptr, *data + 1); - b1 = **data; - result = -(b0-251)*256-b1-108; + long result = 0; + card8 b0 = **data, b1, b2; + *data += 1; - } else { - status = CS_PARSE_CFF_ERROR; - return; - } - NEED(CS_ARG_STACK_MAX, cs2_stack_top+1); - cs2_arg_stack[cs2_stack_top++] = (double) result; + if (b0 == 28) { /* shortint */ + SRC_NEED(endptr, *data + 2); + b1 = **data; + b2 = *(*data + 1); + result = b1 * 256 + b2; + if (result > 0x7fff) + result -= 0x10000L; + *data += 2; + } else if (b0 >= 32 && b0 <= 246) { /* int (1) */ + result = b0 - 139; + } else if (b0 >= 247 && b0 <= 250) { /* int (2) */ + SRC_NEED(endptr, *data + 1); + b1 = **data; + result = (b0 - 247) * 256 + b1 + 108; + *data += 1; + } else if (b0 >= 251 && b0 <= 254) { + SRC_NEED(endptr, *data + 1); + b1 = **data; + result = -(b0 - 251) * 256 - b1 - 108; + *data += 1; + } else { + status = CS_PARSE_CFF_ERROR; + return; + } + + NEED(CS_ARG_STACK_MAX, cs2_stack_top + 1); + cs2_arg_stack[cs2_stack_top++] = (double) result; - return; + return; } /* * Signed 16.16-bits fixed number for Type 2 charstring encoding */ -static void -get_fixed (card8 **data, card8 *endptr) +static void get_fixed(card8 ** data, card8 * endptr) { - long ivalue; - double rvalue; + long ivalue; + double rvalue; - *data += 1; + *data += 1; - SRC_NEED(endptr, *data + 4); + SRC_NEED(endptr, *data + 4); - ivalue = *(*data) * 0x100 + *(*data+1); - rvalue = (ivalue > 0x7fffL) ? (ivalue - 0x10000L) : ivalue; - ivalue = *(*data+2) * 0x100 + *(*data+3); - rvalue += ((double) ivalue) / 0x10000L; + ivalue = *(*data) * 0x100 + *(*data + 1); + rvalue = (ivalue > 0x7fffL) ? (ivalue - 0x10000L) : ivalue; + ivalue = *(*data + 2) * 0x100 + *(*data + 3); + rvalue += ((double) ivalue) / 0x10000L; - NEED(CS_ARG_STACK_MAX, cs2_stack_top+1); - cs2_arg_stack[cs2_stack_top++] = rvalue; - *data += 4; + NEED(CS_ARG_STACK_MAX, cs2_stack_top + 1); + cs2_arg_stack[cs2_stack_top++] = rvalue; + *data += 4; - return; + return; } /* @@ -2354,32 +2398,33 @@ get_fixed (card8 **data, card8 *endptr) * subr_idx: CFF INDEX data that contains subroutines. * id: biased subroutine number. */ -static void -get_subr (card8 **subr, long *len, cff_index *subr_idx, long id) +static void get_subr(card8 ** subr, long *len, cff_index * subr_idx, long id) { - card16 count; + card16 count; - if (subr_idx == NULL) - CFF_ERROR("%s: Subroutine called but no subroutine found.", CS_TYPE2_DEBUG_STR); + if (subr_idx == NULL) + CFF_ERROR("%s: Subroutine called but no subroutine found.", + CS_TYPE2_DEBUG_STR); - count = subr_idx->count; + count = subr_idx->count; - /* Adding bias number */ - if (count < 1240) { - id += 107; - } else if (count < 33900) { - id += 1131; - } else { - id += 32768; - } + /* Adding bias number */ + if (count < 1240) { + id += 107; + } else if (count < 33900) { + id += 1131; + } else { + id += 32768; + } - if (id > count) - CFF_ERROR("%s: Invalid Subr index: %ld (max=%u)", CS_TYPE2_DEBUG_STR, id, count); + if (id > count) + CFF_ERROR("%s: Invalid Subr index: %ld (max=%u)", CS_TYPE2_DEBUG_STR, + id, count); - *len = (subr_idx->offset)[id + 1] - (subr_idx->offset)[id]; - *subr = subr_idx->data + (subr_idx->offset)[id] - 1; + *len = (subr_idx->offset)[id + 1] - (subr_idx->offset)[id]; + *subr = subr_idx->data + (subr_idx->offset)[id] - 1; - return; + return; } /* @@ -2390,112 +2435,115 @@ get_subr (card8 **subr, long *len, cff_index *subr_idx, long id) */ static void -do_charstring (card8 **dest, card8 *limit, - card8 **data, card8 *endptr, - cff_index *gsubr_idx, cff_index *subr_idx) +do_charstring(card8 ** dest, card8 * limit, + card8 ** data, card8 * endptr, + cff_index * gsubr_idx, cff_index * subr_idx) { - card8 b0 = 0, *subr; - long len; - - if (cs2_nest > CS_SUBR_NEST_MAX) - CFF_ERROR("%s: Subroutine nested too deeply.", CS_TYPE2_DEBUG_STR); - - cs2_nest++; - - while (*data < endptr && status == CS_PARSE_OK) { - b0 = **data; - if (b0 == 255) { /* 16-bit.16-bit fixed signed number */ - get_fixed(data, endptr); - } else if (b0 == cs_return) { - status = CS_SUBR_RETURN; - } else if (b0 == cs_callgsubr) { - if (cs2_stack_top < 1) { - status = CS_STACK_CFF_ERROR; - } else { - cs2_stack_top--; - get_subr(&subr, &len, gsubr_idx, (long) cs2_arg_stack[cs2_stack_top]); - if (*dest + len > limit) - CFF_ERROR("%s: Possible buffer overflow.", CS_TYPE2_DEBUG_STR); - do_charstring(dest, limit, &subr, subr + len, - gsubr_idx, subr_idx); - *data += 1; - } - } else if (b0 == cs_callsubr) { - if (cs2_stack_top < 1) { - status = CS_STACK_CFF_ERROR; - } else { - cs2_stack_top--; - get_subr(&subr, &len, subr_idx, (long) cs2_arg_stack[cs2_stack_top]); - if (limit < *dest + len) - CFF_ERROR("%s: Possible buffer overflow.", CS_TYPE2_DEBUG_STR); - do_charstring(dest, limit, &subr, subr + len, - gsubr_idx, subr_idx); - *data += 1; - } - } else if (b0 == cs_escape) { - do_operator2(dest, limit, data, endptr); - } else if (b0 < 32 && b0 != 28) { /* 19, 20 need mask */ - do_operator1(dest, limit, data, endptr); - } else if ((b0 <= 22 && b0 >= 27) || b0 == 31) { /* reserved */ - status = CS_PARSE_CFF_ERROR; /* not an error ? */ - } else { /* integer */ - cs2_get_integer(data, endptr); - } - } - - if (status == CS_SUBR_RETURN) { - status = CS_PARSE_OK; - } else if (status == CS_CHAR_END && *data < endptr) { - WARN("%s: Garbage after endchar.", CS_TYPE2_DEBUG_STR); - } else if (status < CS_PARSE_OK) { /* error */ - CFF_ERROR("%s: Parsing charstring failed: (status=%d, stack=%d)", - CS_TYPE2_DEBUG_STR, status, cs2_stack_top); - } - - cs2_nest--; + card8 b0 = 0, *subr; + long len; + + if (cs2_nest > CS_SUBR_NEST_MAX) + CFF_ERROR("%s: Subroutine nested too deeply.", CS_TYPE2_DEBUG_STR); + + cs2_nest++; + + while (*data < endptr && status == CS_PARSE_OK) { + b0 = **data; + if (b0 == 255) { /* 16-bit.16-bit fixed signed number */ + get_fixed(data, endptr); + } else if (b0 == cs_return) { + status = CS_SUBR_RETURN; + } else if (b0 == cs_callgsubr) { + if (cs2_stack_top < 1) { + status = CS_STACK_CFF_ERROR; + } else { + cs2_stack_top--; + get_subr(&subr, &len, gsubr_idx, + (long) cs2_arg_stack[cs2_stack_top]); + if (*dest + len > limit) + CFF_ERROR("%s: Possible buffer overflow.", + CS_TYPE2_DEBUG_STR); + do_charstring(dest, limit, &subr, subr + len, gsubr_idx, + subr_idx); + *data += 1; + } + } else if (b0 == cs_callsubr) { + if (cs2_stack_top < 1) { + status = CS_STACK_CFF_ERROR; + } else { + cs2_stack_top--; + get_subr(&subr, &len, subr_idx, + (long) cs2_arg_stack[cs2_stack_top]); + if (limit < *dest + len) + CFF_ERROR("%s: Possible buffer overflow.", + CS_TYPE2_DEBUG_STR); + do_charstring(dest, limit, &subr, subr + len, gsubr_idx, + subr_idx); + *data += 1; + } + } else if (b0 == cs_escape) { + do_operator2(dest, limit, data, endptr); + } else if (b0 < 32 && b0 != 28) { /* 19, 20 need mask */ + do_operator1(dest, limit, data, endptr); + } else if ((b0 <= 22 && b0 >= 27) || b0 == 31) { /* reserved */ + status = CS_PARSE_CFF_ERROR; /* not an error ? */ + } else { /* integer */ + cs2_get_integer(data, endptr); + } + } + + if (status == CS_SUBR_RETURN) { + status = CS_PARSE_OK; + } else if (status == CS_CHAR_END && *data < endptr) { + WARN("%s: Garbage after endchar.", CS_TYPE2_DEBUG_STR); + } else if (status < CS_PARSE_OK) { /* error */ + CFF_ERROR("%s: Parsing charstring failed: (status=%d, stack=%d)", + CS_TYPE2_DEBUG_STR, status, cs2_stack_top); + } + + cs2_nest--; - return; + return; } -static void -cs_parse_init (void) +static void cs_parse_init(void) { - status = CS_PARSE_OK; - cs2_nest = 0; - phase = 0; - num_stems = 0; - cs2_stack_top = 0; + status = CS_PARSE_OK; + cs2_nest = 0; + phase = 0; + num_stems = 0; + cs2_stack_top = 0; } /* * Not just copying... */ long -cs_copy_charstring (card8 *dst, long dstlen, - card8 *src, long srclen, - cff_index *gsubr, cff_index *subr, - double default_width, double nominal_width, cs_ginfo *ginfo) +cs_copy_charstring(card8 * dst, long dstlen, + card8 * src, long srclen, + cff_index * gsubr, cff_index * subr, + double default_width, double nominal_width, cs_ginfo * ginfo) { - card8 *save = dst; + card8 *save = dst; - cs_parse_init(); + cs_parse_init(); - width = 0.0; - have_width = 0; + width = 0.0; + have_width = 0; - /* expand call(g)subrs */ - do_charstring(&dst, dst + dstlen, &src, src + srclen, gsubr, subr); + /* expand call(g)subrs */ + do_charstring(&dst, dst + dstlen, &src, src + srclen, gsubr, subr); - if (ginfo) { - ginfo->flags = 0; /* not used */ - if (have_width) { - ginfo->wx = nominal_width + width; - } else { - ginfo->wx = default_width; + if (ginfo) { + ginfo->flags = 0; /* not used */ + if (have_width) { + ginfo->wx = nominal_width + width; + } else { + ginfo->wx = default_width; + } } - } - return (long)(dst - save); + return (long) (dst - save); } /* encodings */ @@ -2505,243 +2553,244 @@ cs_copy_charstring (card8 *dst, long dstlen, * * Encoding and Charset arrays always begin with GID = 1. */ -long cff_read_encoding (cff_font *cff) +long cff_read_encoding(cff_font * cff) { - cff_encoding *encoding; - long offset, length; - card8 i; + cff_encoding *encoding; + long offset, length; + card8 i; - if (cff->topdict == NULL) { - CFF_ERROR("Top DICT data not found"); - } + if (cff->topdict == NULL) { + CFF_ERROR("Top DICT data not found"); + } - if (!cff_dict_known(cff->topdict, "Encoding")) { - cff->flag |= ENCODING_STANDARD; - cff->encoding = NULL; - return 0; - } + if (!cff_dict_known(cff->topdict, "Encoding")) { + cff->flag |= ENCODING_STANDARD; + cff->encoding = NULL; + return 0; + } - offset = (long) cff_dict_get(cff->topdict, "Encoding", 0); - if (offset == 0) { /* predefined */ - cff->flag |= ENCODING_STANDARD; - cff->encoding = NULL; - return 0; - } else if (offset == 1) { - cff->flag |= ENCODING_EXPERT; - cff->encoding = NULL; - return 0; - } + offset = (long) cff_dict_get(cff->topdict, "Encoding", 0); + if (offset == 0) { /* predefined */ + cff->flag |= ENCODING_STANDARD; + cff->encoding = NULL; + return 0; + } else if (offset == 1) { + cff->flag |= ENCODING_EXPERT; + cff->encoding = NULL; + return 0; + } - cff->offset= offset; - cff->encoding = encoding = xcalloc(1, sizeof(cff_encoding)); - encoding->format = get_card8(cff); - length = 1; - - switch (encoding->format & (~0x80)) { - case 0: - encoding->num_entries = get_card8(cff); - (encoding->data).codes = xcalloc(encoding->num_entries, sizeof(card8)); - for (i=0;i<(encoding->num_entries);i++) { - (encoding->data).codes[i] = get_card8(cff); - } - length += encoding->num_entries + 1; - break; - case 1: - { - cff_range1 *ranges; - encoding->num_entries = get_card8(cff); - encoding->data.range1 = ranges - = xcalloc(encoding->num_entries, sizeof(cff_range1)); - for (i=0;i<(encoding->num_entries);i++) { - ranges[i].first = get_card8(cff); - ranges[i].n_left = get_card8(cff); - } - length += (encoding->num_entries) * 2 + 1; - } - break; - default: - xfree(encoding); - CFF_ERROR("Unknown Encoding format"); - break; - } + cff->offset = offset; + cff->encoding = encoding = xcalloc(1, sizeof(cff_encoding)); + encoding->format = get_card8(cff); + length = 1; - /* Supplementary data */ - if ((encoding->format) & 0x80) { - cff_map *map; - encoding->num_supps = get_card8(cff); - encoding->supp = map = xcalloc(encoding->num_supps, sizeof(cff_map)); - for (i=0;i<(encoding->num_supps);i++) { - map[i].code = get_card8(cff); - map[i].glyph = get_card16(cff); /* SID */ - } - length += (encoding->num_supps) * 3 + 1; - } else { - encoding->num_supps = 0; - encoding->supp = NULL; - } + switch (encoding->format & (~0x80)) { + case 0: + encoding->num_entries = get_card8(cff); + (encoding->data).codes = xcalloc(encoding->num_entries, sizeof(card8)); + for (i = 0; i < (encoding->num_entries); i++) { + (encoding->data).codes[i] = get_card8(cff); + } + length += encoding->num_entries + 1; + break; + case 1: + { + cff_range1 *ranges; + encoding->num_entries = get_card8(cff); + encoding->data.range1 = ranges + = xcalloc(encoding->num_entries, sizeof(cff_range1)); + for (i = 0; i < (encoding->num_entries); i++) { + ranges[i].first = get_card8(cff); + ranges[i].n_left = get_card8(cff); + } + length += (encoding->num_entries) * 2 + 1; + } + break; + default: + xfree(encoding); + CFF_ERROR("Unknown Encoding format"); + break; + } + + /* Supplementary data */ + if ((encoding->format) & 0x80) { + cff_map *map; + encoding->num_supps = get_card8(cff); + encoding->supp = map = xcalloc(encoding->num_supps, sizeof(cff_map)); + for (i = 0; i < (encoding->num_supps); i++) { + map[i].code = get_card8(cff); + map[i].glyph = get_card16(cff); /* SID */ + } + length += (encoding->num_supps) * 3 + 1; + } else { + encoding->num_supps = 0; + encoding->supp = NULL; + } - return length; + return length; } -long cff_pack_encoding (cff_font *cff, card8 *dest, long destlen) +long cff_pack_encoding(cff_font * cff, card8 * dest, long destlen) { - long len = 0; - cff_encoding *encoding; - card16 i; + long len = 0; + cff_encoding *encoding; + card16 i; - if (cff->flag & HAVE_STANDARD_ENCODING || cff->encoding == NULL) - return 0; + if (cff->flag & HAVE_STANDARD_ENCODING || cff->encoding == NULL) + return 0; - if (destlen < 2) - CFF_ERROR("in cff_pack_encoding(): Buffer overflow"); - - encoding = cff->encoding; - - dest[len++] = encoding->format; - dest[len++] = encoding->num_entries; - switch (encoding->format & (~0x80)) { - case 0: - if (destlen < len + encoding->num_entries) - CFF_ERROR("in cff_pack_encoding(): Buffer overflow"); - for (i=0;i<(encoding->num_entries);i++) { - dest[len++] = (encoding->data).codes[i]; - } - break; - case 1: - { - if (destlen < len + (encoding->num_entries)*2) - CFF_ERROR("in cff_pack_encoding(): Buffer overflow"); - for (i=0;i<(encoding->num_entries);i++) { - dest[len++] = (encoding->data).range1[i].first & 0xff; - dest[len++] = (encoding->data).range1[i].n_left; - } - } - break; - default: - CFF_ERROR("Unknown Encoding format"); - break; - } + if (destlen < 2) + CFF_ERROR("in cff_pack_encoding(): Buffer overflow"); - if ((encoding->format) & 0x80) { - if (destlen < len + (encoding->num_supps)*3 + 1) - CFF_ERROR("in cff_pack_encoding(): Buffer overflow"); - dest[len++] = encoding->num_supps; - for (i=0;i<(encoding->num_supps);i++) { - dest[len++] = (encoding->supp)[i].code; - dest[len++] = ((encoding->supp)[i].glyph >> 8) & 0xff; - dest[len++] = (encoding->supp)[i].glyph & 0xff; - } - } + encoding = cff->encoding; - return len; + dest[len++] = encoding->format; + dest[len++] = encoding->num_entries; + switch (encoding->format & (~0x80)) { + case 0: + if (destlen < len + encoding->num_entries) + CFF_ERROR("in cff_pack_encoding(): Buffer overflow"); + for (i = 0; i < (encoding->num_entries); i++) { + dest[len++] = (encoding->data).codes[i]; + } + break; + case 1: + { + if (destlen < len + (encoding->num_entries) * 2) + CFF_ERROR("in cff_pack_encoding(): Buffer overflow"); + for (i = 0; i < (encoding->num_entries); i++) { + dest[len++] = (encoding->data).range1[i].first & 0xff; + dest[len++] = (encoding->data).range1[i].n_left; + } + } + break; + default: + CFF_ERROR("Unknown Encoding format"); + break; + } + + if ((encoding->format) & 0x80) { + if (destlen < len + (encoding->num_supps) * 3 + 1) + CFF_ERROR("in cff_pack_encoding(): Buffer overflow"); + dest[len++] = encoding->num_supps; + for (i = 0; i < (encoding->num_supps); i++) { + dest[len++] = (encoding->supp)[i].code; + dest[len++] = ((encoding->supp)[i].glyph >> 8) & 0xff; + dest[len++] = (encoding->supp)[i].glyph & 0xff; + } + } + + return len; } /* CID-Keyed font specific */ -long cff_read_fdselect (cff_font *cff) +long cff_read_fdselect(cff_font * cff) { - cff_fdselect *fdsel; - long offset, length; - card16 i; - - if (cff->topdict == NULL) - CFF_ERROR("Top DICT not available"); - - if (!(cff->flag & FONTTYPE_CIDFONT)) - return 0; - - offset = (long) cff_dict_get(cff->topdict, "FDSelect", 0); - cff->offset = offset; - cff->fdselect = fdsel = xcalloc(1, sizeof(cff_fdselect)); - fdsel->format = get_card8(cff); - - length = 1; - - switch (fdsel->format) { - case 0: - fdsel->num_entries = cff->num_glyphs; - (fdsel->data).fds = xcalloc(fdsel->num_entries, sizeof(card8)); - for (i=0;i<(fdsel->num_entries);i++) { - (fdsel->data).fds[i] = get_card8(cff); - } - length += fdsel->num_entries; - break; - case 3: - { - cff_range3 *ranges; - fdsel->num_entries = get_card16(cff); - fdsel->data.ranges = ranges = xcalloc(fdsel->num_entries, sizeof(cff_range3)); - for (i=0;i<(fdsel->num_entries);i++) { - ranges[i].first = get_card16(cff); - ranges[i].fd = get_card8(cff); - } - if (ranges[0].first != 0) - CFF_ERROR("Range not starting with 0."); - if (cff->num_glyphs != get_card16(cff)) - CFF_ERROR("Sentinel value mismatched with number of glyphs."); - length += (fdsel->num_entries) * 3 + 4; - } - break; - default: - xfree(fdsel); - CFF_ERROR("Unknown FDSelect format."); - break; - } - - return length; + cff_fdselect *fdsel; + long offset, length; + card16 i; + + if (cff->topdict == NULL) + CFF_ERROR("Top DICT not available"); + + if (!(cff->flag & FONTTYPE_CIDFONT)) + return 0; + + offset = (long) cff_dict_get(cff->topdict, "FDSelect", 0); + cff->offset = offset; + cff->fdselect = fdsel = xcalloc(1, sizeof(cff_fdselect)); + fdsel->format = get_card8(cff); + + length = 1; + + switch (fdsel->format) { + case 0: + fdsel->num_entries = cff->num_glyphs; + (fdsel->data).fds = xcalloc(fdsel->num_entries, sizeof(card8)); + for (i = 0; i < (fdsel->num_entries); i++) { + (fdsel->data).fds[i] = get_card8(cff); + } + length += fdsel->num_entries; + break; + case 3: + { + cff_range3 *ranges; + fdsel->num_entries = get_card16(cff); + fdsel->data.ranges = ranges = + xcalloc(fdsel->num_entries, sizeof(cff_range3)); + for (i = 0; i < (fdsel->num_entries); i++) { + ranges[i].first = get_card16(cff); + ranges[i].fd = get_card8(cff); + } + if (ranges[0].first != 0) + CFF_ERROR("Range not starting with 0."); + if (cff->num_glyphs != get_card16(cff)) + CFF_ERROR("Sentinel value mismatched with number of glyphs."); + length += (fdsel->num_entries) * 3 + 4; + } + break; + default: + xfree(fdsel); + CFF_ERROR("Unknown FDSelect format."); + break; + } + + return length; } -long cff_pack_fdselect (cff_font *cff, card8 *dest, long destlen) +long cff_pack_fdselect(cff_font * cff, card8 * dest, long destlen) { - cff_fdselect *fdsel; - long len = 0; - card16 i; - - if (cff->fdselect == NULL) - return 0; + cff_fdselect *fdsel; + long len = 0; + card16 i; - if (destlen < 1) - CFF_ERROR("in cff_pack_fdselect(): Buffur overflow"); - - fdsel = cff->fdselect; - - dest[len++] = fdsel->format; - switch (fdsel->format) { - case 0: - if (fdsel->num_entries != cff->num_glyphs) - CFF_ERROR("in cff_pack_fdselect(): Invalid data"); - if (destlen < len + fdsel->num_entries) - CFF_ERROR("in cff_pack_fdselect(): Buffer overflow"); - for (i=0;i<fdsel->num_entries;i++) { - dest[len++] = (fdsel->data).fds[i]; - } - break; - case 3: - { - if (destlen < len + 2) - CFF_ERROR("in cff_pack_fdselect(): Buffer overflow"); - len += 2; - for (i=0;i<(fdsel->num_entries);i++) { - if (destlen < len + 3) - CFF_ERROR("in cff_pack_fdselect(): Buffer overflow"); - dest[len++] = ((fdsel->data).ranges[i].first >> 8) & 0xff; - dest[len++] = (fdsel->data).ranges[i].first & 0xff; - dest[len++] = (fdsel->data).ranges[i].fd; - } - if (destlen < len + 2) - CFF_ERROR("in cff_pack_fdselect(): Buffer overflow"); - dest[len++] = (cff->num_glyphs >> 8) & 0xff; - dest[len++] = cff->num_glyphs & 0xff; - dest[1] = ((len/3 - 1) >> 8) & 0xff; - dest[2] = (len/3 - 1) & 0xff; - } - break; - default: - CFF_ERROR("Unknown FDSelect format."); - break; - } + if (cff->fdselect == NULL) + return 0; - return len; + if (destlen < 1) + CFF_ERROR("in cff_pack_fdselect(): Buffur overflow"); + + fdsel = cff->fdselect; + + dest[len++] = fdsel->format; + switch (fdsel->format) { + case 0: + if (fdsel->num_entries != cff->num_glyphs) + CFF_ERROR("in cff_pack_fdselect(): Invalid data"); + if (destlen < len + fdsel->num_entries) + CFF_ERROR("in cff_pack_fdselect(): Buffer overflow"); + for (i = 0; i < fdsel->num_entries; i++) { + dest[len++] = (fdsel->data).fds[i]; + } + break; + case 3: + { + if (destlen < len + 2) + CFF_ERROR("in cff_pack_fdselect(): Buffer overflow"); + len += 2; + for (i = 0; i < (fdsel->num_entries); i++) { + if (destlen < len + 3) + CFF_ERROR("in cff_pack_fdselect(): Buffer overflow"); + dest[len++] = ((fdsel->data).ranges[i].first >> 8) & 0xff; + dest[len++] = (fdsel->data).ranges[i].first & 0xff; + dest[len++] = (fdsel->data).ranges[i].fd; + } + if (destlen < len + 2) + CFF_ERROR("in cff_pack_fdselect(): Buffer overflow"); + dest[len++] = (cff->num_glyphs >> 8) & 0xff; + dest[len++] = cff->num_glyphs & 0xff; + dest[1] = ((len / 3 - 1) >> 8) & 0xff; + dest[2] = (len / 3 - 1) & 0xff; + } + break; + default: + CFF_ERROR("Unknown FDSelect format."); + break; + } + + return len; } @@ -2749,335 +2798,334 @@ long cff_pack_fdselect (cff_font *cff, card8 *dest, long destlen) /* * Create an instance of embeddable font. */ -static void -write_fontfile (cff_font *cffont, char *fullname) +static void write_fontfile(cff_font * cffont, char *fullname) { - cff_index *topdict, *fdarray, *private; - unsigned char *dest; - long destlen = 0, i, size; - long offset, topdict_offset, fdarray_offset; - - /* DICT sizes (offset set to long int) */ - topdict = cff_new_index(1); - fdarray = cff_new_index(cffont->num_fds); - private = cff_new_index(cffont->num_fds); - - cff_dict_remove(cffont->topdict, "UniqueID"); - cff_dict_remove(cffont->topdict, "XUID"); - cff_dict_remove(cffont->topdict, "Private"); /* some bad font may have */ - cff_dict_remove(cffont->topdict, "Encoding"); /* some bad font may have */ - - topdict->offset[1] = cff_dict_pack(cffont->topdict, - (card8 *) work_buffer, - WORK_BUFFER_SIZE) + 1; - for (i = 0;i < cffont->num_fds; i++) { - size = 0; - if (cffont->private && cffont->private[i]) { - size = cff_dict_pack(cffont->private[i], - (card8 *) work_buffer, WORK_BUFFER_SIZE); - if (size < 1) { /* Private had contained only Subr */ - cff_dict_remove(cffont->fdarray[i], "Private"); - } - } - (private->offset)[i+1] = (private->offset)[i] + size; - (fdarray->offset)[i+1] = (fdarray->offset)[i] + - cff_dict_pack(cffont->fdarray[i], - (card8 *) work_buffer, WORK_BUFFER_SIZE); - } - - destlen = 4; /* header size */ - destlen += cff_set_name(cffont, fullname); - destlen += cff_index_size(topdict); - destlen += cff_index_size(cffont->string); - destlen += cff_index_size(cffont->gsubr); - destlen += (cffont->charsets->num_entries) * 2 + 1; /* charset format 0 */ - destlen += (cffont->fdselect->num_entries) * 3 + 5; /* fdselect format 3 */ - destlen += cff_index_size(cffont->cstrings); - destlen += cff_index_size(fdarray); - destlen += private->offset[private->count] - 1; /* Private is not INDEX */ - - dest = xcalloc(destlen, sizeof(card8)); - - offset = 0; - /* Header */ - offset += cff_put_header(cffont, dest + offset, destlen - offset); - /* Name */ - offset += cff_pack_index(cffont->name, dest + offset, destlen - offset); - /* Top DICT */ - topdict_offset = offset; - offset += cff_index_size(topdict); - /* Strings */ - offset += cff_pack_index(cffont->string, dest + offset, destlen - offset); - /* Global Subrs */ - offset += cff_pack_index(cffont->gsubr, dest + offset, destlen - offset); - - /* charset */ - cff_dict_set(cffont->topdict, "charset", 0, offset); - offset += cff_pack_charsets(cffont, dest + offset, destlen - offset); - - /* FDSelect */ - cff_dict_set(cffont->topdict, "FDSelect", 0, offset); - offset += cff_pack_fdselect(cffont, dest + offset, destlen - offset); - - /* CharStrings */ - cff_dict_set(cffont->topdict, "CharStrings", 0, offset); - offset += cff_pack_index(cffont->cstrings, - dest + offset, cff_index_size(cffont->cstrings)); - cff_release_index(cffont->cstrings); - cffont->cstrings = NULL; /* Charstrings cosumes huge memory */ - - /* FDArray and Private */ - cff_dict_set(cffont->topdict, "FDArray", 0, offset); - fdarray_offset = offset; - offset += cff_index_size(fdarray); - - fdarray->data = xcalloc(fdarray->offset[fdarray->count] - 1, sizeof(card8)); - for (i = 0; i < cffont->num_fds; i++) { - size = private->offset[i+1] - private->offset[i]; - if (cffont->private[i] && size > 0) { - cff_dict_pack(cffont->private[i], dest + offset, size); - cff_dict_set(cffont->fdarray[i], "Private", 0, size); - cff_dict_set(cffont->fdarray[i], "Private", 1, offset); - } - cff_dict_pack(cffont->fdarray[i], - fdarray->data + (fdarray->offset)[i] - 1, - fdarray->offset[fdarray->count] - 1); - offset += size; - } - - cff_pack_index(fdarray, dest + fdarray_offset, cff_index_size(fdarray)); - cff_release_index(fdarray); - cff_release_index(private); - - /* Finally Top DICT */ - topdict->data = xcalloc(topdict->offset[topdict->count] - 1, sizeof(card8)); - cff_dict_pack(cffont->topdict, - topdict->data, topdict->offset[topdict->count] - 1); - cff_pack_index(topdict, dest + topdict_offset, cff_index_size(topdict)); - cff_release_index(topdict); - - for (i = 0; i < offset; i++) - fb_putchar (dest[i]); - - /*fprintf(stdout," (%i/%i)",offset,cffont->stream_size);*/ - xfree(dest); - return ; + cff_index *topdict, *fdarray, *private; + unsigned char *dest; + long destlen = 0, i, size; + long offset, topdict_offset, fdarray_offset; + + /* DICT sizes (offset set to long int) */ + topdict = cff_new_index(1); + fdarray = cff_new_index(cffont->num_fds); + private = cff_new_index(cffont->num_fds); + + cff_dict_remove(cffont->topdict, "UniqueID"); + cff_dict_remove(cffont->topdict, "XUID"); + cff_dict_remove(cffont->topdict, "Private"); /* some bad font may have */ + cff_dict_remove(cffont->topdict, "Encoding"); /* some bad font may have */ + + topdict->offset[1] = cff_dict_pack(cffont->topdict, + (card8 *) work_buffer, + WORK_BUFFER_SIZE) + 1; + for (i = 0; i < cffont->num_fds; i++) { + size = 0; + if (cffont->private && cffont->private[i]) { + size = cff_dict_pack(cffont->private[i], + (card8 *) work_buffer, WORK_BUFFER_SIZE); + if (size < 1) { /* Private had contained only Subr */ + cff_dict_remove(cffont->fdarray[i], "Private"); + } + } + (private->offset)[i + 1] = (private->offset)[i] + size; + (fdarray->offset)[i + 1] = (fdarray->offset)[i] + + cff_dict_pack(cffont->fdarray[i], + (card8 *) work_buffer, WORK_BUFFER_SIZE); + } + + destlen = 4; /* header size */ + destlen += cff_set_name(cffont, fullname); + destlen += cff_index_size(topdict); + destlen += cff_index_size(cffont->string); + destlen += cff_index_size(cffont->gsubr); + destlen += (cffont->charsets->num_entries) * 2 + 1; /* charset format 0 */ + destlen += (cffont->fdselect->num_entries) * 3 + 5; /* fdselect format 3 */ + destlen += cff_index_size(cffont->cstrings); + destlen += cff_index_size(fdarray); + destlen += private->offset[private->count] - 1; /* Private is not INDEX */ + + dest = xcalloc(destlen, sizeof(card8)); + + offset = 0; + /* Header */ + offset += cff_put_header(cffont, dest + offset, destlen - offset); + /* Name */ + offset += cff_pack_index(cffont->name, dest + offset, destlen - offset); + /* Top DICT */ + topdict_offset = offset; + offset += cff_index_size(topdict); + /* Strings */ + offset += cff_pack_index(cffont->string, dest + offset, destlen - offset); + /* Global Subrs */ + offset += cff_pack_index(cffont->gsubr, dest + offset, destlen - offset); + + /* charset */ + cff_dict_set(cffont->topdict, "charset", 0, offset); + offset += cff_pack_charsets(cffont, dest + offset, destlen - offset); + + /* FDSelect */ + cff_dict_set(cffont->topdict, "FDSelect", 0, offset); + offset += cff_pack_fdselect(cffont, dest + offset, destlen - offset); + + /* CharStrings */ + cff_dict_set(cffont->topdict, "CharStrings", 0, offset); + offset += cff_pack_index(cffont->cstrings, + dest + offset, cff_index_size(cffont->cstrings)); + cff_release_index(cffont->cstrings); + cffont->cstrings = NULL; /* Charstrings cosumes huge memory */ + + /* FDArray and Private */ + cff_dict_set(cffont->topdict, "FDArray", 0, offset); + fdarray_offset = offset; + offset += cff_index_size(fdarray); + + fdarray->data = xcalloc(fdarray->offset[fdarray->count] - 1, sizeof(card8)); + for (i = 0; i < cffont->num_fds; i++) { + size = private->offset[i + 1] - private->offset[i]; + if (cffont->private[i] && size > 0) { + cff_dict_pack(cffont->private[i], dest + offset, size); + cff_dict_set(cffont->fdarray[i], "Private", 0, size); + cff_dict_set(cffont->fdarray[i], "Private", 1, offset); + } + cff_dict_pack(cffont->fdarray[i], + fdarray->data + (fdarray->offset)[i] - 1, + fdarray->offset[fdarray->count] - 1); + offset += size; + } + + cff_pack_index(fdarray, dest + fdarray_offset, cff_index_size(fdarray)); + cff_release_index(fdarray); + cff_release_index(private); + + /* Finally Top DICT */ + topdict->data = xcalloc(topdict->offset[topdict->count] - 1, sizeof(card8)); + cff_dict_pack(cffont->topdict, + topdict->data, topdict->offset[topdict->count] - 1); + cff_pack_index(topdict, dest + topdict_offset, cff_index_size(topdict)); + cff_release_index(topdict); + + for (i = 0; i < offset; i++) + fb_putchar(dest[i]); + + /*fprintf(stdout," (%i/%i)",offset,cffont->stream_size); */ + xfree(dest); + return; } -/* if the CFF data was converted from an old type1 font, then the .notdef - glyph may not be at id 0, so in that case |uglytype1fix| is nonzero */ - -void write_cff(cff_font *cffont, fd_entry *fd, int uglytype1fix) { - cff_index *charstrings, *cs_idx; +/* this block is used a few times */ + +#define DO_COPY_CHARSTRING() \ + if ((avl_find(fd->gl_tree,glyph) != NULL)) { \ + size = cs_idx->offset[code+1] - cs_idx->offset[code]; \ + if (size > CS_STR_LEN_MAX) { \ + pdftex_fail("Charstring too long: gid=%u, %ld bytes", code, size); \ + } \ + if (charstring_len + CS_STR_LEN_MAX >= max_len) { \ + max_len = charstring_len + 2 * CS_STR_LEN_MAX; \ + charstrings->data = xrealloc(charstrings->data, max_len*sizeof(card8)); \ + } \ + (charstrings->offset)[gid] = charstring_len + 1; \ + cffont->offset= offset + (cs_idx->offset)[code] - 1; \ + memcpy(data,&cffont->stream[cffont->offset],size); \ + charstring_len += cs_copy_charstring(charstrings->data + charstring_len, \ + max_len - charstring_len, \ + data, size, \ + cffont->gsubr, (cffont->subrs)[0], \ + default_width, nominal_width, NULL); \ + gid++; \ + } + +void write_cff(cff_font * cffont, fd_entry * fd) +{ + cff_index *charstrings, *cs_idx; - long charstring_len, max_len; - long size, offset = 0; + long charstring_len, max_len; + long size, offset = 0; - card8 *data; - card16 num_glyphs, cs_count, code, gid, last_cid; + card8 *data; + card16 num_glyphs, cs_count, code, gid, last_cid; - double nominal_width, default_width; + double nominal_width, default_width; - char *fullname; + char *fullname; - glw_entry *glyph, *found; - struct avl_traverser t; + glw_entry *glyph, *found; + struct avl_traverser t; + fullname = xcalloc(8 + strlen(fd->fontname), 1); + sprintf(fullname, "%s+%s", fd->subset_tag, fd->fontname); + /* finish parsing the CFF */ + cff_read_private(cffont); + cff_read_subrs(cffont); - - fullname = xcalloc(8+strlen(fd->fontname),1); - sprintf(fullname,"%s+%s",fd->subset_tag,fd->fontname); + /* + * Widths + */ + if (cffont->private[0] && + cff_dict_known(cffont->private[0], "defaultWidthX")) { + default_width = + (double) cff_dict_get(cffont->private[0], "defaultWidthX", 0); + } else { + default_width = CFF_DEFAULTWIDTHX_DEFAULT; + } + if (cffont->private[0] && + cff_dict_known(cffont->private[0], "nominalWidthX")) { + nominal_width = + (double) cff_dict_get(cffont->private[0], "nominalWidthX", 0); + } else { + nominal_width = CFF_NOMINALWIDTHX_DEFAULT; + } - /* finish parsing the CFF */ - cff_read_private(cffont); - cff_read_subrs (cffont); + num_glyphs = 0; + last_cid = 0; + glyph = xtalloc(1, glw_entry); - /* - * Widths - */ - if (cffont->private[0] && - cff_dict_known(cffont->private[0], "defaultWidthX")) { - default_width = (double) cff_dict_get(cffont->private[0], "defaultWidthX", 0); - } else { - default_width = CFF_DEFAULTWIDTHX_DEFAULT; - } - if (cffont->private[0] && - cff_dict_known(cffont->private[0], "nominalWidthX")) { - nominal_width = (double) cff_dict_get(cffont->private[0], "nominalWidthX", 0); - } else { - nominal_width = CFF_NOMINALWIDTHX_DEFAULT; - } + /* insert notdef */ + glyph->id = 0; + if (avl_find(fd->gl_tree, glyph) == NULL) { + avl_insert(fd->gl_tree, glyph); + glyph = xtalloc(1, glw_entry); + } - num_glyphs = 0; - last_cid = 0; - glyph = xtalloc(1,glw_entry); + avl_t_init(&t, fd->gl_tree); + for (found = (glw_entry *) avl_t_first(&t, fd->gl_tree); + found != NULL; found = (glw_entry *) avl_t_next(&t)) { + if (found->id > last_cid) + last_cid = found->id; + num_glyphs++; + } - /* insert notdef */ - glyph->id = uglytype1fix; - if (avl_find(fd->gl_tree, glyph)==NULL) { - /*fprintf(stderr,"seeding .notdef at %i\n",uglytype1fix);*/ - avl_insert(fd->gl_tree, glyph); - glyph = xtalloc(1,glw_entry); - } + { + cff_fdselect *fdselect; + fdselect = xcalloc(1, sizeof(cff_fdselect)); + fdselect->format = 3; + fdselect->num_entries = 1; + fdselect->data.ranges = xcalloc(1, sizeof(cff_range3)); + fdselect->data.ranges[0].first = 0; + fdselect->data.ranges[0].fd = 0; + cffont->fdselect = fdselect; + } - avl_t_init(&t, fd->gl_tree); - for (found = (glw_entry *) avl_t_first(&t, fd->gl_tree); - found != NULL; - found = (glw_entry *) avl_t_next(&t)) { - if (found->id > last_cid) - last_cid = found->id; - num_glyphs++; - } + { + cff_charsets *charset; + + charset = xcalloc(1, sizeof(cff_charsets)); + charset->format = 0; + charset->num_entries = num_glyphs - 1; + charset->data.glyphs = xcalloc(num_glyphs, sizeof(s_SID)); + + gid = 0; + + avl_t_init(&t, fd->gl_tree); + for (found = (glw_entry *) avl_t_first(&t, fd->gl_tree); + found != NULL; found = (glw_entry *) avl_t_next(&t)) { + if (found->id != 0) { + charset->data.glyphs[gid] = found->id; + gid++; + } + } + cffont->charsets = charset; + } + + cff_dict_add(cffont->topdict, "CIDCount", 1); + cff_dict_set(cffont->topdict, "CIDCount", 0, last_cid + 1); + + cffont->fdarray = xcalloc(1, sizeof(cff_dict *)); + cffont->fdarray[0] = cff_new_dict(); + cff_dict_add(cffont->fdarray[0], "FontName", 1); + cff_dict_set(cffont->fdarray[0], "FontName", 0, (double) cff_add_string(cffont, fullname)); /* FIXME: Skip XXXXXX+ */ + cff_dict_add(cffont->fdarray[0], "Private", 2); + cff_dict_set(cffont->fdarray[0], "Private", 0, 0.0); + cff_dict_set(cffont->fdarray[0], "Private", 0, 0.0); + /* FDArray - index offset, not known yet */ + cff_dict_add(cffont->topdict, "FDArray", 1); + cff_dict_set(cffont->topdict, "FDArray", 0, 0.0); + /* FDSelect - offset, not known yet */ + cff_dict_add(cffont->topdict, "FDSelect", 1); + cff_dict_set(cffont->topdict, "FDSelect", 0, 0.0); + + cff_dict_remove(cffont->topdict, "UniqueID"); + cff_dict_remove(cffont->topdict, "XUID"); + cff_dict_remove(cffont->topdict, "Private"); + cff_dict_remove(cffont->topdict, "Encoding"); + + cffont->offset = cff_dict_get(cffont->topdict, "CharStrings", 0); + cs_idx = cff_get_index_header(cffont); + + offset = cffont->offset; + cs_count = cs_idx->count; + if (cs_count < 2) { + CFF_ERROR("No valid charstring data found."); + } + + /* build the new charstrings entry */ + charstrings = cff_new_index(cs_count + 1); + max_len = 2 * CS_STR_LEN_MAX; + charstrings->data = xcalloc(max_len, sizeof(card8)); + charstring_len = 0; - { - cff_fdselect *fdselect; + gid = 0; + data = xcalloc(CS_STR_LEN_MAX, sizeof(card8)); - fdselect = xcalloc(1, sizeof(cff_fdselect)); - fdselect->format = 3; - fdselect->num_entries = 1; - fdselect->data.ranges = xcalloc(1, sizeof(cff_range3)); - fdselect->data.ranges[0].first = 0; - fdselect->data.ranges[0].fd = 0; - cffont->fdselect = fdselect; - } + { + int i; + for (i = 0; i < cs_count; i++) { + code = i; + glyph->id = code; + DO_COPY_CHARSTRING(); + } + } - { - cff_charsets *charset; + /* this happens if the internal metrics do not agree with the actual disk font */ + if (gid < num_glyphs) { + WARN("embedded subset is smaller than expected: %d instead of %d glyphs.", gid, num_glyphs); + num_glyphs = gid; + } - charset = xcalloc(1, sizeof(cff_charsets)); - charset->format = 0; - charset->num_entries = num_glyphs-1; - charset->data.glyphs = xcalloc(num_glyphs, sizeof(s_SID)); + xfree(data); + cff_release_index(cs_idx); - gid = 0; + (charstrings->offset)[num_glyphs] = charstring_len + 1; + charstrings->count = num_glyphs; + cffont->num_glyphs = num_glyphs; + cffont->cstrings = charstrings; - avl_t_init(&t, fd->gl_tree); - for (found = (glw_entry *) avl_t_first(&t, fd->gl_tree); - found != NULL; - found = (glw_entry *) avl_t_next(&t)) { - if(found->id!=0) { - charset->data.glyphs[gid] = found->id; - gid++; - } - } - cffont->charsets = charset; - } + /* + * We don't use subroutines at all. + */ + if (cffont->gsubr) + cff_release_index(cffont->gsubr); + cffont->gsubr = cff_new_index(0); - cff_dict_add(cffont->topdict, "CIDCount", 1); - cff_dict_set(cffont->topdict, "CIDCount", 0, last_cid + 1); - - cffont->fdarray = xcalloc(1, sizeof(cff_dict *)); - cffont->fdarray[0] = cff_new_dict(); - cff_dict_add(cffont->fdarray[0], "FontName", 1); - cff_dict_set(cffont->fdarray[0], "FontName", 0, - (double) cff_add_string(cffont, fullname)); /* FIXME: Skip XXXXXX+ */ - cff_dict_add(cffont->fdarray[0], "Private", 2); - cff_dict_set(cffont->fdarray[0], "Private", 0, 0.0); - cff_dict_set(cffont->fdarray[0], "Private", 0, 0.0); - /* FDArray - index offset, not known yet */ - cff_dict_add(cffont->topdict, "FDArray", 1); - cff_dict_set(cffont->topdict, "FDArray", 0, 0.0); - /* FDSelect - offset, not known yet */ - cff_dict_add(cffont->topdict, "FDSelect", 1); - cff_dict_set(cffont->topdict, "FDSelect", 0, 0.0); - - cff_dict_remove(cffont->topdict, "UniqueID"); - cff_dict_remove(cffont->topdict, "XUID"); - cff_dict_remove(cffont->topdict, "Private"); - cff_dict_remove(cffont->topdict, "Encoding"); - - cffont->offset = cff_dict_get(cffont->topdict, "CharStrings", 0); - cs_idx = cff_get_index_header(cffont); - - offset = cffont->offset; - cs_count = cs_idx->count; - if (cs_count < 2) { - CFF_ERROR("No valid charstring data found."); - } + if (cffont->subrs && cffont->subrs[0]) + cff_release_index(cffont->subrs[0]); + cffont->subrs[0] = NULL; - /* build the new charstrings entry */ - charstrings = cff_new_index(cs_count+1); - max_len = 2 * CS_STR_LEN_MAX; - charstrings->data = xcalloc(max_len, sizeof(card8)); - charstring_len = 0; - - gid = 0; - data = xcalloc(CS_STR_LEN_MAX, sizeof(card8)); - - for (code=0; code < cs_count; code++) { - glyph->id = code; - if ((avl_find(fd->gl_tree,glyph) != NULL)) { - size = cs_idx->offset[code+1] - cs_idx->offset[code]; - - if (size > CS_STR_LEN_MAX) { - pdftex_fail("Charstring too long: gid=%u, %ld bytes", code, size); - } - if (charstring_len + CS_STR_LEN_MAX >= max_len) { - max_len = charstring_len + 2 * CS_STR_LEN_MAX; - charstrings->data = xrealloc(charstrings->data, max_len*sizeof(card8)); - } - (charstrings->offset)[gid] = charstring_len + 1; - cffont->offset= offset + (cs_idx->offset)[code] - 1; - memcpy(data,&cffont->stream[cffont->offset],size); - charstring_len += cs_copy_charstring(charstrings->data + charstring_len, - max_len - charstring_len, - data, size, - cffont->gsubr, (cffont->subrs)[0], - default_width, nominal_width, NULL); - gid++; + if (cffont->private && (cffont->private)[0]) { + cff_dict_remove((cffont->private)[0], "Subrs"); /* no Subrs */ } - } - - /* this happens if the internal metrics do not agree with the actual disk font */ - if (gid < num_glyphs) { - WARN("embedded subset is smaller than expected: %d instead of %d glyphs.", gid, num_glyphs); - num_glyphs = gid; - } - - xfree(data); - cff_release_index(cs_idx); - - (charstrings->offset)[num_glyphs] = charstring_len + 1; - charstrings->count = num_glyphs; - cffont->num_glyphs = num_glyphs; - cffont->cstrings = charstrings; - - /* - * We don't use subroutines at all. - */ - if (cffont->gsubr) - cff_release_index(cffont->gsubr); - cffont->gsubr = cff_new_index(0); - - if (cffont->subrs && cffont->subrs[0]) - cff_release_index(cffont->subrs[0]); - cffont->subrs[0] = NULL; - - if (cffont->private && (cffont->private)[0]) { - cff_dict_remove((cffont->private)[0], "Subrs"); /* no Subrs */ - } - cff_add_string(cffont, (char *)"Adobe"); - cff_add_string(cffont, (char *)"Identity"); + cff_add_string(cffont, (char *) "Adobe"); + cff_add_string(cffont, (char *) "Identity"); - cff_dict_update(cffont->topdict, cffont); - cff_dict_update(cffont->private[0], cffont); - cff_update_string(cffont); + cff_dict_update(cffont->topdict, cffont); + cff_dict_update(cffont->private[0], cffont); + cff_update_string(cffont); - /* CFF code need to be rewrote... */ - cff_dict_add(cffont->topdict, "ROS", 3); - cff_dict_set(cffont->topdict, "ROS", 0, - (double) cff_get_sid(cffont, (char *)"Adobe")); - cff_dict_set(cffont->topdict, "ROS", 1, - (double) cff_get_sid(cffont, (char *)"Identity")); - cff_dict_set(cffont->topdict, "ROS", 2, 0.0); + /* CFF code need to be rewrote... */ + cff_dict_add(cffont->topdict, "ROS", 3); + cff_dict_set(cffont->topdict, "ROS", 0, + (double) cff_get_sid(cffont, (char *) "Adobe")); + cff_dict_set(cffont->topdict, "ROS", 1, + (double) cff_get_sid(cffont, (char *) "Identity")); + cff_dict_set(cffont->topdict, "ROS", 2, 0.0); - write_fontfile(cffont,fullname); - xfree(fullname); - cff_close (cffont); + write_fontfile(cffont, fullname); + xfree(fullname); + cff_close(cffont); } @@ -3086,236 +3134,245 @@ void write_cff(cff_font *cffont, fd_entry *fd, int uglytype1fix) { /* Input : SID or CID (16-bit unsigned int) * Output: glyph index */ -card16 -cff_charsets_lookup (cff_font *cff, card16 cid) +card16 cff_charsets_lookup(cff_font * cff, card16 cid) { - card16 gid = 0; - cff_charsets *charset; - card16 i; - - if (cff->flag & (CHARSETS_ISOADOBE|CHARSETS_EXPERT|CHARSETS_EXPSUB)) { - ERROR("Predefined CFF charsets not supported yet"); - } else if (cff->charsets == NULL) { - ERROR("Charsets data not available"); - } + card16 gid = 0; + cff_charsets *charset; + card16 i; - if (cid == 0) { - return 0; /* GID 0 (.notdef) */ - } + if (cff->flag & (CHARSETS_ISOADOBE | CHARSETS_EXPERT | CHARSETS_EXPSUB)) { + ERROR("Predefined CFF charsets not supported yet"); + } else if (cff->charsets == NULL) { + ERROR("Charsets data not available"); + } - charset = cff->charsets; - - gid = 0; - switch (charset->format) { - case 0: - for (i = 0; i <charset->num_entries; i++) { - if (cid == charset->data.glyphs[i]) { - gid = i + 1; - return gid; - } - } - break; - case 1: - for (i = 0; i < charset->num_entries; i++) { - if (cid >= charset->data.range1[i].first && - cid <= charset->data.range1[i].first + charset->data.range1[i].n_left) { - gid += cid - charset->data.range1[i].first + 1; - return gid; - } - gid += charset->data.range1[i].n_left + 1; - } - break; - case 2: - for (i = 0; i < charset->num_entries; i++) { - if (cid >= charset->data.range2[i].first && - cid <= charset->data.range2[i].first + charset->data.range2[i].n_left) { - gid += cid - charset->data.range2[i].first + 1; - return gid; - } - gid += charset->data.range2[i].n_left + 1; - } - break; - default: - ERROR("Unknown Charset format"); - } + if (cid == 0) { + return 0; /* GID 0 (.notdef) */ + } + + charset = cff->charsets; - return 0; /* not found */ + gid = 0; + switch (charset->format) { + case 0: + for (i = 0; i < charset->num_entries; i++) { + if (cid == charset->data.glyphs[i]) { + gid = i + 1; + return gid; + } + } + break; + case 1: + for (i = 0; i < charset->num_entries; i++) { + if (cid >= charset->data.range1[i].first && + cid <= + charset->data.range1[i].first + + charset->data.range1[i].n_left) { + gid += cid - charset->data.range1[i].first + 1; + return gid; + } + gid += charset->data.range1[i].n_left + 1; + } + break; + case 2: + for (i = 0; i < charset->num_entries; i++) { + if (cid >= charset->data.range2[i].first && + cid <= + charset->data.range2[i].first + + charset->data.range2[i].n_left) { + gid += cid - charset->data.range2[i].first + 1; + return gid; + } + gid += charset->data.range2[i].n_left + 1; + } + break; + default: + ERROR("Unknown Charset format"); + } + + return 0; /* not found */ } #define is_cidfont(a) ((a)->flag & FONTTYPE_CIDFONT) #define CID_MAX 65535 -void write_cid_cff(cff_font *cffont, fd_entry *fd, int uglytype1fix) { - cff_index *charstrings, *cs_idx; +void write_cid_cff(cff_font * cffont, fd_entry * fd) +{ + cff_index *charstrings, *cs_idx; - long charstring_len, max_len; - long size, offset = 0; + long charstring_len, max_len; + long size, offset = 0; - card8 *data; - card16 num_glyphs, cs_count, gid, last_cid; + card8 *data; + card16 num_glyphs, cs_count, gid, last_cid; - int fdsel, prev_fd, cid_count, cid; - char *fullname; + int fdsel, prev_fd, cid_count, cid; + char *fullname; - glw_entry *glyph; + glw_entry *glyph; - unsigned char *CIDToGIDMap = NULL; + unsigned char *CIDToGIDMap = NULL; - cff_fdselect *fdselect = NULL; - cff_charsets *charset = NULL; + cff_fdselect *fdselect = NULL; + cff_charsets *charset = NULL; - if (!is_cidfont(cffont)) { - perror("Not a CIDfont."); - return; - } + if (!is_cidfont(cffont)) { + perror("Not a CIDfont."); + return; + } - fullname = xcalloc(8+strlen(fd->fontname),1); - sprintf(fullname,"%s+%s",fd->subset_tag,fd->fontname); + fullname = xcalloc(8 + strlen(fd->fontname), 1); + sprintf(fullname, "%s+%s", fd->subset_tag, fd->fontname); - /* finish parsing the CFF */ + /* finish parsing the CFF */ - if (cff_dict_known(cffont->topdict, "CIDCount")) { - cid_count = (card16) cff_dict_get(cffont->topdict, "CIDCount", 0); - } else { - cid_count = CFF_CIDCOUNT_DEFAULT; - } - cff_read_charsets(cffont); - CIDToGIDMap = xmalloc((2*cid_count) * sizeof(unsigned char)); - memset(CIDToGIDMap, 0, 2*cid_count); + if (cff_dict_known(cffont->topdict, "CIDCount")) { + cid_count = (card16) cff_dict_get(cffont->topdict, "CIDCount", 0); + } else { + cid_count = CFF_CIDCOUNT_DEFAULT; + } + cff_read_charsets(cffont); + CIDToGIDMap = xmalloc((2 * cid_count) * sizeof(unsigned char)); + memset(CIDToGIDMap, 0, 2 * cid_count); - glyph = xtalloc(1,glw_entry); - /* insert notdef */ - glyph->id = uglytype1fix; - if (avl_find(fd->gl_tree, glyph)==NULL) { - avl_insert(fd->gl_tree, glyph); - glyph = xtalloc(1,glw_entry); - } + glyph = xtalloc(1, glw_entry); + /* insert notdef */ + glyph->id = 0; + if (avl_find(fd->gl_tree, glyph) == NULL) { + avl_insert(fd->gl_tree, glyph); + glyph = xtalloc(1, glw_entry); + } - cid = 0; last_cid = 0; num_glyphs = 0; - for (cid = 0; cid <= CID_MAX; cid++) { - glyph->id = cid; - if (avl_find(fd->gl_tree,glyph) != NULL) { - gid = cff_charsets_lookup(cffont, cid); - CIDToGIDMap[2*cid] = (gid >> 8) & 0xff; - CIDToGIDMap[2*cid+1] = gid & 0xff; - last_cid = cid; - num_glyphs++; + cid = 0; + last_cid = 0; + num_glyphs = 0; + for (cid = 0; cid <= CID_MAX; cid++) { + glyph->id = cid; + if (avl_find(fd->gl_tree, glyph) != NULL) { + gid = cff_charsets_lookup(cffont, cid); + CIDToGIDMap[2 * cid] = (gid >> 8) & 0xff; + CIDToGIDMap[2 * cid + 1] = gid & 0xff; + last_cid = cid; + num_glyphs++; + } } - } - cff_read_fdselect(cffont); - cff_read_fdarray(cffont); - cff_read_private(cffont); - - cff_read_subrs (cffont); + cff_read_fdselect(cffont); + cff_read_fdarray(cffont); + cff_read_private(cffont); + cff_read_subrs(cffont); - cffont->offset = cff_dict_get(cffont->topdict, "CharStrings", 0); - cs_idx = cff_get_index_header(cffont); - offset = cffont->offset; - cs_count = cs_idx->count; - if (cs_count < 2) { - CFF_ERROR("No valid charstring data found."); - } + cffont->offset = cff_dict_get(cffont->topdict, "CharStrings", 0); + cs_idx = cff_get_index_header(cffont); - charset = xcalloc(1, sizeof(cff_charsets)); - charset->format = 0; - charset->num_entries = 0; - charset->data.glyphs = xcalloc(num_glyphs, sizeof(s_SID)); - - fdselect = xcalloc(1, sizeof(cff_fdselect)); - fdselect->format = 3; - fdselect->num_entries = 0; - fdselect->data.ranges = xcalloc(num_glyphs, sizeof(cff_range3)); - - charstrings = cff_new_index(cs_count+1); - max_len = 2 * CS_STR_LEN_MAX; - charstrings->data = xcalloc(max_len, sizeof(card8)); - charstring_len = 0; - - prev_fd = -1; gid = 0; - data = xcalloc(CS_STR_LEN_MAX, sizeof(card8)); - for (cid=0; cid <= last_cid; cid++) { - unsigned short gid_org; - - glyph->id = cid; - if (avl_find(fd->gl_tree,glyph) == NULL) - continue; - - gid_org = (CIDToGIDMap[2*cid] << 8)|(CIDToGIDMap[2*cid+1]); - size = cs_idx->offset[gid_org+1] - cs_idx->offset[gid_org]; - if (size > CS_STR_LEN_MAX) { - pdftex_fail("Charstring too long: gid=%u, %ld bytes", cid, size); - } - if (charstring_len + CS_STR_LEN_MAX >= max_len) { - max_len = charstring_len + 2 * CS_STR_LEN_MAX; - charstrings->data = xrealloc(charstrings->data, max_len*sizeof(card8)); - } - (charstrings->offset)[gid] = charstring_len + 1; - cffont->offset= offset + (cs_idx->offset)[gid_org] - 1; - memcpy(data,&cffont->stream[cffont->offset],size); - fdsel = cff_fdselect_lookup(cffont, gid_org); - charstring_len += cs_copy_charstring(charstrings->data + charstring_len, - max_len - charstring_len, - data, size, - cffont->gsubr, (cffont->subrs)[fdsel], - 0, 0, NULL); - - if (cid>0 && gid_org > 0) { - charset->data.glyphs[charset->num_entries] = cid; - charset->num_entries += 1; - } - if (fdsel != prev_fd) { - fdselect->data.ranges[fdselect->num_entries].first = gid; - fdselect->data.ranges[fdselect->num_entries].fd = fdsel; - fdselect->num_entries += 1; - prev_fd = fdsel; - } - gid++; - } - - if (gid != num_glyphs) - CFF_ERROR("Unexpected error: %i != %i", gid, num_glyphs); - xfree(data); - cff_release_index(cs_idx); - - xfree(CIDToGIDMap); - - (charstrings->offset)[num_glyphs] = charstring_len + 1; - charstrings->count = num_glyphs; - cffont->num_glyphs = num_glyphs; - cffont->cstrings = charstrings; - - cff_release_charsets(cffont->charsets); - cffont->charsets = charset; - cff_release_fdselect(cffont->fdselect); - cffont->fdselect = fdselect; - - /* - * We don't use subroutines at all. - */ - if (cffont->gsubr) - cff_release_index(cffont->gsubr); - cffont->gsubr = cff_new_index(0); - - for (fdsel = 0; fdsel < cffont->num_fds; fdsel++) { - if (cffont->subrs && cffont->subrs[fdsel]) { - cff_release_index(cffont->subrs[fdsel]); - cffont->subrs[fdsel] = NULL; - } - if (cffont->private && (cffont->private)[fdsel]) { - cff_dict_remove((cffont->private)[fdsel], "Subrs"); /* no Subrs */ + offset = cffont->offset; + cs_count = cs_idx->count; + if (cs_count < 2) { + CFF_ERROR("No valid charstring data found."); } - } - write_fontfile(cffont,fullname); - xfree(fullname); - cff_close (cffont); + charset = xcalloc(1, sizeof(cff_charsets)); + charset->format = 0; + charset->num_entries = 0; + charset->data.glyphs = xcalloc(num_glyphs, sizeof(s_SID)); + + fdselect = xcalloc(1, sizeof(cff_fdselect)); + fdselect->format = 3; + fdselect->num_entries = 0; + fdselect->data.ranges = xcalloc(num_glyphs, sizeof(cff_range3)); + + charstrings = cff_new_index(cs_count + 1); + max_len = 2 * CS_STR_LEN_MAX; + charstrings->data = xcalloc(max_len, sizeof(card8)); + charstring_len = 0; + + prev_fd = -1; + gid = 0; + data = xcalloc(CS_STR_LEN_MAX, sizeof(card8)); + for (cid = 0; cid <= last_cid; cid++) { + unsigned short gid_org; + + glyph->id = cid; + if (avl_find(fd->gl_tree, glyph) == NULL) + continue; + + gid_org = (CIDToGIDMap[2 * cid] << 8) | (CIDToGIDMap[2 * cid + 1]); + size = cs_idx->offset[gid_org + 1] - cs_idx->offset[gid_org]; + if (size > CS_STR_LEN_MAX) { + pdftex_fail("Charstring too long: gid=%u, %ld bytes", cid, size); + } + if (charstring_len + CS_STR_LEN_MAX >= max_len) { + max_len = charstring_len + 2 * CS_STR_LEN_MAX; + charstrings->data = + xrealloc(charstrings->data, max_len * sizeof(card8)); + } + (charstrings->offset)[gid] = charstring_len + 1; + cffont->offset = offset + (cs_idx->offset)[gid_org] - 1; + memcpy(data, &cffont->stream[cffont->offset], size); + fdsel = cff_fdselect_lookup(cffont, gid_org); + charstring_len += cs_copy_charstring(charstrings->data + charstring_len, + max_len - charstring_len, + data, size, + cffont->gsubr, + (cffont->subrs)[fdsel], 0, 0, + NULL); + + if (cid > 0 && gid_org > 0) { + charset->data.glyphs[charset->num_entries] = cid; + charset->num_entries += 1; + } + if (fdsel != prev_fd) { + fdselect->data.ranges[fdselect->num_entries].first = gid; + fdselect->data.ranges[fdselect->num_entries].fd = fdsel; + fdselect->num_entries += 1; + prev_fd = fdsel; + } + gid++; + } + + if (gid != num_glyphs) + CFF_ERROR("Unexpected error: %i != %i", gid, num_glyphs); + xfree(data); + cff_release_index(cs_idx); + + xfree(CIDToGIDMap); + + (charstrings->offset)[num_glyphs] = charstring_len + 1; + charstrings->count = num_glyphs; + cffont->num_glyphs = num_glyphs; + cffont->cstrings = charstrings; + + cff_release_charsets(cffont->charsets); + cffont->charsets = charset; + cff_release_fdselect(cffont->fdselect); + cffont->fdselect = fdselect; + + /* + * We don't use subroutines at all. + */ + if (cffont->gsubr) + cff_release_index(cffont->gsubr); + cffont->gsubr = cff_new_index(0); + + for (fdsel = 0; fdsel < cffont->num_fds; fdsel++) { + if (cffont->subrs && cffont->subrs[fdsel]) { + cff_release_index(cffont->subrs[fdsel]); + cffont->subrs[fdsel] = NULL; + } + if (cffont->private && (cffont->private)[fdsel]) { + cff_dict_remove((cffont->private)[fdsel], "Subrs"); /* no Subrs */ + } + } + + write_fontfile(cffont, fullname); + xfree(fullname); + cff_close(cffont); } @@ -3324,58 +3381,56 @@ void write_cid_cff(cff_font *cffont, fd_entry *fd, int uglytype1fix) { * I have defined a utility function in luafflib.c that does exactly that. * If it works out ok, I will clean up this code. */ +extern int ff_createcff(char *, unsigned char **, integer *); /* libs/luafontforge/src/luafflib.c */ -extern int ff_createcff (char *, unsigned char **, integer *); - -void writetype1w (fd_entry *fd) { - cff_font *cff; - int i; - FILE *fp; - ff_entry *ff; - unsigned char *tfm_buffer = NULL; - integer tfm_size = 0; - int notdefpos = 0; - - ff = check_ff_exist(fd->fm->ff_name, 0); - - fp = fopen (ff->ff_path, "rb"); - cur_file_name = ff->ff_path; - - if (!fp) { - fprintf(stderr,"Type1: Could not open Type1 font: %s", cur_file_name); - uexit(1); - } - fclose(fp); +void writetype1w(fd_entry * fd) +{ + cff_font *cff; + int i; + FILE *fp; + ff_entry *ff; + unsigned char *tfm_buffer = NULL; + integer tfm_size = 0; - if (tracefilenames) { - if (is_subsetted(fd->fm)) - tex_printf ("<%s", cur_file_name); - else - tex_printf ("<<%s", cur_file_name); - } + ff = check_ff_exist(fd->fm->ff_name, 0); - notdefpos = ff_createcff(ff->ff_path,&tfm_buffer,&tfm_size); + fp = fopen(ff->ff_path, "rb"); + cur_file_name = ff->ff_path; - if (tfm_size>0) { - cff = read_cff(tfm_buffer,tfm_size,0); - if (cff != NULL) { - write_cff(cff,fd,notdefpos); - } else { - for (i = 0; i < tfm_size ; i++) - fb_putchar (tfm_buffer[i]); + if (!fp) { + fprintf(stderr, "Type1: Could not open Type1 font: %s", cur_file_name); + uexit(1); + } + fclose(fp); + + if (tracefilenames) { + if (is_subsetted(fd->fm)) + tex_printf("<%s", cur_file_name); + else + tex_printf("<<%s", cur_file_name); } - fd->ff_found = 1; - } else { - fprintf(stderr,"Type1: Could not understand Type1 font: %s", cur_file_name); - uexit(1); - } - if (tracefilenames) { - if (is_subsetted (fd->fm)) - tex_printf (">"); - else - tex_printf (">>"); - } - cur_file_name = NULL; -} + (void) ff_createcff(ff->ff_path, &tfm_buffer, &tfm_size); + if (tfm_size > 0) { + cff = read_cff(tfm_buffer, tfm_size, 0); + if (cff != NULL) { + write_cff(cff, fd); + } else { + for (i = 0; i < tfm_size; i++) + fb_putchar(tfm_buffer[i]); + } + fd->ff_found = 1; + } else { + fprintf(stderr, "Type1: Could not understand Type1 font: %s", + cur_file_name); + uexit(1); + } + if (tracefilenames) { + if (is_subsetted(fd->fm)) + tex_printf(">"); + else + tex_printf(">>"); + } + cur_file_name = NULL; +} diff --git a/Build/source/texk/web2c/luatexdir/font/writecff.h b/Build/source/texk/web2c/luatexdir/font/writecff.h index 8cb93024f7a..2d92a8723ae 100644 --- a/Build/source/texk/web2c/luatexdir/font/writecff.h +++ b/Build/source/texk/web2c/luatexdir/font/writecff.h @@ -1,349 +1,344 @@ -/* $Header: /home/cvsroot/dvipdfmx/src/cff_limits.h,v 1.3 2002/10/30 02:27:05 chofchof Exp $ +/* writecff.h - This is dvipdfmx, an eXtended version of dvipdfm by Mark A. Wicks. + Copyright 2002 by Jin-Hwan Cho and Shunsaku Hirata, + the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> - Copyright (C) 2002 by Jin-Hwan Cho and Shunsaku Hirata, - the dvipdfmx project team <dvipdfmx@project.ktug.or.kr> - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. -*/ + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ + +/* $Id: writecff.h 1518 2008-09-30 08:18:10Z taco $ */ #ifndef _CFF_LIMITS_H_ -#define _CFF_LIMITS_H_ +# define _CFF_LIMITS_H_ -#include <limits.h> +# include <limits.h> -#define CFF_INT_MAX 0x7fffffff -#define CFF_INT_MIN (-0x7fffffff - 1) +# define CFF_INT_MAX 0x7fffffff +# define CFF_INT_MIN (-0x7fffffff - 1) -#if (LONG_MAX < CFF_INT_MAX || LONG_MIN > CFF_INT_MIN) -#error "CFF support won't work on this system." -#endif +# if (LONG_MAX < CFF_INT_MAX || LONG_MIN > CFF_INT_MIN) +# error "CFF support won't work on this system." +# endif -#define CFF_SID_MAX 64999 -#define CFF_STDSTR_MAX 391 +# define CFF_SID_MAX 64999 +# define CFF_STDSTR_MAX 391 /* Type 2 Charstring */ -#define CS_NUM_SUBR_MAX 65536 -#define CS_STR_LEN_MAX 65536 -#define CS_STEM_ZONE_MAX 96 -#define CS_ARG_STACK_MAX 48 -#define CS_TRANS_ARRAY_MAX 32 -#define CS_SUBR_NEST_MAX 10 +# define CS_NUM_SUBR_MAX 65536 +# define CS_STR_LEN_MAX 65536 +# define CS_STEM_ZONE_MAX 96 +# define CS_ARG_STACK_MAX 48 +# define CS_TRANS_ARRAY_MAX 32 +# define CS_SUBR_NEST_MAX 10 -#endif /* _CFF_LIMITS_H_ */ +#endif /* _CFF_LIMITS_H_ */ #ifndef _CFF_TYPES_H_ -#define _CFF_TYPES_H_ +# define _CFF_TYPES_H_ /* CFF Data Types */ -#define CFF_TYPE_UNKNOWN 0 -#define CFF_TYPE_INTEGER (1 << 0) -#define CFF_TYPE_REAL (1 << 1) -#define CFF_TYPE_NUMBER (CFF_TYPE_INTEGER|CFF_TYPE_REAL) -#define CFF_TYPE_BOOLEAN (1 << 2) -#define CFF_TYPE_SID (1 << 3) -#define CFF_TYPE_ARRAY (1 << 4) -#define CFF_TYPE_DELTA (1 << 5) +# define CFF_TYPE_UNKNOWN 0 +# define CFF_TYPE_INTEGER (1 << 0) +# define CFF_TYPE_REAL (1 << 1) +# define CFF_TYPE_NUMBER (CFF_TYPE_INTEGER|CFF_TYPE_REAL) +# define CFF_TYPE_BOOLEAN (1 << 2) +# define CFF_TYPE_SID (1 << 3) +# define CFF_TYPE_ARRAY (1 << 4) +# define CFF_TYPE_DELTA (1 << 5) /* SID SID number */ -#define CFF_TYPE_ROS (1 << 6) +# define CFF_TYPE_ROS (1 << 6) /* offset(0) */ -#define CFF_TYPE_OFFSET (1 << 7) +# define CFF_TYPE_OFFSET (1 << 7) /* size offset(0) */ -#define CFF_TYPE_SZOFF (1 << 8) +# define CFF_TYPE_SZOFF (1 << 8) -typedef unsigned char card8; /* 1-byte unsigned number */ -typedef unsigned short card16; /* 2-byte unsigned number */ -typedef unsigned char c_offsize; /* 1-byte unsigned number specifies the size - of an Offset field or fields, range 1-4 */ -typedef unsigned long l_offset; /* 1, 2, 3, or 4-byte offset */ -typedef unsigned short s_SID; /* 2-byte string identifier */ +typedef unsigned char card8; /* 1-byte unsigned number */ +typedef unsigned short card16; /* 2-byte unsigned number */ +typedef unsigned char c_offsize; /* 1-byte unsigned number specifies the size + of an Offset field or fields, range 1-4 */ +typedef unsigned long l_offset; /* 1, 2, 3, or 4-byte offset */ +typedef unsigned short s_SID; /* 2-byte string identifier */ -typedef unsigned long l_size; +typedef unsigned long l_size; typedef struct { - card16 count; /* number of objects stored in INDEX */ - c_offsize offsize; /* Offset array element size, 1-4 */ - l_offset *offset; /* Offset array, count + 1 offsets */ - card8 *data; /* Object data */ + card16 count; /* number of objects stored in INDEX */ + c_offsize offsize; /* Offset array element size, 1-4 */ + l_offset *offset; /* Offset array, count + 1 offsets */ + card8 *data; /* Object data */ } cff_index; /* Dictionary */ typedef struct { - int id; /* encoded data value (as card8 or card16) */ - char *key; /* opname */ - int count; /* number of values */ - double *values; /* values */ + int id; /* encoded data value (as card8 or card16) */ + char *key; /* opname */ + int count; /* number of values */ + double *values; /* values */ } cff_dict_entry; typedef struct { - int max; - int count; - cff_dict_entry *entries; + int max; + int count; + cff_dict_entry *entries; } cff_dict; /* Encoding, Charset and FDSelect */ -typedef struct -{ - s_SID first; /* SID or CID, or card8 for Encoding */ - card8 n_left; /* no. of remaining gids/codes in this range */ +typedef struct { + s_SID first; /* SID or CID, or card8 for Encoding */ + card8 n_left; /* no. of remaining gids/codes in this range */ } cff_range1; -typedef struct -{ - s_SID first; /* SID or CID (card16) */ - card16 n_left; /* card16-version of range1 */ +typedef struct { + s_SID first; /* SID or CID (card16) */ + card16 n_left; /* card16-version of range1 */ } cff_range2; -typedef struct -{ - card8 code; - s_SID glyph; +typedef struct { + card8 code; + s_SID glyph; } cff_map; -typedef struct -{ - card8 format; /* if (format & 0x80) then have supplement */ - card8 num_entries; /* number of entries */ - union { - card8 *codes; /* format 0 */ - cff_range1 *range1; /* format 1 */ - } data; - card8 num_supps; /* number of supplementary data */ - cff_map *supp; /* supplement */ +typedef struct { + card8 format; /* if (format & 0x80) then have supplement */ + card8 num_entries; /* number of entries */ + union { + card8 *codes; /* format 0 */ + cff_range1 *range1; /* format 1 */ + } data; + card8 num_supps; /* number of supplementary data */ + cff_map *supp; /* supplement */ } cff_encoding; -typedef struct -{ - card8 format; - card16 num_entries; - union { - s_SID *glyphs; /* format 0 */ - cff_range1 *range1; /* format 1 */ - cff_range2 *range2; /* format 2 */ - } data; +typedef struct { + card8 format; + card16 num_entries; + union { + s_SID *glyphs; /* format 0 */ + cff_range1 *range1; /* format 1 */ + cff_range2 *range2; /* format 2 */ + } data; } cff_charsets; /* CID-Keyed font specific */ -typedef struct -{ - card16 first; - card8 fd; +typedef struct { + card16 first; + card8 fd; } cff_range3; -typedef struct -{ - card8 format; - card16 num_entries; /* number of glyphs/ranges */ - union { - card8 *fds; /* format 0 */ - cff_range3 *ranges; /* format 3 */ - } data; - /* card16 sentinel; */ /* format 3 only, must be equals to num_glyphs */ +typedef struct { + card8 format; + card16 num_entries; /* number of glyphs/ranges */ + union { + card8 *fds; /* format 0 */ + cff_range3 *ranges; /* format 3 */ + } data; + /* card16 sentinel; *//* format 3 only, must be equals to num_glyphs */ } cff_fdselect; -#endif /* _CFF_TYPES_H_ */ +#endif /* _CFF_TYPES_H_ */ #ifndef _CFF_STDSTR_H_ -#define _CFF_STDSTR_H_ +# define _CFF_STDSTR_H_ -#define CFF_STDSTR_MAX 391 +# define CFF_STDSTR_MAX 391 extern const char *const cff_stdstr[]; -#endif /* _CFF_STDSTR_H_ */ +#endif /* _CFF_STDSTR_H_ */ #ifndef _CFF_H_ -#define _CFF_H_ +# define _CFF_H_ /*#include "mfileio.h"*/ /* Flag */ -#define FONTTYPE_CIDFONT (1 << 0) -#define FONTTYPE_FONT (1 << 1) -#define FONTTYPE_MMASTER (1 << 2) +# define FONTTYPE_CIDFONT (1 << 0) +# define FONTTYPE_FONT (1 << 1) +# define FONTTYPE_MMASTER (1 << 2) -#define ENCODING_STANDARD (1 << 3) -#define ENCODING_EXPERT (1 << 4) +# define ENCODING_STANDARD (1 << 3) +# define ENCODING_EXPERT (1 << 4) -#define CHARSETS_ISOADOBE (1 << 5) -#define CHARSETS_EXPERT (1 << 6) -#define CHARSETS_EXPSUB (1 << 7) +# define CHARSETS_ISOADOBE (1 << 5) +# define CHARSETS_EXPERT (1 << 6) +# define CHARSETS_EXPSUB (1 << 7) -#define HAVE_STANDARD_ENCODING (ENCODING_STANDARD|ENCODING_EXPERT) -#define HAVE_STANDARD_CHARSETS \ +# define HAVE_STANDARD_ENCODING (ENCODING_STANDARD|ENCODING_EXPERT) +# define HAVE_STANDARD_CHARSETS \ (CHARSETS_ISOADOBE|CHARSETS_EXPERT|CHARSETS_EXPSUB) -#define CFF_STRING_NOTDEF 65535 - -typedef struct -{ - char *fontname; /* FontName */ - - /* - CFF structure - */ - - card8 header_major; /* major version */ - card8 header_minor; /* minor version */ - card8 header_hdr_size; /* Header size (bytes) */ - c_offsize header_offsize; /* Absolute offset (0) size */ - - cff_index *name; /* Name INDEX */ - cff_dict *topdict; /* Top DICT (single) */ - cff_index *string; /* String INDEX */ - cff_index *gsubr; /* Global Subr INDEX */ - cff_encoding *encoding; /* Encodings */ - cff_charsets *charsets; /* Charsets */ - cff_fdselect *fdselect; /* FDSelect, CIDFont only */ - cff_index *cstrings; /* CharStrings */ - cff_dict **fdarray; /* CIDFont only */ - cff_dict **private; /* per-Font DICT */ - cff_index **subrs; /* Local Subr INDEX, per-Private DICT */ - - /* -- extra data -- */ - l_offset gsubr_offset; - card16 num_glyphs; /* number of glyphs (CharString INDEX count) */ - card8 num_fds; /* number of Font DICT */ - - /* Updated String INDEX. - * Please fix this. We should separate input and output. - */ - cff_index *_string; - - unsigned char *stream; - l_offset offset; - l_offset stream_size; - - int index; /* CFF fontset index */ - int flag; /* Flag: see above */ +# define CFF_STRING_NOTDEF 65535 + +typedef struct { + char *fontname; /* FontName */ + + /* - CFF structure - */ + + card8 header_major; /* major version */ + card8 header_minor; /* minor version */ + card8 header_hdr_size; /* Header size (bytes) */ + c_offsize header_offsize; /* Absolute offset (0) size */ + + cff_index *name; /* Name INDEX */ + cff_dict *topdict; /* Top DICT (single) */ + cff_index *string; /* String INDEX */ + cff_index *gsubr; /* Global Subr INDEX */ + cff_encoding *encoding; /* Encodings */ + cff_charsets *charsets; /* Charsets */ + cff_fdselect *fdselect; /* FDSelect, CIDFont only */ + cff_index *cstrings; /* CharStrings */ + cff_dict **fdarray; /* CIDFont only */ + cff_dict **private; /* per-Font DICT */ + cff_index **subrs; /* Local Subr INDEX, per-Private DICT */ + + /* -- extra data -- */ + l_offset gsubr_offset; + card16 num_glyphs; /* number of glyphs (CharString INDEX count) */ + card8 num_fds; /* number of Font DICT */ + + /* Updated String INDEX. + * Please fix this. We should separate input and output. + */ + cff_index *_string; + + unsigned char *stream; + l_offset offset; + l_offset stream_size; + + int index; /* CFF fontset index */ + int flag; /* Flag: see above */ } cff_font; extern cff_font *cff_open(unsigned char *stream, long stream_size, int n); -extern void cff_close (cff_font *cff); +extern void cff_close(cff_font * cff); -#define cff_seek_set(c, p) seek_absolute (((c)->stream), ((c)->offset) + (p)); +# define cff_seek_set(c, p) seek_absolute (((c)->stream), ((c)->offset) + (p)); /* CFF Header */ -extern long cff_put_header (cff_font *cff, card8 *dest, long destlen); +extern long cff_put_header(cff_font * cff, card8 * dest, long destlen); /* CFF INDEX */ -extern cff_index *cff_get_index (cff_font *cff); -extern cff_index *cff_get_index_header (cff_font *cff); -extern void cff_release_index (cff_index *idx); -extern cff_index *cff_new_index (card16 count); -extern long cff_index_size (cff_index *idx); -extern long cff_pack_index (cff_index *idx, card8 *dest, long destlen); +extern cff_index *cff_get_index(cff_font * cff); +extern cff_index *cff_get_index_header(cff_font * cff); +extern void cff_release_index(cff_index * idx); +extern cff_index *cff_new_index(card16 count); +extern long cff_index_size(cff_index * idx); +extern long cff_pack_index(cff_index * idx, card8 * dest, long destlen); /* Name INDEX */ -extern char *cff_get_name (cff_font *cff); -extern long cff_set_name (cff_font *cff, char *name); +extern char *cff_get_name(cff_font * cff); +extern long cff_set_name(cff_font * cff, char *name); /* Global and Local Subrs INDEX */ -extern long cff_read_subrs (cff_font *cff); +extern long cff_read_subrs(cff_font * cff); /* Encoding */ -extern long cff_read_encoding (cff_font *cff); -extern long cff_pack_encoding (cff_font *cff, card8 *dest, long destlen); -extern card16 cff_encoding_lookup (cff_font *cff, card8 code); -extern void cff_release_encoding (cff_encoding *encoding); +extern long cff_read_encoding(cff_font * cff); +extern long cff_pack_encoding(cff_font * cff, card8 * dest, long destlen); +extern card16 cff_encoding_lookup(cff_font * cff, card8 code); +extern void cff_release_encoding(cff_encoding * encoding); /* Charsets */ -extern long cff_read_charsets (cff_font *cff); -extern long cff_pack_charsets (cff_font *cff, card8 *dest, long destlen); +extern long cff_read_charsets(cff_font * cff); +extern long cff_pack_charsets(cff_font * cff, card8 * dest, long destlen); /* Returns GID of PS name "glyph" */ -extern card16 cff_glyph_lookup (cff_font *cff, const char *glyph); +extern card16 cff_glyph_lookup(cff_font * cff, const char *glyph); /* Returns GID of glyph with SID/CID "cid" */ -extern card16 cff_charsets_lookup (cff_font *cff, card16 cid); -extern void cff_release_charsets (cff_charsets *charset); +extern card16 cff_charsets_lookup(cff_font * cff, card16 cid); +extern void cff_release_charsets(cff_charsets * charset); /* Returns SID or CID */ -extern card16 cff_charsets_lookup_inverse (cff_font *cff, card16 gid); +extern card16 cff_charsets_lookup_inverse(cff_font * cff, card16 gid); /* FDSelect */ -extern long cff_read_fdselect (cff_font *cff); -extern long cff_pack_fdselect (cff_font *cff, card8 *dest, long destlen); -extern card8 cff_fdselect_lookup (cff_font *cff, card16 gid); -extern void cff_release_fdselect (cff_fdselect *fdselect); +extern long cff_read_fdselect(cff_font * cff); +extern long cff_pack_fdselect(cff_font * cff, card8 * dest, long destlen); +extern card8 cff_fdselect_lookup(cff_font * cff, card16 gid); +extern void cff_release_fdselect(cff_fdselect * fdselect); /* Font DICT(s) */ -extern long cff_read_fdarray (cff_font *cff); +extern long cff_read_fdarray(cff_font * cff); /* Private DICT(s) */ -extern long cff_read_private (cff_font *cff); +extern long cff_read_private(cff_font * cff); /* String */ -extern int cff_match_string (cff_font *cff, const char *str, s_SID sid); -extern char *cff_get_string (cff_font *cff, s_SID id); -extern long cff_get_sid (cff_font *cff, char *str); -extern s_SID cff_add_string (cff_font *cff, char *str); -extern void cff_update_string (cff_font *cff); +extern int cff_match_string(cff_font * cff, const char *str, s_SID sid); +extern char *cff_get_string(cff_font * cff, s_SID id); +extern long cff_get_sid(cff_font * cff, char *str); +extern s_SID cff_add_string(cff_font * cff, char *str); +extern void cff_update_string(cff_font * cff); -#define cff_is_stdstr(s) (cff_get_sid(NULL, (s)) >= 0) +# define cff_is_stdstr(s) (cff_get_sid(NULL, (s)) >= 0) -#endif /* _CFF_H_ */ +#endif /* _CFF_H_ */ #ifndef _CFF_DICT_H_ -#define _CFF_DICT_H_ +# define _CFF_DICT_H_ -#define CFF_CIDCOUNT_DEFAULT 8720 -#define CFF_NOMINALWIDTHX_DEFAULT 0.0 -#define CFF_DEFAULTWIDTHX_DEFAULT 0.0 +# define CFF_CIDCOUNT_DEFAULT 8720 +# define CFF_NOMINALWIDTHX_DEFAULT 0.0 +# define CFF_DEFAULTWIDTHX_DEFAULT 0.0 -extern cff_dict *cff_new_dict (void); -extern void cff_release_dict (cff_dict *dict); +extern cff_dict *cff_new_dict(void); +extern void cff_release_dict(cff_dict * dict); -extern void cff_dict_set (cff_dict *dict, const char *key, int idx, double value); -extern double cff_dict_get (cff_dict *dict, const char *key, int idx); -extern void cff_dict_add (cff_dict *dict, const char *key, int count); -extern void cff_dict_remove (cff_dict *dict, const char *key); -extern int cff_dict_known (cff_dict *dict, const char *key); +extern void cff_dict_set(cff_dict * dict, const char *key, int idx, + double value); +extern double cff_dict_get(cff_dict * dict, const char *key, int idx); +extern void cff_dict_add(cff_dict * dict, const char *key, int count); +extern void cff_dict_remove(cff_dict * dict, const char *key); +extern int cff_dict_known(cff_dict * dict, const char *key); /* decode/encode DICT */ -extern cff_dict *cff_dict_unpack (card8 *data, card8 *endptr); -extern long cff_dict_pack (cff_dict *dict, card8 *dest, long destlen); +extern cff_dict *cff_dict_unpack(card8 * data, card8 * endptr); +extern long cff_dict_pack(cff_dict * dict, card8 * dest, long destlen); -extern void cff_dict_update (cff_dict *dict, cff_font *cff); +extern void cff_dict_update(cff_dict * dict, cff_font * cff); -#endif /* _CFF_DICT_H_ */ +#endif /* _CFF_DICT_H_ */ #ifndef _CS_TYPE2_H_ -#define _CS_TYPE2_H_ +# define _CS_TYPE2_H_ typedef struct { - int flags; /* unused in Type 2 charstring */ - double wx, wy; - struct { - double llx, lly, urx, ury; - } bbox; - struct { - double asb, adx, ady; - card8 bchar, achar; - } seac; /* unused in Type 2 charstring */ + int flags; /* unused in Type 2 charstring */ + double wx, wy; + struct { + double llx, lly, urx, ury; + } bbox; + struct { + double asb, adx, ady; + card8 bchar, achar; + } seac; /* unused in Type 2 charstring */ } cs_ginfo; -extern long cs_copy_charstring (card8 *dest, long destlen, - card8 *src, long srclen, - cff_index *gsubr, cff_index *subr, - double default_width, double nominal_width, cs_ginfo *ginfo); -#endif /* _CS_TYPE2_H_ */ +extern long cs_copy_charstring(card8 * dest, long destlen, + card8 * src, long srclen, + cff_index * gsubr, cff_index * subr, + double default_width, double nominal_width, + cs_ginfo * ginfo); +#endif /* _CS_TYPE2_H_ */ #define cff_is_cidfont(a) (a->flag & FONTTYPE_CIDFONT) #define cff_understandable(a) (a->header_major==1) -extern cff_font *read_cff(unsigned char *buf,long buflength, int subf); +extern cff_font *read_cff(unsigned char *buf, long buflength, int subf); -extern void write_cff(cff_font *cff, fd_entry *fd, int hack); -extern void write_cid_cff(cff_font *cffont, fd_entry *fd, int uglytype1fix) ; +extern void write_cff(cff_font * cff, fd_entry * fd); +extern void write_cid_cff(cff_font * cffont, fd_entry * fd); diff --git a/Build/source/texk/web2c/luatexdir/font/writeenc.c b/Build/source/texk/web2c/luatexdir/font/writeenc.c index feaf1407d1e..648992ba6cd 100644 --- a/Build/source/texk/web2c/luatexdir/font/writeenc.c +++ b/Build/source/texk/web2c/luatexdir/font/writeenc.c @@ -1,27 +1,28 @@ -/* -Copyright (c) 1996-2005 Han The Thanh, <thanh@pdftex.org> +/* writeenc.c + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -This file is part of pdfTeX. + This file is part of LuaTeX. -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -$Id: writeenc.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" +static const char _svn_version[] = + "$Id: writeenc.c 1407 2008-07-15 10:49:28Z taco $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/writeenc.c $"; + /**********************************************************************/ /* All encoding entries go into AVL tree for fast search by name. */ @@ -93,7 +94,7 @@ void epdf_write_enc(char **glyph_names, integer fe_objnum) assert(fe_objnum != 0); pdf_begin_dict(fe_objnum, 1); pdf_puts("/Type /Encoding\n"); - pdf_printf("/Differences ["); + pdf_puts("/Differences ["); for (i = 0, i_old = -2; i < 256; i++) if (glyph_names[i] != notdef) { if (i == i_old + 1) /* no gap */ @@ -119,7 +120,7 @@ void write_enc(char **glyph_names, struct avl_table *tx_tree, integer fe_objnum) assert(fe_objnum != 0); pdf_begin_dict(fe_objnum, 1); pdf_puts("/Type /Encoding\n"); - pdf_printf("/Differences ["); + pdf_puts("/Differences ["); avl_t_init(&t, tx_tree); for (i_old = -2, p = (int *) avl_t_first(&t, tx_tree); p != NULL; p = (int *) avl_t_next(&t)) { diff --git a/Build/source/texk/web2c/luatexdir/font/writefont.c b/Build/source/texk/web2c/luatexdir/font/writefont.c index 679929e32e4..5c6b2d905a0 100644 --- a/Build/source/texk/web2c/luatexdir/font/writefont.c +++ b/Build/source/texk/web2c/luatexdir/font/writefont.c @@ -1,42 +1,32 @@ -/* -Copyright (c) 1996-2006 Han The Thanh, <thanh@pdftex.org> - -This file is part of pdfTeX. +/* writefont.c + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2009 Taco Hoekwater <taco@luatex.org> -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + This file is part of LuaTeX. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -$Id: writefont.c 1139 2008-04-09 14:44:20Z taco $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" +#include "luatexfont.h" -extern void writetype0 (fd_entry * fd) ; -extern void writetype2 (fd_entry * fd) ; -extern unsigned long cidtogid_obj; - -#ifdef DO_TYPE1C -extern void writet1c(fd_entry * fd); /* in writecff.c */ -#endif - -extern void writet1w (fd_entry * fd); /* in writecff.c */ -extern void writetype1w (fd_entry * fd); -extern integer write_cid_tounicode(fo_entry * fo, internalfontnumber f); /* in tounicode.c */ - +static const char _svn_version[] = + "$Id: writefont.c 2097 2009-03-23 22:45:03Z hhenkel $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/writefont.c $"; void write_cid_fontdictionary(fo_entry * fo, internalfontnumber f); -void create_cid_fontdictionary(fm_entry * fm, integer font_objnum, internalfontnumber f); +void create_cid_fontdictionary(fm_entry * fm, integer font_objnum, + internalfontnumber f); /**********************************************************************/ @@ -97,7 +87,7 @@ fd_entry *new_fd_entry(void) fd->fn_objnum = 0; fd->all_glyphs = false; fd->write_ttf_glyph_names = false; - for (i = 0; i < INT_KEYS_NUM; i++) { + for (i = 0; i < FONT_KEYS_NUM; i++) { fd->font_dim[i].val = 0; fd->font_dim[i].set = false; } @@ -121,21 +111,21 @@ static void preset_fontmetrics(fd_entry * fd, internalfontnumber f) int i; fd->font_dim[ITALIC_ANGLE_CODE].val = divide_scaled(-atan(get_slant(f) / 65536.0) * (180 / M_PI), - pdf_font_size(f), 3); + pdf_font_size(f), 3); fd->font_dim[ASCENT_CODE].val = - divide_scaled(char_height(f, 'h'), pdf_font_size(f), 3); + divide_scaled(char_height(f, 'h'), pdf_font_size(f), 3); fd->font_dim[CAPHEIGHT_CODE].val = - divide_scaled(char_height(f, 'H'), pdf_font_size(f), 3); + divide_scaled(char_height(f, 'H'), pdf_font_size(f), 3); i = -divide_scaled(char_depth(f, 'y'), pdf_font_size(f), 3); fd->font_dim[DESCENT_CODE].val = i < 0 ? i : 0; fd->font_dim[STEMV_CODE].val = - divide_scaled(char_width(f, '.') / 3, pdf_font_size(f), 3); + divide_scaled(char_width(f, '.') / 3, pdf_font_size(f), 3); fd->font_dim[XHEIGHT_CODE].val = - divide_scaled(get_x_height(f), pdf_font_size(f), 3); + divide_scaled(get_x_height(f), pdf_font_size(f), 3); fd->font_dim[FONTBBOX1_CODE].val = 0; fd->font_dim[FONTBBOX2_CODE].val = fd->font_dim[DESCENT_CODE].val; fd->font_dim[FONTBBOX3_CODE].val = - divide_scaled(get_quad(f), pdf_font_size(f), 3); + divide_scaled(get_quad(f), pdf_font_size(f), 3); fd->font_dim[FONTBBOX4_CODE].val = fd->font_dim[CAPHEIGHT_CODE].val > fd->font_dim[ASCENT_CODE].val ? fd->font_dim[CAPHEIGHT_CODE].val : fd->font_dim[ASCENT_CODE].val; @@ -143,16 +133,48 @@ static void preset_fontmetrics(fd_entry * fd, internalfontnumber f) fd->font_dim[i].set = true; } +static void fix_fontmetrics(fd_entry * fd) +{ + int i; + intparm *p = (intparm *) fd->font_dim; + assert(p[FONTBBOX1_CODE].set && p[FONTBBOX2_CODE].set + && p[FONTBBOX3_CODE].set && p[FONTBBOX4_CODE].set); + /* make sure there is a rectangle */ + if (p[FONTBBOX3_CODE].val < p[FONTBBOX1_CODE].val) { + i = p[FONTBBOX3_CODE].val; + p[FONTBBOX3_CODE].val = p[FONTBBOX1_CODE].val; + p[FONTBBOX1_CODE].val = i; + } else if (p[FONTBBOX3_CODE].val == p[FONTBBOX1_CODE].val) + p[FONTBBOX3_CODE].val = p[FONTBBOX1_CODE].val + 1; + if (p[FONTBBOX4_CODE].val < p[FONTBBOX2_CODE].val) { + i = p[FONTBBOX4_CODE].val; + p[FONTBBOX4_CODE].val = p[FONTBBOX2_CODE].val; + p[FONTBBOX2_CODE].val = i; + } else if (p[FONTBBOX4_CODE].val == p[FONTBBOX2_CODE].val) + p[FONTBBOX4_CODE].val = p[FONTBBOX2_CODE].val + 1; + if (!p[ASCENT_CODE].set) { + p[ASCENT_CODE].val = p[FONTBBOX4_CODE].val; + p[ASCENT_CODE].set = true; + } + if (!p[DESCENT_CODE].set) { + p[DESCENT_CODE].val = p[FONTBBOX2_CODE].val; + p[DESCENT_CODE].set = true; + } + if (!p[CAPHEIGHT_CODE].set) { + p[CAPHEIGHT_CODE].val = p[FONTBBOX4_CODE].val; + p[CAPHEIGHT_CODE].set = true; + } +} + static void write_fontmetrics(fd_entry * fd) { int i; - if (fd->font_dim[FONTBBOX1_CODE].set && fd->font_dim[FONTBBOX2_CODE].set - && fd->font_dim[FONTBBOX3_CODE].set && fd->font_dim[FONTBBOX4_CODE].set) - pdf_printf("/%s [%i %i %i %i]\n", font_key[FONTBBOX1_CODE].pdfname, - (int) fd->font_dim[FONTBBOX1_CODE].val, - (int) fd->font_dim[FONTBBOX2_CODE].val, - (int) fd->font_dim[FONTBBOX3_CODE].val, - (int) fd->font_dim[FONTBBOX4_CODE].val); + fix_fontmetrics(fd); + pdf_printf("/%s [%i %i %i %i]\n", font_key[FONTBBOX1_CODE].pdfname, + (int) fd->font_dim[FONTBBOX1_CODE].val, + (int) fd->font_dim[FONTBBOX2_CODE].val, + (int) fd->font_dim[FONTBBOX3_CODE].val, + (int) fd->font_dim[FONTBBOX4_CODE].val); for (i = 0; i < GEN_KEY_NUM; i++) if (fd->font_dim[i].set) pdf_printf("/%s %i\n", font_key[i].pdfname, fd->font_dim[i].val); @@ -299,7 +321,7 @@ void get_char_range(fo_entry * fo, internalfontnumber f) { int i; assert(fo != NULL); - for (i = font_bc(f); i <= font_ec(f); i++) /* search for first_char and last_char */ + for (i = font_bc(f); i <= font_ec(f); i++) /* search for first_char and last_char */ if (pdf_char_marked(f, i)) break; fo->first_char = i; @@ -308,15 +330,31 @@ void get_char_range(fo_entry * fo, internalfontnumber f) break; fo->last_char = i; if ((fo->first_char > fo->last_char) - || !pdf_char_marked(f, fo->first_char)) { /* no character used from this font */ + || !pdf_char_marked(f, fo->first_char)) { /* no character used from this font */ fo->last_char = 0; fo->first_char = fo->last_char + 1; } } +static int font_has_subset(internalfontnumber f) +{ + int i, s; + for (i = font_bc(f); i <= font_ec(f); i++) /* search for first_char and last_char */ + if (pdf_char_marked(f, i)) + break; + s = i; + for (i = font_ec(f); i >= font_bc(f); i--) + if (pdf_char_marked(f, i)) + break; + if (s > i) + return 0; + else + return 1; +} + static void write_charwidth_array(fo_entry * fo, internalfontnumber f) { - int i, j, *ip, *fip, width; + int i, j, *ip, *fip; struct avl_traverser t; assert(fo->tx_tree != NULL); assert(fo->cw_objnum == 0); @@ -335,10 +373,7 @@ static void write_charwidth_array(fo_entry * fo, internalfontnumber f) j++; } j = i; - width = divide_scaled(char_width(f, i), pdf_font_size(f), 4); - pdf_printf("%i", (int) width / 10); /* see adv_char_width() in pdftex.web */ - if ((width = width % 10) != 0) - pdf_printf(".%i", width); + pdf_print_charwidth(f, i); } pdf_puts("]\n"); pdf_end_obj(); @@ -374,72 +409,89 @@ void register_fo_entry(fo_entry * fo) assert(fo != NULL); assert(fo->fm != NULL); assert(fo->fm->tfm_name != NULL); - assert (lookup_fo_entry(fo->fm->tfm_name) == NULL) ; - aa = avl_probe(fo_tree, fo); - assert(aa != NULL); + assert(lookup_fo_entry(fo->fm->tfm_name) == NULL); + aa = avl_probe(fo_tree, fo); + assert(aa != NULL); } /**********************************************************************/ static void write_fontfile(fd_entry * fd) { - assert(is_included(fd->fm)); - if (is_cidkeyed(fd->fm)) { - if (is_opentype(fd->fm)) - writetype0(fd); - else if (is_truetype(fd->fm)) - writetype2(fd); - else if (is_type1(fd->fm)) - writetype1w(fd); - else - assert(0); - } else { - if (is_type1(fd->fm)) -#ifdef DO_TYPE1C - writet1c(fd); -#else - writet1(fd); -#endif - else if (is_truetype(fd->fm)) - writettf(fd); - else if (is_opentype(fd->fm)) - writeotf(fd); - else - assert(0); - } - if (!fd->ff_found) - return; - assert(fd->ff_objnum == 0); - fd->ff_objnum = pdf_new_objnum(); - pdf_begin_dict(fd->ff_objnum, 0); /* font file stream */ - if (is_cidkeyed(fd->fm)) { - /* No subtype is used for TrueType-based OpenType fonts */ - if (is_opentype(fd->fm) || is_type1(fd->fm)) - pdf_puts("/Subtype /CIDFontType0C\n"); - /* else - pdf_puts("/Subtype /OpenType\n");*/ - } else { - if (is_type1(fd->fm)) - pdf_printf("/Length1 %i\n/Length2 %i\n/Length3 %i\n", - (int) t1_length1, (int) t1_length2, (int) t1_length3); - else if (is_truetype(fd->fm)) - pdf_printf("/Length1 %i\n", (int) ttf_length); - else if (is_opentype(fd->fm)) - pdf_puts("/Subtype /Type1C\n"); - else - assert(0); + assert(is_included(fd->fm)); + if (is_cidkeyed(fd->fm)) { + if (is_opentype(fd->fm)) + writetype0(fd); + else if (is_truetype(fd->fm)) + writetype2(fd); + else if (is_type1(fd->fm)) + writetype1w(fd); + else + assert(0); + } else { + if (is_type1(fd->fm)) + writet1(fd); + else if (is_truetype(fd->fm)) + writettf(fd); + else if (is_opentype(fd->fm)) + writeotf(fd); + else + assert(0); } - pdf_begin_stream(); - fb_flush(); - pdf_end_stream(); + if (!fd->ff_found) + return; + assert(fd->ff_objnum == 0); + fd->ff_objnum = pdf_new_objnum(); + pdf_begin_dict(fd->ff_objnum, 0); /* font file stream */ + if (is_cidkeyed(fd->fm)) { + /* No subtype is used for TrueType-based OpenType fonts */ + if (is_opentype(fd->fm) || is_type1(fd->fm)) + pdf_puts("/Subtype /CIDFontType0C\n"); + /* else + pdf_puts("/Subtype /OpenType\n"); */ + } else { + if (is_type1(fd->fm)) + pdf_printf("/Length1 %i\n/Length2 %i\n/Length3 %i\n", + (int) t1_length1, (int) t1_length2, (int) t1_length3); + else if (is_truetype(fd->fm)) + pdf_printf("/Length1 %i\n", (int) ttf_length); + else if (is_opentype(fd->fm)) + pdf_puts("/Subtype /Type1C\n"); + else + assert(0); + } + pdf_begin_stream(); + fb_flush(); + pdf_end_stream(); } /**********************************************************************/ static void write_fontdescriptor(fd_entry * fd) { + static const int std_flags[] = { + /* indices for << start with 0, but bits start with 1, so the numbers + * for << are 1 lower than the bits in table 5.20 */ + /* *INDENT-OFF* */ + 1 + 2 + (1 << 5), /* Courier */ + 1 + 2 + (1 << 5) + (1 << 18),/* Courier-Bold */ + 1 + 2 + (1 << 5) + (1 << 6), /* Courier-Oblique */ + 1 + 2 + (1 << 5) + (1 << 6) + (1 << 18),/* Courier-BoldOblique */ + (1 << 5), /* Helvetica */ + (1 << 5) + (1 << 18),/* Helvetica-Bold */ + (1 << 5) + (1 << 6), /* Helvetica-Oblique */ + (1 << 5) + (1 << 6) + (1 << 18),/* Helvetica-BoldOblique */ + 4, /* Symbol */ + 2 + (1 << 5), /* Times-Roman */ + 2 + (1 << 5) + (1 << 18),/* Times-Bold */ + 2 + (1 << 5) + (1 << 6), /* Times-Italic */ + 2 + (1 << 5) + (1 << 6) + (1 << 18),/* Times-BoldItalic */ + 4 /* ZapfDingbats */ + /* *INDENT-ON* */ + }; char *glyph; struct avl_traverser t; + int fd_flags; assert(fd != NULL && fd->fm != NULL); if (is_fontfile(fd->fm)) @@ -451,13 +503,24 @@ static void write_fontdescriptor(fd_entry * fd) pdf_begin_dict(fd->fd_objnum, 1); pdf_puts("/Type /FontDescriptor\n"); write_fontname(fd, "FontName"); - if (!fd->ff_found && fd->fm->fd_flags == 4) - pdf_puts("/Flags 34\n"); /* assumes a roman sans serif font */ - else - pdf_printf("/Flags %i\n", (int) fd->fm->fd_flags); + if (fd->fm->fd_flags != FD_FLAGS_NOT_SET_IN_MAPLINE) + fd_flags = (int) fd->fm->fd_flags; + else if (fd->ff_found) + fd_flags = FD_FLAGS_DEFAULT_EMBED; + else { + fd_flags = is_std_t1font(fd->fm) + ? std_flags[check_std_t1font(fd->fm->ps_name)] + : FD_FLAGS_DEFAULT_NON_EMBED; + pdftex_warn + ("No flags specified for non-embedded font `%s' (%s) (I'm using %i): " + "fix your map entry.", + fd->fm->ps_name != NULL ? fd->fm->ps_name : "No name given", + fd->fm->tfm_name, fd_flags); + } + pdf_printf("/Flags %i\n", fd_flags); write_fontmetrics(fd); if (is_cidkeyed(fd->fm)) { - if (is_type1(fd->fm)) + if (is_type1(fd->fm)) pdf_printf("/FontFile3 %i 0 R\n", (int) fd->ff_objnum); else if (is_truetype(fd->fm)) pdf_printf("/FontFile2 %i 0 R\n", (int) fd->ff_objnum); @@ -466,36 +529,36 @@ static void write_fontdescriptor(fd_entry * fd) else assert(0); } else { - if (fd->ff_found) { - if (is_subsetted(fd->fm) && is_type1(fd->fm)) { - /* /CharSet is optional; names may appear in any order */ - assert(fd->gl_tree != NULL); - avl_t_init(&t, fd->gl_tree); - pdf_puts("/CharSet ("); - for (glyph = (char *) avl_t_first(&t, fd->gl_tree); glyph != NULL; - glyph = (char *) avl_t_next(&t)) - pdf_printf("/%s", glyph); - pdf_puts(")\n"); + if (fd->ff_found) { + if (is_subsetted(fd->fm) && is_type1(fd->fm)) { + /* /CharSet is optional; names may appear in any order */ + assert(fd->gl_tree != NULL); + avl_t_init(&t, fd->gl_tree); + pdf_puts("/CharSet ("); + for (glyph = (char *) avl_t_first(&t, fd->gl_tree); + glyph != NULL; glyph = (char *) avl_t_next(&t)) + pdf_printf("/%s", glyph); + pdf_puts(")\n"); + } + if (is_type1(fd->fm)) + pdf_printf("/FontFile %i 0 R\n", (int) fd->ff_objnum); + else if (is_truetype(fd->fm)) + pdf_printf("/FontFile2 %i 0 R\n", (int) fd->ff_objnum); + else if (is_opentype(fd->fm)) + pdf_printf("/FontFile3 %i 0 R\n", (int) fd->ff_objnum); + else + assert(0); } - if (is_type1(fd->fm)) - pdf_printf("/FontFile %i 0 R\n", (int) fd->ff_objnum); - else if (is_truetype(fd->fm)) - pdf_printf("/FontFile2 %i 0 R\n", (int) fd->ff_objnum); - else if (is_opentype(fd->fm)) - pdf_printf("/FontFile3 %i 0 R\n", (int) fd->ff_objnum); - else - assert(0); - } } /* TODO: Optional keys for CID fonts. - + The most interesting ones are - /Style << /Panose <12-byte string>>> + /Style << /Panose <12-byte string>>> and - /CIDSET <stream> + /CIDSET <stream> the latter can be used in subsets, to give the included CIDs as a bitmap on the whole list. - */ + */ pdf_end_dict(); } @@ -535,11 +598,7 @@ void write_fontdictionary(fo_entry * fo) pdf_puts("/Type /Font\n"); pdf_puts("/Subtype /"); if (is_type1(fo->fm)) -#ifdef DO_TYPE1C - pdf_printf("%s\n", "Type1C"); -#else pdf_printf("%s\n", "Type1"); -#endif else if (is_truetype(fo->fm)) pdf_printf("%s\n", "TrueType"); else if (is_opentype(fo->fm)) @@ -551,14 +610,14 @@ void write_fontdictionary(fo_entry * fo) pdf_printf("/FontDescriptor %i 0 R\n", (int) fo->fd->fd_objnum); assert(fo->cw_objnum != 0); pdf_printf("/FirstChar %i\n/LastChar %i\n/Widths %i 0 R\n", - (int) fo->first_char, (int) fo->last_char, - (int) fo->cw_objnum); - if ((is_type1(fo->fm) || is_opentype(fo->fm)) && fo->fe != NULL && fo->fe->fe_objnum != 0) + (int) fo->first_char, (int) fo->last_char, (int) fo->cw_objnum); + if ((is_type1(fo->fm) || is_opentype(fo->fm)) && fo->fe != NULL + && fo->fe->fe_objnum != 0) pdf_printf("/Encoding %i 0 R\n", (int) fo->fe->fe_objnum); if (fo->tounicode_objnum != 0) pdf_printf("/ToUnicode %i 0 R\n", (int) fo->tounicode_objnum); if (pdf_font_attr(fo->tex_font) != get_nullstr()) { - pdf_print(pdf_font_attr(fo->tex_font)); + pdf_print(pdf_font_attr(fo->tex_font)); pdf_puts("\n"); } pdf_end_dict(); @@ -596,7 +655,8 @@ void create_fontdictionary(fm_entry * fm, integer font_objnum, { fo_entry *fo = new_fo_entry(); get_char_range(fo, f); /* set fo->first_char and fo->last_char from f */ - if (fo->last_char>255) fo->last_char=255; /* added 9-4-2008, mantis #25 */ + if (fo->last_char > 255) + fo->last_char = 255; /* added 9-4-2008, mantis #25 */ assert(fo->last_char >= fo->first_char); fo->fm = fm; fo->fo_objnum = font_objnum; @@ -605,7 +665,7 @@ void create_fontdictionary(fm_entry * fm, integer font_objnum, fo->fe = get_fe_entry(fo->fm->encname); /* returns NULL if .enc file couldn't be opened */ if (fo->fe != NULL && (is_type1(fo->fm) || is_opentype(fo->fm))) { if (fo->fe->fe_objnum == 0) - fo->fe->fe_objnum = pdf_new_objnum(); /* then it will be written out */ + fo->fe->fe_objnum = pdf_new_objnum(); /* then it will be written out */ /* mark encoding pairs used by TeX to optimize encoding vector */ fo->fe->tx_tree = mark_chars(fo, fo->fe->tx_tree, f); } @@ -613,37 +673,37 @@ void create_fontdictionary(fm_entry * fm, integer font_objnum, fo->tx_tree = mark_chars(fo, fo->tx_tree, f); /* for write_charwidth_array() */ write_charwidth_array(fo, f); if (!is_builtin(fo->fm)) { - if (is_type1(fo->fm)) { - if ((fo->fd = lookup_fontdescriptor(fo)) == NULL) { - create_fontdescriptor(fo, f); - register_fd_entry(fo->fd); - } - } else - create_fontdescriptor(fo, f); - if (fo->fe != NULL) { - mark_reenc_glyphs(fo, f); - if (!is_type1(fo->fm)) { - /* mark reencoded characters as chars on TeX level */ - assert(fo->fd->tx_tree == NULL); - fo->fd->tx_tree = mark_chars(fo, fo->fd->tx_tree, f); - if (is_truetype(fo->fm)) - fo->fd->write_ttf_glyph_names = true; - } - } else - /* mark non-reencoded characters as chars on TeX level */ - fo->fd->tx_tree = mark_chars(fo, fo->fd->tx_tree, f); - if (!is_type1(fo->fm)) - write_fontdescriptor(fo->fd); + if (is_type1(fo->fm)) { + if ((fo->fd = lookup_fontdescriptor(fo)) == NULL) { + create_fontdescriptor(fo, f); + register_fd_entry(fo->fd); + } + } else + create_fontdescriptor(fo, f); + if (fo->fe != NULL) { + mark_reenc_glyphs(fo, f); + if (!is_type1(fo->fm)) { + /* mark reencoded characters as chars on TeX level */ + assert(fo->fd->tx_tree == NULL); + fo->fd->tx_tree = mark_chars(fo, fo->fd->tx_tree, f); + if (is_truetype(fo->fm)) + fo->fd->write_ttf_glyph_names = true; + } + } else + /* mark non-reencoded characters as chars on TeX level */ + fo->fd->tx_tree = mark_chars(fo, fo->fd->tx_tree, f); + if (!is_type1(fo->fm)) + write_fontdescriptor(fo->fd); } else { - /* builtin fonts still need the /Widths array and /FontDescriptor - * (to avoid error 'font FOO contains bad /BBox') - */ - create_fontdescriptor(fo, f); - write_fontdescriptor(fo->fd); - if (!is_std_t1font(fo->fm)) - pdftex_warn("font `%s' is not a standard font; " - "I suppose it is available to your PDF viewer then", - fo->fm->ps_name); + /* builtin fonts still need the /Widths array and /FontDescriptor + * (to avoid error 'font FOO contains bad /BBox') + */ + create_fontdescriptor(fo, f); + write_fontdescriptor(fo->fd); + if (!is_std_t1font(fo->fm)) + pdftex_warn("font `%s' is not a standard font; " + "I suppose it is available to your PDF viewer then", + fo->fm->ps_name); } if (is_type1(fo->fm)) register_fo_entry(fo); @@ -658,47 +718,57 @@ void do_pdf_font(integer font_objnum, internalfontnumber f) { fm_entry *fm; /* This is not 100% true: CID is actually needed whenever (and - * only) there are more than 256 separate glyphs used. But for - * now, just assume the user knows what he is doing; - */ - if (font_encodingbytes(f)==2) { - /* Create a virtual font map entry, as this is needed by the - * rest of the font inclusion mechanism. - */ - fm = new_fm_entry(); - fm->tfm_name = font_name(f); /* or whatever, not a real tfm */ - fm->ff_name = font_filename(f); /* the actual file */ - fm->encname = font_encodingname(f); /* for the CIDSystemInfo */ - fm->ps_name = font_fullname(f); /* the true name */ - fm->slant = font_slant(f); /* slant factor */ - fm->extend = font_extend(f); /* extension factor */ - fm->fd_flags = 4; /* can perhaps be done better */ - fm->in_use = true; - - switch (font_format(f)) { - case opentype_format: set_opentype(fm); break; - case truetype_format: set_truetype(fm); break; - case type1_format: set_type1(fm); break; - default: - pdftex_fail("writefont.c: The file format (%s) for font `%s' is incompatible with wide characters\n", - font_format_name(f),font_name(f)); - } - /* This makes "unknown" default to subsetted inclusion */ - if (font_embedding(f)!=no_embedding) { - set_included(fm); - if (font_embedding(f)!=full_embedding) { - set_subsetted(fm); - } - } - set_cidkeyed(fm); - create_cid_fontdictionary(fm, font_objnum, f); - + * only) there are more than 256 separate glyphs used. But for + * now, just assume the user knows what he is doing; + */ + if (!font_has_subset(f)) + return; + + if (font_encodingbytes(f) == 2) { + /* Create a virtual font map entry, as this is needed by the + * rest of the font inclusion mechanism. + */ + fm = new_fm_entry(); + fm->tfm_name = font_name(f); /* or whatever, not a real tfm */ + fm->ff_name = font_filename(f); /* the actual file */ + fm->encname = font_encodingname(f); /* for the CIDSystemInfo */ + fm->ps_name = font_fullname(f); /* the true name */ + fm->slant = font_slant(f); /* slant factor */ + fm->extend = font_extend(f); /* extension factor */ + fm->fd_flags = 4; /* can perhaps be done better */ + fm->in_use = true; + + switch (font_format(f)) { + case opentype_format: + set_opentype(fm); + break; + case truetype_format: + set_truetype(fm); + break; + case type1_format: + set_type1(fm); + break; + default: + pdftex_fail + ("writefont.c: The file format (%s) for font `%s' is incompatible with wide characters\n", + font_format_name(f), font_name(f)); + } + /* This makes "unknown" default to subsetted inclusion */ + if (font_embedding(f) != no_embedding) { + set_included(fm); + if (font_embedding(f) != full_embedding) { + set_subsetted(fm); + } + } + set_cidkeyed(fm); + create_cid_fontdictionary(fm, font_objnum, f); + } else { - fm = hasfmentry(f) ? (fm_entry *) font_map(f) : NULL; - if (fm == NULL || (fm->ps_name == NULL && fm->ff_name == NULL)) - writet3(font_objnum, f); - else - create_fontdictionary(fm, font_objnum, f); + fm = hasfmentry(f) ? (fm_entry *) font_map(f) : NULL; + if (fm == NULL || (fm->ps_name == NULL && fm->ff_name == NULL)) + writet3(font_objnum, f); + else + create_fontdictionary(fm, font_objnum, f); } } @@ -717,11 +787,11 @@ void do_pdf_font(integer font_objnum, internalfontnumber f) int comp_glw_entry(const void *pa, const void *pb, void *p) { - unsigned short i, j; - i = (*(glw_entry *)pa).id; - j = (*(glw_entry *)pb).id; - cmp_return(i,j); - return 0; + unsigned short i, j; + i = (*(glw_entry *) pa).id; + j = (*(glw_entry *) pb).id; + cmp_return(i, j); + return 0; } void create_cid_fontdescriptor(fo_entry * fo, internalfontnumber f) @@ -744,26 +814,29 @@ void create_cid_fontdescriptor(fo_entry * fo, internalfontnumber f) indexes, and those are limited to 16-bit values. */ -static void mark_cid_subset_glyphs(fo_entry *fo, internal_font_number f) -{ - int i, k; - glw_entry *j; - void *aa; - for (k = 1; k <= max_font_id(); k++) { - if ( k == f || -f == pdf_font_num(k)) { - for (i = font_bc(k); i <= font_ec(k); i++) { - if (char_exists(k,i) && char_used(k,i)) { - j = xtalloc(1,glw_entry); - j->id = char_index(k,i); - j->wd = divide_scaled_n(char_width(k, i), pdf_font_size(k), 10000.0); - if ((glw_entry *)avl_find(fo->fd->gl_tree,j) == NULL) { - aa = avl_probe(fo->fd->gl_tree, j); - assert(aa != NULL); - } - } - } +static void mark_cid_subset_glyphs(fo_entry * fo, internal_font_number f) +{ + int i, k, l; + glw_entry *j; + void *aa; + for (k = 1; k <= max_font_id(); k++) { + if (k == f || -f == pdf_font_num(k)) { + l = pdf_font_size(k); + for (i = font_bc(k); i <= font_ec(k); i++) { + if (char_exists(k, i) && char_used(k, i)) { + j = xtalloc(1, glw_entry); + j->id = char_index(k, i); + j->wd = divide_scaled_n(char_width(k, i), l, 10000.0); + if ((glw_entry *) avl_find(fo->fd->gl_tree, j) == NULL) { + aa = avl_probe(fo->fd->gl_tree, j); + assert(aa != NULL); + } else { + xfree(j); + } + } + } + } } - } } /* @@ -782,38 +855,47 @@ static void mark_cid_subset_glyphs(fo_entry *fo, internal_font_number f) static void write_cid_charwidth_array(fo_entry * fo) { - int i, j; - glw_entry *glyph; - struct avl_traverser t; - - assert(fo->cw_objnum == 0); - fo->cw_objnum = pdf_new_objnum(); - pdf_begin_obj(fo->cw_objnum, 1); - avl_t_init(&t, fo->fd->gl_tree); - glyph = (glw_entry *) avl_t_first(&t, fo->fd->gl_tree); - assert(glyph != NULL); - i = glyph->id; - pdf_printf("[ %i [", i); - for (; glyph != NULL; glyph = (glw_entry *) avl_t_next(&t)) { - j = glyph->wd; - if (glyph->id>(i+1)) { - pdf_printf("] %i [", glyph->id); - j = glyph->wd; - } - if (glyph->id==(i+1)) - pdf_puts(" "); - pdf_printf("%i", (j/10)); - if ((j % 10) != 0) - pdf_printf(".%i", (j % 10)); + int i, j; + glw_entry *glyph; + struct avl_traverser t; + + assert(fo->cw_objnum == 0); + fo->cw_objnum = pdf_new_objnum(); + pdf_begin_obj(fo->cw_objnum, 1); + avl_t_init(&t, fo->fd->gl_tree); + glyph = (glw_entry *) avl_t_first(&t, fo->fd->gl_tree); + assert(glyph != NULL); i = glyph->id; - } - pdf_puts("]]\n"); - pdf_end_obj(); + pdf_printf("[ %i [", i); + for (; glyph != NULL; glyph = (glw_entry *) avl_t_next(&t)) { + j = glyph->wd; + if (glyph->id > (unsigned) (i + 1)) { + pdf_printf("] %i [", glyph->id); + j = glyph->wd; + } + if (glyph->id == (unsigned) (i + 1)) + pdf_puts(" "); + + if (j < 0) { + pdf_puts("-"); + j = -j; + } + + /* pdf_print_charwidth(f, i); */ + + pdf_printf("%i", (j / 10)); + if ((j % 10) != 0) + pdf_printf(".%i", (j % 10)); + + i = glyph->id; + } + pdf_puts("]]\n"); + pdf_end_obj(); } void create_cid_fontdictionary(fm_entry * fm, integer font_objnum, - internalfontnumber f) + internalfontnumber f) { fo_entry *fo = new_fo_entry(); get_char_range(fo, f); /* set fo->first_char and fo->last_char from f */ @@ -821,66 +903,68 @@ void create_cid_fontdictionary(fm_entry * fm, integer font_objnum, fo->fm = fm; fo->fo_objnum = font_objnum; fo->tex_font = f; - create_cid_fontdescriptor (fo, f); - mark_cid_subset_glyphs (fo,f); + create_cid_fontdescriptor(fo, f); + mark_cid_subset_glyphs(fo, f); if (is_subsetted(fo->fm)) { - /* - this is a bit sneaky. |make_subset_tag()| actually expects the glyph tree - to contain strings instead of |glw_entry| items. However, all calculations - are done using explicit typecasts, so it works out ok. - */ - make_subset_tag(fo->fd); + /* + this is a bit sneaky. |make_subset_tag()| actually expects the glyph tree + to contain strings instead of |glw_entry| items. However, all calculations + are done using explicit typecasts, so it works out ok. + */ + make_subset_tag(fo->fd); } write_cid_charwidth_array(fo); write_fontdescriptor(fo->fd); - - write_cid_fontdictionary(fo,f); + + write_cid_fontdictionary(fo, f); + xfree(fo); } void write_cid_fontdictionary(fo_entry * fo, internalfontnumber f) { int i; - fo->tounicode_objnum = write_cid_tounicode(fo,f); + fo->tounicode_objnum = write_cid_tounicode(fo, f); pdf_begin_dict(fo->fo_objnum, 1); pdf_puts("/Type /Font\n"); pdf_puts("/Subtype /Type0\n"); pdf_puts("/Encoding /Identity-H\n"); write_fontname(fo->fd, "BaseFont"); - i = pdf_new_objnum(); + i = pdf_new_objnum(); pdf_printf("/DescendantFonts [%i 0 R]\n", i); /* todo: the ToUnicode CMap */ - if (fo->tounicode_objnum != 0) - pdf_printf("/ToUnicode %i 0 R\n", (int) fo->tounicode_objnum); - + if (fo->tounicode_objnum != 0) + pdf_printf("/ToUnicode %i 0 R\n", (int) fo->tounicode_objnum); + pdf_end_dict(); pdf_begin_dict(i, 1); pdf_puts("/Type /Font\n"); if (is_opentype(fo->fm) || is_type1(fo->fm)) { - pdf_puts("/Subtype /CIDFontType0\n"); + pdf_puts("/Subtype /CIDFontType0\n"); } else { - pdf_puts("/Subtype /CIDFontType2\n"); - pdf_printf("/CIDToGIDMap /Identity\n"); + pdf_puts("/Subtype /CIDFontType2\n"); + pdf_printf("/CIDToGIDMap /Identity\n"); } write_fontname(fo->fd, "BaseFont"); pdf_printf("/FontDescriptor %i 0 R\n", (int) fo->fd->fd_objnum); - pdf_printf("/W %i 0 R\n",(int) fo->cw_objnum); + pdf_printf("/W %i 0 R\n", (int) fo->cw_objnum); pdf_printf("/CIDSystemInfo <<\n"); - pdf_printf("/Registry (%s)\n", (font_cidregistry(f)? font_cidregistry(f): "Adobe")); - pdf_printf("/Ordering (%s)\n",(font_cidordering(f)? font_cidordering(f) : "Identity")) ; - pdf_printf("/Supplement %u\n",(unsigned int)font_cidsupplement(f)); + pdf_printf("/Registry (%s)\n", + (font_cidregistry(f) ? font_cidregistry(f) : "Adobe")); + pdf_printf("/Ordering (%s)\n", + (font_cidordering(f) ? font_cidordering(f) : "Identity")); + pdf_printf("/Supplement %u\n", (unsigned int) font_cidsupplement(f)); pdf_printf(">>\n"); /* I doubt there is anything useful that could be written here */ /* - if (pdf_font_attr(fo->tex_font) != get_nullstr()) { - pdf_print(pdf_font_attr(fo->tex_font)); - pdf_puts("\n"); - } - */ + if (pdf_font_attr(fo->tex_font) != get_nullstr()) { + pdf_print(pdf_font_attr(fo->tex_font)); + pdf_puts("\n"); + } + */ pdf_end_dict(); } - diff --git a/Build/source/texk/web2c/luatexdir/font/writet3.c b/Build/source/texk/web2c/luatexdir/font/writet3.c index 42827d1b124..4e349860d22 100644 --- a/Build/source/texk/web2c/luatexdir/font/writet3.c +++ b/Build/source/texk/web2c/luatexdir/font/writet3.c @@ -1,34 +1,36 @@ -/* -Copyright (c) 1996-2006 Han The Thanh, <thanh@pdftex.org> +/* writet3.c + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -This file is part of pdfTeX. + This file is part of LuaTeX. -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -$Id: writet3.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" #include <kpathsea/tex-glyph.h> #include <kpathsea/magstep.h> #include <string.h> +#include "luatexfont.h" + +static const char _svn_version[] = + "$Id: writet3.c 1712 2009-01-02 10:54:55Z taco $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/writet3.c $"; #define T3_BUF_SIZE 1024 typedef char t3_line_entry; -define_array (t3_line); +define_array(t3_line); FILE *t3_file; static boolean t3_image_used; @@ -40,30 +42,18 @@ static float t3_font_scale; static integer t3_b0, t3_b1, t3_b2, t3_b3; static boolean is_pk_font; -static unsigned char *t3_buffer = NULL; -static integer t3_size = 0; -static integer t3_curbyte = 0; - - -#define t3_open() \ - open_input(&t3_file, kpse_miscfonts_format, FOPEN_RBIN_MODE) -#define t3_read_file() readbinfile(t3_file,&t3_buffer,&t3_size) -#define t3_close() xfclose(t3_file, cur_file_name) -#define t3_getchar() t3_buffer[t3_curbyte++] -#define t3_eof() (t3_curbyte>t3_size) - -#define t3_prefix(s) (!strncmp(t3_line_array, s, strlen(s))) -#define t3_putchar(c) pdfout(c) - - +/* not static because used by pkin.c */ +unsigned char *t3_buffer = NULL; +integer t3_size = 0; +integer t3_curbyte = 0; #define t3_check_eof() \ if (t3_eof()) \ pdftex_fail("unexpected end of file"); -static void update_bbox (integer llx, integer lly, integer urx, integer ury, - boolean is_first_glyph) +static void update_bbox(integer llx, integer lly, integer urx, integer ury, + boolean is_first_glyph) { if (is_first_glyph) { t3_b0 = llx; @@ -82,111 +72,111 @@ static void update_bbox (integer llx, integer lly, integer urx, integer ury, } } -static integer get_pk_font_scale (internalfontnumber f) +static integer get_pk_font_scale(internalfontnumber f) { return - divide_scaled (pk_scale_factor, - divide_scaled (pdf_font_size(f), one_hundred_bp, + divide_scaled(pk_scale_factor, + divide_scaled(pdf_font_size(f), one_hundred_bp, fixed_decimal_digits + 2), 0); } -static integer pk_char_width (internalfontnumber f, scaled w) +static integer pk_char_width(internalfontnumber f, scaled w) { return - divide_scaled (divide_scaled (w, pdf_font_size(f), 7), - get_pk_font_scale (f), 0); + divide_scaled(divide_scaled(w, pdf_font_size(f), 7), + get_pk_font_scale(f), 0); } -scaled get_pk_char_width (internalfontnumber f, scaled w) +scaled get_pk_char_width(internalfontnumber f, scaled w) { - return (get_pk_font_scale (f) / 100000.0) * - (pk_char_width (f, w) / 100.0) * pdf_font_size(f); + return (get_pk_font_scale(f) / 100000.0) * + (pk_char_width(f, w) / 100.0) * pdf_font_size(f); } -static boolean writepk (internalfontnumber f) +static boolean writepk(internalfontnumber f) { kpse_glyph_file_type font_ret; integer llx, lly, urx, ury; integer cw, rw, i, j; halfword *row; char *name; - char *ftemp = NULL; + char *ftemp = NULL; chardesc cd; boolean is_null_glyph, check_preamble; integer dpi; - int callback_id=0; - int file_opened=0; - int mallocsize=0; - if (t3_buffer!=NULL) { - xfree(t3_buffer); - t3_buffer=NULL; + int callback_id = 0; + int file_opened = 0; + int mallocsize = 0; + if (t3_buffer != NULL) { + xfree(t3_buffer); + t3_buffer = NULL; } - t3_curbyte=0; - t3_size=0; + t3_curbyte = 0; + t3_size = 0; - callback_id=callback_defined(find_pk_file_callback); + callback_id = callback_defined(find_pk_file_callback); - if (callback_id>0) { - dpi = round (fixed_pk_resolution * - (((float) pdf_font_size(f)) / font_dsize(f))); - /* <base>.dpi/<fontname>.<tdpi>pk */ - cur_file_name = font_name(f); - mallocsize = strlen(cur_file_name)+24+9; - name = xmalloc(mallocsize); - snprintf(name,mallocsize,"%ddpi/%s.%dpk",(int)fixed_pk_resolution,cur_file_name,(int)dpi); - if(run_callback(callback_id,"S->S",name,&ftemp)) { - if(ftemp!=NULL&&strlen(ftemp)) { - free(name); - name = xstrdup(ftemp); - free(ftemp); - } - } - } else { - dpi = - kpse_magstep_fix (round - (fixed_pk_resolution * - (((float) pdf_font_size(f)) / font_dsize(f))), - fixed_pk_resolution, NULL); - cur_file_name = font_name(f); - name = kpse_find_pk (cur_file_name, (unsigned) dpi, &font_ret); - if (name == NULL || - !FILESTRCASEEQ (cur_file_name, font_ret.name) || - !kpse_bitmap_tolerance ((float) font_ret.dpi, (float) dpi)) { - pdftex_warn ("Font %s at %i not found", cur_file_name, (int) dpi); - cur_file_name = NULL; - return false; - } - } - callback_id=callback_defined(read_pk_file_callback); - if (callback_id>0) { - if(! ( run_callback(callback_id,"S->bSd",name, &file_opened, &t3_buffer,&t3_size) && - file_opened && - t3_size>0 ) ) { - pdftex_warn ("Font %s at %i not found", cur_file_name, (int)dpi); - cur_file_name = NULL; - return false; - } + if (callback_id > 0) { + dpi = round(fixed_pk_resolution * + (((float) pdf_font_size(f)) / font_dsize(f))); + /* <base>.dpi/<fontname>.<tdpi>pk */ + cur_file_name = font_name(f); + mallocsize = strlen(cur_file_name) + 24 + 9; + name = xmalloc(mallocsize); + snprintf(name, mallocsize, "%ddpi/%s.%dpk", (int) fixed_pk_resolution, + cur_file_name, (int) dpi); + if (run_callback(callback_id, "S->S", name, &ftemp)) { + if (ftemp != NULL && strlen(ftemp)) { + free(name); + name = xstrdup(ftemp); + free(ftemp); + } + } + } else { + dpi = + kpse_magstep_fix(round + (fixed_pk_resolution * + (((float) pdf_font_size(f)) / font_dsize(f))), + fixed_pk_resolution, NULL); + cur_file_name = font_name(f); + name = kpse_find_pk(cur_file_name, (unsigned) dpi, &font_ret); + if (name == NULL || + !FILESTRCASEEQ(cur_file_name, font_ret.name) || + !kpse_bitmap_tolerance((float) font_ret.dpi, (float) dpi)) { + pdftex_fail("Font %s at %i not found", cur_file_name, (int) dpi); + } + } + callback_id = callback_defined(read_pk_file_callback); + if (callback_id > 0) { + if (! + (run_callback + (callback_id, "S->bSd", name, &file_opened, &t3_buffer, &t3_size) + && file_opened && t3_size > 0)) { + pdftex_warn("Font %s at %i not found", cur_file_name, (int) dpi); + cur_file_name = NULL; + return false; + } } else { - t3_file = xfopen (name, FOPEN_RBIN_MODE); - t3_read_file(); - t3_close(); + t3_file = xfopen(name, FOPEN_RBIN_MODE); + recorder_record_input(name); + t3_read_file(); + t3_close(); } t3_image_used = true; is_pk_font = true; - if (tracefilenames) - tex_printf (" <%s", (char *) name); + if (tracefilenames) + tex_printf(" <%s", (char *) name); cd.rastersize = 256; - cd.raster = xtalloc (cd.rastersize, halfword); + cd.raster = xtalloc(cd.rastersize, halfword); check_preamble = true; - while (readchar (check_preamble, &cd) != 0) { + while (readchar(check_preamble, &cd) != 0) { check_preamble = false; - if (!pdf_char_marked (f, cd.charcode)) + if (!pdf_char_marked(f, cd.charcode)) continue; t3_char_widths[cd.charcode] = - pk_char_width (f, get_charwidth (f, cd.charcode)); + pk_char_width(f, get_charwidth(f, cd.charcode)); if (cd.cwidth < 1 || cd.cheight < 1) { - cd.xescape = cd.cwidth = - round (t3_char_widths[cd.charcode] / 100.0); + cd.xescape = cd.cwidth = round(t3_char_widths[cd.charcode] / 100.0); cd.cheight = 1; cd.xoff = 0; cd.yoff = 0; @@ -197,44 +187,44 @@ static boolean writepk (internalfontnumber f) lly = cd.yoff - cd.cheight + 1; urx = cd.cwidth + llx + 1; ury = cd.cheight + lly; - update_bbox (llx, lly, urx, ury, t3_glyph_num == 0); + update_bbox(llx, lly, urx, ury, t3_glyph_num == 0); t3_glyph_num++; - pdf_new_dict (0, 0, 0); + pdf_new_dict(0, 0, 0); t3_char_procs[cd.charcode] = obj_ptr; - pdf_begin_stream (); - pdf_print_real (t3_char_widths[cd.charcode], 2); - pdf_printf (" 0 %i %i %i %i d1\n", - (int) llx, (int) lly, (int) urx, (int) ury); + pdf_begin_stream(); + pdf_print_real(t3_char_widths[cd.charcode], 2); + pdf_printf(" 0 %i %i %i %i d1\n", + (int) llx, (int) lly, (int) urx, (int) ury); if (is_null_glyph) goto end_stream; - pdf_printf ("q\n%i 0 0 %i %i %i cm\nBI\n", (int) cd.cwidth, - (int) cd.cheight, (int) llx, (int) lly); - pdf_printf ("/W %i\n/H %i\n", (int) cd.cwidth, (int) cd.cheight); - pdf_puts ("/IM true\n/BPC 1\n/D [1 0]\nID "); + pdf_printf("q\n%i 0 0 %i %i %i cm\nBI\n", (int) cd.cwidth, + (int) cd.cheight, (int) llx, (int) lly); + pdf_printf("/W %i\n/H %i\n", (int) cd.cwidth, (int) cd.cheight); + pdf_puts("/IM true\n/BPC 1\n/D [1 0]\nID "); cw = (cd.cwidth + 7) / 8; rw = (cd.cwidth + 15) / 16; row = cd.raster; for (i = 0; i < cd.cheight; i++) { for (j = 0; j < rw - 1; j++) { - pdfout (*row / 256); - pdfout (*row % 256); + pdfout(*row / 256); + pdfout(*row % 256); row++; } - pdfout (*row / 256); + pdfout(*row / 256); if (2 * rw == cw) - pdfout (*row % 256); + pdfout(*row % 256); row++; } - pdf_puts ("\nEI\nQ\n"); + pdf_puts("\nEI\nQ\n"); end_stream: - pdf_end_stream (); + pdf_end_stream(); } - xfree (cd.raster); + xfree(cd.raster); cur_file_name = NULL; return true; } -void writet3 (int objnum, internalfontnumber f) +void writet3(int objnum, internalfontnumber f) { int i; @@ -250,99 +240,99 @@ void writet3 (int objnum, internalfontnumber f) t3_char_procs[i] = 0; t3_char_widths[i] = 0; } - pack_file_name (tex_font_name(f), get_nullstr (), maketexlstring (".pgc",4)); - cur_file_name = makecstring (make_name_string ()); + pack_file_name(tex_font_name(f), get_nullstr(), maketexlstring(".pgc", 4)); + cur_file_name = makecstring(make_name_string()); is_pk_font = false; - if (t3_buffer!=NULL) { - xfree(t3_buffer); - t3_buffer=NULL; + if (t3_buffer != NULL) { + xfree(t3_buffer); + t3_buffer = NULL; + } + t3_curbyte = 0; + t3_size = 0; + if (!writepk(f)) { + cur_file_name = NULL; + return; } - t3_curbyte=0; - t3_size=0; - if (!writepk (f)) { - cur_file_name = NULL; - return; - } for (i = font_bc(f); i <= font_ec(f); i++) - if (pdf_char_marked (f, i)) + if (pdf_char_marked(f, i)) break; first_char = i; for (i = font_ec(f); i > first_char; i--) - if (pdf_char_marked (f, i)) + if (pdf_char_marked(f, i)) break; last_char = i; - pdf_begin_dict (objnum, 1); /* Type 3 font dictionary */ - pdf_puts ("/Type /Font\n/Subtype /Type3\n"); - pdf_printf ("/Name /F%i\n", (int) f); - if (pdf_font_attr(f) != get_nullstr ()) { - pdf_print (pdf_font_attr(f)); - pdf_puts ("\n"); + pdf_begin_dict(objnum, 1); /* Type 3 font dictionary */ + pdf_puts("/Type /Font\n/Subtype /Type3\n"); + pdf_printf("/Name /F%i\n", (int) f); + if (pdf_font_attr(f) != get_nullstr()) { + pdf_print(pdf_font_attr(f)); + pdf_puts("\n"); } if (is_pk_font) { - pk_font_scale = get_pk_font_scale (f); - pdf_puts ("/FontMatrix ["); - pdf_print_real (pk_font_scale, 5); - pdf_puts (" 0 0 "); - pdf_print_real (pk_font_scale, 5); - pdf_puts (" 0 0]\n"); + pk_font_scale = get_pk_font_scale(f); + pdf_puts("/FontMatrix ["); + pdf_print_real(pk_font_scale, 5); + pdf_puts(" 0 0 "); + pdf_print_real(pk_font_scale, 5); + pdf_puts(" 0 0]\n"); } else - pdf_printf ("/FontMatrix [%g 0 0 %g 0 0]\n", - (double) t3_font_scale, (double) t3_font_scale); - pdf_printf ("/%s [ %i %i %i %i ]\n", - font_key[FONTBBOX1_CODE].pdfname, - (int) t3_b0, (int) t3_b1, (int) t3_b2, (int) t3_b3); - pdf_printf ("/Resources << /ProcSet [ /PDF %s] >>\n", - t3_image_used ? "/ImageB " : ""); - pdf_printf ("/FirstChar %i\n/LastChar %i\n", first_char, last_char); - wptr = pdf_new_objnum (); - eptr = pdf_new_objnum (); - cptr = pdf_new_objnum (); - pdf_printf ("/Widths %i 0 R\n/Encoding %i 0 R\n/CharProcs %i 0 R\n", - (int)wptr, (int)eptr, (int)cptr); - pdf_end_dict (); - pdf_begin_obj (wptr, 1); /* chars width array */ - pdf_puts ("["); + pdf_printf("/FontMatrix [%g 0 0 %g 0 0]\n", + (double) t3_font_scale, (double) t3_font_scale); + pdf_printf("/%s [ %i %i %i %i ]\n", + font_key[FONTBBOX1_CODE].pdfname, + (int) t3_b0, (int) t3_b1, (int) t3_b2, (int) t3_b3); + pdf_printf("/Resources << /ProcSet [ /PDF %s] >>\n", + t3_image_used ? "/ImageB " : ""); + pdf_printf("/FirstChar %i\n/LastChar %i\n", first_char, last_char); + wptr = pdf_new_objnum(); + eptr = pdf_new_objnum(); + cptr = pdf_new_objnum(); + pdf_printf("/Widths %i 0 R\n/Encoding %i 0 R\n/CharProcs %i 0 R\n", + (int) wptr, (int) eptr, (int) cptr); + pdf_end_dict(); + pdf_begin_obj(wptr, 1); /* chars width array */ + pdf_puts("["); if (is_pk_font) for (i = first_char; i <= last_char; i++) { - pdf_print_real (t3_char_widths[i], 2); - pdf_puts (" "); + pdf_print_real(t3_char_widths[i], 2); + pdf_puts(" "); } else for (i = first_char; i <= last_char; i++) - pdf_printf ("%i ", (int) t3_char_widths[i]); - pdf_puts ("]\n"); - pdf_end_obj (); - pdf_begin_dict (eptr, 1); /* encoding dictionary */ - pdf_printf ("/Type /Encoding\n/Differences [%i", first_char); + pdf_printf("%i ", (int) t3_char_widths[i]); + pdf_puts("]\n"); + pdf_end_obj(); + pdf_begin_dict(eptr, 1); /* encoding dictionary */ + pdf_printf("/Type /Encoding\n/Differences [%i", first_char); if (t3_char_procs[first_char] == 0) { - pdf_printf ("/%s", notdef); + pdf_printf("/%s", notdef); is_notdef = true; } else { - pdf_printf ("/a%i", first_char); + pdf_printf("/a%i", first_char); is_notdef = false; } for (i = first_char + 1; i <= last_char; i++) { if (t3_char_procs[i] == 0) { if (!is_notdef) { - pdf_printf (" %i/%s", i, notdef); + pdf_printf(" %i/%s", i, notdef); is_notdef = true; } } else { if (is_notdef) { - pdf_printf (" %i", i); + pdf_printf(" %i", i); is_notdef = false; } - pdf_printf ("/a%i", i); + pdf_printf("/a%i", i); } } - pdf_puts ("]\n"); - pdf_end_dict (); - pdf_begin_dict (cptr, 1); /* CharProcs dictionary */ + pdf_puts("]\n"); + pdf_end_dict(); + pdf_begin_dict(cptr, 1); /* CharProcs dictionary */ for (i = first_char; i <= last_char; i++) if (t3_char_procs[i] != 0) - pdf_printf ("/a%i %i 0 R\n", (int) i, (int) t3_char_procs[i]); - pdf_end_dict (); - if (tracefilenames) - tex_printf (">"); + pdf_printf("/a%i %i 0 R\n", (int) i, (int) t3_char_procs[i]); + pdf_end_dict(); + if (tracefilenames) + tex_printf(">"); cur_file_name = NULL; } diff --git a/Build/source/texk/web2c/luatexdir/font/writettf.c b/Build/source/texk/web2c/luatexdir/font/writettf.c index 2a92706a0de..fafd7c6eab4 100644 --- a/Build/source/texk/web2c/luatexdir/font/writettf.c +++ b/Build/source/texk/web2c/luatexdir/font/writettf.c @@ -1,29 +1,30 @@ -/* -Copyright (c) 1996-2006 Han The Thanh, <thanh@pdftex.org> - -This file is part of pdfTeX. +/* writettf.c + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + This file is part of LuaTeX. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -$Id: writettf.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" #include "writettf.h" #include <string.h> +static const char _svn_version[] = + "$Id: writettf.c 1592 2008-11-28 13:23:51Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/writettf.c $"; + #define DEFAULT_NTABS 14 #define NEW_CMAP_SIZE 2 @@ -31,7 +32,7 @@ $Id: writettf.c 1013 2008-02-14 00:09:02Z oneiros $ #define ttf_offset fb_offset #define ttf_seek_outbuf fb_seek - /* #define INFILE ttf_file*/ + /* #define INFILE ttf_file */ unsigned char *ttf_buffer = NULL; integer ttf_size = 0; @@ -40,7 +41,7 @@ integer ttf_curbyte = 0; typedef struct { char *name; /* name of glyph */ long code; /* charcode in case of subfonts */ - short newindex; /* new index of glyph in output file */ + long newindex; /* new index of glyph in output file */ } ttfenc_entry; @@ -59,7 +60,7 @@ typedef struct { char *ttf_name; TTF_USHORT pid; TTF_USHORT eid; - short *table; + long *table; } ttf_cmap_entry; static TTF_USHORT ntabs; @@ -89,7 +90,7 @@ static TTF_ULONG checkSumAdjustment_offset; FILE *ttf_file; static ttfenc_entry ttfenc_tab[256]; -fd_entry *fd_cur; /* pointer to the current font descriptor */ +fd_entry *fd_cur; /* pointer to the current font descriptor */ static struct avl_table *ttf_cmap_tree = NULL; @@ -97,8 +98,8 @@ integer ttf_length; #include "macnames.c" -extern char *fb_array; -extern char charsetstr[]; +extern char *fb_array; /* from luatexdir/utils.c */ +extern char charsetstr[]; /* from mpdir/psout.w */ static const char *newtabnames[] = { "OS/2", @@ -117,44 +118,44 @@ static const char *newtabnames[] = { "prep" }; -ttf_cmap_entry *new_ttf_cmap_entry (void) +ttf_cmap_entry *new_ttf_cmap_entry(void) { ttf_cmap_entry *e; - e = xtalloc (1, ttf_cmap_entry); + e = xtalloc(1, ttf_cmap_entry); e->ttf_name = NULL; e->table = NULL; return e; } -static void destroy_ttf_cmap_entry (void *pa, void *pb) +static void destroy_ttf_cmap_entry(void *pa, void *pb) { ttf_cmap_entry *p; p = (ttf_cmap_entry *) pa; - xfree (p->ttf_name); - xfree (p->table); - xfree (p); + xfree(p->ttf_name); + xfree(p->table); + xfree(p); } -void ttf_free (void) +void ttf_free(void) { if (ttf_cmap_tree != NULL) - avl_destroy (ttf_cmap_tree, destroy_ttf_cmap_entry); + avl_destroy(ttf_cmap_tree, destroy_ttf_cmap_entry); } -static int comp_ttf_cmap_entry (const void *pa, const void *pb, void *p) +static int comp_ttf_cmap_entry(const void *pa, const void *pb, void *p) { const ttf_cmap_entry *p1 = (const ttf_cmap_entry *) pa, *p2 = (const ttf_cmap_entry *) pb; int i; - assert (p1->ttf_name != NULL && p2->ttf_name != NULL); - if ((i = strcmp (p1->ttf_name, p2->ttf_name)) != 0) + assert(p1->ttf_name != NULL && p2->ttf_name != NULL); + if ((i = strcmp(p1->ttf_name, p2->ttf_name)) != 0) return i; - cmp_return (p1->pid, p2->pid); - cmp_return (p1->eid, p2->eid); + cmp_return(p1->pid, p2->pid); + cmp_return(p1->eid, p2->eid); return 0; } -static unsigned char ttf_addchksm (unsigned char b) +static unsigned char ttf_addchksm(unsigned char b) { tmp_ulong = (tmp_ulong << 8) + b; tab_length++; @@ -165,14 +166,14 @@ static unsigned char ttf_addchksm (unsigned char b) return b; } -static TTF_ULONG ttf_getchksm (void) +static TTF_ULONG ttf_getchksm(void) { while (tab_length % 4 != 0) - ttf_putchar (ttf_addchksm (0)); /* ttf_addchksm updates tab_length */ + ttf_putchar(ttf_addchksm(0)); /* ttf_addchksm updates tab_length */ return checksum; } -long ttf_putnum (int s, long n) +long ttf_putnum(int s, long n) { long i = n; char buf[TTF_LONG_SIZE + 1], *p = buf; @@ -182,25 +183,25 @@ long ttf_putnum (int s, long n) } p--; while (p >= buf) - ttf_putchar (ttf_addchksm (*p--)); + ttf_putchar(ttf_addchksm(*p--)); return n; } -long ttf_getnum (int s) +long ttf_getnum(int s) { long i = 0; int c; while (s > 0) { - if (ttf_eof()) - pdftex_fail ("unexpected EOF"); - c = ttf_getchar (); - i = (i << 8) + c; - s--; + if (ttf_eof()) + pdftex_fail("unexpected EOF"); + c = ttf_getchar(); + i = (i << 8) + c; + s--; } return i; } -static long ttf_funit (long n) +static long ttf_funit(long n) { if (n < 0) return -((-n / upem) * 1000 + ((-n % upem) * 1000) / upem); @@ -208,38 +209,38 @@ static long ttf_funit (long n) return (n / upem) * 1000 + ((n % upem) * 1000) / upem; } -static void ttf_ncopy (int n) +static void ttf_ncopy(int n) { while (n-- > 0) - copy_byte (); + copy_byte(); } -dirtab_entry *ttf_name_lookup (const char *s, boolean required) +dirtab_entry *ttf_name_lookup(const char *s, boolean required) { dirtab_entry *tab; for (tab = dir_tab; tab - dir_tab < ntabs; tab++) - if (strncmp (tab->tag, s, 4) == 0) + if (strncmp(tab->tag, s, 4) == 0) break; if (tab - dir_tab == ntabs) { if (required) - pdftex_fail ("can't find table `%s'", s); + pdftex_fail("can't find table `%s'", s); else tab = NULL; } return tab; } -dirtab_entry *ttf_seek_tab (const char *name, TTF_LONG offset) +dirtab_entry *ttf_seek_tab(const char *name, TTF_LONG offset) { - dirtab_entry *tab = ttf_name_lookup (name, true); - /*xfseek (INFILE, tab->offset + offset, SEEK_SET, cur_file_name);*/ - ttf_curbyte = tab->offset + offset; + dirtab_entry *tab = ttf_name_lookup(name, true); + /*xfseek (INFILE, tab->offset + offset, SEEK_SET, cur_file_name); */ + ttf_curbyte = tab->offset + offset; return tab; } -static void ttf_seek_off (TTF_LONG offset) +static void ttf_seek_off(TTF_LONG offset) { - ttf_curbyte = offset; + ttf_curbyte = offset; //xfseek (INFILE, offset, SEEK_SET, cur_file_name); } @@ -294,7 +295,9 @@ static void ttf_copy_encoding(void) e = ttfenc_tab + *q; e->code = charcodes[*q]; if (e->code == -1) - pdftex_warn("character %i is not mapped to any charcode", *q); + pdftex_warn + ("character %i in subfont %s is not mapped to any charcode", + *q, fd_cur->fm->tfm_name); else { assert(e->code < 0x10000); sprintf(buf, "/c%4.4X", (int) e->code); @@ -333,27 +336,27 @@ static char *strip_spaces_and_delims(char *s, int l) return buf; } -static void ttf_read_name (void) +static void ttf_read_name(void) { int i, j; - dirtab_entry *tab = ttf_seek_tab ("name", TTF_USHORT_SIZE); - char *p; - name_record_num = get_ushort (); - name_tab = xtalloc (name_record_num, name_record); + dirtab_entry *tab = ttf_seek_tab("name", TTF_USHORT_SIZE); + char *p, buf[SMALL_BUF_SIZE]; + name_record_num = get_ushort(); + name_tab = xtalloc(name_record_num, name_record); name_buf_size = tab->length - (3 * TTF_USHORT_SIZE + name_record_num * 6 * TTF_USHORT_SIZE); - name_buf = xtalloc (name_buf_size, char); - ttf_skip (TTF_USHORT_SIZE); + name_buf = xtalloc(name_buf_size, char); + ttf_skip(TTF_USHORT_SIZE); for (i = 0; i < name_record_num; i++) { - name_tab[i].platform_id = get_ushort (); - name_tab[i].encoding_id = get_ushort (); - name_tab[i].language_id = get_ushort (); - name_tab[i].name_id = get_ushort (); - name_tab[i].length = get_ushort (); - name_tab[i].offset = get_ushort (); + name_tab[i].platform_id = get_ushort(); + name_tab[i].encoding_id = get_ushort(); + name_tab[i].language_id = get_ushort(); + name_tab[i].name_id = get_ushort(); + name_tab[i].length = get_ushort(); + name_tab[i].offset = get_ushort(); } for (p = name_buf; p - name_buf < name_buf_size; p++) - *p = get_char (); + *p = get_char(); /* look for PS font name */ for (i = 0; i < name_record_num; i++) { if (name_tab[i].platform_id == 1 && @@ -369,12 +372,15 @@ static void ttf_read_name (void) if (!fd_cur->font_dim[FONTNAME_CODE].set) { for (i = 0; i < name_record_num; i++) { if (name_tab[i].platform_id == 3 && - (name_tab[i].encoding_id == 0 || - name_tab[i].encoding_id == 1) && name_tab[i].name_id == 6) { - for (j = 0, p = fd_cur->fontname; j < name_tab[i].length; - j += 2) + (name_tab[i].encoding_id == 0 || name_tab[i].encoding_id == 1) + && name_tab[i].name_id == 6) { + xfree(fd_cur->fontname); + assert(name_tab[i].length < sizeof(buf)); + for (j = 0, p = buf; j < name_tab[i].length; j += 2) *p++ = name_buf[name_tab[i].offset + j + 1]; *p = 0; + fd_cur->fontname = + xstrdup(strip_spaces_and_delims(buf, strlen(buf))); fd_cur->font_dim[FONTNAME_CODE].set = true; break; } @@ -382,28 +388,28 @@ static void ttf_read_name (void) } } -static void ttf_read_mapx (void) +static void ttf_read_mapx(void) { glyph_entry *glyph; - ttf_seek_tab ("maxp", TTF_FIXED_SIZE); - glyph_tab = xtalloc (1 + (glyphs_count = get_ushort ()), glyph_entry); + ttf_seek_tab("maxp", TTF_FIXED_SIZE); + glyph_tab = xtalloc(1 + (glyphs_count = get_ushort()), glyph_entry); for (glyph = glyph_tab; glyph - glyph_tab < glyphs_count; glyph++) { glyph->newindex = -1; glyph->newoffset = 0; glyph->name_index = 0; glyph->name = (char *) notdef; } - glyph_index = xtalloc (glyphs_count, long); + glyph_index = xtalloc(glyphs_count, long); glyph_index[0] = 0; /* index of ".notdef" glyph */ glyph_index[1] = 1; /* index of ".null" glyph */ } -void ttf_read_head (void) +void ttf_read_head(void) { - ttf_seek_tab ("head", - 2 * TTF_FIXED_SIZE + 2 * TTF_ULONG_SIZE + TTF_USHORT_SIZE); - upem = get_ushort (); - ttf_skip (16); + ttf_seek_tab("head", + 2 * TTF_FIXED_SIZE + 2 * TTF_ULONG_SIZE + TTF_USHORT_SIZE); + upem = get_ushort(); + ttf_skip(16); fd_cur->font_dim[FONTBBOX1_CODE].val = ttf_funit(get_fword()); fd_cur->font_dim[FONTBBOX2_CODE].val = ttf_funit(get_fword()); fd_cur->font_dim[FONTBBOX3_CODE].val = ttf_funit(get_fword()); @@ -412,27 +418,27 @@ void ttf_read_head (void) fd_cur->font_dim[FONTBBOX2_CODE].set = true; fd_cur->font_dim[FONTBBOX3_CODE].set = true; fd_cur->font_dim[FONTBBOX4_CODE].set = true; - ttf_skip (2 * TTF_USHORT_SIZE + TTF_SHORT_SIZE); - loca_format = get_short (); + ttf_skip(2 * TTF_USHORT_SIZE + TTF_SHORT_SIZE); + loca_format = get_short(); } -void ttf_read_hhea (void) +void ttf_read_hhea(void) { - ttf_seek_tab ("hhea", TTF_FIXED_SIZE); + ttf_seek_tab("hhea", TTF_FIXED_SIZE); fd_cur->font_dim[ASCENT_CODE].val = ttf_funit(get_fword()); fd_cur->font_dim[DESCENT_CODE].val = ttf_funit(get_fword()); fd_cur->font_dim[ASCENT_CODE].set = true; fd_cur->font_dim[DESCENT_CODE].set = true; - ttf_skip (TTF_FWORD_SIZE + TTF_UFWORD_SIZE + 3 * TTF_FWORD_SIZE + - 8 * TTF_SHORT_SIZE); - nhmtxs = get_ushort (); + ttf_skip(TTF_FWORD_SIZE + TTF_UFWORD_SIZE + 3 * TTF_FWORD_SIZE + + 8 * TTF_SHORT_SIZE); + nhmtxs = get_ushort(); } -void ttf_read_pclt (void) +void ttf_read_pclt(void) { - if (ttf_name_lookup ("PCLT", false) == NULL) + if (ttf_name_lookup("PCLT", false) == NULL) return; - ttf_seek_tab ("PCLT", TTF_FIXED_SIZE + TTF_ULONG_SIZE + TTF_USHORT_SIZE); + ttf_seek_tab("PCLT", TTF_FIXED_SIZE + TTF_ULONG_SIZE + TTF_USHORT_SIZE); fd_cur->font_dim[XHEIGHT_CODE].val = ttf_funit(get_ushort()); ttf_skip(2 * TTF_USHORT_SIZE); fd_cur->font_dim[CAPHEIGHT_CODE].val = ttf_funit(get_ushort()); @@ -440,25 +446,25 @@ void ttf_read_pclt (void) fd_cur->font_dim[CAPHEIGHT_CODE].set = true; } -static void ttf_read_hmtx (void) +static void ttf_read_hmtx(void) { glyph_entry *glyph; TTF_UFWORD last_advWidth; - ttf_seek_tab ("hmtx", 0); + ttf_seek_tab("hmtx", 0); for (glyph = glyph_tab; glyph - glyph_tab < nhmtxs; glyph++) { - glyph->advWidth = get_ufword (); - glyph->lsb = get_ufword (); + glyph->advWidth = get_ufword(); + glyph->lsb = get_ufword(); } if (nhmtxs < glyphs_count) { last_advWidth = glyph[-1].advWidth; for (; glyph - glyph_tab < glyphs_count; glyph++) { glyph->advWidth = last_advWidth; - glyph->lsb = get_ufword (); + glyph->lsb = get_ufword(); } } } -void ttf_read_post (void) +void ttf_read_post(void) { int k, nnames; long length; @@ -467,9 +473,9 @@ void ttf_read_post (void) TTF_FIXED italic_angle; char *p; glyph_entry *glyph; - const dirtab_entry *tab = ttf_seek_tab ("post", 0); - post_format = get_fixed (); - italic_angle = get_fixed (); + const dirtab_entry *tab = ttf_seek_tab("post", 0); + post_format = get_fixed(); + italic_angle = get_fixed(); int_part = italic_angle >> 16; if (int_part > 0x7FFF) { /* a negative number */ int_part = 0x10000 - int_part; @@ -481,7 +487,7 @@ void ttf_read_post (void) fd_cur->font_dim[ITALIC_ANGLE_CODE].set = true; if (glyph_tab == NULL) return; /* being called from writeotf() */ - ttf_skip (2 * TTF_FWORD_SIZE + 5 * TTF_ULONG_SIZE); + ttf_skip(2 * TTF_FWORD_SIZE + 5 * TTF_ULONG_SIZE); switch (post_format) { case 0x10000: for (glyph = glyph_tab; glyph - glyph_tab < NMACGLYPHS; glyph++) { @@ -490,15 +496,15 @@ void ttf_read_post (void) } break; case 0x20000: - nnames = get_ushort (); /* some fonts have this value different from nglyphs */ + nnames = get_ushort(); /* some fonts have this value different from nglyphs */ for (glyph = glyph_tab; glyph - glyph_tab < nnames; glyph++) - glyph->name_index = get_ushort (); - /*length = tab->length - (xftell (INFILE, cur_file_name) - tab->offset);*/ + glyph->name_index = get_ushort(); + /*length = tab->length - (xftell (INFILE, cur_file_name) - tab->offset); */ length = tab->length - (ttf_curbyte - tab->offset); - glyph_name_buf = xtalloc (length, char); + glyph_name_buf = xtalloc(length, char); for (p = glyph_name_buf; p - glyph_name_buf < length;) { - for (k = get_byte (); k > 0; k--) - *p++ = get_char (); + for (k = get_byte(); k > 0; k--) + *p++ = get_char(); *p++ = 0; } for (glyph = glyph_tab; glyph - glyph_tab < nnames; glyph++) { @@ -508,7 +514,7 @@ void ttf_read_post (void) p = glyph_name_buf; k = glyph->name_index - NMACGLYPHS; for (; k > 0; k--) - p = strend (p) + 1; + p = strend(p) + 1; glyph->name = p; } } @@ -519,41 +525,41 @@ void ttf_read_post (void) } break; default: - pdftex_fail ("unsupported format (%.8X) of `post' table", - (unsigned int) post_format); + pdftex_fail("unsupported format (%.8X) of `post' table", + (unsigned int) post_format); } } -static void ttf_read_loca (void) +static void ttf_read_loca(void) { glyph_entry *glyph; - ttf_seek_tab ("loca", 0); + ttf_seek_tab("loca", 0); if (loca_format != 0) for (glyph = glyph_tab; glyph - glyph_tab < glyphs_count + 1; glyph++) - glyph->offset = get_ulong (); + glyph->offset = get_ulong(); else for (glyph = glyph_tab; glyph - glyph_tab < glyphs_count + 1; glyph++) - glyph->offset = get_ushort () << 1; + glyph->offset = get_ushort() << 1; } -void ttf_read_tabdir (void) +void ttf_read_tabdir(void) { int i; dirtab_entry *tab; - ttf_skip (TTF_FIXED_SIZE); /* ignore the sfnt number */ - dir_tab = xtalloc (ntabs = get_ushort (), dirtab_entry); - ttf_skip (3 * TTF_USHORT_SIZE); + ttf_skip(TTF_FIXED_SIZE); /* ignore the sfnt number */ + dir_tab = xtalloc(ntabs = get_ushort(), dirtab_entry); + ttf_skip(3 * TTF_USHORT_SIZE); for (tab = dir_tab; tab - dir_tab < ntabs; tab++) { for (i = 0; i < 4; i++) - tab->tag[i] = get_char (); - tab->checksum = get_ulong (); - tab->offset = get_ulong (); - tab->length = get_ulong (); + tab->tag[i] = get_char(); + tab->checksum = get_ulong(); + tab->offset = get_ulong(); + tab->length = get_ulong(); } } -static ttf_cmap_entry *ttf_read_cmap (char *ttf_name, int pid, int eid, - boolean warn) +static ttf_cmap_entry *ttf_read_cmap(char *ttf_name, int pid, int eid, + boolean warn) { seg_entry *seg_tab, *s; TTF_USHORT *glyphId, format, segCount; @@ -568,71 +574,71 @@ static ttf_cmap_entry *ttf_read_cmap (char *ttf_name, int pid, int eid, tmp_e.pid = pid; tmp_e.eid = eid; if (ttf_cmap_tree == NULL) { - ttf_cmap_tree = avl_create (comp_ttf_cmap_entry, NULL, &avl_xallocator); - assert (ttf_cmap_tree != NULL); + ttf_cmap_tree = avl_create(comp_ttf_cmap_entry, NULL, &avl_xallocator); + assert(ttf_cmap_tree != NULL); } - p = (ttf_cmap_entry *) avl_find (ttf_cmap_tree, &tmp_e); + p = (ttf_cmap_entry *) avl_find(ttf_cmap_tree, &tmp_e); if (p != NULL) return p; /* not found, have to read it */ - ttf_seek_tab ("cmap", TTF_USHORT_SIZE); /* skip the table vesrion number (=0) */ - ncmapsubtabs = get_ushort (); - /* cmap_offset = xftell (INFILE, cur_file_name) - 2 * TTF_USHORT_SIZE;*/ - cmap_offset = ttf_curbyte - 2 * TTF_USHORT_SIZE; - cmap_tab = xtalloc (ncmapsubtabs, cmap_entry); + ttf_seek_tab("cmap", TTF_USHORT_SIZE); /* skip the table vesrion number (=0) */ + ncmapsubtabs = get_ushort(); + /* cmap_offset = xftell (INFILE, cur_file_name) - 2 * TTF_USHORT_SIZE; */ + cmap_offset = ttf_curbyte - 2 * TTF_USHORT_SIZE; + cmap_tab = xtalloc(ncmapsubtabs, cmap_entry); for (i = 0; i < ncmapsubtabs; ++i) { - tmp_pid = get_ushort (); - tmp_eid = get_ushort (); - tmp_offset = get_ulong (); + tmp_pid = get_ushort(); + tmp_eid = get_ushort(); + tmp_offset = get_ulong(); if (tmp_pid == pid && tmp_eid == eid) { - ttf_seek_off (cmap_offset + tmp_offset); - format = get_ushort (); + ttf_seek_off(cmap_offset + tmp_offset); + format = get_ushort(); if (format == 4) goto read_cmap_format_4; else { if (warn) - pdftex_warn ("cmap format %i unsupported", format); + pdftex_warn("cmap format %i unsupported", format); return NULL; } } } if (warn) - pdftex_warn ("cannot find cmap subtable for (pid,eid) = (%i, %i)", - pid, eid); + pdftex_warn("cannot find cmap subtable for (pid,eid) = (%i, %i)", + pid, eid); return NULL; read_cmap_format_4: /* initialize the new entry */ - p = new_ttf_cmap_entry (); - p->ttf_name = xstrdup (ttf_name); + p = new_ttf_cmap_entry(); + p->ttf_name = xstrdup(ttf_name); p->pid = pid; p->eid = eid; - p->table = xtalloc (0x10000, short); + p->table = xtalloc(0x10000, long); for (i = 0; i < 0x10000; ++i) p->table[i] = -1; /* unassigned yet */ /* read the subtable */ - length = get_ushort (); /* length of subtable */ - (void) get_ushort (); /* skip the version number */ - segCount = get_ushort () / 2; - (void) get_ushort (); /* skip searchRange */ - (void) get_ushort (); /* skip entrySelector */ - (void) get_ushort (); /* skip rangeShift */ - seg_tab = xtalloc (segCount, seg_entry); + length = get_ushort(); /* length of subtable */ + (void) get_ushort(); /* skip the version number */ + segCount = get_ushort() / 2; + (void) get_ushort(); /* skip searchRange */ + (void) get_ushort(); /* skip entrySelector */ + (void) get_ushort(); /* skip rangeShift */ + seg_tab = xtalloc(segCount, seg_entry); for (s = seg_tab; s - seg_tab < segCount; s++) - s->endCode = get_ushort (); - (void) get_ushort (); /* skip reversedPad */ + s->endCode = get_ushort(); + (void) get_ushort(); /* skip reversedPad */ for (s = seg_tab; s - seg_tab < segCount; s++) - s->startCode = get_ushort (); + s->startCode = get_ushort(); for (s = seg_tab; s - seg_tab < segCount; s++) - s->idDelta = get_ushort (); + s->idDelta = get_ushort(); for (s = seg_tab; s - seg_tab < segCount; s++) - s->idRangeOffset = get_ushort (); + s->idRangeOffset = get_ushort(); length -= 8 * TTF_USHORT_SIZE + 4 * segCount * TTF_USHORT_SIZE; n = length / TTF_USHORT_SIZE; /* number of glyphID's */ - glyphId = xtalloc (n, TTF_USHORT); + glyphId = xtalloc(n, TTF_USHORT); for (i = 0; i < n; i++) - glyphId[i] = get_ushort (); + glyphId[i] = get_ushort(); for (s = seg_tab; s - seg_tab < segCount; s++) { for (i = s->startCode; i <= s->endCode; i++) { if (i == 0xFFFF) @@ -643,144 +649,144 @@ static ttf_cmap_entry *ttf_read_cmap (char *ttf_name, int pid, int eid, else { k = (i - s->startCode) + s->idRangeOffset / 2 + (s - seg_tab) - segCount; - assert (k >= 0 && k < n); + assert(k >= 0 && k < n); index = glyphId[k]; if (index != 0) index = (index + s->idDelta) & 0xFFFF; } if (index >= glyphs_count) - pdftex_fail ("cmap: glyph index %li out of range [0..%i)", - index, glyphs_count); + pdftex_fail("cmap: glyph index %li out of range [0..%i)", + index, glyphs_count); if (p->table[i] != -1) pdftex_warn ("cmap: multiple glyphs are mapped to unicode %.4lX, " - "only %i will be used (glyph %li being ignored)", i, + "only %li will be used (glyph %li being ignored)", i, p->table[i], index); else p->table[i] = index; } } } - xfree (seg_tab); - xfree (glyphId); - aa = avl_probe (ttf_cmap_tree, p); - assert (aa != NULL); + xfree(seg_tab); + xfree(glyphId); + aa = avl_probe(ttf_cmap_tree, p); + assert(aa != NULL); return p; } -static void ttf_read_font (void) +static void ttf_read_font(void) { - ttf_read_tabdir (); - if (ttf_name_lookup ("PCLT", false) == NULL) + ttf_read_tabdir(); + if (ttf_name_lookup("PCLT", false) == NULL) new_ntabs--; - if (ttf_name_lookup ("fpgm", false) == NULL) + if (ttf_name_lookup("fpgm", false) == NULL) new_ntabs--; - if (ttf_name_lookup ("cvt ", false) == NULL) + if (ttf_name_lookup("cvt ", false) == NULL) new_ntabs--; - if (ttf_name_lookup ("prep", false) == NULL) + if (ttf_name_lookup("prep", false) == NULL) new_ntabs--; - ttf_read_mapx (); - ttf_read_head (); - ttf_read_hhea (); - ttf_read_pclt (); - ttf_read_hmtx (); - ttf_read_post (); - ttf_read_loca (); - ttf_read_name (); + ttf_read_mapx(); + ttf_read_head(); + ttf_read_hhea(); + ttf_read_pclt(); + ttf_read_hmtx(); + ttf_read_post(); + ttf_read_loca(); + ttf_read_name(); } -static void ttf_reset_chksm (dirtab_entry * tab) +static void ttf_reset_chksm(dirtab_entry * tab) { checksum = 0; tab_length = 0; tmp_ulong = 0; - tab->offset = ttf_offset (); + tab->offset = ttf_offset(); if (tab->offset % 4 != 0) - pdftex_warn ("offset of `%4.4s' is not a multiple of 4", tab->tag); + pdftex_warn("offset of `%4.4s' is not a multiple of 4", tab->tag); } -static void ttf_set_chksm (dirtab_entry * tab) +static void ttf_set_chksm(dirtab_entry * tab) { - tab->length = ttf_offset () - tab->offset; - tab->checksum = ttf_getchksm (); + tab->length = ttf_offset() - tab->offset; + tab->checksum = ttf_getchksm(); } -static void ttf_copytab (const char *name) +static void ttf_copytab(const char *name) { long i; - dirtab_entry *tab = ttf_seek_tab (name, 0); - ttf_reset_chksm (tab); + dirtab_entry *tab = ttf_seek_tab(name, 0); + ttf_reset_chksm(tab); for (i = tab->length; i > 0; i--) - copy_char (); - ttf_set_chksm (tab); + copy_char(); + ttf_set_chksm(tab); } #define BYTE_ENCODING_LENGTH \ ((256)*TTF_BYTE_SIZE + 3*TTF_USHORT_SIZE) -static void ttf_byte_encoding (void) +static void ttf_byte_encoding(void) { ttfenc_entry *e; - (void) put_ushort (0); /* format number (0: byte encoding table) */ - (void) put_ushort (BYTE_ENCODING_LENGTH); /* length of table */ - (void) put_ushort (0); /* version number */ + (void) put_ushort(0); /* format number (0: byte encoding table) */ + (void) put_ushort(BYTE_ENCODING_LENGTH); /* length of table */ + (void) put_ushort(0); /* version number */ for (e = ttfenc_tab; e - ttfenc_tab < 256; e++) if (e->newindex < 256) { - put_byte (e->newindex); + put_byte(e->newindex); } else { if (e->name != notdef) pdftex_warn ("glyph `%s' has been mapped to `%s' in `ttf_byte_encoding' cmap table", e->name, notdef); - put_byte (0); /* notdef */ + put_byte(0); /* notdef */ } } #define TRIMMED_TABLE_MAP_LENGTH (TTF_USHORT_SIZE*(5 + (256))) -static void ttf_trimmed_table_map (void) +static void ttf_trimmed_table_map(void) { ttfenc_entry *e; - (void) put_ushort (6); /* format number (6): trimmed table mapping */ - (void) put_ushort (TRIMMED_TABLE_MAP_LENGTH); - (void) put_ushort (0); /* version number (0) */ - (void) put_ushort (0); /* first character code */ - (void) put_ushort (256); /* number of character code in table */ + (void) put_ushort(6); /* format number (6): trimmed table mapping */ + (void) put_ushort(TRIMMED_TABLE_MAP_LENGTH); + (void) put_ushort(0); /* version number (0) */ + (void) put_ushort(0); /* first character code */ + (void) put_ushort(256); /* number of character code in table */ for (e = ttfenc_tab; e - ttfenc_tab < 256; e++) - (void) put_ushort (e->newindex); + (void) put_ushort(e->newindex); } #define SEG_MAP_DELTA_LENGTH ((16 + (256))*TTF_USHORT_SIZE) -static void ttf_seg_map_delta (void) +static void ttf_seg_map_delta(void) { ttfenc_entry *e; - (void) put_ushort (4); /* format number (4: segment mapping to delta values) */ - (void) put_ushort (SEG_MAP_DELTA_LENGTH); - (void) put_ushort (0); /* version number */ - (void) put_ushort (4); /* 2*segCount */ - (void) put_ushort (4); /* searchRange */ - (void) put_ushort (1); /* entrySelector */ - (void) put_ushort (0); /* rangeShift */ - (void) put_ushort (0xF0FF); /* endCount[0] */ - (void) put_ushort (0xFFFF); /* endCount[1] */ - (void) put_ushort (0); /* reversedPad */ - (void) put_ushort (0xF000); /* startCount[0] */ - (void) put_ushort (0xFFFF); /* startCount[1] */ - (void) put_ushort (0); /* idDelta[0] */ - (void) put_ushort (1); /* idDelta[1] */ - (void) put_ushort (2 * TTF_USHORT_SIZE); /* idRangeOffset[0] */ - (void) put_ushort (0); /* idRangeOffset[1] */ + (void) put_ushort(4); /* format number (4: segment mapping to delta values) */ + (void) put_ushort(SEG_MAP_DELTA_LENGTH); + (void) put_ushort(0); /* version number */ + (void) put_ushort(4); /* 2*segCount */ + (void) put_ushort(4); /* searchRange */ + (void) put_ushort(1); /* entrySelector */ + (void) put_ushort(0); /* rangeShift */ + (void) put_ushort(0xF0FF); /* endCount[0] */ + (void) put_ushort(0xFFFF); /* endCount[1] */ + (void) put_ushort(0); /* reversedPad */ + (void) put_ushort(0xF000); /* startCount[0] */ + (void) put_ushort(0xFFFF); /* startCount[1] */ + (void) put_ushort(0); /* idDelta[0] */ + (void) put_ushort(1); /* idDelta[1] */ + (void) put_ushort(2 * TTF_USHORT_SIZE); /* idRangeOffset[0] */ + (void) put_ushort(0); /* idRangeOffset[1] */ for (e = ttfenc_tab; e - ttfenc_tab < 256; e++) - (void) put_ushort (e->newindex); + (void) put_ushort(e->newindex); } #define CMAP_ENTRY_LENGTH (2*TTF_USHORT_SIZE + TTF_ULONG_SIZE) -static void ttf_select_cmap (void) +static void ttf_select_cmap(void) { - assert (sizeof (new_cmap_tab) <= NEW_CMAP_SIZE * sizeof (cmap_entry)); + assert(sizeof(new_cmap_tab) <= NEW_CMAP_SIZE * sizeof(cmap_entry)); new_cmap_tab[0].platform_id = 1; /* Macintosh */ new_cmap_tab[0].encoding_id = 0; /* Symbol; ignore code page */ new_cmap_tab[0].format = new_glyphs_count < 256 ? 0 /* byte encoding */ @@ -790,15 +796,15 @@ static void ttf_select_cmap (void) new_cmap_tab[1].format = 4; /* segment mapping to delta */ } -static void ttf_write_cmap (void) +static void ttf_write_cmap(void) { cmap_entry *ce; long offset; - dirtab_entry *tab = ttf_name_lookup ("cmap", true); - ttf_select_cmap (); - ttf_reset_chksm (tab); - (void) put_ushort (0); /* table version number (0) */ - (void) put_ushort (NEW_CMAP_SIZE); /* number of encoding tables */ + dirtab_entry *tab = ttf_name_lookup("cmap", true); + ttf_select_cmap(); + ttf_reset_chksm(tab); + (void) put_ushort(0); /* table version number (0) */ + (void) put_ushort(NEW_CMAP_SIZE); /* number of encoding tables */ offset = 2 * TTF_USHORT_SIZE + NEW_CMAP_SIZE * CMAP_ENTRY_LENGTH; for (ce = new_cmap_tab; ce - new_cmap_tab < NEW_CMAP_SIZE; ce++) { ce->offset = offset; @@ -813,33 +819,34 @@ static void ttf_write_cmap (void) offset += TRIMMED_TABLE_MAP_LENGTH; break; default: - pdftex_fail ("invalid format (it should not have happened)"); + pdftex_fail("invalid format (it should not have happened)"); } - (void) put_ushort (ce->platform_id); - (void) put_ushort (ce->encoding_id); - put_ulong (ce->offset); + (void) put_ushort(ce->platform_id); + (void) put_ushort(ce->encoding_id); + put_ulong(ce->offset); } for (ce = new_cmap_tab; ce - new_cmap_tab < NEW_CMAP_SIZE; ce++) { switch (ce->format) { case 0: - ttf_byte_encoding (); + ttf_byte_encoding(); break; case 4: - ttf_seg_map_delta (); + ttf_seg_map_delta(); break; case 6: - ttf_trimmed_table_map (); + ttf_trimmed_table_map(); break; } } - ttf_set_chksm (tab); + ttf_set_chksm(tab); } -static int prepend_subset_tags (int index, char *p) +static int prepend_subset_tags(int index, char *p) { - const boolean is_unicode = (name_tab[index].platform_id == 3); + boolean is_unicode; int i; - assert (index > 0 && index < name_record_num && fd_cur->subset_tag != NULL); + assert(index >= 0 && index < name_record_num && fd_cur->subset_tag != NULL); + is_unicode = (name_tab[index].platform_id == 3); if (is_unicode) { for (i = 0; i < 6; ++i) { *p++ = 0; @@ -849,7 +856,7 @@ static int prepend_subset_tags (int index, char *p) *p++ = '+'; return 14; } else { - strncpy (p, fd_cur->subset_tag, 6); + strncpy(p, fd_cur->subset_tag, 6); p += 6; *p++ = '+'; return 7; @@ -857,19 +864,19 @@ static int prepend_subset_tags (int index, char *p) } -static void ttf_write_name (void) +static void ttf_write_name(void) { int i, l; char *p; int new_name_buf_size; char *new_name_buf; name_record *n; - dirtab_entry *tab = ttf_name_lookup ("name", true); - if (is_subsetted (fd_cur->fm)) { + dirtab_entry *tab = ttf_name_lookup("name", true); + if (is_subsetted(fd_cur->fm)) { l = 0; for (i = 0; i < name_record_num; i++) l += name_tab[i].length + 14; /* maximum lengh of new stogare area */ - new_name_buf = xtalloc (l, char); + new_name_buf = xtalloc(l, char); /* additional space for subset tags */ p = new_name_buf; for (i = 0; i < name_record_num; i++) { @@ -880,11 +887,11 @@ static void ttf_write_name (void) ((n->platform_id == 1 && n->encoding_id == 0) || (n->platform_id == 3 && n->encoding_id == 0) || (n->platform_id == 3 && n->encoding_id == 1))) { - l = prepend_subset_tags (i, p); + l = prepend_subset_tags(i, p); p += l; } else l = 0; - memcpy (p, name_buf + n->offset, n->length); + memcpy(p, name_buf + n->offset, n->length); p += n->length; n->new_length = n->length + l; } @@ -893,51 +900,51 @@ static void ttf_write_name (void) new_name_buf = name_buf; new_name_buf_size = name_buf_size; } - ttf_reset_chksm (tab); - (void) put_ushort (0); /* Format selector */ - (void) put_ushort (name_record_num); - (void) put_ushort (3 * TTF_USHORT_SIZE + - name_record_num * 6 * TTF_USHORT_SIZE); + ttf_reset_chksm(tab); + (void) put_ushort(0); /* Format selector */ + (void) put_ushort(name_record_num); + (void) put_ushort(3 * TTF_USHORT_SIZE + + name_record_num * 6 * TTF_USHORT_SIZE); for (i = 0; i < name_record_num; i++) { - (void) put_ushort (name_tab[i].platform_id); - (void) put_ushort (name_tab[i].encoding_id); - (void) put_ushort (name_tab[i].language_id); - (void) put_ushort (name_tab[i].name_id); - (void) put_ushort (name_tab[i].new_length); - (void) put_ushort (name_tab[i].new_offset); + (void) put_ushort(name_tab[i].platform_id); + (void) put_ushort(name_tab[i].encoding_id); + (void) put_ushort(name_tab[i].language_id); + (void) put_ushort(name_tab[i].name_id); + (void) put_ushort(name_tab[i].new_length); + (void) put_ushort(name_tab[i].new_offset); } for (p = new_name_buf; p - new_name_buf < new_name_buf_size; p++) - put_char (*p); - ttf_set_chksm (tab); + put_char(*p); + ttf_set_chksm(tab); if (new_name_buf != name_buf) - xfree (new_name_buf); + xfree(new_name_buf); } -static void ttf_write_dirtab (void) +static void ttf_write_dirtab(void) { dirtab_entry *tab; TTF_ULONG i, k; char *p; - const integer save_offset = ttf_offset (); - ttf_seek_outbuf (TABDIR_OFF); - if (is_subsetted (fd_cur->fm)) { + const integer save_offset = ttf_offset(); + ttf_seek_outbuf(TABDIR_OFF); + if (is_subsetted(fd_cur->fm)) { for (i = 0; i < DEFAULT_NTABS; i++) { - tab = ttf_name_lookup (newtabnames[i], false); + tab = ttf_name_lookup(newtabnames[i], false); if (tab == NULL) continue; for (k = 0; k < 4; k++) - put_char (tab->tag[k]); - put_ulong (tab->checksum); - put_ulong (tab->offset); - put_ulong (tab->length); + put_char(tab->tag[k]); + put_ulong(tab->checksum); + put_ulong(tab->offset); + put_ulong(tab->length); } } else { for (tab = dir_tab; tab - dir_tab < ntabs; tab++) { for (k = 0; k < 4; k++) - put_char (tab->tag[k]); - put_ulong (tab->checksum); - put_ulong (tab->offset); - put_ulong (tab->length); + put_char(tab->tag[k]); + put_ulong(tab->checksum); + put_ulong(tab->offset); + put_ulong(tab->length); } } /* adjust checkSumAdjustment */ @@ -952,34 +959,34 @@ static void ttf_write_dirtab (void) } } if (i % 4 != 0) { - pdftex_warn ("font length is not a multiple of 4 (%li)", i); + pdftex_warn("font length is not a multiple of 4 (%li)", i); checksum <<= 8 * (4 - i % 4); } k = 0xB1B0AFBA - checksum; - ttf_seek_outbuf (checkSumAdjustment_offset); - put_ulong (k); - ttf_seek_outbuf (save_offset); + ttf_seek_outbuf(checkSumAdjustment_offset); + put_ulong(k); + ttf_seek_outbuf(save_offset); } -static void ttf_write_glyf (void) +static void ttf_write_glyf(void) { long *id, k; TTF_USHORT idx; TTF_USHORT flags; - dirtab_entry *tab = ttf_name_lookup ("glyf", true); + dirtab_entry *tab = ttf_name_lookup("glyf", true); const long glyf_offset = tab->offset; - const long new_glyf_offset = ttf_offset (); - ttf_reset_chksm (tab); + const long new_glyf_offset = ttf_offset(); + ttf_reset_chksm(tab); for (id = glyph_index; id - glyph_index < new_glyphs_count; id++) { - glyph_tab[*id].newoffset = ttf_offset () - new_glyf_offset; + glyph_tab[*id].newoffset = ttf_offset() - new_glyf_offset; if (glyph_tab[*id].offset != glyph_tab[*id + 1].offset) { - ttf_seek_off (glyf_offset + glyph_tab[*id].offset); - k = copy_short (); - ttf_ncopy (4 * TTF_FWORD_SIZE); + ttf_seek_off(glyf_offset + glyph_tab[*id].offset); + k = copy_short(); + ttf_ncopy(4 * TTF_FWORD_SIZE); if (k < 0) { do { - flags = copy_ushort (); - idx = get_ushort (); + flags = copy_ushort(); + idx = get_ushort(); if (glyph_tab[idx].newindex < 0) { glyph_tab[idx].newindex = new_glyphs_count; glyph_index[new_glyphs_count++] = idx; @@ -988,27 +995,27 @@ static void ttf_write_glyf (void) which appears in the condition of the `for' loop */ } - (void) put_ushort (glyph_tab[idx].newindex); + (void) put_ushort(glyph_tab[idx].newindex); if (flags & ARG_1_AND_2_ARE_WORDS) - ttf_ncopy (2 * TTF_SHORT_SIZE); + ttf_ncopy(2 * TTF_SHORT_SIZE); else - ttf_ncopy (TTF_USHORT_SIZE); + ttf_ncopy(TTF_USHORT_SIZE); if (flags & WE_HAVE_A_SCALE) - ttf_ncopy (TTF_F2DOT14_SIZE); + ttf_ncopy(TTF_F2DOT14_SIZE); else if (flags & WE_HAVE_AN_X_AND_Y_SCALE) - ttf_ncopy (2 * TTF_F2DOT14_SIZE); + ttf_ncopy(2 * TTF_F2DOT14_SIZE); else if (flags & WE_HAVE_A_TWO_BY_TWO) - ttf_ncopy (4 * TTF_F2DOT14_SIZE); + ttf_ncopy(4 * TTF_F2DOT14_SIZE); } while (flags & MORE_COMPONENTS); if (flags & WE_HAVE_INSTRUCTIONS) - ttf_ncopy (copy_ushort ()); + ttf_ncopy(copy_ushort()); } else - ttf_ncopy (glyph_tab[*id + 1].offset - glyph_tab[*id].offset - - TTF_USHORT_SIZE - 4 * TTF_FWORD_SIZE); + ttf_ncopy(glyph_tab[*id + 1].offset - glyph_tab[*id].offset - + TTF_USHORT_SIZE - 4 * TTF_FWORD_SIZE); } } - last_glyf_offset = ttf_offset () - new_glyf_offset; - ttf_set_chksm (tab); + last_glyf_offset = ttf_offset() - new_glyf_offset; + ttf_set_chksm(tab); } static void ttf_reindex_glyphs(void) @@ -1016,7 +1023,7 @@ static void ttf_reindex_glyphs(void) ttfenc_entry *e; glyph_entry *glyph; int index; - short *t; + long *t; ttf_cmap_entry *cmap = NULL; boolean cmap_not_found = false; @@ -1089,7 +1096,7 @@ static void ttf_reindex_glyphs(void) if (t[index] != -1) { if (t[index] >= glyphs_count) { pdftex_warn - ("`%s' is mapped to index %i which is out of valid range [0..%i)", + ("`%s' is mapped to index %li which is out of valid range [0..%i)", e->name, t[index], glyphs_count); continue; } @@ -1112,7 +1119,7 @@ static void ttf_reindex_glyphs(void) append_new_glyph: assert(glyph > glyph_tab && glyph - glyph_tab < glyphs_count); if (glyph->newindex < 0) { - glyph_index[new_glyphs_count] = (short) (glyph - glyph_tab); + glyph_index[new_glyphs_count] = (short) (glyph - glyph_tab); glyph->newindex = new_glyphs_count; new_glyphs_count++; } @@ -1120,53 +1127,53 @@ static void ttf_reindex_glyphs(void) } } -static void ttf_write_head () +static void ttf_write_head() { dirtab_entry *tab; - tab = ttf_seek_tab ("head", 0); - ttf_reset_chksm (tab); - ttf_ncopy (2 * TTF_FIXED_SIZE); - checkSumAdjustment_offset = ttf_offset (); - put_ulong (0); - ttf_skip (TTF_ULONG_SIZE); /* skip checkSumAdjustment */ - ttf_ncopy (TTF_ULONG_SIZE + 2 * TTF_USHORT_SIZE + 16 + - 4 * TTF_FWORD_SIZE + 2 * TTF_USHORT_SIZE + TTF_SHORT_SIZE); + tab = ttf_seek_tab("head", 0); + ttf_reset_chksm(tab); + ttf_ncopy(2 * TTF_FIXED_SIZE); + checkSumAdjustment_offset = ttf_offset(); + put_ulong(0); + ttf_skip(TTF_ULONG_SIZE); /* skip checkSumAdjustment */ + ttf_ncopy(TTF_ULONG_SIZE + 2 * TTF_USHORT_SIZE + 16 + + 4 * TTF_FWORD_SIZE + 2 * TTF_USHORT_SIZE + TTF_SHORT_SIZE); if (is_subsetted(fd_cur->fm)) { - (void) put_short (loca_format); - (void) put_short (0); + (void) put_short(loca_format); + (void) put_short(0); } else - ttf_ncopy (2 * TTF_SHORT_SIZE); - ttf_set_chksm (tab); + ttf_ncopy(2 * TTF_SHORT_SIZE); + ttf_set_chksm(tab); } -static void ttf_write_hhea (void) +static void ttf_write_hhea(void) { dirtab_entry *tab; - tab = ttf_seek_tab ("hhea", 0); - ttf_reset_chksm (tab); - ttf_ncopy (TTF_FIXED_SIZE + 3 * TTF_FWORD_SIZE + TTF_UFWORD_SIZE + - 3 * TTF_FWORD_SIZE + 8 * TTF_SHORT_SIZE); - (void) put_ushort (new_glyphs_count); - ttf_set_chksm (tab); + tab = ttf_seek_tab("hhea", 0); + ttf_reset_chksm(tab); + ttf_ncopy(TTF_FIXED_SIZE + 3 * TTF_FWORD_SIZE + TTF_UFWORD_SIZE + + 3 * TTF_FWORD_SIZE + 8 * TTF_SHORT_SIZE); + (void) put_ushort(new_glyphs_count); + ttf_set_chksm(tab); } -static void ttf_write_htmx (void) +static void ttf_write_htmx(void) { long *id; - dirtab_entry *tab = ttf_seek_tab ("hmtx", 0); - ttf_reset_chksm (tab); + dirtab_entry *tab = ttf_seek_tab("hmtx", 0); + ttf_reset_chksm(tab); for (id = glyph_index; id - glyph_index < new_glyphs_count; id++) { - put_ufword (glyph_tab[*id].advWidth); - put_ufword (glyph_tab[*id].lsb); + put_ufword(glyph_tab[*id].advWidth); + put_ufword(glyph_tab[*id].lsb); } - ttf_set_chksm (tab); + ttf_set_chksm(tab); } -static void ttf_write_loca (void) +static void ttf_write_loca(void) { long *id; - dirtab_entry *tab = ttf_seek_tab ("loca", 0); - ttf_reset_chksm (tab); + dirtab_entry *tab = ttf_seek_tab("loca", 0); + ttf_reset_chksm(tab); loca_format = 0; if (last_glyf_offset >= 0x00020000 || (last_glyf_offset & 1)) loca_format = 1; @@ -1178,152 +1185,152 @@ static void ttf_write_loca (void) } if (loca_format != 0) { for (id = glyph_index; id - glyph_index < new_glyphs_count; id++) - put_ulong (glyph_tab[*id].newoffset); - put_ulong (last_glyf_offset); + put_ulong(glyph_tab[*id].newoffset); + put_ulong(last_glyf_offset); } else { for (id = glyph_index; id - glyph_index < new_glyphs_count; id++) - (void) put_ushort (glyph_tab[*id].newoffset / 2); - (void) put_ushort (last_glyf_offset / 2); + (void) put_ushort(glyph_tab[*id].newoffset / 2); + (void) put_ushort(last_glyf_offset / 2); } - ttf_set_chksm (tab); + ttf_set_chksm(tab); } -static void ttf_write_mapx (void) +static void ttf_write_mapx(void) { - dirtab_entry *tab = ttf_seek_tab ("maxp", TTF_FIXED_SIZE + TTF_USHORT_SIZE); - ttf_reset_chksm (tab); - put_fixed (0x00010000); - (void) put_ushort (new_glyphs_count); - ttf_ncopy (13 * TTF_USHORT_SIZE); - ttf_set_chksm (tab); + dirtab_entry *tab = ttf_seek_tab("maxp", TTF_FIXED_SIZE + TTF_USHORT_SIZE); + ttf_reset_chksm(tab); + put_fixed(0x00010000); + (void) put_ushort(new_glyphs_count); + ttf_ncopy(13 * TTF_USHORT_SIZE); + ttf_set_chksm(tab); } -static void ttf_write_OS2 (void) +static void ttf_write_OS2(void) { - dirtab_entry *tab = ttf_seek_tab ("OS/2", 0); + dirtab_entry *tab = ttf_seek_tab("OS/2", 0); TTF_USHORT version; - ttf_reset_chksm (tab); - version = get_ushort (); + ttf_reset_chksm(tab); + version = get_ushort(); if (version > 3) - pdftex_fail ("unknown version of OS/2 table (%.4X)", version); - (void) put_ushort (0x0001); /* fix version to 1 */ - ttf_ncopy (2 * TTF_USHORT_SIZE + 13 * TTF_SHORT_SIZE + 10 * TTF_BYTE_SIZE); - ttf_skip (4 * TTF_ULONG_SIZE); /* ulUnicodeRange 1--4 */ - put_ulong (0x00000003); /* Basic Latin + Latin-1 Supplement (0x0000--0x00FF) */ - put_ulong (0x10000000); /* Private Use (0xE000--0xF8FF) */ - put_ulong (0x00000000); - put_ulong (0x00000000); - ttf_ncopy (4 * TTF_CHAR_SIZE + TTF_USHORT_SIZE); /* achVendID + fsSelection */ - ttf_skip (2 * TTF_USHORT_SIZE); - (void) put_ushort (0x0000); /* usFirstCharIndex */ - (void) put_ushort (0xF0FF); /* usLastCharIndex */ - ttf_ncopy (5 * TTF_USHORT_SIZE); + pdftex_fail("unknown version of OS/2 table (%.4X)", version); + (void) put_ushort(0x0001); /* fix version to 1 */ + ttf_ncopy(2 * TTF_USHORT_SIZE + 13 * TTF_SHORT_SIZE + 10 * TTF_BYTE_SIZE); + ttf_skip(4 * TTF_ULONG_SIZE); /* ulUnicodeRange 1--4 */ + put_ulong(0x00000003); /* Basic Latin + Latin-1 Supplement (0x0000--0x00FF) */ + put_ulong(0x10000000); /* Private Use (0xE000--0xF8FF) */ + put_ulong(0x00000000); + put_ulong(0x00000000); + ttf_ncopy(4 * TTF_CHAR_SIZE + TTF_USHORT_SIZE); /* achVendID + fsSelection */ + ttf_skip(2 * TTF_USHORT_SIZE); + (void) put_ushort(0x0000); /* usFirstCharIndex */ + (void) put_ushort(0xF0FF); /* usLastCharIndex */ + ttf_ncopy(5 * TTF_USHORT_SIZE); /* for version 0 the OS/2 table ends here, the rest is for version 1 */ - put_ulong (0x80000000); /* Symbol Character Set---don't use any code page */ - put_ulong (0x00000000); - ttf_set_chksm (tab); + put_ulong(0x80000000); /* Symbol Character Set---don't use any code page */ + put_ulong(0x00000000); + ttf_set_chksm(tab); } -static boolean unsafe_name (char *s) +static boolean unsafe_name(char *s) { const char **p; for (p = ambiguous_names; *p != NULL; p++) - if (strcmp (s, *p) == 0) + if (strcmp(s, *p) == 0) return true; return false; } -static void ttf_write_post (void) +static void ttf_write_post(void) { - dirtab_entry *tab = ttf_seek_tab ("post", TTF_FIXED_SIZE); + dirtab_entry *tab = ttf_seek_tab("post", TTF_FIXED_SIZE); glyph_entry *glyph; char *s; long *id; int l; - ttf_reset_chksm (tab); + ttf_reset_chksm(tab); if (!fd_cur->write_ttf_glyph_names || post_format == 0x00030000) { - put_fixed (0x00030000); - ttf_ncopy (TTF_FIXED_SIZE + 2 * TTF_FWORD_SIZE + 5 * TTF_ULONG_SIZE); + put_fixed(0x00030000); + ttf_ncopy(TTF_FIXED_SIZE + 2 * TTF_FWORD_SIZE + 5 * TTF_ULONG_SIZE); } else { - put_fixed (0x00020000); - ttf_ncopy (TTF_FIXED_SIZE + 2 * TTF_FWORD_SIZE + 5 * TTF_ULONG_SIZE); - (void) put_ushort (new_glyphs_count); + put_fixed(0x00020000); + ttf_ncopy(TTF_FIXED_SIZE + 2 * TTF_FWORD_SIZE + 5 * TTF_ULONG_SIZE); + (void) put_ushort(new_glyphs_count); k = 0; for (id = glyph_index; id - glyph_index < new_glyphs_count; id++) { glyph = glyph_tab + *id; - if (glyph->name_index >= NMACGLYPHS || unsafe_name (glyph->name)) + if (glyph->name_index >= NMACGLYPHS || unsafe_name(glyph->name)) glyph->name_index = NMACGLYPHS + k++; - (void) put_ushort (glyph->name_index); + (void) put_ushort(glyph->name_index); } for (id = glyph_index; id - glyph_index < new_glyphs_count; id++) { glyph = glyph_tab + *id; if (glyph->name_index >= NMACGLYPHS) { s = glyph->name; - l = strlen (s); - put_byte (l); + l = strlen(s); + put_byte(l); while (l-- > 0) - put_char (*s++); + put_char(*s++); } } } - ttf_set_chksm (tab); + ttf_set_chksm(tab); } -static void ttf_init_font (int n) +static void ttf_init_font(int n) { int i, k; for (i = 1, k = 0; i <= n; i <<= 1, k++); - put_fixed (0x00010000); /* font version */ - (void) put_ushort (n); /* number of tables */ - (void) put_ushort (i << 3); /* search range */ - (void) put_ushort (k - 1); /* entry selector */ - (void) put_ushort ((n << 4) - (i << 3)); /* range shift */ - ttf_seek_outbuf (TABDIR_OFF + n * 4 * TTF_ULONG_SIZE); + put_fixed(0x00010000); /* font version */ + (void) put_ushort(n); /* number of tables */ + (void) put_ushort(i << 3); /* search range */ + (void) put_ushort(k - 1); /* entry selector */ + (void) put_ushort((n << 4) - (i << 3)); /* range shift */ + ttf_seek_outbuf(TABDIR_OFF + n * 4 * TTF_ULONG_SIZE); } -static void ttf_subset_font (void) +static void ttf_subset_font(void) { - ttf_init_font (new_ntabs); - if (ttf_name_lookup ("PCLT", false) != NULL) - ttf_copytab ("PCLT"); - if (ttf_name_lookup ("fpgm", false) != NULL) - ttf_copytab ("fpgm"); - if (ttf_name_lookup ("cvt ", false) != NULL) - ttf_copytab ("cvt "); - if (ttf_name_lookup ("prep", false) != NULL) - ttf_copytab ("prep"); - ttf_reindex_glyphs (); - ttf_write_glyf (); - ttf_write_loca (); - ttf_write_OS2 (); - ttf_write_head (); - ttf_write_hhea (); - ttf_write_htmx (); - ttf_write_mapx (); - ttf_write_name (); - ttf_write_post (); - ttf_write_cmap (); - ttf_write_dirtab (); + ttf_init_font(new_ntabs); + if (ttf_name_lookup("PCLT", false) != NULL) + ttf_copytab("PCLT"); + if (ttf_name_lookup("fpgm", false) != NULL) + ttf_copytab("fpgm"); + if (ttf_name_lookup("cvt ", false) != NULL) + ttf_copytab("cvt "); + if (ttf_name_lookup("prep", false) != NULL) + ttf_copytab("prep"); + ttf_reindex_glyphs(); + ttf_write_glyf(); + ttf_write_loca(); + ttf_write_OS2(); + ttf_write_head(); + ttf_write_hhea(); + ttf_write_htmx(); + ttf_write_mapx(); + ttf_write_name(); + ttf_write_post(); + ttf_write_cmap(); + ttf_write_dirtab(); } -static void ttf_copy_font (void) +static void ttf_copy_font(void) { dirtab_entry *tab; - ttf_init_font (ntabs); + ttf_init_font(ntabs); for (tab = dir_tab; tab - dir_tab < ntabs; tab++) { - if (strncmp (tab->tag, "head", 4) == 0) - ttf_write_head (); + if (strncmp(tab->tag, "head", 4) == 0) + ttf_write_head(); else - ttf_copytab (tab->tag); + ttf_copytab(tab->tag); } - ttf_write_dirtab (); + ttf_write_dirtab(); } void writettf(fd_entry * fd) { - int callback_id; - int file_opened = 0; - char *ftemp = NULL; + int callback_id; + int file_opened = 0; + char *ftemp = NULL; fd_cur = fd; /* fd_cur is global inside writettf.c */ assert(fd_cur->fm != NULL); assert(is_truetype(fd_cur->fm)); @@ -1333,47 +1340,46 @@ void writettf(fd_entry * fd) if (is_subsetted(fd_cur->fm) && (fd_cur->fe == NULL) && !is_subfont(fd_cur->fm)) { - pdftex_warn ("Subset TrueType must be a reencoded or a subfont"); - cur_file_name = NULL; - return; + pdftex_fail("Subset TrueType must be a reencoded or a subfont"); + } + ttf_curbyte = 0; + ttf_size = 0; + callback_id = callback_defined(find_truetype_file_callback); + if (callback_id > 0) { + if (run_callback + (callback_id, "S->S", (char *) (nameoffile + 1), &ftemp)) { + if (ftemp != NULL && strlen(ftemp)) { + free(nameoffile); + namelength = strlen(ftemp); + nameoffile = xmalloc(namelength + 2); + strcpy((char *) (nameoffile + 1), ftemp); + free(ftemp); + } + } + } + + callback_id = callback_defined(read_truetype_file_callback); + if (callback_id > 0) { + if (run_callback(callback_id, "S->bSd", (char *) (nameoffile + 1), + &file_opened, &ttf_buffer, &ttf_size) && + file_opened && ttf_size > 0) { + } else { + pdftex_fail("cannot open TrueType font file for reading"); + } + } else { + if (!ttf_open()) { + pdftex_fail("cannot open TrueType font file for reading"); + } + ttf_read_file(); + ttf_close(); } - ttf_curbyte=0; - ttf_size=0; - callback_id=callback_defined(find_truetype_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->S",(char *)(nameoffile+1),&ftemp)) { - if(ftemp!=NULL&&strlen(ftemp)) { - free(nameoffile); - namelength = strlen(ftemp); - nameoffile = xmalloc(namelength+2); - strcpy((char *)(nameoffile+1),ftemp); - free(ftemp); - } - } - } - - callback_id=callback_defined(read_truetype_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->bSd",(char *)(nameoffile+1), - &file_opened, &ttf_buffer,&ttf_size) && - file_opened && ttf_size>0) { - } else { - pdftex_fail ("cannot open TrueType font file for reading"); - } - } else { - if (!ttf_open ()) { - pdftex_fail ("cannot open TrueType font file for reading"); - } - ttf_read_file(); - ttf_close(); - } cur_file_name = (char *) nameoffile + 1; - if (tracefilenames) { - if (is_subsetted(fd_cur->fm)) - tex_printf ("<%s", cur_file_name); - else - tex_printf ("<<%s", cur_file_name); - } + if (tracefilenames) { + if (is_subsetted(fd_cur->fm)) + tex_printf("<%s", cur_file_name); + else + tex_printf("<<%s", cur_file_name); + } fd_cur->ff_found = true; new_glyphs_count = 2; new_ntabs = DEFAULT_NTABS; @@ -1383,107 +1389,111 @@ void writettf(fd_entry * fd) glyph_name_buf = NULL; name_tab = NULL; name_buf = NULL; - ttf_read_font (); - - pdf_save_offset = pdfoffset (); - pdf_flush (); - - if (is_subsetted(fd_cur->fm)) { - ttf_copy_encoding (); - ttf_subset_font (); - } else - ttf_copy_font (); - ttf_length = ttf_offset (); - - xfree (dir_tab); - xfree (glyph_tab); - xfree (glyph_index); - xfree (glyph_name_buf); - xfree (name_tab); - xfree (name_buf); - if (tracefilenames) { - if (is_subsetted (fd_cur->fm)) - tex_printf (">"); - else - tex_printf (">>"); - } + ttf_read_font(); + + pdf_save_offset = pdfoffset(); + pdf_flush(); + + if (is_subsetted(fd_cur->fm)) { + ttf_copy_encoding(); + ttf_subset_font(); + } else + ttf_copy_font(); + ttf_length = ttf_offset(); + + xfree(dir_tab); + xfree(glyph_tab); + xfree(glyph_index); + xfree(glyph_name_buf); + xfree(name_tab); + xfree(name_buf); + if (tracefilenames) { + if (is_subsetted(fd_cur->fm)) + tex_printf(">"); + else + tex_printf(">>"); + } + xfree(ttf_buffer); cur_file_name = NULL; } void do_writeotf(fd_entry * fd) { - long i; - dirtab_entry *tab; - dir_tab = NULL; - glyph_tab = NULL; - if (tracefilenames) - tex_printf ("<<%s", cur_file_name); - ttf_read_tabdir (); - /* read font parameters */ - if (ttf_name_lookup ("head", false) != NULL) - ttf_read_head (); - if (ttf_name_lookup ("hhea", false) != NULL) - ttf_read_hhea (); - if (ttf_name_lookup ("PCLT", false) != NULL) - ttf_read_pclt (); - if (ttf_name_lookup ("post", false) != NULL) - ttf_read_post (); - /* copy font file */ - tab = ttf_seek_tab ("CFF ", 0); - for (i = tab->length; i > 0; i--) - copy_char (); - xfree (dir_tab); - /* ttf_close ();*/ - if (tracefilenames) - tex_printf (">>"); + long i; + dirtab_entry *tab; + dir_tab = NULL; + glyph_tab = NULL; + if (tracefilenames) + tex_printf("<<%s", cur_file_name); + ttf_read_tabdir(); + /* read font parameters */ + if (ttf_name_lookup("head", false) != NULL) + ttf_read_head(); + if (ttf_name_lookup("hhea", false) != NULL) + ttf_read_hhea(); + if (ttf_name_lookup("PCLT", false) != NULL) + ttf_read_pclt(); + if (ttf_name_lookup("post", false) != NULL) + ttf_read_post(); + /* copy font file */ + tab = ttf_seek_tab("CFF ", 0); + for (i = tab->length; i > 0; i--) + copy_char(); + xfree(dir_tab); + /* ttf_close (); */ + if (tracefilenames) + tex_printf(">>"); } -void writeotf (fd_entry * fd) { - int callback_id; - int file_opened = 0; - char *ftemp = NULL; - - - fd_cur = fd; /* fd_cur is global inside writettf.c */ - assert(fd_cur->fm != NULL); - assert(is_opentype(fd_cur->fm)); - assert(is_included(fd_cur->fm)); - - set_cur_file_name(fd_cur->fm->ff_name); - ttf_curbyte=0; - ttf_size=0; - callback_id=callback_defined(find_opentype_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->S",(char *)(nameoffile+1),&ftemp)) { - if(ftemp!=NULL&&strlen(ftemp)) { - free(nameoffile); - namelength = strlen(ftemp); - nameoffile = xmalloc(namelength+2); - strcpy((char *)(nameoffile+1),ftemp); - free(ftemp); - } +void writeotf(fd_entry * fd) +{ + int callback_id; + int file_opened = 0; + char *ftemp = NULL; + + + fd_cur = fd; /* fd_cur is global inside writettf.c */ + assert(fd_cur->fm != NULL); + assert(is_opentype(fd_cur->fm)); + assert(is_included(fd_cur->fm)); + + set_cur_file_name(fd_cur->fm->ff_name); + ttf_curbyte = 0; + ttf_size = 0; + callback_id = callback_defined(find_opentype_file_callback); + if (callback_id > 0) { + if (run_callback + (callback_id, "S->S", (char *) (nameoffile + 1), &ftemp)) { + if (ftemp != NULL && strlen(ftemp)) { + free(nameoffile); + namelength = strlen(ftemp); + nameoffile = xmalloc(namelength + 2); + strcpy((char *) (nameoffile + 1), ftemp); + free(ftemp); + } + } } - } - callback_id=callback_defined(read_opentype_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->bSd",(char *)(nameoffile+1), - &file_opened, &ttf_buffer,&ttf_size) && - file_opened && ttf_size>0) { + callback_id = callback_defined(read_opentype_file_callback); + if (callback_id > 0) { + if (run_callback(callback_id, "S->bSd", (char *) (nameoffile + 1), + &file_opened, &ttf_buffer, &ttf_size) && + file_opened && ttf_size > 0) { + } else { + pdftex_fail("cannot open OpenType font file for reading"); + } } else { - pdftex_fail ("cannot open OpenType font file for reading"); - } - } else { - if (!otf_open ()) { - pdftex_fail ("cannot open OpenType font file for reading"); + if (!otf_open()) { + pdftex_fail("cannot open OpenType font file for reading"); + } + ttf_read_file(); + ttf_close(); } - ttf_read_file(); - ttf_close(); - } - - cur_file_name = (char *) nameoffile + 1; - fd_cur->ff_found = true; - do_writeotf(fd); - cur_file_name = NULL; + + cur_file_name = (char *) nameoffile + 1; + fd_cur->ff_found = true; + do_writeotf(fd); + xfree(ttf_buffer); + cur_file_name = NULL; } /* diff --git a/Build/source/texk/web2c/luatexdir/font/writettf.h b/Build/source/texk/web2c/luatexdir/font/writettf.h index ecfaa2c37e3..42a57a72c8f 100644 --- a/Build/source/texk/web2c/luatexdir/font/writettf.h +++ b/Build/source/texk/web2c/luatexdir/font/writettf.h @@ -1,25 +1,27 @@ -/* -Copyright (c) 1996-2006 Han The Thanh, <thanh@pdftex.org> +/* writettf.h + + Copyright 1996-2006 Han The Thanh <thanh@pdftex.org> + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -This file is part of pdfTeX. + This file is part of LuaTeX. -pdfTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -pdfTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -You should have received a copy of the GNU General Public License -along with pdfTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ -$Id: writettf.h 1013 2008-02-14 00:09:02Z oneiros $ -*/ +/* $Id: writettf.h 1592 2008-11-28 13:23:51Z oneiros $ */ +#ifndef WRITETTF_H +# define WRITETTF_H 1 typedef signed char TTF_CHAR; typedef unsigned char TTF_BYTE; typedef signed short TTF_SHORT; @@ -32,79 +34,82 @@ typedef signed short TTF_FWORD; typedef unsigned short TTF_UFWORD; typedef unsigned short TTF_F2DOT14; -#define TTF_CHAR_SIZE 1 -#define TTF_BYTE_SIZE 1 -#define TTF_SHORT_SIZE 2 -#define TTF_USHORT_SIZE 2 -#define TTF_LONG_SIZE 4 -#define TTF_ULONG_SIZE 4 -#define TTF_FIXED_SIZE 4 -#define TTF_FWORD_SIZE 2 -#define TTF_UFWORD_SIZE 2 -#define TTF_F2DOT14_SIZE 2 - -#define ARG_1_AND_2_ARE_WORDS (1<<0) -#define ARGS_ARE_XY_VALUES (1<<1) -#define ROUND_XY_TO_GRID (1<<2) -#define WE_HAVE_A_SCALE (1<<3) -#define RESERVED (1<<4) -#define MORE_COMPONENTS (1<<5) -#define WE_HAVE_AN_X_AND_Y_SCALE (1<<6) -#define WE_HAVE_A_TWO_BY_TWO (1<<7) -#define WE_HAVE_INSTRUCTIONS (1<<8) -#define USE_MY_METRICS (1<<9) - -#define get_type(t) ((t)ttf_getnum(t##_SIZE)) -#define ttf_skip(n) ttf_getnum(n) - -#define get_byte() get_type(TTF_BYTE) -#define get_char() get_type(TTF_CHAR) -#define get_ushort() get_type(TTF_USHORT) -#define get_short() get_type(TTF_SHORT) -#define get_ulong() get_type(TTF_ULONG) -#define get_long() get_type(TTF_LONG) -#define get_fixed() get_type(TTF_FIXED) -#define get_funit() get_type(TTF_FUNIT) -#define get_fword() get_type(TTF_FWORD) -#define get_ufword() get_type(TTF_UFWORD) -#define get_f2dot14() get_type(TTF_F2DOT14) - -#define put_num(t,n) ((t)ttf_putnum(t##_SIZE, n)) - -#define put_char(n) (void)put_num(TTF_CHAR, n) -#define put_byte(n) (void)put_num(TTF_BYTE, n) -#define put_short(n) put_num(TTF_SHORT, n) -#define put_ushort(n) put_num(TTF_USHORT, n) -#define put_long(n) put_num(TTF_LONG, n) -#define put_ulong(n) (void)put_num(TTF_ULONG, n) -#define put_fixed(n) (void)put_num(TTF_FIXED, n) -#define put_funit(n) put_num(TTF_FUNIT, n) -#define put_fword(n) put_num(TTF_FWORD, n) -#define put_ufword(n) (void)put_num(TTF_UFWORD, n) -#define put_f2dot14(n) put_num(TTF_F2DOT14, n) - -#define copy_byte() put_byte(get_byte()) -#define copy_char() put_char(get_char()) -#define copy_ushort() put_ushort(get_ushort()) -#define copy_short() put_short(get_short()) -#define copy_ulong() put_ulong(get_ulong()) -#define copy_long() put_long(get_long()) -#define copy_fixed() put_fixed(get_fixed()) -#define copy_funit() put_funit(get_funit()) -#define copy_fword() put_fword(get_fword()) -#define copy_ufword() put_ufword(get_ufword()) -#define copy_f2dot14() put_f2dot14(get_f2dot14()) - -#define is_unicode_mapping(e) \ +# define TTF_CHAR_SIZE 1 +# define TTF_BYTE_SIZE 1 +# define TTF_SHORT_SIZE 2 +# define TTF_USHORT_SIZE 2 +# define TTF_LONG_SIZE 4 +# define TTF_ULONG_SIZE 4 +# define TTF_FIXED_SIZE 4 +# define TTF_FWORD_SIZE 2 +# define TTF_UFWORD_SIZE 2 +# define TTF_F2DOT14_SIZE 2 + +/* + * TrueType outline data. + */ +# define ARG_1_AND_2_ARE_WORDS (1<<0) +# define ARGS_ARE_XY_VALUES (1<<1) +# define ROUND_XY_TO_GRID (1<<2) +# define WE_HAVE_A_SCALE (1<<3) +# define RESERVED (1<<4) +# define MORE_COMPONENTS (1<<5) +# define WE_HAVE_AN_X_AND_Y_SCALE (1<<6) +# define WE_HAVE_A_TWO_BY_TWO (1<<7) +# define WE_HAVE_INSTRUCTIONS (1<<8) +# define USE_MY_METRICS (1<<9) + +# define get_type(t) ((t)ttf_getnum(t##_SIZE)) +# define ttf_skip(n) ttf_getnum(n) + +# define get_byte() get_type(TTF_BYTE) +# define get_char() get_type(TTF_CHAR) +# define get_ushort() get_type(TTF_USHORT) +# define get_short() get_type(TTF_SHORT) +# define get_ulong() get_type(TTF_ULONG) +# define get_long() get_type(TTF_LONG) +# define get_fixed() get_type(TTF_FIXED) +# define get_funit() get_type(TTF_FUNIT) +# define get_fword() get_type(TTF_FWORD) +# define get_ufword() get_type(TTF_UFWORD) +# define get_f2dot14() get_type(TTF_F2DOT14) + +# define put_num(t,n) ((t)ttf_putnum(t##_SIZE, n)) + +# define put_char(n) (void)put_num(TTF_CHAR, n) +# define put_byte(n) (void)put_num(TTF_BYTE, n) +# define put_short(n) put_num(TTF_SHORT, n) +# define put_ushort(n) put_num(TTF_USHORT, n) +# define put_long(n) put_num(TTF_LONG, n) +# define put_ulong(n) (void)put_num(TTF_ULONG, n) +# define put_fixed(n) (void)put_num(TTF_FIXED, n) +# define put_funit(n) put_num(TTF_FUNIT, n) +# define put_fword(n) put_num(TTF_FWORD, n) +# define put_ufword(n) (void)put_num(TTF_UFWORD, n) +# define put_f2dot14(n) put_num(TTF_F2DOT14, n) + +# define copy_byte() put_byte(get_byte()) +# define copy_char() put_char(get_char()) +# define copy_ushort() put_ushort(get_ushort()) +# define copy_short() put_short(get_short()) +# define copy_ulong() put_ulong(get_ulong()) +# define copy_long() put_long(get_long()) +# define copy_fixed() put_fixed(get_fixed()) +# define copy_funit() put_funit(get_funit()) +# define copy_fword() put_fword(get_fword()) +# define copy_ufword() put_ufword(get_ufword()) +# define copy_f2dot14() put_f2dot14(get_f2dot14()) + +# define is_unicode_mapping(e) \ (e->platform_id == 0 || (e->platform_id == 3 || e->encoding_id == 1)) -#define NMACGLYPHS 258 -#define TABDIR_OFF 12 -#define ENC_BUF_SIZE 1024 +# define NMACGLYPHS 258 +# define TABDIR_OFF 12 +# define ENC_BUF_SIZE 1024 -#define GLYPH_PREFIX_INDEX "index" -#define GLYPH_PREFIX_UNICODE "uni" +# define GLYPH_PREFIX_INDEX "index" +# define GLYPH_PREFIX_UNICODE "uni" typedef struct { char tag[4]; @@ -145,28 +150,27 @@ extern integer ttf_size; extern integer ttf_curbyte; extern glyph_entry *glyph_tab; extern dirtab_entry *dir_tab; -extern dirtab_entry *ttf_name_lookup (const char *s, boolean required); -extern dirtab_entry *ttf_seek_tab (const char *name, TTF_LONG offset); +extern dirtab_entry *ttf_name_lookup(const char *s, boolean required); +extern dirtab_entry *ttf_seek_tab(const char *name, TTF_LONG offset); -extern void ttf_read_tabdir (void); -extern void ttf_read_head (void); -extern void ttf_read_hhea (void); -extern void ttf_read_pclt (void); -extern void ttf_read_post (void); +extern void ttf_read_tabdir(void); +extern void ttf_read_head(void); +extern void ttf_read_hhea(void); +extern void ttf_read_pclt(void); +extern void ttf_read_post(void); extern FILE *ttf_file; -#define ttf_open() \ - open_input(&ttf_file, kpse_truetype_format, FOPEN_RBIN_MODE) -#define otf_open() \ - open_input(&ttf_file, kpse_opentype_format, FOPEN_RBIN_MODE) -#define ttf_read_file() \ +# define ttf_open() \ + (ttf_file = fopen((char *) nameoffile + 1, FOPEN_RBIN_MODE)) +# define otf_open() \ + (ttf_file = fopen((char *) nameoffile + 1, FOPEN_RBIN_MODE)) +# define ttf_read_file() \ readbinfile(ttf_file,&ttf_buffer,&ttf_size) -#define ttf_close() xfclose(ttf_file,cur_file_name) -#define ttf_getchar() ttf_buffer[ttf_curbyte++] -#define ttf_eof() (ttf_curbyte>ttf_size) - -extern long ttf_putnum (int s, long n); -extern long ttf_getnum (int s); - +# define ttf_close() xfclose(ttf_file,cur_file_name) +# define ttf_getchar() ttf_buffer[ttf_curbyte++] +# define ttf_eof() (ttf_curbyte>ttf_size) +extern long ttf_putnum(int s, long n); +extern long ttf_getnum(int s); +#endif diff --git a/Build/source/texk/web2c/luatexdir/font/writetype0.c b/Build/source/texk/web2c/luatexdir/font/writetype0.c index 0f9eecaac7c..846314bedab 100644 --- a/Build/source/texk/web2c/luatexdir/font/writetype0.c +++ b/Build/source/texk/web2c/luatexdir/font/writetype0.c @@ -1,124 +1,125 @@ -/* -Copyright (c) 2007 Taco Hoekwater, taco@luatex.org +/* writetype0.c + + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -This file is part of luaTeX. + This file is part of LuaTeX. -luaTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -luaTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -You should have received a copy of the GNU General Public License -along with luaTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -$Id: writetype0.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" - #include "writettf.h" - #include "writecff.h" -void writetype0 (fd_entry * fd) { - int callback_id; - int file_opened = 0; - char *ftemp = NULL; - long i; - dirtab_entry *tab; - cff_font *cff; - - dir_tab = NULL; - glyph_tab = NULL; - - fd_cur = fd; /* fd_cur is global inside writettf.c */ - assert(fd_cur->fm != NULL); - assert(is_opentype(fd_cur->fm)); - assert(is_included(fd_cur->fm)); - - set_cur_file_name(fd_cur->fm->ff_name); - ttf_curbyte=0; - ttf_size=0; - callback_id=callback_defined(find_opentype_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->S",(char *)(nameoffile+1),&ftemp)) { - if(ftemp!=NULL&&strlen(ftemp)) { - free(nameoffile); - namelength = strlen(ftemp); - nameoffile = xmalloc(namelength+2); - strcpy((char *)(nameoffile+1),ftemp); - free(ftemp); - } +static const char _svn_version[] = + "$Id: writetype0.c 1783 2009-01-18 12:51:01Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/writetype0.c $"; + +void writetype0(fd_entry * fd) +{ + int callback_id; + int file_opened = 0; + char *ftemp = NULL; + long i; + dirtab_entry *tab; + cff_font *cff; + + dir_tab = NULL; + glyph_tab = NULL; + + fd_cur = fd; /* fd_cur is global inside writettf.c */ + assert(fd_cur->fm != NULL); + assert(is_opentype(fd_cur->fm)); + assert(is_included(fd_cur->fm)); + + set_cur_file_name(fd_cur->fm->ff_name); + ttf_curbyte = 0; + ttf_size = 0; + callback_id = callback_defined(find_opentype_file_callback); + if (callback_id > 0) { + if (run_callback + (callback_id, "S->S", (char *) (nameoffile + 1), &ftemp)) { + if (ftemp != NULL && strlen(ftemp)) { + free(nameoffile); + namelength = strlen(ftemp); + nameoffile = xmalloc(namelength + 2); + strcpy((char *) (nameoffile + 1), ftemp); + free(ftemp); + } + } } - } - callback_id=callback_defined(read_opentype_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->bSd",(char *)(nameoffile+1), - &file_opened, &ttf_buffer,&ttf_size) && - file_opened && ttf_size>0) { + callback_id = callback_defined(read_opentype_file_callback); + if (callback_id > 0) { + if (run_callback(callback_id, "S->bSd", (char *) (nameoffile + 1), + &file_opened, &ttf_buffer, &ttf_size) && + file_opened && ttf_size > 0) { + } else { + pdftex_fail("cannot open OpenType font file for reading"); + } } else { - pdftex_fail ("cannot open OpenType font file for reading"); - } - } else { - if (!otf_open ()) { - pdftex_fail ("cannot open OpenType font file for reading"); + if (!otf_open()) { + pdftex_fail("cannot open OpenType font file for reading"); + } + ttf_read_file(); + ttf_close(); } - ttf_read_file(); - ttf_close(); - } - - cur_file_name = (char *) nameoffile + 1; - fd_cur->ff_found = true; - if (tracefilenames) { - if (is_subsetted(fd_cur->fm)) - tex_printf ("<%s", cur_file_name); - else - tex_printf ("<<%s", cur_file_name); - } - ttf_read_tabdir (); - /* read font parameters */ - if (ttf_name_lookup ("head", false) != NULL) - ttf_read_head (); - if (ttf_name_lookup ("hhea", false) != NULL) - ttf_read_hhea (); - if (ttf_name_lookup ("PCLT", false) != NULL) - ttf_read_pclt (); - if (ttf_name_lookup ("post", false) != NULL) - ttf_read_post (); + cur_file_name = (char *) nameoffile + 1; + fd_cur->ff_found = true; - /* copy font file */ - tab = ttf_seek_tab ("CFF ", 0); + if (tracefilenames) { + if (is_subsetted(fd_cur->fm)) + tex_printf("<%s", cur_file_name); + else + tex_printf("<<%s", cur_file_name); + } + ttf_read_tabdir(); + /* read font parameters */ + if (ttf_name_lookup("head", false) != NULL) + ttf_read_head(); + if (ttf_name_lookup("hhea", false) != NULL) + ttf_read_hhea(); + if (ttf_name_lookup("PCLT", false) != NULL) + ttf_read_pclt(); + if (ttf_name_lookup("post", false) != NULL) + ttf_read_post(); - /* TODO the next 0 is a subfont index */ - cff = read_cff(ttf_buffer+ttf_curbyte,tab->length,0); - if (cff != NULL) { - if (cff_is_cidfont(cff)) { - write_cid_cff(cff,fd_cur,0); - /* - for (i = tab->length; i > 0; i--) - fb_putchar (ttf_getnum(1)); - */ + /* copy font file */ + tab = ttf_seek_tab("CFF ", 0); + + /* TODO the next 0 is a subfont index */ + cff = read_cff(ttf_buffer + ttf_curbyte, tab->length, 0); + if (cff != NULL) { + if (cff_is_cidfont(cff)) { + write_cid_cff(cff, fd_cur); + /* + for (i = tab->length; i > 0; i--) + fb_putchar (ttf_getnum(1)); + */ + } else { + write_cff(cff, fd_cur); + } } else { - write_cff(cff,fd_cur,0); + /* not understood, just do a copy */ + for (i = tab->length; i > 0; i--) + fb_putchar(ttf_getnum(1)); + } + xfree(dir_tab); + xfree(ttf_buffer); + if (tracefilenames) { + if (is_subsetted(fd_cur->fm)) + tex_printf(">"); + else + tex_printf(">>"); } - } else { - /* not understood, just do a copy */ - for (i = tab->length; i > 0; i--) - fb_putchar (ttf_getnum(1)); - } - xfree (dir_tab); - if (tracefilenames) { - if (is_subsetted (fd_cur->fm)) - tex_printf (">"); - else - tex_printf (">>"); - } - cur_file_name = NULL; + cur_file_name = NULL; } diff --git a/Build/source/texk/web2c/luatexdir/font/writetype2.c b/Build/source/texk/web2c/luatexdir/font/writetype2.c index 649c350b707..ba98772b931 100644 --- a/Build/source/texk/web2c/luatexdir/font/writetype2.c +++ b/Build/source/texk/web2c/luatexdir/font/writetype2.c @@ -1,25 +1,21 @@ +/* writetype0.c + + Copyright 2006-2008 Taco Hoekwater <taco@luatex.org> -/* -Copyright (c) 2007 Taco Hoekwater, taco@luatex.org - -This file is part of luaTeX. - -luaTeX is free software; you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation; either version 2 of the License, or -(at your option) any later version. + This file is part of LuaTeX. -luaTeX is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. -You should have received a copy of the GNU General Public License -along with luaTeX; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. -$Id: writetype2.c 1013 2008-02-14 00:09:02Z oneiros $ -*/ + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see <http://www.gnu.org/licenses/>. */ #include "ptexlib.h" #include "writettf.h" @@ -28,170 +24,185 @@ $Id: writetype2.c 1013 2008-02-14 00:09:02Z oneiros $ #include "sfnt.h" #include "tt_glyf.h" +static const char _svn_version[] = + "$Id: writetype2.c 1783 2009-01-18 12:51:01Z oneiros $ $URL: http://scm.foundry.supelec.fr/svn/luatex/trunk/src/texk/web2c/luatexdir/font/writetype2.c $"; + /* forward*/ -void make_tt_subset (fd_entry * fd,unsigned char *buffer, integer buflen) ; +void make_tt_subset(fd_entry * fd, unsigned char *buffer, integer buflen); unsigned long cidtogid_obj = 0; /* low-level helpers */ -#define test_loc(l) \ - if ((f->loc+l)>f->buflen) { \ - fprintf (stderr,"File ended prematurely\n"); \ - uexit(1); \ +#define test_loc(l) \ + if ((f->loc+l)>f->buflen) { \ + fprintf (stderr,"File ended prematurely\n"); \ + uexit(1); \ } -BYTE get_unsigned_byte(sfnt* f) { - test_loc(1); - return (BYTE)f->buffer[(f->loc++)]; +BYTE get_unsigned_byte(sfnt * f) +{ + test_loc(1); + return (BYTE) f->buffer[(f->loc++)]; }; -ICHAR get_signed_byte(sfnt* f) { - test_loc(1); - return (ICHAR)f->buffer[(f->loc++)]; +ICHAR get_signed_byte(sfnt * f) +{ + test_loc(1); + return (ICHAR) f->buffer[(f->loc++)]; }; -USHORT get_unsigned_pair(sfnt* f){ - USHORT l; - test_loc(2); - l = f->buffer[(f->loc++)]; - l = l*0x100 + f->buffer[(f->loc++)]; - return l; +USHORT get_unsigned_pair(sfnt * f) +{ + USHORT l; + test_loc(2); + l = f->buffer[(f->loc++)]; + l = l * 0x100 + f->buffer[(f->loc++)]; + return l; }; -SHORT get_signed_pair(sfnt* f){ - long l; - test_loc(2); - l = f->buffer[(f->loc++)]; - if (l>0x80) l -= 0x100; - l = l*0x100 + f->buffer[(f->loc++)]; - return l; +SHORT get_signed_pair(sfnt * f) +{ + long l; + test_loc(2); + l = f->buffer[(f->loc++)]; + if (l > 0x80) + l -= 0x100; + l = l * 0x100 + f->buffer[(f->loc++)]; + return l; }; -ULONG get_unsigned_quad(sfnt* f){ - ULONG l; - test_loc(4); - l = f->buffer[(f->loc++)]; - l = l*0x100 + f->buffer[(f->loc++)]; - l = l*0x100 + f->buffer[(f->loc++)]; - l = l*0x100 + f->buffer[(f->loc++)]; - return l; +ULONG get_unsigned_quad(sfnt * f) +{ + ULONG l; + test_loc(4); + l = f->buffer[(f->loc++)]; + l = l * 0x100 + f->buffer[(f->loc++)]; + l = l * 0x100 + f->buffer[(f->loc++)]; + l = l * 0x100 + f->buffer[(f->loc++)]; + return l; }; -int do_sfnt_read (unsigned char *dest, int len, sfnt *f) { - int i; - test_loc(len); - for (i=0;i<len;i++) { - *(dest+i)=f->buffer[f->loc+i]; - } - f->loc += len; - return len; +int do_sfnt_read(unsigned char *dest, int len, sfnt * f) +{ + int i; + test_loc(len); + for (i = 0; i < len; i++) { + *(dest + i) = f->buffer[f->loc + i]; + } + f->loc += len; + return len; }; -pdf_obj *pdf_new_stream(void) { - pdf_obj *stream = xmalloc(sizeof(pdf_obj)) ; - stream->length =0; - stream->data=NULL; - return stream; +pdf_obj *pdf_new_stream(void) +{ + pdf_obj *stream = xmalloc(sizeof(pdf_obj)); + stream->length = 0; + stream->data = NULL; + return stream; }; -void pdf_add_stream(pdf_obj *stream, unsigned char *buf, long len) { - int i; - assert (stream!=NULL); - if (stream->data==NULL) { - stream->data = xmalloc(len); - } else { - stream->data = xrealloc(stream->data,len+stream->length); - } - for (i=0;i<len;i++) { - *(stream->data+stream->length+i)=*(buf+i); - } - stream->length+=len; +void pdf_add_stream(pdf_obj * stream, unsigned char *buf, long len) +{ + int i; + assert(stream != NULL); + if (stream->data == NULL) { + stream->data = xmalloc(len); + } else { + stream->data = xrealloc(stream->data, len + stream->length); + } + for (i = 0; i < len; i++) { + *(stream->data + stream->length + i) = *(buf + i); + } + stream->length += len; }; -void pdf_release_obj(pdf_obj *stream) { - if (stream!=NULL) { - if (stream->data!=NULL) { - xfree(stream->data); +void pdf_release_obj(pdf_obj * stream) +{ + if (stream != NULL) { + if (stream->data != NULL) { + xfree(stream->data); + } + xfree(stream); } - xfree(stream); - } }; -void -writetype2 (fd_entry * fd) { - int callback_id; - int file_opened = 0; - char *ftemp = NULL; - - glyph_tab = NULL; - - fd_cur = fd; /* fd_cur is global inside writettf.c */ - assert(fd_cur->fm != NULL); - assert(is_truetype(fd_cur->fm)); - - if (!is_subsetted(fd_cur->fm)) { - writettf(fd); - return; - } - - assert(is_included(fd_cur->fm)); - - set_cur_file_name(fd_cur->fm->ff_name); - ttf_curbyte=0; - ttf_size=0; - callback_id=callback_defined(find_opentype_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->S",(char *)(nameoffile+1),&ftemp)) { - if(ftemp!=NULL&&strlen(ftemp)) { - free(nameoffile); - namelength = strlen(ftemp); - nameoffile = xmalloc(namelength+2); - strcpy((char *)(nameoffile+1),ftemp); - free(ftemp); - } +void writetype2(fd_entry * fd) +{ + int callback_id; + int file_opened = 0; + char *ftemp = NULL; + + glyph_tab = NULL; + + fd_cur = fd; /* fd_cur is global inside writettf.c */ + assert(fd_cur->fm != NULL); + assert(is_truetype(fd_cur->fm)); + + if (!is_subsetted(fd_cur->fm)) { + writettf(fd); + return; } - } - callback_id=callback_defined(read_opentype_file_callback); - if (callback_id>0) { - if(run_callback(callback_id,"S->bSd",(char *)(nameoffile+1), - &file_opened, &ttf_buffer,&ttf_size) && - file_opened && ttf_size>0) { + + assert(is_included(fd_cur->fm)); + + set_cur_file_name(fd_cur->fm->ff_name); + ttf_curbyte = 0; + ttf_size = 0; + callback_id = callback_defined(find_opentype_file_callback); + if (callback_id > 0) { + if (run_callback + (callback_id, "S->S", (char *) (nameoffile + 1), &ftemp)) { + if (ftemp != NULL && strlen(ftemp)) { + free(nameoffile); + namelength = strlen(ftemp); + nameoffile = xmalloc(namelength + 2); + strcpy((char *) (nameoffile + 1), ftemp); + free(ftemp); + } + } + } + callback_id = callback_defined(read_opentype_file_callback); + if (callback_id > 0) { + if (run_callback(callback_id, "S->bSd", (char *) (nameoffile + 1), + &file_opened, &ttf_buffer, &ttf_size) && + file_opened && ttf_size > 0) { + } else { + pdftex_fail("cannot open OpenType font file for reading"); + } } else { - pdftex_fail ("cannot open OpenType font file for reading"); + if (!otf_open()) { + pdftex_fail("cannot open OpenType font file for reading"); + } + ttf_read_file(); + ttf_close(); } - } else { - if (!otf_open ()) { - pdftex_fail ("cannot open OpenType font file for reading"); + + cur_file_name = (char *) nameoffile + 1; + fd_cur->ff_found = true; + + if (tracefilenames) { + if (is_subsetted(fd_cur->fm)) + tex_printf("<%s", cur_file_name); + else + tex_printf("<<%s", cur_file_name); } - ttf_read_file(); - ttf_close(); - } - - cur_file_name = (char *) nameoffile + 1; - fd_cur->ff_found = true; - - if (tracefilenames) { - if (is_subsetted(fd_cur->fm)) - tex_printf ("<%s", cur_file_name); - else - tex_printf ("<<%s", cur_file_name); - } - /* here is the real work */ + /* here is the real work */ - make_tt_subset(fd,ttf_buffer,ttf_size); + make_tt_subset(fd, ttf_buffer, ttf_size); - /*xfree (dir_tab);*/ - if (tracefilenames) { - if (is_subsetted (fd_cur->fm)) - tex_printf (">"); - else - tex_printf (">>"); - } - cur_file_name = NULL; + /*xfree (dir_tab); */ + xfree(ttf_buffer); + if (tracefilenames) { + if (is_subsetted(fd_cur->fm)) + tex_printf(">"); + else + tex_printf(">>"); + } + cur_file_name = NULL; } /* @@ -216,207 +227,216 @@ writetype2 (fd_entry * fd) { * The 'name' table added. See comments in ttf.c. */ -static struct -{ - const char *name; - int must_exist; +static struct { + const char *name; + int must_exist; } required_table[] = { - {"OS/2", 0}, {"head", 1}, {"hhea", 1}, {"loca", 1}, {"maxp", 1}, - {"name", 1}, {"glyf", 1}, {"hmtx", 1}, {"fpgm", 0}, {"cvt ", 0}, - {"prep", 0}, {NULL, 0} + { + "OS/2", 0}, { + "cmap", 0}, { + "head", 1}, { + "hhea", 1}, { + "loca", 1}, { + "maxp", 1}, { + "name", 1}, { + "glyf", 1}, { + "hmtx", 1}, { + "fpgm", 0}, { + "cvt ", 0}, { + "prep", 0}, { + NULL, 0} }; -unsigned long ttc_read_offset (sfnt *sfont, int ttc_idx) +unsigned long ttc_read_offset(sfnt * sfont, int ttc_idx) { - long version; - unsigned long offset = 0; - unsigned long num_dirs = 0; + long version; + unsigned long offset = 0; + unsigned long num_dirs = 0; - sfnt_seek_set (sfont, 4); /* skip version tag */ + sfnt_seek_set(sfont, 4); /* skip version tag */ - version = sfnt_get_ulong(sfont); - num_dirs = sfnt_get_ulong(sfont); - if (ttc_idx < 0 || ttc_idx > num_dirs - 1) { - fprintf(stderr,"Invalid TTC index number\n"); - uexit(1); - } + version = sfnt_get_ulong(sfont); + num_dirs = sfnt_get_ulong(sfont); + if (ttc_idx < 0 || ttc_idx > (int) (num_dirs - 1)) { + fprintf(stderr, "Invalid TTC index number\n"); + uexit(1); + } - sfnt_seek_set (sfont, 12 + ttc_idx * 4); - offset = sfnt_get_ulong (sfont); + sfnt_seek_set(sfont, 12 + ttc_idx * 4); + offset = sfnt_get_ulong(sfont); - return offset; + return offset; } -extern int ff_get_ttc_index(char *ffname, char*psname); - -void make_tt_subset (fd_entry * fd,unsigned char *buffer, integer buflen) { - - long i, cid; - unsigned int last_cid; - glw_entry *glyph, *found; - struct avl_traverser t; - unsigned char *cidtogidmap ; - unsigned short num_glyphs, gid; - struct tt_glyphs *glyphs; - char *used_chars; - sfnt *sfont; - pdf_obj *fontfile; - int verbose = 0, error = 0; - - cidtogidmap = NULL; - - sfont = sfnt_open(buffer, buflen); - - if (sfont->type == SFNT_TYPE_TTC) { - i = ff_get_ttc_index(fd->fm->ff_name,fd->fm->ps_name); - error = sfnt_read_table_directory(sfont, ttc_read_offset(sfont, i)); - } else { - error = sfnt_read_table_directory(sfont, 0); - } +extern int ff_get_ttc_index(char *ffname, char *psname); /* libs/luafontforge/src/luafflib.c */ - if (error < 0) { - fprintf(stderr,"Could not parse the ttf directory.\n"); - uexit(1); - } +void make_tt_subset(fd_entry * fd, unsigned char *buffer, integer buflen) +{ + + long i, cid; + unsigned int last_cid; + glw_entry *found; + struct avl_traverser t; + unsigned char *cidtogidmap; + unsigned short num_glyphs, gid; + struct tt_glyphs *glyphs; + char *used_chars; + sfnt *sfont; + pdf_obj *fontfile; + int verbose = 0, error = 0; + + cidtogidmap = NULL; + + sfont = sfnt_open(buffer, buflen); + + if (sfont->type == SFNT_TYPE_TTC) { + i = ff_get_ttc_index(fd->fm->ff_name, fd->fm->ps_name); + error = sfnt_read_table_directory(sfont, ttc_read_offset(sfont, i)); + } else { + error = sfnt_read_table_directory(sfont, 0); + } - glyphs = tt_build_init(); + if (error < 0) { + fprintf(stderr, "Could not parse the ttf directory.\n"); + uexit(1); + } - last_cid = 0; - num_glyphs = 1; /* .notdef */ + glyphs = tt_build_init(); - glyph = xtalloc(1,glw_entry); + last_cid = 0; + + avl_t_init(&t, fd->gl_tree); + for (found = (glw_entry *) avl_t_first(&t, fd->gl_tree); + found != NULL; found = (glw_entry *) avl_t_next(&t)) { + if (found->id > last_cid) + last_cid = found->id; + } - avl_t_init(&t, fd->gl_tree); - for (found = (glw_entry *) avl_t_first(&t, fd->gl_tree); - found != NULL; - found = (glw_entry *) avl_t_next(&t)) { - if (found->id > last_cid) - last_cid = found->id; - } - #ifndef NO_GHOSTSCRIPT_BUG - cidtogidmap = NULL; + cidtogidmap = NULL; #else - cidtogidmap = xmalloc(((last_cid + 1) * 2) * sizeof(unsigned char)); - memset(cidtogidmap, 0, (last_cid + 1) * 2); + cidtogidmap = xmalloc(((last_cid + 1) * 2) * sizeof(unsigned char)); + memset(cidtogidmap, 0, (last_cid + 1) * 2); #endif - /* fill used_chars */ - used_chars = xmalloc((last_cid + 1) * sizeof(char)); - memset(used_chars, 0, (last_cid + 1)); - avl_t_init(&t, fd->gl_tree); - for (found = (glw_entry *) avl_t_first(&t, fd->gl_tree); - found != NULL; - found = (glw_entry *) avl_t_next(&t)) { - used_chars[found->id] = 1; - } + /* fill used_chars */ + used_chars = xmalloc((last_cid + 1) * sizeof(char)); + memset(used_chars, 0, (last_cid + 1)); + avl_t_init(&t, fd->gl_tree); + for (found = (glw_entry *) avl_t_first(&t, fd->gl_tree); + found != NULL; found = (glw_entry *) avl_t_next(&t)) { + used_chars[found->id] = 1; + } - /* - * Map CIDs to GIDs. - */ + /* + * Map CIDs to GIDs. + */ - num_glyphs = 1; /* .notdef */ - for (cid = 1; cid <= last_cid; cid++) { - if (used_chars[cid]==0) - continue; - gid = cid; + num_glyphs = 1; /* .notdef */ + for (cid = 1; cid <= (long) last_cid; cid++) { + if (used_chars[cid] == 0) + continue; + gid = cid; #ifndef NO_GHOSTSCRIPT_BUG - gid = tt_add_glyph(glyphs, gid, cid); + gid = tt_add_glyph(glyphs, gid, cid); #else - gid = tt_add_glyph(glyphs, gid, num_glyphs); - cidtogidmap[2*cid ] = gid >> 8; - cidtogidmap[2*cid+1] = gid & 0xff; -#endif /* !NO_GHOSTSCRIPT_BUG */ - - num_glyphs++; - } + gid = tt_add_glyph(glyphs, gid, num_glyphs); + cidtogidmap[2 * cid] = gid >> 8; + cidtogidmap[2 * cid + 1] = gid & 0xff; +#endif /* !NO_GHOSTSCRIPT_BUG */ - if (num_glyphs==1) { - fprintf(stderr,"No glyphs in subset?.\n"); - uexit(1); - } + num_glyphs++; + } - if (tt_build_tables(sfont, glyphs) < 0) { - fprintf(stderr,"Could not parse the ttf buffer.\n"); - uexit(1); - } - - if (verbose > 1) { - fprintf(stdout,"[%u glyphs (Max CID: %u)]", glyphs->num_glyphs, last_cid); - } + if (num_glyphs == 1) { + fprintf(stderr, "No glyphs in subset?.\n"); + uexit(1); + } - tt_build_finish(glyphs); + if (tt_build_tables(sfont, glyphs) < 0) { + fprintf(stderr, "Could not parse the ttf buffer.\n"); + uexit(1); + } - /* Create font file */ + if (verbose > 1) { + fprintf(stdout, "[%u glyphs (Max CID: %u)]", glyphs->num_glyphs, + last_cid); + } - for (i = 0; required_table[i].name; i++) { - if (sfnt_require_table(sfont, - required_table[i].name, - required_table[i].must_exist) < 0) { - fprintf(stderr,"Some required TrueType table does not exist."); - uexit(1); + tt_build_finish(glyphs); + + /* Create font file */ + + for (i = 0; required_table[i].name; i++) { + if (sfnt_require_table(sfont, + required_table[i].name, + required_table[i].must_exist) < 0) { + fprintf(stderr, "Some required TrueType table does not exist."); + uexit(1); + } } - } - fontfile = sfnt_create_FontFile_stream(sfont); + fontfile = sfnt_create_FontFile_stream(sfont); - if (verbose > 1) { - fprintf(stdout,"[%ld bytes]", fontfile->length); - } + if (verbose > 1) { + fprintf(stdout, "[%ld bytes]", fontfile->length); + } - /* squeeze in the cidgidmap */ - if (cidtogidmap!=NULL) { - cidtogid_obj = pdf_new_objnum(); - pdf_begin_dict(cidtogid_obj, 0); - pdf_printf("/Length %i\n",((last_cid + 1) * 2)); - pdf_end_dict(); - pdf_printf("stream\n"); - pdfroom ((last_cid + 1) * 2); - for (i = 0; i<((last_cid + 1) * 2); i++ ) { - pdf_buf[pdf_ptr++] = cidtogidmap[i]; + /* squeeze in the cidgidmap */ + if (cidtogidmap != NULL) { + cidtogid_obj = pdf_new_objnum(); + pdf_begin_dict(cidtogid_obj, 0); + pdf_printf("/Length %i\n", ((last_cid + 1) * 2)); + pdf_end_dict(); + pdf_printf("stream\n"); + pdfroom((last_cid + 1) * 2); + for (i = 0; i < ((int) (last_cid + 1) * 2); i++) { + pdf_buf[pdf_ptr++] = cidtogidmap[i]; + } + pdf_printf("\nendstream\n"); } - pdf_printf("\nendstream\n"); - } - /* the tff subset */ - for (i = 0; i<fontfile->length; i++ ) - fb_putchar (fontfile->data[i]); - - - /* other stuff that needs fixing: */ - - /* - * DW, W, DW2, and W2 - */ - /* - if (opt_flags & CIDFONT_FORCE_FIXEDPITCH) { - pdf_add_dict(font->fontdict, - pdf_new_name("DW"), pdf_new_number(1000.0)); - } else { - add_TTCIDHMetrics(font->fontdict, glyphs, used_chars, cidtogidmap, last_cid); - if (v_used_chars) - add_TTCIDVMetrics(font->fontdict, glyphs, used_chars, cidtogidmap, last_cid); - } - */ - - /* - * CIDSet - */ - /* - { - pdf_obj *cidset; - - cidset = pdf_new_stream(STREAM_COMPRESS); - pdf_add_stream(cidset, used_chars, last_cid/8 + 1); - pdf_add_dict(font->descriptor, - pdf_new_name("CIDSet"), - pdf_ref_obj(cidset)); - pdf_release_obj(cidset); - } - */ + /* the tff subset */ + for (i = 0; i < (int) (fontfile->length); i++) + fb_putchar(fontfile->data[i]); - return; + pdf_release_obj(fontfile); + + /* other stuff that needs fixing: */ + + /* + * DW, W, DW2, and W2 + */ + /* + if (opt_flags & CIDFONT_FORCE_FIXEDPITCH) { + pdf_add_dict(font->fontdict, + pdf_new_name("DW"), pdf_new_number(1000.0)); + } else { + add_TTCIDHMetrics(font->fontdict, glyphs, used_chars, cidtogidmap, last_cid); + if (v_used_chars) + add_TTCIDVMetrics(font->fontdict, glyphs, used_chars, cidtogidmap, last_cid); + } + */ + + /* + * CIDSet + */ + /* + { + pdf_obj *cidset; + + cidset = pdf_new_stream(STREAM_COMPRESS); + pdf_add_stream(cidset, used_chars, last_cid/8 + 1); + pdf_add_dict(font->descriptor, + pdf_new_name("CIDSet"), + pdf_ref_obj(cidset)); + pdf_release_obj(cidset); + } + */ + xfree(used_chars); + sfnt_close(sfont); + return; } |