otfdump_SOURCE = otfdump.c
otfdump_LDADD = ${CommonLDADD}
-otfdump_LDFLAGS = ${CommonLDFLAGS}
+otfdump_LDFLAGS = ${CommonLDFLAGS} -lefence
otfdraw_SOURCE = otfdraw
otfdraw_LDADD = ${CommonLDADD}
otf = otf_open (argv[1]);
if (! otf)
- otf_perror ("otfdraw:");
+ otf_perror ("otfdraw:", 1);
gstring.size = 10;
gstring.glyphs = (OTF_Glyph *) malloc (sizeof (OTF_Glyph) * 30);
memset (gstring.glyphs, 0, sizeof (OTF_Glyph) * 30);
#include <sys/stat.h>
#include <fcntl.h>
+extern int EF_ALIGNMENT;
+extern int EF_PROTECT_BELOW;
+extern int EF_PROTECT_FREE;
+
#include <otf.h>
char *indent_spaces[] =
int i;
printf ("(OTF");
+
dump_offset_table (1, &otf->offset_table);
for (i = 0; i < otf->offset_table.numTables; i++)
dump_table_directory (1, otf->table_dirs + i, i);
- dump_head_table (1, (OTF_head *) otf_get_table (otf, otf_tag ("head")));
- dump_name_table (1, (OTF_name *) otf_get_table (otf, otf_tag ("name")));
- dump_cmap_table (1, (OTF_cmap *) otf_get_table (otf, otf_tag ("cmap")));
- dump_gdef_table (1, (OTF_GDEF *) otf_get_table (otf, otf_tag ("GDEF")));
- dump_gsub_table (1, (OTF_GSUB *) otf_get_table (otf, otf_tag ("GSUB")));
- dump_gpos_table (1, (OTF_GPOS *) otf_get_table (otf, otf_tag ("GPOS")));
+
+ if (otf->head)
+ dump_head_table (1, otf->head);
+ if (otf->name)
+ dump_name_table (1, otf->name);
+ if (otf->cmap)
+ dump_cmap_table (1, otf->cmap);
+ if (otf->gdef)
+ dump_gdef_table (1, otf->gdef);
+ if (otf->gsub)
+ dump_gsub_table (1, otf->gsub);
+ if (otf->gpos)
+ dump_gpos_table (1, otf->gpos);
#if 0
- dump_base_table (1, (OTF_BASE *) otf_get_table (otf, otf_tag ("BASE")));
- dump_jstf_table (1, (OTF_JSTF *) otf_get_table (otf, otf_tag ("JSTF")));
+ if (otf->base)
+ dump_base_table (1, otf->base);
+ if (otf->jstf)
+ dump_jstf_table (1, otf->jstf);
#endif
printf (")\n");
}
{
OTF *otf;
+ EF_ALIGNMENT = 1;
+ EF_PROTECT_BELOW = 1;
+ EF_PROTECT_FREE = 1;
+
if (argc != 2)
{
fprintf (stderr, "Usage, dtfdump OTF-FILE");
}
otf = otf_open (argv[1]);
- otf_get_table (otf, otf_tag ("head"));
- otf_get_table (otf, otf_tag ("name"));
- otf_get_table (otf, otf_tag ("cmap"));
- otf_get_table (otf, otf_tag ("GDEF"));
- otf_get_table (otf, otf_tag ("GSUB"));
- otf_get_table (otf, otf_tag ("GPOS"));
+ if (! otf)
+ otf_perror ("otfdump: ", 1);
+ otf_get_table (otf, "head");
+ otf_get_table (otf, "name");
+ otf_get_table (otf, "cmap");
+ otf_get_table (otf, "GDEF");
+ otf_get_table (otf, "GSUB");
+ otf_get_table (otf, "GPOS");
+#if 0
+ otf_get_table (otf, "BASE");
+ otf_get_table (otf, "JSTF");
+#endif
otf_dump (otf);
otf_close (otf);
exit (0);
+#ifndef _OTF_H_
+#define _OTF_H_
+
/***
@file otf.h
@brief This file defines APIs for the OTF library.
- The @e OTF @e library is for reading and processing OpenType font
- tables. It can handle the tables of the following names.a
+ The @e OTF @e library is for reading and driving OpenType font
+ tables. It can handle the tables of the following names.
@li @e head:
*/
-#ifndef _OTF_H_
-#define _OTF_H_
////
the standard output according to the value of otf_error. If this
variable is zero, do nothing. */
-extern void otf_perror (char *prefix);
+extern void otf_perror (char *prefix, int exit_code);
/*** Macros for error codes. */
extern OTF *otf_open (char *name);
extern void otf_close (OTF *otf);
-extern int otf_get_table (OTF *otf, OTF_Tag tag);
+extern int otf_get_table (OTF *otf, char *name);
extern int otf_drive_cmap (OTF *otf, OTF_GlyphString *gstring);
extern int otf_drive_gdef (OTF *otf, OTF_GlyphString *gstring);
return gidx;
}
-int
-otf_drive_gsub (OTF *otf, OTF_Tag script_tag, OTF_Tag langsys_tag,
- OTF_GlyphString *gstring)
-{
- OTF_GSUB *gsub = (OTF_GSUB *) otf->gsub->table;
- OTF_LangSys *langsys;
- int i, j;
-
- if (! gsub)
- gsub = (OTF_GSUB *) otf_get_table (otf, otf_tag ("GSUB"));
- if (! gsub)
- return -1;
- langsys = get_langsys (&gsub->ScriptList, script_tag, langsys_tag);
- if (! langsys)
- return -1;
-
- for (i = 0; i < langsys->FeatureCount; i++)
- {
- OTF_Feature *feature
- = gsub->FeatureList.Feature + langsys->FeatureIndex[i];
-
- for (j = 0; j < feature->LookupCount; j++)
- {
- int gidx = 0;
-
- while (gidx < gstring->used)
- gidx = lookup_gsub (&gsub->LookupList, feature->LookupListIndex[j],
- gstring, gidx);
- }
- }
-
- return 0;
-}
-
\f
/* GPOS */
return gidx;
}
-int
-otf_drive_gpos (OTF *otf, OTF_Tag script_tag, OTF_Tag langsys_tag,
- OTF_GlyphString *gstring)
+static int
+lookup_cmap (OTF_cmap *cmap, int c)
{
- OTF_GPOS *gpos = (OTF_GPOS *) otf->gpos->table;
- OTF_LangSys *langsys;
- int i, j;
+ int i;
- if (! gpos)
- gpos = (OTF_GPOS *) otf_get_table (otf, otf_tag ("GPOS"));
- if (! gpos)
- return -1;
- langsys = get_langsys (&gpos->ScriptList, script_tag, langsys_tag);
- if (! langsys)
- return -1;
+ if (! cmap || ! cmap->Unicode)
+ return 0;
- for (i = 0; i < langsys->FeatureCount; i++)
+ switch (cmap->Unicode->subtable.format)
{
- OTF_Feature *feature
- = gpos->FeatureList.Feature + langsys->FeatureIndex[i];
+ case 0:
+ break;
- for (j = 0; j < feature->LookupCount; j++)
- {
- int gidx = 0;
+ case 4:
+ {
+ OTF_EncodingSubtable4 *sub4 = cmap->Unicode->subtable.f.f4;
+ int segCount = sub4->segCountX2 / 2;
- while (gidx < gstring->used)
- gidx = lookup_gpos (&gpos->LookupList, feature->LookupListIndex[j],
- gstring, gidx);
- }
+ for (i = 0; i < segCount; i++)
+ if (c <= sub4->segments[i].endCount)
+ break;
+ if (i == segCount || c < sub4->segments[i].startCount)
+ return 0;
+ if (sub4->segments[i].idRangeOffset == 0xFFFF)
+ return c + sub4->segments[i].idDelta;
+ return sub4->glyphIdArray[sub4->segments[i].idRangeOffset
+ + (c - sub4->segments[i].startCount)];
+ }
+ break;
}
-
return 0;
}
+\f
+
+/* APIs */
+
+int
+otf_drive_cmap (OTF *otf, OTF_GlyphString *gstring)
+{
+ OTF_cmap *cmap;
+ int i;
+
+ if (! otf->cmap
+ && otf_get_table (otf, "cmap") < 0)
+ return -1;
+
+ cmap = otf->cmap;
+ for (i = 0; i < gstring->used; i++)
+ gstring->glyphs[i].glyph_id = lookup_cmap (cmap, gstring->glyphs[i].c);
+
+ return 0;
+}
int
otf_drive_gdef (OTF *otf, OTF_GlyphString *gstring)
{
+ OTF_GDEF *gdef;
int i;
- OTF_GDEF *gdef = (OTF_GDEF *) otf->gdef->table;
- if (! gdef)
- gdef = (OTF_GDEF *) otf_get_table (otf, otf_tag ("GDEF"));
- if (! gdef)
+ if (! otf->gdef
+ && otf_get_table (otf, "GDEF") < 0)
return -1;
+ gdef = otf->gdef;
if (gdef->glyph_class_def.offset)
for (i = 0; i < gstring->used; i++)
return 0;
}
+
int
-lookup_cmap (OTF_cmap *cmap, int c)
+otf_drive_gsub (OTF *otf, OTF_Tag script_tag, OTF_Tag langsys_tag,
+ OTF_GlyphString *gstring)
{
- int i;
+ OTF_GSUB *gsub;
+ OTF_LangSys *langsys;
+ int i, j;
- if (! cmap || ! cmap->Unicode)
- return 0;
+ if (! otf->gsub
+ && otf_get_table (otf, "GSUB") < 0)
+ return -1;
+ gsub = otf->gsub;
- switch (cmap->Unicode->subtable.format)
+ langsys = get_langsys (&gsub->ScriptList, script_tag, langsys_tag);
+ if (! langsys)
+ return -1;
+
+ for (i = 0; i < langsys->FeatureCount; i++)
{
- case 0:
- break;
+ OTF_Feature *feature
+ = gsub->FeatureList.Feature + langsys->FeatureIndex[i];
- case 4:
- {
- OTF_EncodingSubtable4 *sub4 = cmap->Unicode->subtable.f.f4;
- int segCount = sub4->segCountX2 / 2;
+ for (j = 0; j < feature->LookupCount; j++)
+ {
+ int gidx = 0;
- for (i = 0; i < segCount; i++)
- if (c <= sub4->segments[i].endCount)
- break;
- if (i == segCount || c < sub4->segments[i].startCount)
- return 0;
- if (sub4->segments[i].idRangeOffset == 0xFFFF)
- return c + sub4->segments[i].idDelta;
- return sub4->glyphIdArray[sub4->segments[i].idRangeOffset
- + (c - sub4->segments[i].startCount)];
- }
- break;
+ while (gidx < gstring->used)
+ gidx = lookup_gsub (&gsub->LookupList, feature->LookupListIndex[j],
+ gstring, gidx);
+ }
}
+
return 0;
}
int
-otf_drive_cmap (OTF *otf, OTF_GlyphString *gstring)
+otf_drive_gpos (OTF *otf, OTF_Tag script_tag, OTF_Tag langsys_tag,
+ OTF_GlyphString *gstring)
{
- OTF_cmap *cmap = (OTF_cmap *) otf->cmap->table;
- int i;
+ OTF_GPOS *gpos;
+ OTF_LangSys *langsys;
+ int i, j;
- if (! cmap)
- cmap = (OTF_cmap *) otf_get_table (otf, otf_tag ("cmap"));
- if (! cmap)
+ if (! otf->gpos
+ && otf_get_table (otf, "GPOS") < 0)
return -1;
+ gpos = otf->gpos;
- for (i = 0; i < gstring->used; i++)
- gstring->glyphs[i].glyph_id = lookup_cmap (cmap, gstring->glyphs[i].c);
+ langsys = get_langsys (&gpos->ScriptList, script_tag, langsys_tag);
+ if (! langsys)
+ return -1;
+
+ for (i = 0; i < langsys->FeatureCount; i++)
+ {
+ OTF_Feature *feature
+ = gpos->FeatureList.Feature + langsys->FeatureIndex[i];
+
+ for (j = 0; j < feature->LookupCount; j++)
+ {
+ int gidx = 0;
+
+ while (gidx < gstring->used)
+ gidx = lookup_gpos (&gpos->LookupList, feature->LookupListIndex[j],
+ gstring, gidx);
+ }
+ }
return 0;
}
};
-static int
+static OTF_MemoryRecord *
allocate_memory_record (OTF *otf)
{
OTF_InternalData *internal_data = (OTF_InternalData *) otf->internal_data;
- OTF_MemoryRecord *mem_rec = calloc (1, sizeof (OTF_MemoryRecord));
+ OTF_MemoryRecord *memrec = calloc (1, sizeof (OTF_MemoryRecord));
- if (! mem_rec)
- return -1;
- mem_rec->used = 0;
- mem_rec->next = internal_data->memory_record;
- internal_data->memory_record = mem_rec;
- return 0;
+ if (! memrec)
+ return NULL;
+ memrec->used = 0;
+ memrec->next = internal_data->memory_record;
+ internal_data->memory_record = memrec;
+ return memrec;
}
/* Memory allocation macros. */
-#define OTF_MALLOC(p, size, arg) \
- do { \
- (p) = malloc (sizeof (*(p)) * (size)); \
- if (! (p) \
- || ((((OTF_InternalData *) otf->internal_data)->memory_record->used \
- >= OTF_MEMORY_RECORD_SIZE) \
- && (allocate_memory_record (otf) < 0))) \
- OTF_ERROR (OTF_ERROR_MEMORY, (arg)); \
- ((OTF_InternalData *) otf->internal_data)->memory_record->memory \
- [((OTF_InternalData *) otf->internal_data)->memory_record->used++] \
- = (p); \
+#define OTF_MALLOC(p, size, arg) \
+ do { \
+ if (size == 0) \
+ (p) = NULL; \
+ else \
+ { \
+ OTF_MemoryRecord *memrec \
+ = ((OTF_InternalData *) otf->internal_data)->memory_record; \
+ (p) = malloc (sizeof (*(p)) * (size)); \
+ if (! (p) \
+ || (memrec->used >= OTF_MEMORY_RECORD_SIZE \
+ && ! (memrec = allocate_memory_record (otf)))) \
+ OTF_ERROR (OTF_ERROR_MEMORY, (arg)); \
+ memrec->memory[memrec->used++] = (p); \
+ } \
} while (0)
\f
+static void *read_head_table (OTF *otf, OTF_Stream *stream);
+static void *read_name_table (OTF *otf, OTF_Stream *stream);
+static void *read_cmap_table (OTF *otf, OTF_Stream *stream);
+static void *read_gdef_table (OTF *otf, OTF_Stream *stream);
+static void *read_gsub_table (OTF *otf, OTF_Stream *stream);
+static void *read_gpos_table (OTF *otf, OTF_Stream *stream);
+
int
read_offset_table (OTF *otf, OTF_Stream *stream, OTF_OffsetTable *table)
{
OTF_Stream *stream;
int i;
- OTF_CALLOC (internal_data, 1, " (InternalData");
+ internal_data = calloc (1, sizeof (OTF_InternalData));
+ if (! internal_data)
+ OTF_ERROR (OTF_ERROR_MEMORY, " (InternalData");
otf->internal_data = internal_data;
- internal_data->table_info[OTF_TABLE_TYPE_HEAD].address = &otf->head;
+ internal_data->table_info[OTF_TABLE_TYPE_HEAD].address = (void *) &otf->head;
internal_data->table_info[OTF_TABLE_TYPE_HEAD].reader = read_head_table;
- internal_data->table_info[OTF_TABLE_TYPE_NAME].address = &otf->name;
+ internal_data->table_info[OTF_TABLE_TYPE_NAME].address = (void *) &otf->name;
internal_data->table_info[OTF_TABLE_TYPE_NAME].reader = read_name_table;
- internal_data->table_info[OTF_TABLE_TYPE_CMAP].address = &otf->cmap;
+ internal_data->table_info[OTF_TABLE_TYPE_CMAP].address = (void *) &otf->cmap;
internal_data->table_info[OTF_TABLE_TYPE_CMAP].reader = read_cmap_table;
- internal_data->table_info[OTF_TABLE_TYPE_GDEF].address = &otf->gdef;
+ internal_data->table_info[OTF_TABLE_TYPE_GDEF].address = (void *) &otf->gdef;
internal_data->table_info[OTF_TABLE_TYPE_GDEF].reader = read_gdef_table;
- internal_data->table_info[OTF_TABLE_TYPE_GSUB].address = &otf->gsub;
+ internal_data->table_info[OTF_TABLE_TYPE_GSUB].address = (void *) &otf->gsub;
internal_data->table_info[OTF_TABLE_TYPE_GSUB].reader = read_gsub_table;
- internal_data->table_info[OTF_TABLE_TYPE_GPOS].address = &otf->gpos;
+ internal_data->table_info[OTF_TABLE_TYPE_GPOS].address = (void *) &otf->gpos;
internal_data->table_info[OTF_TABLE_TYPE_GPOS].reader = read_gpos_table;
if (allocate_memory_record (otf) < 0)
if (internal_data->header_stream)
free_stream (internal_data->header_stream);
- if (internal_data->streams)
- for (i = 0; i < otf->offset_table.numTables; i++)
- if (internal_data->streams[i])
- free_stream (internal_data->streams[i]);
+ for (i = 0; i < OTF_TABLE_TYPE_MAX; i++)
+ if (internal_data->table_info[i].stream)
+ free_stream (internal_data->table_info[i].stream);
while (memrec)
{
int
-otf_get_table (OTF *otf, OTF_Tag tag)
+otf_get_table (OTF *otf, char *name)
{
char *errfmt = "OTF Table Read";
int errret = -1;
OTF_InternalData *internal_data = otf->internal_data;
OTF_TableInfo *table_info;
+ OTF_Tag tag = otf_tag (name);
+
+ if (! tag)
+ OTF_ERROR (OTF_ERROR_TABLE, " (unknown)");
if (tag == otf_tag ("head"))
table_info = internal_data->table_info + OTF_TABLE_TYPE_HEAD;
}
void
-otf_perror (char *prefix)
+otf_perror (char *prefix, int exit_code)
{
if (otf_error < 0)
{
if (prefix)
- fprintf (stderr, "%s %s\n", prefix, error_message);
+ fprintf (stderr, "%s%s\n", prefix, error_message);
else
fprintf (stderr, "%s\n", error_message);
+ if (exit_code > 0)
+ exit (exit_code);
}
}