mysql_common/misc/raw/
flags.rs
1use bitflags::Flags;
10use num_traits::{Bounded, PrimInt};
11
12use std::{fmt, io, marker::PhantomData, mem::size_of};
13
14use crate::{
15 io::ParseBuf,
16 proto::{MyDeserialize, MySerialize},
17};
18
19use super::{int::IntRepr, RawInt};
20
21#[derive(Clone, Default, Copy, Eq, PartialEq, Ord, PartialOrd, Hash)]
25#[repr(transparent)]
26pub struct RawFlags<T: Flags, U>(pub T::Bits, PhantomData<U>);
27
28impl<T: Flags, U> RawFlags<T, U> {
29 pub fn new(value: T::Bits) -> Self {
31 Self(value, PhantomData)
32 }
33
34 pub fn get(&self) -> T {
36 T::from_bits_truncate(self.0)
37 }
38}
39
40impl<T: fmt::Debug, U> fmt::Debug for RawFlags<T, U>
41where
42 T: Flags,
43 T::Bits: fmt::Binary + Bounded + PrimInt,
44{
45 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
46 write!(f, "{:?}", self.get())?;
47 let unknown_bits = self.0 & (T::Bits::max_value() ^ T::all().bits());
48 if unknown_bits.count_ones() > 0 {
49 write!(
50 f,
51 " (Unknown bits: {:0width$b})",
52 unknown_bits,
53 width = T::Bits::max_value().count_ones() as usize,
54 )?
55 }
56 Ok(())
57 }
58}
59
60impl<'de, T: Flags, U> MyDeserialize<'de> for RawFlags<T, U>
61where
62 U: IntRepr<Primitive = T::Bits>,
63{
64 const SIZE: Option<usize> = Some(size_of::<T::Bits>());
65 type Ctx = ();
66
67 fn deserialize((): Self::Ctx, buf: &mut ParseBuf<'de>) -> io::Result<Self> {
68 let value = buf.parse_unchecked::<RawInt<U>>(())?;
69 Ok(Self::new(*value))
70 }
71}
72
73impl<T: Flags, U> MySerialize for RawFlags<T, U>
74where
75 U: IntRepr<Primitive = T::Bits>,
76{
77 fn serialize(&self, buf: &mut Vec<u8>) {
78 RawInt::<U>::new(self.0).serialize(buf);
79 }
80}