diff --git a/src/lib/pubkey/frodokem/frodo_constants.cpp b/src/lib/pubkey/frodokem/frodo_constants.cpp index ad810077d35..c5871192e97 100644 --- a/src/lib/pubkey/frodokem/frodo_constants.cpp +++ b/src/lib/pubkey/frodokem/frodo_constants.cpp @@ -1,14 +1,14 @@ /* -* FrodoKEM modes and constants -* Based on the MIT licensed reference implementation by the designers -* (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM modes and constants + * Based on the MIT licensed reference implementation by the designers + * (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ #include @@ -16,15 +16,11 @@ namespace Botan { -FrodoKEMConstants::FrodoKEMConstants(FrodoKEMMode mode) : m_mode(mode) { +FrodoKEMConstants::FrodoKEMConstants(FrodoKEMMode mode) : m_mode(mode), m_len_a(128), m_n_bar(8) { #if !defined(BOTAN_HAS_AES) BOTAN_ARG_CHECK(!mode.is_aes(), "cannot instantiate AES-based FrodoKEM: This build does not support AES"); #endif - //Common for all parameter sets: - m_n_bar = 8; - m_len_a = 128; - if(mode.is_ephemeral()) { m_len_salt = 0; } diff --git a/src/lib/pubkey/frodokem/frodo_constants.h b/src/lib/pubkey/frodokem/frodo_constants.h index 36ef716cb64..ede32521711 100644 --- a/src/lib/pubkey/frodokem/frodo_constants.h +++ b/src/lib/pubkey/frodokem/frodo_constants.h @@ -1,14 +1,14 @@ /* -* FrodoKEM constants -* Based on the MIT licensed reference implementation by the designers -* (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM constants + * Based on the MIT licensed reference implementation by the designers + * (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ #ifndef BOTAN_FRODOKEM_CONSTANTS_H_ #define BOTAN_FRODOKEM_CONSTANTS_H_ @@ -46,9 +46,9 @@ class BOTAN_TEST_API FrodoKEMConstants { size_t n() const { return m_n; } - size_t b() const { return m_b; } + size_t b() const { return m_b; } // extracted bits - size_t d() const { return m_d; } //D = logq + size_t d() const { return m_d; } // D = logq size_t n_bar() const { return m_n_bar; } @@ -62,7 +62,7 @@ class BOTAN_TEST_API FrodoKEMConstants { size_t len_ct_bytes() const { return (m_d * m_n * m_n_bar + m_d * m_n_bar * m_n_bar + m_len_salt) / 8; - } //Ciphertext length in bytes + } // Ciphertext length in bytes size_t len_public_key_bytes() const { return (m_len_a + (m_d * m_n * m_n_bar)) / 8; } @@ -84,14 +84,14 @@ class BOTAN_TEST_API FrodoKEMConstants { private: FrodoKEMMode m_mode; - size_t m_nist_strength; //len_sec + size_t m_nist_strength; size_t m_len_salt; size_t m_len_se; size_t m_len_a; - size_t m_b; //extracted bits + size_t m_b; size_t m_n; size_t m_n_bar; - size_t m_d; //log_q + size_t m_d; std::vector m_cdf_table; // Distribution table T_chi diff --git a/src/lib/pubkey/frodokem/frodo_matrix.cpp b/src/lib/pubkey/frodokem/frodo_matrix.cpp index 02c7233cdb0..30039b18997 100644 --- a/src/lib/pubkey/frodokem/frodo_matrix.cpp +++ b/src/lib/pubkey/frodokem/frodo_matrix.cpp @@ -1,14 +1,16 @@ /* -* FrodoKEM matrix logic -* Based on the MIT licensed reference implementation by the designers -* (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM matrix logic + * Based on the MIT licensed reference implementation by the designers + * (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ + +#include #include #include @@ -20,7 +22,6 @@ #include #include #include -#include #include #include #include @@ -38,8 +39,8 @@ namespace Botan { namespace { -std::vector make_elements_vector(const FrodoMatrix::Dimensions& dimensions) { - return std::vector(static_cast(std::get<0>(dimensions)) * std::get<1>(dimensions)); +secure_vector make_elements_vector(const FrodoMatrix::Dimensions& dimensions) { + return secure_vector(static_cast(std::get<0>(dimensions)) * std::get<1>(dimensions)); } std::function out, uint16_t i)> make_row_generator(const FrodoKEMConstants& constants, @@ -96,9 +97,6 @@ std::function out, uint16_t i)> make_row_generator(const FrodoMatrix FrodoMatrix::sample(const FrodoKEMConstants& constants, const Dimensions& dimensions, StrongSpan r) { - // Creates a matrix with n samples from the noise distribution which requires 16 bits to sample. - // The distribution is specified by its CDF. - // Input: pseudo-random values (2*n bytes) passed in r. BOTAN_ASSERT_NOMSG(r.size() % 2 == 0); const auto n = r.size() / 2; @@ -131,10 +129,6 @@ FrodoMatrix FrodoMatrix::mul_add_as_plus_e(const FrodoKEMConstants& constants, const FrodoMatrix& s, const FrodoMatrix& e, StrongSpan seed_a) { - // Generate-and-multiply: generate matrix A (N x N) row-wise, multiply by s on the right. - // Inputs: s^T (N_BAR x N), e (N x N_BAR), seed for matrix A - // Output: The elements of the FrodoMatrix will correspond to A*s + e (N x N_BAR). - BOTAN_ASSERT(std::get<0>(e.dimensions()) == std::get<1>(s.dimensions()) && std::get<1>(e.dimensions()) == std::get<0>(s.dimensions()), "FrodoMatrix dimension mismatch of E and S"); @@ -195,11 +189,6 @@ FrodoMatrix FrodoMatrix::mul_add_sa_plus_e(const FrodoKEMConstants& constants, const FrodoMatrix& s, const FrodoMatrix& e, StrongSpan seed_a) { - // Generate-and-multiply: generate matrix A (N x N) column-wise, multiply by s' on the left. - // Inputs: s', e' (N_BAR x N) - // Output: out = s'*A + e' (N_BAR x N) - // The matrix multiplication uses the row-wise blocking and packing (RWCF) approach described in: J.W. Bos, M. Ofner, J. Renes, - // T. Schneider, C. van Vredendaal, "The Matrix Reloaded: Multiplication Strategies in FrodoKEM". https://eprint.iacr.org/2021/711 BOTAN_ASSERT(std::get<0>(e.dimensions()) == std::get<0>(s.dimensions()) && std::get<1>(e.dimensions()) == std::get<1>(s.dimensions()), "FrodoMatrix dimension mismatch of E and S"); @@ -258,9 +247,6 @@ FrodoMatrix FrodoMatrix::mul_add_sb_plus_e(const FrodoKEMConstants& constants, const FrodoMatrix& b, const FrodoMatrix& s, const FrodoMatrix& e) { - // Multiply by s on the left - // Inputs: b (N x N_BAR), s (N_BAR x N), e (N_BAR x N_BAR) - // Output: out = s*b + e (N_BAR x N_BAR). The existing elements are overwritten and a self reference is returned. BOTAN_ASSERT(std::get<0>(b.dimensions()) == std::get<1>(s.dimensions()) && std::get<1>(b.dimensions()) == std::get<0>(s.dimensions()), "FrodoMatrix dimension mismatch of B and S"); @@ -308,12 +294,7 @@ FrodoMatrix FrodoMatrix::encode(const FrodoKEMConstants& constants, StrongSpan(a.dimensions()) == constants.n_bar() && @@ -328,12 +309,7 @@ FrodoMatrix FrodoMatrix::add(const FrodoKEMConstants& constants, return FrodoMatrix(a.dimensions(), std::move(elements)); } -FrodoMatrix FrodoMatrix::sub(const FrodoKEMConstants& constants, - const FrodoMatrix& a, - const FrodoMatrix& b) { // Subtract a and b - // Inputs: a, b (N_BAR x N_BAR) - // Output: c = a - b - +FrodoMatrix FrodoMatrix::sub(const FrodoKEMConstants& constants, const FrodoMatrix& a, const FrodoMatrix& b) { // Subtraction is defined for n_bar x n_bar matrices only BOTAN_ASSERT_NOMSG(a.dimensions() == b.dimensions()); BOTAN_ASSERT_NOMSG(std::get<0>(a.dimensions()) == constants.n_bar() && @@ -357,11 +333,7 @@ bool FrodoMatrix::constant_time_compare(const FrodoMatrix& other) const { sizeof(decltype(m_elements)::value_type) * m_elements.size()); } -FrodoMatrix FrodoMatrix::mul_bs(const FrodoKEMConstants& constants, - const FrodoMatrix& b, - const FrodoMatrix& s) { // Multiply by s on the right - // Inputs: b (N_BAR x N), s^T (N_BAR x N) - // Output: out = b*s (N_BAR x N_BAR) +FrodoMatrix FrodoMatrix::mul_bs(const FrodoKEMConstants& constants, const FrodoMatrix& b, const FrodoMatrix& s) { Dimensions dimensions = {constants.n_bar(), constants.n_bar()}; auto elements = make_elements_vector(dimensions); @@ -382,7 +354,6 @@ FrodoMatrix FrodoMatrix::mul_bs(const FrodoKEMConstants& constants, } void FrodoMatrix::pack(const FrodoKEMConstants& constants, StrongSpan out) const { - // Pack m_elements into a output buffer, copying lsb = D = log2 q bits from each input element. const size_t outlen = packed_size(constants); BOTAN_ASSERT_NOMSG(out.size() == outlen); @@ -468,9 +439,6 @@ FrodoPlaintext FrodoMatrix::decode(const FrodoKEMConstants& constants) const { FrodoMatrix FrodoMatrix::unpack(const FrodoKEMConstants& constants, const Dimensions& dimensions, StrongSpan packed_bytes) { - // Unpack the input char vector into the 16 bit m_elements vector, copying lsb bits - // for each output element from input. outlen must be at least ceil(inlen * 8 / lsb). - // m_elements is allocated here. const uint8_t lsb = static_cast(constants.d()); const size_t inlen = packed_bytes.size(); const size_t outlen = static_cast(std::get<0>(dimensions)) * std::get<1>(dimensions); @@ -526,7 +494,7 @@ FrodoMatrix FrodoMatrix::unpack(const FrodoKEMConstants& constants, } FrodoMatrix FrodoMatrix::deserialize(const Dimensions& dimensions, StrongSpan bytes) { - std::vector elements = make_elements_vector(dimensions); + auto elements = make_elements_vector(dimensions); BOTAN_ASSERT_NOMSG(elements.size() * 2 == bytes.size()); load_le(elements.data(), bytes.data(), elements.size()); return FrodoMatrix(dimensions, std::move(elements)); diff --git a/src/lib/pubkey/frodokem/frodo_matrix.h b/src/lib/pubkey/frodokem/frodo_matrix.h index 4c6e0dcaa24..4826316f708 100644 --- a/src/lib/pubkey/frodokem/frodo_matrix.h +++ b/src/lib/pubkey/frodokem/frodo_matrix.h @@ -1,14 +1,14 @@ /* -* FrodoKEM matrix logic -* Based on the MIT licensed reference implementation by the designers -* (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM matrix logic + * Based on the MIT licensed reference implementation by the designers + * (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ #ifndef BOTAN_FRODOKEM_MATRIX_H_ #define BOTAN_FRODOKEM_MATRIX_H_ @@ -43,41 +43,73 @@ class FrodoMatrix { return out; } - void pack(const FrodoKEMConstants& constants, - StrongSpan out) const; //Section 7.3 of spec + // Pack m_elements into a output buffer, copying lsb = D = log2 q bits from each input element. + // Section 7.3 of spec + void pack(const FrodoKEMConstants& constants, StrongSpan out) const; + FrodoSerializedMatrix serialize() const; FrodoPlaintext decode(const FrodoKEMConstants& constants) const; + // Unpack the input FrodoPackedMatrix into the 16 bit m_elements vector, copying d bits + // for each output element from input. outlen must be at least ceil(inlen * 8 / d). + // m_elements is allocated here. static FrodoMatrix unpack(const FrodoKEMConstants& constants, const Dimensions& dimensions, StrongSpan packed_bytes); + static FrodoMatrix deserialize(const Dimensions& dimensions, StrongSpan bytes); static FrodoMatrix encode(const FrodoKEMConstants& constants, - StrongSpan in); //Section 7.2 of spec + StrongSpan in); // Section 7.2 of spec + + // Creates a matrix with n samples from the noise distribution which requires 16 bits to sample. + // The distribution is specified by its CDF. + // Input: pseudo-random values (2*n bytes) passed in r. + // Section 7.5 of spec + static FrodoMatrix sample(const FrodoKEMConstants& constants, + const Dimensions& dimensions, + StrongSpan r); - static FrodoMatrix sample( - const FrodoKEMConstants& constants, - const Dimensions& dimensions, - StrongSpan r); // Matrix sampling from the error distribution, Section 7.5 of spec + // Generate-and-multiply: generate matrix A (N x N) row-wise, multiply by s on the right. + // Inputs: s^T (N_BAR x N), e (N x N_BAR), seed for matrix A + // Output: The elements of the FrodoMatrix will correspond to A*s + e (N x N_BAR). static FrodoMatrix mul_add_as_plus_e(const FrodoKEMConstants& constants, const FrodoMatrix& s, const FrodoMatrix& e, - StrongSpan seed_a); //A*s + e + StrongSpan seed_a); + + // Generate-and-multiply: generate matrix A (N x N) column-wise, multiply by s' on the left. + // Inputs: s', e' (N_BAR x N) + // Output: out = s'*A + e' (N_BAR x N) + // The matrix multiplication uses the row-wise blocking and packing (RWCF) approach described in: J.W. Bos, M. Ofner, J. Renes, + // T. Schneider, C. van Vredendaal, "The Matrix Reloaded: Multiplication Strategies in FrodoKEM". https://eprint.iacr.org/2021/711 static FrodoMatrix mul_add_sa_plus_e(const FrodoKEMConstants& constants, const FrodoMatrix& s, const FrodoMatrix& e, - StrongSpan seed_a); //s*A + e + StrongSpan seed_a); + + // Multiply by s on the left + // Inputs: b (N x N_BAR), s (N_BAR x N), e (N_BAR x N_BAR) + // Output: out = s*b + e (N_BAR x N_BAR). The existing elements are overwritten and a self reference is returned. static FrodoMatrix mul_add_sb_plus_e(const FrodoKEMConstants& constants, const FrodoMatrix& b, const FrodoMatrix& s, - const FrodoMatrix& e); //s*B + e - static FrodoMatrix mul_bs(const FrodoKEMConstants& constants, - const FrodoMatrix& b_p, - const FrodoMatrix& s); // B * s + const FrodoMatrix& e); + // Multiply by s on the right + // Inputs: b (N_BAR x N), s^T (N_BAR x N) + // Output: out = b*s (N_BAR x N_BAR) + static FrodoMatrix mul_bs(const FrodoKEMConstants& constants, const FrodoMatrix& b_p, const FrodoMatrix& s); + + // Add a and b + // Inputs: a, b (N_BAR x N_BAR) + // Output: c = a + b static FrodoMatrix add(const FrodoKEMConstants& constants, const FrodoMatrix& a, const FrodoMatrix& b); + + // Subtract a and b + // Inputs: a, b (N_BAR x N_BAR) + // Output: c = a - b static FrodoMatrix sub(const FrodoKEMConstants& constants, const FrodoMatrix& a, const FrodoMatrix& b); Dimensions dimensions() const { return {m_dim1, m_dim2}; } @@ -89,18 +121,14 @@ class FrodoMatrix { void reduce(const FrodoKEMConstants& constants); private: - FrodoMatrix(const Dimensions& dimensions, std::vector elements) : + FrodoMatrix(const Dimensions& dimensions, secure_vector elements) : m_dim1(std::get<0>(dimensions)), m_dim2(std::get<1>(dimensions)), m_elements(std::move(elements)) {} private: size_t m_dim1; size_t m_dim2; - // This may hold sensitive information (e.g. S and E matrices), though - // it is not modeled as a secure_vector (because it's uint16_t). - // - // TODO: consider allowing to use secure_vector for this - std::vector m_elements; + secure_vector m_elements; }; } // namespace Botan diff --git a/src/lib/pubkey/frodokem/frodo_mode.cpp b/src/lib/pubkey/frodokem/frodo_mode.cpp index 782ccef183c..bb45e6656ee 100644 --- a/src/lib/pubkey/frodokem/frodo_mode.cpp +++ b/src/lib/pubkey/frodokem/frodo_mode.cpp @@ -1,14 +1,14 @@ /* -* FrodoKEM modes and constants -* Based on the MIT licensed reference implementation by the designers -* (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM modes and constants + * Based on the MIT licensed reference implementation by the designers + * (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ #include diff --git a/src/lib/pubkey/frodokem/frodo_mode.h b/src/lib/pubkey/frodokem/frodo_mode.h index 9ed5d427437..0fc0b666d3d 100644 --- a/src/lib/pubkey/frodokem/frodo_mode.h +++ b/src/lib/pubkey/frodokem/frodo_mode.h @@ -1,14 +1,14 @@ /* -* FrodoKEM modes and constants -* Based on the MIT licensed reference implementation by the designers -* (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM modes and constants + * Based on the MIT licensed reference implementation by the designers + * (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ #ifndef BOTAN_FRODOKEM_MODE_H_ #define BOTAN_FRODOKEM_MODE_H_ diff --git a/src/lib/pubkey/frodokem/frodo_types.h b/src/lib/pubkey/frodokem/frodo_types.h index 4c48fb3fedd..2ed26402638 100644 --- a/src/lib/pubkey/frodokem/frodo_types.h +++ b/src/lib/pubkey/frodokem/frodo_types.h @@ -1,12 +1,12 @@ /* -* FrodoKEM modes and constants -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM modes and constants + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ #ifndef BOTAN_FRODOKEM_TYPES_H_ #define BOTAN_FRODOKEM_TYPES_H_ @@ -19,25 +19,41 @@ namespace Botan { +// Bytes of seed_a using FrodoSeedA = Strong, struct FrodoSeedA_>; + +// Bytes of s using FrodoSeedS = Strong, struct FrodoSeedS_>; + +// Bytes of seed_se using FrodoSeedSE = Strong, struct FrodoSeedSE_>; + +// Bytes of z using FrodoSeedZ = Strong, struct FrodoSeedZ_>; + +// Bytes of an r^(i) using FrodoSampleR = Strong, struct FrodoSampleR_>; + +// Bytes of pkh using FrodoPublicKeyHash = Strong, struct FrodoPublicKeyHash_>; +// Bytes of a packed Matrix using FrodoPackedMatrix = Strong, struct FrodoPackedMatrix_>; + +// Bytes of a serialized Matrix using FrodoSerializedMatrix = Strong, struct FrodoSerializedMatrix_>; +// Constant byte 0x5F/0x96 given to SHAKE for domain separation using FrodoDomainSeparator = Strong, struct FrodoDoaminSeparator_>; -/// u/u' in the spec +// Bytes of u/u' using FrodoPlaintext = Strong, struct FrodoPlaintext_>; +// Bytes of salt using FrodoSalt = Strong, struct FrodoSalt_>; -// TODO: Find a better name for this -using FrodoK = Strong, struct FrodoK_>; +// Bytes of k/k' aka intermediate shared secret in FO transform +using FrodoIntermediateSharedSecret = Strong, struct FrodoIntermediateSharedSecret_>; } // namespace Botan diff --git a/src/lib/pubkey/frodokem/frodokem.cpp b/src/lib/pubkey/frodokem/frodokem.cpp index 89eb22f9139..841ea486ab6 100644 --- a/src/lib/pubkey/frodokem/frodokem.cpp +++ b/src/lib/pubkey/frodokem/frodokem.cpp @@ -1,14 +1,14 @@ /* -* FrodoKEM implemenation -* Based on the MIT licensed reference implementation by the designers -* (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM implemenation + * Based on the MIT licensed reference implementation by the designers + * (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ #include @@ -107,7 +107,7 @@ class Frodo_KEM_Encryptor final : public PK_Ops::KEM_Encryption_with_KDF { shake.update(u); shake.update(salt); const auto seed_se = shake.output(consts.len_se_bytes()); - const auto k = shake.output(consts.len_sec_bytes()); + const auto k = shake.output(consts.len_sec_bytes()); shake.clear(); shake.update(consts.encapsulation_domain_separator()); @@ -188,7 +188,7 @@ class Frodo_KEM_Decryptor final : public PK_Ops::KEM_Decryption_with_KDF { shake.update(salt); const auto seed_se_p = shake.output(consts.len_se_bytes()); - const auto k_p = shake.output(consts.len_sec_bytes()); + const auto k_p = shake.output(consts.len_sec_bytes()); shake.clear(); shake.update(consts.encapsulation_domain_separator()); diff --git a/src/lib/pubkey/frodokem/frodokem.h b/src/lib/pubkey/frodokem/frodokem.h index 862da9fd67b..2bc8012b143 100644 --- a/src/lib/pubkey/frodokem/frodokem.h +++ b/src/lib/pubkey/frodokem/frodokem.h @@ -1,14 +1,14 @@ /* -* FrodoKEM implementation -* Based on the MIT licensed reference implementation by the designers -* (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) -* -* The Fellowship of the FrodoKEM: -* (C) 2023 Jack Lloyd -* 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity -* -* Botan is released under the Simplified BSD License (see license.txt) -*/ + * FrodoKEM implementation + * Based on the MIT licensed reference implementation by the designers + * (https://github.com/microsoft/PQCrypto-LWEKE/tree/master/src) + * + * The Fellowship of the FrodoKEM: + * (C) 2023 Jack Lloyd + * 2023 René Meusel, Amos Treiber - Rohde & Schwarz Cybersecurity + * + * Botan is released under the Simplified BSD License (see license.txt) + */ #ifndef BOTAN_FRODOKEM_H_ #define BOTAN_FRODOKEM_H_ @@ -25,7 +25,7 @@ class FrodoKEM_PublicKeyInternal; class FrodoKEM_PrivateKeyInternal; /** - * FrodoKEM is a unstructured lattice-based post-quantum secure KEM. It is a + * FrodoKEM is an unstructured lattice-based post-quantum secure KEM. It is a * round 3 candidate in NIST's PQC competition but was eventually not considered * for standardization by NIST. Nevertheless, it is endorsed by the German * Federal Office for Information Security for its conservative security diff --git a/src/scripts/dev_tools/gen_frodo_kat.py b/src/scripts/dev_tools/gen_frodo_kat.py index 08ff472213e..c1837e7b44e 100644 --- a/src/scripts/dev_tools/gen_frodo_kat.py +++ b/src/scripts/dev_tools/gen_frodo_kat.py @@ -107,25 +107,23 @@ def main(args = None): if args is None: args = sys.argv - output = open('src/tests/data/pubkey/frodokem_kat.vec', 'w') - print("# This file was auto-generated from the reference implemention's KATs", file=output) - print("# See src/scripts/dev_tools/gen_frodo_kat.py\n", file=output) + with open('src/tests/data/pubkey/frodokem_kat.vec', 'w') as output: + print("# This file was auto-generated from the reference implemention's KATs", file=output) + print("# See src/scripts/dev_tools/gen_frodo_kat.py\n", file=output) - for file in args[1:]: - mode = map_mode(os.path.basename(os.path.splitext(file)[0]), is_ephemeral) + for file in args[1:]: + mode = map_mode(os.path.basename(os.path.splitext(file)[0]), is_ephemeral) - reader = KatReader(open(file)) + reader = KatReader(open(file)) - print(f"[{mode}]", file=output) + print(f"[{mode}]", file=output) - for kat in list(reader.read_kats())[:25]: - kat = compress_kat(kat) + for kat in list(reader.read_kats())[:25]: + kat = compress_kat(kat) - for key in kat.keys(): - print(key, '=', kat[key], file=output) - print("", file=output) - - output.close() + for key in kat.keys(): + print(key, '=', kat[key], file=output) + print("", file=output) if __name__ == '__main__': sys.exit(main()) diff --git a/src/tests/test_frodokem.cpp b/src/tests/test_frodokem.cpp index 58a02f045fd..1774aedab94 100644 --- a/src/tests/test_frodokem.cpp +++ b/src/tests/test_frodokem.cpp @@ -1,5 +1,5 @@ /* - * Tests for FrodoKEM + * Tests for FrodoKEM ("You SHALL Pass") * - KAT tests using the KAT vectors from * https://github.com/microsoft/PQCrypto-LWEKE/tree/master/KAT * @@ -168,7 +168,7 @@ std::vector test_frodo_roundtrips() { result.test_eq("shared secrets match", ss, enc_res.shared_key()); result.test_eq("length of shared secret (decaps)", ss.size(), dec1.shared_key_length(0)); - // Decryption failures + // Decryption failures ("All right then, keep your secrets.") Botan::FrodoKEM_PrivateKey sk2(rng, mode); // Decryption failure: mismatching private key