Post-Quantum. MLDSA44 verifier
Some checks are pending
Build Debian packages / bookworm (push) Waiting to run
Build Debian packages / bullseye (push) Waiting to run
Build Debian packages / buster (push) Waiting to run
Build on FreeBSD / with UPnP (push) Waiting to run
Build on OSX / With USE_UPNP=no (push) Waiting to run
Build on OSX / With USE_UPNP=yes (push) Waiting to run
Build on Windows / clang-x86_64 (push) Waiting to run
Build on Windows / i686 (push) Waiting to run
Build on Windows / ucrt-x86_64 (push) Waiting to run
Build on Windows / x86_64 (push) Waiting to run
Build on Windows / CMake clang-x86_64 (push) Waiting to run
Build on Windows / CMake i686 (push) Waiting to run
Build on Windows / CMake ucrt-x86_64 (push) Waiting to run
Build on Windows / CMake x86_64 (push) Waiting to run
Build on Windows / XP (push) Waiting to run
Build on Ubuntu / Make with USE_UPNP=no (push) Waiting to run
Build on Ubuntu / Make with USE_UPNP=yes (push) Waiting to run
Build on Ubuntu / CMake with -DWITH_UPNP=OFF (push) Waiting to run
Build on Ubuntu / CMake with -DWITH_UPNP=ON (push) Waiting to run
Build containers / Building container for linux/amd64 (push) Waiting to run
Build containers / Building container for linux/arm64 (push) Waiting to run
Build containers / Building container for linux/arm/v7 (push) Waiting to run
Build containers / Building container for linux/386 (push) Waiting to run
Build containers / Pushing merged manifest (push) Blocked by required conditions

This commit is contained in:
orignal 2025-03-12 15:41:12 -04:00
parent 972c6854bc
commit dd58b2f867
5 changed files with 92 additions and 2 deletions

View file

@ -33,6 +33,9 @@
# if (!defined(LIBRESSL_VERSION_NUMBER) && (OPENSSL_VERSION_NUMBER != 0x030000000)) // 3.0.0, regression in SipHash, not implemented in LibreSSL # if (!defined(LIBRESSL_VERSION_NUMBER) && (OPENSSL_VERSION_NUMBER != 0x030000000)) // 3.0.0, regression in SipHash, not implemented in LibreSSL
# define OPENSSL_SIPHASH 1 # define OPENSSL_SIPHASH 1
# endif # endif
# if (OPENSSL_VERSION_NUMBER >= 0x030500000) // 3.5.0
# define OPENSSL_PQ 1
# endif
#endif #endif
namespace i2p namespace i2p

View file

