1use alloc::string::{String, ToString};
2use core::fmt;
3use core::ops::{
4 Add, AddAssign, Div, DivAssign, Mul, MulAssign, Neg, Not, Rem, RemAssign, Shl, ShlAssign, Shr,
5 ShrAssign, Sub, SubAssign,
6};
7use core::str::FromStr;
8
9use crate::errors::{DivideByZeroError, DivisionError, OverflowError, OverflowOperation, StdError};
10use crate::forward_ref::{forward_ref_binop, forward_ref_op_assign};
11use crate::{
12 Int128, Int256, Int64, Uint128, Uint256, Uint512, Uint64, __internal::forward_ref_partial_eq,
13};
14
15use bnum::types::{I512, U512};
18
19use super::conversion::{grow_be_int, primitive_to_wrapped_int, try_from_uint_to_int};
20use super::impl_int_serde;
21use super::num_consts::NumConsts;
22
23#[derive(Copy, Clone, Default, Debug, PartialEq, Eq, PartialOrd, Ord, schemars::JsonSchema)]
50pub struct Int512(#[schemars(with = "String")] pub(crate) I512);
51
52impl_int_serde!(Int512);
53forward_ref_partial_eq!(Int512, Int512);
54
55impl Int512 {
56 pub const MAX: Int512 = Int512(I512::MAX);
57 pub const MIN: Int512 = Int512(I512::MIN);
58
59 #[inline]
68 #[must_use]
69 pub const fn new(value: i128) -> Self {
70 Self::from_be_bytes(grow_be_int(value.to_be_bytes()))
71 }
72
73 #[inline]
75 pub const fn zero() -> Self {
76 Int512(I512::ZERO)
77 }
78
79 #[inline]
81 pub const fn one() -> Self {
82 Self(I512::ONE)
83 }
84
85 #[must_use]
86 pub const fn from_be_bytes(data: [u8; 64]) -> Self {
87 let words: [u64; 8] = [
88 u64::from_le_bytes([
89 data[63], data[62], data[61], data[60], data[59], data[58], data[57], data[56],
90 ]),
91 u64::from_le_bytes([
92 data[55], data[54], data[53], data[52], data[51], data[50], data[49], data[48],
93 ]),
94 u64::from_le_bytes([
95 data[47], data[46], data[45], data[44], data[43], data[42], data[41], data[40],
96 ]),
97 u64::from_le_bytes([
98 data[39], data[38], data[37], data[36], data[35], data[34], data[33], data[32],
99 ]),
100 u64::from_le_bytes([
101 data[31], data[30], data[29], data[28], data[27], data[26], data[25], data[24],
102 ]),
103 u64::from_le_bytes([
104 data[23], data[22], data[21], data[20], data[19], data[18], data[17], data[16],
105 ]),
106 u64::from_le_bytes([
107 data[15], data[14], data[13], data[12], data[11], data[10], data[9], data[8],
108 ]),
109 u64::from_le_bytes([
110 data[7], data[6], data[5], data[4], data[3], data[2], data[1], data[0],
111 ]),
112 ];
113 Self(I512::from_bits(U512::from_digits(words)))
114 }
115
116 #[must_use]
117 pub const fn from_le_bytes(data: [u8; 64]) -> Self {
118 let words: [u64; 8] = [
119 u64::from_le_bytes([
120 data[0], data[1], data[2], data[3], data[4], data[5], data[6], data[7],
121 ]),
122 u64::from_le_bytes([
123 data[8], data[9], data[10], data[11], data[12], data[13], data[14], data[15],
124 ]),
125 u64::from_le_bytes([
126 data[16], data[17], data[18], data[19], data[20], data[21], data[22], data[23],
127 ]),
128 u64::from_le_bytes([
129 data[24], data[25], data[26], data[27], data[28], data[29], data[30], data[31],
130 ]),
131 u64::from_le_bytes([
132 data[32], data[33], data[34], data[35], data[36], data[37], data[38], data[39],
133 ]),
134 u64::from_le_bytes([
135 data[40], data[41], data[42], data[43], data[44], data[45], data[46], data[47],
136 ]),
137 u64::from_le_bytes([
138 data[48], data[49], data[50], data[51], data[52], data[53], data[54], data[55],
139 ]),
140 u64::from_le_bytes([
141 data[56], data[57], data[58], data[59], data[60], data[61], data[62], data[63],
142 ]),
143 ];
144 Self(I512::from_bits(U512::from_digits(words)))
145 }
146
147 #[must_use = "this returns the result of the operation, without modifying the original"]
149 pub const fn to_be_bytes(self) -> [u8; 64] {
150 let bits = self.0.to_bits();
151 let words = bits.digits();
152 let words = [
153 words[7].to_be_bytes(),
154 words[6].to_be_bytes(),
155 words[5].to_be_bytes(),
156 words[4].to_be_bytes(),
157 words[3].to_be_bytes(),
158 words[2].to_be_bytes(),
159 words[1].to_be_bytes(),
160 words[0].to_be_bytes(),
161 ];
162 unsafe { core::mem::transmute::<[[u8; 8]; 8], [u8; 64]>(words) }
163 }
164
165 #[must_use = "this returns the result of the operation, without modifying the original"]
167 pub const fn to_le_bytes(self) -> [u8; 64] {
168 let bits = self.0.to_bits();
169 let words = bits.digits();
170 let words = [
171 words[0].to_le_bytes(),
172 words[1].to_le_bytes(),
173 words[2].to_le_bytes(),
174 words[3].to_le_bytes(),
175 words[4].to_le_bytes(),
176 words[5].to_le_bytes(),
177 words[6].to_le_bytes(),
178 words[7].to_le_bytes(),
179 ];
180 unsafe { core::mem::transmute::<[[u8; 8]; 8], [u8; 64]>(words) }
181 }
182
183 #[must_use]
184 pub const fn is_zero(&self) -> bool {
185 self.0.is_zero()
186 }
187
188 #[must_use]
189 pub const fn is_negative(&self) -> bool {
190 self.0.is_negative()
191 }
192
193 #[must_use = "this returns the result of the operation, without modifying the original"]
194 pub const fn pow(self, exp: u32) -> Self {
195 match self.0.checked_pow(exp) {
196 Some(val) => Self(val),
197 None => panic!("attempt to exponentiate with overflow"),
198 }
199 }
200
201 pub fn checked_add(self, other: Self) -> Result<Self, OverflowError> {
202 self.0
203 .checked_add(other.0)
204 .map(Self)
205 .ok_or_else(|| OverflowError::new(OverflowOperation::Add))
206 }
207
208 pub fn checked_sub(self, other: Self) -> Result<Self, OverflowError> {
209 self.0
210 .checked_sub(other.0)
211 .map(Self)
212 .ok_or_else(|| OverflowError::new(OverflowOperation::Sub))
213 }
214
215 pub fn checked_mul(self, other: Self) -> Result<Self, OverflowError> {
216 self.0
217 .checked_mul(other.0)
218 .map(Self)
219 .ok_or_else(|| OverflowError::new(OverflowOperation::Mul))
220 }
221
222 pub fn checked_pow(self, exp: u32) -> Result<Self, OverflowError> {
223 self.0
224 .checked_pow(exp)
225 .map(Self)
226 .ok_or_else(|| OverflowError::new(OverflowOperation::Pow))
227 }
228
229 pub fn checked_div(self, other: Self) -> Result<Self, DivisionError> {
230 if other.is_zero() {
231 return Err(DivisionError::DivideByZero);
232 }
233 self.0
234 .checked_div(other.0)
235 .map(Self)
236 .ok_or(DivisionError::Overflow)
237 }
238
239 pub fn checked_div_euclid(self, other: Self) -> Result<Self, DivisionError> {
240 if other.is_zero() {
241 return Err(DivisionError::DivideByZero);
242 }
243 self.0
244 .checked_div_euclid(other.0)
245 .map(Self)
246 .ok_or(DivisionError::Overflow)
247 }
248
249 pub fn checked_rem(self, other: Self) -> Result<Self, DivideByZeroError> {
250 self.0
251 .checked_rem(other.0)
252 .map(Self)
253 .ok_or(DivideByZeroError)
254 }
255
256 pub fn checked_shr(self, other: u32) -> Result<Self, OverflowError> {
257 if other >= 512 {
258 return Err(OverflowError::new(OverflowOperation::Shr));
259 }
260
261 Ok(Self(self.0.shr(other)))
262 }
263
264 pub fn checked_shl(self, other: u32) -> Result<Self, OverflowError> {
265 if other >= 512 {
266 return Err(OverflowError::new(OverflowOperation::Shl));
267 }
268
269 Ok(Self(self.0.shl(other)))
270 }
271
272 #[must_use = "this returns the result of the operation, without modifying the original"]
273 #[inline]
274 pub fn wrapping_add(self, other: Self) -> Self {
275 Self(self.0.wrapping_add(other.0))
276 }
277
278 #[must_use = "this returns the result of the operation, without modifying the original"]
279 #[inline]
280 pub fn wrapping_sub(self, other: Self) -> Self {
281 Self(self.0.wrapping_sub(other.0))
282 }
283
284 #[must_use = "this returns the result of the operation, without modifying the original"]
285 #[inline]
286 pub fn wrapping_mul(self, other: Self) -> Self {
287 Self(self.0.wrapping_mul(other.0))
288 }
289
290 #[must_use = "this returns the result of the operation, without modifying the original"]
291 #[inline]
292 pub fn wrapping_pow(self, other: u32) -> Self {
293 Self(self.0.wrapping_pow(other))
294 }
295
296 #[must_use = "this returns the result of the operation, without modifying the original"]
297 pub fn saturating_add(self, other: Self) -> Self {
298 Self(self.0.saturating_add(other.0))
299 }
300
301 #[must_use = "this returns the result of the operation, without modifying the original"]
302 pub fn saturating_sub(self, other: Self) -> Self {
303 Self(self.0.saturating_sub(other.0))
304 }
305
306 #[must_use = "this returns the result of the operation, without modifying the original"]
307 pub fn saturating_mul(self, other: Self) -> Self {
308 Self(self.0.saturating_mul(other.0))
309 }
310
311 #[must_use = "this returns the result of the operation, without modifying the original"]
312 pub fn saturating_pow(self, exp: u32) -> Self {
313 Self(self.0.saturating_pow(exp))
314 }
315
316 #[must_use = "this returns the result of the operation, without modifying the original"]
317 pub const fn abs_diff(self, other: Self) -> Uint512 {
318 Uint512(self.0.abs_diff(other.0))
319 }
320
321 #[must_use = "this returns the result of the operation, without modifying the original"]
322 pub const fn abs(self) -> Self {
323 match self.0.checked_abs() {
324 Some(val) => Self(val),
325 None => panic!("attempt to calculate absolute value with overflow"),
326 }
327 }
328
329 #[must_use = "this returns the result of the operation, without modifying the original"]
330 pub const fn unsigned_abs(self) -> Uint512 {
331 Uint512(self.0.unsigned_abs())
332 }
333
334 pub const fn strict_neg(self) -> Self {
338 match self.0.checked_neg() {
339 Some(val) => Self(val),
340 None => panic!("attempt to negate with overflow"),
341 }
342 }
343}
344
345impl NumConsts for Int512 {
346 const ZERO: Self = Self::zero();
347 const ONE: Self = Self::one();
348 const MAX: Self = Self::MAX;
349 const MIN: Self = Self::MIN;
350}
351
352try_from_uint_to_int!(Uint512, Int512);
354
355impl From<Uint256> for Int512 {
356 fn from(val: Uint256) -> Self {
357 let mut bytes = [0u8; 64];
358 bytes[32..].copy_from_slice(&val.to_be_bytes());
359
360 Self::from_be_bytes(bytes)
361 }
362}
363
364impl From<Uint128> for Int512 {
365 fn from(val: Uint128) -> Self {
366 val.u128().into()
367 }
368}
369
370impl From<Uint64> for Int512 {
371 fn from(val: Uint64) -> Self {
372 val.u64().into()
373 }
374}
375
376primitive_to_wrapped_int!(u8, Int512);
378primitive_to_wrapped_int!(u16, Int512);
379primitive_to_wrapped_int!(u32, Int512);
380primitive_to_wrapped_int!(u64, Int512);
381primitive_to_wrapped_int!(u128, Int512);
382
383primitive_to_wrapped_int!(i8, Int512);
385primitive_to_wrapped_int!(i16, Int512);
386primitive_to_wrapped_int!(i32, Int512);
387primitive_to_wrapped_int!(i64, Int512);
388primitive_to_wrapped_int!(i128, Int512);
389
390impl From<Int64> for Int512 {
392 fn from(val: Int64) -> Self {
393 Int512(val.i64().into())
394 }
395}
396
397impl From<Int128> for Int512 {
398 fn from(val: Int128) -> Self {
399 Int512(val.i128().into())
400 }
401}
402
403impl From<Int256> for Int512 {
404 fn from(val: Int256) -> Self {
405 Self::from_be_bytes(grow_be_int(val.to_be_bytes()))
406 }
407}
408
409impl TryFrom<&str> for Int512 {
410 type Error = StdError;
411
412 fn try_from(val: &str) -> Result<Self, Self::Error> {
413 Self::from_str(val)
414 }
415}
416
417impl FromStr for Int512 {
418 type Err = StdError;
419
420 fn from_str(s: &str) -> Result<Self, Self::Err> {
421 match I512::from_str_radix(s, 10) {
422 Ok(u) => Ok(Self(u)),
423 Err(e) => Err(StdError::generic_err(format!("Parsing Int512: {e}"))),
424 }
425 }
426}
427
428impl From<Int512> for String {
429 fn from(original: Int512) -> Self {
430 original.to_string()
431 }
432}
433
434impl fmt::Display for Int512 {
435 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
436 self.0.fmt(f)
437 }
438}
439
440impl Add<Int512> for Int512 {
441 type Output = Self;
442
443 fn add(self, rhs: Self) -> Self {
444 Int512(self.0.checked_add(rhs.0).unwrap())
445 }
446}
447forward_ref_binop!(impl Add, add for Int512, Int512);
448
449impl Sub<Int512> for Int512 {
450 type Output = Self;
451
452 fn sub(self, rhs: Self) -> Self {
453 Int512(self.0.checked_sub(rhs.0).unwrap())
454 }
455}
456forward_ref_binop!(impl Sub, sub for Int512, Int512);
457
458impl SubAssign<Int512> for Int512 {
459 fn sub_assign(&mut self, rhs: Int512) {
460 self.0 = self.0.checked_sub(rhs.0).unwrap();
461 }
462}
463forward_ref_op_assign!(impl SubAssign, sub_assign for Int512, Int512);
464
465impl Div<Int512> for Int512 {
466 type Output = Self;
467
468 fn div(self, rhs: Self) -> Self::Output {
469 Self(self.0.checked_div(rhs.0).unwrap())
470 }
471}
472forward_ref_binop!(impl Div, div for Int512, Int512);
473
474impl Rem for Int512 {
475 type Output = Self;
476
477 #[inline]
481 fn rem(self, rhs: Self) -> Self {
482 Self(self.0.rem(rhs.0))
483 }
484}
485forward_ref_binop!(impl Rem, rem for Int512, Int512);
486
487impl Not for Int512 {
488 type Output = Self;
489
490 fn not(self) -> Self::Output {
491 Self(!self.0)
492 }
493}
494
495impl Neg for Int512 {
496 type Output = Self;
497
498 fn neg(self) -> Self::Output {
499 self.strict_neg()
500 }
501}
502
503impl RemAssign<Int512> for Int512 {
504 fn rem_assign(&mut self, rhs: Int512) {
505 *self = *self % rhs;
506 }
507}
508forward_ref_op_assign!(impl RemAssign, rem_assign for Int512, Int512);
509
510impl Mul<Int512> for Int512 {
511 type Output = Self;
512
513 fn mul(self, rhs: Self) -> Self::Output {
514 Self(self.0.checked_mul(rhs.0).unwrap())
515 }
516}
517forward_ref_binop!(impl Mul, mul for Int512, Int512);
518
519impl MulAssign<Int512> for Int512 {
520 fn mul_assign(&mut self, rhs: Self) {
521 self.0 = self.0.checked_mul(rhs.0).unwrap();
522 }
523}
524forward_ref_op_assign!(impl MulAssign, mul_assign for Int512, Int512);
525
526impl Shr<u32> for Int512 {
527 type Output = Self;
528
529 fn shr(self, rhs: u32) -> Self::Output {
530 self.checked_shr(rhs).unwrap_or_else(|_| {
531 panic!("right shift error: {rhs} is larger or equal than the number of bits in Int512",)
532 })
533 }
534}
535forward_ref_binop!(impl Shr, shr for Int512, u32);
536
537impl Shl<u32> for Int512 {
538 type Output = Self;
539
540 fn shl(self, rhs: u32) -> Self::Output {
541 self.checked_shl(rhs).unwrap_or_else(|_| {
542 panic!("left shift error: {rhs} is larger or equal than the number of bits in Int512",)
543 })
544 }
545}
546forward_ref_binop!(impl Shl, shl for Int512, u32);
547
548impl AddAssign<Int512> for Int512 {
549 fn add_assign(&mut self, rhs: Int512) {
550 self.0 = self.0.checked_add(rhs.0).unwrap();
551 }
552}
553forward_ref_op_assign!(impl AddAssign, add_assign for Int512, Int512);
554
555impl DivAssign<Int512> for Int512 {
556 fn div_assign(&mut self, rhs: Self) {
557 self.0 = self.0.checked_div(rhs.0).unwrap();
558 }
559}
560forward_ref_op_assign!(impl DivAssign, div_assign for Int512, Int512);
561
562impl ShrAssign<u32> for Int512 {
563 fn shr_assign(&mut self, rhs: u32) {
564 *self = Shr::<u32>::shr(*self, rhs);
565 }
566}
567forward_ref_op_assign!(impl ShrAssign, shr_assign for Int512, u32);
568
569impl ShlAssign<u32> for Int512 {
570 fn shl_assign(&mut self, rhs: u32) {
571 *self = Shl::<u32>::shl(*self, rhs);
572 }
573}
574forward_ref_op_assign!(impl ShlAssign, shl_assign for Int512, u32);
575
576impl<A> core::iter::Sum<A> for Int512
577where
578 Self: Add<A, Output = Self>,
579{
580 fn sum<I: Iterator<Item = A>>(iter: I) -> Self {
581 iter.fold(Self::zero(), Add::add)
582 }
583}
584
585#[cfg(test)]
586mod tests {
587 use super::*;
588 use crate::math::conversion::test_try_from_uint_to_int;
589
590 #[test]
591 fn size_of_works() {
592 assert_eq!(core::mem::size_of::<Int512>(), 64);
593 }
594
595 #[test]
596 fn int512_new_works() {
597 let num = Int512::new(1);
598 assert_eq!(
599 num.to_be_bytes(),
600 [
601 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
602 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
603 0, 0, 0, 0, 0, 0, 0, 1
604 ]
605 );
606
607 let num = Int512::new(-1);
608 assert_eq!(
609 num.to_be_bytes(),
610 [
611 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
612 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
613 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
614 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
615 ]
616 );
617
618 for v in [0, 1, -4, 18, 875786576, -11763498739, i128::MAX, i128::MIN] {
619 let uut = Int512::new(v);
621 assert_eq!(uut, Int512::from(v));
622 }
623 }
624
625 #[test]
626 fn int512_from_be_bytes_works() {
627 let num = Int512::from_be_bytes([1; 64]);
628 let a: [u8; 64] = num.to_be_bytes();
629 assert_eq!(a, [1; 64]);
630
631 let be_bytes = [
632 0u8, 222u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
633 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
634 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
635 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 1u8, 2u8, 3u8,
636 ];
637 let num = Int512::from_be_bytes(be_bytes);
638 let resulting_bytes: [u8; 64] = num.to_be_bytes();
639 assert_eq!(be_bytes, resulting_bytes);
640 }
641
642 #[test]
643 fn int512_not_works() {
644 let num = Int512::from_be_bytes([1; 64]);
645 let a = (!num).to_be_bytes();
646 assert_eq!(a, [254; 64]);
647
648 assert_eq!(!Int512::from(-1234806i128), Int512::from(!-1234806i128));
649
650 assert_eq!(!Int512::MAX, Int512::MIN);
651 assert_eq!(!Int512::MIN, Int512::MAX);
652 }
653
654 #[test]
655 fn int512_zero_works() {
656 let zero = Int512::zero();
657 assert_eq!(zero.to_be_bytes(), [0; 64]);
658 }
659
660 #[test]
661 fn uint512_one_works() {
662 let one = Int512::one();
663 let mut one_be = [0; 64];
664 one_be[63] = 1;
665
666 assert_eq!(one.to_be_bytes(), one_be);
667 }
668
669 #[test]
670 fn int512_endianness() {
671 let be_bytes = [
672 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
673 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
674 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
675 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 1u8, 2u8, 3u8,
676 ];
677 let le_bytes = [
678 3u8, 2u8, 1u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
679 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
680 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
681 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
682 ];
683
684 let a = Int512::from_be_bytes(be_bytes);
686 let b = Int512::from_le_bytes(le_bytes);
687 assert_eq!(a, Int512::from(65536u32 + 512 + 3));
688 assert_eq!(a, b);
689 }
690
691 #[test]
692 fn int512_convert_from() {
693 let a = Int512::from(5u128);
694 assert_eq!(a.0, I512::from(5u32));
695
696 let a = Int512::from(5u64);
697 assert_eq!(a.0, I512::from(5u32));
698
699 let a = Int512::from(5u32);
700 assert_eq!(a.0, I512::from(5u32));
701
702 let a = Int512::from(5u16);
703 assert_eq!(a.0, I512::from(5u32));
704
705 let a = Int512::from(5u8);
706 assert_eq!(a.0, I512::from(5u32));
707
708 let a = Int512::from(-5i128);
709 assert_eq!(a.0, I512::from(-5i32));
710
711 let a = Int512::from(-5i64);
712 assert_eq!(a.0, I512::from(-5i32));
713
714 let a = Int512::from(-5i32);
715 assert_eq!(a.0, I512::from(-5i32));
716
717 let a = Int512::from(-5i16);
718 assert_eq!(a.0, I512::from(-5i32));
719
720 let a = Int512::from(-5i8);
721 assert_eq!(a.0, I512::from(-5i32));
722
723 let values = [
725 Int64::MAX,
726 Int64::MIN,
727 Int64::one(),
728 -Int64::one(),
729 Int64::zero(),
730 ];
731 for v in values {
732 assert_eq!(Int512::from(v).to_string(), v.to_string());
733 }
734
735 let values = [
736 Int128::MAX,
737 Int128::MIN,
738 Int128::one(),
739 -Int128::one(),
740 Int128::zero(),
741 ];
742 for v in values {
743 assert_eq!(Int512::from(v).to_string(), v.to_string());
744 }
745
746 let values = [
747 Int256::MAX,
748 Int256::MIN,
749 Int256::one(),
750 -Int256::one(),
751 Int256::zero(),
752 ];
753 for v in values {
754 assert_eq!(Int512::from(v).to_string(), v.to_string());
755 }
756
757 let result = Int512::try_from("34567");
758 assert_eq!(
759 result.unwrap().0,
760 I512::from_str_radix("34567", 10).unwrap()
761 );
762
763 let result = Int512::try_from("1.23");
764 assert!(result.is_err());
765 }
766
767 #[test]
768 fn int512_try_from_unsigned_works() {
769 test_try_from_uint_to_int::<Uint256, Int256>("Uint256", "Int256");
770 test_try_from_uint_to_int::<Uint512, Int256>("Uint512", "Int256");
771 }
772
773 #[test]
774 fn int512_implements_display() {
775 let a = Int512::from(12345u32);
776 assert_eq!(format!("Embedded: {a}"), "Embedded: 12345");
777 assert_eq!(a.to_string(), "12345");
778
779 let a = Int512::from(-12345i32);
780 assert_eq!(format!("Embedded: {a}"), "Embedded: -12345");
781 assert_eq!(a.to_string(), "-12345");
782
783 let a = Int512::zero();
784 assert_eq!(format!("Embedded: {a}"), "Embedded: 0");
785 assert_eq!(a.to_string(), "0");
786 }
787
788 #[test]
789 fn int512_display_padding_works() {
790 let a = Int512::from(123u64);
792 assert_eq!(format!("Embedded: {a:05}"), "Embedded: 00123");
793 let a = Int512::from(-123i64);
794 assert_eq!(format!("Embedded: {a:05}"), "Embedded: -0123");
795
796 let a = Int512::from(123u64);
798 assert_eq!(format!("Embedded: {a:02}"), "Embedded: 123");
799 let a = Int512::from(-123i64);
800 assert_eq!(format!("Embedded: {a:02}"), "Embedded: -123");
801 }
802
803 #[test]
804 fn int512_to_be_bytes_works() {
805 assert_eq!(Int512::zero().to_be_bytes(), [0; 64]);
806
807 let mut max = [0xff; 64];
808 max[0] = 0x7f;
809 assert_eq!(Int512::MAX.to_be_bytes(), max);
810
811 let mut one = [0; 64];
812 one[63] = 1;
813 assert_eq!(Int512::from(1u128).to_be_bytes(), one);
814 assert_eq!(
816 Int512::from(240282366920938463463374607431768124608u128).to_be_bytes(),
817 [
818 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
819 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 180, 196, 179, 87, 165,
820 121, 59, 133, 246, 117, 221, 191, 255, 254, 172, 192
821 ]
822 );
823 assert_eq!(
824 Int512::from_be_bytes([
825 17, 4, 23, 32, 87, 67, 123, 200, 58, 91, 0, 38, 33, 21, 67, 78, 87, 76, 65, 54,
826 211, 201, 192, 7, 42, 233, 2, 240, 200, 115, 150, 240, 218, 88, 106, 45, 208, 134,
827 238, 119, 85, 22, 14, 88, 166, 195, 154, 73, 64, 10, 44, 59, 13, 22, 47, 12, 99, 8,
828 252, 96, 230, 187, 38, 29
829 ])
830 .to_be_bytes(),
831 [
832 17, 4, 23, 32, 87, 67, 123, 200, 58, 91, 0, 38, 33, 21, 67, 78, 87, 76, 65, 54,
833 211, 201, 192, 7, 42, 233, 2, 240, 200, 115, 150, 240, 218, 88, 106, 45, 208, 134,
834 238, 119, 85, 22, 14, 88, 166, 195, 154, 73, 64, 10, 44, 59, 13, 22, 47, 12, 99, 8,
835 252, 96, 230, 187, 38, 29
836 ]
837 );
838 }
839
840 #[test]
841 fn int512_to_le_bytes_works() {
842 assert_eq!(Int512::zero().to_le_bytes(), [0; 64]);
843
844 let mut max = [0xff; 64];
845 max[63] = 0x7f;
846 assert_eq!(Int512::MAX.to_le_bytes(), max);
847
848 let mut one = [0; 64];
849 one[0] = 1;
850 assert_eq!(Int512::from(1u128).to_le_bytes(), one);
851 assert_eq!(
853 Int512::from(240282366920938463463374607431768124608u128).to_le_bytes(),
854 [
855 192, 172, 254, 255, 191, 221, 117, 246, 133, 59, 121, 165, 87, 179, 196, 180, 0, 0,
856 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
857 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
858 ]
859 );
860 assert_eq!(
861 Int512::from_be_bytes([
862 17, 4, 23, 32, 87, 67, 123, 200, 58, 91, 0, 38, 33, 21, 67, 78, 87, 76, 65, 54,
863 211, 201, 192, 7, 42, 233, 2, 240, 200, 115, 150, 240, 218, 88, 106, 45, 208, 134,
864 238, 119, 85, 22, 14, 88, 166, 195, 154, 73, 64, 10, 44, 59, 13, 22, 47, 12, 99, 8,
865 252, 96, 230, 187, 38, 29
866 ])
867 .to_le_bytes(),
868 [
869 29, 38, 187, 230, 96, 252, 8, 99, 12, 47, 22, 13, 59, 44, 10, 64, 73, 154, 195,
870 166, 88, 14, 22, 85, 119, 238, 134, 208, 45, 106, 88, 218, 240, 150, 115, 200, 240,
871 2, 233, 42, 7, 192, 201, 211, 54, 65, 76, 87, 78, 67, 21, 33, 38, 0, 91, 58, 200,
872 123, 67, 87, 32, 23, 4, 17
873 ]
874 );
875 }
876
877 #[test]
878 fn int512_is_zero_works() {
879 assert!(Int512::zero().is_zero());
880 assert!(Int512(I512::from(0u32)).is_zero());
881
882 assert!(!Int512::from(1u32).is_zero());
883 assert!(!Int512::from(123u32).is_zero());
884 assert!(!Int512::from(-123i32).is_zero());
885 }
886
887 #[test]
888 fn int512_is_negative_works() {
889 assert!(Int512::MIN.is_negative());
890 assert!(Int512::from(-123i32).is_negative());
891
892 assert!(!Int512::MAX.is_negative());
893 assert!(!Int512::zero().is_negative());
894 assert!(!Int512::from(123u32).is_negative());
895 }
896
897 #[test]
898 fn int512_wrapping_methods() {
899 assert_eq!(
901 Int512::from(2u32).wrapping_add(Int512::from(2u32)),
902 Int512::from(4u32)
903 ); assert_eq!(Int512::MAX.wrapping_add(Int512::from(1u32)), Int512::MIN); assert_eq!(
908 Int512::from(7u32).wrapping_sub(Int512::from(5u32)),
909 Int512::from(2u32)
910 ); assert_eq!(Int512::MIN.wrapping_sub(Int512::from(1u32)), Int512::MAX); assert_eq!(
915 Int512::from(3u32).wrapping_mul(Int512::from(2u32)),
916 Int512::from(6u32)
917 ); assert_eq!(
919 Int512::MAX.wrapping_mul(Int512::from(2u32)),
920 Int512::from(-2i32)
921 ); assert_eq!(Int512::from(2u32).wrapping_pow(3), Int512::from(8u32)); assert_eq!(Int512::MAX.wrapping_pow(2), Int512::from(1u32)); }
927
928 #[test]
929 fn int512_json() {
930 let orig = Int512::from(1234567890987654321u128);
931 let serialized = serde_json::to_vec(&orig).unwrap();
932 assert_eq!(serialized.as_slice(), b"\"1234567890987654321\"");
933 let parsed: Int512 = serde_json::from_slice(&serialized).unwrap();
934 assert_eq!(parsed, orig);
935 }
936
937 #[test]
938 fn int512_compare() {
939 let a = Int512::from(12345u32);
940 let b = Int512::from(23456u32);
941
942 assert!(a < b);
943 assert!(b > a);
944 assert_eq!(a, Int512::from(12345u32));
945 }
946
947 #[test]
948 #[allow(clippy::op_ref)]
949 fn int512_math() {
950 let a = Int512::from(-12345i32);
951 let b = Int512::from(23456u32);
952
953 assert_eq!(a + b, Int512::from(11111u32));
955 assert_eq!(a + &b, Int512::from(11111u32));
956
957 assert_eq!(b - a, Int512::from(35801u32));
959 assert_eq!(b - &a, Int512::from(35801u32));
960
961 let mut c = Int512::from(300000u32);
963 c += b;
964 assert_eq!(c, Int512::from(323456u32));
965 let mut d = Int512::from(300000u32);
966 d += &b;
967 assert_eq!(d, Int512::from(323456u32));
968
969 let mut c = Int512::from(300000u32);
971 c -= b;
972 assert_eq!(c, Int512::from(276544u32));
973 let mut d = Int512::from(300000u32);
974 d -= &b;
975 assert_eq!(d, Int512::from(276544u32));
976
977 assert_eq!(a - b, Int512::from(-35801i32));
979 }
980
981 #[test]
982 #[should_panic]
983 fn int512_add_overflow_panics() {
984 let _ = Int512::MAX + Int512::from(12u32);
985 }
986
987 #[test]
988 #[allow(clippy::op_ref)]
989 fn int512_sub_works() {
990 assert_eq!(Int512::from(2u32) - Int512::from(1u32), Int512::from(1u32));
991 assert_eq!(Int512::from(2u32) - Int512::from(0u32), Int512::from(2u32));
992 assert_eq!(Int512::from(2u32) - Int512::from(2u32), Int512::from(0u32));
993 assert_eq!(Int512::from(2u32) - Int512::from(3u32), Int512::from(-1i32));
994
995 let a = Int512::from(10u32);
997 let b = Int512::from(3u32);
998 let expected = Int512::from(7u32);
999 assert_eq!(a - b, expected);
1000 assert_eq!(a - &b, expected);
1001 assert_eq!(&a - b, expected);
1002 assert_eq!(&a - &b, expected);
1003 }
1004
1005 #[test]
1006 #[should_panic]
1007 fn int512_sub_overflow_panics() {
1008 let _ = Int512::MIN + Int512::one() - Int512::from(2u32);
1009 }
1010
1011 #[test]
1012 fn int512_sub_assign_works() {
1013 let mut a = Int512::from(14u32);
1014 a -= Int512::from(2u32);
1015 assert_eq!(a, Int512::from(12u32));
1016
1017 let mut a = Int512::from(10u32);
1019 let b = Int512::from(3u32);
1020 let expected = Int512::from(7u32);
1021 a -= &b;
1022 assert_eq!(a, expected);
1023 }
1024
1025 #[test]
1026 #[allow(clippy::op_ref)]
1027 fn int512_mul_works() {
1028 assert_eq!(Int512::from(2u32) * Int512::from(3u32), Int512::from(6u32));
1029 assert_eq!(Int512::from(2u32) * Int512::zero(), Int512::zero());
1030
1031 let a = Int512::from(11u32);
1033 let b = Int512::from(3u32);
1034 let expected = Int512::from(33u32);
1035 assert_eq!(a * b, expected);
1036 assert_eq!(a * &b, expected);
1037 assert_eq!(&a * b, expected);
1038 assert_eq!(&a * &b, expected);
1039 }
1040
1041 #[test]
1042 fn int512_mul_assign_works() {
1043 let mut a = Int512::from(14u32);
1044 a *= Int512::from(2u32);
1045 assert_eq!(a, Int512::from(28u32));
1046
1047 let mut a = Int512::from(10u32);
1049 let b = Int512::from(3u32);
1050 a *= &b;
1051 assert_eq!(a, Int512::from(30u32));
1052 }
1053
1054 #[test]
1055 fn int512_pow_works() {
1056 assert_eq!(Int512::from(2u32).pow(2), Int512::from(4u32));
1057 assert_eq!(Int512::from(2u32).pow(10), Int512::from(1024u32));
1058 }
1059
1060 #[test]
1061 #[should_panic]
1062 fn int512_pow_overflow_panics() {
1063 _ = Int512::MAX.pow(2u32);
1064 }
1065
1066 #[test]
1067 fn int512_shr_works() {
1068 let original = Int512::from_be_bytes([
1069 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
1070 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
1071 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
1072 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 2u8, 0u8, 4u8, 2u8,
1073 ]);
1074
1075 let shifted = Int512::from_be_bytes([
1076 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
1077 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
1078 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8,
1079 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 128u8, 1u8, 0u8,
1080 ]);
1081
1082 assert_eq!(original >> 2u32, shifted);
1083 }
1084
1085 #[test]
1086 #[should_panic]
1087 fn int512_shr_overflow_panics() {
1088 let _ = Int512::from(1u32) >> 512u32;
1089 }
1090
1091 #[test]
1092 fn sum_works() {
1093 let nums = vec![
1094 Int512::from(17u32),
1095 Int512::from(123u32),
1096 Int512::from(540u32),
1097 Int512::from(82u32),
1098 ];
1099 let expected = Int512::from(762u32);
1100
1101 let sum_as_ref: Int512 = nums.iter().sum();
1102 assert_eq!(expected, sum_as_ref);
1103
1104 let sum_as_owned: Int512 = nums.into_iter().sum();
1105 assert_eq!(expected, sum_as_owned);
1106 }
1107
1108 #[test]
1109 fn int512_methods() {
1110 assert!(matches!(
1112 Int512::MAX.checked_add(Int512::from(1u32)),
1113 Err(OverflowError { .. })
1114 ));
1115 assert_eq!(
1116 Int512::from(1u32).checked_add(Int512::from(1u32)),
1117 Ok(Int512::from(2u32)),
1118 );
1119 assert!(matches!(
1120 Int512::MIN.checked_sub(Int512::from(1u32)),
1121 Err(OverflowError { .. })
1122 ));
1123 assert_eq!(
1124 Int512::from(2u32).checked_sub(Int512::from(1u32)),
1125 Ok(Int512::from(1u32)),
1126 );
1127 assert!(matches!(
1128 Int512::MAX.checked_mul(Int512::from(2u32)),
1129 Err(OverflowError { .. })
1130 ));
1131 assert_eq!(
1132 Int512::from(2u32).checked_mul(Int512::from(2u32)),
1133 Ok(Int512::from(4u32)),
1134 );
1135 assert!(matches!(
1136 Int512::MAX.checked_pow(2u32),
1137 Err(OverflowError { .. })
1138 ));
1139 assert_eq!(Int512::from(2u32).checked_pow(3u32), Ok(Int512::from(8u32)),);
1140 assert_eq!(
1141 Int512::MAX.checked_div(Int512::from(0u32)),
1142 Err(DivisionError::DivideByZero)
1143 );
1144 assert_eq!(
1145 Int512::from(6u32).checked_div(Int512::from(2u32)),
1146 Ok(Int512::from(3u32)),
1147 );
1148 assert_eq!(
1149 Int512::MAX.checked_div_euclid(Int512::from(0u32)),
1150 Err(DivisionError::DivideByZero)
1151 );
1152 assert_eq!(
1153 Int512::from(6u32).checked_div_euclid(Int512::from(2u32)),
1154 Ok(Int512::from(3u32)),
1155 );
1156 assert_eq!(
1157 Int512::from(7u32).checked_div_euclid(Int512::from(2u32)),
1158 Ok(Int512::from(3u32)),
1159 );
1160 assert!(matches!(
1161 Int512::MAX.checked_rem(Int512::from(0u32)),
1162 Err(DivideByZeroError { .. })
1163 ));
1164 assert_eq!(
1166 Int512::from(-12i32).checked_div(Int512::from(10i32)),
1167 Ok(Int512::from(-1i32)),
1168 );
1169 assert_eq!(
1170 Int512::from(-2i32).checked_pow(3u32),
1171 Ok(Int512::from(-8i32)),
1172 );
1173 assert_eq!(
1174 Int512::from(-6i32).checked_mul(Int512::from(-7i32)),
1175 Ok(Int512::from(42i32)),
1176 );
1177 assert_eq!(
1178 Int512::from(-2i32).checked_add(Int512::from(3i32)),
1179 Ok(Int512::from(1i32)),
1180 );
1181 assert_eq!(
1182 Int512::from(-1i32).checked_div_euclid(Int512::from(-2i32)),
1183 Ok(Int512::from(1u32)),
1184 );
1185
1186 assert_eq!(Int512::MAX.saturating_add(Int512::from(1u32)), Int512::MAX);
1188 assert_eq!(Int512::MIN.saturating_sub(Int512::from(1u32)), Int512::MIN);
1189 assert_eq!(Int512::MAX.saturating_mul(Int512::from(2u32)), Int512::MAX);
1190 assert_eq!(Int512::from(4u32).saturating_pow(2u32), Int512::from(16u32));
1191 assert_eq!(Int512::MAX.saturating_pow(2u32), Int512::MAX);
1192 }
1193
1194 #[test]
1195 #[allow(clippy::op_ref)]
1196 fn int512_implements_rem() {
1197 let a = Int512::from(10u32);
1198 assert_eq!(a % Int512::from(10u32), Int512::zero());
1199 assert_eq!(a % Int512::from(2u32), Int512::zero());
1200 assert_eq!(a % Int512::from(1u32), Int512::zero());
1201 assert_eq!(a % Int512::from(3u32), Int512::from(1u32));
1202 assert_eq!(a % Int512::from(4u32), Int512::from(2u32));
1203
1204 assert_eq!(
1205 Int512::from(-12i32) % Int512::from(10i32),
1206 Int512::from(-2i32)
1207 );
1208 assert_eq!(
1209 Int512::from(12i32) % Int512::from(-10i32),
1210 Int512::from(2i32)
1211 );
1212 assert_eq!(
1213 Int512::from(-12i32) % Int512::from(-10i32),
1214 Int512::from(-2i32)
1215 );
1216
1217 let a = Int512::from(10u32);
1219 let b = Int512::from(3u32);
1220 let expected = Int512::from(1u32);
1221 assert_eq!(a % b, expected);
1222 assert_eq!(a % &b, expected);
1223 assert_eq!(&a % b, expected);
1224 assert_eq!(&a % &b, expected);
1225 }
1226
1227 #[test]
1228 #[should_panic(expected = "divisor of zero")]
1229 fn int512_rem_panics_for_zero() {
1230 let _ = Int512::from(10u32) % Int512::zero();
1231 }
1232
1233 #[test]
1234 fn int512_rem_assign_works() {
1235 let mut a = Int512::from(30u32);
1236 a %= Int512::from(4u32);
1237 assert_eq!(a, Int512::from(2u32));
1238
1239 let mut a = Int512::from(25u32);
1241 let b = Int512::from(6u32);
1242 a %= &b;
1243 assert_eq!(a, Int512::from(1u32));
1244 }
1245
1246 #[test]
1247 fn int512_shr() {
1248 let x: Int512 = 0x8000_0000_0000_0000_0000_0000_0000_0000u128.into();
1249 assert_eq!(x >> 0, x); assert_eq!(
1251 x >> 1,
1252 Int512::from(0x4000_0000_0000_0000_0000_0000_0000_0000u128)
1253 );
1254 assert_eq!(
1255 x >> 4,
1256 Int512::from(0x0800_0000_0000_0000_0000_0000_0000_0000u128)
1257 );
1258 assert_eq!(
1260 Int512::MIN >> (core::mem::size_of::<Int512>() as u32 * 8 - 1),
1261 -Int512::one()
1262 );
1263 }
1264
1265 #[test]
1266 fn int512_shl() {
1267 let x: Int512 = 0x0800_0000_0000_0000_0000_0000_0000_0000u128.into();
1268 assert_eq!(x << 0, x); assert_eq!(
1270 x << 1,
1271 Int512::from(0x1000_0000_0000_0000_0000_0000_0000_0000u128)
1272 );
1273 assert_eq!(
1274 x << 4,
1275 Int512::from(0x8000_0000_0000_0000_0000_0000_0000_0000u128)
1276 );
1277 assert_eq!(
1279 Int512::one() << (core::mem::size_of::<Int512>() as u32 * 8 - 1),
1280 Int512::MIN
1281 );
1282 }
1283
1284 #[test]
1285 fn int512_abs_diff_works() {
1286 let a = Int512::from(42u32);
1287 let b = Int512::from(5u32);
1288 let expected = Uint512::from(37u32);
1289 assert_eq!(a.abs_diff(b), expected);
1290 assert_eq!(b.abs_diff(a), expected);
1291
1292 let c = Int512::from(-5i32);
1293 assert_eq!(b.abs_diff(c), Uint512::from(10u32));
1294 assert_eq!(c.abs_diff(b), Uint512::from(10u32));
1295 }
1296
1297 #[test]
1298 fn int512_abs_works() {
1299 let a = Int512::from(42i32);
1300 assert_eq!(a.abs(), a);
1301
1302 let b = Int512::from(-42i32);
1303 assert_eq!(b.abs(), a);
1304
1305 assert_eq!(Int512::zero().abs(), Int512::zero());
1306 assert_eq!((Int512::MIN + Int512::one()).abs(), Int512::MAX);
1307 }
1308
1309 #[test]
1310 fn int512_unsigned_abs_works() {
1311 assert_eq!(Int512::zero().unsigned_abs(), Uint512::zero());
1312 assert_eq!(Int512::one().unsigned_abs(), Uint512::one());
1313 assert_eq!(
1314 Int512::MIN.unsigned_abs(),
1315 Uint512::from_be_bytes(Int512::MAX.to_be_bytes()) + Uint512::one()
1316 );
1317
1318 let v = Int512::from(-42i32);
1319 assert_eq!(v.unsigned_abs(), v.abs_diff(Int512::zero()));
1320 }
1321
1322 #[test]
1323 #[should_panic = "attempt to calculate absolute value with overflow"]
1324 fn int512_abs_min_panics() {
1325 _ = Int512::MIN.abs();
1326 }
1327
1328 #[test]
1329 #[should_panic = "attempt to negate with overflow"]
1330 fn int512_neg_min_panics() {
1331 _ = -Int512::MIN;
1332 }
1333
1334 #[test]
1335 fn int512_partial_eq() {
1336 let test_cases = [(1, 1, true), (42, 42, true), (42, 24, false), (0, 0, true)]
1337 .into_iter()
1338 .map(|(lhs, rhs, expected): (u64, u64, bool)| {
1339 (Int512::from(lhs), Int512::from(rhs), expected)
1340 });
1341
1342 #[allow(clippy::op_ref)]
1343 for (lhs, rhs, expected) in test_cases {
1344 assert_eq!(lhs == rhs, expected);
1345 assert_eq!(&lhs == rhs, expected);
1346 assert_eq!(lhs == &rhs, expected);
1347 assert_eq!(&lhs == &rhs, expected);
1348 }
1349 }
1350}