ref: e421a0bffc13299f3d8f0229a312991d85bcc23a
parent: deb261556a0af4495233b782c2aa74a53af4d478
author: Werner Lemberg <[email protected]>
date: Sat Sep 10 04:02:30 EDT 2016
[sfnt] Fix previous commit. Problems reported as https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=40 We now map the strike index right before accessing the physical data, not earlier. * src/sfnt/sfobjs.c (sfnt_load_face): Set `face->sbit_strike_map' after creating the map so that... * src/sfnt/ttsbit.c (tt_face_load_strike_metrics): ... this function can be used before and after setting up `sbit_strike_map'. (tt_face_set_sbit_strike): Revert change. (tt_sbit_decoder_init, tt_face_load_sbix_image): Map strike index. * src/truetype/ttdriver.c (tt_size_select): Revert change.
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,24 @@
+2016-09-10 Werner Lemberg <[email protected]>
+
+ [sfnt] Fix previous commit.
+
+ Problems reported as
+
+ https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=40
+
+ We now map the strike index right before accessing the physical
+ data, not earlier.
+
+ * src/sfnt/sfobjs.c (sfnt_load_face): Set `face->sbit_strike_map'
+ after creating the map so that...
+
+ * src/sfnt/ttsbit.c (tt_face_load_strike_metrics): ... this function
+ can be used before and after setting up `sbit_strike_map'.
+ (tt_face_set_sbit_strike): Revert change.
+ (tt_sbit_decoder_init, tt_face_load_sbix_image): Map strike index.
+
+ * src/truetype/ttdriver.c (tt_size_select): Revert change.
+
2016-09-09 Werner Lemberg <[email protected]>
[ftfuzzer] Minor improvements.
--- a/src/sfnt/sfobjs.c
+++ b/src/sfnt/sfobjs.c
@@ -1423,7 +1423,8 @@
FT_Short avgwidth = face->os2.xAvgCharWidth;
FT_Size_Metrics metrics;
- FT_UInt strike_idx, bsize_idx;
+ FT_UInt* sbit_strike_map = NULL;
+ FT_UInt strike_idx, bsize_idx;
if ( em_size == 0 || face->os2.version == 0xFFFFU )
@@ -1436,7 +1437,7 @@
/* of `FT_Face', we map `available_sizes' indices to strike */
/* indices */
if ( FT_NEW_ARRAY( root->available_sizes, count ) ||
- FT_NEW_ARRAY( face->sbit_strike_map, count ) )
+ FT_NEW_ARRAY( sbit_strike_map, count ) )
goto Exit;
bsize_idx = 0;
@@ -1447,7 +1448,7 @@
error = sfnt->load_strike_metrics( face, strike_idx, &metrics );
if ( error )
- goto Exit;
+ continue;
bsize->height = (FT_Short)( metrics.height >> 6 );
bsize->width = (FT_Short)(
@@ -1461,14 +1462,21 @@
/* only use strikes with valid PPEM values */
if ( bsize->x_ppem && bsize->y_ppem )
- face->sbit_strike_map[bsize_idx++] = strike_idx;
+ sbit_strike_map[bsize_idx++] = strike_idx;
}
/* reduce array size to the actually used elements */
- (void)FT_RENEW_ARRAY( face->sbit_strike_map, count, bsize_idx );
+ (void)FT_RENEW_ARRAY( sbit_strike_map, count, bsize_idx );
- root->face_flags |= FT_FACE_FLAG_FIXED_SIZES;
- root->num_fixed_sizes = (FT_Int)bsize_idx;
+ /* from now on, all strike indices are mapped */
+ /* using `sbit_strike_map' */
+ if ( bsize_idx )
+ {
+ face->sbit_strike_map = sbit_strike_map;
+
+ root->face_flags |= FT_FACE_FLAG_FIXED_SIZES;
+ root->num_fixed_sizes = (FT_Int)bsize_idx;
+ }
}
}
--- a/src/sfnt/ttsbit.c
+++ b/src/sfnt/ttsbit.c
@@ -251,14 +251,7 @@
FT_Size_Request req,
FT_ULong* astrike_index )
{
- FT_Error error;
-
-
- error = FT_Match_Size( (FT_Face)face, req, 0, astrike_index );
- if ( !error )
- *astrike_index = face->sbit_strike_map[*astrike_index];
-
- return error;
+ return FT_Match_Size( (FT_Face)face, req, 0, astrike_index );
}
@@ -267,9 +260,23 @@
FT_ULong strike_index,
FT_Size_Metrics* metrics )
{
- if ( strike_index >= (FT_ULong)face->sbit_num_strikes )
- return FT_THROW( Invalid_Argument );
+ /* we have to test for the existence of `sbit_strike_map' */
+ /* because the function gets also used at the very beginning */
+ /* to construct `sbit_strike_map' itself */
+ if ( face->sbit_strike_map )
+ {
+ if ( strike_index >= (FT_ULong)face->root.num_fixed_sizes )
+ return FT_THROW( Invalid_Argument );
+ /* map to real index */
+ strike_index = face->sbit_strike_map[strike_index];
+ }
+ else
+ {
+ if ( strike_index >= (FT_ULong)face->sbit_num_strikes )
+ return FT_THROW( Invalid_Argument );
+ }
+
switch ( (FT_UInt)face->sbit_table_type )
{
case TT_SBIT_TABLE_TYPE_EBLC:
@@ -457,6 +464,8 @@
FT_Stream stream = face->root.stream;
+ strike_index = face->sbit_strike_map[strike_index];
+
if ( !face->ebdt_size )
goto Exit;
if ( FT_STREAM_SEEK( face->ebdt_start ) )
@@ -1417,6 +1426,8 @@
FT_UNUSED( map );
+
+ strike_index = face->sbit_strike_map[strike_index];
metrics->width = 0;
metrics->height = 0;
--- a/src/truetype/ttdriver.c
+++ b/src/truetype/ttdriver.c
@@ -273,21 +273,19 @@
static FT_Error
tt_size_select( FT_Size size,
- FT_ULong bsize_index )
+ FT_ULong strike_index )
{
TT_Face ttface = (TT_Face)size->face;
TT_Size ttsize = (TT_Size)size;
FT_Error error = FT_Err_Ok;
- FT_UInt strike_index = ttface->sbit_strike_map[bsize_index];
-
ttsize->strike_index = strike_index;
if ( FT_IS_SCALABLE( size->face ) )
{
/* use the scaled metrics, even when tt_size_reset fails */
- FT_Select_Metrics( size->face, bsize_index );
+ FT_Select_Metrics( size->face, strike_index );
tt_size_reset( ttsize ); /* ignore return value */
}