| ... | ... | @@ -1,12 +1,10 @@ |
| 1 | 1 | //! Implementation of the IND-CCA2 post-quantum secure key encapsulation mechanism (KEM) |
| 2 | 2 | //! ML-KEM (NIST FIPS-203 publication) and CRYSTALS-Kyber (v3.02/"draft00" CFRG draft). |
| 3 | 3 | //! |
| 4 | | //! The schemes are not finalized yet, and are still subject to breaking changes. |
| 5 | | //! |
| 6 | 4 | //! The Kyber namespace suffix (currently `_d00`) refers to the version currently |
| 7 | | //! implemented, in accordance with the draft. |
| 8 | | //! The ML-KEM namespace suffix (currently `_01`) refers to the NIST FIPS-203 draft |
| 9 | | //! published on August 24, 2023, with the unintentional transposition of  having been reverted. |
| 5 | //! implemented, in accordance with the CFRG draft. |
| 6 | //! |
| 7 | //! The ML-KEM namespace refers to the FIPS-203 publication. |
| 10 | 8 | //! |
| 11 | 9 | //! Suffixes may not be updated if new versions of the documents only include editorial changes. |
| 12 | 10 | //! The suffixes will be removed once the schemes are finalized. |
| ... | ... | @@ -174,7 +172,9 @@ pub const kyber_d00 = struct { |
| 174 | 172 | }); |
| 175 | 173 | }; |
| 176 | 174 | |
| 177 | | pub const ml_kem_01 = struct { |
| 175 | pub const ml_kem_01 = @compileError("deprecated: final version of the specification has been published, use ml_kem instead"); |
| 176 | |
| 177 | pub const ml_kem = struct { |
| 178 | 178 | pub const MLKem512 = Kyber(.{ |
| 179 | 179 | .name = "ML-KEM-512", |
| 180 | 180 | .ml_kem = true, |
| ... | ... | @@ -207,9 +207,9 @@ const modes = [_]type{ |
| 207 | 207 | kyber_d00.Kyber512, |
| 208 | 208 | kyber_d00.Kyber768, |
| 209 | 209 | kyber_d00.Kyber1024, |
| 210 | | ml_kem_01.MLKem512, |
| 211 | | ml_kem_01.MLKem768, |
| 212 | | ml_kem_01.MLKem1024, |
| 210 | ml_kem.MLKem512, |
| 211 | ml_kem.MLKem768, |
| 212 | ml_kem.MLKem1024, |
| 213 | 213 | }; |
| 214 | 214 | const h_length: usize = 32; |
| 215 | 215 | const inner_seed_length: usize = 32; |
| ... | ... | @@ -505,7 +505,10 @@ fn Kyber(comptime p: Params) type { |
| 505 | 505 | // Derives inner PKE keypair from given seed. |
| 506 | 506 | fn innerKeyFromSeed(seed: [inner_seed_length]u8, pk: *InnerPk, sk: *InnerSk) void { |
| 507 | 507 | var expanded_seed: [64]u8 = undefined; |
| 508 | | sha3.Sha3_512.hash(&seed, &expanded_seed, .{}); |
| 508 | var h = sha3.Sha3_512.init(.{}); |
| 509 | if (p.ml_kem) h.update(&[1]u8{p.k}); |
| 510 | h.update(&seed); |
| 511 | h.final(&expanded_seed); |
| 509 | 512 | pk.rho = expanded_seed[0..32].*; |
| 510 | 513 | const sigma = expanded_seed[32..64]; |
| 511 | 514 | pk.aT = M.uniform(pk.rho, false); // Expand ρ to A; we'll transpose later on |