Fixes for bugs uncovered by libFuzzer analysis. A write past buffer, … · google/woff2@a15a8ab (original) (raw)
`@@ -70,6 +70,10 @@ const size_t kCompositeGlyphBegin = 10;
`
70
70
`// Largest glyph ever observed was 72k bytes
`
71
71
`const size_t kDefaultGlyphBuf = 5120;
`
72
72
``
``
73
`+
// Over 14k test fonts the max compression ratio seen to date was ~20.
`
``
74
`+
// >100 suggests you wrote a bad uncompressed size.
`
``
75
`+
const float kMaxPlausibleCompressionRatio = 100.0;
`
``
76
+
73
77
`// metadata for a TTC font entry
`
74
78
`struct TtcFont {
`
75
79
`uint32_t flavor;
`
`@@ -478,7 +482,7 @@ bool ReconstructGlyf(const uint8_t* data, Table* glyf_table,
`
478
482
` }
`
479
483
` }
`
480
484
``
481
``
`-
size_t size_needed = 2 + composite_size + instruction_size;
`
``
485
`+
size_t size_needed = 12 + composite_size + instruction_size;
`
482
486
`if (PREDICT_FALSE(glyph_buf_size < size_needed)) {
`
483
487
` glyph_buf.reset(new uint8_t[size_needed]);
`
484
488
` glyph_buf_size = size_needed;
`
`@@ -672,6 +676,11 @@ bool ReconstructTransformedHmtx(const uint8_t* transformed_buf,
`
672
676
``
673
677
`assert(x_mins.size() == num_glyphs);
`
674
678
``
``
679
`+
// num_glyphs 0 is OK if there is no 'glyf' but cannot then xform 'hmtx'.
`
``
680
`+
if (PREDICT_FALSE(num_hmetrics > num_glyphs)) {
`
``
681
`+
return FONT_COMPRESSION_FAILURE();
`
``
682
`+
}
`
``
683
+
675
684
`for (uint16_t i = 0; i < num_hmetrics; i++) {
`
676
685
`uint16_t advance_width;
`
677
686
`if (PREDICT_FALSE(!hmtx_buff_in.ReadU16(&advance_width))) {
`
`@@ -1270,6 +1279,14 @@ bool ConvertWOFF2ToTTF(const uint8_t* data, size_t length,
`
1270
1279
`return FONT_COMPRESSION_FAILURE();
`
1271
1280
` }
`
1272
1281
``
``
1282
`+
const float compression_ratio = (float) hdr.uncompressed_size / length;
`
``
1283
`+
if (compression_ratio > kMaxPlausibleCompressionRatio) {
`
``
1284
`+
#ifdef FONT_COMPRESSION_BIN
`
``
1285
`+
fprintf(stderr, "Implausible compression ratio %.01f\n", compression_ratio);
`
``
1286
`+
#endif
`
``
1287
`+
return FONT_COMPRESSION_FAILURE();
`
``
1288
`+
}
`
``
1289
+
1273
1290
`const uint8_t* src_buf = data + hdr.compressed_offset;
`
1274
1291
` std::vector uncompressed_buf(hdr.uncompressed_size);
`
1275
1292
`if (PREDICT_FALSE(!Woff2Uncompress(&uncompressed_buf[0],
`