blob: 37a0918ef5e9ceba263417f195a633bd8b7fc990 [file] [log] [blame]
Selim Gurun30d4e1f2013-08-15 12:46:15 -07001/*
2 * Copyright 2011 Google Inc. All Rights Reserved.
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_READABLE_FONT_DATA_H_
18#define SFNTLY_CPP_SRC_SFNTLY_DATA_READABLE_FONT_DATA_H_
19
20#include "sfntly/data/font_data.h"
21#include "sfntly/port/lock.h"
22
23namespace sfntly {
24
Selim Gurun30d4e1f2013-08-15 12:46:15 -070025class OutputStream;
Colin Cross13a82432017-04-07 10:50:33 -070026class WritableFontData;
Selim Gurun30d4e1f2013-08-15 12:46:15 -070027
28// Writable font data wrapper. Supports reading of data primitives in the
29// TrueType / OpenType spec.
30// The data types used are as listed:
31// BYTE 8-bit unsigned integer.
32// CHAR 8-bit signed integer.
33// USHORT 16-bit unsigned integer.
34// SHORT 16-bit signed integer.
35// UINT24 24-bit unsigned integer.
36// ULONG 32-bit unsigned integer.
37// LONG 32-bit signed integer.
38// Fixed 32-bit signed fixed-point number (16.16)
39// FUNIT Smallest measurable distance in the em space.
40// FWORD 16-bit signed integer (SHORT) that describes a quantity in FUnits.
41// UFWORD 16-bit unsigned integer (USHORT) that describes a quantity in
42// FUnits.
43// F2DOT14 16-bit signed fixed number with the low 14 bits of fraction (2.14)
44// LONGDATETIME Date represented in number of seconds since 12:00 midnight,
45// January 1, 1904. The value is represented as a signed 64-bit
46// integer.
47
48class ReadableFontData : public FontData,
49 public RefCounted<ReadableFontData> {
50 public:
51 explicit ReadableFontData(ByteArray* array);
52 virtual ~ReadableFontData();
53
Colin Cross13a82432017-04-07 10:50:33 -070054 static const int32_t kInvalidByte = 128;
55 static const int32_t kInvalidShort = 32768;
56 static const int32_t kInvalidLong = 0xffffffff;
57 static const int32_t kInvalidUnsigned = -1;
58 static const int64_t kInvalidLongDateTime = -1;
59
Selim Gurun30d4e1f2013-08-15 12:46:15 -070060 static CALLER_ATTACH ReadableFontData* CreateReadableFontData(ByteVector* b);
61
62 // Gets a computed checksum for the data. This checksum uses the OpenType spec
63 // calculation. Every ULong value (32 bit unsigned) in the data is summed and
64 // the resulting value is truncated to 32 bits. If the data length in bytes is
65 // not an integral multiple of 4 then any remaining bytes are treated as the
66 // start of a 4 byte sequence whose remaining bytes are zero.
67 // @return the checksum
68 int64_t Checksum();
69
70 // Sets the bounds to use for computing the checksum. These bounds are in
71 // begin and end pairs. If an odd number is given then the final range is
72 // assumed to extend to the end of the data. The lengths of each range must be
73 // a multiple of 4.
74 // @param ranges the range bounds to use for the checksum
75 void SetCheckSumRanges(const IntegerList& ranges);
76
77 // Read the UBYTE at the given index.
78 // @param index index into the font data
79 // @return the UBYTE; -1 if outside the bounds of the font data
80 // @throws IndexOutOfBoundsException if index is outside the FontData's range
81 virtual int32_t ReadUByte(int32_t index);
82
83 // Read the BYTE at the given index.
84 // @param index index into the font data
Colin Cross13a82432017-04-07 10:50:33 -070085 // @return the BYTE; |kInvalidByte| if outside the bounds of the font data
Selim Gurun30d4e1f2013-08-15 12:46:15 -070086 // @throws IndexOutOfBoundsException if index is outside the FontData's range
87 virtual int32_t ReadByte(int32_t index);
88
89 // Read the bytes at the given index into the array.
90 // @param index index into the font data
91 // @param b the destination for the bytes read
92 // @param offset offset in the byte array to place the bytes
93 // @param length the length of bytes to read
94 // @return the number of bytes actually read; -1 if the index is outside the
95 // bounds of the font data
96 virtual int32_t ReadBytes(int32_t index,
97 byte_t* b,
98 int32_t offset,
99 int32_t length);
100
101 // Read the CHAR at the given index.
102 // @param index index into the font data
Colin Cross13a82432017-04-07 10:50:33 -0700103 // @return the CHAR; -1 if outside the bounds of the font data
Selim Gurun30d4e1f2013-08-15 12:46:15 -0700104 // @throws IndexOutOfBoundsException if index is outside the FontData's range
105 virtual int32_t ReadChar(int32_t index);
106
107 // Read the USHORT at the given index.
108 // @param index index into the font data
Colin Cross13a82432017-04-07 10:50:33 -0700109 // @return the USHORT; -1 if outside the bounds of the font data
Selim Gurun30d4e1f2013-08-15 12:46:15 -0700110 // @throws IndexOutOfBoundsException if index is outside the FontData's range
111 virtual int32_t ReadUShort(int32_t index);
112
113 // Read the SHORT at the given index.
114 // @param index index into the font data
Colin Cross13a82432017-04-07 10:50:33 -0700115 // @return the SHORT; |kInvalidShort| if outside the bounds of the font data
Selim Gurun30d4e1f2013-08-15 12:46:15 -0700116 // @throws IndexOutOfBoundsException if index is outside the FontData's range
117 virtual int32_t ReadShort(int32_t index);
118
119 // Read the UINT24 at the given index.
120 // @param index index into the font data
Colin Cross13a82432017-04-07 10:50:33 -0700121 // @return the UINT24; -1 if outside the bounds of the font data
Selim Gurun30d4e1f2013-08-15 12:46:15 -0700122 // @throws IndexOutOfBoundsException if index is outside the FontData's range
123 virtual int32_t ReadUInt24(int32_t index);
124
125 // Read the ULONG at the given index.
126 // @param index index into the font data
Colin Cross13a82432017-04-07 10:50:33 -0700127 // @return the ULONG; kInvalidUnsigned if outside the bounds of the font data
Selim Gurun30d4e1f2013-08-15 12:46:15 -0700128 // @throws IndexOutOfBoundsException if index is outside the FontData's range
129 virtual int64_t ReadULong(int32_t index);
130
131 // Read the ULONG at the given index as int32_t.
132 // @param index index into the font data
133 // @return the ULONG
134 // @throws IndexOutOfBoundsException if index is outside the FontData's range
135 virtual int32_t ReadULongAsInt(int32_t index);
136
137 // Read the ULONG at the given index, little-endian variant
138 // @param index index into the font data
139 // @return the ULONG
140 // @throws IndexOutOfBoundsException if index is outside the FontData's range
141 virtual int64_t ReadULongLE(int32_t index);
142
143 // Read the LONG at the given index.
144 // @param index index into the font data
Colin Cross13a82432017-04-07 10:50:33 -0700145 // @return the LONG; kInvalidLong if outside the bounds of the font data
Selim Gurun30d4e1f2013-08-15 12:46:15 -0700146 // @throws IndexOutOfBoundsException if index is outside the FontData's range
147 virtual int32_t ReadLong(int32_t index);
148
149 // Read the Fixed at the given index.
150 // @param index index into the font data
151 // @return the Fixed
152 // @throws IndexOutOfBoundsException if index is outside the FontData's range
153 virtual int32_t ReadFixed(int32_t index);
154
155 // Read the LONGDATETIME at the given index.
156 // @param index index into the font data
Colin Cross13a82432017-04-07 10:50:33 -0700157 // @return the LONGDATETIME; kInvalidLongDateTime if outside the bounds of the
158 // font data
Selim Gurun30d4e1f2013-08-15 12:46:15 -0700159 // @throws IndexOutOfBoundsException if index is outside the FontData's range
160 virtual int64_t ReadDateTimeAsLong(int32_t index);
161
162 // Read the FWORD at the given index.
163 // @param index index into the font data
164 // @return the FWORD
165 // @throws IndexOutOfBoundsException if index is outside the FontData's range
166 virtual int32_t ReadFWord(int32_t index);
167
168 // Read the UFWORD at the given index.
169 // @param index index into the font data
170 // @return the UFWORD
171 // @throws IndexOutOfBoundsException if index is outside the FontData's range
172 virtual int32_t ReadFUFWord(int32_t index);
173
174 // Note: Not ported because they just throw UnsupportedOperationException()
175 // in Java.
176 /*
177 virtual int32_t ReadFUnit(int32_t index);
178 virtual int64_t ReadF2Dot14(int32_t index);
179 */
180
181 // Copy the FontData to an OutputStream.
182 // @param os the destination
183 // @return number of bytes copied
184 // @throws IOException
185 virtual int32_t CopyTo(OutputStream* os);
186
187 // Copy the FontData to a WritableFontData.
188 // @param wfd the destination
189 // @return number of bytes copied
190 // @throws IOException
191 virtual int32_t CopyTo(WritableFontData* wfd);
192
193 // Make gcc -Woverloaded-virtual happy.
194 virtual int32_t CopyTo(ByteArray* ba);
195
196 // Search for the key value in the range tables provided.
197 // The search looks through the start-end pairs looking for the key value. It
198 // is assumed that the start-end pairs are both represented by UShort values,
199 // ranges do not overlap, and are monotonically increasing.
200 // @param startIndex the position to read the first start value from
201 // @param startOffset the offset between subsequent start values
202 // @param endIndex the position to read the first end value from
203 // @param endOffset the offset between subsequent end values
204 // @param length the number of start-end pairs
205 // @param key the value to search for
206 // @return the index of the start-end pairs in which the key was found; -1
207 // otherwise
208 int32_t SearchUShort(int32_t start_index,
209 int32_t start_offset,
210 int32_t end_index,
211 int32_t end_offset,
212 int32_t length,
213 int32_t key);
214
215 // Search for the key value in the table provided.
216 // The search looks through the values looking for the key value. It is
217 // assumed that the are represented by UShort values and are monotonically
218 // increasing.
219 // @param startIndex the position to read the first start value from
220 // @param startOffset the offset between subsequent start values
221 // @param length the number of start-end pairs
222 // @param key the value to search for
223 // @return the index of the start-end pairs in which the key was found; -1
224 // otherwise
225 int32_t SearchUShort(int32_t start_index,
226 int32_t start_offset,
227 int32_t length,
228 int32_t key);
229
230 // Search for the key value in the range tables provided.
231 // The search looks through the start-end pairs looking for the key value. It
232 // is assumed that the start-end pairs are both represented by ULong values
233 // that can be represented within 31 bits, ranges do not overlap, and are
234 // monotonically increasing.
235 // @param startIndex the position to read the first start value from
236 // @param startOffset the offset between subsequent start values
237 // @param endIndex the position to read the first end value from
238 // @param endOffset the offset between subsequent end values
239 // @param length the number of start-end pairs
240 // @param key the value to search for
241 // @return the index of the start-end pairs in which the key was found; -1
242 // otherwise
243 int32_t SearchULong(int32_t start_index,
244 int32_t start_offset,
245 int32_t end_index,
246 int32_t end_offset,
247 int32_t length,
248 int32_t key);
249
250
251 // TODO(arthurhsu): IMPLEMENT
252 /*
253 virtual int32_t ReadFUnit(int32_t index);
254 virtual int64_t ReadF2Dot14(int32_t index);
255 virtual int64_t ReadLongDateTime(int32_t index);
256 */
257
258 // Makes a slice of this FontData. The returned slice will share the data with
259 // the original FontData.
260 // @param offset the start of the slice
261 // @param length the number of bytes in the slice
262 // @return a slice of the original FontData
263 // Note: C++ polymorphism requires return type to be consistent
264 virtual CALLER_ATTACH FontData* Slice(int32_t offset, int32_t length);
265
266 // Makes a bottom bound only slice of this array. The returned slice will
267 // share the data with the original FontData.
268 // @param offset the start of the slice
269 // @return a slice of the original FontData
270 // Note: C++ polymorphism requires return type to be consistent
271 virtual CALLER_ATTACH FontData* Slice(int32_t offset);
272
273 // Not Ported: toString()
274
275 protected:
276 // Constructor. Creates a bounded wrapper of another ReadableFontData from the
277 // given offset until the end of the original ReadableFontData.
278 // @param data data to wrap
279 // @param offset the start of this data's view of the original data
280 ReadableFontData(ReadableFontData* data, int32_t offset);
281
282 // Constructor. Creates a bounded wrapper of another ReadableFontData from the
283 // given offset until the end of the original ReadableFontData.
284 // @param data data to wrap
285 // @param offset the start of this data's view of the original data
286 // @param length the length of the other FontData to use
287 ReadableFontData(ReadableFontData* data, int32_t offset, int32_t length);
288
289 private:
290 // Compute the checksum for the font data using any ranges set for the
291 // calculation.
292 void ComputeChecksum();
293
294 // Do the actual computation of the checksum for a range using the
295 // TrueType/OpenType checksum algorithm. The range used is from the low bound
296 // to the high bound in steps of four bytes. If any of the bytes within that 4
297 // byte segment are not readable then it will considered a zero for
298 // calculation.
299 // Only called from within a synchronized method so it does not need to be
300 // synchronized itself.
301 // @param lowBound first position to start a 4 byte segment on
302 // @param highBound last possible position to start a 4 byte segment on
303 // @return the checksum for the total range
304 int64_t ComputeCheckSum(int32_t low_bound, int32_t high_bound);
305
306 Lock checksum_lock_;
307 bool checksum_set_;
308 int64_t checksum_;
309 IntegerList checksum_range_;
310};
311typedef Ptr<ReadableFontData> ReadableFontDataPtr;
312
313} // namespace sfntly
314
315#endif // SFNTLY_CPP_SRC_SFNTLY_DATA_READABLE_FONT_DATA_H_