* src/otvalid/otvcommn.c, src/otvalid/otvcommn.h
(otv_Coverage_validate): Add fourth argument to pass an expected count value. Update all users. Check glyph IDs. (otv_ClassDef_validate): Check `StartGlyph'. * src/otvalid/otvgsub.c (otv_SingleSubst_validate): More glyph ID checks. * src/otvalid/otvmath.c (otv_MathConstants_validate): There are only 56 constants. (otv_GlyphAssembly_validate, otv_MathGlyphConstruction_validate): Check glyph IDs.
This commit is contained in:
parent
d76fe5a1af
commit
3f1905b191
16
ChangeLog
16
ChangeLog
@ -1,3 +1,19 @@
|
||||
2007-08-11 George Williams <gww@silcom.com>
|
||||
|
||||
* src/otvalid/otvcommn.c, src/otvalid/otvcommn.h
|
||||
(otv_Coverage_validate): Add fourth argument to pass an expected
|
||||
count value. Update all users.
|
||||
Check glyph IDs.
|
||||
(otv_ClassDef_validate): Check `StartGlyph'.
|
||||
|
||||
* src/otvalid/otvgsub.c (otv_SingleSubst_validate): More glyph ID
|
||||
checks.
|
||||
|
||||
* src/otvalid/otvmath.c (otv_MathConstants_validate): There are only
|
||||
56 constants.
|
||||
(otv_GlyphAssembly_validate, otv_MathGlyphConstruction_validate):
|
||||
Check glyph IDs.
|
||||
|
||||
2007-08-08 Werner Lemberg <wl@gnu.org>
|
||||
|
||||
* src/otvalid/otvbase.c, src/otvalid/otvcommn.c,
|
||||
|
@ -39,10 +39,12 @@
|
||||
|
||||
FT_LOCAL_DEF( void )
|
||||
otv_Coverage_validate( FT_Bytes table,
|
||||
OTV_Validator valid )
|
||||
OTV_Validator valid,
|
||||
FT_Int expected_count )
|
||||
{
|
||||
FT_Bytes p = table;
|
||||
FT_UInt CoverageFormat;
|
||||
FT_UInt total = 0;
|
||||
|
||||
|
||||
OTV_NAME_ENTER( "Coverage" );
|
||||
@ -57,6 +59,7 @@
|
||||
case 1: /* CoverageFormat1 */
|
||||
{
|
||||
FT_UInt GlyphCount;
|
||||
FT_UInt i;
|
||||
|
||||
|
||||
GlyphCount = FT_NEXT_USHORT( p );
|
||||
@ -64,13 +67,25 @@
|
||||
OTV_TRACE(( " (GlyphCount = %d)\n", GlyphCount ));
|
||||
|
||||
OTV_LIMIT_CHECK( GlyphCount * 2 ); /* GlyphArray */
|
||||
|
||||
for ( i = 0; i < GlyphCount; ++i )
|
||||
{
|
||||
FT_UInt gid;
|
||||
|
||||
|
||||
gid = FT_NEXT_USHORT( p );
|
||||
if ( gid >= valid->glyph_count )
|
||||
FT_INVALID_GLYPH_ID;
|
||||
}
|
||||
|
||||
total = GlyphCount;
|
||||
}
|
||||
break;
|
||||
|
||||
case 2: /* CoverageFormat2 */
|
||||
{
|
||||
FT_UInt n, RangeCount;
|
||||
FT_UInt Start, End, StartCoverageIndex, total = 0, last = 0;
|
||||
FT_UInt Start, End, StartCoverageIndex, last = 0;
|
||||
|
||||
|
||||
RangeCount = FT_NEXT_USHORT( p );
|
||||
@ -89,6 +104,9 @@
|
||||
if ( Start > End || StartCoverageIndex != total )
|
||||
FT_INVALID_DATA;
|
||||
|
||||
if ( End >= valid->glyph_count )
|
||||
FT_INVALID_GLYPH_ID;
|
||||
|
||||
if ( n > 0 && Start <= last )
|
||||
FT_INVALID_DATA;
|
||||
|
||||
@ -102,8 +120,11 @@
|
||||
FT_INVALID_FORMAT;
|
||||
}
|
||||
|
||||
/* no need to check glyph indices used as input to coverage tables */
|
||||
/* since even invalid glyph indices return a meaningful result */
|
||||
/* Generally, a coverage table offset has an associated count field. */
|
||||
/* The number of glyphs in the table should match this field. If */
|
||||
/* there is no associated count, a value of -1 tells us not to check. */
|
||||
if ( expected_count != -1 && (FT_UInt)expected_count != total )
|
||||
FT_INVALID_DATA;
|
||||
|
||||
OTV_EXIT;
|
||||
}
|
||||
@ -215,18 +236,21 @@
|
||||
{
|
||||
case 1: /* ClassDefFormat1 */
|
||||
{
|
||||
FT_UInt StartGlyph;
|
||||
FT_UInt GlyphCount;
|
||||
|
||||
|
||||
p += 2; /* skip StartGlyph */
|
||||
|
||||
OTV_LIMIT_CHECK( 2 );
|
||||
OTV_LIMIT_CHECK( 4 );
|
||||
|
||||
StartGlyph = FT_NEXT_USHORT( p );
|
||||
GlyphCount = FT_NEXT_USHORT( p );
|
||||
|
||||
OTV_TRACE(( " (GlyphCount = %d)\n", GlyphCount ));
|
||||
|
||||
OTV_LIMIT_CHECK( GlyphCount * 2 ); /* ClassValueArray */
|
||||
|
||||
if ( StartGlyph + GlyphCount - 1 >= valid->glyph_count )
|
||||
FT_INVALID_GLYPH_ID;
|
||||
}
|
||||
break;
|
||||
|
||||
@ -252,6 +276,9 @@
|
||||
if ( Start > End || ( n > 0 && Start <= last ) )
|
||||
FT_INVALID_DATA;
|
||||
|
||||
if ( End >= valid->glyph_count )
|
||||
FT_INVALID_GLYPH_ID;
|
||||
|
||||
last = End;
|
||||
}
|
||||
}
|
||||
@ -660,7 +687,7 @@
|
||||
|
||||
OTV_TRACE(( " (Count = %d)\n", Count ));
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, Count );
|
||||
|
||||
OTV_LIMIT_CHECK( Count * 2 );
|
||||
|
||||
@ -827,7 +854,7 @@
|
||||
|
||||
OTV_TRACE(( " (ClassSetCount = %d)\n", ClassSetCount ));
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, -1 );
|
||||
otv_ClassDef_validate( table + ClassDef, valid );
|
||||
|
||||
OTV_LIMIT_CHECK( ClassSetCount * 2 );
|
||||
@ -875,7 +902,7 @@
|
||||
OTV_LIMIT_CHECK( GlyphCount * 2 + Count * 4 );
|
||||
|
||||
for ( count1 = GlyphCount; count1 > 0; count1-- )
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid );
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid, -1 );
|
||||
|
||||
for ( ; Count > 0; Count-- )
|
||||
{
|
||||
@ -916,7 +943,7 @@
|
||||
|
||||
OTV_TRACE(( " (ChainClassSetCount = %d)\n", ChainClassSetCount ));
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, -1 );
|
||||
|
||||
otv_ClassDef_validate( table + BacktrackClassDef, valid );
|
||||
otv_ClassDef_validate( table + InputClassDef, valid );
|
||||
@ -966,7 +993,7 @@
|
||||
OTV_LIMIT_CHECK( BacktrackGlyphCount * 2 + 2 );
|
||||
|
||||
for ( ; BacktrackGlyphCount > 0; BacktrackGlyphCount-- )
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid );
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid, -1 );
|
||||
|
||||
InputGlyphCount = FT_NEXT_USHORT( p );
|
||||
|
||||
@ -975,7 +1002,7 @@
|
||||
OTV_LIMIT_CHECK( InputGlyphCount * 2 + 2 );
|
||||
|
||||
for ( count1 = InputGlyphCount; count1 > 0; count1-- )
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid );
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid, -1 );
|
||||
|
||||
LookaheadGlyphCount = FT_NEXT_USHORT( p );
|
||||
|
||||
@ -984,7 +1011,7 @@
|
||||
OTV_LIMIT_CHECK( LookaheadGlyphCount * 2 + 2 );
|
||||
|
||||
for ( ; LookaheadGlyphCount > 0; LookaheadGlyphCount-- )
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid );
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid, -1 );
|
||||
|
||||
count2 = FT_NEXT_USHORT( p );
|
||||
|
||||
|
@ -4,7 +4,7 @@
|
||||
/* */
|
||||
/* OpenType common tables validation (specification). */
|
||||
/* */
|
||||
/* Copyright 2004, 2005 by */
|
||||
/* Copyright 2004, 2005, 2007 by */
|
||||
/* David Turner, Robert Wilhelm, and Werner Lemberg. */
|
||||
/* */
|
||||
/* This file is part of the FreeType project, and may only be used, */
|
||||
@ -215,7 +215,8 @@ FT_BEGIN_HEADER
|
||||
|
||||
FT_LOCAL( void )
|
||||
otv_Coverage_validate( FT_Bytes table,
|
||||
OTV_Validator valid );
|
||||
OTV_Validator valid,
|
||||
FT_Int expected_count );
|
||||
|
||||
/* return first covered glyph */
|
||||
FT_LOCAL( FT_UInt )
|
||||
|
@ -61,7 +61,7 @@
|
||||
|
||||
OTV_TRACE(( " (GlyphCount = %d)\n", GlyphCount ));
|
||||
|
||||
otv_Coverage_validate( Coverage, valid );
|
||||
otv_Coverage_validate( Coverage, valid, GlyphCount );
|
||||
if ( GlyphCount != otv_Coverage_get_count( Coverage ) )
|
||||
FT_INVALID_DATA;
|
||||
|
||||
|
@ -124,8 +124,8 @@
|
||||
Array1 = FT_NEXT_USHORT( p );
|
||||
Array2 = FT_NEXT_USHORT( p );
|
||||
|
||||
otv_Coverage_validate( table + Coverage1, valid );
|
||||
otv_Coverage_validate( table + Coverage2, valid );
|
||||
otv_Coverage_validate( table + Coverage1, valid, -1 );
|
||||
otv_Coverage_validate( table + Coverage2, valid, -1 );
|
||||
|
||||
otv_MarkArray_validate( table + Array1, valid );
|
||||
|
||||
@ -376,7 +376,7 @@
|
||||
Coverage = FT_NEXT_USHORT( p );
|
||||
ValueFormat = FT_NEXT_USHORT( p );
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, -1 );
|
||||
otv_ValueRecord_validate( p, ValueFormat, valid ); /* Value */
|
||||
}
|
||||
break;
|
||||
@ -395,7 +395,7 @@
|
||||
|
||||
len_value = otv_value_length( ValueFormat );
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, ValueCount );
|
||||
|
||||
OTV_LIMIT_CHECK( ValueCount * len_value );
|
||||
|
||||
@ -498,7 +498,7 @@
|
||||
|
||||
OTV_TRACE(( " (PairSetCount = %d)\n", PairSetCount ));
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, -1 );
|
||||
|
||||
OTV_LIMIT_CHECK( PairSetCount * 2 );
|
||||
|
||||
@ -530,7 +530,7 @@
|
||||
len_value1 = otv_value_length( ValueFormat1 );
|
||||
len_value2 = otv_value_length( ValueFormat2 );
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, -1 );
|
||||
otv_ClassDef_validate( table + ClassDef1, valid );
|
||||
otv_ClassDef_validate( table + ClassDef2, valid );
|
||||
|
||||
@ -605,7 +605,7 @@
|
||||
|
||||
OTV_TRACE(( " (EntryExitCount = %d)\n", EntryExitCount ));
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, EntryExitCount );
|
||||
|
||||
OTV_LIMIT_CHECK( EntryExitCount * 4 );
|
||||
|
||||
|
@ -68,15 +68,19 @@
|
||||
Coverage = table + FT_NEXT_USHORT( p );
|
||||
DeltaGlyphID = FT_NEXT_SHORT( p );
|
||||
|
||||
otv_Coverage_validate( Coverage, valid );
|
||||
otv_Coverage_validate( Coverage, valid, -1 );
|
||||
|
||||
idx = otv_Coverage_get_first( Coverage ) + DeltaGlyphID;
|
||||
if ( idx < 0 )
|
||||
FT_INVALID_DATA;
|
||||
if ( idx < 0 ||
|
||||
idx + DeltaGlyphID < 0 ||
|
||||
(FT_UInt)idx + DeltaGlyphID >= valid->glyph_count )
|
||||
FT_INVALID_GLYPH_ID;
|
||||
|
||||
idx = otv_Coverage_get_last( Coverage ) + DeltaGlyphID;
|
||||
if ( (FT_UInt)idx >= valid->glyph_count )
|
||||
FT_INVALID_DATA;
|
||||
if ( (FT_UInt)idx >= valid->glyph_count ||
|
||||
idx + DeltaGlyphID < 0 ||
|
||||
(FT_UInt)idx + DeltaGlyphID >= valid->glyph_count )
|
||||
FT_INVALID_GLYPH_ID;
|
||||
}
|
||||
break;
|
||||
|
||||
@ -91,14 +95,14 @@
|
||||
|
||||
OTV_TRACE(( " (GlyphCount = %d)\n", GlyphCount ));
|
||||
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, GlyphCount );
|
||||
|
||||
OTV_LIMIT_CHECK( GlyphCount * 2 );
|
||||
|
||||
/* Substitute */
|
||||
for ( ; GlyphCount > 0; GlyphCount-- )
|
||||
if ( FT_NEXT_USHORT( p ) >= valid->glyph_count )
|
||||
FT_INVALID_DATA;
|
||||
FT_INVALID_GLYPH_ID;
|
||||
}
|
||||
break;
|
||||
|
||||
@ -476,12 +480,12 @@
|
||||
|
||||
OTV_TRACE(( " (BacktrackGlyphCount = %d)\n", BacktrackGlyphCount ));
|
||||
|
||||
otv_Coverage_validate( Coverage, valid );
|
||||
otv_Coverage_validate( Coverage, valid, -1 );
|
||||
|
||||
OTV_LIMIT_CHECK( BacktrackGlyphCount * 2 + 2 );
|
||||
|
||||
for ( ; BacktrackGlyphCount > 0; BacktrackGlyphCount-- )
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid );
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid, -1 );
|
||||
|
||||
LookaheadGlyphCount = FT_NEXT_USHORT( p );
|
||||
|
||||
@ -490,7 +494,7 @@
|
||||
OTV_LIMIT_CHECK( LookaheadGlyphCount * 2 + 2 );
|
||||
|
||||
for ( ; LookaheadGlyphCount > 0; LookaheadGlyphCount-- )
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid );
|
||||
otv_Coverage_validate( table + FT_NEXT_USHORT( p ), valid, -1 );
|
||||
|
||||
GlyphCount = FT_NEXT_USHORT( p );
|
||||
|
||||
|
@ -55,12 +55,12 @@
|
||||
|
||||
OTV_NAME_ENTER( "MathConstants" );
|
||||
|
||||
/* 57 constants, 52 have device tables */
|
||||
OTV_LIMIT_CHECK( 2 * ( 57 + 52 ) );
|
||||
table_size = 2 * ( 57 + 52 );
|
||||
/* 56 constants, 51 have device tables */
|
||||
OTV_LIMIT_CHECK( 2 * ( 56 + 51 ) );
|
||||
table_size = 2 * ( 56 + 51 );
|
||||
|
||||
p += 4 * 2; /* First 4 constants have no device tables */
|
||||
for ( i = 0; i < 52; ++i )
|
||||
for ( i = 0; i < 51; ++i )
|
||||
{
|
||||
p += 2; /* skip the value */
|
||||
OTV_OPTIONAL_OFFSET( DeviceTableOffset );
|
||||
@ -106,7 +106,7 @@
|
||||
table_size = 4 + 4 * cnt;
|
||||
|
||||
OTV_SIZE_CHECK( Coverage );
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, cnt );
|
||||
|
||||
for ( i = 0; i < cnt; ++i )
|
||||
{
|
||||
@ -194,7 +194,7 @@
|
||||
table_size = 4 + 8 * cnt;
|
||||
|
||||
OTV_SIZE_CHECK( Coverage );
|
||||
otv_Coverage_validate( table + Coverage, valid );
|
||||
otv_Coverage_validate( table + Coverage, valid, cnt );
|
||||
|
||||
for ( i = 0; i < cnt; ++i )
|
||||
{
|
||||
@ -248,7 +248,7 @@
|
||||
|
||||
if ( ExtendedShapeCoverage ) {
|
||||
OTV_NAME_ENTER( "ExtendedShapeCoverage" );
|
||||
otv_Coverage_validate( table + ExtendedShapeCoverage, valid );
|
||||
otv_Coverage_validate( table + ExtendedShapeCoverage, valid, -1 );
|
||||
OTV_EXIT;
|
||||
}
|
||||
|
||||
@ -273,6 +273,7 @@
|
||||
{
|
||||
FT_Bytes p = table;
|
||||
FT_UInt pcnt, table_size;
|
||||
FT_UInt i;
|
||||
|
||||
OTV_OPTIONAL_TABLE( DeviceTableOffset );
|
||||
|
||||
@ -292,6 +293,17 @@
|
||||
if ( DeviceTableOffset )
|
||||
otv_Device_validate( table + DeviceTableOffset, valid );
|
||||
|
||||
for ( i = 0; i < pcnt; ++i )
|
||||
{
|
||||
FT_UInt gid;
|
||||
|
||||
|
||||
gid = FT_NEXT_USHORT( p );
|
||||
if ( gid >= valid->glyph_count )
|
||||
FT_INVALID_GLYPH_ID;
|
||||
p += 2*4; /* skip the Start, End, Full, and Flags fields */
|
||||
}
|
||||
|
||||
/* OTV_EXIT; */
|
||||
}
|
||||
|
||||
@ -302,6 +314,7 @@
|
||||
{
|
||||
FT_Bytes p = table;
|
||||
FT_UInt vcnt, table_size;
|
||||
FT_UInt i;
|
||||
|
||||
OTV_OPTIONAL_TABLE( GlyphAssembly );
|
||||
|
||||
@ -316,6 +329,17 @@
|
||||
OTV_LIMIT_CHECK( 4 * vcnt );
|
||||
table_size = 4 + 4 * vcnt;
|
||||
|
||||
for ( i = 0; i < vcnt; ++i )
|
||||
{
|
||||
FT_UInt gid;
|
||||
|
||||
|
||||
gid = FT_NEXT_USHORT( p );
|
||||
if ( gid >= valid->glyph_count )
|
||||
FT_INVALID_GLYPH_ID;
|
||||
p += 2; /* skip the size */
|
||||
}
|
||||
|
||||
OTV_SIZE_CHECK( GlyphAssembly );
|
||||
if ( GlyphAssembly )
|
||||
otv_GlyphAssembly_validate( table+GlyphAssembly, valid );
|
||||
@ -351,11 +375,11 @@
|
||||
|
||||
OTV_SIZE_CHECK( VCoverage );
|
||||
if ( VCoverage )
|
||||
otv_Coverage_validate( table + VCoverage, valid );
|
||||
otv_Coverage_validate( table + VCoverage, valid, vcnt );
|
||||
|
||||
OTV_SIZE_CHECK( HCoverage );
|
||||
if ( HCoverage )
|
||||
otv_Coverage_validate( table + HCoverage, valid );
|
||||
otv_Coverage_validate( table + HCoverage, valid, hcnt );
|
||||
|
||||
for ( i = 0; i < vcnt; ++i )
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user