1- use  crate :: Uint ; 
21#[ cfg( feature = "alloc" ) ]  
32use  crate :: { BoxedUint ,  ConstantTimeSelect } ; 
3+ use  crate :: { Odd ,  Uint } ; 
44
5- pub ( crate )  fn  div_by_2 < const  LIMBS :  usize > ( a :  & Uint < LIMBS > ,  modulus :  & Uint < LIMBS > )  -> Uint < LIMBS >  { 
6-     // We are looking for such `x` that `x * 2 = y mod modulus`, 
7-     // where the given `a = M(y)` is the Montgomery representation of some `y`. 
8-     // This means that in Montgomery representation it would still apply: 
9-     // `M(x) + M(x) = a mod modulus`. 
10-     // So we can just forget about Montgomery representation, and return whatever is 
11-     // `a` divided by 2, and this will be the Montgomery representation of `x`. 
12-     // (Which means that this function works regardless of whether `a` 
13-     // is in Montgomery representation or not, but the algorithm below 
14-     // does need `modulus` to be odd) 
15- 
5+ pub ( crate )  const  fn  div_by_2 < const  LIMBS :  usize > ( 
6+     a :  & Uint < LIMBS > , 
7+     modulus :  & Odd < Uint < LIMBS > > , 
8+ )  -> Uint < LIMBS >  { 
9+     // We are looking for such `b` that `b + b = a mod modulus`. 
1610    // Two possibilities: 
1711    // - if `a` is even, we can just divide by 2; 
1812    // - if `a` is odd, we divide `(a + modulus)` by 2. 
1913    // To stay within the modulus we open the parentheses turning it into `a / 2 + modulus / 2 + 1` 
2014    // ("+1" because both `a` and `modulus` are odd, we lose 0.5 in each integer division). 
2115    // This will not overflow, so we can just use wrapping operations. 
2216
17+     // Note that this also works if `a` is a Montgomery representation modulo `modulus` 
18+     // of some integer `x`. 
19+     // If `b + b = a mod modulus` it means that `y + y = x mod modulus` where `y` is the integer 
20+     // whose Mongtgomery representation is `b`. 
21+ 
2322    let  ( half,  is_odd)  = a. shr1_with_carry ( ) ; 
24-     let  half_modulus = modulus. shr1 ( ) ; 
23+     let  half_modulus = modulus. 0 . shr1 ( ) ; 
2524
2625    let  if_even = half; 
2726    let  if_odd = half
@@ -32,7 +31,7 @@ pub(crate) fn div_by_2<const LIMBS: usize>(a: &Uint<LIMBS>, modulus: &Uint<LIMBS
3231} 
3332
3433#[ cfg( feature = "alloc" ) ]  
35- pub ( crate )  fn  div_by_2_boxed ( a :  & BoxedUint ,  modulus :  & BoxedUint )  -> BoxedUint  { 
34+ pub ( crate )  fn  div_by_2_boxed ( a :  & BoxedUint ,  modulus :  & Odd < BoxedUint > )  -> BoxedUint  { 
3635    debug_assert_eq ! ( a. bits_precision( ) ,  modulus. bits_precision( ) ) ; 
3736
3837    let  ( mut  half,  is_odd)  = a. shr1_with_carry ( ) ; 
0 commit comments