Skip to content

Commit 2a713f3

Browse files
authored
yescrypt: add link to paper and improve docs (#693)
Incorporates portions of the paper into comments/rustdoc
1 parent b822e3f commit 2a713f3

File tree

4 files changed

+41
-7
lines changed

4 files changed

+41
-7
lines changed

yescrypt/README.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ yescrypt is a variant of the [scrypt] password-based key derivation function and
1515
[Password Hashing Competition]. It has been adopted by several Linux distributions for the system
1616
password hashing function, including Fedora, Debian, Ubuntu, and Arch.
1717

18+
The algorithm is described in [yescrypt - a Password Hashing Competition submission][paper].
19+
1820
## ⚠️ Security Warning
1921

2022
The implementation contained in this crate has never been independently audited!
@@ -64,3 +66,4 @@ dual licensed as above, without any additional terms or conditions.
6466
[yescrypt]: https://www.openwall.com/yescrypt/
6567
[scrypt]: https://en.wikipedia.org/wiki/Scrypt
6668
[Password Hashing Competition]: https://www.password-hashing.net/
69+
[paper]: https://www.password-hashing.net/submissions/specs/yescrypt-v2.pdf

yescrypt/src/flags.rs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,12 @@ const MODE_MASK: u32 = 0x3;
1010
const RW_FLAVOR_MASK: u32 = 0x3fc;
1111

1212
/// Flags for selecting the "flavor" of `yescrypt`.
13+
///
14+
/// A bitmask allowing to enable the individual extra features of yescrypt, e.g:
15+
///
16+
/// - [`Flags::RW`]: yescrypt’s native mode. Call [`Flags::default`] to fully configure this.
17+
/// - [`Flags::WORM`]: conservative enhancement of classic scrypt. Mutually exclusive with `RW`.
18+
/// - [`Flags::EMPTY`]: requests classic scrypt.
1319
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
1420
pub struct Flags(pub(crate) u32);
1521

yescrypt/src/params.rs

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,9 @@ pub struct Params {
2020
pub(crate) flags: Flags,
2121

2222
/// `N`: CPU/memory cost (like `scrypt`).
23+
///
24+
/// yescrypt, including in scrypt compatibility mode, is defined only for values of N that are
25+
/// powers of 2 (and larger than 1, which matches scrypt’s requirements).
2326
pub(crate) n: u64,
2427

2528
/// `r`: block size (like `scrypt`).
@@ -28,10 +31,14 @@ pub struct Params {
2831
/// `p`: parallelism (like `scrypt`).
2932
pub(crate) p: u32,
3033

31-
/// special to yescrypt.
34+
/// Controls yescrypt’s computation time while keeping its peak memory usage the same.
35+
///
36+
/// `t = 0` is optimal for achieving the highest normalized area-time cost for ASIC attackers.
3237
pub(crate) t: u32,
3338

34-
/// special to yescrypt.
39+
/// The number of cost upgrades performed to the hash so far.
40+
///
41+
/// `0` means no upgrades yet, and is currently the only allowed value.
3542
pub(crate) g: u32,
3643

3744
/// special to yescrypt.

yescrypt/src/pwxform.rs

Lines changed: 23 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,31 @@
1-
//! pwxform: parallel wide transformation
1+
//! pwxform stands for "parallel wide transformation", although it can as well be tuned to be as
2+
//! narrow as one 64-bit lane.
3+
//!
4+
//! It operates on 64-bit lanes which are designed to be grouped into wider "simple SIMD" lanes,
5+
//! which are in turn possibly grouped into an even wider "gather SIMD" vector.
26
37
use crate::{
48
salsa20,
59
util::{slice_as_chunks_mut, xor},
610
};
711

8-
// These are tunable, but they must meet certain constraints.
12+
/// Number of 64-bit lanes per "simple SIMD" lane (requiring only arithmetic and bitwise operations
13+
/// on its 64-bit elements). Must be a power of 2.
914
const PWXSIMPLE: usize = 2;
15+
16+
/// Number of parallel "simple SIMD" lanes per "gather SIMD" vector (requiring "S-box lookups" of
17+
/// values as wide as a "simple SIMD" lane from PWXgather typically non-contiguous memory
18+
/// locations). Must be a power of 2.
1019
const PWXGATHER: usize = 4;
20+
21+
/// Number of sequential rounds of pwxform’s basic transformation. Must be a power of 2, plus 2
22+
/// (e.g. 3, 4, 6, 10).
1123
const PWXROUNDS: usize = 6;
24+
25+
/// Number of S-box index bits, thereby controlling the size of each of pwxform’s two S-boxes
26+
/// (in "simple SIMD" wide elements).
1227
const SWIDTH: usize = 8;
1328

14-
// Derived values. Not tunable on their own.
1529
const PWXBYTES: usize = PWXGATHER * PWXSIMPLE * 8;
1630
const PWXWORDS: usize = PWXBYTES / size_of::<u32>();
1731
const SMASK: usize = ((1 << SWIDTH) - 1) * PWXSIMPLE * 8;
@@ -28,9 +42,13 @@ pub(crate) struct PwxformCtx<'a> {
2842
}
2943

3044
impl PwxformCtx<'_> {
31-
/// Compute `B = BlockMix_pwxform{salsa20/2, ctx, r}(B)`.
45+
/// Compute `B = BlockMix_pwxform{salsa20/2, ctx, r}(B)`. Input `B` must be 128 bytes in length.
3246
///
33-
/// The input `B` must be 128r bytes in length.
47+
/// `BlockMix_pwxform` differs from scrypt’s `BlockMix` in that it doesn’t shuffle output
48+
/// sub-blocks, uses pwxform in place of Salsa20/8 for as long as sub-blocks processed with
49+
/// pwxform fit in the provided block B, and finally uses Salsa20/2 (that is, Salsa20 with only
50+
/// one double-round) to post-process the last sub-block output by pwxform (thereby finally
51+
/// mixing pwxform’s parallel lanes).
3452
pub(crate) fn blockmix_pwxform(&mut self, b: &mut [u32], r: usize) {
3553
// Convert 128-byte blocks to PWXbytes blocks
3654
// TODO(tarcieri): use upstream `[T]::as_chunks_mut` when MSRV is 1.88

0 commit comments

Comments
 (0)