Skip to content
Merged
Show file tree
Hide file tree
Changes from 5 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
## v0.3.3
* Unify encoding of integer=0 across backends [#45]
* Deserialize returns an error on invalid radix, instead of panicking [#45]
* Fix primality test on num-bigint backend [#46]

[#45]: https://github.com/LFDT-Lockness/fast-paillier/pull/45
[#46]: https://github.com/LFDT-Lockness/fast-paillier/pull/46

## v0.3.2
* Make `random_below`, `random_below_ref`, `random_bits`, `random_bits_signed`,
Expand Down
110 changes: 69 additions & 41 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

18 changes: 13 additions & 5 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,8 @@ bytemuck = { version = "1.5", features = ["derive"], optional = true }
num-bigint = { version = "0.4.6", optional = true, default-features = false, features = ["rand"] }
num-traits = { version = "0.2.19", optional = true, default-features = false }
num-integer = { version = "0.1.46", optional = true, default-features = false }
glass_pumpkin = { version = "1.8", optional = true, default-features = false }
crypto-bigint = { version = "0.7", default-features = false, features = ["alloc"], optional = true }
crypto-primes = { version = "0.7", default-features = false, optional = true }
rand = { version = "0.8", optional = true, default-features = false }

rand_core = "0.6"
Expand All @@ -45,14 +46,17 @@ libpaillier = { version = "0.5", default-features = false, features = ["gmp"] }
[features]
default = ["backend-num-bigint", "std"]

std = ["glass_pumpkin?/std"]
no_std = ["glass_pumpkin?/no_std"]
std = []
no_std = []

serde = ["dep:serde"]
quickcheck = ["dep:quickcheck"]

backend-rug = ["dep:rug", "dep:bytemuck"]
backend-num-bigint = ["dep:num-bigint", "dep:num-traits", "dep:num-integer", "dep:glass_pumpkin", "dep:rand"]
backend-num-bigint = [
"dep:num-bigint", "dep:num-traits", "dep:num-integer", "dep:rand", "dep:crypto-bigint",
"dep:crypto-primes",
]

[[bench]]
name = "comparison"
Expand All @@ -63,4 +67,8 @@ harness = false
num-bigint.opt-level = 3
num-traits.opt-level = 3
num-integer.opt-level = 3
glass_pumpkin.opt-level = 3

# See https://docs.rs/cpubits/0.1.1/cpubits/#lint-configuration-for-cfgcpubits
[lints.rust.unexpected_cfgs]
level = "warn"
check-cfg = ['cfg(cpubits, values("16", "32", "64"))']
39 changes: 35 additions & 4 deletions src/backend/num_bigint.rs
Original file line number Diff line number Diff line change
Expand Up @@ -215,6 +215,11 @@ impl Integer {
self.invert_ref(modulo)
}
pub fn invert_ref(&self, modulo: &Self) -> Option<Self> {
// Nbi returns wrong result if modulo = 1, and self is negative. Correct response is `0`,
// but nbi gives `1`.
if self.cmp0().is_lt() && modulo.is_one() {
return Some(Self::zero());
}
let r = self.0.modinv(&modulo.0).map(Integer)?;
// Rug always produces a positive result here. Num-bigint always
// produces a result between zero and modulo. When modulo is negative,
Expand Down Expand Up @@ -294,11 +299,11 @@ impl Integer {
}

// TODO reps is unused here, need to unify with rug
pub fn is_probably_prime(&self, _reps: u32, rng: &mut impl rand_core::RngCore) -> IsPrime {
pub fn is_probably_prime(&self, _reps: u32, _rng: &mut impl rand_core::RngCore) -> IsPrime {
Comment thread
maurges marked this conversation as resolved.
Resolved
if self.cmp0().is_le() {
IsPrime::No
} else if glass_pumpkin::prime::check_with(self.0.magnitude(), rng) {
IsPrime::Yes
} else if glass_pumpkin::is_prime(self.0.magnitude()) {
IsPrime::Probably
} else {
IsPrime::No
}
Expand All @@ -310,7 +315,7 @@ impl Integer {
x.assign_random_bits(bit_size, rng);
x.set_bit(bit_size - 1, true);
x |= 1u32;
if glass_pumpkin::prime::check_with(x.0.magnitude(), rng) {
if glass_pumpkin::is_prime(x.0.magnitude()) {
break x;
}
}
Expand Down Expand Up @@ -424,6 +429,32 @@ impl quickcheck::Arbitrary for Integer {
}
}

/// This module was taken from <https://docs.rs/glass_pumpkin/2.0.0/src/glass_pumpkin/common.rs.html>
/// preserving only function that performs primality test. The code was modified to work with
/// older version of the `rand_core` crate.
///
/// We cannot use the latest version of the library as it requires introducing breaking changes
/// in the code. We cannot use older version of the library, which has compatible `rand_core`
/// dependency, as it is buggy.
///
/// We can migrate back to that dependency when we update our ecosystem to latest `rand_core`.
Comment thread
maurges marked this conversation as resolved.
Resolved
mod glass_pumpkin {
/// Checks if a number is probably prime using the deterministic-base
/// Baillie-PSW test.
///
/// The RNG parameter is retained for API compatibility and is not consumed.
Comment thread
maurges marked this conversation as resolved.
Resolved
pub fn is_prime(candidate: &num_bigint::BigUint) -> bool {
crypto_primes::is_prime(crypto_primes::Flavor::Any, &boxed_uint(candidate))
}

fn boxed_uint(n: &num_bigint::BigUint) -> crypto_bigint::BoxedUint {
crypto_bigint::cpubits! {
16 | 32 => { crypto_bigint::BoxedUint::from_words(n.iter_u32_digits()) }
64 => { crypto_bigint::BoxedUint::from_words(n.iter_u64_digits()) }
}
}
}

#[cfg(test)]
mod test {
use super::Integer;
Expand Down
Loading
Loading