forked from minhngoc25a/freetype2
[truetype] Improve handling of buggy `prep' tables.
In case of an error in the `prep' table, no longer try to execute it again and again. This makes FreeType handle endless loops in buggy fonts much faster. * src/truetype/ttobjs.h (TT_SizeRec): The fields `bytecode_ready' and `cvt_ready' are now negative if not initialized yet, otherwise they indicate the error code of the last run. * src/truetype/ttobjs.c (tt_size_run_fpgm, tt_size_run_prep, tt_size_done_bytecode, tt_size_init_bytecode, tt_size_ready_bytecode, tt_size_init, tt_size_done, tt_size_reset): Updated. * src/truetype/ttgload.c (tt_loader_init): Updated. * src/truetype/ttinterp.c (TT_RunIns): Force reexecution of `fpgm' and `prep' only if we are in the `glyf' table.
This commit is contained in:
parent
e98e2bc1aa
commit
441b3f3898
21
ChangeLog
21
ChangeLog
|
@ -1,3 +1,24 @@
|
|||
2014-07-13 Werner Lemberg <wl@gnu.org>
|
||||
|
||||
[truetype] Improve handling of buggy `prep' tables.
|
||||
|
||||
In case of an error in the `prep' table, no longer try to execute it
|
||||
again and again. This makes FreeType handle endless loops in buggy
|
||||
fonts much faster.
|
||||
|
||||
* src/truetype/ttobjs.h (TT_SizeRec): The fields `bytecode_ready'
|
||||
and `cvt_ready' are now negative if not initialized yet, otherwise
|
||||
they indicate the error code of the last run.
|
||||
|
||||
* src/truetype/ttobjs.c (tt_size_run_fpgm, tt_size_run_prep,
|
||||
tt_size_done_bytecode, tt_size_init_bytecode,
|
||||
tt_size_ready_bytecode, tt_size_init, tt_size_done, tt_size_reset):
|
||||
Updated.
|
||||
|
||||
* src/truetype/ttgload.c (tt_loader_init): Updated.
|
||||
* src/truetype/ttinterp.c (TT_RunIns): Force reexecution of `fpgm'
|
||||
and `prep' only if we are in the `glyf' table.
|
||||
|
||||
2014-07-12 Werner Lemberg <wl@gnu.org>
|
||||
|
||||
* builds/vms/ftconfig.h: Synchronize.
|
||||
|
|
|
@ -2120,7 +2120,7 @@
|
|||
FT_Bool reexecute = FALSE;
|
||||
|
||||
|
||||
if ( !size->cvt_ready )
|
||||
if ( size->bytecode_ready < 0 || size->cvt_ready < 0 )
|
||||
{
|
||||
FT_Error error = tt_size_ready_bytecode( size, pedantic );
|
||||
|
||||
|
@ -2128,6 +2128,10 @@
|
|||
if ( error )
|
||||
return error;
|
||||
}
|
||||
else if ( size->bytecode_ready )
|
||||
return size->bytecode_ready;
|
||||
else if ( size->cvt_ready )
|
||||
return size->cvt_ready;
|
||||
|
||||
/* query new execution context */
|
||||
exec = size->debug ? size->context
|
||||
|
@ -2238,12 +2242,15 @@
|
|||
|
||||
if ( reexecute )
|
||||
{
|
||||
FT_UInt i;
|
||||
FT_UInt i;
|
||||
FT_Error error;
|
||||
|
||||
|
||||
for ( i = 0; i < size->cvt_size; i++ )
|
||||
size->cvt[i] = FT_MulFix( face->cvt[i], size->ttmetrics.scale );
|
||||
tt_size_run_prep( size, pedantic );
|
||||
error = tt_size_run_prep( size, pedantic );
|
||||
if ( error )
|
||||
return error;
|
||||
}
|
||||
|
||||
/* see whether the cvt program has disabled hinting */
|
||||
|
|
|
@ -9035,10 +9035,13 @@
|
|||
/* If any errors have occurred, function tables may be broken. */
|
||||
/* Force a re-execution of `prep' and `fpgm' tables if no */
|
||||
/* bytecode debugger is run. */
|
||||
if ( CUR.error && !CUR.instruction_trap )
|
||||
if ( CUR.error
|
||||
&& !CUR.instruction_trap
|
||||
&& CUR.curRange == tt_coderange_glyph )
|
||||
{
|
||||
FT_TRACE1(( " The interpreter returned error 0x%x\n", CUR.error ));
|
||||
exc->size->cvt_ready = FALSE;
|
||||
exc->size->bytecode_ready = -1;
|
||||
exc->size->cvt_ready = -1;
|
||||
}
|
||||
|
||||
return CUR.error;
|
||||
|
|
|
@ -813,6 +813,8 @@
|
|||
else
|
||||
error = FT_Err_Ok;
|
||||
|
||||
size->bytecode_ready = error;
|
||||
|
||||
if ( !error )
|
||||
TT_Save_Context( exec, size );
|
||||
|
||||
|
@ -884,6 +886,8 @@
|
|||
else
|
||||
error = FT_Err_Ok;
|
||||
|
||||
size->cvt_ready = error;
|
||||
|
||||
/* UNDOCUMENTED! The MS rasterizer doesn't allow the following */
|
||||
/* graphics state variables to be modified by the CVT program. */
|
||||
|
||||
|
@ -912,10 +916,6 @@
|
|||
return error;
|
||||
}
|
||||
|
||||
#endif /* TT_USE_BYTECODE_INTERPRETER */
|
||||
|
||||
|
||||
#ifdef TT_USE_BYTECODE_INTERPRETER
|
||||
|
||||
static void
|
||||
tt_size_done_bytecode( FT_Size ftsize )
|
||||
|
@ -953,8 +953,8 @@
|
|||
size->max_func = 0;
|
||||
size->max_ins = 0;
|
||||
|
||||
size->bytecode_ready = 0;
|
||||
size->cvt_ready = 0;
|
||||
size->bytecode_ready = -1;
|
||||
size->cvt_ready = -1;
|
||||
}
|
||||
|
||||
|
||||
|
@ -974,8 +974,8 @@
|
|||
TT_MaxProfile* maxp = &face->max_profile;
|
||||
|
||||
|
||||
size->bytecode_ready = 1;
|
||||
size->cvt_ready = 0;
|
||||
size->bytecode_ready = -1;
|
||||
size->cvt_ready = -1;
|
||||
|
||||
size->max_function_defs = maxp->maxFunctionDefs;
|
||||
size->max_instruction_defs = maxp->maxInstructionDefs;
|
||||
|
@ -1052,15 +1052,14 @@
|
|||
FT_Error error = FT_Err_Ok;
|
||||
|
||||
|
||||
if ( !size->bytecode_ready )
|
||||
{
|
||||
if ( size->bytecode_ready < 0 )
|
||||
error = tt_size_init_bytecode( (FT_Size)size, pedantic );
|
||||
if ( error )
|
||||
goto Exit;
|
||||
}
|
||||
|
||||
if ( error || size->bytecode_ready )
|
||||
goto Exit;
|
||||
|
||||
/* rescale CVT when needed */
|
||||
if ( !size->cvt_ready )
|
||||
if ( size->cvt_ready < 0 )
|
||||
{
|
||||
FT_UInt i;
|
||||
TT_Face face = (TT_Face)size->root.face;
|
||||
|
@ -1087,8 +1086,6 @@
|
|||
size->GS = tt_default_graphics_state;
|
||||
|
||||
error = tt_size_run_prep( size, pedantic );
|
||||
if ( !error )
|
||||
size->cvt_ready = 1;
|
||||
}
|
||||
|
||||
Exit:
|
||||
|
@ -1119,8 +1116,8 @@
|
|||
FT_Error error = FT_Err_Ok;
|
||||
|
||||
#ifdef TT_USE_BYTECODE_INTERPRETER
|
||||
size->bytecode_ready = 0;
|
||||
size->cvt_ready = 0;
|
||||
size->bytecode_ready = -1;
|
||||
size->cvt_ready = -1;
|
||||
#endif
|
||||
|
||||
size->ttmetrics.valid = FALSE;
|
||||
|
@ -1148,7 +1145,7 @@
|
|||
|
||||
|
||||
#ifdef TT_USE_BYTECODE_INTERPRETER
|
||||
if ( size->bytecode_ready )
|
||||
if ( size->bytecode_ready >= 0 )
|
||||
tt_size_done_bytecode( ttsize );
|
||||
#endif
|
||||
|
||||
|
@ -1229,7 +1226,7 @@
|
|||
}
|
||||
|
||||
#ifdef TT_USE_BYTECODE_INTERPRETER
|
||||
size->cvt_ready = 0;
|
||||
size->cvt_ready = -1;
|
||||
#endif /* TT_USE_BYTECODE_INTERPRETER */
|
||||
|
||||
if ( !error )
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
/* */
|
||||
/* Objects manager (specification). */
|
||||
/* */
|
||||
/* Copyright 1996-2009, 2011-2013 by */
|
||||
/* Copyright 1996-2009, 2011-2014 by */
|
||||
/* David Turner, Robert Wilhelm, and Werner Lemberg. */
|
||||
/* */
|
||||
/* This file is part of the FreeType project, and may only be used, */
|
||||
|
@ -333,8 +333,10 @@ FT_BEGIN_HEADER
|
|||
FT_Bool debug;
|
||||
TT_ExecContext context;
|
||||
|
||||
FT_Bool bytecode_ready;
|
||||
FT_Bool cvt_ready;
|
||||
/* if negative, `fpgm' (resp. `prep'), wasn't executed yet; */
|
||||
/* otherwise it is the returned error code */
|
||||
FT_Error bytecode_ready;
|
||||
FT_Error cvt_ready;
|
||||
|
||||
#endif /* TT_USE_BYTECODE_INTERPRETER */
|
||||
|
||||
|
|
|
@ -956,7 +956,7 @@
|
|||
if ( loader->exec->rasterizer_version != TT_INTERPRETER_VERSION_35 )
|
||||
{
|
||||
loader->exec->rasterizer_version = TT_INTERPRETER_VERSION_35;
|
||||
loader->exec->size->cvt_ready = FALSE;
|
||||
loader->exec->size->cvt_ready = -1;
|
||||
|
||||
tt_size_ready_bytecode(
|
||||
loader->exec->size,
|
||||
|
@ -971,7 +971,7 @@
|
|||
SPH_OPTION_SET_RASTERIZER_VERSION )
|
||||
{
|
||||
loader->exec->rasterizer_version = SPH_OPTION_SET_RASTERIZER_VERSION;
|
||||
loader->exec->size->cvt_ready = FALSE;
|
||||
loader->exec->size->cvt_ready = -1;
|
||||
|
||||
tt_size_ready_bytecode(
|
||||
loader->exec->size,
|
||||
|
|
Loading…
Reference in New Issue