82 #define MATCH(A,B) (strncmp((A),(B), MAX_NAME) == 0)
88 static char *ident = NULL;
107 ASCENDER, CHARBBOX, CODE, COMPCHAR, CAPHEIGHT, COMMENT,
108 DESCENDER, ENCODINGSCHEME, ENDCHARMETRICS, ENDCOMPOSITES,
109 ENDFONTMETRICS, ENDKERNDATA, ENDKERNPAIRS, ENDTRACKKERN,
110 FAMILYNAME, FONTBBOX, FONTNAME, FULLNAME, ISFIXEDPITCH,
111 ITALICANGLE, KERNPAIR, KERNPAIRXAMT, LIGATURE, CHARNAME,
112 NOTICE, COMPCHARPIECE, STARTCHARMETRICS, STARTCOMPOSITES,
113 STARTFONTMETRICS, STARTKERNDATA, STARTKERNPAIRS,
114 STARTTRACKKERN, TRACKKERN, UNDERLINEPOSITION,
115 UNDERLINETHICKNESS, VERSION, XYWIDTH, XWIDTH, WEIGHT, XHEIGHT,
131 static char *keyStrings[] = {
132 "Ascender",
"B",
"C",
"CC",
"CapHeight",
"Comment",
133 "Descender",
"EncodingScheme",
"EndCharMetrics",
"EndComposites",
134 "EndFontMetrics",
"EndKernData",
"EndKernPairs",
"EndTrackKern",
135 "FamilyName",
"FontBBox",
"FontName",
"FullName",
"IsFixedPitch",
136 "ItalicAngle",
"KP",
"KPX",
"L",
"N",
137 "Notice",
"PCC",
"StartCharMetrics",
"StartComposites",
138 "StartFontMetrics",
"StartKernData",
"StartKernPairs",
139 "StartTrackKern",
"TrackKern",
"UnderlinePosition",
140 "UnderlineThickness",
"Version",
"W",
"WX",
"Weight",
"XHeight",
153 static char *token(FILE *stream)
158 while ((ch = fgetc(stream)) ==
' ' || ch == lineterm ||
159 ch ==
',' || ch ==
'\t' || ch ==
';');
162 while (ch != EOF && ch !=
' ' && ch != lineterm
163 && ch !=
'\t' && ch !=
':' && ch !=
';' && idx < (
MAX_NAME - 1))
169 if (ch == EOF && idx < 1)
return ((
char *)NULL);
170 if (idx >= 1 && ch !=
':' ) ungetc(ch, stream);
171 if (idx < 1 ) ident[idx++] = ch;
186 static char *linetoken(FILE *stream)
190 while ((ch = fgetc(stream)) ==
' ' || ch ==
'\t' );
193 while (ch != EOF && ch != lineterm && idx < (
MAX_NAME - 1))
217 static enum parseKey recognize(
char *ident)
219 int lower = 0, upper = (int) NOPE, midpoint, cmpvalue;
222 while ((upper >= lower) && !found)
224 midpoint = (lower + upper)/2;
225 if (keyStrings[midpoint] == NULL)
break;
226 cmpvalue = strncmp(ident, keyStrings[midpoint],
MAX_NAME);
227 if (cmpvalue == 0) found =
TRUE;
228 else if (cmpvalue < 0) upper = midpoint - 1;
229 else lower = midpoint + 1;
232 if (found)
return (
enum parseKey) midpoint;
261 BOOL cont =
TRUE, save = (gfi != NULL);
263 register char *keyword;
279 switch (recognize(keyword))
281 case STARTCHARMETRICS:
294 switch(recognize(keyword))
296 case STARTFONTMETRICS:
298 gfi->
afmVersion = (
char *) malloc(strlen(keyword) + 1);
302 keyword = linetoken(fp);
306 gfi->
fontName = (
char *) malloc(strlen(keyword) + 1);
312 malloc(strlen(keyword) + 1);
316 keyword = linetoken(fp);
317 gfi->
fullName = (
char *) malloc(strlen(keyword) + 1);
321 keyword = linetoken(fp);
322 gfi->
familyName = (
char *) malloc(strlen(keyword) + 1);
327 gfi->
weight = (
char *) malloc(strlen(keyword) + 1);
328 strcpy(gfi->
weight, keyword);
337 if (MATCH(keyword,
False))
342 case UNDERLINEPOSITION:
346 case UNDERLINETHICKNESS:
352 gfi->
version = (
char *) malloc(strlen(keyword) + 1);
356 keyword = linetoken(fp);
357 gfi->
notice = (
char *) malloc(strlen(keyword) + 1);
358 strcpy(gfi->
notice, keyword);
386 case STARTCHARMETRICS:
425 static int initializeArray(FILE *fp,
int *cwi)
428 long opos = ftell(fp);
429 int code = 0, width = 0, i = 0, error = 0;
430 register char *keyword;
440 switch(recognize(keyword))
443 keyword = linetoken(fp);
446 code = atoi(token(fp));
449 width = atoi(token(fp));
453 if (MATCH(keyword, Space))
476 for (i = 0; i < 256; ++i)
506 static int parseCharWidths(FILE *fp,
int *cwi)
508 BOOL cont =
TRUE, save = (cwi != NULL);
509 int pos = 0, error =
ok;
510 register char *keyword;
525 switch (recognize(keyword))
540 switch(recognize(keyword))
543 keyword = linetoken(fp);
551 keyword = token(fp); keyword = token(fp);
557 cwi[pos] = atoi(keyword);
570 keyword = token(fp); keyword = token(fp);
571 keyword = token(fp); keyword = token(fp);
574 keyword = token(fp); keyword = token(fp);
605 static int parseCharMetrics(FILE *fp,
FontInfo *fi)
608 int error =
ok, count = 0;
610 register char *keyword;
620 switch(recognize(keyword))
623 keyword = linetoken(fp);
626 if (count < fi->numOfChars)
628 if (firstTime) firstTime =
FALSE;
630 temp->
code = atoi(token(fp));
640 temp->
wx = atoi(token(fp));
641 temp->
wy = atoi(token(fp));
644 temp->
wx = atoi(token(fp));
648 temp->
name = (
char *) malloc(strlen(keyword) + 1);
649 strcpy(temp->
name, keyword);
663 while (node->
next != NULL)
665 tail = &(node->
next);
670 (*tail)->succ = (
char *) malloc(strlen(keyword) + 1);
671 strcpy((*tail)->succ, keyword);
673 (*tail)->lig = (
char *) malloc(strlen(keyword) + 1);
674 strcpy((*tail)->lig, keyword);
714 static int parseTrackKernData(FILE *fp,
FontInfo *fi)
717 int pos = 0, error =
ok, tcount = 0;
718 register char *keyword;
732 switch(recognize(keyword))
748 switch(recognize(keyword))
751 keyword = linetoken(fp);
754 if (tcount < fi->numOfTracks)
816 static int parsePairKernData(FILE *fp,
FontInfo *fi)
819 int pos = 0, error =
ok, pcount = 0;
820 register char *keyword;
834 switch(recognize(keyword))
850 switch(recognize(keyword))
853 keyword = linetoken(fp);
856 if (pcount < fi->numOfPairs)
860 malloc(strlen(keyword) + 1);
861 strcpy(fi->
pkd[pos].
name1, keyword);
864 malloc(strlen(keyword) + 1);
865 strcpy(fi->
pkd[pos].
name2, keyword);
867 fi->
pkd[pos].
xamt = atoi(keyword);
869 fi->
pkd[pos++].
yamt = atoi(keyword);
879 if (pcount < fi->numOfPairs)
883 malloc(strlen(keyword) + 1);
884 strcpy(fi->
pkd[pos].
name1, keyword);
887 malloc(strlen(keyword) + 1);
888 strcpy(fi->
pkd[pos].
name2, keyword);
890 fi->
pkd[pos++].
xamt = atoi(keyword);
940 static int parseCompCharData(FILE *fp,
FontInfo *fi)
943 int pos = 0, j = 0, error =
ok, ccount = 0, pcount = 0;
944 register char *keyword;
964 switch(recognize(keyword))
979 switch(recognize(keyword))
982 keyword = linetoken(fp);
985 if (ccount < fi->numOfComps)
991 if (firstTime) firstTime =
FALSE;
994 malloc(strlen(keyword) + 1);
1010 if (pcount < fi->ccd[pos].numOfPieces)
1012 keyword = token(fp);
1014 malloc(strlen(keyword) + 1);
1016 keyword = token(fp);
1018 keyword = token(fp);
1028 case ENDFONTMETRICS:
1073 extern int afm_parse_file(FILE *fp,
FontInfo **fi,
FLAGS flags)
1079 register char *keyword;
1083 ident = (
char *) calloc(
MAX_NAME,
sizeof(
char));
1097 code = parseGlobals(fp, (*fi)->gfi);
1099 if (code < 0) error = code;
1109 if ((code != normalEOF) && (code !=
earlyEOF))
1111 (*fi)->numOfChars = atoi(token(fp));
1117 code = parseCharMetrics(fp, *fi);
1123 (*fi)->cwi = (
int *) calloc(256,
sizeof(
int));
1124 if ((*fi)->cwi == NULL)
1131 code = parseCharWidths(fp, (*fi)->cwi);
1135 if ((error !=
earlyEOF) && (code < 0)) error = code;
1143 while ((code != normalEOF) && (code !=
earlyEOF))
1145 keyword = token(fp);
1146 if (keyword == NULL)
1153 switch(recognize(keyword))
1159 case STARTTRACKKERN:
1160 keyword = token(fp);
1163 (*fi)->numOfTracks = atoi(keyword);
1166 if ((*fi)->tkd == NULL)
1172 code = parseTrackKernData(fp, *fi);
1174 case STARTKERNPAIRS:
1175 keyword = token(fp);
1178 (*fi)->numOfPairs = atoi(keyword);
1181 if ((*fi)->pkd == NULL)
1187 code = parsePairKernData(fp, *fi);
1189 case STARTCOMPOSITES:
1190 keyword = token(fp);
1193 (*fi)->numOfComps = atoi(keyword);
1196 if ((*fi)->ccd == NULL)
1202 code = parseCompCharData(fp, *fi);
1204 case ENDFONTMETRICS:
1213 if ((error !=
earlyEOF) && (code < 0)) error = code;
1217 if ((error !=
earlyEOF) && (code < 0)) error = code;
1219 if (ident != NULL) { free(ident); ident = NULL; }
1227 void afm_free_fontinfo(
FontInfo *fi)
1231 if (fi->
gfi != NULL)
1241 free(fi->
gfi); fi->
gfi = NULL;
1244 if (fi->
cwi != NULL)
1245 { free(fi->
cwi); fi->
cwi = NULL; }
1247 if (fi->
cmi != NULL)
1255 for (node = temp->
ligs; node != NULL; node = node->
next)
1257 free(node->
succ); node->
succ = NULL;
1258 free(node->
lig); node->
lig = NULL;
1261 free(temp->
name); temp->
name = NULL;
1265 free(fi->
cmi); fi->
cmi = NULL;
1268 if (fi->
tkd != NULL)
1269 { free(fi->
tkd); fi->
tkd = NULL; }
1271 if (fi->
pkd != NULL)
1275 free(fi->
pkd); fi->
pkd = NULL;
1278 if (fi->
ccd != NULL)
1287 free(ccd[i].pieces[j].pccName);
1291 free(ccd[i].ccName); ccd[i].
ccName = NULL;
1294 free(fi->
ccd); fi->
ccd = NULL;