LMS: SHA-256/192 parameters

Add support for parameter sets with SHA-256/192.
This commit is contained in:
Sean Parkinson
2024-09-24 22:06:34 +10:00
parent bc6881974d
commit ae46f52a66
7 changed files with 1285 additions and 385 deletions

View File

@ -1545,6 +1545,12 @@ do
small)
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_WC_LMS_SMALL"
;;
no-sha256-256)
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_NO_LMS_SHA256_256"
;;
sha256-192)
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_LMS_SHA256_192"
;;
*)
AC_MSG_ERROR([Invalid choice for LMS []: $ENABLED_LMS.])
break;;

View File

@ -1692,7 +1692,8 @@ static const char* bench_result_words3[][5] = {
defined(HAVE_CURVE448) || defined(HAVE_ED448) || \
defined(HAVE_ECC) || !defined(NO_DH) || \
!defined(NO_RSA) || defined(HAVE_SCRYPT) || \
defined(WOLFSSL_HAVE_KYBER) || defined(HAVE_DILITHIUM)
defined(WOLFSSL_HAVE_KYBER) || defined(HAVE_DILITHIUM) || \
defined(WOLFSSL_HAVE_LMS)
#define BENCH_ASYM
#endif
@ -1700,7 +1701,8 @@ static const char* bench_result_words3[][5] = {
#if defined(HAVE_ECC) || !defined(NO_RSA) || !defined(NO_DH) || \
defined(HAVE_CURVE25519) || defined(HAVE_ED25519) || \
defined(HAVE_CURVE448) || defined(HAVE_ED448) || \
defined(WOLFSSL_HAVE_KYBER) || defined(HAVE_DILITHIUM)
defined(WOLFSSL_HAVE_KYBER) || defined(HAVE_DILITHIUM) || \
defined(WOLFSSL_HAVE_LMS)
static const char* bench_result_words2[][5] = {
#ifdef BENCH_MICROSECOND
{ "ops took", "μsec" , "avg" , "ops/μsec", NULL }, /* 0 English
@ -2656,7 +2658,8 @@ static void bench_stats_sym_finish(const char* desc, int useDeviceID,
#if defined(HAVE_ECC) || !defined(NO_RSA) || !defined(NO_DH) || \
defined(HAVE_CURVE25519) || defined(HAVE_ED25519) || \
defined(HAVE_CURVE448) || defined(HAVE_ED448) || \
defined(WOLFSSL_HAVE_KYBER) || defined(HAVE_DILITHIUM)
defined(WOLFSSL_HAVE_KYBER) || defined(HAVE_DILITHIUM) || \
defined(WOLFSSL_HAVE_LMS)
static void bench_stats_asym_finish_ex(const char* algo, int strength,
const char* desc, const char* desc_extra, int useDeviceID, int count,
double start, int ret)
@ -9442,6 +9445,7 @@ void bench_kyber(int type)
#endif
#if defined(WOLFSSL_HAVE_LMS) && !defined(WOLFSSL_LMS_VERIFY_ONLY)
#ifndef WOLFSSL_NO_LMS_SHA256_256
/* WC_LMS_PARM_L2_H10_W2
* signature length: 9300 */
static const byte lms_priv_L2_H10_W2[64] =
@ -9597,6 +9601,7 @@ static const byte lms_pub_L4_H5_W8[60] =
0x85,0x1A,0x7A,0xD8,0xD5,0x46,0x74,0x3B,
0x74,0x24,0x12,0xC8
};
#endif
static int lms_write_key_mem(const byte* priv, word32 privSz, void* context)
{
@ -9757,6 +9762,7 @@ static void bench_lms_sign_verify(enum wc_LmsParm parm, byte* pub)
}
switch (parm) {
#ifndef WOLFSSL_NO_LMS_SHA256_256
case WC_LMS_PARM_L2_H10_W2:
XMEMCPY(lms_priv, lms_priv_L2_H10_W2, sizeof(lms_priv_L2_H10_W2));
XMEMCPY(key.pub, lms_pub_L2_H10_W2, HSS_MAX_PUBLIC_KEY_LEN);
@ -9817,6 +9823,28 @@ static void bench_lms_sign_verify(enum wc_LmsParm parm, byte* pub)
case WC_LMS_PARM_L4_H5_W4:
case WC_LMS_PARM_L4_H10_W4:
case WC_LMS_PARM_L4_H10_W8:
#endif
#ifdef WOLFSSL_LMS_SHA256_192
case WC_LMS_PARM_SHA256_192_L1_H5_W1:
case WC_LMS_PARM_SHA256_192_L1_H5_W2:
case WC_LMS_PARM_SHA256_192_L1_H5_W4:
case WC_LMS_PARM_SHA256_192_L1_H5_W8:
case WC_LMS_PARM_SHA256_192_L1_H10_W2:
case WC_LMS_PARM_SHA256_192_L1_H10_W4:
case WC_LMS_PARM_SHA256_192_L1_H10_W8:
case WC_LMS_PARM_SHA256_192_L1_H15_W2:
case WC_LMS_PARM_SHA256_192_L1_H15_W4:
case WC_LMS_PARM_SHA256_192_L2_H10_W2:
case WC_LMS_PARM_SHA256_192_L2_H10_W4:
case WC_LMS_PARM_SHA256_192_L2_H10_W8:
case WC_LMS_PARM_SHA256_192_L3_H5_W2:
case WC_LMS_PARM_SHA256_192_L3_H5_W4:
case WC_LMS_PARM_SHA256_192_L3_H5_W8:
case WC_LMS_PARM_SHA256_192_L3_H10_W4:
case WC_LMS_PARM_SHA256_192_L4_H5_W8:
#endif
default:
XMEMCPY(key.pub, pub, HSS_MAX_PUBLIC_KEY_LEN);
break;
@ -9991,6 +10019,7 @@ void bench_lms(void)
{
byte pub[HSS_MAX_PUBLIC_KEY_LEN];
#ifndef WOLFSSL_NO_LMS_SHA256_256
#ifdef BENCH_LMS_SLOW_KEYGEN
#if !defined(WOLFSSL_WC_LMS) || (LMS_MAX_HEIGHT >= 15)
bench_lms_keygen(WC_LMS_PARM_L1_H15_W2, pub);
@ -10036,6 +10065,55 @@ void bench_lms(void)
bench_lms_keygen(WC_LMS_PARM_L1_H5_W1, pub);
bench_lms_sign_verify(WC_LMS_PARM_L1_H5_W1, pub);
#endif
#endif /* !WOLFSSL_NO_LMS_SHA256_256 */
#ifdef WOLFSSL_LMS_SHA256_192
#ifdef BENCH_LMS_SLOW_KEYGEN
#if !defined(WOLFSSL_WC_LMS) || (LMS_MAX_HEIGHT >= 15)
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L1_H15_W2, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L1_H15_W2, pub);
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L1_H15_W4, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L1_H15_W4, pub);
#undef LMS_PARAMS_BENCHED
#define LMS_PARAMS_BENCHED
#endif
#endif
#if !defined(WOLFSSL_WC_LMS) || ((LMS_MAX_LEVELS >= 2) && \
(LMS_MAX_HEIGHT >= 10))
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L2_H10_W2, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L2_H10_W2, pub);
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L2_H10_W4, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L2_H10_W4, pub);
#undef LMS_PARAMS_BENCHED
#define LMS_PARAMS_BENCHED
#ifdef BENCH_LMS_SLOW_KEYGEN
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L2_H10_W8, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L2_H10_W8, pub);
#endif
#endif
#if !defined(WOLFSSL_WC_LMS) || (LMS_MAX_LEVELS >= 3)
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L3_H5_W4, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L3_H5_W4, pub);
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L3_H5_W8, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L3_H5_W8, pub);
#undef LMS_PARAMS_BENCHED
#define LMS_PARAMS_BENCHED
#endif
#if !defined(WOLFSSL_WC_LMS) || ((LMS_MAX_LEVELS >= 3) && \
(LMS_MAX_HEIGHT >= 10))
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L3_H10_W4, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L3_H10_W4, pub);
#endif
#if !defined(WOLFSSL_WC_LMS) || (LMS_MAX_LEVELS >= 4)
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L4_H5_W8, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L4_H5_W8, pub);
#endif
#if defined(WOLFSSL_WC_LMS) && !defined(LMS_PARAMS_BENCHED)
bench_lms_keygen(WC_LMS_PARM_SHA256_192_L1_H5_W1, pub);
bench_lms_sign_verify(WC_LMS_PARM_SHA256_192_L1_H5_W1, pub);
#endif
#endif /* WOLFSSL_LMS_SHA256_192 */
return;
}

