From 1fb4d7dc6e99d225159ca3dbf7f56b2ff5d20a85 Mon Sep 17 00:00:00 2001 From: John Safranek Date: Mon, 22 Jul 2024 18:22:47 -0700 Subject: [PATCH] Use wolfCrypt SSHv2 KDF 1. Switching to use the new SSH-KDF function in wolfCrypt. 2. Add check in configure for wc_SSH_KDF and set a flag if present. Note: This only works in FIPS builds when Kyber isn't used. --- src/internal.c | 30 +++++++++++++++++++++++++++++- wolfssh/error.h | 3 ++- wolfssh/internal.h | 1 + 3 files changed, 32 insertions(+), 2 deletions(-) diff --git a/src/internal.c b/src/internal.c index cf1f2f6e0..c4c69985a 100644 --- a/src/internal.c +++ b/src/internal.c @@ -47,6 +47,7 @@ #include #include #include +#include #ifdef WOLFSSH_HAVE_LIBOQS #include @@ -453,6 +454,9 @@ const char* GetErrorString(int err) case WS_AUTH_PENDING: return "userauth is still pending (callback would block)"; + case WS_KDF_E: + return "KDF error"; + default: return "Unknown error code"; } @@ -2158,6 +2162,28 @@ int GenerateKey(byte hashId, byte keyId, const byte* h, word32 hSz, const byte* sessionId, word32 sessionIdSz, byte doKeyPad) +#if (LIBWOLFSSL_VERSION_HEX >= WOLFSSL_V5_7_2) && defined(HAVE_FIPS) +/* Cannot use the SSH KDF with Kyber. With Kyber, doKeyPad must be false, + * and the FIPS SSH KDF doesn't know how to do that. On top of that, the + * Kyber algorithm isn't in our FIPS boundary at the moment. */ +{ + int ret = WS_SUCCESS; + + if (!doKeyPad) { + WLOG(WS_LOG_ERROR, "cannot use FIPS KDF with Kyber"); + ret = WS_INVALID_ALGO_ID; + } + else { + ret = wc_SSH_KDF(hashId, keyId, key, keySz, + k, kSz, h, hSz, sessionId, sessionIdSz); + if (ret != 0) { + WLOG(WS_LOG_ERROR, "SSH KDF failed (%d)", ret); + ret = WS_KDF_E; + } + } + return ret; +} +#else { word32 blocks, remainder; wc_HashAlg hash; @@ -2168,12 +2194,13 @@ int GenerateKey(byte hashId, byte keyId, int digestSz; int ret; + WLOG(WS_LOG_DEBUG, "Entering GenerateKey()"); + if (key == NULL || keySz == 0 || k == NULL || kSz == 0 || h == NULL || hSz == 0 || sessionId == NULL || sessionIdSz == 0) { - WLOG(WS_LOG_DEBUG, "GK: bad argument"); return WS_BAD_ARGUMENT; } @@ -2268,6 +2295,7 @@ int GenerateKey(byte hashId, byte keyId, return ret; } +#endif /* HAVE_FIPS && LIBWOLFSSL_VERSION_HEX >= WOLFSSL_V5_7_2 */ static int GenerateKeys(WOLFSSH* ssh, byte hashId, byte doKeyPad) diff --git a/wolfssh/error.h b/wolfssh/error.h index 9d3832fa3..d41f840b8 100644 --- a/wolfssh/error.h +++ b/wolfssh/error.h @@ -135,8 +135,9 @@ enum WS_ErrorCodes { WS_MSGID_NOT_ALLOWED_E = -1094, /* Message not allowed before userauth */ WS_ED25519_E = -1095, /* Ed25519 failure */ WS_AUTH_PENDING = -1096, /* User authentication still pending */ + WS_KDF_E = -1097, /* KDF error*/ - WS_LAST_E = -1096 /* Update this to indicate last error */ + WS_LAST_E = -1097 /* Update this to indicate last error */ }; diff --git a/wolfssh/internal.h b/wolfssh/internal.h index 286acaf9d..7e891eba0 100644 --- a/wolfssh/internal.h +++ b/wolfssh/internal.h @@ -1347,6 +1347,7 @@ enum TerminalModes { #define WOLFSSL_V5_7_0 0x05007000 +#define WOLFSSL_V5_7_2 0x05007002 #ifdef __cplusplus