mirror of
https://github.com/saymrwulf/curve25519-dalek-source.git
synced 2026-09-04 20:24:10 +00:00
Merge branch 'master' into develop
This commit is contained in:
commit
64e4274aad
6 changed files with 77 additions and 17 deletions
|
|
@ -1,6 +1,6 @@
|
|||
[package]
|
||||
name = "curve25519-dalek"
|
||||
version = "0.8.1"
|
||||
version = "0.9.0"
|
||||
authors = ["Isis Lovecruft <isis@patternsinthevoid.net>",
|
||||
"Henry de Valence <hdevalence@hdevalence.ca>"]
|
||||
readme = "README.md"
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
|
||||
# curve25519-dalek   
|
||||
# curve25519-dalek [](https://crates.io/curve25519-dalek) [](https://docs.rs/curve25519-dalek) [](https://travis-ci.org/isislovecruft/curve25519-dalek)
|
||||
|
||||
**A low-level cryptographic library for point, group, field, and scalar
|
||||
operations on a curve isomorphic to the twisted Edwards curve defined by -x²+y²
|
||||
|
|
@ -44,7 +44,7 @@ Extensive documentation is available [here](https://docs.rs/curve25519-dalek).
|
|||
To install, add the following to the dependencies section of your project's
|
||||
`Cargo.toml`:
|
||||
|
||||
curve25519-dalek = "^0.8"
|
||||
curve25519-dalek = "^0.9"
|
||||
|
||||
Then, in your library or executable source, add:
|
||||
|
||||
|
|
@ -57,7 +57,6 @@ fast.
|
|||
## TODO
|
||||
|
||||
* Implement hashing to a point on the curve (Elligator).
|
||||
* Maybe use serde for serialization.
|
||||
* Make a new `mask` type in `subtle.rs` and return that instead of `u8`s.
|
||||
* Implement all utilities in Golang's `crypto/subtle` package, and
|
||||
move the module to its own crate.
|
||||
|
|
|
|||
|
|
@ -90,7 +90,7 @@ use core::ops::Index;
|
|||
use constants;
|
||||
use field::FieldElement;
|
||||
use scalar::Scalar;
|
||||
use subtle::arrays_equal_ct;
|
||||
use subtle::arrays_equal;
|
||||
use subtle::bytes_equal_ct;
|
||||
use subtle::CTAssignable;
|
||||
use subtle::CTEq;
|
||||
|
|
@ -518,8 +518,8 @@ impl CTAssignable for ExtendedPoint {
|
|||
|
||||
impl CTEq for ExtendedPoint {
|
||||
fn ct_eq(&self, other: &ExtendedPoint) -> u8 {
|
||||
arrays_equal_ct( self.compress_edwards().as_bytes(),
|
||||
other.compress_edwards().as_bytes())
|
||||
arrays_equal( self.compress_edwards().as_bytes(),
|
||||
other.compress_edwards().as_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -23,7 +23,7 @@ use core::ops::{Index, IndexMut};
|
|||
use core::cmp::{Eq, PartialEq};
|
||||
use core::ops::Neg;
|
||||
|
||||
use subtle::arrays_equal_ct;
|
||||
use subtle::arrays_equal;
|
||||
use subtle::byte_is_nonzero;
|
||||
use subtle::CTAssignable;
|
||||
use subtle::CTEq;
|
||||
|
|
@ -96,7 +96,7 @@ impl CTEq for FieldElement {
|
|||
///
|
||||
/// `1u8` if the two `FieldElement`s are equal, and `0u8` otherwise.
|
||||
fn ct_eq(&self, other: &FieldElement) -> u8 {
|
||||
arrays_equal_ct(&self.to_bytes(), &other.to_bytes())
|
||||
arrays_equal(&self.to_bytes(), &other.to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -47,7 +47,7 @@ use constants;
|
|||
use utils::{load3, load4};
|
||||
use subtle::CTAssignable;
|
||||
use subtle::CTEq;
|
||||
use subtle::arrays_equal_ct;
|
||||
use subtle::arrays_equal;
|
||||
|
||||
/// The `Scalar` struct represents an element in ℤ/lℤ, where
|
||||
///
|
||||
|
|
@ -76,7 +76,7 @@ impl PartialEq for Scalar {
|
|||
///
|
||||
/// True if they are equal, and false otherwise.
|
||||
fn eq(&self, other: &Self) -> bool {
|
||||
arrays_equal_ct(&self.0, &other.0) == 1u8
|
||||
arrays_equal(&self.0, &other.0) == 1u8
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -87,7 +87,7 @@ impl CTEq for Scalar {
|
|||
///
|
||||
/// `1u8` if they are equal, and `0u8` otherwise.
|
||||
fn ct_eq(&self, other: &Self) -> u8 {
|
||||
arrays_equal_ct(&self.0, &other.0)
|
||||
arrays_equal(&self.0, &other.0)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -69,12 +69,16 @@ pub fn bytes_equal_ct(a: u8, b: u8) -> u8 {
|
|||
|
||||
/// Test if a byte is non-zero in constant time.
|
||||
///
|
||||
/// ```rust,ignore
|
||||
/// ```
|
||||
/// # extern crate curve25519_dalek;
|
||||
/// # use curve25519_dalek::subtle::byte_is_nonzero;
|
||||
/// # fn main() {
|
||||
/// let mut x: u8;
|
||||
/// x = 0;
|
||||
/// assert!(byte_is_nonzero(x));
|
||||
/// assert!(byte_is_nonzero(x) == 0);
|
||||
/// x = 3;
|
||||
/// assert!(byte_is_nonzero(x) == 1);
|
||||
/// # }
|
||||
/// ```
|
||||
///
|
||||
/// # Return
|
||||
|
|
@ -90,17 +94,74 @@ pub fn byte_is_nonzero(b: u8) -> u8 {
|
|||
(x & 1)
|
||||
}
|
||||
|
||||
/// Check equality of two 32-byte arrays in constant time.
|
||||
/// Check equality of two arrays, `a` and `b`, in constant time.
|
||||
///
|
||||
/// There is a `debug_assert!` that the two arrays are of equal length. For
|
||||
/// example, the following code will panic:
|
||||
///
|
||||
/// ```rust,ignore
|
||||
/// let a: [u8; 3] = [0, 0, 0];
|
||||
/// let b: [u8; 4] = [0, 0, 0, 0];
|
||||
///
|
||||
/// assert!(arrays_equal(&a, &b) == 1);
|
||||
/// ```
|
||||
///
|
||||
/// However, if the arrays are equal length, but their contents do *not* match,
|
||||
/// `0u8` will be returned:
|
||||
///
|
||||
/// ```
|
||||
/// # extern crate curve25519_dalek;
|
||||
/// # use curve25519_dalek::subtle::arrays_equal;
|
||||
/// # fn main() {
|
||||
/// let a: [u8; 3] = [0, 1, 2];
|
||||
/// let b: [u8; 3] = [1, 2, 3];
|
||||
///
|
||||
/// assert!(arrays_equal(&a, &b) == 0);
|
||||
/// # }
|
||||
/// ```
|
||||
///
|
||||
/// And finally, if the contents *do* match, `1u8` is returned:
|
||||
///
|
||||
/// ```
|
||||
/// # extern crate curve25519_dalek;
|
||||
/// # use curve25519_dalek::subtle::arrays_equal;
|
||||
/// # fn main() {
|
||||
/// let a: [u8; 3] = [0, 1, 2];
|
||||
/// let b: [u8; 3] = [0, 1, 2];
|
||||
///
|
||||
/// assert!(arrays_equal(&a, &b) == 1);
|
||||
/// # }
|
||||
/// ```
|
||||
///
|
||||
/// This function is commonly used in various cryptographic applications, such
|
||||
/// as [signature verification](https://github.com/isislovecruft/ed25519-dalek/blob/0.3.2/src/ed25519.rs#L280),
|
||||
/// among many other applications.
|
||||
///
|
||||
/// # Return
|
||||
///
|
||||
/// Returns `1u8` if `a == b` and `0u8` otherwise.
|
||||
#[inline(always)]
|
||||
pub fn arrays_equal_ct(a: &[u8; 32], b: &[u8; 32]) -> u8 {
|
||||
pub fn arrays_equal(a: &[u8], b: &[u8]) -> u8 {
|
||||
debug_assert!(a.len() == b.len());
|
||||
|
||||
let mut x: u8 = 0;
|
||||
|
||||
for i in 0..32 {
|
||||
for i in 0 .. a.len() {
|
||||
x |= a[i] ^ b[i];
|
||||
}
|
||||
bytes_equal_ct(x, 0)
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod test {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
#[should_panic]
|
||||
fn arrays_equal_different_lengths() {
|
||||
let a: [u8; 3] = [0, 0, 0];
|
||||
let b: [u8; 4] = [0, 0, 0, 0];
|
||||
|
||||
assert!(arrays_equal(&a, &b) == 1);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue