mirror of https://github.com/freetype/freetype
- various performance enhancements
- fixing apinames.c, adding support for Watcom and Borland compilers - adding generation of exported symbols list to the build system, including the Unix one !! sorry Werner, I have no time to document this in ChangeLog at the moment
This commit is contained in:
parent
69d45172b6
commit
9fbd2ab884
6
Jamfile
6
Jamfile
|
@ -155,12 +155,14 @@ SubInclude FT2_TOP $(FT2_SRC_DIR) tools ;
|
|||
|
||||
rule GenExportSymbols
|
||||
{
|
||||
local headers = [ Glob $(2) : *.h ] ;
|
||||
local apinames = apinames$(SUFEXE) ;
|
||||
local headers = [ Glob $(2) : *.h ] ;
|
||||
|
||||
APINAMES on $(1) = apinames$(SUFEXE) ;
|
||||
|
||||
Depends $(1) : $(headers) ;
|
||||
Depends $(1) : $(apinames) $(headers) ;
|
||||
GenExportSymbols1 $(1) : $(headers) ;
|
||||
Clean clean : $(1) ;
|
||||
}
|
||||
|
||||
actions GenExportSymbols1 bind APINAMES
|
||||
|
|
|
@ -55,6 +55,9 @@ L := /Fl
|
|||
#
|
||||
T := /Fo
|
||||
|
||||
# Target executable flag
|
||||
#
|
||||
TE := /Fe
|
||||
|
||||
# C flags
|
||||
#
|
||||
|
|
|
@ -19,6 +19,10 @@ BUILD_DIR := $(TOP_DIR)/builds/dos
|
|||
PLATFORM := dos
|
||||
|
||||
|
||||
# The executable file extension (for tools). NOTE: WE INCLUDE THE DOT HERE !!
|
||||
#
|
||||
E := .exe
|
||||
|
||||
# The directory where all object files are placed.
|
||||
#
|
||||
# This lets you build the library in your own directory with something like
|
||||
|
|
|
@ -142,6 +142,9 @@ FT_COMPILE = $(CC) $(ANSIFLAGS) $(FT_CFLAGS)
|
|||
#
|
||||
include $(TOP_DIR)/builds/modules.mk
|
||||
|
||||
# Includes the 'exports' rules file.
|
||||
#
|
||||
include $(TOP_DIR)/builds/exports.mk
|
||||
|
||||
# Initialize the list of objects.
|
||||
#
|
||||
|
@ -247,6 +250,8 @@ objects: $(OBJECTS_LIST)
|
|||
|
||||
library: $(PROJECT_LIBRARY)
|
||||
|
||||
dll: $(PROJECT_LIBRARY) exported_symbols
|
||||
|
||||
.c.$O:
|
||||
$(FT_COMPILE) $T$(subst /,$(COMPILER_SEP),$@ $<)
|
||||
|
||||
|
@ -283,7 +288,7 @@ distclean_project_std: clean_project_std
|
|||
# working correctly on Win9x.
|
||||
#
|
||||
clean_project_dos:
|
||||
-$(DELETE) $(subst /,\,$(OBJ)/*.$O $(CLEAN) $(NO_OUTPUT))
|
||||
-$(DELETE) $(subst /,\,$(OBJ_DIR)/*.$O $(CLEAN) $(NO_OUTPUT))
|
||||
|
||||
distclean_project_dos: clean_project_dos
|
||||
-$(DELETE) $(subst /,\,$(PROJECT_LIBRARY) $(DISTCLEAN) $(NO_OUTPUT))
|
||||
|
|
|
@ -18,6 +18,9 @@ SEP := $(strip \ )
|
|||
BUILD_DIR := $(TOP_DIR)/builds/os2
|
||||
PLATFORM := os2
|
||||
|
||||
# The executable file extension (for tools). NOTE: WE INCLUDE THE DOT HERE !!
|
||||
#
|
||||
E := .exe
|
||||
|
||||
# The directory where all object files are placed.
|
||||
#
|
||||
|
|
|
@ -280,27 +280,27 @@
|
|||
else
|
||||
{
|
||||
ssize_t total_read_count;
|
||||
|
||||
|
||||
|
||||
FT_ERROR(( "FT_Stream_Open:" ));
|
||||
FT_ERROR(( " could not `mmap' file `%s'\n", filepathname ));
|
||||
|
||||
|
||||
stream->base = (unsigned char*)ft_alloc( NULL, stream->size );
|
||||
|
||||
|
||||
if ( !stream->base )
|
||||
{
|
||||
FT_ERROR(( "FT_Stream_Open:" ));
|
||||
FT_ERROR(( " could not `alloc' memory\n" ));
|
||||
goto Fail_Map;
|
||||
}
|
||||
|
||||
|
||||
total_read_count = 0;
|
||||
do {
|
||||
ssize_t read_count;
|
||||
|
||||
|
||||
read_count = read( file,
|
||||
stream->base + total_read_count,
|
||||
read_count = read( file,
|
||||
stream->base + total_read_count,
|
||||
stream->size - total_read_count );
|
||||
|
||||
if ( ( read_count == -1 ) )
|
||||
|
|
|
@ -90,11 +90,16 @@ CC := $(LIBTOOL) --mode=compile $(CCraw)
|
|||
LDFLAGS := @LDFLAGS@
|
||||
|
||||
|
||||
# export symbols (XXX: HOW TO DEAL WITH CROSS COMPILATION ?)
|
||||
#
|
||||
EXPORTS_LIST := $(OBJ_DIR)/ftexport.sym
|
||||
CCexe := $(CCraw) # used to compile "apinames" only
|
||||
|
||||
|
||||
# Library linking
|
||||
#
|
||||
LINK_LIBRARY = $(LIBTOOL) --mode=link $(CCraw) -o $@ $(OBJECTS_LIST) \
|
||||
-rpath $(libdir) -version-info $(version_info) \
|
||||
$(LDFLAGS)
|
||||
|
||||
$(LDFLAGS) -export-symbols $(EXPORTS_LIST)
|
||||
|
||||
# EOF
|
||||
|
|
|
@ -51,5 +51,4 @@ LIB_DIR := $(OBJ_DIR)
|
|||
|
||||
NO_OUTPUT := 2> /dev/null
|
||||
|
||||
|
||||
# EOF
|
||||
|
|
|
@ -12,6 +12,11 @@
|
|||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
# default definitions of the export list
|
||||
#
|
||||
EXPORTS_LIST = $(OBJ_DIR)/freetype.def
|
||||
EXPORTS_OPTIONS = /DEF:$(EXPORTS_LIST)
|
||||
APINAMES_OPTIONS := -dfreetype.dll -wB
|
||||
|
||||
include $(TOP_DIR)/builds/win32/win32-def.mk
|
||||
include $(TOP_DIR)/builds/compiler/bcc.mk
|
||||
|
|
|
@ -12,6 +12,11 @@
|
|||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
# default definitions of the export list
|
||||
#
|
||||
EXPORTS_LIST = $(OBJ_DIR)/freetype.def
|
||||
EXPORTS_OPTIONS = $(EXPORTS_LIST)
|
||||
APINAMES_OPTIONS := -dfreetype.dll -w
|
||||
|
||||
# include Win32-specific definitions
|
||||
include $(TOP_DIR)/builds/win32/win32-def.mk
|
||||
|
|
|
@ -12,6 +12,11 @@
|
|||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
# default definitions of the export list
|
||||
#
|
||||
EXPORTS_LIST = $(OBJ_DIR)/freetype.def
|
||||
EXPORTS_OPTIONS = /DEF:$(EXPORTS_LIST)
|
||||
APINAMES_OPTIONS := -dfreetype.dll -w
|
||||
|
||||
include $(TOP_DIR)/builds/win32/win32-def.mk
|
||||
include $(TOP_DIR)/builds/compiler/visualage.mk
|
||||
|
|
|
@ -12,6 +12,11 @@
|
|||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
# default definitions of the export list
|
||||
#
|
||||
EXPORTS_LIST = $(OBJ_DIR)/freetype.def
|
||||
EXPORTS_OPTIONS = /DEF:$(EXPORTS_LIST)
|
||||
APINAMES_OPTIONS := -dfreetype.dll -w
|
||||
|
||||
include $(TOP_DIR)/builds/win32/win32-def.mk
|
||||
include $(TOP_DIR)/builds/compiler/intelc.mk
|
||||
|
|
|
@ -12,6 +12,11 @@
|
|||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
# default definitions of the export list
|
||||
#
|
||||
EXPORTS_LIST = $(OBJ_DIR)/freetype.def
|
||||
EXPORTS_OPTIONS = $(EXPORTS_LIST)
|
||||
APINAMES_OPTIONS := -dfreetype.dll -w
|
||||
|
||||
# include Win32-specific definitions
|
||||
include $(TOP_DIR)/builds/win32/win32-def.mk
|
||||
|
|
|
@ -12,6 +12,11 @@
|
|||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
# definitions of the export list
|
||||
#
|
||||
EXPORTS_LIST = $(OBJ_DIR)/freetype.def
|
||||
EXPORTS_OPTIONS = /DEF:$(EXPORTS_LIST)
|
||||
APINAMES_OPTIONS := -dfreetype.dll -w
|
||||
|
||||
include $(TOP_DIR)/builds/win32/win32-def.mk
|
||||
include $(TOP_DIR)/builds/compiler/visualc.mk
|
||||
|
|
|
@ -12,6 +12,11 @@
|
|||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
# redefine export symbol definitions
|
||||
#
|
||||
EXPORTS_LIST = $(OBJ_DIR)/watcom-ftexports.lbc
|
||||
EXPORTS_OPTIONS = -\"export @$(EXPORTS_LIST)\"-
|
||||
APINAMES_OPTIONS := -wW
|
||||
|
||||
include $(TOP_DIR)/builds/win32/win32-def.mk
|
||||
include $(TOP_DIR)/builds/compiler/watcom.mk
|
||||
|
|
|
@ -18,6 +18,9 @@ SEP := $(strip \ )
|
|||
BUILD_DIR := $(TOP_DIR)/builds/win32
|
||||
PLATFORM := win32
|
||||
|
||||
# The executable file extension (for tools). NOTE: WE INCLUDE THE DOT HERE !!
|
||||
#
|
||||
E := .exe
|
||||
|
||||
# The directory where all object files are placed.
|
||||
#
|
||||
|
|
|
@ -59,7 +59,7 @@ FT_BEGIN_HEADER
|
|||
FT_Int arg1;
|
||||
FT_Int arg2;
|
||||
FT_Matrix transform;
|
||||
|
||||
|
||||
} FT_SubGlyphRec;
|
||||
|
||||
|
||||
|
@ -117,6 +117,22 @@ FT_BEGIN_HEADER
|
|||
FT_UInt n_points,
|
||||
FT_UInt n_contours );
|
||||
|
||||
#define FT_GLYPHLOADER_CHECK_P(_loader,_count) \
|
||||
( (_count) == 0 || (int)((_loader)->base.outline.n_points + \
|
||||
(_loader)->current.outline.n_points + \
|
||||
(_count)) <= (int)(_loader)->max_points )
|
||||
|
||||
#define FT_GLYPHLOADER_CHECK_C(_loader,_count) \
|
||||
( (_count) == 0 || (int)((_loader)->base.outline.n_contours + \
|
||||
(_loader)->current.outline.n_contours + \
|
||||
(_count)) <= (int)(_loader)->max_contours )
|
||||
|
||||
#define FT_GLYPHLOADER_CHECK_POINTS(_loader,_points,_contours) \
|
||||
( ( FT_GLYPHLOADER_CHECK_P(_loader,_points) && \
|
||||
FT_GLYPHLOADER_CHECK_C(_loader,_contours) ) \
|
||||
? 0 \
|
||||
: FT_GlyphLoader_CheckPoints( (_loader), (_points), (_contours) ) )
|
||||
|
||||
/* check that there is enough space to add `n_subs' sub-glyphs to */
|
||||
/* a glyph loader */
|
||||
FT_BASE( FT_Error )
|
||||
|
|
|
@ -265,11 +265,55 @@
|
|||
#endif /* AF_DEBUG */
|
||||
|
||||
|
||||
|
||||
/* compute the direction value of a given vector */
|
||||
FT_LOCAL_DEF( AF_Direction )
|
||||
af_direction_compute( FT_Pos dx,
|
||||
FT_Pos dy )
|
||||
{
|
||||
#if 1
|
||||
AF_Direction dir = AF_DIR_NONE;
|
||||
|
||||
if ( dx < 0 )
|
||||
{
|
||||
if ( dy < 0 )
|
||||
{
|
||||
if ( -dx*12 < -dy )
|
||||
dir = AF_DIR_DOWN;
|
||||
|
||||
else if ( -dy*12 < -dx )
|
||||
dir = AF_DIR_LEFT;
|
||||
}
|
||||
else /* dy >= 0 */
|
||||
{
|
||||
if ( -dx*12 < dy )
|
||||
dir = AF_DIR_UP;
|
||||
|
||||
else if ( dy*12 < -dx )
|
||||
dir = AF_DIR_LEFT;
|
||||
}
|
||||
}
|
||||
else /* dx >= 0 */
|
||||
{
|
||||
if ( dy < 0 )
|
||||
{
|
||||
if ( dx*12 < -dy )
|
||||
dir = AF_DIR_DOWN;
|
||||
|
||||
else if ( -dy*12 < dx )
|
||||
dir = AF_DIR_RIGHT;
|
||||
}
|
||||
else /* dy >= 0 */
|
||||
{
|
||||
if ( dx*12 < dy )
|
||||
dir = AF_DIR_UP;
|
||||
|
||||
else if ( dy*12 < dx )
|
||||
dir = AF_DIR_RIGHT;
|
||||
}
|
||||
}
|
||||
return dir;
|
||||
#else
|
||||
AF_Direction dir;
|
||||
FT_Pos ax = FT_ABS( dx );
|
||||
FT_Pos ay = FT_ABS( dy );
|
||||
|
@ -291,6 +335,7 @@
|
|||
}
|
||||
|
||||
return dir;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
@ -350,7 +395,8 @@
|
|||
} while ( angle_in == angle_seg );
|
||||
|
||||
first = start;
|
||||
diff_in = af_angle_diff( angle_in, angle_seg );
|
||||
|
||||
AF_ANGLE_DIFF( diff_in, angle_in, angle_seg );
|
||||
|
||||
/* now, process all segments in the contour */
|
||||
do
|
||||
|
@ -373,7 +419,7 @@
|
|||
|
||||
} while ( angle_out == angle_seg );
|
||||
|
||||
diff_out = af_angle_diff( angle_seg, angle_out );
|
||||
AF_ANGLE_DIFF( diff_out, angle_seg, angle_out );
|
||||
|
||||
if ( ( diff_in ^ diff_out ) < 0 )
|
||||
{
|
||||
|
@ -657,7 +703,8 @@
|
|||
|
||||
angle_in = af_angle_atan( in_x, in_y );
|
||||
angle_out = af_angle_atan( out_x, out_y );
|
||||
delta = af_angle_diff( angle_in, angle_out );
|
||||
|
||||
AF_ANGLE_DIFF( delta, angle_in, angle_out );
|
||||
|
||||
if ( delta < 2 && delta > -2 )
|
||||
goto Is_Weak_Point;
|
||||
|
|
|
@ -138,9 +138,9 @@
|
|||
|
||||
/* copy the outline points in the loader's current */
|
||||
/* extra points which is used to keep original glyph coordinates */
|
||||
error = FT_GlyphLoader_CheckPoints( gloader,
|
||||
slot->outline.n_points + 4,
|
||||
slot->outline.n_contours );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( gloader,
|
||||
slot->outline.n_points + 4,
|
||||
slot->outline.n_contours );
|
||||
if ( error )
|
||||
goto Exit;
|
||||
|
||||
|
|
|
@ -133,6 +133,20 @@ FT_BEGIN_HEADER
|
|||
af_angle_diff( AF_Angle angle1,
|
||||
AF_Angle angle2 );
|
||||
|
||||
#define AF_ANGLE_DIFF(result,angle1,angle2) \
|
||||
FT_BEGIN_STMNT \
|
||||
AF_Angle _delta = (angle2) - (angle1); \
|
||||
\
|
||||
\
|
||||
_delta %= AF_ANGLE_2PI; \
|
||||
if ( _delta < 0 ) \
|
||||
_delta += AF_ANGLE_2PI; \
|
||||
\
|
||||
if ( _delta > AF_ANGLE_PI ) \
|
||||
_delta -= AF_ANGLE_2PI; \
|
||||
\
|
||||
result = _delta; \
|
||||
FT_END_STMNT
|
||||
|
||||
/*************************************************************************/
|
||||
/*************************************************************************/
|
||||
|
|
|
@ -394,6 +394,38 @@
|
|||
FT_MulFix( FT_Long a,
|
||||
FT_Long b )
|
||||
{
|
||||
#if 1
|
||||
FT_Long sa, sb;
|
||||
FT_ULong ua, ub;
|
||||
|
||||
|
||||
if ( a == 0 || b == 0x10000L )
|
||||
return a;
|
||||
|
||||
sa = (a >> (sizeof(a)*8 - 1)); a = (a^sa) - sa;
|
||||
sb = (b >> (sizeof(b)*8 - 1)); b = (b^sb) - sb;
|
||||
|
||||
ua = (FT_ULong)a;
|
||||
ub = (FT_ULong)b;
|
||||
|
||||
if ( ua <= 2048 && ub <= 1048576L )
|
||||
{
|
||||
ua = ( ua * ub + 0x8000 ) >> 16;
|
||||
}
|
||||
else
|
||||
{
|
||||
FT_ULong al = ua & 0xFFFF;
|
||||
|
||||
|
||||
ua = ( ua >> 16 ) * ub + al * ( ub >> 16 ) +
|
||||
( ( al * ( ub & 0xFFFF ) + 0x8000 ) >> 16 );
|
||||
}
|
||||
|
||||
sa ^= sb,
|
||||
ua = (FT_ULong)((ua ^ sa) - sa);
|
||||
|
||||
return (FT_Long)ua;
|
||||
#else
|
||||
FT_Long s;
|
||||
FT_ULong ua, ub;
|
||||
|
||||
|
@ -421,6 +453,7 @@
|
|||
}
|
||||
|
||||
return ( s < 0 ? -(FT_Long)ua : (FT_Long)ua );
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -195,7 +195,7 @@
|
|||
FT_Error error = FT_Err_Ok;
|
||||
FT_Outline* base = &loader->base.outline;
|
||||
FT_Outline* current = &loader->current.outline;
|
||||
FT_Bool adjust = 1;
|
||||
FT_Bool adjust = 0;
|
||||
|
||||
FT_UInt new_max, old_max;
|
||||
|
||||
|
|
|
@ -109,6 +109,46 @@
|
|||
z = ( ( x >= 0 ) ? x : - x ) | ( (y >= 0) ? y : -y );
|
||||
shift = 0;
|
||||
|
||||
#if 1
|
||||
/* determine msb bit index in 'shift' */
|
||||
if ( z >= (1L << 16 ) )
|
||||
{
|
||||
z >>= 16;
|
||||
shift += 16;
|
||||
}
|
||||
if ( z >= (1L << 8) )
|
||||
{
|
||||
z >>= 8;
|
||||
shift += 8;
|
||||
}
|
||||
if ( z >= (1L << 4) )
|
||||
{
|
||||
z >>= 4;
|
||||
shift += 4;
|
||||
}
|
||||
if ( z >= (1L << 2) )
|
||||
{
|
||||
z >>= 2;
|
||||
shift += 2;
|
||||
}
|
||||
if ( z >= 1 )
|
||||
shift += 1;
|
||||
|
||||
if ( shift < 28 )
|
||||
{
|
||||
shift = 28-shift;
|
||||
|
||||
vec->x = x << shift;
|
||||
vec->y = y << shift;
|
||||
}
|
||||
else if ( shift > 28 )
|
||||
{
|
||||
shift -= 28;
|
||||
vec->x = x >> shift;
|
||||
vec->y = y >> shift;
|
||||
shift = -shift;
|
||||
}
|
||||
#else
|
||||
if ( z < ( 1L << 27 ) )
|
||||
{
|
||||
do
|
||||
|
@ -116,7 +156,6 @@
|
|||
shift++;
|
||||
z <<= 1;
|
||||
} while ( z < ( 1L << 27 ) );
|
||||
|
||||
vec->x = x << shift;
|
||||
vec->y = y << shift;
|
||||
}
|
||||
|
@ -132,6 +171,7 @@
|
|||
vec->y = y >> shift;
|
||||
shift = -shift;
|
||||
}
|
||||
#endif
|
||||
return shift;
|
||||
}
|
||||
|
||||
|
|
|
@ -403,7 +403,7 @@
|
|||
check_points( CFF_Builder* builder,
|
||||
FT_Int count )
|
||||
{
|
||||
return FT_GlyphLoader_CheckPoints( builder->loader, count, 0 );
|
||||
return FT_GLYPHLOADER_CHECK_POINTS( builder->loader, count, 0 );
|
||||
}
|
||||
|
||||
|
||||
|
@ -465,7 +465,7 @@
|
|||
return CFF_Err_Ok;
|
||||
}
|
||||
|
||||
error = FT_GlyphLoader_CheckPoints( builder->loader, 0, 1 );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( builder->loader, 0, 1 );
|
||||
if ( !error )
|
||||
{
|
||||
if ( outline->n_contours > 0 )
|
||||
|
|
|
@ -133,7 +133,7 @@
|
|||
/* check that we have begun a new path */
|
||||
FT_ASSERT( glyph->path_begun != 0 );
|
||||
|
||||
error = FT_GlyphLoader_CheckPoints( loader, 1, 0 );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( loader, 1, 0 );
|
||||
if ( !error )
|
||||
{
|
||||
FT_UInt n = outline->n_points;
|
||||
|
@ -163,7 +163,7 @@
|
|||
/* check that we have begun a new path */
|
||||
FT_ASSERT( glyph->path_begun != 0 );
|
||||
|
||||
error = FT_GlyphLoader_CheckPoints( loader, 3, 0 );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( loader, 3, 0 );
|
||||
if ( !error )
|
||||
{
|
||||
FT_Vector* vec = outline->points + outline->n_points;
|
||||
|
@ -199,7 +199,7 @@
|
|||
glyph->path_begun = 1;
|
||||
|
||||
/* check that there is space for a new contour and a new point */
|
||||
error = FT_GlyphLoader_CheckPoints( loader, 1, 1 );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( loader, 1, 1 );
|
||||
if ( !error )
|
||||
/* add new start point */
|
||||
error = pfr_glyph_line_to( glyph, to );
|
||||
|
|
|
@ -609,148 +609,6 @@
|
|||
}
|
||||
|
||||
|
||||
#ifndef FT_OPTIMIZE_MEMORY
|
||||
|
||||
/*
|
||||
* The kerning data embedded in a PFR font are (charcode,charcode)
|
||||
* pairs; we need to translate them to (gindex,gindex) and sort
|
||||
* the resulting array.
|
||||
*/
|
||||
static FT_UInt
|
||||
pfr_get_gindex( PFR_Char chars,
|
||||
FT_UInt count,
|
||||
FT_UInt charcode )
|
||||
{
|
||||
FT_UInt min = 0;
|
||||
FT_UInt max = count;
|
||||
|
||||
|
||||
while ( min < max )
|
||||
{
|
||||
FT_UInt mid = ( min + max ) >> 1;
|
||||
PFR_Char c = chars + mid;
|
||||
|
||||
|
||||
if ( c->char_code == charcode )
|
||||
return mid + 1;
|
||||
|
||||
if ( c->char_code < charcode )
|
||||
min = mid + 1;
|
||||
else
|
||||
max = mid;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
FT_CALLBACK_DEF( int )
|
||||
pfr_compare_kern_pairs( const void* pair1,
|
||||
const void* pair2 )
|
||||
{
|
||||
FT_UInt32 p1 = PFR_KERN_PAIR_INDEX( (PFR_KernPair)pair1 );
|
||||
FT_UInt32 p2 = PFR_KERN_PAIR_INDEX( (PFR_KernPair)pair2 );
|
||||
|
||||
|
||||
if ( p1 < p2 )
|
||||
return -1;
|
||||
if ( p1 > p2 )
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static FT_Error
|
||||
pfr_sort_kerning_pairs( FT_Stream stream,
|
||||
PFR_PhyFont phy_font )
|
||||
{
|
||||
FT_Error error;
|
||||
FT_Memory memory = stream->memory;
|
||||
PFR_KernPair pairs;
|
||||
PFR_KernItem item;
|
||||
PFR_Char chars = phy_font->chars;
|
||||
FT_UInt num_chars = phy_font->num_chars;
|
||||
FT_UInt count;
|
||||
|
||||
|
||||
/* create kerning pairs array */
|
||||
if ( FT_NEW_ARRAY( phy_font->kern_pairs, phy_font->num_kern_pairs ) )
|
||||
goto Exit;
|
||||
|
||||
/*
|
||||
* load all kerning items into the array,
|
||||
* converting character codes into glyph indices
|
||||
*/
|
||||
pairs = phy_font->kern_pairs;
|
||||
item = phy_font->kern_items;
|
||||
count = 0;
|
||||
|
||||
for ( ; item; item = item->next )
|
||||
{
|
||||
FT_UInt limit = count + item->pair_count;
|
||||
FT_Byte* p;
|
||||
|
||||
|
||||
if ( limit > phy_font->num_kern_pairs )
|
||||
{
|
||||
error = PFR_Err_Invalid_Table;
|
||||
goto Exit;
|
||||
}
|
||||
|
||||
if ( FT_STREAM_SEEK( item->offset ) ||
|
||||
FT_FRAME_ENTER( item->pair_count * item->pair_size ) )
|
||||
goto Exit;
|
||||
|
||||
p = stream->cursor;
|
||||
|
||||
for ( ; count < limit; count++ )
|
||||
{
|
||||
PFR_KernPair pair = pairs + count;
|
||||
FT_UInt char1, char2;
|
||||
FT_Int kerning;
|
||||
|
||||
|
||||
if ( item->flags & PFR_KERN_2BYTE_CHAR )
|
||||
{
|
||||
char1 = FT_NEXT_USHORT( p );
|
||||
char2 = FT_NEXT_USHORT( p );
|
||||
}
|
||||
else
|
||||
{
|
||||
char1 = FT_NEXT_BYTE( p );
|
||||
char2 = FT_NEXT_BYTE( p );
|
||||
}
|
||||
|
||||
if ( item->flags & PFR_KERN_2BYTE_ADJ )
|
||||
kerning = item->base_adj + FT_NEXT_SHORT( p );
|
||||
else
|
||||
kerning = item->base_adj + FT_NEXT_BYTE( p );
|
||||
|
||||
pair->glyph1 = pfr_get_gindex( chars, num_chars, char1 );
|
||||
pair->glyph2 = pfr_get_gindex( chars, num_chars, char2 );
|
||||
pair->kerning = kerning;
|
||||
}
|
||||
|
||||
FT_FRAME_EXIT();
|
||||
}
|
||||
|
||||
/* sort the resulting array */
|
||||
ft_qsort( pairs, count,
|
||||
sizeof ( PFR_KernPairRec ),
|
||||
pfr_compare_kern_pairs );
|
||||
|
||||
Exit:
|
||||
if ( error )
|
||||
{
|
||||
/* disable kerning data in case of error
|
||||
*/
|
||||
phy_font->num_kern_pairs = 0;
|
||||
}
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
#endif /* !FT_OPTIMIZE_MEMORY */
|
||||
|
||||
|
||||
static const PFR_ExtraItemRec pfr_phy_font_extra_items[] =
|
||||
{
|
||||
|
@ -829,10 +687,6 @@
|
|||
FT_FREE( phy_font->blue_values );
|
||||
phy_font->num_blue_values = 0;
|
||||
|
||||
#ifndef FT_OPTIMIZE_MEMORY
|
||||
FT_FREE( phy_font->kern_pairs );
|
||||
#endif
|
||||
|
||||
{
|
||||
PFR_KernItem item, next;
|
||||
|
||||
|
@ -1071,11 +925,6 @@
|
|||
phy_font->bct_offset = FT_STREAM_POS();
|
||||
phy_font->cursor = NULL;
|
||||
|
||||
#ifndef FT_OPTIMIZE_MEMORY
|
||||
/* now sort kerning pairs */
|
||||
error = pfr_sort_kerning_pairs( stream, phy_font );
|
||||
#endif
|
||||
|
||||
Exit:
|
||||
return error;
|
||||
|
||||
|
|
|
@ -422,8 +422,6 @@
|
|||
/*************************************************************************/
|
||||
/*************************************************************************/
|
||||
|
||||
#ifdef FT_OPTIMIZE_MEMORY
|
||||
|
||||
FT_LOCAL_DEF( FT_Error )
|
||||
pfr_face_get_kerning( FT_Face pfrface, /* PFR_Face */
|
||||
FT_UInt glyph1,
|
||||
|
@ -546,51 +544,4 @@
|
|||
return error;
|
||||
}
|
||||
|
||||
#else /* !FT_OPTIMIZE_MEMORY */
|
||||
|
||||
FT_LOCAL_DEF( FT_Error )
|
||||
pfr_face_get_kerning( FT_Face pfrface, /* PFR_Face */
|
||||
FT_UInt glyph1,
|
||||
FT_UInt glyph2,
|
||||
FT_Vector* kerning )
|
||||
{
|
||||
PFR_Face face = (PFR_Face)pfrface;
|
||||
FT_Error error = PFR_Err_Ok;
|
||||
PFR_PhyFont phy_font = &face->phy_font;
|
||||
PFR_KernPair pairs = phy_font->kern_pairs;
|
||||
FT_UInt32 idx = PFR_KERN_INDEX( glyph1, glyph2 );
|
||||
FT_UInt min, max;
|
||||
|
||||
|
||||
kerning->x = 0;
|
||||
kerning->y = 0;
|
||||
|
||||
min = 0;
|
||||
max = phy_font->num_kern_pairs;
|
||||
|
||||
while ( min < max )
|
||||
{
|
||||
FT_UInt mid = ( min + max ) >> 1;
|
||||
PFR_KernPair pair = pairs + mid;
|
||||
FT_UInt32 pidx = PFR_KERN_PAIR_INDEX( pair );
|
||||
|
||||
|
||||
if ( pidx == idx )
|
||||
{
|
||||
kerning->x = pair->kerning;
|
||||
break;
|
||||
}
|
||||
|
||||
if ( pidx < idx )
|
||||
min = mid + 1;
|
||||
else
|
||||
max = mid;
|
||||
}
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
#endif /* !FT_OPTIMIZE_MEMORY */
|
||||
|
||||
|
||||
/* END */
|
||||
|
|
|
@ -217,14 +217,6 @@ FT_BEGIN_HEADER
|
|||
( (FT_UInt32)p[-2] << 16 ) | p[-1] )
|
||||
|
||||
|
||||
typedef struct PFR_KernPairRec_
|
||||
{
|
||||
FT_UInt glyph1;
|
||||
FT_UInt glyph2;
|
||||
FT_Int kerning;
|
||||
|
||||
} PFR_KernPairRec, *PFR_KernPair;
|
||||
|
||||
/************************************************************************/
|
||||
|
||||
typedef struct PFR_PhyFontRec_
|
||||
|
@ -266,9 +258,6 @@ FT_BEGIN_HEADER
|
|||
FT_UInt num_kern_pairs;
|
||||
PFR_KernItem kern_items;
|
||||
PFR_KernItem* kern_items_tail;
|
||||
#ifndef FT_OPTIMIZE_MEMORY
|
||||
PFR_KernPair kern_pairs;
|
||||
#endif
|
||||
|
||||
/* not part of the spec, but used during load */
|
||||
FT_UInt32 bct_offset;
|
||||
|
|
|
@ -1623,7 +1623,7 @@
|
|||
t1_builder_check_points( T1_Builder builder,
|
||||
FT_Int count )
|
||||
{
|
||||
return FT_GlyphLoader_CheckPoints( builder->loader, count, 0 );
|
||||
return FT_GLYPHLOADER_CHECK_POINTS( builder->loader, count, 0 );
|
||||
}
|
||||
|
||||
|
||||
|
@ -1689,7 +1689,7 @@
|
|||
return PSaux_Err_Ok;
|
||||
}
|
||||
|
||||
error = FT_GlyphLoader_CheckPoints( builder->loader, 0, 1 );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( builder->loader, 0, 1 );
|
||||
if ( !error )
|
||||
{
|
||||
if ( outline->n_contours > 0 )
|
||||
|
|
|
@ -1,323 +1,441 @@
|
|||
/*
|
||||
* This little program is used to parse the FreeType headers and
|
||||
* find the declaration of all public API. This is easy, because
|
||||
* they all look like the following:
|
||||
*
|
||||
* FT_EXPORT( return_type )
|
||||
* function_name( function arguments );
|
||||
*
|
||||
* You must pass the list of header files as arguments. Wildcards are
|
||||
* accepted if you are using GCC for compilation (and probably by
|
||||
* other compilers too).
|
||||
*
|
||||
* Author: David Turner, 2005
|
||||
*
|
||||
* This code is explicitly placed into the public domain.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#define PROGRAM_NAME "apinames"
|
||||
#define PROGRAM_VERSION "0.1"
|
||||
|
||||
#define LINEBUFF_SIZE 1024
|
||||
|
||||
static void
|
||||
panic( const char* message )
|
||||
{
|
||||
fprintf( stderr, "PANIC: %s\n", message );
|
||||
exit(2);
|
||||
}
|
||||
|
||||
|
||||
typedef struct
|
||||
{
|
||||
char* name;
|
||||
unsigned int hash;
|
||||
|
||||
} NameRec, *Name;
|
||||
|
||||
static Name the_names;
|
||||
static int num_names;
|
||||
static int max_names;
|
||||
|
||||
static void
|
||||
names_add( const char* name,
|
||||
const char* end )
|
||||
{
|
||||
int nn, len, h;
|
||||
Name nm;
|
||||
|
||||
if ( end <= name )
|
||||
return;
|
||||
|
||||
/* compute hash value */
|
||||
len = (int)(end - name);
|
||||
h = 0;
|
||||
for ( nn = 0; nn < len; nn++ )
|
||||
h = h*33 + name[nn];
|
||||
|
||||
/* check for an pre-existing name */
|
||||
for ( nn = 0; nn < num_names; nn++ )
|
||||
{
|
||||
nm = the_names + nn;
|
||||
|
||||
if ( nm->hash == h &&
|
||||
memcmp( name, nm->name, len ) == 0 &&
|
||||
nm->name[len] == 0 )
|
||||
return;
|
||||
}
|
||||
|
||||
/* add new name */
|
||||
if ( num_names >= max_names )
|
||||
{
|
||||
max_names += (max_names >> 1) + 4;
|
||||
the_names = realloc( the_names, sizeof(the_names[0])*max_names );
|
||||
if ( the_names == NULL )
|
||||
panic( "not enough memory" );
|
||||
}
|
||||
nm = &the_names[num_names++];
|
||||
|
||||
nm->hash = h;
|
||||
nm->name = malloc( len+1 );
|
||||
if ( nm->name == NULL )
|
||||
panic( "not enough memory" );
|
||||
|
||||
memcpy( nm->name, name, len );
|
||||
nm->name[len] = 0;
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
name_compare( const void* name1,
|
||||
const void* name2 )
|
||||
{
|
||||
Name n1 = (Name)name1;
|
||||
Name n2 = (Name)name2;
|
||||
|
||||
return strcmp( n1->name, n2->name );
|
||||
}
|
||||
|
||||
static void
|
||||
names_sort( void )
|
||||
{
|
||||
qsort( the_names, (size_t)num_names, sizeof(the_names[0]), name_compare );
|
||||
}
|
||||
|
||||
static void
|
||||
names_dump( FILE* out )
|
||||
{
|
||||
int nn;
|
||||
|
||||
for ( nn = 0; nn < num_names; nn++ )
|
||||
fprintf( out, "%s\n", the_names[nn].name );
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
names_dump_windef( FILE* out )
|
||||
{
|
||||
int nn;
|
||||
|
||||
/* note that we assume that __cdecl was used when compiling the
|
||||
* DLL object files.
|
||||
*/
|
||||
fprintf( out, "DESCRIPTION FreeType 2 DLL\n" );
|
||||
fprintf( out, "EXPORTS\n" );
|
||||
for ( nn = 0; nn < num_names; nn++ )
|
||||
fprintf( out, " %s\n", the_names[nn].name );
|
||||
}
|
||||
|
||||
|
||||
/* states of the line parser */
|
||||
|
||||
typedef enum
|
||||
{
|
||||
STATE_START = 0, /* waiting for FT_EXPORT keyword and return type */
|
||||
STATE_TYPE, /* type was read, waiting for function name */
|
||||
|
||||
} State;
|
||||
|
||||
static int
|
||||
read_header_file( FILE* file, int verbose )
|
||||
{
|
||||
static char buff[ LINEBUFF_SIZE+1 ];
|
||||
State state = STATE_START;
|
||||
|
||||
while ( !feof( file ) )
|
||||
{
|
||||
char* p;
|
||||
|
||||
if ( !fgets( buff, LINEBUFF_SIZE, file ) )
|
||||
break;
|
||||
|
||||
p = buff;
|
||||
|
||||
while ( *p && (*p == ' ' || *p == '\\') ) /* skip leading whitespace */
|
||||
p++;
|
||||
|
||||
if ( *p == '\n' || *p == '\r' ) /* skip empty lines */
|
||||
continue;
|
||||
|
||||
switch ( state )
|
||||
{
|
||||
case STATE_START:
|
||||
{
|
||||
if ( memcmp( p, "FT_EXPORT(", 10 ) != 0 )
|
||||
break;
|
||||
|
||||
p += 10;
|
||||
for (;;)
|
||||
{
|
||||
if ( *p == 0 || *p == '\n' || *p == '\r' )
|
||||
goto NextLine;
|
||||
|
||||
if ( *p == ')' )
|
||||
{
|
||||
p++;
|
||||
break;
|
||||
}
|
||||
|
||||
p++;
|
||||
}
|
||||
|
||||
state = STATE_TYPE;
|
||||
|
||||
/* sometimes, the name is just after the FT_EXPORT(...), so
|
||||
* skip whitespace, and fall-through if we find an alphanumeric
|
||||
* character
|
||||
*/
|
||||
while ( *p == ' ' || *p == '\t' )
|
||||
p++;
|
||||
|
||||
if ( !isalpha(*p) )
|
||||
break;
|
||||
}
|
||||
/* fall-through */
|
||||
|
||||
case STATE_TYPE:
|
||||
{
|
||||
char* name = p;
|
||||
size_t func_len;
|
||||
|
||||
while ( isalpha(*p) || *p == '_' )
|
||||
p++;
|
||||
|
||||
if ( p > name )
|
||||
{
|
||||
if ( verbose )
|
||||
fprintf( stderr, ">>> %.*s\n", p-name, name );
|
||||
|
||||
names_add( name, p );
|
||||
}
|
||||
|
||||
state = STATE_START;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
;
|
||||
}
|
||||
|
||||
NextLine:
|
||||
;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
usage( void )
|
||||
{
|
||||
fprintf( stderr,
|
||||
"%s %s: extract FreeType API names from header files\n\n"
|
||||
"this program is used to extract the list of public FreeType API\n"
|
||||
"functions. It receives the list of header files as argument and\n"
|
||||
"generates a sorted list of unique identifiers\n\n"
|
||||
|
||||
"usage: %s header1 [options] [header2 ...]\n\n"
|
||||
|
||||
"options: - : parse the content of stdin, ignore arguments\n"
|
||||
" -v : verbose mode\n",
|
||||
" -w : output windows .DEF file\n"
|
||||
,
|
||||
PROGRAM_NAME,
|
||||
PROGRAM_VERSION,
|
||||
PROGRAM_NAME
|
||||
);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
|
||||
int main( int argc, const char* const* argv )
|
||||
{
|
||||
int from_stdin = 0;
|
||||
int verbose = 0;
|
||||
int do_win_def = 0;
|
||||
|
||||
if ( argc < 2 )
|
||||
usage();
|
||||
|
||||
/* '-' used as a single argument means read source file from stdin */
|
||||
while ( argc > 1 && argv[1][0] == '-' )
|
||||
{
|
||||
switch ( argv[1][1] )
|
||||
{
|
||||
case 'v':
|
||||
verbose = 1;
|
||||
break;
|
||||
|
||||
case 'w':
|
||||
do_win_def = 1;
|
||||
break;
|
||||
|
||||
case 0:
|
||||
from_stdin = 1;
|
||||
break;
|
||||
|
||||
default:
|
||||
usage();
|
||||
}
|
||||
|
||||
argc--;
|
||||
argv++;
|
||||
}
|
||||
|
||||
if ( from_stdin )
|
||||
{
|
||||
read_header_file( stdin, verbose );
|
||||
}
|
||||
else
|
||||
{
|
||||
for ( --argc, argv++; argc > 0; argc--, argv++ )
|
||||
{
|
||||
FILE* file = fopen( argv[0], "rb" );
|
||||
|
||||
if ( file == NULL )
|
||||
fprintf( stderr, "unable to open '%s'\n", argv[0] );
|
||||
else
|
||||
{
|
||||
if ( verbose )
|
||||
fprintf( stderr, "opening '%s'\n", argv[0] );
|
||||
|
||||
read_header_file( file, verbose );
|
||||
fclose( file );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( num_names == 0 )
|
||||
panic( "could not find exported functions !!\n" );
|
||||
|
||||
names_sort();
|
||||
|
||||
if ( do_win_def )
|
||||
names_dump_windef( stdout );
|
||||
else
|
||||
names_dump( stdout );
|
||||
|
||||
return 0;
|
||||
}
|
||||
/*
|
||||
* This little program is used to parse the FreeType headers and
|
||||
* find the declaration of all public API. This is easy, because
|
||||
* they all look like the following:
|
||||
*
|
||||
* FT_EXPORT( return_type )
|
||||
* function_name( function arguments );
|
||||
*
|
||||
* You must pass the list of header files as arguments. Wildcards are
|
||||
* accepted if you are using GCC for compilation (and probably by
|
||||
* other compilers too).
|
||||
*
|
||||
* Author: David Turner, 2005
|
||||
*
|
||||
* This code is explicitly placed into the public domain.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#define PROGRAM_NAME "apinames"
|
||||
#define PROGRAM_VERSION "0.1"
|
||||
|
||||
#define LINEBUFF_SIZE 1024
|
||||
|
||||
typedef enum
|
||||
{
|
||||
OUTPUT_LIST = 0, /* output the list of names, one per line */
|
||||
OUTPUT_WINDOWS_DEF, /* output a Windows .DEF file for Visual C++ or Mingw */
|
||||
OUTPUT_BORLAND_DEF, /* output a Windows .DEF file for Borland C++ */
|
||||
OUTPUT_WATCOM_LBC /* output a Watcom Linker Command File */
|
||||
|
||||
} OutputFormat;
|
||||
|
||||
|
||||
static void
|
||||
panic( const char* message )
|
||||
{
|
||||
fprintf( stderr, "PANIC: %s\n", message );
|
||||
exit(2);
|
||||
}
|
||||
|
||||
|
||||
typedef struct
|
||||
{
|
||||
char* name;
|
||||
unsigned int hash;
|
||||
|
||||
} NameRec, *Name;
|
||||
|
||||
static Name the_names;
|
||||
static int num_names;
|
||||
static int max_names;
|
||||
|
||||
static void
|
||||
names_add( const char* name,
|
||||
const char* end )
|
||||
{
|
||||
int nn, len, h;
|
||||
Name nm;
|
||||
|
||||
if ( end <= name )
|
||||
return;
|
||||
|
||||
/* compute hash value */
|
||||
len = (int)(end - name);
|
||||
h = 0;
|
||||
for ( nn = 0; nn < len; nn++ )
|
||||
h = h*33 + name[nn];
|
||||
|
||||
/* check for an pre-existing name */
|
||||
for ( nn = 0; nn < num_names; nn++ )
|
||||
{
|
||||
nm = the_names + nn;
|
||||
|
||||
if ( nm->hash == h &&
|
||||
memcmp( name, nm->name, len ) == 0 &&
|
||||
nm->name[len] == 0 )
|
||||
return;
|
||||
}
|
||||
|
||||
/* add new name */
|
||||
if ( num_names >= max_names )
|
||||
{
|
||||
max_names += (max_names >> 1) + 4;
|
||||
the_names = realloc( the_names, sizeof(the_names[0])*max_names );
|
||||
if ( the_names == NULL )
|
||||
panic( "not enough memory" );
|
||||
}
|
||||
nm = &the_names[num_names++];
|
||||
|
||||
nm->hash = h;
|
||||
nm->name = malloc( len+1 );
|
||||
if ( nm->name == NULL )
|
||||
panic( "not enough memory" );
|
||||
|
||||
memcpy( nm->name, name, len );
|
||||
nm->name[len] = 0;
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
name_compare( const void* name1,
|
||||
const void* name2 )
|
||||
{
|
||||
Name n1 = (Name)name1;
|
||||
Name n2 = (Name)name2;
|
||||
|
||||
return strcmp( n1->name, n2->name );
|
||||
}
|
||||
|
||||
static void
|
||||
names_sort( void )
|
||||
{
|
||||
qsort( the_names, (size_t)num_names, sizeof(the_names[0]), name_compare );
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
names_dump( FILE* out,
|
||||
OutputFormat format,
|
||||
const char* dll_name )
|
||||
{
|
||||
int nn;
|
||||
|
||||
switch ( format )
|
||||
{
|
||||
case OUTPUT_WINDOWS_DEF:
|
||||
if ( dll_name )
|
||||
fprintf( out, "LIBRARY %s\n", dll_name );
|
||||
|
||||
fprintf( out, "DESCRIPTION FreeType 2 DLL\n" );
|
||||
fprintf( out, "EXPORTS\n" );
|
||||
for ( nn = 0; nn < num_names; nn++ )
|
||||
fprintf( out, " %s\n", the_names[nn].name );
|
||||
break;
|
||||
|
||||
case OUTPUT_BORLAND_DEF:
|
||||
if ( dll_name )
|
||||
fprintf( out, "LIBRARY %s\n", dll_name );
|
||||
|
||||
fprintf( out, "DESCRIPTION FreeType 2 DLL\n" );
|
||||
fprintf( out, "EXPORTS\n" );
|
||||
for ( nn = 0; nn < num_names; nn++ )
|
||||
fprintf( out, " _%s\n", the_names[nn].name );
|
||||
break;
|
||||
|
||||
case OUTPUT_WATCOM_LBC:
|
||||
{
|
||||
/* we must omit the .dll suffix from the library name */
|
||||
char temp[512];
|
||||
char* dot;
|
||||
|
||||
if ( dll_name == NULL )
|
||||
{
|
||||
fprintf( stderr,
|
||||
"you must provide a DLL name with the -d option !!\n" );
|
||||
exit(4);
|
||||
}
|
||||
|
||||
dot = strchr( dll_name, '.' );
|
||||
if ( dot != NULL )
|
||||
{
|
||||
int len = (dot - dll_name);
|
||||
if ( len > sizeof(temp)-1 )
|
||||
len = sizeof(temp)-1;
|
||||
|
||||
memcpy( temp, dll_name, len );
|
||||
temp[len] = 0;
|
||||
|
||||
dll_name = (const char*)temp;
|
||||
}
|
||||
|
||||
for ( nn = 0; nn < num_names; nn++ )
|
||||
fprintf( out, "++_%s.%s.%s\n", the_names[nn].name, dll_name,
|
||||
the_names[nn].name );
|
||||
}
|
||||
break;
|
||||
|
||||
default: /* LIST */
|
||||
for ( nn = 0; nn < num_names; nn++ )
|
||||
fprintf( out, "%s\n", the_names[nn].name );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/* states of the line parser */
|
||||
|
||||
typedef enum
|
||||
{
|
||||
STATE_START = 0, /* waiting for FT_EXPORT keyword and return type */
|
||||
STATE_TYPE, /* type was read, waiting for function name */
|
||||
|
||||
} State;
|
||||
|
||||
static int
|
||||
read_header_file( FILE* file, int verbose )
|
||||
{
|
||||
static char buff[ LINEBUFF_SIZE+1 ];
|
||||
State state = STATE_START;
|
||||
|
||||
while ( !feof( file ) )
|
||||
{
|
||||
char* p;
|
||||
|
||||
if ( !fgets( buff, LINEBUFF_SIZE, file ) )
|
||||
break;
|
||||
|
||||
p = buff;
|
||||
|
||||
while ( *p && (*p == ' ' || *p == '\\') ) /* skip leading whitespace */
|
||||
p++;
|
||||
|
||||
if ( *p == '\n' || *p == '\r' ) /* skip empty lines */
|
||||
continue;
|
||||
|
||||
switch ( state )
|
||||
{
|
||||
case STATE_START:
|
||||
{
|
||||
if ( memcmp( p, "FT_EXPORT(", 10 ) != 0 )
|
||||
break;
|
||||
|
||||
p += 10;
|
||||
for (;;)
|
||||
{
|
||||
if ( *p == 0 || *p == '\n' || *p == '\r' )
|
||||
goto NextLine;
|
||||
|
||||
if ( *p == ')' )
|
||||
{
|
||||
p++;
|
||||
break;
|
||||
}
|
||||
|
||||
p++;
|
||||
}
|
||||
|
||||
state = STATE_TYPE;
|
||||
|
||||
/* sometimes, the name is just after the FT_EXPORT(...), so
|
||||
* skip whitespace, and fall-through if we find an alphanumeric
|
||||
* character
|
||||
*/
|
||||
while ( *p == ' ' || *p == '\t' )
|
||||
p++;
|
||||
|
||||
if ( !isalpha(*p) )
|
||||
break;
|
||||
}
|
||||
/* fall-through */
|
||||
|
||||
case STATE_TYPE:
|
||||
{
|
||||
char* name = p;
|
||||
size_t func_len;
|
||||
|
||||
while ( isalnum(*p) || *p == '_' )
|
||||
p++;
|
||||
|
||||
if ( p > name )
|
||||
{
|
||||
if ( verbose )
|
||||
fprintf( stderr, ">>> %.*s\n", p-name, name );
|
||||
|
||||
names_add( name, p );
|
||||
}
|
||||
|
||||
state = STATE_START;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
;
|
||||
}
|
||||
|
||||
NextLine:
|
||||
;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
usage( void )
|
||||
{
|
||||
fprintf( stderr,
|
||||
"%s %s: extract FreeType API names from header files\n\n"
|
||||
"this program is used to extract the list of public FreeType API\n"
|
||||
"functions. It receives the list of header files as argument and\n"
|
||||
"generates a sorted list of unique identifiers\n\n"
|
||||
|
||||
"usage: %s header1 [options] [header2 ...]\n\n"
|
||||
|
||||
"options: - : parse the content of stdin, ignore arguments\n"
|
||||
" -v : verbose mode, output sent to standard error\n",
|
||||
" -oFILE : write output to FILE instead of standard output\n"
|
||||
" -dNAME : indicate DLL file name, 'freetype.dll' by default\n"
|
||||
" -w : output .DEF file for Visual C++ and Mingw\n"
|
||||
" -wB : output .DEF file for Borland C++\n"
|
||||
" -wW : output Watcom Linker Response File\n"
|
||||
"\n"
|
||||
,
|
||||
PROGRAM_NAME,
|
||||
PROGRAM_VERSION,
|
||||
PROGRAM_NAME
|
||||
);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
|
||||
int main( int argc, const char* const* argv )
|
||||
{
|
||||
int from_stdin = 0;
|
||||
int verbose = 0;
|
||||
OutputFormat format = OUTPUT_LIST; /* the default */
|
||||
FILE* out = stdout;
|
||||
const char* library_name = NULL;
|
||||
|
||||
if ( argc < 2 )
|
||||
usage();
|
||||
|
||||
/* '-' used as a single argument means read source file from stdin */
|
||||
while ( argc > 1 && argv[1][0] == '-' )
|
||||
{
|
||||
const char* arg = argv[1];
|
||||
|
||||
switch ( arg[1] )
|
||||
{
|
||||
case 'v':
|
||||
verbose = 1;
|
||||
break;
|
||||
|
||||
case 'o':
|
||||
if ( arg[2] == 0 )
|
||||
{
|
||||
if ( argc < 2 )
|
||||
usage();
|
||||
|
||||
arg = argv[2];
|
||||
argv++;
|
||||
argc--;
|
||||
}
|
||||
else
|
||||
arg += 2;
|
||||
|
||||
out = fopen( arg, "wt" );
|
||||
if ( out == NULL )
|
||||
{
|
||||
fprintf( stderr, "could not open '%s' for writing\n", argv[2] );
|
||||
exit(3);
|
||||
}
|
||||
break;
|
||||
|
||||
case 'd':
|
||||
if ( arg[2] == 0 )
|
||||
{
|
||||
if ( argc < 2 )
|
||||
usage();
|
||||
|
||||
arg = argv[2];
|
||||
argv++;
|
||||
argc--;
|
||||
}
|
||||
else
|
||||
arg += 2;
|
||||
|
||||
library_name = arg;
|
||||
break;
|
||||
|
||||
case 'w':
|
||||
format = OUTPUT_WINDOWS_DEF;
|
||||
switch ( arg[2] )
|
||||
{
|
||||
case 'B':
|
||||
format = OUTPUT_BORLAND_DEF;
|
||||
break;
|
||||
|
||||
case 'W':
|
||||
format = OUTPUT_WATCOM_LBC;
|
||||
break;
|
||||
|
||||
case 0:
|
||||
break;
|
||||
|
||||
default:
|
||||
usage();
|
||||
}
|
||||
break;
|
||||
|
||||
case 0:
|
||||
from_stdin = 1;
|
||||
break;
|
||||
|
||||
default:
|
||||
usage();
|
||||
}
|
||||
|
||||
argc--;
|
||||
argv++;
|
||||
}
|
||||
|
||||
if ( from_stdin )
|
||||
{
|
||||
read_header_file( stdin, verbose );
|
||||
}
|
||||
else
|
||||
{
|
||||
for ( --argc, argv++; argc > 0; argc--, argv++ )
|
||||
{
|
||||
FILE* file = fopen( argv[0], "rb" );
|
||||
|
||||
if ( file == NULL )
|
||||
fprintf( stderr, "unable to open '%s'\n", argv[0] );
|
||||
else
|
||||
{
|
||||
if ( verbose )
|
||||
fprintf( stderr, "opening '%s'\n", argv[0] );
|
||||
|
||||
read_header_file( file, verbose );
|
||||
fclose( file );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( num_names == 0 )
|
||||
panic( "could not find exported functions !!\n" );
|
||||
|
||||
names_sort();
|
||||
names_dump( out, format, library_name );
|
||||
|
||||
if ( out != stdout )
|
||||
fclose( out );
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -420,7 +420,7 @@
|
|||
|
||||
|
||||
/* check that we can add the contours to the glyph */
|
||||
error = FT_GlyphLoader_CheckPoints( gloader, 0, n_contours );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( gloader, 0, n_contours );
|
||||
if ( error )
|
||||
goto Fail;
|
||||
|
||||
|
@ -441,7 +441,7 @@
|
|||
n_points = cont[-1] + 1;
|
||||
|
||||
/* note that we will add four phantom points later */
|
||||
error = FT_GlyphLoader_CheckPoints( gloader, n_points + 4, 0 );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( gloader, n_points + 4, 0 );
|
||||
if ( error )
|
||||
goto Fail;
|
||||
|
||||
|
@ -1106,9 +1106,9 @@
|
|||
outline = &loader->gloader->base.outline;
|
||||
|
||||
/* make room for phantom points */
|
||||
error = FT_GlyphLoader_CheckPoints( loader->gloader,
|
||||
outline->n_points + 4,
|
||||
0 );
|
||||
error = FT_GLYPHLOADER_CHECK_POINTS( loader->gloader,
|
||||
outline->n_points + 4,
|
||||
0 );
|
||||
if ( error )
|
||||
return error;
|
||||
|
||||
|
|
Loading…
Reference in New Issue