decaf377/ark_curve/
on_curve.rs1use ark_ec::{
2 models::{twisted_edwards::Projective, twisted_edwards::TECurveConfig},
3 Group,
4};
5use ark_ff::{BigInteger, Field, PrimeField, Zero};
6use ark_serialize::CanonicalSerialize;
7
8use crate::ark_curve::constants;
9
10pub trait OnCurve {
11 fn is_on_curve(&self) -> bool;
12}
13
14#[cfg(feature = "arkworks")]
15impl<P: TECurveConfig> OnCurve for Projective<P> {
16 #[allow(non_snake_case)]
17 fn is_on_curve(&self) -> bool {
18 let XX = self.x.square();
19 let YY = self.y.square();
20 let ZZ = self.z.square();
21 let TT = self.t.square();
22
23 let on_curve = (YY + P::COEFF_A * XX) == (ZZ + P::COEFF_D * TT);
24 let on_segre_embedding = self.t * self.z == self.x * self.y;
25 let z_non_zero = self.z != P::BaseField::zero();
26 let point_order_2r = {
27 let mut r_bytes = [0u8; 32];
28 (*constants::R)
29 .serialize_compressed(&mut r_bytes[..])
30 .expect("serialization into array should be infallible");
31 let r = P::ScalarField::from_le_bytes_mod_order(&r_bytes);
32 let mut two_r_bigint = r.into_bigint();
33 two_r_bigint.mul2();
34 self.mul_bigint(two_r_bigint) == Projective::zero()
35 };
36
37 on_curve && on_segre_embedding && z_non_zero && point_order_2r
38 }
39}