Skip to content

Commit 3dc9c92

Browse files
committed
Fix LibreSSL ML-KEM indexing and unsupported PQ fallback paths
1 parent 09e8ae3 commit 3dc9c92

3 files changed

Lines changed: 47 additions & 11 deletions

File tree

libi2pd/NTCP2.cpp

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,11 @@ namespace transport
7070
switch (version)
7171
{
7272
case 3:
73+
#if defined(LIBRESSL_VERSION_NUMBER)
74+
m_CryptoType = i2p::data::CRYPTO_KEY_TYPE_ECIES_X25519_AEAD; // ML-KEM-512 is not available on LibreSSL
75+
#else
7376
m_CryptoType = i2p::data::CRYPTO_KEY_TYPE_ECIES_MLKEM512_X25519_AEAD;
77+
#endif
7478
break;
7579
case 4:
7680
m_CryptoType = i2p::data::CRYPTO_KEY_TYPE_ECIES_MLKEM768_X25519_AEAD;
@@ -173,13 +177,22 @@ namespace transport
173177
#if OPENSSL_MLKEM
174178
if (m_CryptoType > i2p::data::CRYPTO_KEY_TYPE_ECIES_X25519_AEAD)
175179
{
176-
uint8_t pub[32];
177-
memcpy (pub, GetPub (), 32);
178-
pub[31] |= 0x80; // set highest bit
179-
encryption.Encrypt (pub, 32, m_IV, m_Buffer); // X
180-
// ML-KEM encap_key
181180
m_PQKeys = i2p::crypto::CreateMLKEMKeys (m_CryptoType);
182-
m_PQKeys->GenerateKeys ();
181+
if (m_PQKeys)
182+
{
183+
m_PQKeys->GenerateKeys ();
184+
uint8_t pub[32];
185+
memcpy (pub, GetPub (), 32);
186+
pub[31] |= 0x80; // set highest bit
187+
encryption.Encrypt (pub, 32, m_IV, m_Buffer); // X
188+
}
189+
else
190+
{
191+
LogPrint (eLogWarning, "NTCP2: ML-KEM type ", (int)m_CryptoType, " is not available, fallback to X25519");
192+
m_CryptoType = i2p::data::CRYPTO_KEY_TYPE_ECIES_X25519_AEAD;
193+
m_IsLongPadding = false;
194+
encryption.Encrypt (GetPub (), 32, m_IV, m_Buffer); // X
195+
}
183196
}
184197
else
185198
encryption.Encrypt (GetPub (), 32, m_IV, m_Buffer); // X
@@ -398,6 +411,11 @@ namespace transport
398411
MixHash (m_Buffer + offset, keyLen + 16);
399412
offset += keyLen + 16;
400413
m_PQKeys = i2p::crypto::CreateMLKEMKeys (m_CryptoType);
414+
if (!m_PQKeys)
415+
{
416+
LogPrint (eLogWarning, "NTCP2: ML-KEM type ", (int)m_CryptoType, " is not available");
417+
return false;
418+
}
401419
m_PQKeys->SetPublicKey (encapsKey.data ());
402420
}
403421
}

libi2pd/PostQuantum.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@ namespace crypto
4545
#if defined(LIBRESSL_VERSION_NUMBER)
4646
constexpr std::array MLKEMS =
4747
{
48+
std::make_tuple ("ML-KEM-512", MLKEM512_KEY_LENGTH, MLKEM512_CIPHER_TEXT_LENGTH),
4849
std::make_tuple ("ML-KEM-768", MLKEM768_KEY_LENGTH, MLKEM768_CIPHER_TEXT_LENGTH),
4950
std::make_tuple ("ML-KEM-1024", MLKEM1024_KEY_LENGTH, MLKEM1024_CIPHER_TEXT_LENGTH)
5051
};
@@ -62,8 +63,8 @@ namespace crypto
6263
#if defined(LIBRESSL_VERSION_NUMBER)
6364
switch (type)
6465
{
65-
case i2p::data::CRYPTO_KEY_TYPE_ECIES_MLKEM768_X25519_AEAD: return 0;
66-
case i2p::data::CRYPTO_KEY_TYPE_ECIES_MLKEM1024_X25519_AEAD: return 1;
66+
case i2p::data::CRYPTO_KEY_TYPE_ECIES_MLKEM768_X25519_AEAD: return 1;
67+
case i2p::data::CRYPTO_KEY_TYPE_ECIES_MLKEM1024_X25519_AEAD: return 2;
6768
default: return -1;
6869
}
6970
#else

libi2pd/SSU2Session.cpp

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -743,9 +743,17 @@ namespace transport
743743
{
744744
i2p::data::CryptoKeyType cryptoType = (i2p::data::CryptoKeyType)(m_Version + 2);
745745
m_PQKeys = i2p::crypto::CreateMLKEMKeys (cryptoType);
746-
m_PQKeys->GenerateKeys ();
747-
offset = m_PQKeys->GetKeyLen () + 16;
748-
payloadSize += offset;
746+
if (m_PQKeys)
747+
{
748+
m_PQKeys->GenerateKeys ();
749+
offset = m_PQKeys->GetKeyLen () + 16;
750+
payloadSize += offset;
751+
}
752+
else
753+
{
754+
LogPrint (eLogWarning, "SSU2: ML-KEM type ", (int)cryptoType, " is not available, fallback to version 2");
755+
m_Version = 2;
756+
}
749757
}
750758
#endif
751759
payload[payloadSize] = eSSU2BlkDateTime;
@@ -915,6 +923,11 @@ namespace transport
915923
m_NoiseState->MixHash (buf + offset, keyLen + 16);
916924
offset += keyLen + 16;
917925
m_PQKeys = i2p::crypto::CreateMLKEMKeys (cryptoType);
926+
if (!m_PQKeys)
927+
{
928+
LogPrint (eLogWarning, "SSU2: ML-KEM type ", (int)cryptoType, " is not available");
929+
return false;
930+
}
918931
m_PQKeys->SetPublicKey (encapsKey.data ());
919932
}
920933
#endif
@@ -3460,7 +3473,11 @@ namespace transport
34603473
switch (version)
34613474
{
34623475
case 3:
3476+
#if defined(LIBRESSL_VERSION_NUMBER)
3477+
m_Version = 2; // ML-KEM-512 is not available on LibreSSL
3478+
#else
34633479
m_Version = 3;
3480+
#endif
34643481
break;
34653482
case 4:
34663483
m_Version = (m_MaxPayloadSize >= SSU2_MLKEM768_MIN_PAYLOAD_SIZE) ? 4: 2;

0 commit comments

Comments
 (0)