Override from_noncanonical_u96() for Goldilocks field

This commit is contained in:
Robin Salen 2023-02-14 15:34:37 -05:00
parent 10e7329a95
commit bb2233cb21
No known key found for this signature in database
GPG Key ID: FB87BACFB3CB2007
2 changed files with 27 additions and 1 deletions

View File

@ -10,9 +10,22 @@ macro_rules! test_field_arithmetic {
use num::bigint::BigUint;
use rand::rngs::OsRng;
use rand::Rng;
use rand::{Rng, RngCore};
use $crate::types::{Field, Sample};
#[test]
fn modular_reduction() {
let mut rng = OsRng;
for _ in 0..10 {
let x_lo = rng.next_u64();
let x_hi = rng.next_u32();
let x = (x_lo as u128) + ((x_hi as u128) << 64);
let a = <$field>::from_noncanonical_u128(x);
let b = <$field>::from_noncanonical_u96((x_lo, x_hi));
assert_eq!(a, b);
}
}
#[test]
fn batch_inversion() {
for n in 0..20 {

View File

@ -110,6 +110,10 @@ impl Field for GoldilocksField {
Self(n)
}
fn from_noncanonical_u96((n_lo, n_hi): (u64, u32)) -> Self {
reduce96((n_lo, n_hi))
}
fn from_noncanonical_u128(n: u128) -> Self {
reduce128(n)
}
@ -337,6 +341,15 @@ unsafe fn add_no_canonicalize_trashing_input(x: u64, y: u64) -> u64 {
res_wrapped + EPSILON * (carry as u64)
}
/// Reduces to a 64-bit value. The result might not be in canonical form; it could be in between the
/// field order and `2^64`.
#[inline]
fn reduce96((x_lo, x_hi): (u64, u32)) -> GoldilocksField {
let t1 = x_hi as u64 * EPSILON;
let t2 = unsafe { add_no_canonicalize_trashing_input(x_lo, t1) };
GoldilocksField(t2)
}
/// Reduces to a 64-bit value. The result might not be in canonical form; it could be in between the
/// field order and `2^64`.
#[inline]