Skip to main content

ark_serialize/
flags.rs

1/// Represents metadata to be appended to an object's serialization.
2///
3/// For example, when serializing elliptic curve points, one can
4/// use a `Flag` to represent whether the serialization is the point
5/// at infinity, or whether the `y` coordinate is positive or not.
6/// These bits will be appended to the end of the point's serialization,
7/// or included in a new byte, depending on space available.
8///
9/// This is meant to be provided to `CanonicalSerializeWithFlags` and
10/// `CanonicalDeserializeWithFlags`
11pub trait Flags: Default + Clone + Copy + Sized {
12    /// The number of bits required to encode `Self`.
13    /// This should be at most 8.
14    const BIT_SIZE: usize;
15
16    /// Returns a bit mask corresponding to `self`.
17    /// For example, if `Self` contains two variants, there are just two possible
18    /// bit masks: `0` and `1 << 7`.
19    fn u8_bitmask(&self) -> u8;
20
21    /// Tries to read `Self` from `value`. Should return `None` if the
22    /// `Self::BIT_SIZE` most-significant bits of `value` do not correspond to
23    /// those generated by `u8_bitmask`.
24    ///
25    /// That is, this method ignores all but the top `Self::BIT_SIZE` bits, and
26    /// decides whether these top bits correspond to a bitmask output by
27    /// `u8_bitmask`.
28    fn from_u8(value: u8) -> Option<Self>;
29
30    /// Convenience method that reads `Self` from `value`, just like `Self::from_u8`,
31    /// but additionally zeroes out the bits corresponding to the resulting flag
32    /// in `value`. If `Self::from_u8(*value)` would return `None`, then this
33    /// method should *not* modify `value`.
34    fn from_u8_remove_flags(value: &mut u8) -> Option<Self> {
35        Self::from_u8(*value).map(|f| {
36            *value &= !f.u8_bitmask();
37            f
38        })
39    }
40}
41
42/// Flags to be encoded into the serialization.
43#[derive(Default, Clone, Copy, PartialEq, Eq)]
44pub struct EmptyFlags;
45
46impl Flags for EmptyFlags {
47    const BIT_SIZE: usize = 0;
48
49    #[inline]
50    fn u8_bitmask(&self) -> u8 {
51        0
52    }
53
54    #[inline]
55    fn from_u8(_: u8) -> Option<Self> {
56        Some(Self)
57    }
58}