Line | Count | Source |
1 | | // Copyright (c) 2018 The OTS Authors. All rights reserved. |
2 | | // Use of this source code is governed by a BSD-style license that can be |
3 | | // found in the LICENSE file. |
4 | | |
5 | | #include "vvar.h" |
6 | | |
7 | | #include "variations.h" |
8 | | |
9 | | namespace ots { |
10 | | |
11 | | // ----------------------------------------------------------------------------- |
12 | | // OpenTypeVVAR |
13 | | // ----------------------------------------------------------------------------- |
14 | | |
15 | 275 | bool OpenTypeVVAR::Parse(const uint8_t* data, size_t length) { |
16 | 275 | Buffer table(data, length); |
17 | | |
18 | 275 | uint16_t majorVersion; |
19 | 275 | uint16_t minorVersion; |
20 | 275 | uint32_t itemVariationStoreOffset; |
21 | 275 | uint32_t advanceHeightMappingOffset; |
22 | 275 | uint32_t tsbMappingOffset; |
23 | 275 | uint32_t bsbMappingOffset; |
24 | 275 | uint32_t vOrgMappingOffset; |
25 | | |
26 | 275 | if (!table.ReadU16(&majorVersion) || |
27 | 249 | !table.ReadU16(&minorVersion) || |
28 | 244 | !table.ReadU32(&itemVariationStoreOffset) || |
29 | 235 | !table.ReadU32(&advanceHeightMappingOffset) || |
30 | 233 | !table.ReadU32(&tsbMappingOffset) || |
31 | 230 | !table.ReadU32(&bsbMappingOffset) || |
32 | 226 | !table.ReadU32(&vOrgMappingOffset)) { |
33 | 61 | return DropVariations("Failed to read table header"); |
34 | 61 | } |
35 | | |
36 | 214 | if (majorVersion != 1) { |
37 | 75 | return DropVariations("Unknown table version"); |
38 | 75 | } |
39 | | |
40 | 139 | if (itemVariationStoreOffset > length || |
41 | 111 | advanceHeightMappingOffset > length || |
42 | 107 | tsbMappingOffset > length || |
43 | 97 | bsbMappingOffset > length || |
44 | 90 | vOrgMappingOffset > length) { |
45 | 56 | return DropVariations("Invalid subtable offset"); |
46 | 56 | } |
47 | | |
48 | 83 | if (!ParseItemVariationStore(GetFont(), data + itemVariationStoreOffset, |
49 | 83 | length - itemVariationStoreOffset)) { |
50 | 31 | return DropVariations("Failed to parse item variation store"); |
51 | 31 | } |
52 | | |
53 | 52 | if (advanceHeightMappingOffset) { |
54 | 51 | if (!ParseDeltaSetIndexMap(GetFont(), data + advanceHeightMappingOffset, |
55 | 51 | length - advanceHeightMappingOffset)) { |
56 | 10 | return DropVariations("Failed to parse advance height mappings"); |
57 | 10 | } |
58 | 51 | } |
59 | | |
60 | 42 | if (tsbMappingOffset) { |
61 | 22 | if (!ParseDeltaSetIndexMap(GetFont(), data + tsbMappingOffset, |
62 | 22 | length - tsbMappingOffset)) { |
63 | 8 | return DropVariations("Failed to parse TSB mappings"); |
64 | 8 | } |
65 | 22 | } |
66 | | |
67 | 34 | if (bsbMappingOffset) { |
68 | 15 | if (!ParseDeltaSetIndexMap(GetFont(), data + bsbMappingOffset, |
69 | 15 | length - bsbMappingOffset)) { |
70 | 4 | return DropVariations("Failed to parse BSB mappings"); |
71 | 4 | } |
72 | 15 | } |
73 | | |
74 | 30 | if (vOrgMappingOffset) { |
75 | 26 | if (!ParseDeltaSetIndexMap(GetFont(), data + vOrgMappingOffset, |
76 | 26 | length - vOrgMappingOffset)) { |
77 | 4 | return DropVariations("Failed to parse vOrg mappings"); |
78 | 4 | } |
79 | 26 | } |
80 | | |
81 | 26 | this->m_data = data; |
82 | 26 | this->m_length = length; |
83 | | |
84 | 26 | return true; |
85 | 30 | } |
86 | | |
87 | 10 | bool OpenTypeVVAR::Serialize(OTSStream* out) { |
88 | 10 | if (!out->Write(this->m_data, this->m_length)) { |
89 | 0 | return Error("Failed to write VVAR table"); |
90 | 0 | } |
91 | | |
92 | 10 | return true; |
93 | 10 | } |
94 | | |
95 | | } // namespace ots |