View File

@ -42,8 +42,8 @@
*
* @param [in] w Winternitz width.
*/
#define LMS_U(w) \
(8 * WC_SHA256_DIGEST_SIZE / (w))
#define LMS_U(w, hLen) \
(8 * (hLen) / (w))
/* Calculate u. Appendix B. Works for w of 1, 2, 4, or 8.
*
* @param [in] w Winternitz width.
@ -63,17 +63,17 @@
* @param [in] w Winternitz width.
* @param [in] wb Winternitz width length in bits.
*/
#define LMS_P(w, wb) \
(LMS_U(w) + LMS_V(w, wb))
#define LMS_P(w, wb, hLen) \
(LMS_U(w, hLen) + LMS_V(w, wb))
/* Calculate signature length.
*
* @param [in] l Number of levels.
* @param [in] h Height of the trees.
* @param [in] p Number of n-byte string elements in signature for a tree.
*/
#define LMS_PARAMS_SIG_LEN(l, h, p) \
(4 + (l) * (4 + 4 + 4 + WC_SHA256_DIGEST_SIZE * (1 + (p) + (h))) + \
((l) - 1) * LMS_PUBKEY_LEN)
#define LMS_PARAMS_SIG_LEN(l, h, p, hLen) \
(4 + (l) * (4 + 4 + 4 + (hLen) * (1 + (p) + (h))) + \
((l) - 1) * LMS_PUBKEY_LEN(hLen))
#ifndef WOLFSSL_WC_LMS_SMALL
/* Root levels and leaf cache bits. */
@ -94,9 +94,10 @@
* @param [in] t LMS type.
* @param [in] t2 LM-OTS type.
*/
#define LMS_PARAMS(l, h, w, wb, t, t2) \
{ l, h, w, LMS_LS(w, wb), LMS_P(w, wb), t, t2, \
LMS_PARAMS_SIG_LEN(l, h, LMS_P(w, wb)), LMS_PARAMS_CACHE(h) }
#define LMS_PARAMS(l, h, w, wb, t, t2, hLen) \
{ l, h, w, LMS_LS(w, wb), LMS_P(w, wb, hLen), t, t2, \
LMS_PARAMS_SIG_LEN(l, h, LMS_P(w, wb, hLen), hLen), \
(hLen), LMS_PARAMS_CACHE(h) }
/* Initialize the working state for LMS operations.
@ -138,112 +139,230 @@ static void wc_lmskey_state_free(LmsState* state)
/* Supported LMS parameters. */
static const wc_LmsParamsMap wc_lms_map[] = {
#ifndef WOLFSSL_NO_LMS_SHA256_256
#if LMS_MAX_HEIGHT >= 15
{ WC_LMS_PARM_NONE , "LMS_NONE" ,
LMS_PARAMS(1, 15, 2, 1, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W2) },
LMS_PARAMS(1, 15, 2, 1, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H15_W2, "LMS/HSS L1_H15_W2",
LMS_PARAMS(1, 15, 2, 1, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W2) },
LMS_PARAMS(1, 15, 2, 1, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H15_W4, "LMS/HSS L1_H15_W4",
LMS_PARAMS(1, 15, 4, 2, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W4) },
LMS_PARAMS(1, 15, 4, 2, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
#endif
#if LMS_MAX_LEVELS >= 2
#if LMS_MAX_HEIGHT >= 10
{ WC_LMS_PARM_L2_H10_W2, "LMS/HSS L2_H10_W2",
LMS_PARAMS(2, 10, 2, 1, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W2) },
LMS_PARAMS(2, 10, 2, 1, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L2_H10_W4, "LMS/HSS L2_H10_W4",
LMS_PARAMS(2, 10, 4, 2, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W4) },
LMS_PARAMS(2, 10, 4, 2, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L2_H10_W8, "LMS/HSS L2_H10_W8",
LMS_PARAMS(2, 10, 8, 3, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W8) },
LMS_PARAMS(2, 10, 8, 3, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
#endif
#if LMS_MAX_LEVELS >= 3
{ WC_LMS_PARM_L3_H5_W2 , "LMS/HSS L3_H5_W2" ,
LMS_PARAMS(3, 5, 2, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W2) },
LMS_PARAMS(3, 5, 2, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L3_H5_W4 , "LMS/HSS L3_H5_W4" ,
LMS_PARAMS(3, 5, 4, 2, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W4) },
LMS_PARAMS(3, 5, 4, 2, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L3_H5_W8 , "LMS/HSS L3_H5_W8" ,
LMS_PARAMS(3, 5, 8, 3, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W8) },
LMS_PARAMS(3, 5, 8, 3, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#if LMS_MAX_HEIGHT >= 10
{ WC_LMS_PARM_L3_H10_W4, "LMS/HSS L3_H10_W4",
LMS_PARAMS(3, 10, 4, 2, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W4) },
LMS_PARAMS(3, 10, 4, 2, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
#endif
#endif
#if LMS_MAX_LEVELS >= 4
{ WC_LMS_PARM_L4_H5_W8 , "LMS/HSS L4_H5_W8" ,
LMS_PARAMS(4, 5, 8, 3, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W8) },
LMS_PARAMS(4, 5, 8, 3, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
/* For when user sets L, H, W explicitly. */
{ WC_LMS_PARM_L1_H5_W1 , "LMS/HSS_L1_H5_W1" ,
LMS_PARAMS(1, 5, 1, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W1) },
LMS_PARAMS(1, 5, 1, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W1,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H5_W2 , "LMS/HSS_L1_H5_W2" ,
LMS_PARAMS(1, 5, 2, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W2) },
LMS_PARAMS(1, 5, 2, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H5_W4 , "LMS/HSS_L1_H5_W4" ,
LMS_PARAMS(1, 5, 4, 2, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W4) },
LMS_PARAMS(1, 5, 4, 2, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H5_W8 , "LMS/HSS_L1_H5_W8" ,
LMS_PARAMS(1, 5, 8, 3, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W8) },
LMS_PARAMS(1, 5, 8, 3, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#if LMS_MAX_HEIGHT >= 10
{ WC_LMS_PARM_L1_H10_W2 , "LMS/HSS_L1_H10_W2",
LMS_PARAMS(1, 10, 2, 1, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W2) },
LMS_PARAMS(1, 10, 2, 1, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H10_W4 , "LMS/HSS_L1_H10_W4",
LMS_PARAMS(1, 10, 4, 2, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W4) },
LMS_PARAMS(1, 10, 4, 2, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H10_W8 , "LMS/HSS_L1_H10_W8",
LMS_PARAMS(1, 10, 8, 3, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W8) },
LMS_PARAMS(1, 10, 8, 3, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
#if LMS_MAX_HEIGHT >= 15
{ WC_LMS_PARM_L1_H15_W8 , "LMS/HSS L1_H15_W8",
LMS_PARAMS(1, 15, 8, 3, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W8) },
LMS_PARAMS(1, 15, 8, 3, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
#if LMS_MAX_HEIGHT >= 20
{ WC_LMS_PARM_L1_H20_W2 , "LMS/HSS_L1_H20_W2",
LMS_PARAMS(1, 20, 2, 1, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W2) },
LMS_PARAMS(1, 20, 2, 1, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H20_W4 , "LMS/HSS_L1_H20_W4",
LMS_PARAMS(1, 20, 4, 2, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W4) },
LMS_PARAMS(1, 20, 4, 2, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H20_W8 , "LMS/HSS_L1_H20_W8",
LMS_PARAMS(1, 20, 8, 3, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W8) },
LMS_PARAMS(1, 20, 8, 3, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
#if LMS_MAX_LEVELS >= 2
{ WC_LMS_PARM_L2_H5_W2 , "LMS/HSS_L2_H5_W2" ,
LMS_PARAMS(2, 5, 2, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W2) },
LMS_PARAMS(2, 5, 2, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L2_H5_W4 , "LMS/HSS_L2_H5_W4" ,
LMS_PARAMS(2, 5, 4, 2, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W4) },
LMS_PARAMS(2, 5, 4, 2, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L2_H5_W8 , "LMS/HSS_L2_H5_W8" ,
LMS_PARAMS(2, 5, 8, 3, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W8) },
LMS_PARAMS(2, 5, 8, 3, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#if LMS_MAX_HEIGHT >= 15
{ WC_LMS_PARM_L2_H15_W2 , "LMS/HSS_L2_H15_W2",
LMS_PARAMS(2, 15, 2, 1, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W2) },
LMS_PARAMS(2, 15, 2, 1, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L2_H15_W4 , "LMS/HSS_L2_H15_W4",
LMS_PARAMS(2, 15, 4, 2, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W4) },
LMS_PARAMS(2, 15, 4, 2, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L2_H15_W8 , "LMS/HSS_L2_H15_W8",
LMS_PARAMS(2, 15, 8, 3, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W8) },
LMS_PARAMS(2, 15, 8, 3, LMS_SHA256_M32_H15, LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
#if LMS_MAX_HEIGHT >= 20
{ WC_LMS_PARM_L2_H20_W2 , "LMS/HSS_L2_H20_W2",
LMS_PARAMS(2, 20, 2, 1, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W2) },
LMS_PARAMS(2, 20, 2, 1, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L2_H20_W4 , "LMS/HSS_L2_H20_W4",
LMS_PARAMS(2, 20, 4, 2, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W4) },
LMS_PARAMS(2, 20, 4, 2, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L2_H20_W8 , "LMS/HSS_L2_H20_W8",
LMS_PARAMS(2, 20, 8, 3, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W8) },
LMS_PARAMS(2, 20, 8, 3, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
#endif
#if LMS_MAX_LEVELS >= 3
#if LMS_MAX_HEIGHT >= 10
{ WC_LMS_PARM_L3_H10_W8 , "LMS/HSS L3_H10_W8",
LMS_PARAMS(3, 10, 8, 3, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W8) },
LMS_PARAMS(3, 10, 8, 3, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
#endif
#if LMS_MAX_LEVELS >= 4
{ WC_LMS_PARM_L4_H5_W2 , "LMS/HSS L4_H5_W2" ,
LMS_PARAMS(4, 5, 2, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W2) },
LMS_PARAMS(4, 5, 2, 1, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W2,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L4_H5_W4 , "LMS/HSS L4_H5_W4" ,
LMS_PARAMS(4, 5, 4, 2, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W4) },
LMS_PARAMS(4, 5, 4, 2, LMS_SHA256_M32_H5 , LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
#if LMS_MAX_HEIGHT >= 10
{ WC_LMS_PARM_L4_H10_W4 , "LMS/HSS L4_H10_W4",
LMS_PARAMS(4, 10, 4, 2, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W4) },
LMS_PARAMS(4, 10, 4, 2, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W4,
WC_SHA256_DIGEST_SIZE) },
{ WC_LMS_PARM_L4_H10_W8 , "LMS/HSS L4_H10_W8",
LMS_PARAMS(4, 10, 8, 3, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W8) },
LMS_PARAMS(4, 10, 8, 3, LMS_SHA256_M32_H10, LMOTS_SHA256_N32_W8,
WC_SHA256_DIGEST_SIZE) },
#endif
#endif
#endif /* !WOLFSSL_NO_LMS_SHA256_256 */
#ifdef WOLFSSL_LMS_SHA256_192
#if LMS_MAX_HEIGHT >= 15
{ WC_LMS_PARM_SHA256_192_L1_H15_W2, "LMS/HSS_SHA256/192 L1_H15_W2",
LMS_PARAMS(1, 15, 2, 1, LMS_SHA256_M24_H15, LMOTS_SHA256_N24_W2,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L1_H15_W4, "LMS/HSS_SHA256/192 L1_H15_W4",
LMS_PARAMS(1, 15, 4, 2, LMS_SHA256_M24_H15, LMOTS_SHA256_N24_W4,
WC_SHA256_192_DIGEST_SIZE) },
#endif
#if LMS_MAX_LEVELS >= 2
#if LMS_MAX_HEIGHT >= 10
{ WC_LMS_PARM_SHA256_192_L2_H10_W2, "LMS/HSS SHA256/192 L2_H10_W2",
LMS_PARAMS(2, 10, 2, 1, LMS_SHA256_M24_H10, LMOTS_SHA256_N24_W2,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L2_H10_W4, "LMS/HSS SHA256/192 L2_H10_W4",
LMS_PARAMS(2, 10, 4, 2, LMS_SHA256_M24_H10, LMOTS_SHA256_N24_W4,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L2_H10_W8, "LMS/HSS SHA256/192 L2_H10_W8",
LMS_PARAMS(2, 10, 8, 3, LMS_SHA256_M24_H10, LMOTS_SHA256_N24_W8,
WC_SHA256_192_DIGEST_SIZE) },
#endif
#endif
#if LMS_MAX_LEVELS >= 3
{ WC_LMS_PARM_SHA256_192_L3_H5_W2 , "LMS/HSS_SHA256/192 L3_H5_W2" ,
LMS_PARAMS(3, 5, 2, 1, LMS_SHA256_M24_H5 , LMOTS_SHA256_N24_W2,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L3_H5_W4 , "LMS/HSS_SHA256/192 L3_H5_W4" ,
LMS_PARAMS(3, 5, 4, 2, LMS_SHA256_M24_H5 , LMOTS_SHA256_N24_W4,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L3_H5_W8 , "LMS/HSS_SHA256/192 L3_H5_W8" ,
LMS_PARAMS(3, 5, 8, 3, LMS_SHA256_M24_H5 , LMOTS_SHA256_N24_W8,
WC_SHA256_192_DIGEST_SIZE) },
#if LMS_MAX_HEIGHT >= 10
{ WC_LMS_PARM_SHA256_192_L3_H10_W4, "LMS/HSS_SHA256/192 L3_H10_W4",
LMS_PARAMS(3, 10, 4, 2, LMS_SHA256_M24_H10, LMOTS_SHA256_N24_W4,
WC_SHA256_192_DIGEST_SIZE) },
#endif
#endif
#if LMS_MAX_LEVELS >= 4
{ WC_LMS_PARM_SHA256_192_L4_H5_W8 , "LMS/HSS_SHA256/192 L4_H5_W8" ,
LMS_PARAMS(4, 5, 8, 3, LMS_SHA256_M24_H5 , LMOTS_SHA256_N24_W8,
WC_SHA256_192_DIGEST_SIZE) },
#endif
{ WC_LMS_PARM_SHA256_192_L1_H5_W1 , "LMS/HSS_SHA256/192_L1_H5_W1" ,
LMS_PARAMS(1, 5, 1, 1, LMS_SHA256_M24_H5 , LMOTS_SHA256_N24_W1,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L1_H5_W2 , "LMS/HSS_SHA256/192_L1_H5_W2" ,
LMS_PARAMS(1, 5, 2, 1, LMS_SHA256_M24_H5 , LMOTS_SHA256_N24_W2,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L1_H5_W4 , "LMS/HSS_SHA256/192_L1_H5_W4" ,
LMS_PARAMS(1, 5, 4, 2, LMS_SHA256_M24_H5 , LMOTS_SHA256_N24_W4,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L1_H5_W8 , "LMS/HSS_SHA256/192_L1_H5_W8" ,
LMS_PARAMS(1, 5, 8, 3, LMS_SHA256_M24_H5 , LMOTS_SHA256_N24_W8,
WC_SHA256_192_DIGEST_SIZE) },
#if LMS_MAX_HEIGHT >= 10
{ WC_LMS_PARM_SHA256_192_L1_H10_W2 , "LMS/HSS_SHA256/192_L1_H10_W2",
LMS_PARAMS(1, 10, 2, 1, LMS_SHA256_M24_H10, LMOTS_SHA256_N24_W2,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L1_H10_W4 , "LMS/HSS_SHA256/192_L1_H10_W4",
LMS_PARAMS(1, 10, 4, 2, LMS_SHA256_M24_H10, LMOTS_SHA256_N24_W4,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_SHA256_192_L1_H10_W8 , "LMS/HSS_SHA256/192_L1_H10_W8",
LMS_PARAMS(1, 10, 8, 3, LMS_SHA256_M24_H10, LMOTS_SHA256_N24_W8,
WC_SHA256_192_DIGEST_SIZE) },
#endif
#if LMS_MAX_HEIGHT >= 20
{ WC_LMS_PARM_L1_H20_W2 , "LMS/HSS_SHA256/192_L1_H20_W2",
LMS_PARAMS(1, 20, 2, 1, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W2,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H20_W4 , "LMS/HSS_SHA256/192_L1_H20_W4",
LMS_PARAMS(1, 20, 4, 2, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W4,
WC_SHA256_192_DIGEST_SIZE) },
{ WC_LMS_PARM_L1_H20_W8 , "LMS/HSS_SHA256/192_L1_H20_W8",
LMS_PARAMS(1, 20, 8, 3, LMS_SHA256_M32_H20, LMOTS_SHA256_N32_W8,
WC_SHA256_192_DIGEST_SIZE) },
#endif
#endif /* WOLFSSL_LMS_SHA256_192 */
};
/* Number of parameter sets supported. */
#define WC_LMS_MAP_LEN ((int)(sizeof(wc_lms_map) / sizeof(*wc_lms_map)))
@ -476,7 +595,7 @@ void wc_LmsKey_Free(LmsKey* key)
ForceZero(key->priv_data, LMS_PRIV_DATA_LEN(params->levels,
params->height, params->p, params->rootLevels,
params->cacheBits));
params->cacheBits, params->hash_len));
XFREE(key->priv_data, key->heap, DYNAMIC_TYPE_LMS);
}
@ -630,8 +749,8 @@ int wc_LmsKey_MakeKey(LmsKey* key, WC_RNG* rng)
/* Allocate memory for the private key data. */
key->priv_data = (byte *)XMALLOC(LMS_PRIV_DATA_LEN(params->levels,
params->height, params->p, params->rootLevels, params->cacheBits),
key->heap, DYNAMIC_TYPE_LMS);
params->height, params->p, params->rootLevels, params->cacheBits,
params->hash_len), key->heap, DYNAMIC_TYPE_LMS);
/* Check pointer is valid. */
if (key->priv_data == NULL) {
ret = MEMORY_E;
@ -669,8 +788,8 @@ int wc_LmsKey_MakeKey(LmsKey* key, WC_RNG* rng)
}
if (ret == 0) {
/* Write private key to storage. */
int rv = key->write_private_key(key->priv_raw, HSS_PRIVATE_KEY_LEN,
key->context);
int rv = key->write_private_key(key->priv_raw,
HSS_PRIVATE_KEY_LEN(key->params->hash_len), key->context);
if (rv != WC_LMS_RC_SAVED_TO_NV_MEMORY) {
ret = IO_FAILED_E;
}
@ -729,8 +848,8 @@ int wc_LmsKey_Reload(LmsKey* key)
/* Allocate memory for the private key data. */
key->priv_data = (byte *)XMALLOC(LMS_PRIV_DATA_LEN(params->levels,
params->height, params->p, params->rootLevels, params->cacheBits),
key->heap, DYNAMIC_TYPE_LMS);
params->height, params->p, params->rootLevels, params->cacheBits,
params->hash_len), key->heap, DYNAMIC_TYPE_LMS);
/* Check pointer is valid. */
if (key->priv_data == NULL) {
ret = MEMORY_E;
@ -738,8 +857,8 @@ int wc_LmsKey_Reload(LmsKey* key)
}
if (ret == 0) {
/* Load private key. */
int rv = key->read_private_key(key->priv_raw, HSS_PRIVATE_KEY_LEN,
key->context);
int rv = key->read_private_key(key->priv_raw,
HSS_PRIVATE_KEY_LEN(key->params->hash_len), key->context);
if (rv != WC_LMS_RC_READ_TO_MEMORY) {
ret = IO_FAILED_E;
}
@ -808,7 +927,7 @@ int wc_LmsKey_GetPrivLen(const LmsKey* key, word32* len)
if (ret == 0) {
/* Return private key length from parameter set. */
*len = HSS_PRIVATE_KEY_LEN;
*len = HSS_PRIVATE_KEY_LEN(key->params->hash_len);
}
return ret;
@ -885,8 +1004,8 @@ int wc_LmsKey_Sign(LmsKey* key, byte* sig, word32* sigSz, const byte* msg,
}
if (ret == 0) {
/* Write private key to storage. */
int rv = key->write_private_key(key->priv_raw, HSS_PRIVATE_KEY_LEN,
key->context);
int rv = key->write_private_key(key->priv_raw,
HSS_PRIVATE_KEY_LEN(key->params->hash_len), key->context);
if (rv != WC_LMS_RC_SAVED_TO_NV_MEMORY) {
ret = IO_FAILED_E;
}
@ -933,7 +1052,7 @@ int wc_LmsKey_GetPubLen(const LmsKey* key, word32* len)
}
if (ret == 0) {
*len = HSS_PUBLIC_KEY_LEN;
*len = HSS_PUBLIC_KEY_LEN(key->params->hash_len);
}
return ret;
@ -996,14 +1115,15 @@ int wc_LmsKey_ExportPubRaw(const LmsKey* key, byte* out, word32* outLen)
ret = BAD_FUNC_ARG;
}
/* Check size of out is sufficient. */
if ((ret == 0) && (*outLen < HSS_PUBLIC_KEY_LEN)) {
if ((ret == 0) &&
(*outLen < (word32)HSS_PUBLIC_KEY_LEN(key->params->hash_len))) {
ret = BUFFER_E;
}
if (ret == 0) {
/* Return encoded public key. */
XMEMCPY(out, key->pub, HSS_PUBLIC_KEY_LEN);
*outLen = HSS_PUBLIC_KEY_LEN;
XMEMCPY(out, key->pub, HSS_PUBLIC_KEY_LEN(key->params->hash_len));
*outLen = HSS_PUBLIC_KEY_LEN(key->params->hash_len);
}
return ret;
@ -1032,7 +1152,8 @@ int wc_LmsKey_ImportPubRaw(LmsKey* key, const byte* in, word32 inLen)
if ((key == NULL) || (in == NULL)) {
ret = BAD_FUNC_ARG;
}
if ((ret == 0) && (inLen != HSS_PUBLIC_KEY_LEN)) {
if ((ret == 0) &&
(inLen != (word32)HSS_PUBLIC_KEY_LEN(key->params->hash_len))) {
/* Something inconsistent. Parameters weren't set, or input
* pub key is wrong.*/
return BUFFER_E;

File diff suppressed because it is too large Load Diff

View File

@ -656,8 +656,8 @@ WOLFSSL_TEST_SUBROUTINE wc_test_ret_t scrypt_test(void);
#endif
#if defined(WOLFSSL_HAVE_LMS)
#if !defined(WOLFSSL_SMALL_STACK)
#if (defined(WOLFSSL_WC_LMS) && (LMS_MAX_HEIGHT >= 10)) || \
defined(HAVE_LIBLMS)
#if (defined(WOLFSSL_WC_LMS) && (LMS_MAX_HEIGHT >= 10) && \
!defined(WOLFSSL_NO_LMS_SHA256_256)) || defined(HAVE_LIBLMS)
WOLFSSL_TEST_SUBROUTINE wc_test_ret_t lms_test_verify_only(void);
#endif
#endif
@ -2192,8 +2192,8 @@ options: [-s max_relative_stack_bytes] [-m max_relative_heap_memory_bytes]\n\
#if defined(WOLFSSL_HAVE_LMS)
#if !defined(WOLFSSL_SMALL_STACK)
#if (defined(WOLFSSL_WC_LMS) && (LMS_MAX_HEIGHT >= 10)) || \
defined(HAVE_LIBLMS)
#if (defined(WOLFSSL_WC_LMS) && (LMS_MAX_HEIGHT >= 10) && \
!defined(WOLFSSL_NO_LMS_SHA256_256)) || defined(HAVE_LIBLMS)
if ( (ret = lms_test_verify_only()) != 0)
TEST_FAIL("LMS Vfy test failed!\n", ret);
else
@ -45960,7 +45960,11 @@ static int lms_read_key_mem(byte * priv, word32 privSz, void *context)
/* LMS signature sizes are a function of their parameters. This
* test has a signature of 8688 bytes. */
#ifndef WOLFSSL_NO_LMS_SHA256_256
#define WC_TEST_LMS_SIG_LEN (8688)
#else
#define WC_TEST_LMS_SIG_LEN (4984)
#endif
WOLFSSL_TEST_SUBROUTINE wc_test_ret_t lms_test(void)
{
@ -46103,8 +46107,8 @@ WOLFSSL_TEST_SUBROUTINE wc_test_ret_t lms_test(void)
#endif /* if defined(WOLFSSL_HAVE_LMS) && !defined(WOLFSSL_LMS_VERIFY_ONLY) */
#if defined(WOLFSSL_HAVE_LMS) && !defined(WOLFSSL_SMALL_STACK)
#if (defined(WOLFSSL_WC_LMS) && (LMS_MAX_HEIGHT >= 10)) || \
defined(HAVE_LIBLMS)
#if (defined(WOLFSSL_WC_LMS) && (LMS_MAX_HEIGHT >= 10) && \
!defined(WOLFSSL_NO_LMS_SHA256_256)) || defined(HAVE_LIBLMS)
/* A simple LMS verify only test.
*

View File

@ -78,6 +78,7 @@ enum wc_LmsRc {
* Not predefining many sets with Winternitz=1, because the signatures
* will be large. */
enum wc_LmsParm {
#ifndef WOLFSSL_NO_LMS_SHA256_256
WC_LMS_PARM_NONE = 0,
WC_LMS_PARM_L1_H5_W1 = 1,
WC_LMS_PARM_L1_H5_W2 = 2,
@ -114,6 +115,27 @@ enum wc_LmsParm {
WC_LMS_PARM_L4_H5_W8 = 33,
WC_LMS_PARM_L4_H10_W4 = 34,
WC_LMS_PARM_L4_H10_W8 = 35,
#endif
#ifdef WOLFSSL_LMS_SHA256_192
WC_LMS_PARM_SHA256_192_L1_H5_W1 = 36,
WC_LMS_PARM_SHA256_192_L1_H5_W2 = 37,
WC_LMS_PARM_SHA256_192_L1_H5_W4 = 38,
WC_LMS_PARM_SHA256_192_L1_H5_W8 = 39,
WC_LMS_PARM_SHA256_192_L1_H10_W2 = 40,
WC_LMS_PARM_SHA256_192_L1_H10_W4 = 41,
WC_LMS_PARM_SHA256_192_L1_H10_W8 = 42,
WC_LMS_PARM_SHA256_192_L1_H15_W2 = 43,
WC_LMS_PARM_SHA256_192_L1_H15_W4 = 44,
WC_LMS_PARM_SHA256_192_L2_H10_W2 = 45,
WC_LMS_PARM_SHA256_192_L2_H10_W4 = 46,
WC_LMS_PARM_SHA256_192_L2_H10_W8 = 47,
WC_LMS_PARM_SHA256_192_L3_H5_W2 = 48,
WC_LMS_PARM_SHA256_192_L3_H5_W4 = 49,
WC_LMS_PARM_SHA256_192_L3_H5_W8 = 50,
WC_LMS_PARM_SHA256_192_L3_H10_W4 = 51,
WC_LMS_PARM_SHA256_192_L4_H5_W8 = 52,
#endif
};
/* enum wc_LmsState is to help track the state of an LMS/HSS Key. */

View File

@ -134,6 +134,9 @@
/* Length of numeric types when encoding. */
#define LMS_TYPE_LEN 4
/* Size of digest output when truncatint SHA-256 to 192 bits. */
#define WC_SHA256_192_DIGEST_SIZE 24
/* Maximum size of a node hash. */
#define LMS_MAX_NODE_LEN WC_SHA256_DIGEST_SIZE
/* Maximum size of SEED (produced by hash). */
@ -142,8 +145,6 @@
* Value of P when N=32 and W=1.
*/
#define LMS_MAX_P 265
/* Length of SEED and I in bytes. */
#define LMS_SEED_I_LEN (LMS_SEED_LEN + LMS_I_LEN)
#ifndef WOLFSSL_LMS_ROOT_LEVELS
@ -192,33 +193,32 @@
(HSS_COMPRESS_PARAM_SET_LEN * HSS_MAX_LEVELS)
/* Private key length for one level. */
#define LMS_PRIV_LEN \
(LMS_Q_LEN + LMS_SEED_LEN + LMS_I_LEN)
#define LMS_PRIV_LEN(hLen) \
(LMS_Q_LEN + (hLen) + LMS_I_LEN)
/* Public key length in signature. */
#define LMS_PUBKEY_LEN \
(LMS_TYPE_LEN + LMS_TYPE_LEN + LMS_I_LEN + LMS_MAX_NODE_LEN)
#define LMS_PUBKEY_LEN(hLen) \
(LMS_TYPE_LEN + LMS_TYPE_LEN + LMS_I_LEN + (hLen))
/* LMS signature data length. */
#define LMS_SIG_LEN(h, p) \
(LMS_Q_LEN + LMS_TYPE_LEN + LMS_MAX_NODE_LEN + (p) * LMS_MAX_NODE_LEN + \
LMS_TYPE_LEN + (h) * LMS_MAX_NODE_LEN)
#define LMS_SIG_LEN(h, p, hLen) \
(LMS_Q_LEN + LMS_TYPE_LEN + (hLen) + (p) * (hLen) + LMS_TYPE_LEN + \
(h) * (hLen))
/* Length of public key. */
#define HSS_PUBLIC_KEY_LEN (LMS_L_LEN + LMS_PUBKEY_LEN)
#define HSS_PUBLIC_KEY_LEN(hLen) (LMS_L_LEN + LMS_PUBKEY_LEN(hLen))
/* Length of private key. */
#define HSS_PRIVATE_KEY_LEN \
(HSS_Q_LEN + HSS_PRIV_KEY_PARAM_SET_LEN + LMS_SEED_LEN + LMS_I_LEN)
#define HSS_PRIVATE_KEY_LEN(hLen) \
(HSS_Q_LEN + HSS_PRIV_KEY_PARAM_SET_LEN + (hLen) + LMS_I_LEN)
/* Maximum public key length - length is constant for all parameters. */
#define HSS_MAX_PRIVATE_KEY_LEN HSS_PRIVATE_KEY_LEN
#define HSS_MAX_PRIVATE_KEY_LEN HSS_PRIVATE_KEY_LEN(LMS_MAX_NODE_LEN)
/* Maximum private key length - length is constant for all parameters. */
#define HSS_MAX_PUBLIC_KEY_LEN HSS_PUBLIC_KEY_LEN
#define HSS_MAX_PUBLIC_KEY_LEN HSS_PUBLIC_KEY_LEN(LMS_MAX_NODE_LEN)
/* Maximum signature length. */
#define HSS_MAX_SIG_LEN \
(LMS_TYPE_LEN + \
LMS_MAX_LEVELS * (LMS_Q_LEN + LMS_TYPE_LEN + LMS_TYPE_LEN + \
LMS_MAX_NODE_LEN * (1 + LMS_MAX_P + LMS_MAX_HEIGHT)) + \
(LMS_MAX_LEVELS - 1) * LMS_PUBKEY_LEN \
)
(LMS_MAX_LEVELS - 1) * LMS_PUBKEY_LEN(LMS_MAX_NODE_LEN))
/* Maximum buffer length required for use when hashing. */
#define LMS_MAX_BUFFER_LEN \
@ -229,20 +229,20 @@
*
* HSSPrivKey.priv
*/
#define LMS_PRIV_KEY_LEN(l) \
((l) * LMS_PRIV_LEN)
#define LMS_PRIV_KEY_LEN(l, hLen) \
((l) * LMS_PRIV_LEN(hLen))
/* Stack of nodes. */
#define LMS_STACK_CACHE_LEN(h) \
(((h) + 1) * LMS_MAX_NODE_LEN)
#define LMS_STACK_CACHE_LEN(h, hLen) \
(((h) + 1) * (hLen))
/* Root cache length. */
#define LMS_ROOT_CACHE_LEN(rl) \
(((1 << (rl)) - 1) * LMS_MAX_NODE_LEN)
#define LMS_ROOT_CACHE_LEN(rl, hLen) \
(((1 << (rl)) - 1) * (hLen))
/* Leaf cache length. */
#define LMS_LEAF_CACHE_LEN(cb) \
((1 << (cb)) * LMS_MAX_NODE_LEN)
#define LMS_LEAF_CACHE_LEN(cb, hLen) \
((1 << (cb)) * (hLen))
/* Length of LMS private key state.
*
@ -252,75 +252,103 @@
* stack.stack + stack.offset +
* cache.leaf + cache.index + cache.offset
*/
#define LMS_PRIV_STATE_LEN(h, rl, cb) \
(((h) * LMS_MAX_NODE_LEN) + \
LMS_STACK_CACHE_LEN(h) + 4 + \
LMS_ROOT_CACHE_LEN(rl) + \
LMS_LEAF_CACHE_LEN(cb) + 4 + 4)
#define LMS_PRIV_STATE_LEN(h, rl, cb, hLen) \
(((h) * (hLen)) + \
LMS_STACK_CACHE_LEN(h, hLen) + 4 + \
LMS_ROOT_CACHE_LEN(rl, hLen) + \
LMS_LEAF_CACHE_LEN(cb, hLen) + 4 + 4)
#ifndef WOLFSSL_WC_LMS_SMALL
/* Private key data state for all levels. */
#define LMS_PRIV_STATE_ALL_LEN(l, h, rl, cb) \
((l) * LMS_PRIV_STATE_LEN(h, rl, cb))
#define LMS_PRIV_STATE_ALL_LEN(l, h, rl, cb, hLen) \
((l) * LMS_PRIV_STATE_LEN(h, rl, cb, hLen))
#else
/* Private key data state for all levels. */
#define LMS_PRIV_STATE_ALL_LEN(l, h, rl, cb) 0
#define LMS_PRIV_STATE_ALL_LEN(l, h, rl, cb, hLen) 0
#endif
#ifndef WOLFSSL_LMS_NO_SIGN_SMOOTHING
/* Extra private key data for smoothing. */
#define LMS_PRIV_SMOOTH_LEN(l, h, rl, cb) \
(LMS_PRIV_KEY_LEN(l) + \
((l) - 1) * LMS_PRIV_STATE_LEN(h, rl, cb))
#define LMS_PRIV_SMOOTH_LEN(l, h, rl, cb, hLen) \
(LMS_PRIV_KEY_LEN(l, hLen) + \
((l) - 1) * LMS_PRIV_STATE_LEN(h, rl, cb, hLen))
#else
/* Extra private key data for smoothing. */
#define LMS_PRIV_SMOOTH_LEN(l, h, rl, cb) 0
#define LMS_PRIV_SMOOTH_LEN(l, h, rl, cb, hLen) 0
#endif
#ifndef WOLFSSL_LMS_NO_SIG_CACHE
#define LMS_PRIV_Y_TREE_LEN(p) \
(LMS_MAX_NODE_LEN + (p) * LMS_MAX_NODE_LEN)
#define LMS_PRIV_Y_TREE_LEN(p, hLen) \
((hLen) + (p) * (hLen))
/* Length of the y data cached in private key data. */
#define LMS_PRIV_Y_LEN(l, p) \
(((l) - 1) * (LMS_MAX_NODE_LEN + (p) * LMS_MAX_NODE_LEN))
#define LMS_PRIV_Y_LEN(l, p, hLen) \
(((l) - 1) * ((hLen) + (p) * (hLen)))
#else
/* Length of the y data cached in private key data. */
#define LMS_PRIV_Y_LEN(l, p) 0
#define LMS_PRIV_Y_LEN(l, p, hLen) 0
#endif
#ifndef WOLFSSL_WC_LMS_SMALL
/* Length of private key data. */
#define LMS_PRIV_DATA_LEN(l, h, p, rl, cb) \
(LMS_PRIV_KEY_LEN(l) + \
LMS_PRIV_STATE_ALL_LEN(l, h, rl, cb) + \
LMS_PRIV_SMOOTH_LEN(l, h, rl, cb) + \
LMS_PRIV_Y_LEN(l, p))
#define LMS_PRIV_DATA_LEN(l, h, p, rl, cb, hLen) \
(LMS_PRIV_KEY_LEN(l, hLen) + \
LMS_PRIV_STATE_ALL_LEN(l, h, rl, cb, hLen) + \
LMS_PRIV_SMOOTH_LEN(l, h, rl, cb, hLen) + \
LMS_PRIV_Y_LEN(l, p, hLen))
#else
#define LMS_PRIV_DATA_LEN(l, h, p, rl, cb) \
LMS_PRIV_KEY_LEN(l)
#define LMS_PRIV_DATA_LEN(l, h, p, rl, cb, hLen) \
LMS_PRIV_KEY_LEN(l, hLen)
#endif
/* Indicates using SHA-256 for hashing. */
#define LMS_SHA256 0x00
/* Indicates using SHA-256/192 for hashing. */
#define LMS_SHA256_192 0x10
/* Mask to get hashing algorithm from type. */
#define LMS_HASH_MASK 0xf0
/* Mask to get height or Winternitz width from type. */
#define LMS_H_W_MASK 0x0f
/* LMS Parameters. */
/* SHA-256 hash, 32-bytes of hash used, tree height of 5. */
#define LMS_SHA256_M32_H5 5
#define LMS_SHA256_M32_H5 0x05
/* SHA-256 hash, 32-bytes of hash used, tree height of 10. */
#define LMS_SHA256_M32_H10 6
#define LMS_SHA256_M32_H10 0x06
/* SHA-256 hash, 32-bytes of hash used, tree height of 15. */
#define LMS_SHA256_M32_H15 7
#define LMS_SHA256_M32_H15 0x07
/* SHA-256 hash, 32-bytes of hash used, tree height of 20. */
#define LMS_SHA256_M32_H20 8
#define LMS_SHA256_M32_H20 0x08
/* SHA-256 hash, 32-bytes of hash used, tree height of 25. */
#define LMS_SHA256_M32_H25 9
#define LMS_SHA256_M32_H25 0x09
/* SHA-256 hash, 32-bytes of hash used, Winternitz width of 1 bit. */
#define LMOTS_SHA256_N32_W1 1
#define LMOTS_SHA256_N32_W1 0x01
/* SHA-256 hash, 32-bytes of hash used, Winternitz width of 2 bits. */
#define LMOTS_SHA256_N32_W2 2
#define LMOTS_SHA256_N32_W2 0x02
/* SHA-256 hash, 32-bytes of hash used, Winternitz width of 4 bits. */
#define LMOTS_SHA256_N32_W4 3
#define LMOTS_SHA256_N32_W4 0x03
/* SHA-256 hash, 32-bytes of hash used, Winternitz width of 8 bits. */
#define LMOTS_SHA256_N32_W8 4
#define LMOTS_SHA256_N32_W8 0x04
/* SHA-256 hash, 32-bytes of hash used, tree height of 5. */
#define LMS_SHA256_M24_H5 (0x05 | LMS_SHA256_192)
/* SHA-256 hash, 32-bytes of hash used, tree height of 10. */
#define LMS_SHA256_M24_H10 (0x06 | LMS_SHA256_192)
/* SHA-256 hash, 32-bytes of hash used, tree height of 15. */
#define LMS_SHA256_M24_H15 (0x07 | LMS_SHA256_192)
/* SHA-256 hash, 32-bytes of hash used, tree height of 20. */
#define LMS_SHA256_M24_H20 (0x08 | LMS_SHA256_192)
/* SHA-256 hash, 32-bytes of hash used, tree height of 25. */
#define LMS_SHA256_M24_H25 (0x09 | LMS_SHA256_192)
/* SHA-256 hash, 32-bytes of hash used, Winternitz width of 1 bit. */
#define LMOTS_SHA256_N24_W1 (0x01 | LMS_SHA256_192)
/* SHA-256 hash, 32-bytes of hash used, Winternitz width of 2 bits. */
#define LMOTS_SHA256_N24_W2 (0x02 | LMS_SHA256_192)
/* SHA-256 hash, 32-bytes of hash used, Winternitz width of 4 bits. */
#define LMOTS_SHA256_N24_W4 (0x03 | LMS_SHA256_192)
/* SHA-256 hash, 32-bytes of hash used, Winternitz width of 8 bits. */
#define LMOTS_SHA256_N24_W8 (0x04 | LMS_SHA256_192)
typedef struct LmsParams {
/* Number of tree levels. */
@ -339,6 +367,8 @@ typedef struct LmsParams {
word16 lmOtsType;
/* Length of LM-OTS signature. */
word16 sig_len;
/* Length of seed. */
word16 hash_len;
#ifndef WOLFSSL_WC_LMS_SMALL
/* Number of root levels of interior nodes to store. */
word8 rootLevels;
@ -426,10 +456,10 @@ typedef struct HssPrivKey {
struct LmsKey {
/* Public key. */
ALIGN16 byte pub[HSS_PUBLIC_KEY_LEN];
ALIGN16 byte pub[HSS_PUBLIC_KEY_LEN(LMS_MAX_NODE_LEN)];
#ifndef WOLFSSL_LMS_VERIFY_ONLY
/* Encoded private key. */
ALIGN16 byte priv_raw[HSS_PRIVATE_KEY_LEN];
ALIGN16 byte priv_raw[HSS_MAX_PRIVATE_KEY_LEN];
/* Packed private key data. */
byte* priv_data;