tpm2_protocol/macro/
enum.rs1#[macro_export]
10macro_rules! tpm_enum {
11 (@impl $(#[$enum_meta:meta])* $vis:vis enum $name:ident($wrapper:ty, $repr:ty) {
12 $(
13 $(#[$variant_meta:meta])*
14 ($variant:ident, $value:expr, $display:literal)
15 ),* $(,)?
16 }) => {
17 $(#[$enum_meta])*
18 #[repr($repr)]
19 $vis enum $name {
20 $(
21 $(#[$variant_meta])*
22 $variant = $value
23 ),*
24 }
25
26 impl TryFrom<$repr> for $name {
27 type Error = $crate::TpmError;
28
29 #[allow(clippy::cast_lossless, clippy::cast_sign_loss)]
30 fn try_from(value: $repr) -> Result<Self, $crate::TpmError> {
31 match value {
32 $(
33 _ if value == $value => Ok(Self::$variant),
34 )*
35 _ => Err($crate::TpmError::VariantNotAvailable(
36 $crate::TpmErrorValue::new(0).value(value as u64),
37 )),
38 }
39 }
40 }
41
42 impl $name {
43 #[must_use]
44 pub const fn value(self) -> $repr {
45 self as $repr
46 }
47 }
48
49 impl core::fmt::Display for $name {
50 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
51 let s = match self {
52 $(Self::$variant => $display),*
53 };
54 write!(f, "{}", s)
55 }
56 }
57
58 impl $crate::TpmSized for $name {
59 const SIZE: usize = core::mem::size_of::<$repr>();
60
61 fn len(&self) -> usize {
62 Self::SIZE
63 }
64 }
65
66 impl $crate::TpmMarshal for $name {
67 fn marshal(&self, writer: &mut $crate::TpmWriter) -> $crate::TpmResult<()> {
68 let value = <$wrapper>::from(*self as $repr);
69 $crate::TpmMarshal::marshal(&value, writer)
70 }
71 }
72
73 impl<'a> $crate::TpmField<'a> for $name {
74 type View = Self;
75
76 fn cast_prefix_field(buf: &'a [u8]) -> $crate::TpmResult<(Self::View, &'a [u8])> {
77 let (value, buf) = <$wrapper as $crate::TpmCast>::cast_prefix(buf)?;
78 let raw: $repr = value.get();
79 let enum_val = Self::try_from(raw)?;
80
81 Ok((enum_val, buf))
82 }
83 }
84 };
85
86 ($(#[$meta:meta])* $vis:vis enum $name:ident(TpmUint8) { $($rest:tt)* }) => {
87 tpm_enum!(@impl $(#[$meta])* $vis enum $name($crate::basic::TpmUint8, u8) { $($rest)* });
88 };
89 ($(#[$meta:meta])* $vis:vis enum $name:ident(TpmInt8) { $($rest:tt)* }) => {
90 tpm_enum!(@impl $(#[$meta])* $vis enum $name($crate::basic::TpmInt8, i8) { $($rest)* });
91 };
92 ($(#[$meta:meta])* $vis:vis enum $name:ident(TpmUint16) { $($rest:tt)* }) => {
93 tpm_enum!(@impl $(#[$meta])* $vis enum $name($crate::basic::TpmUint16, u16) { $($rest)* });
94 };
95 ($(#[$meta:meta])* $vis:vis enum $name:ident(TpmUint32) { $($rest:tt)* }) => {
96 tpm_enum!(@impl $(#[$meta])* $vis enum $name($crate::basic::TpmUint32, u32) { $($rest)* });
97 };
98 ($(#[$meta:meta])* $vis:vis enum $name:ident(TpmInt32) { $($rest:tt)* }) => {
99 tpm_enum!(@impl $(#[$meta])* $vis enum $name($crate::basic::TpmInt32, i32) { $($rest)* });
100 };
101 ($(#[$meta:meta])* $vis:vis enum $name:ident(TpmUint64) { $($rest:tt)* }) => {
102 tpm_enum!(@impl $(#[$meta])* $vis enum $name($crate::basic::TpmUint64, u64) { $($rest)* });
103 };
104}