From cb3fa8ff9e57627c1dd3af706536968fd430f9e4 Mon Sep 17 00:00:00 2001 From: Hideki Miyazaki Date: Sat, 23 Jan 2021 08:56:17 +0900 Subject: [PATCH] SHA224 implementation --- src/ssl.c | 47 ++++++++++++++++++++++++++++++++++++++ tests/api.c | 24 +++++++++++++++++++ wolfssl/openssl/sha.h | 5 ++++ wolfssl/ssl.h | 1 + wolfssl/wolfcrypt/sha256.h | 5 +++- 5 files changed, 81 insertions(+), 1 deletion(-) diff --git a/src/ssl.c b/src/ssl.c index bff47af33..25bdd76f6 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -42931,6 +42931,53 @@ err: } #endif /* ! NO_SHA */ +#ifdef WOLFSSL_SHA224 + /* One shot SHA224 hash of message. + * + * d message to hash + * n size of d buffer + * md buffer to hold digest. Should be WC_SHA224_DIGEST_SIZE. + * + * Note: if md is null then a static buffer of WC_SHA256_DIGEST_SIZE is used. + * When the static buffer is used this function is not thread safe. + * + * Returns a pointer to the message digest on success and NULL on failure. + */ + unsigned char *wolfSSL_SHA224(const unsigned char *d, size_t n, + unsigned char *md) + { + static byte dig[WC_SHA224_DIGEST_SIZE]; + byte* ret = md; + wc_Sha256 sha; + + WOLFSSL_ENTER("wolfSSL_SHA224"); + + if (wc_InitSha224_ex(&sha, NULL, 0) != 0) { + WOLFSSL_MSG("SHA224 Init failed"); + return NULL; + } + + if (wc_Sha224Update(&sha, (const byte*)d, (word32)n) != 0) { + WOLFSSL_MSG("SHA224 Update failed"); + return NULL; + } + + if (md == NULL) { + WOLFSSL_MSG("STATIC BUFFER BEING USED. wolfSSL_SHA224 IS NOT " + "THREAD SAFE WHEN md == NULL"); + ret = dig; + } + if (wc_Sha224Final(&sha, ret) != 0) { + WOLFSSL_MSG("SHA224 Final failed"); + wc_Sha224Free(&sha); + return NULL; + } + wc_Sha224Free(&sha); + + return ret; + } +#endif + #ifndef NO_SHA256 /* One shot SHA256 hash of message. * diff --git a/tests/api.c b/tests/api.c index 3ef4d884c..79b1c7781 100644 --- a/tests/api.c +++ b/tests/api.c @@ -33003,6 +33003,29 @@ static void test_wolfSSL_AES_ecb_encrypt(void) #endif } +static void test_wolfSSL_SHA224(void) +{ +#if defined(OPENSSL_EXTRA) && defined(WOLFSSL_SHA224) && \ + defined(NO_OLD_SHA_NAMES) && !defined(HAVE_FIPS) && !defined(HAVE_SELFTEST) + unsigned char input[] = + "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq"; + unsigned char output[] = + "\x75\x38\x8b\x16\x51\x27\x76\xcc\x5d\xba\x5d\xa1\xfd\x89\x01" + "\x50\xb0\xc6\x45\x5c\xb4\xf5\x8b\x19\x52\x52\x25\x25"; + size_t inLen; + byte hash[WC_SHA224_DIGEST_SIZE]; + + printf(testingFmt, "wolfSSL_SHA224)"); + inLen = XSTRLEN((char*)input); + + XMEMSET(hash, 0, WC_SHA224_DIGEST_SIZE); + AssertNotNull(SHA224(input, inLen, hash)); + AssertIntEQ(XMEMCMP(hash, output, WC_SHA224_DIGEST_SIZE), 0); + + printf(resultFmt, passed); +#endif +} + static void test_wolfSSL_SHA256(void) { #if defined(OPENSSL_EXTRA) && !defined(NO_SHA256) && \ @@ -40913,6 +40936,7 @@ void ApiTest(void) test_wolfSSL_PEM_write_DHparams(); test_wolfSSL_AES_ecb_encrypt(); test_wolfSSL_SHA256(); + test_wolfSSL_SHA224(); test_wolfSSL_X509_get_serialNumber(); test_wolfSSL_X509_CRL(); test_wolfSSL_d2i_X509_REQ(); diff --git a/wolfssl/openssl/sha.h b/wolfssl/openssl/sha.h index e3a814717..277a70e2c 100644 --- a/wolfssl/openssl/sha.h +++ b/wolfssl/openssl/sha.h @@ -99,6 +99,11 @@ typedef WOLFSSL_SHA224_CTX SHA224_CTX; #define SHA224_Init wolfSSL_SHA224_Init #define SHA224_Update wolfSSL_SHA224_Update #define SHA224_Final wolfSSL_SHA224_Final +#if defined(NO_OLD_SHA_NAMES) && !defined(HAVE_FIPS) && !defined(HAVE_SELFTEST) + /* SHA224 is only available in non-fips mode because of SHA224 enum in FIPS + * build. */ + #define SHA224 wolfSSL_SHA224 +#endif #endif /* WOLFSSL_SHA224 */ diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index f36f38be8..d2bdfcf09 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -3639,6 +3639,7 @@ WOLFSSL_API void* wolfSSL_get_app_data( const WOLFSSL *ssl); WOLFSSL_API int wolfSSL_set_app_data(WOLFSSL *ssl, void *arg); WOLFSSL_API WOLFSSL_ASN1_OBJECT * wolfSSL_X509_NAME_ENTRY_get_object(WOLFSSL_X509_NAME_ENTRY *ne); WOLFSSL_API unsigned char *wolfSSL_SHA1(const unsigned char *d, size_t n, unsigned char *md); +WOLFSSL_API unsigned char *wolfSSL_SHA224(const unsigned char *d, size_t n, unsigned char *md); WOLFSSL_API unsigned char *wolfSSL_SHA256(const unsigned char *d, size_t n, unsigned char *md); WOLFSSL_API unsigned char *wolfSSL_SHA384(const unsigned char *d, size_t n, unsigned char *md); WOLFSSL_API unsigned char *wolfSSL_SHA512(const unsigned char *d, size_t n, unsigned char *md); diff --git a/wolfssl/wolfcrypt/sha256.h b/wolfssl/wolfcrypt/sha256.h index 9538fed7b..2fb267cb0 100644 --- a/wolfssl/wolfcrypt/sha256.h +++ b/wolfssl/wolfcrypt/sha256.h @@ -216,9 +216,12 @@ WOLFSSL_API void wc_Sha256SizeSet(wc_Sha256*, word32); #if !defined(HAVE_FIPS) || \ (defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2)) +#if !defined(NO_OLD_SHA_NAMES) + #define SHA224 WC_SHA224 +#endif + #ifndef NO_OLD_WC_NAMES #define Sha224 wc_Sha224 - #define SHA224 WC_SHA224 #define SHA224_BLOCK_SIZE WC_SHA224_BLOCK_SIZE #define SHA224_DIGEST_SIZE WC_SHA224_DIGEST_SIZE #define SHA224_PAD_SIZE WC_SHA224_PAD_SIZE