cryptix-bn254 0.1.0

A library for bn254 elliptic curve related algorithms
Documentation
#![allow(incomplete_features)]
#![feature(generic_const_exprs)]

use cryptix_bigint::bigint;
use cryptix_field::Element;
use cryptix_field::field::MulInverse;
use cryptix_field::field::montgomery::MontgomeryOps;
use cryptix_field::field::primefield::FpElement;
use cryptix_bn254::galoisfield::fp2::Fp2Element;
use cryptix_bn254::galoisfield::{U256, BN254};
use cryptix_bn254::{fp, fp2};

#[allow(non_upper_case_globals)]
const A: Fp2Element = fp2!(
    "206743e9b42b2cba7d527ee9b3284b03ffbd0bd7cd0aa20190ec5173cf9f5fa3",
    "110a06573d3face930d8722a9bbe8584814a795afc1eceb391c5cf229d09d3b0"
);

#[allow(non_upper_case_globals)]
const B: Fp2Element = fp2!(
    "1d4edbc4972a57dd6af4c6e1cfededccdb6a46e7ffc8913306bb32fa3e1f19f2",
    "07482f3cf322f298cfa2b51eac13e3d8d37683e994faa78d979cbc5feed461a3"
);

#[test]
fn test_fp2_add() {
    assert_eq!(A + B, Fp2Element(
        FpElement(Element::new(bigint!(U256, "1892bb2c0b5584962e12f84b831638c87a0652bfccd33320f0a7846e0dbe7982"))),
        FpElement(Element::new(bigint!(U256, "1852359430629f82007b274947d2695d54c0fd449119764129628b828bde3553")))
    ))
}

#[test]
fn test_fp2_mul() {
    assert_eq!(A * B, Fp2Element(
        FpElement(Element::new(bigint!(U256, "229ba3a0643c8bce9464c9039a8dd2289468a3516df19df822a37ee63e78ea50"))),
        FpElement(Element::new(bigint!(U256, "198828d14ab2b1c1d3f990f1dcccdbdcd8a244ddef6d775c2d50a6aa818f6268")))
    ))
}

#[test]
fn test_fp2_inv() {
    assert_eq!(A.mul_inv(), Fp2Element(
        FpElement(Element::new(bigint!(U256, "1d621521c9c115a8db5542145caea493057e8a95198363e53857c891c03bb4f4"))),
        FpElement(Element::new(bigint!(U256, "12d91a8f136975d62d4a969fd342b1f8e8d03beb97c758d407703a13a117cf92")))
    ))
}

#[test]
fn test_fp2_exp() {
    let e: FpElement<U256, BN254> = fp!("01");
    assert_eq!(A.mont_exp(e.repr()), A);

    let e: FpElement<U256, BN254> = fp!("02");
    assert_eq!(A.mont_exp(e.repr()), A * A);
}


#[cfg(feature = "rand")]
#[test]
fn test_fp2_sqr_mul() {
    use rand::SeedableRng;
    let mut rng = rand_chacha::ChaCha8Rng::from_seed(SEED);
    for _ in 0..TEST_COUNT {
        let a = Fp2Element::rand(&mut rng).mont_form();
        let c = a.mont_sqr().mont_rdc();
        let d = a.mont_mul(a).mont_rdc();

        assert_eq!(c, d)
    }
}

#[cfg(feature = "rand")]
#[test]
fn test_fp2_mont_inv() {
    use rand::SeedableRng;
    use cryptix_field::field::MulIdentity;
    let mut rng = rand_chacha::ChaCha8Rng::from_seed(SEED);
    for _ in 0..TEST_COUNT {
        // c = aR
        let a = Fp2Element::rand(&mut rng).mont_form();
        // b = a^-1R^-1
        let b = a.mont_inv();
        // bcR^-1 = 
        assert_eq!(a.mont_mul(b).mont_rdc(), Fp2Element::ONE);
    }
}

#[cfg(feature = "rand")]
#[test]
fn test_fp2_map() {
    use rand::SeedableRng;
    use cryptix_field::Modular;
    let mut rng = rand_chacha::ChaCha8Rng::from_seed(SEED);
    for _ in 0..20 {
        let a = Fp2Element::rand(&mut rng).mont_form();
        let c = a.map_frob();
        let b = a.mont_exp(BN254::P).mont_rdc();
        let c = c.mont_rdc();

        assert_eq!(b, c);
    }
}