Skip to content
This repository was archived by the owner on Dec 8, 2025. It is now read-only.

Commit 33a1de2

Browse files
committed
Replace __multi3 with a faster alternative, on wasm
1 parent 938e0ff commit 33a1de2

File tree

2 files changed

+45
-5
lines changed

2 files changed

+45
-5
lines changed

ff/src/biginteger/arithmetic.rs

Lines changed: 42 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,30 @@
11
use ark_std::vec::Vec;
22

3+
/// Make 4 u64 multiplications, instead of 1 u128
4+
/// It's faster than __multi3 in wasm
5+
/// https://github.com/rust-lang/compiler-builtins/blob/4797774cd72e453e30785cfee684aaf68e16e03e/src/int/mul.rs#L108
6+
/// https://github.com/zkBob/fawkes-crypto/pull/15
7+
#[cfg(target_family = "wasm")]
8+
#[inline(always)]
9+
pub fn u64_mul_u64(x: u64, y: u64) -> u128 {
10+
let x_low = (x as u32) as u64;
11+
let x_high = x >> 32;
12+
let y_low = (y as u32) as u64;
13+
let y_high = y >> 32;
14+
15+
let z_low = x_low * y_low;
16+
let z_high = x_high * y_high;
17+
let z = u128::from(x_low * y_high) + u128::from(x_high * y_low);
18+
19+
(u128::from(z_high) << 64) + (z << 32) + u128::from(z_low)
20+
}
21+
22+
#[cfg(not(target_family = "wasm"))]
23+
#[inline(always)]
24+
pub fn u64_mul_u64(x: u64, y: u64) -> u128 {
25+
u128::from(x) * u128::from(y)
26+
}
27+
328
/// Calculate a + b + carry, returning the sum and modifying the
429
/// carry value.
530
macro_rules! adc {
@@ -15,6 +40,19 @@ macro_rules! adc {
1540
/// Calculate a + (b * c) + carry, returning the least significant digit
1641
/// and setting carry to the most significant digit.
1742
macro_rules! mac_with_carry {
43+
($a:expr, $b:expr, $c:expr, &mut $carry:expr$(,)?) => {{
44+
let tmp = ($a as u128) + crate::biginteger::arithmetic::u64_mul_u64($b, $c) + ($carry as u128);
45+
// let tmp = ($a as u128) + ($b as u128 * $c as u128) + ($carry as u128);
46+
47+
$carry = (tmp >> 64) as u64;
48+
49+
tmp as u64
50+
}};
51+
}
52+
53+
/// Calculate a + (b * c) + carry, returning the least significant digit
54+
/// and setting carry to the most significant digit.
55+
macro_rules! const_mac_with_carry {
1856
($a:expr, $b:expr, $c:expr, &mut $carry:expr$(,)?) => {{
1957
let tmp = ($a as u128) + ($b as u128 * $c as u128) + ($carry as u128);
2058

@@ -38,7 +76,8 @@ macro_rules! sbb {
3876

3977
#[inline(always)]
4078
pub(crate) fn mac(a: u64, b: u64, c: u64, carry: &mut u64) -> u64 {
41-
let tmp = (u128::from(a)) + u128::from(b) * u128::from(c);
79+
let tmp = (u128::from(a)) + u64_mul_u64(b, c);
80+
// let tmp = (u128::from(a)) + u128::from(b) * u128::from(c);
4281

4382
*carry = (tmp >> 64) as u64;
4483

@@ -47,7 +86,8 @@ pub(crate) fn mac(a: u64, b: u64, c: u64, carry: &mut u64) -> u64 {
4786

4887
#[inline(always)]
4988
pub(crate) fn mac_discard(a: u64, b: u64, c: u64, carry: &mut u64) {
50-
let tmp = (u128::from(a)) + u128::from(b) * u128::from(c);
89+
let tmp = (u128::from(a)) + u64_mul_u64(b, c);
90+
// let tmp = (u128::from(a)) + u128::from(b) * u128::from(c);
5191

5292
*carry = (tmp >> 64) as u64;
5393
}

ff/src/fields/macros.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -191,7 +191,7 @@ macro_rules! impl_Fp {
191191
for i in 0..$limbs {
192192
let mut carry = 0;
193193
for j in 0..$limbs {
194-
r[j + i] = mac_with_carry!(r[j + i], (self.0).0[i], (other.0).0[j], &mut carry);
194+
r[j + i] = const_mac_with_carry!(r[j + i], (self.0).0[i], (other.0).0[j], &mut carry);
195195
}
196196
r[$limbs + i] = carry;
197197
}
@@ -200,9 +200,9 @@ macro_rules! impl_Fp {
200200
for i in 0..$limbs {
201201
let k = r[i].wrapping_mul(inv);
202202
let mut carry = 0;
203-
mac_with_carry!(r[i], k, modulus.0[0], &mut carry);
203+
const_mac_with_carry!(r[i], k, modulus.0[0], &mut carry);
204204
for j in 1..$limbs {
205-
r[j + i] = mac_with_carry!(r[j + i], k, modulus.0[j], &mut carry);
205+
r[j + i] = const_mac_with_carry!(r[j + i], k, modulus.0[j], &mut carry);
206206
}
207207
r[$limbs + i] = adc!(r[$limbs + i], _carry2, &mut carry);
208208
_carry2 = carry;

0 commit comments

Comments
 (0)