1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
// Copyright © 2024 kyberlib. All rights reserved.
// SPDX-License-Identifier: Apache-2.0 OR MIT
//! # `kyberlib` — FIPS 203 ML-KEM in Rust
//!
//! Audit-friendly, `no_std`-compatible implementation of **FIPS 203
//! ML-KEM** (the standardised CRYSTALS-Kyber post-quantum key
//! encapsulation mechanism, finalised August 2024). 60/60 ACVP
//! conformance against the NIST test corpus.
//!
//! [](https://kyberlib.com)
//!
//! ## At a glance
//!
//! - **Three parameter sets**: [`MlKem512`], [`MlKem768`] (default),
//! [`MlKem1024`] — covering NIST security categories 1, 3, 5.
//! - **Two APIs**: the v0.0.7 *typed-state* API ([`KemCore`] trait +
//! typed wrappers) and the legacy free-function API
//! ([`keypair`] / [`encapsulate`] / [`decapsulate`]).
//! - **Constant-time**: KyberSlash audit clean (ADR 0003); secrets
//! carry [`zeroize::Zeroize`]; `dudect` regression gate in
//! `scripts/dudect.sh`.
//! - **`no_std`**: optional `std` feature. Default features pull in
//! `std` for ergonomic error types.
//! - **No `unsafe`** in the safe core. The optional `avx2` / `nasm`
//! backends scope `unsafe` to the SIMD module only.
//!
//! ## Quick start (typed API — recommended)
//!
//! ```
//! # fn main() -> Result<(), kyberlib::KyberLibError> {
//! use kyberlib::{KemCore, MlKem768};
//!
//! let mut rng = rand::thread_rng();
//!
//! // Bob generates a (decap, encap) keypair.
//! let (bob_dk, bob_ek) = MlKem768::generate(&mut rng)?;
//!
//! // Alice encapsulates a shared secret against Bob's encap key.
//! let (ciphertext, ss_alice) = bob_ek.encapsulate(&mut rng)?;
//!
//! // Bob decapsulates with his decap key (implicit rejection per
//! // FIPS 203 §6.3 — never panics, never branches on validity).
//! let ss_bob = bob_dk.decapsulate(&ciphertext);
//!
//! assert_eq!(ss_alice, ss_bob);
//! # Ok(()) }
//! ```
//!
//! ## Quick start (legacy free-function API)
//!
//! ```
//! # fn main() -> Result<(), kyberlib::KyberLibError> {
//! use kyberlib::{keypair, encapsulate, decapsulate};
//!
//! let mut rng = rand::thread_rng();
//! let bob = keypair(&mut rng)?;
//! let (ct, ss_a) = encapsulate(&bob.public, &mut rng)?;
//! let ss_b = decapsulate(&ct, &bob.secret)?;
//! assert_eq!(ss_a, ss_b);
//! # Ok(()) }
//! ```
//!
//! ## Cargo features
//!
//! | Feature | Default | Description |
//! |---|---|---|
//! | `std` | ✅ | Enables the `std` library — required for `std::error::Error` on [`KyberLibError`]. Disable for `no_std` targets. |
//! | `kyber768` | ✅ | NIST security category 3 (≈ AES-192). Default. |
//! | `kyber512` | | NIST security category 1 (≈ AES-128). Mutually exclusive with `kyber768`/`kyber1024`. |
//! | `kyber1024` | | NIST security category 5 (≈ AES-256). Required by CNSA 2.0 for NSS by 2027-01-01. Mutually exclusive with `kyber768`/`kyber512`. |
//! | `90s` | | "Kyber-90s" variant — SHA-2 / AES-CTR instead of SHAKE. Removed in FIPS 203 but retained for pre-spec compatibility. |
//! | `90s-fixslice` | | `90s` with a bitsliced AES implementation (`aes` + `ctr` crates). |
//! | `avx2` | | AVX2-accelerated backend (x86_64 only). Compile-errors on other arches. |
//! | `nasm` | | AVX2 via NASM assembler (instead of GAS). Requires NASM installed. Implies `avx2`. |
//! | `hazmat` | | Re-exports the IND-CPA primitives (no Fujisaki–Okamoto transform). Advanced use only; the resulting construction is NOT IND-CCA secure. |
//!
//! ## Architecture
//!
//! See [`api`] for the legacy free-function surface, [`ml_kem`] for
//! the v0.0.7 typed-state API, [`kex`] for the Uake/Ake key-exchange
//! wrappers, and [`error`] for the [`KyberLibError`] enum.
//!
//! ## Errors
//!
//! All fallible public functions return [`KyberLibError`]. Variants:
//!
//! - [`KyberLibError::InvalidInput`] — input slice length mismatch.
//! Typical cause: two peers using different security levels.
//! - [`KyberLibError::InvalidKey`] — imported keypair fails the
//! encap/decap self-test (the public and secret halves don't
//! belong together).
//! - [`KyberLibError::InvalidLength`] — buffer length below the
//! required copy length.
//! - [`KyberLibError::Decapsulation`] — ciphertext failed to
//! authenticate. *Not* normally returned: the FIPS 203 implicit-
//! rejection construction returns a pseudorandom shared secret on
//! invalid input instead.
//! - [`KyberLibError::RandomBytesGeneration`] — external RNG failed
//! (e.g. hardware RNG fault).
//!
//! ## Macros (legacy compatibility surface)
//!
//! See [`macros`] for the `kyberlib_*` macro family that wraps the
//! free-function API for terser call sites. Prefer the typed API
//! ([`KemCore`]) in new code.
//!
// Every public item must carry rustdoc. See issue #137.
// `unsafe` policy:
// - Default build (no `avx2`, no `nasm`): `forbid(unsafe_code)` —
// strongest guarantee, no inner `#[allow]` can lift it.
// - With `--features avx2` or `--features nasm`: crate-level
// `deny(unsafe_code)` keeps the safe-core modules (api / kex /
// kem / ml_kem / params / rng / symmetric / oid / error) unsafe-
// free; only the `mod avx2;` declaration itself carries
// `#[allow(unsafe_code)]`, so the SIMD intrinsics + assembly
// trampolines are the only place `unsafe` is permitted.
// - Phase 1.2 (#143) tracks the full source relocation into a
// dedicated `kyberlib-asm` workspace crate. The granular gate
// below gives the same *safety property* (safe core stays
// unsafe-free under every feature combination) without the
// cross-crate refactor.
// Prevent usage of mutually exclusive features
compile_error!;
// Phase 5 backend selection. Both backend features are reservations
// only at this stage — they declare the feature name in the manifest
// so downstream consumers can pre-wire `--features fips` or
// `--features verified` against the eventual delegation surface
// (issues #170 / #171). Today they are pure no-ops: the pure-Rust
// path is always used regardless of which is enabled.
//
// The mutual-exclusion guard between `fips` and `verified` lands
// alongside the first feature with a non-trivial implementation.
// Until then we tolerate `--all-features` enabling both for CI's
// sake.
/// Marker for the `fips` backend (skeleton — see issue #170).
pub const __FIPS_BACKEND_STUB: &str =
"kyberlib `fips` feature is a phase-5 placeholder — see issue #170";
/// Marker for the `verified` backend (skeleton — see issue #171).
pub const __VERIFIED_BACKEND_STUB: &str =
"kyberlib `verified` feature is a phase-5 placeholder — see issue #171";
// `#[allow(unsafe_code)]` is the granular exception to the crate-level
// `deny(unsafe_code)` policy (see the policy block above). The safe-core
// modules — declared below this — inherit `deny` and stay unsafe-free
// even under `--features avx2`. Phase 1.2 (#143) relocates this module
// into `kyberlib-asm` so the source layout matches the safety policy
// 1:1.
// `cfg_attr` (rather than `#[allow]` directly) keeps the `allow` and
// the cfg-gating in sync — without this, Rust 1.74's E0453 check
// triggers `allow(unsafe_code) incompatible with previous forbid`
// before cfg evaluation, even though the module is excluded under
// default features.
use *;
/// Reference implementation for the KyberLib library.
use *;
pub use indcpa;
// WebAssembly bindings live in the dedicated `kyberlib-wasm` workspace
// crate from v0.0.7 onwards (#144). The `wasm` Cargo feature is retained
// as a no-op for one release for downstream compatibility.
/// API for the KyberLib library.
/// Error types for the KyberLib library.
/// Key encapsulation module for the KyberLib library.
/// Key exchange structs for the KyberLib library.
/// Macro utilities for the KyberLib library.
/// Parameters for the KyberLib library.
/// Random number generators for the KyberLib library.
/// Symmetric key encapsulation module for the KyberLib library.
/// FIPS 203 ML-KEM type-state API (v0.0.7 — see issue #130).
/// Parameter-pack trait unifying ML-KEM-512 / 768 / 1024 — foundation
/// for the const-generic refactor tracked as #130b.
/// Internal test-surface wrappers. **Not part of the public API.**
///
/// Wraps the generic FIPS 203 pipeline functions for integration-test
/// harnesses that need deterministic-seed access across all three
/// parameter sets (e.g. NIST ACVP). Items here may change or
/// disappear without warning — downstream code MUST NOT depend on
/// them.
/// IETF LAMPS object identifiers for ML-KEM parameter sets (v0.0.7
/// — see issue #150).
pub use *;
pub use KyberLibError;
pub use *;
pub use ;
pub use ;
pub use MlKemParams;
pub use ;
// Feature hack to expose private functions for the Known Answer Tests
// and fuzzing. Will fail to compile if used outside `cargo test` or
// the fuzz binaries.
pub use *;