1use std::{cell::RefCell, rc::Rc, sync::Arc};
2
3use num_bigint::BigInt;
4
5use crate::{BytePos, Span};
6
7pub trait EqIgnoreSpan {
9 fn eq_ignore_span(&self, other: &Self) -> bool;
10}
11
12impl EqIgnoreSpan for Span {
13 #[inline]
15 fn eq_ignore_span(&self, _: &Self) -> bool {
16 true
17 }
18}
19
20impl EqIgnoreSpan for swc_atoms::Atom {
21 #[inline]
22 fn eq_ignore_span(&self, r: &Self) -> bool {
23 self == r
24 }
25}
26
27impl<T> EqIgnoreSpan for [T]
28where
29 T: EqIgnoreSpan,
30{
31 fn eq_ignore_span(&self, other: &Self) -> bool {
32 self.len() == other.len()
33 && self
34 .iter()
35 .zip(other.iter())
36 .all(|(a, b)| a.eq_ignore_span(b))
37 }
38}
39
40impl<T> EqIgnoreSpan for Option<T>
41where
42 T: EqIgnoreSpan,
43{
44 fn eq_ignore_span(&self, other: &Self) -> bool {
45 match (self, other) {
46 (Some(l), Some(r)) => l.eq_ignore_span(r),
47 (None, None) => true,
48 _ => false,
49 }
50 }
51}
52
53impl<T> EqIgnoreSpan for Vec<T>
54where
55 T: EqIgnoreSpan,
56{
57 fn eq_ignore_span(&self, other: &Self) -> bool {
58 self.len() == other.len()
59 && self
60 .iter()
61 .zip(other.iter())
62 .all(|(a, b)| a.eq_ignore_span(b))
63 }
64}
65
66pub trait TypeEq {
83 fn type_eq(&self, other: &Self) -> bool;
85}
86
87impl TypeEq for Span {
88 #[inline]
90 fn type_eq(&self, _: &Self) -> bool {
91 true
92 }
93}
94
95impl<T> TypeEq for Option<T>
96where
97 T: TypeEq,
98{
99 fn type_eq(&self, other: &Self) -> bool {
100 match (self, other) {
101 (Some(l), Some(r)) => l.type_eq(r),
102 (None, None) => true,
103 _ => false,
104 }
105 }
106}
107
108impl<T> TypeEq for Vec<T>
109where
110 T: TypeEq,
111{
112 fn type_eq(&self, other: &Self) -> bool {
113 self.len() == other.len() && self.iter().zip(other.iter()).all(|(a, b)| a.type_eq(b))
114 }
115}
116
117macro_rules! eq {
119 ($T:ty) => {
120 impl EqIgnoreSpan for $T {
121 #[inline]
122 fn eq_ignore_span(&self, other: &Self) -> bool {
123 self == other
124 }
125 }
126
127 impl TypeEq for $T {
128 #[inline]
129 fn type_eq(&self, other: &Self) -> bool {
130 self == other
131 }
132 }
133 };
134
135 (
136 $(
137 $T:ty
138 ),*
139 ) => {
140 $(
141 eq!($T);
142 )*
143 };
144}
145
146eq!(BytePos);
147eq!(bool);
148eq!(usize, u8, u16, u32, u64, u128);
149eq!(isize, i8, i16, i32, i64, i128);
150eq!(f32, f64);
151eq!(char, str, String);
152
153macro_rules! deref {
154 ($T:ident) => {
155 impl<N> EqIgnoreSpan for $T<N>
156 where
157 N: EqIgnoreSpan,
158 {
159 #[inline]
160 fn eq_ignore_span(&self, other: &Self) -> bool {
161 (**self).eq_ignore_span(&**other)
162 }
163 }
164
165 impl<N> TypeEq for $T<N>
166 where
167 N: TypeEq,
168 {
169 #[inline]
170 fn type_eq(&self, other: &Self) -> bool {
171 (**self).type_eq(&**other)
172 }
173 }
174 };
175
176
177 (
178 $(
179 $T:ident
180 ),*
181 ) => {
182 $(
183 deref!($T);
184 )*
185 };
186}
187
188deref!(Box, Rc, Arc);
189
190impl<N> EqIgnoreSpan for &N
213where
214 N: EqIgnoreSpan,
215{
216 #[inline]
217 fn eq_ignore_span(&self, other: &Self) -> bool {
218 (**self).eq_ignore_span(&**other)
219 }
220}
221
222impl<N> TypeEq for &N
223where
224 N: TypeEq,
225{
226 #[inline]
227 fn type_eq(&self, other: &Self) -> bool {
228 (**self).type_eq(&**other)
229 }
230}
231
232impl<N> EqIgnoreSpan for RefCell<N>
233where
234 N: EqIgnoreSpan,
235{
236 fn eq_ignore_span(&self, other: &Self) -> bool {
237 self.borrow().eq_ignore_span(&*other.borrow())
238 }
239}
240
241impl<N> TypeEq for RefCell<N>
242where
243 N: TypeEq,
244{
245 fn type_eq(&self, other: &Self) -> bool {
246 self.borrow().type_eq(&*other.borrow())
247 }
248}
249
250impl EqIgnoreSpan for BigInt {
251 fn eq_ignore_span(&self, other: &Self) -> bool {
252 self == other
253 }
254}
255impl TypeEq for BigInt {
256 fn type_eq(&self, other: &Self) -> bool {
257 self == other
258 }
259}
260
261macro_rules! tuple {
262 (
263 $num:tt: $F:ident
264 ) => {};
265
266
267 (
268 $first:tt: $F:ident,
269 $(
270 $num:tt: $N:ident
271 ),*
272 ) =>{
273 tuple!($($num: $N),*);
274
275 impl<$F: EqIgnoreSpan, $($N: EqIgnoreSpan),*> EqIgnoreSpan for ($F, $($N,)*) {
276 fn eq_ignore_span(&self,rhs: &Self) -> bool {
277 self.$first.eq_ignore_span(&rhs.$first) &&
278 $(
279 self.$num.eq_ignore_span(&rhs.$num)
280 )
281 && *
282 }
283 }
284
285 impl<$F: TypeEq, $($N: TypeEq),*> TypeEq for ($F, $($N,)*) {
286 fn type_eq(&self,rhs: &Self) -> bool {
287 self.$first.type_eq(&rhs.$first) &&
288 $(
289 self.$num.type_eq(&rhs.$num)
290 )
291 && *
292 }
293 }
294 };
295}
296
297tuple!(
298 25: Z,
299 24: Y,
300 23: X,
301 22: W,
302 21: V,
303 20: U,
304 19: T,
305 18: S,
306 17: R,
307 16: Q,
308 15: P,
309 14: O,
310 13: N,
311 12: M,
312 11: L,
313 10: K,
314 9: J,
315 8: I,
316 7: H,
317 6: G,
318 5: F,
319 4: E,
320 3: D,
321 2: C,
322 1: B,
323 0: A
324);