Merge pull request #5536 from SparkiDev/sha3_x64

SHA-3 improvements
This commit is contained in:
David Garske 2022-09-02 09:46:14 -07:00 committed by GitHub
commit 4a8a11315b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
19 changed files with 17223 additions and 50 deletions

View File

@ -2605,6 +2605,13 @@ then
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_SHA3_SMALL"
fi
# SHAKE128
AC_ARG_ENABLE([shake128],
[AS_HELP_STRING([--enable-shake128],[Enable wolfSSL SHAKE128 support (default: disabled)])],
[ ENABLED_SHAKE128=$enableval ],
[ ENABLED_SHAKE128=no ]
)
# SHAKE256
AC_ARG_ENABLE([shake256],
[AS_HELP_STRING([--enable-shake256],[Enable wolfSSL SHAKE256 support (default: disabled)])],
@ -4015,6 +4022,10 @@ AS_CASE([$FIPS_VERSION],
AS_IF([test "$ENABLED_WOLFSSH" != "yes" && (test "$FIPS_VERSION" != "v5-dev" || test "$enable_ssh" != "no")],
[enable_ssh="yes"])
# Shake128 is a SHA-3 algorithm not in our FIPS algorithm list
AS_IF([test "$ENABLED_SHAKE128" != "no" && (test "$FIPS_VERSION" != "v5-dev" || test "$enable_shake128" != "yes")],
[ENABLED_SHAKE128=no; AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_NO_SHAKE128"])
# Shake256 is a SHA-3 algorithm not in our FIPS algorithm list
AS_IF([test "$ENABLED_SHAKE256" != "no" && (test "$FIPS_VERSION" != "v5-dev" || test "$enable_shake256" != "yes")],
[ENABLED_SHAKE256=no; AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_NO_SHAKE256"])
@ -4170,6 +4181,21 @@ then
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_SHA3"
fi
# Set SHAKE128 flags
# FIPS does not support SHAKE 128
AS_IF([test "x$ENABLED_FIPS" = "xyes"],[ENABLED_SHAKE128="no"])
if test "$ENABLED_SHAKE128" != "no" && test "$ENABLED_32BIT" = "no"
then
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_SHAKE128"
if test "$ENABLED_SHA3" = "no"
then
AC_MSG_ERROR([Must have SHA-3 enabled: --enable-sha3])
fi
else
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_NO_SHAKE128"
fi
# Set SHAKE256 flags
# FIPS does not support SHAKE 256
AS_IF([test "x$ENABLED_FIPS" = "xyes"],[ENABLED_SHAKE256="no"])
@ -8367,6 +8393,7 @@ echo " * SHA-224: $ENABLED_SHA224"
echo " * SHA-384: $ENABLED_SHA384"
echo " * SHA-512: $ENABLED_SHA512"
echo " * SHA3: $ENABLED_SHA3"
echo " * SHAKE128: $ENABLED_SHAKE128"
echo " * SHAKE256: $ENABLED_SHAKE256"
echo " * BLAKE2: $ENABLED_BLAKE2"
echo " * BLAKE2S: $ENABLED_BLAKE2S"

View File

@ -143,6 +143,30 @@ int wc_Md5Hash(const byte* data, word32 len, byte* hash);
*/
int wc_ShaHash(const byte* data, word32 len, byte* hash);
/*!
\ingroup SHA
\brief Convenience function, handles all the hashing and places the
result into hash.
\return 0 Success
\return <0 Error
\param data the data to hash
\param len the length of data
\param hash Byte array to hold hash value.
_Example_
\code
none
\endcode
\sa wc_InitSha224
\sa wc_Sha224Update
\sa wc_Sha224Final
*/
int wc_Sha224Hash(const byte* data, word32 len, byte* hash);
/*!
\ingroup SHA
@ -174,8 +198,9 @@ int wc_Sha256Hash(const byte* data, word32 len, byte* hash);
\brief Convenience function, handles all the hashing and places the
result into hash.
\return 0 Success
\return <0 Error
\return 0 Returned upon successfully hashing the data
\return Memory_E memory error, unable to allocate memory. This is only
possible with the small stack option enabled.
\param data the data to hash
\param len the length of data
@ -186,11 +211,11 @@ int wc_Sha256Hash(const byte* data, word32 len, byte* hash);
none
\endcode
\sa wc_InitSha224
\sa wc_Sha224Update
\sa wc_Sha224Final
\sa wc_Sha384Hash
\sa wc_Sha384Final
\sa wc_InitSha384
*/
int wc_Sha224Hash(const byte* data, word32 len, byte* hash);
int wc_Sha384Hash(const byte* data, word32 len, byte* hash);
/*!
\ingroup SHA
@ -236,8 +261,136 @@ int wc_Sha512Hash(const byte* data, word32 len, byte* hash);
none
\endcode
\sa wc_Sha384Hash
\sa wc_Sha384Final
\sa wc_InitSha384
\sa wc_InitSha3_224
\sa wc_Sha3_224_Update
\sa wc_Sha3_224_Final
*/
int wc_Sha384Hash(const byte* data, word32 len, byte* hash);
int wc_Sha3_224Hash(const byte* data, word32 len, byte* hash);
/*!
\ingroup SHA
\brief Convenience function, handles all the hashing and places the
result into hash.
\return 0 Returned upon successfully hashing the data
\return Memory_E memory error, unable to allocate memory. This is only
possible with the small stack option enabled.
\param data the data to hash
\param len the length of data
\param hash Byte array to hold hash value.
_Example_
\code
none
\endcode
\sa wc_InitSha3_256
\sa wc_Sha3_256_Update
\sa wc_Sha3_256_Final
*/
int wc_Sha3_256Hash(const byte* data, word32 len, byte* hash);
/*!
\ingroup SHA
\brief Convenience function, handles all the hashing and places the
result into hash.
\return 0 Returned upon successfully hashing the data
\return Memory_E memory error, unable to allocate memory. This is only
possible with the small stack option enabled.
\param data the data to hash
\param len the length of data
\param hash Byte array to hold hash value.
_Example_
\code
none
\endcode
\sa wc_InitSha3_384
\sa wc_Sha3_384_Update
\sa wc_Sha3_384_Final
*/
int wc_Sha3_384Hash(const byte* data, word32 len, byte* hash);
/*!
\ingroup SHA
\brief Convenience function, handles all the hashing and places the
result into hash.
\return 0 Returned upon successfully hashing the inputted data
\return Memory_E memory error, unable to allocate memory. This is only
possible with the small stack option enabled.
\param data the data to hash
\param len the length of data
\param hash Byte array to hold hash value.
_Example_
\code
none
\endcode
\sa wc_InitSha3_512
\sa wc_Sha3_512_Update
\sa wc_Sha3_512_Final
*/
int wc_Sha3_512Hash(const byte* data, word32 len, byte* hash);
/*!
\ingroup SHA
\brief Convenience function, handles all the hashing and places the
result into hash.
\return 0 Returned upon successfully hashing the inputted data
\return Memory_E memory error, unable to allocate memory. This is only
possible with the small stack option enabled.
\param data the data to hash
\param len the length of data
\param hash Byte array to hold hash value.
_Example_
\code
none
\endcode
\sa wc_InitShake128
\sa wc_Shake128_Update
\sa wc_Shake128_Final
*/
int wc_Shake128Hash(const byte* data, word32 len, byte* hash);
/*!
\ingroup SHA
\brief Convenience function, handles all the hashing and places the
result into hash.
\return 0 Returned upon successfully hashing the inputted data
\return Memory_E memory error, unable to allocate memory. This is only
possible with the small stack option enabled.
\param data the data to hash
\param len the length of data
\param hash Byte array to hold hash value.
_Example_
\code
none
\endcode
\sa wc_InitShake256
\sa wc_Shake256_Update
\sa wc_Shake256_Final
*/
int wc_Shake256Hash(const byte* data, word32 len, byte* hash);

File diff suppressed because it is too large Load Diff

View File

@ -134,6 +134,9 @@ endif
if BUILD_SHA3
src_libwolfssl_la_SOURCES += wolfcrypt/src/sha3.c
if BUILD_INTELASM
src_libwolfssl_la_SOURCES += wolfcrypt/src/sha3_asm.S
endif
endif
if BUILD_DH
@ -234,6 +237,9 @@ else
src_libwolfssl_la_SOURCES += wolfcrypt/src/port/arm/armv8-sha3-asm.S
endif
endif
if BUILD_INTELASM
src_libwolfssl_la_SOURCES += wolfcrypt/src/sha3_asm.S
endif
endif
if BUILD_DH
@ -434,6 +440,9 @@ else
src_libwolfssl_la_SOURCES += wolfcrypt/src/port/arm/armv8-sha3-asm.S
endif
endif
if BUILD_INTELASM
src_libwolfssl_la_SOURCES += wolfcrypt/src/sha3_asm.S
endif
endif
endif !BUILD_FIPS_CURRENT

View File

@ -19,6 +19,10 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#ifdef WOLFSSL_USER_SETTINGS
#include "wolfssl/wolfcrypt/settings.h"
#endif
#ifndef HAVE_INTEL_AVX1
#define HAVE_INTEL_AVX1
#endif /* HAVE_INTEL_AVX1 */

View File

@ -19,6 +19,10 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#ifdef WOLFSSL_USER_SETTINGS
#include "wolfssl/wolfcrypt/settings.h"
#endif
#ifndef HAVE_INTEL_AVX1
#define HAVE_INTEL_AVX1
#endif /* HAVE_INTEL_AVX1 */

View File

@ -4864,8 +4864,10 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD* type)
case WC_HASH_TYPE_MD5_SHA:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
default:
@ -5389,8 +5391,10 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD* type)
case WC_HASH_TYPE_MD5_SHA:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
default:
@ -7270,8 +7274,10 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD* type)
case WC_HASH_TYPE_MD5_SHA:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
default:
@ -7381,8 +7387,10 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD* type)
case WC_HASH_TYPE_MD5_SHA:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
default:

View File

@ -19,6 +19,10 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#ifdef WOLFSSL_USER_SETTINGS
#include "wolfssl/wolfcrypt/settings.h"
#endif
#ifndef HAVE_INTEL_AVX1
#define HAVE_INTEL_AVX1
#endif /* HAVE_INTEL_AVX1 */

View File

@ -212,16 +212,14 @@ int wc_HashGetOID(enum wc_HashType hash_type)
oid = SHA3_512h;
#endif
break;
#ifndef WOLFSSL_NO_SHAKE256
#if defined(WOLFSSL_SHA3) && defined(WOLFSSL_SHAKE128)
case WC_HASH_TYPE_SHAKE128:
#if defined(WOLFSSL_SHA3) && defined(WOLFSSL_SHAKE128)
oid = SHAKE128h;
#endif
break;
#endif
#if defined(WOLFSSL_SHA3) && defined(WOLFSSL_SHAKE256)
case WC_HASH_TYPE_SHAKE256:
#if defined(WOLFSSL_SHA3) && defined(WOLFSSL_SHAKE256)
oid = SHAKE256h;
#endif
break;
#endif
@ -398,8 +396,10 @@ int wc_HashGetDigestSize(enum wc_HashType hash_type)
break;
/* Not Supported */
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
case WC_HASH_TYPE_NONE:
@ -509,8 +509,10 @@ int wc_HashGetBlockSize(enum wc_HashType hash_type)
break;
/* Not Supported */
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
case WC_HASH_TYPE_NONE:
@ -625,8 +627,10 @@ int wc_Hash(enum wc_HashType hash_type, const byte* data,
case WC_HASH_TYPE_MD4:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
case WC_HASH_TYPE_NONE:
@ -721,8 +725,10 @@ int wc_HashInit_ex(wc_HashAlg* hash, enum wc_HashType type, void* heap,
case WC_HASH_TYPE_MD4:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
case WC_HASH_TYPE_NONE:
@ -825,8 +831,10 @@ int wc_HashUpdate(wc_HashAlg* hash, enum wc_HashType type, const byte* data,
case WC_HASH_TYPE_MD4:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
case WC_HASH_TYPE_NONE:
@ -920,8 +928,10 @@ int wc_HashFinal(wc_HashAlg* hash, enum wc_HashType type, byte* out)
case WC_HASH_TYPE_MD4:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
case WC_HASH_TYPE_NONE:
@ -1027,8 +1037,10 @@ int wc_HashFree(wc_HashAlg* hash, enum wc_HashType type)
case WC_HASH_TYPE_MD4:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
case WC_HASH_TYPE_NONE:
@ -1101,8 +1113,10 @@ int wc_HashSetFlags(wc_HashAlg* hash, enum wc_HashType type, word32 flags)
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
case WC_HASH_TYPE_NONE:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
default:
@ -1171,8 +1185,10 @@ int wc_HashGetFlags(wc_HashAlg* hash, enum wc_HashType type, word32* flags)
case WC_HASH_TYPE_MD4:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
case WC_HASH_TYPE_NONE:
@ -1664,6 +1680,45 @@ int wc_HashGetFlags(wc_HashAlg* hash, enum wc_HashType type, word32* flags)
}
#endif /* !WOLFSSL_NOSHA3_512 */
#ifdef WOLFSSL_SHAKE128
int wc_Shake128Hash(const byte* data, word32 len, byte* hash,
word32 hashLen)
{
int ret = 0;
#ifdef WOLFSSL_SMALL_STACK
wc_Shake* shake;
#else
wc_Shake shake[1];
#endif
#ifdef WOLFSSL_SMALL_STACK
shake = (wc_Shake*)XMALLOC(sizeof(wc_Shake), NULL,
DYNAMIC_TYPE_TMP_BUFFER);
if (shake == NULL)
return MEMORY_E;
#endif
if ((ret = wc_InitShake128(shake, NULL, INVALID_DEVID)) != 0) {
WOLFSSL_MSG("InitShake128 failed");
}
else {
if ((ret = wc_Shake128_Update(shake, data, len)) != 0) {
WOLFSSL_MSG("Shake128_Update failed");
}
else if ((ret = wc_Shake128_Final(shake, hash, hashLen)) != 0) {
WOLFSSL_MSG("Shake128_Final failed");
}
wc_Shake128_Free(shake);
}
#ifdef WOLFSSL_SMALL_STACK
XFREE(shake, NULL, DYNAMIC_TYPE_TMP_BUFFER);
#endif
return ret;
}
#endif /* WOLFSSL_SHAKE_128 */
#ifdef WOLFSSL_SHAKE256
int wc_Shake256Hash(const byte* data, word32 len, byte* hash,
word32 hashLen)

View File

@ -19,6 +19,10 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#ifdef WOLFSSL_USER_SETTINGS
#include "wolfssl/wolfcrypt/settings.h"
#endif
#ifndef HAVE_INTEL_AVX1
#define HAVE_INTEL_AVX1
#endif /* HAVE_INTEL_AVX1 */

View File

@ -1989,8 +1989,10 @@ int wc_hash2mgf(enum wc_HashType hType)
case WC_HASH_TYPE_SHA3_512:
case WC_HASH_TYPE_BLAKE2B:
case WC_HASH_TYPE_BLAKE2S:
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
case WC_HASH_TYPE_SHAKE128:
#endif
#ifndef WOLFSSL_NO_SHAKE256
case WC_HASH_TYPE_SHAKE256:
#endif
default:

View File

@ -19,6 +19,10 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#ifdef WOLFSSL_USER_SETTINGS
#include "wolfssl/wolfcrypt/settings.h"
#endif
#ifndef HAVE_INTEL_AVX1
#define HAVE_INTEL_AVX1
#endif /* HAVE_INTEL_AVX1 */

View File

@ -52,6 +52,17 @@
#if !defined(WOLFSSL_ARMASM) || !defined(WOLFSSL_ARMASM_CRYPTO_SHA3)
#ifdef USE_INTEL_SPEEDUP
#include <wolfssl/wolfcrypt/cpuid.h>
word32 cpuid_flags;
int cpuid_flags_set = 0;
void (*sha3_block)(word64 *s) = NULL;
void (*sha3_block_n)(word64 *s, const byte* data, word32 n,
word64 c) = NULL;
#endif
#ifdef WOLFSSL_SHA3_SMALL
/* Rotate a 64-bit value left.
*
@ -217,7 +228,10 @@ while (0)
*
* s The state.
*/
static void BlockSha3(word64 *s)
#ifndef USE_INTEL_SPEEDUP
static
#endif
void BlockSha3(word64 *s)
{
byte i, x, y;
word64 t0, t1;
@ -505,7 +519,10 @@ while (0)
*
* s The state.
*/
static void BlockSha3(word64 *s)
#ifndef USE_INTEL_SPEEDUP
static
#endif
void BlockSha3(word64 *s)
{
word64 n[25];
word64 b[5];
@ -593,6 +610,23 @@ static int InitSha3(wc_Sha3* sha3)
sha3->flags = 0;
#endif
#ifdef USE_INTEL_SPEEDUP
if (!cpuid_flags_set) {
cpuid_flags = cpuid_get_flags();
cpuid_flags_set = 1;
if (IS_INTEL_BMI2(cpuid_flags)) {
sha3_block = sha3_block_bmi2;
sha3_block_n = sha3_block_n_bmi2;
}
else if (IS_INTEL_AVX2(cpuid_flags)) {
sha3_block = sha3_block_avx2;
}
else {
sha3_block = BlockSha3;
}
}
#endif
return 0;
}
@ -609,6 +643,7 @@ static int Sha3Update(wc_Sha3* sha3, const byte* data, word32 len, byte p)
word32 i;
byte l;
byte *t;
word32 blocks;
if (sha3->i > 0) {
l = p * 8 - sha3->i;
@ -617,29 +652,48 @@ static int Sha3Update(wc_Sha3* sha3, const byte* data, word32 len, byte p)
}
t = &sha3->t[sha3->i];
for (i = 0; i < l; i++)
for (i = 0; i < l; i++) {
t[i] = data[i];
}
data += i;
len -= i;
sha3->i += (byte) i;
if (sha3->i == p * 8) {
for (i = 0; i < p; i++)
for (i = 0; i < p; i++) {
sha3->s[i] ^= Load64BitBigEndian(sha3->t + 8 * i);
}
#ifdef USE_INTEL_SPEEDUP
(*sha3_block)(sha3->s);
#else
BlockSha3(sha3->s);
#endif
sha3->i = 0;
}
}
while (len >= ((word32)(p * 8))) {
for (i = 0; i < p; i++)
blocks = len / (p * 8);
#ifdef USE_INTEL_SPEEDUP
if ((sha3_block_n != NULL) && (blocks > 0)) {
(*sha3_block_n)(sha3->s, data, blocks, p * 8);
len -= blocks * (p * 8);
data += blocks * (p * 8);
blocks = 0;
}
#endif
for (; blocks > 0; blocks--) {
for (i = 0; i < p; i++) {
sha3->s[i] ^= Load64Unaligned(data + 8 * i);
}
#ifdef USE_INTEL_SPEEDUP
(*sha3_block)(sha3->s);
#else
BlockSha3(sha3->s);
#endif
len -= p * 8;
data += p * 8;
}
for (i = 0; i < len; i++)
sha3->t[i] = data[i];
sha3->i += (byte) i;
XMEMCPY(sha3->t, data, len);
sha3->i += len;
return 0;
}
@ -660,17 +714,21 @@ static int Sha3Final(wc_Sha3* sha3, byte padChar, byte* hash, byte p, word32 l)
sha3->t[rate - 1] = 0x00;
#ifdef WOLFSSL_HASH_FLAGS
if (p == WC_SHA3_256_COUNT && sha3->flags & WC_HASH_SHA3_KECCAK256)
if ((p == WC_SHA3_256_COUNT) && (sha3->flags & WC_HASH_SHA3_KECCAK256))
padChar = 0x01;
#endif
sha3->t[sha3->i ] = padChar;
sha3->t[rate - 1] |= 0x80;
for (i=sha3->i + 1; i < rate - 1; i++)
sha3->t[i] = 0;
for (i = 0; i < p; i++)
XMEMSET(sha3->t + sha3->i + 1, 0, rate - 1 - sha3->i - 1);
for (i = 0; i < p; i++) {
sha3->s[i] ^= Load64BitBigEndian(sha3->t + 8 * i);
}
for (j = 0; l - j >= rate; j += rate) {
#ifdef USE_INTEL_SPEEDUP
(*sha3_block)(sha3->s);
#else
BlockSha3(sha3->s);
#endif
#if defined(BIG_ENDIAN_ORDER)
ByteReverseWords64((word64*)(hash + j), sha3->s, rate);
#else
@ -678,7 +736,11 @@ static int Sha3Final(wc_Sha3* sha3, byte padChar, byte* hash, byte p, word32 l)
#endif
}
if (j != l) {
#ifdef USE_INTEL_SPEEDUP
(*sha3_block)(sha3->s);
#else
BlockSha3(sha3->s);
#endif
#if defined(BIG_ENDIAN_ORDER)
ByteReverseWords64(sha3->s, sha3->s, rate);
#endif
@ -1168,6 +1230,135 @@ int wc_Sha3_GetFlags(wc_Sha3* sha3, word32* flags)
}
#endif
#ifdef WOLFSSL_SHAKE128
/* Initialize the state for a Shake128 hash operation.
*
* shake wc_Shake object holding state.
* heap Heap reference for dynamic memory allocation. (Used in async ops.)
* devId Device identifier for asynchronous operation.
* returns 0 on success.
*/
int wc_InitShake128(wc_Shake* shake, void* heap, int devId)
{
return wc_InitSha3(shake, heap, devId);
}
/* Update the SHAKE128 hash state with message data.
*
* shake wc_Shake object holding state.
* data Message data to be hashed.
* len Length of the message data.
* returns 0 on success.
*/
int wc_Shake128_Update(wc_Shake* shake, const byte* data, word32 len)
{
if (shake == NULL || (data == NULL && len > 0)) {
return BAD_FUNC_ARG;
}
if (data == NULL && len == 0) {
/* valid, but do nothing */
return 0;
}
return Sha3Update(shake, data, len, WC_SHA3_128_COUNT);
}
/* Calculate the SHAKE128 hash based on all the message data seen.
* The state is initialized ready for a new message to hash.
*
* shake wc_Shake object holding state.
* hash Buffer to hold the hash result. Must be at least 64 bytes.
* returns 0 on success.
*/
int wc_Shake128_Final(wc_Shake* shake, byte* hash, word32 hashLen)
{
int ret;
if (shake == NULL || hash == NULL) {
return BAD_FUNC_ARG;
}
ret = Sha3Final(shake, 0x1f, hash, WC_SHA3_128_COUNT, hashLen);
if (ret != 0)
return ret;
return InitSha3(shake); /* reset state */
}
/* Absorb the data for squeezing.
*
* Update and final with data but no output and no reset
*
* shake wc_Shake object holding state.
* data Data to absorb.
* len Length of d to absorb in bytes.
* returns 0 on success.
*/
int wc_Shake128_Absorb(wc_Shake* shake, const byte* data, word32 len)
{
int ret;
byte hash[1];
ret = Sha3Update(shake, data, len, WC_SHA3_128_COUNT);
if (ret == 0) {
ret = Sha3Final(shake, 0x1f, hash, WC_SHA3_128_COUNT, 0);
}
/* No partial data. */
shake->i = 0;
return ret;
}
/* Squeeze the state to produce pseudo-random output.
*
* shake wc_Shake object holding state.
* out Output buffer.
* blockCnt Number of blocks to write.
* returns 0 on success.
*/
int wc_Shake128_SqueezeBlocks(wc_Shake* shake, byte* out, word32 blockCnt)
{
for (; (blockCnt > 0); blockCnt--) {
#ifdef USE_INTEL_SPEEDUP
(*sha3_block)(shake->s);
#else
BlockSha3(shake->s);
#endif
#if defined(BIG_ENDIAN_ORDER)
ByteReverseWords64((word64*)out, shake->s, WC_SHA3_128_COUNT * 8);
#else
XMEMCPY(out, shake->s, WC_SHA3_128_COUNT * 8);
#endif
out += WC_SHA3_128_COUNT * 8;
}
return 0;
}
/* Dispose of any dynamically allocated data from the SHAKE128 operation.
* (Required for async ops.)
*
* shake wc_Shake object holding state.
* returns 0 on success.
*/
void wc_Shake128_Free(wc_Shake* shake)
{
wc_Sha3Free(shake);
}
/* Copy the state of the SHA3-512 operation.
*
* src wc_Shake object holding state top copy.
* dst wc_Shake object to copy into.
* returns 0 on success.
*/
int wc_Shake128_Copy(wc_Shake* src, wc_Shake* dst)
{
return wc_Sha3Copy(src, dst);
}
#endif
#ifdef WOLFSSL_SHAKE256
/* Initialize the state for a Shake256 hash operation.
*
@ -1224,6 +1415,56 @@ int wc_Shake256_Final(wc_Shake* shake, byte* hash, word32 hashLen)
return InitSha3(shake); /* reset state */
}
/* Absorb the data for squeezing.
*
* Update and final with data but no output and no reset
*
* shake wc_Shake object holding state.
* data Data to absorb.
* len Length of d to absorb in bytes.
* returns 0 on success.
*/
int wc_Shake256_Absorb(wc_Shake* shake, const byte* data, word32 len)
{
int ret;
byte hash[1];
ret = Sha3Update(shake, data, len, WC_SHA3_256_COUNT);
if (ret == 0) {
ret = Sha3Final(shake, 0x1f, hash, WC_SHA3_256_COUNT, 0);
}
/* No partial data. */
shake->i = 0;
return ret;
}
/* Squeeze the state to produce pseudo-random output.
*
* shake wc_Shake object holding state.
* out Output buffer.
* blockCnt Number of blocks to write.
* returns 0 on success.
*/
int wc_Shake256_SqueezeBlocks(wc_Shake* shake, byte* out, word32 blockCnt)
{
for (; (blockCnt > 0); blockCnt--) {
#ifdef USE_INTEL_SPEEDUP
(*sha3_block)(shake->s);
#else
BlockSha3(shake->s);
#endif
#if defined(BIG_ENDIAN_ORDER)
ByteReverseWords64((word64*)out, shake->s, WC_SHA3_256_COUNT * 8);
#else
XMEMCPY(out, shake->s, WC_SHA3_256_COUNT * 8);
#endif
out += WC_SHA3_256_COUNT * 8;
}
return 0;
}
/* Dispose of any dynamically allocated data from the SHAKE256 operation.
* (Required for async ops.)
*

14868
wolfcrypt/src/sha3_asm.S Normal file

File diff suppressed because it is too large Load Diff

View File

@ -19,6 +19,10 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#ifdef WOLFSSL_USER_SETTINGS
#include "wolfssl/wolfcrypt/settings.h"
#endif
#ifndef HAVE_INTEL_AVX1
#define HAVE_INTEL_AVX1
#endif /* HAVE_INTEL_AVX1 */

View File

@ -406,6 +406,7 @@ WOLFSSL_TEST_SUBROUTINE int sha256_test(void);
WOLFSSL_TEST_SUBROUTINE int sha512_test(void);
WOLFSSL_TEST_SUBROUTINE int sha384_test(void);
WOLFSSL_TEST_SUBROUTINE int sha3_test(void);
WOLFSSL_TEST_SUBROUTINE int shake128_test(void);
WOLFSSL_TEST_SUBROUTINE int shake256_test(void);
WOLFSSL_TEST_SUBROUTINE int hash_test(void);
WOLFSSL_TEST_SUBROUTINE int hmac_md5_test(void);
@ -920,6 +921,13 @@ options: [-s max_relative_stack_bytes] [-m max_relative_heap_memory_bytes]\n\
TEST_PASS("SHA-3 test passed!\n");
#endif
#ifdef WOLFSSL_SHAKE128
if ( (ret = shake128_test()) != 0)
return err_sys("SHAKE128 test failed!\n", ret);
else
TEST_PASS("SHAKE128 test passed!\n");
#endif
#ifdef WOLFSSL_SHAKE256
if ( (ret = shake256_test()) != 0)
return err_sys("SHAKE256 test failed!\n", ret);
@ -3491,7 +3499,499 @@ WOLFSSL_TEST_SUBROUTINE int sha3_test(void)
}
#endif /* WOLFSSL_SHA3 */
#ifdef WOLFSSL_SHAKE128
static int shake128_absorb_test(wc_Shake* sha)
{
byte hash[WC_SHA3_128_BLOCK_SIZE*2];
testVector a, b, c, d, e;
testVector test_sha[5];
int ret = 0;
int times = sizeof(test_sha) / sizeof(struct testVector), i;
byte large_input[1024];
const char* large_digest =
"\x2b\xd1\x69\x9f\xb3\x75\x40\x74\xb8\xb2\xd2\x0b\x92\x47\x9b\xfe"
"\xc9\x91\x48\xbe\xda\xa4\x09\xd7\x61\x35\x18\x05\x07\x71\xa5\x61"
"\x4d\xc4\x94\xad\xbe\x04\x7d\xad\x95\x2f\xeb\x2c\xc0\x10\x67\x43"
"\x40\xf1\x4a\x58\x1c\x54\xfa\x24\x1c\x1a\x4e\x8d\x9b\xbc\xea\xa7"
"\x32\xf2\x4c\xc7\x86\x05\x36\xdc\xb4\x42\xd8\x35\xd1\xb4\xa2\x79"
"\xa2\xe6\xee\x67\x4f\xbf\x2a\x93\x41\x88\x25\x56\x29\x90\x1a\x06"
"\xba\xfe\x9f\xa6\x1a\x74\xe8\x7e\x85\x4a\xc8\x58\x60\xb1\x7b\x18"
"\xdf\x77\x59\x46\x04\xc1\xff\x4b\x9b\xcb\xad\xfe\x91\x28\xf0\x01"
"\xc1\x33\xd0\x99\x99\x2e\x0c\x86\x84\x67\x4d\x37\xa4\x42\x45\x10"
"\xdc\x8f\xdb\x6f\xa6\x9b\xee\x8a\x60\xa5\x1f\x95\x3f\x8f\xf5\x31"
"\x4b\x1d\x48\x1e\x45\xff\x79\x5c\xbe\x72\xfc\x56\xed\x6d\x1a\x99"
"\x7f\x23\x7c\xd1\xa5\x50\x9e\xb0\x4d\x61\x37\xa5\xcb\x24\x71\x3b"
"\xa3\x60\x51\x2e\x80\x83\x8b\xe0\x55\x50\xa7\x1e\xcc\x9f\xac\x41"
"\x77\x2c\x79\x22\x30\x09\x1b\x1a\x83\x5b\x2c\x48\xdc\x09\x7d\x59"
"\x0d\xf0\x54\x17\xfb\x5e\x38\x68\xde\xdb\xc5\x93\xab\x17\x5f\x4b"
"\x4d\x6d\xf2\xc7\x4e\x15\x1e\x10\x76\xc4\xcb\x87\xd8\xb7\x9d\xa8"
"\xbf\xc5\x2e\x5e\xfc\xd3\x6c\x45\xd4\x5d\x72\x0f\x66\xeb\x67\x86"
"\xfa\x6c\xd6\x80\xa4\x23\xcb\x5d\xed\x3c\xde\xdc\x5b\x3d\xca\x95"
"\x43\x4b\xdc\xe8\x49\xd3\xe1\x01\xd4\xf1\xe4\x47\xcf\x56\xba\x71"
"\xb4\x69\xed\xe7\xdb\x0f\x89\xd6\xbb\xcd\x1a\xff\xb4\xbe\x72\x26"
"\xdc\x76\x79\xb3\x1a\x4b\xe6\x8d\x9b\x8e\xd9\xe9\xe6\xf9\xff\xa5";
a.input = "";
a.output = "\x7f\x9c\x2b\xa4\xe8\x8f\x82\x7d\x61\x60\x45\x50\x76\x05\x85"
"\x3e\xd7\x3b\x80\x93\xf6\xef\xbc\x88\xeb\x1a\x6e\xac\xfa\x66"
"\xef\x26\x3c\xb1\xee\xa9\x88\x00\x4b\x93\x10\x3c\xfb\x0a\xee"
"\xfd\x2a\x68\x6e\x01\xfa\x4a\x58\xe8\xa3\x63\x9c\xa8\xa1\xe3"
"\xf9\xae\x57\xe2\x35\xb8\xcc\x87\x3c\x23\xdc\x62\xb8\xd2\x60"
"\x16\x9a\xfa\x2f\x75\xab\x91\x6a\x58\xd9\x74\x91\x88\x35\xd2"
"\x5e\x6a\x43\x50\x85\xb2\xba\xdf\xd6\xdf\xaa\xc3\x59\xa5\xef"
"\xbb\x7b\xcc\x4b\x59\xd5\x38\xdf\x9a\x04\x30\x2e\x10\xc8\xbc"
"\x1c\xbf\x1a\x0b\x3a\x51\x20\xea\x17\xcd\xa7\xcf\xad\x76\x5f"
"\x56\x23\x47\x4d\x36\x8c\xcc\xa8\xaf\x00\x07\xcd\x9f\x5e\x4c"
"\x84\x9f\x16\x7a\x58\x0b\x14\xaa\xbd\xef\xae\xe7\xee\xf4\x7c"
"\xb0\xfc\xa9";
a.inLen = XSTRLEN(a.input);
a.outLen = WC_SHA3_128_BLOCK_SIZE;
b.input = "abc";
b.output = "\x58\x81\x09\x2d\xd8\x18\xbf\x5c\xf8\xa3\xdd\xb7\x93\xfb\xcb"
"\xa7\x40\x97\xd5\xc5\x26\xa6\xd3\x5f\x97\xb8\x33\x51\x94\x0f"
"\x2c\xc8\x44\xc5\x0a\xf3\x2a\xcd\x3f\x2c\xdd\x06\x65\x68\x70"
"\x6f\x50\x9b\xc1\xbd\xde\x58\x29\x5d\xae\x3f\x89\x1a\x9a\x0f"
"\xca\x57\x83\x78\x9a\x41\xf8\x61\x12\x14\xce\x61\x23\x94\xdf"
"\x28\x6a\x62\xd1\xa2\x25\x2a\xa9\x4d\xb9\xc5\x38\x95\x6c\x71"
"\x7d\xc2\xbe\xd4\xf2\x32\xa0\x29\x4c\x85\x7c\x73\x0a\xa1\x60"
"\x67\xac\x10\x62\xf1\x20\x1f\xb0\xd3\x77\xcf\xb9\xcd\xe4\xc6"
"\x35\x99\xb2\x7f\x34\x62\xbb\xa4\xa0\xed\x29\x6c\x80\x1f\x9f"
"\xf7\xf5\x73\x02\xbb\x30\x76\xee\x14\x5f\x97\xa3\x2a\xe6\x8e"
"\x76\xab\x66\xc4\x8d\x51\x67\x5b\xd4\x9a\xcc\x29\x08\x2f\x56"
"\x47\x58\x4e";
b.inLen = XSTRLEN(b.input);
b.outLen = WC_SHA3_128_BLOCK_SIZE;
c.input = "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq";
c.output = "\x1a\x96\x18\x2b\x50\xfb\x8c\x7e\x74\xe0\xa7\x07\x78\x8f\x55"
"\xe9\x82\x09\xb8\xd9\x1f\xad\xe8\xf3\x2f\x8d\xd5\xcf\xf7\xbf"
"\x21\xf5\x4e\xe5\xf1\x95\x50\x82\x5a\x6e\x07\x00\x30\x51\x9e"
"\x94\x42\x63\xac\x1c\x67\x65\x28\x70\x65\x62\x1f\x9f\xcb\x32"
"\x01\x72\x3e\x32\x23\xb6\x3a\x46\xc2\x93\x8a\xa9\x53\xba\x84"
"\x01\xd0\xea\x77\xb8\xd2\x64\x90\x77\x55\x66\x40\x7b\x95\x67"
"\x3c\x0f\x4c\xc1\xce\x9f\xd9\x66\x14\x8d\x7e\xfd\xff\x26\xbb"
"\xf9\xf4\x8a\x21\xc6\xda\x35\xbf\xaa\x54\x56\x54\xf7\x0a\xe5"
"\x86\xff\x10\x13\x14\x20\x77\x14\x83\xec\x92\xed\xab\x40\x8c"
"\x76\x7b\xf4\xc5\xb4\xff\xfa\xa8\x0c\x8c\xa2\x14\xd8\x4c\x4d"
"\xc7\x00\xd0\xc5\x06\x30\xb2\xff\xc3\x79\x3e\xa4\xd8\x72\x58"
"\xb4\xc9\x54";
c.inLen = XSTRLEN(c.input);
c.outLen = WC_SHA3_128_BLOCK_SIZE;
/* Taken from NIST CAVP test vectors - full rate output. */
d.input = "\xdc\x88\x6d\xf3\xf6\x9c\x49\x51\x3d\xe3\x62\x7e\x94\x81\xdb"
"\x58\x71\xe8\xee\x88\xeb\x9f\x99\x61\x15\x41\x93\x0a\x8b\xc8"
"\x85\xe0";
d.output = "\x93\x68\xf0\x15\x10\x92\x44\xeb\x02\x47\xfa\x3a\x0e\x57\xf5"
"\x2e\xa7\xd9\xeb\xa2\x3d\xae\x7a\x19\x7f\x0a\x29\xe9\x22\x55"
"\x06\x05\x98\x16\xb7\x84\x48\xb6\x49\x7a\x76\xeb\x96\x2d\xb3"
"\xf8\x4d\x37\x60\xf1\xfe\xb4\xbd\xc1\xfd\x4a\xc9\x4e\x91\x7a"
"\xc2\xea\x5e\x4f\x38\x37\x4a\xa5\x6e\x4f\x47\x67\xb8\xd7\x83"
"\x1b\x2d\x51\x49\x5a\xb8\xea\xb7\xc9\x82\x20\xaf\x13\x41\x5a"
"\x59\xbb\x7c\x17\x7a\xcd\x62\x8e\xf0\xff\xe3\x6c\xeb\x18\x59"
"\x5d\x14\x4c\xbf\x25\xef\xc0\x6c\xd9\x56\xa5\x78\x20\x6e\xa8"
"\xf9\x14\x5e\xf9\xce\x19\x50\x6a\x9d\x04\x4e\xc7\x00\x79\x9f"
"\xa1\x41\x9b\xaf\x60\x52\xc0\xc1\xb4\x45\xf8\x35\x17\x57\xb0"
"\xd0\x22\x87\x21\x89\xe2\xc0\x27\x3f\x82\xd9\x69\x69\x66\x3e"
"\x55\x4d\x09";
d.inLen = 32;
d.outLen = WC_SHA3_128_BLOCK_SIZE;
/* Taken from NIST CAVP test vectors - more than one output block. */
e.input = "\x8d\x80\x01\xe2\xc0\x96\xf1\xb8\x8e\x7c\x92\x24\xa0\x86\xef"
"\xd4\x79\x7f\xbf\x74\xa8\x03\x3a\x2d\x42\x2a\x2b\x6b\x8f\x67"
"\x47\xe4";
e.output = "\xe1\x7e\xab\x0d\xa4\x04\xf9\xb6\xac\xc0\x84\x97\x2f\xc5\x79"
"\xe8\x6d\xaa\x76\x10\xa5\xe1\x7c\x23\x2f\x79\x19\x83\x96\xfd"
"\x01\xc2\x4c\x34\xbb\x54\xf4\xb0\x1e\xf7\x40\xb4\x25\x33\x4a"
"\x55\xdd\x24\x81\x3d\xc8\xea\x86\xf5\x6e\xf7\x27\x67\x26\x2b"
"\xf2\x25\x74\x8c\xcc\x3d\x9f\x48\x6f\xfb\x72\x8f\x4e\xad\x29"
"\x60\xc9\x6c\x3e\x44\x63\x86\xea\xce\x21\x9c\x84\x28\x16\x11"
"\x63\x58\xb0\xf4\x2d\x7d\xff\xf7\xdd\x24\x11\xfa\x2a\x56\x79"
"\xfd\x7a\x94\x77\x45\x75\xba\xf9\xfc\xad\x68\xa1\x9e\x30\xd1"
"\x49\xb0\x59\xb5\x9c\x44\x6c\x4e\xdc\xa5\x9b\xc5\xa4\x79\x9d"
"\xc4\x65\xaa\x9e\x78\x2c\xed\x9f\x21\xc5\x5d\xe2\x42\xdd\x25"
"\xd0\xd9\xde\x60\xd0\x9f\xf8\x6a\xba\xf3\xa0\x3a\x76\x71\xb3"
"\x05\x42\xdf\xbe\x72\xfc\x56\xed\x6d\x1a\x99\x7f\x23\x7c\xd1"
"\xa5\x50\x9e\xb0\x4d\x61\x37\xa5\xcb\x24\x71\x3b\xa3\x60\x51"
"\x2e\x80\x83\x8b\xe0\x55\x50\xa7\x1e\xcc\x9f\xac\x41\x77\x2c"
"\x79\x22\x30\x09\x1b\x1a\x83\x5b\x2c\x48\xdc\x09\x7d\x59\x0d"
"\xf0\x54\x17\xfb\x5e\x38\x68\xde\xdb\xc5\x93\xab\x17\x5f\x4b"
"\x4d\x6d\xf2\xc7\x4e\x15\x1e\x10\x76\xc4\xcb\x87\xd8\xb7\x9d"
"\xa8\xbf\xc5\x2e\x5e\xfc\xd3\x6c\x45\xd4\x5d\x72\x0f\x66\xeb"
"\x67\x86\xfa\x6c\xd6\x80\xa4\x23\xcb\x5d\xed\x3c\xde\xdc\x5b"
"\x3d\xca\x95\x43\x4b\xdc\xe8\x49\xd3\xe1\x01\xd4\xf1\xe4\x47"
"\xcf\x56\xba\x71\xb4\x69\xed\xe7\xdb\x0f\x89\xd6\xbb\xcd\x1a"
"\xff\xb4\xbe\x72\x26\xdc\x76\x79\xb3\x1a\x4b\xe6\x8d\x9b\x8e"
"\xd9\xe9\xe6\xf9\xff\xa5";
e.inLen = 32;
e.outLen = 2 * WC_SHA3_128_BLOCK_SIZE;
test_sha[0] = a;
test_sha[1] = b;
test_sha[2] = c;
test_sha[3] = d;
test_sha[4] = e;
for (i = 0; i < times; ++i) {
ret = wc_InitShake128(sha, HEAP_HINT, devId);
if (ret != 0)
ERROR_OUT(-3100 - i, exit);
ret = wc_Shake128_Absorb(sha, (byte*)test_sha[i].input,
(word32)test_sha[i].inLen);
if (ret != 0)
ERROR_OUT(-3101 - i, exit);
ret = wc_Shake128_SqueezeBlocks(sha, hash,
(word32)test_sha[i].outLen / WC_SHA3_128_BLOCK_SIZE);
if (ret != 0)
ERROR_OUT(-3102 - i, exit);
if (XMEMCMP(hash, test_sha[i].output, (word32)test_sha[i].outLen) != 0)
ERROR_OUT(-3103 - i, exit);
}
/* BEGIN LARGE HASH TEST */ {
for (i = 0; i < (int)sizeof(large_input); i++) {
large_input[i] = (byte)(i & 0xFF);
}
ret = wc_InitShake128(sha, HEAP_HINT, devId);
if (ret != 0)
ERROR_OUT(-3104, exit);
/* Absorb is non-incremental. */
ret = wc_Shake128_Absorb(sha, (byte*)large_input,
(word32)sizeof(large_input));
if (ret != 0)
ERROR_OUT(-3105, exit);
/* Able to squeeze out blocks incrementally. */
ret = wc_Shake128_SqueezeBlocks(sha, hash, 1);
if (ret != 0)
ERROR_OUT(-3106, exit);
ret = wc_Shake128_SqueezeBlocks(sha, hash,
((word32)sizeof(hash) / WC_SHA3_128_BLOCK_SIZE) - 1);
if (ret != 0)
ERROR_OUT(-3106, exit);
if (XMEMCMP(hash, large_digest, sizeof(hash)) != 0)
ERROR_OUT(-3107, exit);
} /* END LARGE HASH TEST */
exit:
return ret;
}
WOLFSSL_TEST_SUBROUTINE int shake128_test(void)
{
wc_Shake sha;
byte hash[250];
testVector a, b, c, d, e;
testVector test_sha[5];
int ret = 0;
int times = sizeof(test_sha) / sizeof(struct testVector), i;
byte large_input[1024];
const char* large_digest =
"\x88\xd7\x0e\x86\x46\x72\x6b\x3d\x7d\x22\xe1\xa9\x2d\x02\xdb\x35"
"\x92\x4f\x1b\x03\x90\xee\xa3\xce\xd1\x3a\x08\x3a\xd7\x4e\x10\xdf"
"\x09\x67\x33\x35\x4f\xdd\x38\x50\x5b\xcb\x75\xc7\xba\x65\xe5\xe8"
"\xb8\x76\xde\xc5\xee\xd7\xf1\x65\x93\x4e\x5e\xc4\xb1\xd7\x6b\xee"
"\x4b\x57\x48\xf5\x38\x49\x9e\x45\xa0\xf7\x32\xe9\x05\x26\x6a\x10"
"\x70\xd4\x7c\x19\x01\x1f\x6d\x37\xba\x7b\x74\xc2\xbc\xb6\xbc\x74"
"\xa3\x66\x6c\x9b\x11\x84\x9d\x4a\x36\xbc\x8a\x0d\x4c\xe3\x39\xfa"
"\xfa\x1b";
a.input = "";
a.output = "\x7f\x9c\x2b\xa4\xe8\x8f\x82\x7d\x61\x60\x45\x50\x76\x05\x85"
"\x3e\xd7\x3b\x80\x93\xf6\xef\xbc\x88\xeb\x1a\x6e\xac\xfa\x66"
"\xef\x26\x3c\xb1\xee\xa9\x88\x00\x4b\x93\x10\x3c\xfb\x0a\xee"
"\xfd\x2a\x68\x6e\x01\xfa\x4a\x58\xe8\xa3\x63\x9c\xa8\xa1\xe3"
"\xf9\xae\x57\xe2\x35\xb8\xcc\x87\x3c\x23\xdc\x62\xb8\xd2\x60"
"\x16\x9a\xfa\x2f\x75\xab\x91\x6a\x58\xd9\x74\x91\x88\x35\xd2"
"\x5e\x6a\x43\x50\x85\xb2\xba\xdf\xd6\xdf\xaa\xc3\x59\xa5\xef"
"\xbb\x7b\xcc\x4b\x59\xd5\x38\xdf\x9a";
a.inLen = XSTRLEN(a.input);
a.outLen = 114;
b.input = "abc";
b.output = "\x58\x81\x09\x2d\xd8\x18\xbf\x5c\xf8\xa3\xdd\xb7\x93\xfb\xcb"
"\xa7\x40\x97\xd5\xc5\x26\xa6\xd3\x5f\x97\xb8\x33\x51\x94\x0f"
"\x2c\xc8\x44\xc5\x0a\xf3\x2a\xcd\x3f\x2c\xdd\x06\x65\x68\x70"
"\x6f\x50\x9b\xc1\xbd\xde\x58\x29\x5d\xae\x3f\x89\x1a\x9a\x0f"
"\xca\x57\x83\x78\x9a\x41\xf8\x61\x12\x14\xce\x61\x23\x94\xdf"
"\x28\x6a\x62\xd1\xa2\x25\x2a\xa9\x4d\xb9\xc5\x38\x95\x6c\x71"
"\x7d\xc2\xbe\xd4\xf2\x32\xa0\x29\x4c\x85\x7c\x73\x0a\xa1\x60"
"\x67\xac\x10\x62\xf1\x20\x1f\xb0\xd3";
b.inLen = XSTRLEN(b.input);
b.outLen = 114;
c.input = "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq";
c.output = "\x1a\x96\x18\x2b\x50\xfb\x8c\x7e\x74\xe0\xa7\x07\x78\x8f\x55"
"\xe9\x82\x09\xb8\xd9\x1f\xad\xe8\xf3\x2f\x8d\xd5\xcf\xf7\xbf"
"\x21\xf5\x4e\xe5\xf1\x95\x50\x82\x5a\x6e\x07\x00\x30\x51\x9e"
"\x94\x42\x63\xac\x1c\x67\x65\x28\x70\x65\x62\x1f\x9f\xcb\x32"
"\x01\x72\x3e\x32\x23\xb6\x3a\x46\xc2\x93\x8a\xa9\x53\xba\x84"
"\x01\xd0\xea\x77\xb8\xd2\x64\x90\x77\x55\x66\x40\x7b\x95\x67"
"\x3c\x0f\x4c\xc1\xce\x9f\xd9\x66\x14\x8d\x7e\xfd\xff\x26\xbb"
"\xf9\xf4\x8a\x21\xc6\xda\x35\xbf\xaa";
c.inLen = XSTRLEN(c.input);
c.outLen = 114;
/* Taken from NIST CAVP test vectors - full rate output. */
d.input = "\xdc\x88\x6d\xf3\xf6\x9c\x49\x51\x3d\xe3\x62\x7e\x94\x81\xdb"
"\x58\x71\xe8\xee\x88\xeb\x9f\x99\x61\x15\x41\x93\x0a\x8b\xc8"
"\x85\xe0";
d.output = "\x93\x68\xf0\x15\x10\x92\x44\xeb\x02\x47\xfa\x3a\x0e\x57\xf5"
"\x2e\xa7\xd9\xeb\xa2\x3d\xae\x7a\x19\x7f\x0a\x29\xe9\x22\x55"
"\x06\x05\x98\x16\xb7\x84\x48\xb6\x49\x7a\x76\xeb\x96\x2d\xb3"
"\xf8\x4d\x37\x60\xf1\xfe\xb4\xbd\xc1\xfd\x4a\xc9\x4e\x91\x7a"
"\xc2\xea\x5e\x4f\x38\x37\x4a\xa5\x6e\x4f\x47\x67\xb8\xd7\x83"
"\x1b\x2d\x51\x49\x5a\xb8\xea\xb7\xc9\x82\x20\xaf\x13\x41\x5a"
"\x59\xbb\x7c\x17\x7a\xcd\x62\x8e\xf0\xff\xe3\x6c\xeb\x18\x59"
"\x5d\x14\x4c\xbf\x25\xef\xc0\x6c\xd9\x56\xa5\x78\x20\x6e\xa8"
"\xf9\x14\x5e\xf9\xce\x19\x50\x6a\x9d\x04\x4e\xc7\x00\x79\x9f"
"\xa1";
d.inLen = 32;
d.outLen = 136;
/* Taken from NIST CAVP test vectors - more than one output block. */
e.input = "\x8d\x80\x01\xe2\xc0\x96\xf1\xb8\x8e\x7c\x92\x24\xa0\x86\xef"
"\xd4\x79\x7f\xbf\x74\xa8\x03\x3a\x2d\x42\x2a\x2b\x6b\x8f\x67"
"\x47\xe4";
e.output = "\xe1\x7e\xab\x0d\xa4\x04\xf9\xb6\xac\xc0\x84\x97\x2f\xc5\x79"
"\xe8\x6d\xaa\x76\x10\xa5\xe1\x7c\x23\x2f\x79\x19\x83\x96\xfd"
"\x01\xc2\x4c\x34\xbb\x54\xf4\xb0\x1e\xf7\x40\xb4\x25\x33\x4a"
"\x55\xdd\x24\x81\x3d\xc8\xea\x86\xf5\x6e\xf7\x27\x67\x26\x2b"
"\xf2\x25\x74\x8c\xcc\x3d\x9f\x48\x6f\xfb\x72\x8f\x4e\xad\x29"
"\x60\xc9\x6c\x3e\x44\x63\x86\xea\xce\x21\x9c\x84\x28\x16\x11"
"\x63\x58\xb0\xf4\x2d\x7d\xff\xf7\xdd\x24\x11\xfa\x2a\x56\x79"
"\xfd\x7a\x94\x77\x45\x75\xba\xf9\xfc\xad\x68\xa1\x9e\x30\xd1"
"\x49\xb0\x59\xb5\x9c\x44\x6c\x4e\xdc\xa5\x9b\xc5\xa4\x79\x9d"
"\xc4\x65\xaa\x9e\x78\x2c\xed\x9f\x21\xc5\x5d\xe2\x42\xdd\x25"
"\xd0\xd9\xde\x60\xd0\x9f\xf8\x6a\xba\xf3\xa0\x3a\x76\x71\xb3"
"\x05\x42\xdf\xbe\x72\xfc\x56\xed\x6d\x1a\x99\x7f\x23\x7c\xd1"
"\xa5\x50\x9e\xb0\x4d\x61\x37\xa5\xcb\x24\x71\x3b\xa3\x60\x51"
"\x2e\x80\x83\x8b\xe0\x55\x50\xa7\x1e\xcc\x9f\xac\x41\x77\x2c"
"\x79\x22\x30\x09\x1b\x1a\x83\x5b\x2c\x48\xdc\x09\x7d\x59\x0d"
"\xf0\x54\x17\xfb\x5e\x38\x68\xde\xdb\xc5\x93\xab\x17\x5f\x4b"
"\x4d\x6d\xf2\xc7\x4e\x15\x1e\x10\x76\xc4";
e.inLen = 32;
e.outLen = 250;
test_sha[0] = a;
test_sha[1] = b;
test_sha[2] = c;
test_sha[3] = d;
test_sha[4] = e;
ret = wc_InitShake128(&sha, HEAP_HINT, devId);
if (ret != 0)
return -3100;
for (i = 0; i < times; ++i) {
ret = wc_Shake128_Update(&sha, (byte*)test_sha[i].input,
(word32)test_sha[i].inLen);
if (ret != 0)
ERROR_OUT(-3101 - i, exit);
ret = wc_Shake128_Final(&sha, hash, (word32)test_sha[i].outLen);
if (ret != 0)
ERROR_OUT(-3102 - i, exit);
if (XMEMCMP(hash, test_sha[i].output, test_sha[i].outLen) != 0)
ERROR_OUT(-3103 - i, exit);
}
/* BEGIN LARGE HASH TEST */ {
for (i = 0; i < (int)sizeof(large_input); i++) {
large_input[i] = (byte)(i & 0xFF);
}
times = 100;
for (i = 0; i < times; ++i) {
ret = wc_Shake128_Update(&sha, (byte*)large_input,
(word32)sizeof(large_input));
if (ret != 0)
ERROR_OUT(-3104, exit);
}
ret = wc_Shake128_Final(&sha, hash, (word32)sizeof(hash));
if (ret != 0)
ERROR_OUT(-3105, exit);
if (XMEMCMP(hash, large_digest, 114) != 0)
ERROR_OUT(-3106, exit);
} /* END LARGE HASH TEST */
ret = shake128_absorb_test(&sha);
exit:
wc_Shake128_Free(&sha);
return ret;
}
#endif
#ifdef WOLFSSL_SHAKE256
static int shake256_absorb_test(wc_Shake* sha)
{
byte hash[WC_SHA3_256_BLOCK_SIZE*2];
testVector a, b, c, d, e;
testVector test_sha[5];
int ret = 0;
int times = sizeof(test_sha) / sizeof(struct testVector), i;
byte large_input[1024];
const char* large_digest =
"\x21\x25\x8e\xae\x6e\x4f\xa7\xe1\xb9\x6d\xa7\xc9\x7d\x46\x03\x69"
"\x29\x0d\x81\x49\xba\x5d\xaf\x37\xfd\xeb\x25\x52\x1d\xd9\xbd\x65"
"\xfa\x99\xb9\xd1\x70\x6b\xeb\xd4\xc1\x2c\xea\x24\x20\x27\xa7\xcd"
"\xfa\xe1\x81\xd9\xd5\xc1\x1c\xc7\xe9\x70\xc3\xc7\x21\x6f\x32\x22"
"\xe3\x27\xdb\x58\x5e\xea\x18\x2d\x63\x4d\x14\x6c\x94\xcf\x2b\x7e"
"\x6e\x2a\x74\xf3\xe0\xac\xb3\xb2\xcc\xef\x38\xe9\xe7\x35\xb3\xc5"
"\x77\x9d\xff\xe3\x08\x8e\xf8\x2c\x89\xbb\x45\x22\x16\x99\x91\xc0"
"\xe7\x71\x57\x75\xc5\xb1\xc6\xaf\x27\xcb\x64\x8c\xc4\xee\x3d\x5f"
"\x4c\x35\xfb\x1c\xf3\xf8\x0e\xfd\x5e\xfc\x07\xd8\x4d\x55\x32\x49"
"\x45\x0d\xab\x4a\x49\xc4\x83\xde\xd2\x50\xc9\x33\x8f\x85\xcd\x93"
"\x7a\xe6\x6b\xb4\x36\xf3\xb4\x02\x6e\x85\x9f\xda\x1c\xa5\x71\x43"
"\x2f\x3b\xfc\x09\xe7\xc0\x3c\xa4\xd1\x83\xb7\x41\x11\x1c\xa0\x48"
"\x3d\x0e\xda\xbc\x03\xfe\xb2\x3b\x17\xee\x48\xe8\x44\xba\x24\x08"
"\xd9\xdc\xfd\x01\x39\xd2\xe8\xc7\x31\x01\x25\xae\xe8\x01\xc6\x1a"
"\xb7\x90\x0d\x1e\xfc\x47\xc0\x78\x28\x17\x66\xf3\x61\xc5\xe6\x11"
"\x13\x46\x23\x5e\x1d\xc3\x83\x25\x66\x6c\x68\x1b\x30\xdd\xc4\xe6"
"\x83\x8b\x0f\x23\x58\x7e\x06\x5f\x4a\x2b\xed\xc9\x6c\x97\x68\x44";
a.input = "";
a.output = "\x46\xb9\xdd\x2b\x0b\xa8\x8d\x13\x23\x3b\x3f\xeb\x74\x3e\xeb"
"\x24\x3f\xcd\x52\xea\x62\xb8\x1b\x82\xb5\x0c\x27\x64\x6e\xd5"
"\x76\x2f\xd7\x5d\xc4\xdd\xd8\xc0\xf2\x00\xcb\x05\x01\x9d\x67"
"\xb5\x92\xf6\xfc\x82\x1c\x49\x47\x9a\xb4\x86\x40\x29\x2e\xac"
"\xb3\xb7\xc4\xbe\x14\x1e\x96\x61\x6f\xb1\x39\x57\x69\x2c\xc7"
"\xed\xd0\xb4\x5a\xe3\xdc\x07\x22\x3c\x8e\x92\x93\x7b\xef\x84"
"\xbc\x0e\xab\x86\x28\x53\x34\x9e\xc7\x55\x46\xf5\x8f\xb7\xc2"
"\x77\x5c\x38\x46\x2c\x50\x10\xd8\x46\xc1\x85\xc1\x51\x11\xe5"
"\x95\x52\x2a\x6b\xcd\x16\xcf\x86\xf3\xd1\x22\x10\x9e\x3b\x1f"
"\xdd";
a.inLen = XSTRLEN(a.input);
a.outLen = WC_SHA3_256_BLOCK_SIZE;
b.input = "abc";
b.output = "\x48\x33\x66\x60\x13\x60\xa8\x77\x1c\x68\x63\x08\x0c\xc4\x11"
"\x4d\x8d\xb4\x45\x30\xf8\xf1\xe1\xee\x4f\x94\xea\x37\xe7\x8b"
"\x57\x39\xd5\xa1\x5b\xef\x18\x6a\x53\x86\xc7\x57\x44\xc0\x52"
"\x7e\x1f\xaa\x9f\x87\x26\xe4\x62\xa1\x2a\x4f\xeb\x06\xbd\x88"
"\x01\xe7\x51\xe4\x13\x85\x14\x12\x04\xf3\x29\x97\x9f\xd3\x04"
"\x7a\x13\xc5\x65\x77\x24\xad\xa6\x4d\x24\x70\x15\x7b\x3c\xdc"
"\x28\x86\x20\x94\x4d\x78\xdb\xcd\xdb\xd9\x12\x99\x3f\x09\x13"
"\xf1\x64\xfb\x2c\xe9\x51\x31\xa2\xd0\x9a\x3e\x6d\x51\xcb\xfc"
"\x62\x27\x20\xd7\xa7\x5c\x63\x34\xe8\xa2\xd7\xec\x71\xa7\xcc"
"\x29";
b.inLen = XSTRLEN(b.input);
b.outLen = WC_SHA3_256_BLOCK_SIZE;
c.input = "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq";
c.output = "\x4d\x8c\x2d\xd2\x43\x5a\x01\x28\xee\xfb\xb8\xc3\x6f\x6f\x87"
"\x13\x3a\x79\x11\xe1\x8d\x97\x9e\xe1\xae\x6b\xe5\xd4\xfd\x2e"
"\x33\x29\x40\xd8\x68\x8a\x4e\x6a\x59\xaa\x80\x60\xf1\xf9\xbc"
"\x99\x6c\x05\xac\xa3\xc6\x96\xa8\xb6\x62\x79\xdc\x67\x2c\x74"
"\x0b\xb2\x24\xec\x37\xa9\x2b\x65\xdb\x05\x39\xc0\x20\x34\x55"
"\xf5\x1d\x97\xcc\xe4\xcf\xc4\x91\x27\xd7\x26\x0a\xfc\x67\x3a"
"\xf2\x08\xba\xf1\x9b\xe2\x12\x33\xf3\xde\xbe\x78\xd0\x67\x60"
"\xcf\xa5\x51\xee\x1e\x07\x91\x41\xd4\x9d\xd3\xef\x7e\x18\x2b"
"\x15\x24\xdf\x82\xea\x1c\xef\xe1\xc6\xc3\x96\x61\x75\xf0\x22"
"\x8d";
c.inLen = XSTRLEN(c.input);
c.outLen = WC_SHA3_256_BLOCK_SIZE;
/* Taken from NIST CAVP test vectors - full rate output. */
d.input = "\xdc\x88\x6d\xf3\xf6\x9c\x49\x51\x3d\xe3\x62\x7e\x94\x81\xdb"
"\x58\x71\xe8\xee\x88\xeb\x9f\x99\x61\x15\x41\x93\x0a\x8b\xc8"
"\x85\xe0";
d.output = "\x00\x64\x8a\xfb\xc5\xe6\x51\x64\x9d\xb1\xfd\x82\x93\x6b\x00"
"\xdb\xbc\x12\x2f\xb4\xc8\x77\x86\x0d\x38\x5c\x49\x50\xd5\x6d"
"\xe7\xe0\x96\xd6\x13\xd7\xa3\xf2\x7e\xd8\xf2\x63\x34\xb0\xcc"
"\xc1\x40\x7b\x41\xdc\xcb\x23\xdf\xaa\x52\x98\x18\xd1\x12\x5c"
"\xd5\x34\x80\x92\x52\x43\x66\xb8\x5f\xab\xb9\x7c\x6c\xd1\xe6"
"\x06\x6f\x45\x9b\xcc\x56\x6d\xa8\x7e\xc9\xb7\xba\x36\x79\x2d"
"\x11\x8a\xc3\x9a\x4c\xce\xf6\x19\x2b\xbf\x3a\x54\xaf\x18\xe5"
"\x7b\x0c\x14\x61\x01\xf6\xae\xaa\x82\x2b\xc4\xb4\xc9\x70\x8b"
"\x09\xf0\xb3\xba\xb4\x1b\xcc\xe9\x64\xd9\x99\xd1\x10\x7b\xd7"
"\xc2";
d.inLen = 32;
d.outLen = WC_SHA3_256_BLOCK_SIZE;
/* Taken from NIST CAVP test vectors - more than one output block. */
e.input = "\x8d\x80\x01\xe2\xc0\x96\xf1\xb8\x8e\x7c\x92\x24\xa0\x86\xef"
"\xd4\x79\x7f\xbf\x74\xa8\x03\x3a\x2d\x42\x2a\x2b\x6b\x8f\x67"
"\x47\xe4";
e.output = "\x2e\x97\x5f\x6a\x8a\x14\xf0\x70\x4d\x51\xb1\x36\x67\xd8\x19"
"\x5c\x21\x9f\x71\xe6\x34\x56\x96\xc4\x9f\xa4\xb9\xd0\x8e\x92"
"\x25\xd3\xd3\x93\x93\x42\x51\x52\xc9\x7e\x71\xdd\x24\x60\x1c"
"\x11\xab\xcf\xa0\xf1\x2f\x53\xc6\x80\xbd\x3a\xe7\x57\xb8\x13"
"\x4a\x9c\x10\xd4\x29\x61\x58\x69\x21\x7f\xdd\x58\x85\xc4\xdb"
"\x17\x49\x85\x70\x3a\x6d\x6d\xe9\x4a\x66\x7e\xac\x30\x23\x44"
"\x3a\x83\x37\xae\x1b\xc6\x01\xb7\x6d\x7d\x38\xec\x3c\x34\x46"
"\x31\x05\xf0\xd3\x94\x9d\x78\xe5\x62\xa0\x39\xe4\x46\x95\x48"
"\xb6\x09\x39\x5d\xe5\xa4\xfd\x43\xc4\x6c\xa9\xfd\x6e\xe2\x9a"
"\xda\x5e\xfc\x07\xd8\x4d\x55\x32\x49\x45\x0d\xab\x4a\x49\xc4"
"\x83\xde\xd2\x50\xc9\x33\x8f\x85\xcd\x93\x7a\xe6\x6b\xb4\x36"
"\xf3\xb4\x02\x6e\x85\x9f\xda\x1c\xa5\x71\x43\x2f\x3b\xfc\x09"
"\xe7\xc0\x3c\xa4\xd1\x83\xb7\x41\x11\x1c\xa0\x48\x3d\x0e\xda"
"\xbc\x03\xfe\xb2\x3b\x17\xee\x48\xe8\x44\xba\x24\x08\xd9\xdc"
"\xfd\x01\x39\xd2\xe8\xc7\x31\x01\x25\xae\xe8\x01\xc6\x1a\xb7"
"\x90\x0d\x1e\xfc\x47\xc0\x78\x28\x17\x66\xf3\x61\xc5\xe6\x11"
"\x13\x46\x23\x5e\x1d\xc3\x83\x25\x66\x6c\x68\x1b\x30\xdd\xc4"
"\xe6\x83\x8b\x0f\x23\x58\x7e\x06\x5f\x4a\x2b\xed\xc9\x6c\x97"
"\x68\x44";
e.inLen = 32;
e.outLen = 2 * WC_SHA3_256_BLOCK_SIZE;
test_sha[0] = a;
test_sha[1] = b;
test_sha[2] = c;
test_sha[3] = d;
test_sha[4] = e;
for (i = 0; i < times; ++i) {
ret = wc_InitShake256(sha, HEAP_HINT, devId);
if (ret != 0)
ERROR_OUT(-3100 - i, exit);
ret = wc_Shake256_Absorb(sha, (byte*)test_sha[i].input,
(word32)test_sha[i].inLen);
if (ret != 0)
ERROR_OUT(-3101 - i, exit);
ret = wc_Shake256_SqueezeBlocks(sha, hash,
(word32)test_sha[i].outLen / WC_SHA3_256_BLOCK_SIZE);
if (ret != 0)
ERROR_OUT(-3102 - i, exit);
if (XMEMCMP(hash, test_sha[i].output, (word32)test_sha[i].outLen) != 0)
ERROR_OUT(-3103 - i, exit);
}
/* BEGIN LARGE HASH TEST */ {
for (i = 0; i < (int)sizeof(large_input); i++) {
large_input[i] = (byte)(i & 0xFF);
}
ret = wc_InitShake256(sha, HEAP_HINT, devId);
if (ret != 0)
ERROR_OUT(-3104, exit);
/* Absorb is non-incremental. */
ret = wc_Shake256_Absorb(sha, (byte*)large_input,
(word32)sizeof(large_input));
if (ret != 0)
ERROR_OUT(-3105, exit);
/* Able to squeeze out blocks incrementally. */
ret = wc_Shake256_SqueezeBlocks(sha, hash, 1);
if (ret != 0)
ERROR_OUT(-3106, exit);
ret = wc_Shake256_SqueezeBlocks(sha, hash,
((word32)sizeof(hash) / WC_SHA3_256_BLOCK_SIZE) - 1);
if (ret != 0)
ERROR_OUT(-3106, exit);
if (XMEMCMP(hash, large_digest, sizeof(hash)) != 0)
ERROR_OUT(-3107, exit);
} /* END LARGE HASH TEST */
exit:
return ret;
}
WOLFSSL_TEST_SUBROUTINE int shake256_test(void)
{
wc_Shake sha;
@ -3630,6 +4130,7 @@ WOLFSSL_TEST_SUBROUTINE int shake256_test(void)
ERROR_OUT(-3106, exit);
} /* END LARGE HASH TEST */
ret = shake256_absorb_test(&sha);
exit:
wc_Shake256_Free(&sha);

View File

@ -215,8 +215,13 @@ WOLFSSL_API int wc_Sha3_224Hash(const byte* data, word32 len, byte* hash);
WOLFSSL_API int wc_Sha3_256Hash(const byte* data, word32 len, byte* hash);
WOLFSSL_API int wc_Sha3_384Hash(const byte* data, word32 len, byte* hash);
WOLFSSL_API int wc_Sha3_512Hash(const byte* data, word32 len, byte* hash);
#ifdef WOLFSSL_SHAKE128
WOLFSSL_API int wc_Shake128Hash(const byte* data, word32 len, byte* hash,
word32 hashLen);
#endif
#ifdef WOLFSSL_SHAKE256
WOLFSSL_API int wc_Shake256Hash(const byte* data, word32 len, byte* hash, word32 hashLen);
WOLFSSL_API int wc_Shake256Hash(const byte* data, word32 len, byte* hash,
word32 hashLen);
#endif
#endif /* WOLFSSL_SHA3 */

View File

@ -42,6 +42,9 @@
/* in bytes */
enum {
/* SHAKE-128 */
WC_SHA3_128_COUNT = 21,
WC_SHA3_224 = WC_HASH_TYPE_SHA3_224,
WC_SHA3_224_DIGEST_SIZE = 28,
WC_SHA3_224_COUNT = 18,
@ -58,8 +61,10 @@ enum {
WC_SHA3_512_DIGEST_SIZE = 64,
WC_SHA3_512_COUNT = 9,
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
WC_SHAKE128 = WC_HASH_TYPE_SHAKE128,
#endif
#ifndef WOLFSSL_NO_SHAKE256
WC_SHAKE256 = WC_HASH_TYPE_SHAKE256,
#endif
@ -67,6 +72,7 @@ enum {
defined(HAVE_SELFTEST_VERSION) && (HAVE_SELFTEST_VERSION >= 2)
/* These values are used for HMAC, not SHA-3 directly.
* They come from from FIPS PUB 202. */
WC_SHA3_128_BLOCK_SIZE = 168,
WC_SHA3_224_BLOCK_SIZE = 144,
WC_SHA3_256_BLOCK_SIZE = 136,
WC_SHA3_384_BLOCK_SIZE = 104,
@ -124,14 +130,10 @@ struct wc_Sha3 {
#endif
#ifndef WOLFSSL_NO_SHAKE256
#if !defined(WOLFSSL_NO_SHAKE128) || !defined(WOLFSSL_NO_SHAKE256)
typedef wc_Sha3 wc_Shake;
#endif
#if defined(WOLFSSL_ARMASM) && defined(WOLFSSL_ARMASM_CRYPTO_SHA3)
WOLFSSL_LOCAL void BlockSha3(word64 *s);
#endif
WOLFSSL_API int wc_InitSha3_224(wc_Sha3* sha3, void* heap, int devId);
WOLFSSL_API int wc_Sha3_224_Update(wc_Sha3* sha3, const byte* data, word32 len);
WOLFSSL_API int wc_Sha3_224_Final(wc_Sha3* sha3, byte* hash);
@ -160,10 +162,26 @@ WOLFSSL_API void wc_Sha3_512_Free(wc_Sha3* sha3);
WOLFSSL_API int wc_Sha3_512_GetHash(wc_Sha3* sha3, byte* hash);
WOLFSSL_API int wc_Sha3_512_Copy(wc_Sha3* src, wc_Sha3* dst);
#ifndef WOLFSSL_NO_SHAKE128
WOLFSSL_API int wc_InitShake128(wc_Shake* shake, void* heap, int devId);
WOLFSSL_API int wc_Shake128_Update(wc_Shake* shake, const byte* data, word32 len);
WOLFSSL_API int wc_Shake128_Final(wc_Shake* shake, byte* hash, word32 hashLen);
WOLFSSL_API int wc_Shake128_Absorb(wc_Shake* shake, const byte* data,
word32 len);
WOLFSSL_API int wc_Shake128_SqueezeBlocks(wc_Shake* shake, byte* out,
word32 blockCnt);
WOLFSSL_API void wc_Shake128_Free(wc_Shake* shake);
WOLFSSL_API int wc_Shake128_Copy(wc_Shake* src, wc_Sha3* dst);
#endif
#ifndef WOLFSSL_NO_SHAKE256
WOLFSSL_API int wc_InitShake256(wc_Shake* shake, void* heap, int devId);
WOLFSSL_API int wc_Shake256_Update(wc_Shake* shake, const byte* data, word32 len);
WOLFSSL_API int wc_Shake256_Final(wc_Shake* shake, byte* hash, word32 hashLen);
WOLFSSL_API int wc_Shake256_Absorb(wc_Shake* shake, const byte* data,
word32 len);
WOLFSSL_API int wc_Shake256_SqueezeBlocks(wc_Shake* shake, byte* out,
word32 blockCnt);
WOLFSSL_API void wc_Shake256_Free(wc_Shake* shake);
WOLFSSL_API int wc_Shake256_Copy(wc_Shake* src, wc_Sha3* dst);
#endif
@ -173,6 +191,17 @@ WOLFSSL_API int wc_Shake256_Copy(wc_Shake* src, wc_Sha3* dst);
WOLFSSL_API int wc_Sha3_GetFlags(wc_Sha3* sha3, word32* flags);
#endif
#ifdef USE_INTEL_SPEEDUP
WOLFSSL_LOCAL void sha3_block_n_bmi2(word64* s, const byte* data, word32 n,
word64 c);
WOLFSSL_LOCAL void sha3_block_bmi2(word64* s);
WOLFSSL_LOCAL void sha3_block_avx2(word64* s);
WOLFSSL_LOCAL void BlockSha3(word64 *s);
#endif
#if defined(WOLFSSL_ARMASM) && defined(WOLFSSL_ARMASM_CRYPTO_SHA3)
WOLFSSL_LOCAL void BlockSha3(word64 *s);
#endif
#ifdef __cplusplus
} /* extern "C" */
#endif

View File

@ -1041,8 +1041,10 @@ typedef struct w64wrapper {
#undef _WC_HASH_TYPE_MAX
#define _WC_HASH_TYPE_MAX WC_HASH_TYPE_SHA512_256
#endif
#ifndef WOLFSSL_NO_SHAKE256
#ifndef WOLFSSL_NO_SHAKE128
WC_HASH_TYPE_SHAKE128 = 18,
#endif
#ifndef WOLFSSL_NO_SHAKE256
WC_HASH_TYPE_SHAKE256 = 19,
#undef _WC_HASH_TYPE_MAX
#define _WC_HASH_TYPE_MAX WC_HASH_TYPE_SHAKE256