memory_addresses/
macros.rs1macro_rules! impl_address {
6 ($T:ident, $V:ty) => {
7 impl $crate::MemoryAddress for $T {
8 type RAW = $V;
9
10 fn raw(self) -> Self::RAW {
11 self.0
12 }
13 }
14
15 impl $T {
16 #[inline]
24 pub const unsafe fn new_unsafe(addr: $V) -> $T {
25 $T(addr)
26 }
27
28 #[inline]
29 pub const fn is_null(self) -> bool {
31 self.0 == 0
32 }
33
34 #[inline]
36 pub const fn zero() -> $T {
37 $T::new(0)
38 }
39
40 paste::paste! {
41 #[doc = "Converts the address to an `" $V "`."]
42 #[inline]
43 pub const fn [< as_ $V >] (self) -> $V {
44 self.0
45 }
46 }
47 }
48
49 impl core::ops::Add<$V> for $T {
50 type Output = Self;
51 #[inline]
52 fn add(self, rhs: $V) -> Self::Output {
53 $T::new(self.0 + rhs)
54 }
55 }
56
57 impl core::ops::AddAssign<$V> for $T {
58 #[inline]
59 fn add_assign(&mut self, rhs: $V) {
60 *self = *self + rhs;
61 }
62 }
63
64 impl core::ops::Sub<$V> for $T {
65 type Output = Self;
66 #[inline]
67 fn sub(self, rhs: $V) -> Self::Output {
68 $T::new(self.0.checked_sub(rhs).unwrap())
69 }
70 }
71
72 impl core::ops::SubAssign<$V> for $T {
73 #[inline]
74 fn sub_assign(&mut self, rhs: $V) {
75 *self = *self - rhs;
76 }
77 }
78
79 impl core::ops::Sub<$T> for $T {
80 type Output = $V;
81 #[inline]
82 fn sub(self, rhs: $T) -> Self::Output {
83 paste::paste! {
84 self.[< as _$V >]().checked_sub(rhs.[< as_ $V >]()).unwrap()
85 }
86 }
87 }
88
89 impl core::ops::BitOr<$V> for $T {
90 type Output = $V;
91 #[inline]
92 fn bitor(self, rhs: $V) -> Self::Output {
93 self.0 | rhs
94 }
95 }
96
97 impl core::ops::BitOrAssign<$V> for $T {
98 #[inline]
99 fn bitor_assign(&mut self, rhs: $V) {
100 *self = Self::new_truncate(self.0 | rhs);
101 }
102 }
103
104 impl core::ops::BitAnd<$V> for $T {
105 type Output = $V;
106 #[inline]
107 fn bitand(self, rhs: $V) -> Self::Output {
108 self.0 & rhs
109 }
110 }
111
112 impl core::ops::BitAndAssign<$V> for $T {
113 #[inline]
114 fn bitand_assign(&mut self, rhs: $V) {
115 *self = Self::new_truncate(self.0 & rhs);
116 }
117 }
118
119 impl core::ops::BitXor<$V> for $T {
120 type Output = $V;
121 #[inline]
122 fn bitxor(self, rhs: $V) -> Self::Output {
123 self.0 ^ rhs
124 }
125 }
126
127 impl core::ops::BitXorAssign<$V> for $T {
128 #[inline]
129 fn bitxor_assign(&mut self, rhs: $V) {
130 *self = Self::new_truncate(self.0 ^ rhs);
131 }
132 }
133
134 impl core::ops::Shl<usize> for $T {
135 type Output = $T;
136 #[inline]
137 fn shl(self, rhs: usize) -> Self::Output {
138 Self::new_truncate(self.0 << rhs)
139 }
140 }
141
142 impl core::ops::Shr<usize> for $T {
143 type Output = $T;
144 #[inline]
145 fn shr(self, rhs: usize) -> Self::Output {
146 Self::new_truncate(self.0 >> rhs)
147 }
148 }
149
150 impl core::ops::ShlAssign<usize> for $T {
151 #[inline]
152 fn shl_assign(&mut self, rhs: usize) {
153 *self = Self::new_truncate(self.0 << rhs);
154 }
155 }
156
157 impl core::ops::ShrAssign<usize> for $T {
158 #[inline]
159 fn shr_assign(&mut self, rhs: usize) {
160 *self = Self::new_truncate(self.0 >> rhs);
161 }
162 }
163
164 impl From<$V> for $T {
165 #[inline]
166 fn from(addr: $V) -> $T {
167 Self::new_truncate(addr)
168 }
169 }
170
171 impl core::fmt::Debug for $T {
172 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
173 f.debug_tuple(stringify!($T))
174 .field(&format_args!("{:#x}", self.0))
175 .finish()
176 }
177 }
178
179 impl core::fmt::Binary for $T {
180 #[inline]
181 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
182 fmt::Binary::fmt(&self.0, f)
183 }
184 }
185
186 impl core::fmt::LowerHex for $T {
187 #[inline]
188 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
189 fmt::LowerHex::fmt(&self.0, f)
190 }
191 }
192
193 impl core::fmt::Octal for $T {
194 #[inline]
195 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
196 fmt::Octal::fmt(&self.0, f)
197 }
198 }
199
200 impl core::fmt::UpperHex for $T {
201 #[inline]
202 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
203 fmt::UpperHex::fmt(&self.0, f)
204 }
205 }
206
207 impl core::fmt::Pointer for $T {
208 #[inline]
209 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
210 fmt::Pointer::fmt(&(self.0 as *const ()), f)
211 }
212 }
213 };
214}
215
216pub(crate) use impl_address;