1#[allow(unused_imports)]
6use crate::codegen_prelude::*;
7
8#[derive(Debug, Clone, Copy)]
10#[doc(hidden)]
11pub struct DsigMarker {
12 signature_records_byte_len: usize,
13}
14
15impl DsigMarker {
16 pub fn version_byte_range(&self) -> Range<usize> {
17 let start = 0;
18 start..start + u32::RAW_BYTE_LEN
19 }
20
21 pub fn num_signatures_byte_range(&self) -> Range<usize> {
22 let start = self.version_byte_range().end;
23 start..start + u16::RAW_BYTE_LEN
24 }
25
26 pub fn flags_byte_range(&self) -> Range<usize> {
27 let start = self.num_signatures_byte_range().end;
28 start..start + PermissionFlags::RAW_BYTE_LEN
29 }
30
31 pub fn signature_records_byte_range(&self) -> Range<usize> {
32 let start = self.flags_byte_range().end;
33 start..start + self.signature_records_byte_len
34 }
35}
36
37impl MinByteRange for DsigMarker {
38 fn min_byte_range(&self) -> Range<usize> {
39 0..self.signature_records_byte_range().end
40 }
41}
42
43impl TopLevelTable for Dsig<'_> {
44 const TAG: Tag = Tag::new(b"DSIG");
46}
47
48impl<'a> FontRead<'a> for Dsig<'a> {
49 fn read(data: FontData<'a>) -> Result<Self, ReadError> {
50 let mut cursor = data.cursor();
51 cursor.advance::<u32>();
52 let num_signatures: u16 = cursor.read()?;
53 cursor.advance::<PermissionFlags>();
54 let signature_records_byte_len = (num_signatures as usize)
55 .checked_mul(SignatureRecord::RAW_BYTE_LEN)
56 .ok_or(ReadError::OutOfBounds)?;
57 cursor.advance_by(signature_records_byte_len);
58 cursor.finish(DsigMarker {
59 signature_records_byte_len,
60 })
61 }
62}
63
64pub type Dsig<'a> = TableRef<'a, DsigMarker>;
66
67#[allow(clippy::needless_lifetimes)]
68impl<'a> Dsig<'a> {
69 pub fn version(&self) -> u32 {
71 let range = self.shape.version_byte_range();
72 self.data.read_at(range.start).unwrap()
73 }
74
75 pub fn num_signatures(&self) -> u16 {
77 let range = self.shape.num_signatures_byte_range();
78 self.data.read_at(range.start).unwrap()
79 }
80
81 pub fn flags(&self) -> PermissionFlags {
83 let range = self.shape.flags_byte_range();
84 self.data.read_at(range.start).unwrap()
85 }
86
87 pub fn signature_records(&self) -> &'a [SignatureRecord] {
89 let range = self.shape.signature_records_byte_range();
90 self.data.read_array(range).unwrap()
91 }
92}
93
94#[cfg(feature = "experimental_traverse")]
95impl<'a> SomeTable<'a> for Dsig<'a> {
96 fn type_name(&self) -> &str {
97 "Dsig"
98 }
99 fn get_field(&self, idx: usize) -> Option<Field<'a>> {
100 match idx {
101 0usize => Some(Field::new("version", self.version())),
102 1usize => Some(Field::new("num_signatures", self.num_signatures())),
103 2usize => Some(Field::new("flags", self.flags())),
104 3usize => Some(Field::new(
105 "signature_records",
106 traversal::FieldType::array_of_records(
107 stringify!(SignatureRecord),
108 self.signature_records(),
109 self.offset_data(),
110 ),
111 )),
112 _ => None,
113 }
114 }
115}
116
117#[cfg(feature = "experimental_traverse")]
118#[allow(clippy::needless_lifetimes)]
119impl<'a> std::fmt::Debug for Dsig<'a> {
120 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
121 (self as &dyn SomeTable<'a>).fmt(f)
122 }
123}
124
125#[derive(Clone, Copy, Default, PartialEq, Eq, PartialOrd, Ord, Hash, bytemuck :: AnyBitPattern)]
127#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
128#[repr(transparent)]
129pub struct PermissionFlags {
130 bits: u16,
131}
132
133impl PermissionFlags {
134 pub const CANNOT_BE_RESIGNED: Self = Self {
136 bits: 0b0000_0000_0000_0001,
137 };
138}
139
140impl PermissionFlags {
141 #[inline]
143 pub const fn empty() -> Self {
144 Self { bits: 0 }
145 }
146
147 #[inline]
149 pub const fn all() -> Self {
150 Self {
151 bits: Self::CANNOT_BE_RESIGNED.bits,
152 }
153 }
154
155 #[inline]
157 pub const fn bits(&self) -> u16 {
158 self.bits
159 }
160
161 #[inline]
164 pub const fn from_bits(bits: u16) -> Option<Self> {
165 if (bits & !Self::all().bits()) == 0 {
166 Some(Self { bits })
167 } else {
168 None
169 }
170 }
171
172 #[inline]
175 pub const fn from_bits_truncate(bits: u16) -> Self {
176 Self {
177 bits: bits & Self::all().bits,
178 }
179 }
180
181 #[inline]
183 pub const fn is_empty(&self) -> bool {
184 self.bits() == Self::empty().bits()
185 }
186
187 #[inline]
189 pub const fn intersects(&self, other: Self) -> bool {
190 !(Self {
191 bits: self.bits & other.bits,
192 })
193 .is_empty()
194 }
195
196 #[inline]
198 pub const fn contains(&self, other: Self) -> bool {
199 (self.bits & other.bits) == other.bits
200 }
201
202 #[inline]
204 pub fn insert(&mut self, other: Self) {
205 self.bits |= other.bits;
206 }
207
208 #[inline]
210 pub fn remove(&mut self, other: Self) {
211 self.bits &= !other.bits;
212 }
213
214 #[inline]
216 pub fn toggle(&mut self, other: Self) {
217 self.bits ^= other.bits;
218 }
219
220 #[inline]
231 #[must_use]
232 pub const fn intersection(self, other: Self) -> Self {
233 Self {
234 bits: self.bits & other.bits,
235 }
236 }
237
238 #[inline]
249 #[must_use]
250 pub const fn union(self, other: Self) -> Self {
251 Self {
252 bits: self.bits | other.bits,
253 }
254 }
255
256 #[inline]
269 #[must_use]
270 pub const fn difference(self, other: Self) -> Self {
271 Self {
272 bits: self.bits & !other.bits,
273 }
274 }
275}
276
277impl std::ops::BitOr for PermissionFlags {
278 type Output = Self;
279
280 #[inline]
282 fn bitor(self, other: PermissionFlags) -> Self {
283 Self {
284 bits: self.bits | other.bits,
285 }
286 }
287}
288
289impl std::ops::BitOrAssign for PermissionFlags {
290 #[inline]
292 fn bitor_assign(&mut self, other: Self) {
293 self.bits |= other.bits;
294 }
295}
296
297impl std::ops::BitXor for PermissionFlags {
298 type Output = Self;
299
300 #[inline]
302 fn bitxor(self, other: Self) -> Self {
303 Self {
304 bits: self.bits ^ other.bits,
305 }
306 }
307}
308
309impl std::ops::BitXorAssign for PermissionFlags {
310 #[inline]
312 fn bitxor_assign(&mut self, other: Self) {
313 self.bits ^= other.bits;
314 }
315}
316
317impl std::ops::BitAnd for PermissionFlags {
318 type Output = Self;
319
320 #[inline]
322 fn bitand(self, other: Self) -> Self {
323 Self {
324 bits: self.bits & other.bits,
325 }
326 }
327}
328
329impl std::ops::BitAndAssign for PermissionFlags {
330 #[inline]
332 fn bitand_assign(&mut self, other: Self) {
333 self.bits &= other.bits;
334 }
335}
336
337impl std::ops::Sub for PermissionFlags {
338 type Output = Self;
339
340 #[inline]
342 fn sub(self, other: Self) -> Self {
343 Self {
344 bits: self.bits & !other.bits,
345 }
346 }
347}
348
349impl std::ops::SubAssign for PermissionFlags {
350 #[inline]
352 fn sub_assign(&mut self, other: Self) {
353 self.bits &= !other.bits;
354 }
355}
356
357impl std::ops::Not for PermissionFlags {
358 type Output = Self;
359
360 #[inline]
362 fn not(self) -> Self {
363 Self { bits: !self.bits } & Self::all()
364 }
365}
366
367impl std::fmt::Debug for PermissionFlags {
368 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
369 let members: &[(&str, Self)] = &[("CANNOT_BE_RESIGNED", Self::CANNOT_BE_RESIGNED)];
370 let mut first = true;
371 for (name, value) in members {
372 if self.contains(*value) {
373 if !first {
374 f.write_str(" | ")?;
375 }
376 first = false;
377 f.write_str(name)?;
378 }
379 }
380 if first {
381 f.write_str("(empty)")?;
382 }
383 Ok(())
384 }
385}
386
387impl std::fmt::Binary for PermissionFlags {
388 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
389 std::fmt::Binary::fmt(&self.bits, f)
390 }
391}
392
393impl std::fmt::Octal for PermissionFlags {
394 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
395 std::fmt::Octal::fmt(&self.bits, f)
396 }
397}
398
399impl std::fmt::LowerHex for PermissionFlags {
400 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
401 std::fmt::LowerHex::fmt(&self.bits, f)
402 }
403}
404
405impl std::fmt::UpperHex for PermissionFlags {
406 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
407 std::fmt::UpperHex::fmt(&self.bits, f)
408 }
409}
410
411impl font_types::Scalar for PermissionFlags {
412 type Raw = <u16 as font_types::Scalar>::Raw;
413 fn to_raw(self) -> Self::Raw {
414 self.bits().to_raw()
415 }
416 fn from_raw(raw: Self::Raw) -> Self {
417 let t = <u16>::from_raw(raw);
418 Self::from_bits_truncate(t)
419 }
420}
421
422#[cfg(feature = "experimental_traverse")]
423impl<'a> From<PermissionFlags> for FieldType<'a> {
424 fn from(src: PermissionFlags) -> FieldType<'a> {
425 src.bits().into()
426 }
427}
428
429#[derive(Clone, Debug, Copy, bytemuck :: AnyBitPattern)]
431#[repr(C)]
432#[repr(packed)]
433pub struct SignatureRecord {
434 pub format: BigEndian<u32>,
436 pub length: BigEndian<u32>,
438 pub signature_block_offset: BigEndian<Offset32>,
440}
441
442impl SignatureRecord {
443 pub fn format(&self) -> u32 {
445 self.format.get()
446 }
447
448 pub fn length(&self) -> u32 {
450 self.length.get()
451 }
452
453 pub fn signature_block_offset(&self) -> Offset32 {
455 self.signature_block_offset.get()
456 }
457}
458
459impl FixedSize for SignatureRecord {
460 const RAW_BYTE_LEN: usize = u32::RAW_BYTE_LEN + u32::RAW_BYTE_LEN + Offset32::RAW_BYTE_LEN;
461}
462
463#[cfg(feature = "experimental_traverse")]
464impl<'a> SomeRecord<'a> for SignatureRecord {
465 fn traverse(self, data: FontData<'a>) -> RecordResolver<'a> {
466 RecordResolver {
467 name: "SignatureRecord",
468 get_field: Box::new(move |idx, _data| match idx {
469 0usize => Some(Field::new("format", self.format())),
470 1usize => Some(Field::new("length", self.length())),
471 2usize => Some(Field::new(
472 "signature_block_offset",
473 FieldType::offset(self.signature_block_offset(), self.signature_block(_data)),
474 )),
475 _ => None,
476 }),
477 data,
478 }
479 }
480}
481
482#[derive(Debug, Clone, Copy)]
484#[doc(hidden)]
485pub struct SignatureBlockFormat1Marker {
486 signature_byte_len: usize,
487}
488
489impl SignatureBlockFormat1Marker {
490 pub fn _reserved1_byte_range(&self) -> Range<usize> {
491 let start = 0;
492 start..start + u16::RAW_BYTE_LEN
493 }
494
495 pub fn _reserved2_byte_range(&self) -> Range<usize> {
496 let start = self._reserved1_byte_range().end;
497 start..start + u16::RAW_BYTE_LEN
498 }
499
500 pub fn signature_length_byte_range(&self) -> Range<usize> {
501 let start = self._reserved2_byte_range().end;
502 start..start + u32::RAW_BYTE_LEN
503 }
504
505 pub fn signature_byte_range(&self) -> Range<usize> {
506 let start = self.signature_length_byte_range().end;
507 start..start + self.signature_byte_len
508 }
509}
510
511impl MinByteRange for SignatureBlockFormat1Marker {
512 fn min_byte_range(&self) -> Range<usize> {
513 0..self.signature_byte_range().end
514 }
515}
516
517impl<'a> FontRead<'a> for SignatureBlockFormat1<'a> {
518 fn read(data: FontData<'a>) -> Result<Self, ReadError> {
519 let mut cursor = data.cursor();
520 cursor.advance::<u16>();
521 cursor.advance::<u16>();
522 let signature_length: u32 = cursor.read()?;
523 let signature_byte_len = (signature_length as usize)
524 .checked_mul(u8::RAW_BYTE_LEN)
525 .ok_or(ReadError::OutOfBounds)?;
526 cursor.advance_by(signature_byte_len);
527 cursor.finish(SignatureBlockFormat1Marker { signature_byte_len })
528 }
529}
530
531pub type SignatureBlockFormat1<'a> = TableRef<'a, SignatureBlockFormat1Marker>;
533
534#[allow(clippy::needless_lifetimes)]
535impl<'a> SignatureBlockFormat1<'a> {
536 pub fn signature_length(&self) -> u32 {
538 let range = self.shape.signature_length_byte_range();
539 self.data.read_at(range.start).unwrap()
540 }
541
542 pub fn signature(&self) -> &'a [u8] {
544 let range = self.shape.signature_byte_range();
545 self.data.read_array(range).unwrap()
546 }
547}
548
549#[cfg(feature = "experimental_traverse")]
550impl<'a> SomeTable<'a> for SignatureBlockFormat1<'a> {
551 fn type_name(&self) -> &str {
552 "SignatureBlockFormat1"
553 }
554 fn get_field(&self, idx: usize) -> Option<Field<'a>> {
555 match idx {
556 0usize => Some(Field::new("signature_length", self.signature_length())),
557 1usize => Some(Field::new("signature", self.signature())),
558 _ => None,
559 }
560 }
561}
562
563#[cfg(feature = "experimental_traverse")]
564#[allow(clippy::needless_lifetimes)]
565impl<'a> std::fmt::Debug for SignatureBlockFormat1<'a> {
566 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
567 (self as &dyn SomeTable<'a>).fmt(f)
568 }
569}