Open-source Rust library

Password hashing for Rust that upgrades old hashes as users sign in

hsh hashes passwords with Argon2id, bcrypt, scrypt or PBKDF2 under one policy, and when a stored hash falls behind that policy, the next successful sign-in replaces it.

  • Linux
  • macOS
  • Windows
  • Command line
  • AWS-LC FIPS module

What it does

Password storage that keeps up with its own policy

Each card opens its section on the features page.

One policy, four algorithms

Argon2id, bcrypt, scrypt and PBKDF2 behind one Policy. New hashes use its algorithm; any of the four verifies.

How a policy works

Rehash on login

When a stored hash is weaker than the policy, a successful verify returns a fresh hash to save in its place.

How upgrades happen

A pepper with key rotation

An HMAC-SHA-256 pepper with numbered keys, so a stolen database alone cannot be cracked offline.

How the pepper works

FIPS 140-3 mode

A FIPS policy hashes only with PBKDF2 through the AWS-LC FIPS module, and refuses to hash at all in a build that cannot.

What the mode guarantees

Safety rails

bcrypt input over 72 bytes is rejected, not truncated; comparisons are constant time; secrets are wiped from memory.

See the rails

A command-line tool

hsh hashes, verifies, rehashes and inspects from the shell, and calibrates the cost to your hardware.

Use it from the shell

Algorithms

The OWASP 2025 minimums, out of the box

Policy::owasp_minimum_2025() starts from these parameters. Every one can be raised.

Default

Argon2id

19,456 KiB of memory, 2 passes, 1 lane. Memory-hard, the recommended choice for new systems.

Compare the algorithms

Legacy and compatibility

bcrypt and scrypt

bcrypt at cost 10 with a 72-byte limit; scrypt at N = 217, r = 8, p = 1.

Compare the algorithms

FIPS 140-3

PBKDF2

HMAC-SHA-256 with 600,000 iterations. The only one of the four with FIPS-validated implementations.

The FIPS mode

Install

Hash, verify and upgrade in one call

Hash with a policy, then verify with the same policy: a hash that has fallen behind comes back upgraded. The library needs Rust 1.85 or newer.

  • cargo add hsh
  • cargo install hsh-cli
src/main.rs
use hsh::{api, Outcome, Policy};

fn main() -> Result<(), hsh::Error> {
    let policy = Policy::owasp_minimum_2025();
    let stored = api::hash(&policy, "correct horse")?;

    match api::verify_and_upgrade(&policy, "correct horse", &stored)? {
        Outcome::Valid { rehashed: Some(new) } => { /* save new */ }
        Outcome::Valid { rehashed: None } => { /* signed in */ }
        Outcome::Invalid => { /* deny */ }
    }
    Ok(())
}
Security

Fails closed, and says so

hsh refuses rather than degrades: no silent truncation, no silent fallback from a FIPS policy, no peppered hash accepted without its key.

hsh is at 0.0.x and has not had a third-party audit. The security page lists what is checked, what is a stub, and what is not promised.

Unsafe code
Forbidden
Fuzz targets
5
Release signing
Keyless cosign
Build provenance
SLSA

In numbers

What the workspace ships

Counted from hsh 0.0.10, the latest release of the library on crates.io.

Password algorithms
4
Default Argon2id memory
19 MiB
PBKDF2 iterations
600,000
Crates on crates.io
5
  • hsh: the library
  • hsh-cli: the hsh command
  • hsh-kms: the pepper
  • hsh-digest: SHA-2, SHA-3, BLAKE3
  • hsh-backend-awslc: the FIPS route

What is hsh?

hsh, the Hash (HSH) project, is a free, open-source password hashing library for Rust. You describe how passwords should be stored in a Policy; api::hash turns a password into a PHC string to store, and api::verify_and_upgrade checks a password against a stored hash and, when the hash was made under an older or weaker policy, returns a new one to save. It supports Argon2id, bcrypt, scrypt and PBKDF2, an optional pepper and a FIPS 140-3 mode, and is dual-licensed under Apache-2.0 or MIT.

Is it quantum-resistant?

The old version of this site said so; it is not a claim hsh makes. hsh stores passwords with the established password-hashing functions above. For post-quantum key exchange or signatures, use a library built for them.

Which version should I use?

0.0.10, the latest release of the hsh library on crates.io, published on 27 May 2026. The repository is tagged 0.0.12, but that release did not reach crates.io for the library or the command-line tool. The changelog has the detail.

Who makes it?

hsh is written by Sebastien Rousseau and its contributors. The source, the issue tracker and every release are on GitHub; the crates are on crates.io. Read more on the about page.