| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "gsub.h" | 5 #include "gsub.h" |
| 6 | 6 |
| 7 #include <limits> | 7 #include <limits> |
| 8 #include <vector> | 8 #include <vector> |
| 9 | 9 |
| 10 #include "layout.h" | 10 #include "layout.h" |
| (...skipping 510 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 521 length - offsets_lookahead[i], num_glyphs)) { | 521 length - offsets_lookahead[i], num_glyphs)) { |
| 522 return OTS_FAILURE_MSG("Failed to parse lookahead coverage table %d in rev
erse chaining table", i); | 522 return OTS_FAILURE_MSG("Failed to parse lookahead coverage table %d in rev
erse chaining table", i); |
| 523 } | 523 } |
| 524 } | 524 } |
| 525 | 525 |
| 526 return true; | 526 return true; |
| 527 } | 527 } |
| 528 | 528 |
| 529 } // namespace | 529 } // namespace |
| 530 | 530 |
| 531 #define DROP_THIS_TABLE(msg_) \ | |
| 532 do { \ | |
| 533 OTS_FAILURE_MSG(msg_ ", table discarded"); \ | |
| 534 font->gsub->data = 0; \ | |
| 535 font->gsub->length = 0; \ | |
| 536 } while (0) | |
| 537 | |
| 538 namespace ots { | 531 namespace ots { |
| 539 | 532 |
| 540 // As far as I checked, following fonts contain invalid values in GSUB table. | 533 // As far as I checked, following fonts contain invalid values in GSUB table. |
| 541 // OTS will drop their GSUB table. | 534 // OTS will drop their GSUB table. |
| 542 // | 535 // |
| 543 // # too large substitute (value is 0xFFFF) | 536 // # too large substitute (value is 0xFFFF) |
| 544 // kaiu.ttf | 537 // kaiu.ttf |
| 545 // mingliub2.ttf | 538 // mingliub2.ttf |
| 546 // mingliub1.ttf | 539 // mingliub1.ttf |
| 547 // mingliub0.ttf | 540 // mingliub0.ttf |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 599 font->gsub = gsub; | 592 font->gsub = gsub; |
| 600 | 593 |
| 601 uint32_t version = 0; | 594 uint32_t version = 0; |
| 602 uint16_t offset_script_list = 0; | 595 uint16_t offset_script_list = 0; |
| 603 uint16_t offset_feature_list = 0; | 596 uint16_t offset_feature_list = 0; |
| 604 uint16_t offset_lookup_list = 0; | 597 uint16_t offset_lookup_list = 0; |
| 605 if (!table.ReadU32(&version) || | 598 if (!table.ReadU32(&version) || |
| 606 !table.ReadU16(&offset_script_list) || | 599 !table.ReadU16(&offset_script_list) || |
| 607 !table.ReadU16(&offset_feature_list) || | 600 !table.ReadU16(&offset_feature_list) || |
| 608 !table.ReadU16(&offset_lookup_list)) { | 601 !table.ReadU16(&offset_lookup_list)) { |
| 609 DROP_THIS_TABLE("Incomplete table"); | 602 return OTS_FAILURE_MSG("Incomplete table"); |
| 610 return true; | |
| 611 } | 603 } |
| 612 | 604 |
| 613 if (version != 0x00010000) { | 605 if (version != 0x00010000) { |
| 614 DROP_THIS_TABLE("Bad version"); | 606 return OTS_FAILURE_MSG("Bad version"); |
| 615 return true; | |
| 616 } | 607 } |
| 617 | 608 |
| 618 if (offset_lookup_list) { | 609 if (offset_lookup_list) { |
| 619 if (offset_lookup_list < kGsubHeaderSize || offset_lookup_list >= length) { | 610 if (offset_lookup_list < kGsubHeaderSize || offset_lookup_list >= length) { |
| 620 DROP_THIS_TABLE("Bad lookup list offset in table header"); | 611 return OTS_FAILURE_MSG("Bad lookup list offset in table header"); |
| 621 return true; | |
| 622 } | 612 } |
| 623 | 613 |
| 624 if (!ParseLookupListTable(font, data + offset_lookup_list, | 614 if (!ParseLookupListTable(font, data + offset_lookup_list, |
| 625 length - offset_lookup_list, | 615 length - offset_lookup_list, |
| 626 &kGsubLookupSubtableParser, | 616 &kGsubLookupSubtableParser, |
| 627 &gsub->num_lookups)) { | 617 &gsub->num_lookups)) { |
| 628 DROP_THIS_TABLE("Failed to parse lookup list table"); | 618 return OTS_FAILURE_MSG("Failed to parse lookup list table"); |
| 629 return true; | |
| 630 } | 619 } |
| 631 } | 620 } |
| 632 | 621 |
| 633 uint16_t num_features = 0; | 622 uint16_t num_features = 0; |
| 634 if (offset_feature_list) { | 623 if (offset_feature_list) { |
| 635 if (offset_feature_list < kGsubHeaderSize || offset_feature_list >= length)
{ | 624 if (offset_feature_list < kGsubHeaderSize || offset_feature_list >= length)
{ |
| 636 DROP_THIS_TABLE("Bad feature list offset in table header"); | 625 return OTS_FAILURE_MSG("Bad feature list offset in table header"); |
| 637 return true; | |
| 638 } | 626 } |
| 639 | 627 |
| 640 if (!ParseFeatureListTable(font, data + offset_feature_list, | 628 if (!ParseFeatureListTable(font, data + offset_feature_list, |
| 641 length - offset_feature_list, gsub->num_lookups, | 629 length - offset_feature_list, gsub->num_lookups, |
| 642 &num_features)) { | 630 &num_features)) { |
| 643 DROP_THIS_TABLE("Failed to parse feature list table"); | 631 return OTS_FAILURE_MSG("Failed to parse feature list table"); |
| 644 return true; | |
| 645 } | 632 } |
| 646 } | 633 } |
| 647 | 634 |
| 648 if (offset_script_list) { | 635 if (offset_script_list) { |
| 649 if (offset_script_list < kGsubHeaderSize || offset_script_list >= length) { | 636 if (offset_script_list < kGsubHeaderSize || offset_script_list >= length) { |
| 650 DROP_THIS_TABLE("Bad script list offset in table header"); | 637 return OTS_FAILURE_MSG("Bad script list offset in table header"); |
| 651 return true; | |
| 652 } | 638 } |
| 653 | 639 |
| 654 if (!ParseScriptListTable(font, data + offset_script_list, | 640 if (!ParseScriptListTable(font, data + offset_script_list, |
| 655 length - offset_script_list, num_features)) { | 641 length - offset_script_list, num_features)) { |
| 656 DROP_THIS_TABLE("Failed to parse script list table"); | 642 return OTS_FAILURE_MSG("Failed to parse script list table"); |
| 657 return true; | |
| 658 } | 643 } |
| 659 } | 644 } |
| 660 | 645 |
| 661 gsub->data = data; | 646 gsub->data = data; |
| 662 gsub->length = length; | 647 gsub->length = length; |
| 663 return true; | 648 return true; |
| 664 } | 649 } |
| 665 | 650 |
| 666 bool ots_gsub_should_serialise(Font *font) { | 651 bool ots_gsub_should_serialise(Font *font) { |
| 667 return font->gsub != NULL && font->gsub->data != NULL; | 652 return font->gsub != NULL && font->gsub->data != NULL; |
| (...skipping 12 matching lines...) Expand all Loading... |
| 680 font->gsub_reused = true; | 665 font->gsub_reused = true; |
| 681 } | 666 } |
| 682 | 667 |
| 683 void ots_gsub_free(Font *font) { | 668 void ots_gsub_free(Font *font) { |
| 684 delete font->gsub; | 669 delete font->gsub; |
| 685 } | 670 } |
| 686 | 671 |
| 687 } // namespace ots | 672 } // namespace ots |
| 688 | 673 |
| 689 #undef TABLE_NAME | 674 #undef TABLE_NAME |
| 690 #undef DROP_THIS_TABLE | |
| OLD | NEW |