1use std::fmt;
2
3use agglayer_primitives::{Digest, B256};
4use serde::{Deserialize, Serialize};
5
6macro_rules! define_digest_type {
7 ($name:ident) => {
8 #[derive(
9 Clone, Copy, Debug, Serialize, Deserialize, PartialEq, Eq, PartialOrd, Ord, Default,
10 )]
11 #[serde(transparent)]
12 pub struct $name(Digest);
13
14 impl $name {
15 #[inline]
16 pub const fn new(digest: Digest) -> Self {
17 Self(digest)
18 }
19 }
20
21 impl AsRef<[u8]> for $name {
22 #[inline]
23 fn as_ref(&self) -> &[u8] {
24 self.0.as_slice()
25 }
26 }
27
28 impl AsRef<Digest> for $name {
29 #[inline]
30 fn as_ref(&self) -> &Digest {
31 &self.0
32 }
33 }
34
35 impl AsRef<[u8; 32]> for $name {
36 #[inline]
37 fn as_ref(&self) -> &[u8; 32] {
38 &self.0 .0
39 }
40 }
41
42 impl AsMut<[u8; 32]> for $name {
43 #[inline]
44 fn as_mut(&mut self) -> &mut [u8; 32] {
45 &mut self.0 .0
46 }
47 }
48
49 impl TryFrom<Vec<u8>> for $name {
50 type Error = std::array::TryFromSliceError;
51
52 #[inline]
53 fn try_from(value: Vec<u8>) -> Result<Self, Self::Error> {
54 Digest::try_from(value).map(Self)
55 }
56 }
57
58 impl From<Digest> for $name {
59 #[inline]
60 fn from(digest: Digest) -> Self {
61 Self(digest)
62 }
63 }
64
65 impl From<[u8; 32]> for $name {
66 #[inline]
67 fn from(array: [u8; 32]) -> Self {
68 Self(array.into())
69 }
70 }
71
72 impl From<$name> for Digest {
73 #[inline]
74 fn from(it: $name) -> Self {
75 it.0
76 }
77 }
78
79 impl TryFrom<&[u8]> for $name {
80 type Error = std::array::TryFromSliceError;
81
82 #[inline]
83 fn try_from(value: &[u8]) -> Result<Self, Self::Error> {
84 Digest::try_from(value).map(Self)
85 }
86 }
87
88 impl From<B256> for $name {
89 #[inline]
90 fn from(value: B256) -> Self {
91 Self(Digest::from(value))
92 }
93 }
94
95 impl From<$name> for B256 {
96 #[inline]
97 fn from(value: $name) -> Self {
98 B256::from(value.0)
99 }
100 }
101
102 impl fmt::UpperHex for $name {
103 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
104 self.0.fmt(f)
105 }
106 }
107
108 impl fmt::LowerHex for $name {
109 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
110 self.0.fmt(f)
111 }
112 }
113
114 impl fmt::Display for $name {
115 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
116 self.0.fmt(f)
117 }
118 }
119 };
120}
121
122define_digest_type!(LocalBalanceRoot);
123define_digest_type!(LocalNullifierRoot);
124define_digest_type!(LocalExitRoot);
125define_digest_type!(PessimisticRoot);
126define_digest_type!(L1InfoRoot);