@@ -379,39 +379,37 @@ impl CompressedEdwardsY {
379379     /// 
380380     /// Returns `None` if the input is not the \\(y\\)-coordinate of a 
381381     /// curve point. 
382+      // See https://www.rfc-editor.org/rfc/rfc8032.html#section-5.2.3. 
382383    pub  fn  decompress_unchecked ( & self )  -> CtOption < AffinePoint >  { 
383384        // Safe to unwrap here as the underlying data structure is a slice 
384385        let  ( sign,  b)  = self . 0 . split_last ( ) . expect ( "slice is non-empty" ) ; 
385386
386387        let  mut  y_bytes:  [ u8 ;  56 ]  = [ 0 ;  56 ] ; 
387388        y_bytes. copy_from_slice ( b) ; 
388- 
389-         // Recover x using y 
389+         // TODO: this should fail if unreduced. 
390390        let  y = FieldElement :: from_bytes ( & y_bytes) ; 
391-         let  yy = y. square ( ) ; 
392-         let  dyy = FieldElement :: EDWARDS_D  *  yy; 
393-         let  numerator = FieldElement :: ONE  - yy; 
394-         let  denominator = FieldElement :: ONE  - dyy; 
395391
396-         let  ( mut  x,  is_res)  = FieldElement :: sqrt_ratio ( & numerator,  & denominator) ; 
392+         // x^2 = (y^2 - 1) / (d y^2 - 1) 
393+         let  yy = y. square ( ) ; 
394+         let  u = yy - FieldElement :: ONE ; 
395+         let  v = FieldElement :: EDWARDS_D  *  yy - FieldElement :: ONE ; 
396+         let  ( mut  x,  is_square)  = FieldElement :: sqrt_ratio ( & u,  & v) ; 
397397
398398        // Compute correct sign of x 
399399        let  compressed_sign_bit = Choice :: from ( sign >> 7 ) ; 
400400        let  is_negative = x. is_negative ( ) ; 
401401        x. conditional_negate ( compressed_sign_bit ^ is_negative) ; 
402402
403-         CtOption :: new ( AffinePoint  {  x,  y } ,  is_res ) 
403+         CtOption :: new ( AffinePoint  {  x,  y } ,  is_square ) 
404404    } 
405405
406406    /// Attempt to decompress to an `AffinePoint`. 
407407     /// 
408408     /// Returns `None`: 
409409     /// - if the input is not the \\(y\\)-coordinate of a curve point. 
410-      /// - if the input point is not on the curve. 
411410     /// - if the input point has nonzero torsion component. 
412411     pub  fn  decompress ( & self )  -> CtOption < AffinePoint >  { 
413412        self . decompress_unchecked ( ) 
414-             . and_then ( |pt| CtOption :: new ( pt,  pt. is_on_curve ( )  &  pt. to_edwards ( ) . is_torsion_free ( ) ) ) 
415413    } 
416414
417415    /// View this `CompressedEdwardsY` as an array of bytes. 
0 commit comments