crypto_bigint/uint/boxed/
ct.rs1use super::BoxedUint;
4use crate::{ConstantTimeSelect, Limb};
5use subtle::{Choice, ConditionallySelectable};
6
7impl ConstantTimeSelect for BoxedUint {
9 #[inline]
10 fn ct_select(a: &Self, b: &Self, choice: Choice) -> Self {
11 debug_assert_eq!(a.bits_precision(), b.bits_precision());
12 let mut limbs = vec![Limb::ZERO; a.nlimbs()].into_boxed_slice();
13
14 for i in 0..a.nlimbs() {
15 limbs[i] = Limb::conditional_select(&a.limbs[i], &b.limbs[i], choice);
16 }
17
18 Self { limbs }
19 }
20
21 #[inline]
22 fn ct_assign(&mut self, other: &Self, choice: Choice) {
23 debug_assert_eq!(self.bits_precision(), other.bits_precision());
24
25 for i in 0..self.nlimbs() {
26 self.limbs[i].conditional_assign(&other.limbs[i], choice);
27 }
28 }
29
30 #[inline]
31 fn ct_swap(a: &mut Self, b: &mut Self, choice: Choice) {
32 debug_assert_eq!(a.bits_precision(), b.bits_precision());
33
34 for i in 0..a.nlimbs() {
35 Limb::conditional_swap(&mut a.limbs[i], &mut b.limbs[i], choice);
36 }
37 }
38}
39
40#[cfg(test)]
41mod tests {
42 use super::BoxedUint;
43 use crate::ConstantTimeSelect;
44 use subtle::Choice;
45
46 #[test]
47 fn conditional_select() {
48 let a = BoxedUint::zero_with_precision(128);
49 let b = BoxedUint::max(128);
50
51 assert_eq!(a, BoxedUint::ct_select(&a, &b, Choice::from(0)));
52 assert_eq!(b, BoxedUint::ct_select(&a, &b, Choice::from(1)));
53 }
54}