@ -119,6 +119,16 @@ namespace data
memcpy (m_StandardIdentity.signingKey, signingKey, i2p::crypto::GOSTR3410_512_PUBLIC_KEY_LENGTH); memcpy (m_StandardIdentity.signingKey, signingKey, i2p::crypto::GOSTR3410_512_PUBLIC_KEY_LENGTH);
break; break;
} }
#if OPENSSL_PQ
case SIGNING_KEY_TYPE_MLDSA44:
{
memcpy (m_StandardIdentity, signingKey, 384);
excessLen = i2p::crypto::MLDSA44_PUBLIC_KEY_LENGTH - 384;
excessBuf = new uint8_t[excessLen];
memcpy (excessBuf, signingKey + 384, excessLen);
break;
}
#endif
default: default:
LogPrint (eLogError, "Identity: Signing key type ", (int)type, " is not supported"); LogPrint (eLogError, "Identity: Signing key type ", (int)type, " is not supported");
} }
@ -352,6 +362,10 @@ namespace data
return new i2p::crypto::GOSTR3410_512_Verifier (i2p::crypto::eGOSTR3410TC26A512); return new i2p::crypto::GOSTR3410_512_Verifier (i2p::crypto::eGOSTR3410TC26A512);
case SIGNING_KEY_TYPE_REDDSA_SHA512_ED25519: case SIGNING_KEY_TYPE_REDDSA_SHA512_ED25519:
return new i2p::crypto::RedDSA25519Verifier (); return new i2p::crypto::RedDSA25519Verifier ();
#if OPENSSL_PQ
case SIGNING_KEY_TYPE_MLDSA44:
return new i2p::crypto::MLDSA44Verifier ();
#endif
case SIGNING_KEY_TYPE_RSA_SHA256_2048: case SIGNING_KEY_TYPE_RSA_SHA256_2048:
case SIGNING_KEY_TYPE_RSA_SHA384_3072: case SIGNING_KEY_TYPE_RSA_SHA384_3072:
case SIGNING_KEY_TYPE_RSA_SHA512_4096: case SIGNING_KEY_TYPE_RSA_SHA512_4096:
@ -373,6 +387,18 @@ namespace data
auto keyLen = verifier->GetPublicKeyLen (); auto keyLen = verifier->GetPublicKeyLen ();
if (keyLen <= 128) if (keyLen <= 128)
verifier->SetPublicKey (m_StandardIdentity.signingKey + 128 - keyLen); verifier->SetPublicKey (m_StandardIdentity.signingKey + 128 - keyLen);
#if OPENSSL_PQ
else if (keyLen > 384)
{
// for post-quantum
uint8_t * signingKey = new uint8_t[keyLen];
memcpy (signingKey, m_StandardIdentity.signingKey, 384);
size_t excessLen = keyLen - 384;
memcpy (signingKey + 384, m_ExtendedBuffer + 4, excessLen); // right after signing and crypto key types
verifier->SetPublicKey (signingKey);
delete[] signingKey;
}
#endif
else else
{ {
// for P521 // for P521

View file

@ -55,6 +55,8 @@ namespace data
Identity& operator=(const Keys& keys); Identity& operator=(const Keys& keys);
size_t FromBuffer (const uint8_t * buf, size_t len); size_t FromBuffer (const uint8_t * buf, size_t len);
IdentHash Hash () const; IdentHash Hash () const;
operator uint8_t * () { return reinterpret_cast<uint8_t *>(this); }
operator const uint8_t * () const { return reinterpret_cast<const uint8_t *>(this); }
}; };
Keys CreateRandomKeys (); Keys CreateRandomKeys ();
@ -77,7 +79,8 @@ namespace data
const uint16_t SIGNING_KEY_TYPE_GOSTR3410_CRYPTO_PRO_A_GOSTR3411_256 = 9; const uint16_t SIGNING_KEY_TYPE_GOSTR3410_CRYPTO_PRO_A_GOSTR3411_256 = 9;
const uint16_t SIGNING_KEY_TYPE_GOSTR3410_TC26_A_512_GOSTR3411_512 = 10; // approved by FSB const uint16_t SIGNING_KEY_TYPE_GOSTR3410_TC26_A_512_GOSTR3411_512 = 10; // approved by FSB
const uint16_t SIGNING_KEY_TYPE_REDDSA_SHA512_ED25519 = 11; // for LeaseSet2 only const uint16_t SIGNING_KEY_TYPE_REDDSA_SHA512_ED25519 = 11; // for LeaseSet2 only
const uint16_t SIGNING_KEY_TYPE_MLDSA44 = 15;
typedef uint16_t SigningKeyType; typedef uint16_t SigningKeyType;
typedef uint16_t CryptoKeyType; typedef uint16_t CryptoKeyType;
@ -132,7 +135,7 @@ namespace data
IdentHash m_IdentHash; IdentHash m_IdentHash;
std::unique_ptr<i2p::crypto::Verifier> m_Verifier; std::unique_ptr<i2p::crypto::Verifier> m_Verifier;
size_t m_ExtendedLen; size_t m_ExtendedLen;
uint8_t m_ExtendedBuffer[MAX_EXTENDED_BUFFER_SIZE]; uint8_t m_ExtendedBuffer[MAX_EXTENDED_BUFFER_SIZE]; // TODO: support PQ keys
}; };
size_t GetIdentityBufferLen (const uint8_t * buf, size_t len); // return actual identity length in buffer size_t GetIdentityBufferLen (const uint8_t * buf, size_t len); // return actual identity length in buffer

View file

@ -199,6 +199,40 @@ namespace crypto
else else
LogPrint (eLogError, "EdDSA signing key is not set"); LogPrint (eLogError, "EdDSA signing key is not set");
} }
#endif
#if OPENSSL_PQ
MLDSA44Verifier::MLDSA44Verifier ():
m_Pkey (nullptr)
{
}
MLDSA44Verifier::~MLDSA44Verifier ()
{
EVP_PKEY_free (m_Pkey);
}
void MLDSA44Verifier::SetPublicKey (const uint8_t * signingKey)
{
if (m_Pkey) EVP_PKEY_free (m_Pkey);
m_Pkey = EVP_PKEY_new_raw_public_key (EVP_PKEY_ML_DSA_44, NULL, signingKey, GetPublicKeyLen ());
}
bool MLDSA44Verifier::Verify (const uint8_t * buf, size_t len, const uint8_t * signature) const
{
if (m_Pkey)
{
EVP_MD_CTX * ctx = EVP_MD_CTX_create ();
EVP_DigestVerifyInit (ctx, NULL, NULL, NULL, m_Pkey);
auto ret = EVP_DigestVerify (ctx, signature, GetSignatureLen (), buf, len);
EVP_MD_CTX_destroy (ctx);
return ret;
}
else
LogPrint (eLogError, "MLDSA44 verification key is not set");
return false;
}
#endif #endif
} }
} }

View file

@ -560,6 +560,30 @@ namespace crypto
RedDSA25519Signer signer (signingPrivateKey); RedDSA25519Signer signer (signingPrivateKey);
memcpy (signingPublicKey, signer.GetPublicKey (), EDDSA25519_PUBLIC_KEY_LENGTH); memcpy (signingPublicKey, signer.GetPublicKey (), EDDSA25519_PUBLIC_KEY_LENGTH);
} }
#if OPENSSL_PQ
// Post-Quantum
const size_t MLDSA44_PUBLIC_KEY_LENGTH = 1312;
const size_t MLDSA44_SIGNATURE_LENGTH = 2420;
class MLDSA44Verifier: public Verifier
{
public:
MLDSA44Verifier ();
void SetPublicKey (const uint8_t * signingKey);
~MLDSA44Verifier ();
bool Verify (const uint8_t * buf, size_t len, const uint8_t * signature) const;
size_t GetPublicKeyLen () const { return MLDSA44_PUBLIC_KEY_LENGTH; };
size_t GetSignatureLen () const { return MLDSA44_SIGNATURE_LENGTH; };
private:
EVP_PKEY * m_Pkey;
};
#endif
} }
} }