Port for Nordic nRF51 RNG, RTC and AES. Added RNG test for wc_RNG_GenerateBlock 0's check even if HAVE_HASHDRBG is enabled. Added NIST test vectors for ECC P-256, P-384 and P-521. Added helpful debug message in ECC import if issue finding ecc_sets[] for curve. Moved memory tracker into separate file and added support for it to wolfcrypt test and benchmark. Added Ed255519/Curve25519 options for granular control of sign, verify, shared secret, import and export. Added AES options for max key size (AES_MAX_KEY_SIZE), no decrypt (NO_AES_DECRYPT) and no CBC (NO_AES_CBC).

pull/349/head
David Garske 2016-03-15 13:58:51 -07:00
parent 47491e6c22
commit a38183b816
15 changed files with 1112 additions and 339 deletions

View File

@ -127,6 +127,10 @@
#include "wolfcrypt/benchmark/benchmark.h"
#ifdef USE_WOLFSSL_MEMORY
#include "wolfssl/mem_track.h"
#endif
void bench_des(void);
void bench_idea(void);
void bench_arc4(void);
@ -156,9 +160,11 @@ void bench_eccKeyGen(void);
void bench_eccKeyAgree(void);
#endif
#ifdef HAVE_CURVE25519
void bench_curve25519KeyGen(void);
void bench_curve25519KeyAgree(void);
#endif
void bench_curve25519KeyGen(void);
#ifdef HAVE_CURVE25519_SHARED_SECRET
void bench_curve25519KeyAgree(void);
#endif /* HAVE_CURVE25519_SHARED_SECRET */
#endif /* HAVE_CURVE25519 */
#ifdef HAVE_ED25519
void bench_ed25519KeyGen(void);
void bench_ed25519KeySign(void);
@ -250,6 +256,10 @@ int benchmark_test(void *args)
(void)args;
#endif
#ifdef USE_WOLFSSL_MEMORY
InitMemoryTracker();
#endif
wolfCrypt_Init();
#if defined(DEBUG_WOLFSSL) && !defined(HAVE_VALGRIND)
@ -375,7 +385,9 @@ int benchmark_test(void *args)
#ifdef HAVE_CURVE25519
bench_curve25519KeyGen();
#ifdef HAVE_CURVE25519_SHARED_SECRET
bench_curve25519KeyAgree();
#endif
#endif
#ifdef HAVE_ED25519
@ -387,6 +399,10 @@ int benchmark_test(void *args)
wc_FreeRng(&rng);
#endif
#ifdef USE_WOLFSSL_MEMORY
ShowMemoryTracker();
#endif
return 0;
}
@ -1672,7 +1688,7 @@ void bench_eccKeyAgree(void)
double start, total, each, milliEach;
int i, ret;
byte shared[32];
#ifndef NO_ASN
#if !defined(NO_ASN) && !defined(NO_ECC_SIGN)
byte sig[64+16]; /* der encoding too */
#endif
byte digest[32];
@ -1715,7 +1731,7 @@ void bench_eccKeyAgree(void)
digest[i] = (byte)i;
#ifndef NO_ASN
#if !defined(NO_ASN) && !defined(NO_ECC_SIGN)
start = current_time(1);
for(i = 0; i < agreeTimes; i++) {
@ -1779,7 +1795,7 @@ void bench_curve25519KeyGen(void)
" iterations\n", milliEach, genTimes);
}
#ifdef HAVE_CURVE25519_SHARED_SECRET
void bench_curve25519KeyAgree(void)
{
curve25519_key genKey, genKey2;
@ -1823,6 +1839,7 @@ void bench_curve25519KeyAgree(void)
wc_curve25519_free(&genKey2);
wc_curve25519_free(&genKey);
}
#endif /* HAVE_CURVE25519_SHARED_SECRET */
#endif /* HAVE_CURVE25519 */
#ifdef HAVE_ED25519
@ -1852,12 +1869,15 @@ void bench_ed25519KeyGen(void)
void bench_ed25519KeySign(void)
{
int ret;
ed25519_key genKey;
#ifdef HAVE_ED25519_SIGN
double start, total, each, milliEach;
int i, ret;
int i;
byte sig[ED25519_SIG_SIZE];
byte msg[512];
word32 x = 0;
#endif
wc_ed25519_init(&genKey);
@ -1866,11 +1886,12 @@ void bench_ed25519KeySign(void)
printf("ed25519_make_key failed\n");
return;
}
#ifdef HAVE_ED25519_SIGN
/* make dummy msg */
for (i = 0; i < (int)sizeof(msg); i++)
msg[i] = (byte)i;
start = current_time(1);
for(i = 0; i < agreeTimes; i++) {
@ -1888,6 +1909,7 @@ void bench_ed25519KeySign(void)
printf("ED25519 sign time %6.3f milliseconds, avg over %d"
" iterations\n", milliEach, agreeTimes);
#ifdef HAVE_ED25519_VERIFY
start = current_time(1);
for(i = 0; i < agreeTimes; i++) {
@ -1905,6 +1927,8 @@ void bench_ed25519KeySign(void)
milliEach = each * 1000; /* milliseconds */
printf("ED25519 verify time %6.3f milliseconds, avg over %d"
" iterations\n", milliEach, agreeTimes);
#endif /* HAVE_ED25519_VERIFY */
#endif /* HAVE_ED25519_SIGN */
wc_ed25519_free(&genKey);
}

View File

@ -48,12 +48,12 @@ int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz)
return AesCbcEncrypt_fips(aes, out, in, sz);
}
#ifdef HAVE_AES_DECRYPT
int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz)
{
return AesCbcDecrypt_fips(aes, out, in, sz);
}
#endif /* HAVE_AES_DECRYPT */
/* AES-CTR */
#ifdef WOLFSSL_AES_COUNTER
@ -70,12 +70,12 @@ void wc_AesEncryptDirect(Aes* aes, byte* out, const byte* in)
AesEncryptDirect(aes, out, in);
}
#ifdef HAVE_AES_DECRYPT
void wc_AesDecryptDirect(Aes* aes, byte* out, const byte* in)
{
AesDecryptDirect(aes, out, in);
}
#endif /* HAVE_AES_DECRYPT */
int wc_AesSetKeyDirect(Aes* aes, const byte* key, word32 len,
const byte* iv, int dir)
@ -101,7 +101,7 @@ int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz,
authIn, authInSz);
}
#ifdef HAVE_AES_DECRYPT
int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz,
const byte* iv, word32 ivSz,
const byte* authTag, word32 authTagSz,
@ -110,7 +110,7 @@ int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz,
return AesGcmDecrypt_fips(aes, out, in, sz, iv, ivSz, authTag, authTagSz,
authIn, authInSz);
}
#endif /* HAVE_AES_DECRYPT */
int wc_GmacSetKey(Gmac* gmac, const byte* key, word32 len)
{
@ -149,7 +149,7 @@ int wc_AesCcmEncrypt(Aes* aes, byte* out, const byte* in, word32 inSz,
return 0;
}
#ifdef HAVE_AES_DECRYPT
int wc_AesCcmDecrypt(Aes* aes, byte* out, const byte* in, word32 inSz,
const byte* nonce, word32 nonceSz,
const byte* authTag, word32 authTagSz,
@ -158,6 +158,7 @@ int wc_AesCcmDecrypt(Aes* aes, byte* out, const byte* in, word32 inSz,
return AesCcmDecrypt(aes, out, in, inSz, nonce, nonceSz, authTag, authTagSz,
authIn, authInSz);
}
#endif /* HAVE_AES_DECRYPT */
#endif /* HAVE_AESCCM */
#ifdef HAVE_CAVIUM
@ -195,7 +196,7 @@ void wc_AesFreeCavium(Aes* aes)
#pragma warning(disable: 4127)
#endif
/* Define AES implementation includes and functions */
#if defined(STM32F2_CRYPTO)
/* STM32F2 hardware AES support for CBC, CTR modes through the STM32F2
* Standard Peripheral Library. Documentation located in STM32F2xx
@ -227,6 +228,7 @@ void wc_AesFreeCavium(Aes* aes)
}
return ret;
}
#ifdef HAVE_AES_DECRYPT
static int wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
{
int ret = wolfSSL_CryptHwMutexLock();
@ -236,6 +238,7 @@ void wc_AesFreeCavium(Aes* aes)
}
return ret;
}
#endif /* HAVE_AES_DECRYPT */
#elif defined(WOLFSSL_PIC32MZ_CRYPT)
/* NOTE: no support for AES-CCM/Direct */
#define DEBUG_WOLFSSL
@ -251,12 +254,29 @@ void wc_AesFreeCavium(Aes* aes)
const byte* iv);
static int wc_AesCaviumCbcEncrypt(Aes* aes, byte* out, const byte* in,
word32 length);
#ifdef HAVE_AES_DECRYPT
static int wc_AesCaviumCbcDecrypt(Aes* aes, byte* out, const byte* in,
word32 length);
#endif /* HAVE_AES_DECRYPT */
#elif defined(WOLFSSL_NRF51_AES)
/* Use built-in AES hardware - AES 128 ECB Encrypt Only */
#include "wolfssl/wolfcrypt/port/nrf51.h"
static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock)
{
return nrf51_aes_encrypt(inBlock, (byte*)aes->key, aes->rounds, outBlock);
}
#ifdef HAVE_AES_DECRYPT
static int wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
{
return nrf51_aes_decrypt(inBlock, (byte*)aes->key, aes->rounds, outBlock);
}
#endif /* HAVE_AES_DECRYPT */
#else
/* using CTaoCrypt software AES implementation */
/* using wolfCrypt software AES implementation */
#define NEED_AES_TABLES
#endif /* STM32F2_CRYPTO */
#endif
#ifdef NEED_AES_TABLES
@ -937,6 +957,7 @@ static const word32 Td[5][256] = {
#define GETBYTE(x, y) (word32)((byte)((x) >> (8 * (y))))
#ifdef WOLFSSL_AESNI
/* Each platform needs to query info type 1 from cpuid to see if aesni is
@ -983,20 +1004,22 @@ void AES_CBC_encrypt(const unsigned char* in, unsigned char* out,
const unsigned char* KS, int nr)
XASM_LINK("AES_CBC_encrypt");
#ifdef HAVE_AES_DECRYPT
void AES_CBC_decrypt(const unsigned char* in, unsigned char* out,
unsigned char* ivec, unsigned long length,
const unsigned char* KS, int nr)
XASM_LINK("AES_CBC_decrypt");
#endif
void AES_ECB_encrypt(const unsigned char* in, unsigned char* out,
unsigned long length, const unsigned char* KS, int nr)
XASM_LINK("AES_ECB_encrypt");
#ifdef HAVE_AES_DECRYPT
void AES_ECB_decrypt(const unsigned char* in, unsigned char* out,
unsigned long length, const unsigned char* KS, int nr)
XASM_LINK("AES_ECB_decrypt");
#endif
void AES_128_Key_Expansion(const unsigned char* userkey,
unsigned char* key_schedule)
@ -1032,7 +1055,7 @@ static int AES_set_encrypt_key(const unsigned char *userKey, const int bits,
return BAD_FUNC_ARG;
}
#ifdef HAVE_AES_DECRYPT
static int AES_set_decrypt_key(const unsigned char* userKey, const int bits,
Aes* aes)
{
@ -1075,9 +1098,7 @@ static int AES_set_decrypt_key(const unsigned char* userKey, const int bits,
return 0;
}
#endif /* HAVE_AES_DECRYPT */
#endif /* WOLFSSL_AESNI */
@ -1103,7 +1124,7 @@ static void wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock)
printf("sz = %d\n", AES_BLOCK_SIZE);
#endif
/* check alignment, decrypt doesn't need alignment */
/* check alignment, encrypt doesn't need alignment */
if ((wolfssl_word)inBlock % 16) {
#ifndef NO_WOLFSSL_ALLOC_ALIGN
byte* tmp = (byte*)XMALLOC(AES_BLOCK_SIZE, NULL,
@ -1260,6 +1281,7 @@ static void wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock)
XMEMCPY(outBlock + 3 * sizeof(s0), &s3, sizeof(s3));
}
#ifdef HAVE_AES_DECRYPT
static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
{
word32 s0, s1, s2, s3;
@ -1418,7 +1440,7 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
XMEMCPY(outBlock + 2 * sizeof(s0), &s2, sizeof(s2));
XMEMCPY(outBlock + 3 * sizeof(s0), &s3, sizeof(s3));
}
#endif /* HAVE_AES_DECRYPT */
#endif /* NEED_AES_TABLES */
@ -1533,6 +1555,29 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
return ret;
}
int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen,
const byte* iv, int dir)
{
return wc_AesSetKey(aes, userKey, keylen, iv, dir);
}
#elif defined(WOLFSSL_NRF51_AES)
int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, const byte* iv,
int dir)
{
int ret;
(void)dir;
(void)iv;
if (keylen != 16)
return BAD_FUNC_ARG;
aes->rounds = keylen/4 + 6;
ret = nrf51_aes_set_key(userKey);
return ret;
}
int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen,
const byte* iv, int dir)
{
@ -1574,6 +1619,7 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
switch(keylen)
{
#if defined(AES_MAX_KEY_SIZE) && AES_MAX_KEY_SIZE >= 128
case 16:
while (1)
{
@ -1592,7 +1638,9 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
rk += 4;
}
break;
#endif /* 128 */
#if defined(AES_MAX_KEY_SIZE) && AES_MAX_KEY_SIZE >= 192
case 24:
/* for (;;) here triggers a bug in VC60 SP4 w/ Pro Pack */
while (1)
@ -1614,7 +1662,9 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
rk += 6;
}
break;
#endif /* 192 */
#if defined(AES_MAX_KEY_SIZE) && AES_MAX_KEY_SIZE >= 256
case 32:
while (1)
{
@ -1643,11 +1693,13 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
rk += 8;
}
break;
#endif /* 256 */
default:
return BAD_FUNC_ARG;
}
#ifdef HAVE_AES_DECRYPT
if (dir == AES_DECRYPTION)
{
unsigned int j;
@ -1686,6 +1738,7 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
Td[3][Te[4][GETBYTE(rk[3], 0)] & 0xff];
}
}
#endif /* HAVE_AES_DECRYPT */
return wc_AesSetIV(aes, iv);
}
@ -1697,6 +1750,14 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
if (!((keylen == 16) || (keylen == 24) || (keylen == 32)))
return BAD_FUNC_ARG;
/* Check key length */
#if defined(AES_MAX_KEY_SIZE)
const word32 max_key_len = (AES_MAX_KEY_SIZE / 8);
if (keylen > max_key_len) {
return BAD_FUNC_ARG;
}
#endif
#ifdef HAVE_CAVIUM
if (aes->magic == WOLFSSL_AES_CAVIUM_MAGIC)
return wc_AesCaviumSetKey(aes, userKey, keylen, iv);
@ -1713,8 +1774,10 @@ static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock)
XMEMCPY(aes->reg, iv, AES_BLOCK_SIZE);
if (dir == AES_ENCRYPTION)
return AES_set_encrypt_key(userKey, keylen * 8, aes);
#ifdef HAVE_AES_DECRYPT
else
return AES_set_decrypt_key(userKey, keylen * 8, aes);
#endif
}
#endif /* WOLFSSL_AESNI */
@ -1768,13 +1831,13 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
{
wc_AesEncrypt(aes, in, out);
}
#ifdef HAVE_AES_DECRYPT
/* Allow direct access to one block decrypt */
void wc_AesDecryptDirect(Aes* aes, byte* out, const byte* in)
{
wc_AesDecrypt(aes, in, out);
}
#endif /* HAVE_AES_DECRYPT */
#endif /* AES direct block */
#endif /* WOLFSSL_AES_DIRECT */
@ -1886,6 +1949,7 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
return 0;
}
#ifdef HAVE_AES_DECRYPT
int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz)
{
word32 *dec_key, *iv;
@ -2006,7 +2070,7 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
return 0;
}
#endif /* HAVE_AES_DECRYPT */
#elif defined(HAVE_COLDFIRE_SEC)
static int wc_AesCbcCrypt(Aes* aes, byte* po, const byte* pi, word32 sz,
word32 descHeader)
@ -2106,11 +2170,12 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
return (wc_AesCbcCrypt(aes, po, pi, sz, SEC_DESC_AES_CBC_ENCRYPT));
}
#ifdef HAVE_AES_DECRYPT
int wc_AesCbcDecrypt(Aes* aes, byte* po, const byte* pi, word32 sz)
{
return (wc_AesCbcCrypt(aes, po, pi, sz, SEC_DESC_AES_CBC_DECRYPT));
}
#endif /* HAVE_AES_DECRYPT */
#elif defined(FREESCALE_MMCAU)
int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz)
{
@ -2147,7 +2212,7 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
return 0;
}
#ifdef HAVE_AES_DECRYPT
int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz)
{
int i;
@ -2183,7 +2248,7 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
return 0;
}
#endif /* HAVE_AES_DECRYPT */
#elif defined(WOLFSSL_PIC32MZ_CRYPT)
/* core hardware crypt engine driver */
static void wc_AesCrypt(Aes *aes, byte* out, const byte* in, word32 sz,
@ -2286,13 +2351,49 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
PIC32_CRYPTOALGO_RCBC );
return 0 ;
}
#ifdef HAVE_AES_DECRYPT
int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz)
{
wc_AesCrypt(aes, out, in, sz, PIC32_DECRYPTION, PIC32_ALGO_AES,
PIC32_CRYPTOALGO_RCBC);
return 0 ;
}
#endif /* HAVE_AES_DECRYPT */
#elif defined(WOLFSSL_NRF51_AES)
int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz)
{
int i, ret;
int offset = 0;
int len = sz;
byte *iv;
byte temp_block[AES_BLOCK_SIZE];
iv = (byte*)aes->reg;
while (len > 0)
{
XMEMCPY(temp_block, in + offset, AES_BLOCK_SIZE);
/* XOR block with IV for CBC */
for (i = 0; i < AES_BLOCK_SIZE; i++) {
temp_block[i] ^= iv[i];
}
ret = wc_AesEncrypt(aes, temp_block, out + offset);
if (ret != 0) {
return ret;
}
len -= AES_BLOCK_SIZE;
offset += AES_BLOCK_SIZE;
/* store IV for next block */
XMEMCPY(iv, out + offset - AES_BLOCK_SIZE, AES_BLOCK_SIZE);
}
return 0;
}
#else
int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz)
@ -2358,6 +2459,7 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
return 0;
}
#ifdef HAVE_AES_DECRYPT
int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz)
{
word32 blocks = sz / AES_BLOCK_SIZE;
@ -2401,6 +2503,7 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
return 0;
}
#endif
#endif /* STM32F2_CRYPTO, AES-CBC block */
@ -2650,6 +2753,9 @@ int wc_AesSetIV(Aes* aes, const byte* iv)
#elif defined(HAVE_COLDFIRE_SEC)
#error "Coldfire SEC doesn't currently support AES-GCM mode"
#elif defined(WOLFSSL_NRF51_AES)
#error "nRF51 doesn't currently support AES-GCM mode"
#endif
enum {
@ -2967,6 +3073,7 @@ static void AES_GCM_encrypt(const unsigned char *in,
}
#ifdef HAVE_AES_DECRYPT
/* Figure 10. AES-GCM Decrypt With Single Block Ghash at a Time */
static int AES_GCM_decrypt(const unsigned char *in,
@ -3185,7 +3292,7 @@ static int AES_GCM_decrypt(const unsigned char *in,
return 1; /* when successful returns 1 */
}
#endif /* HAVE_AES_DECRYPT */
#endif /* WOLFSSL_AESNI */
@ -3764,6 +3871,7 @@ int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz,
}
#ifdef HAVE_AES_DECRYPT
int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz,
const byte* iv, word32 ivSz,
const byte* authTag, word32 authTagSz,
@ -3845,7 +3953,7 @@ int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz,
return 0;
}
#endif /* HAVE_AES_DECRYPT */
WOLFSSL_API int wc_GmacSetKey(Gmac* gmac, const byte* key, word32 len)
{
@ -4029,7 +4137,7 @@ int wc_AesCcmEncrypt(Aes* aes, byte* out, const byte* in, word32 inSz,
return 0;
}
#ifdef HAVE_AES_DECRYPT
int wc_AesCcmDecrypt(Aes* aes, byte* out, const byte* in, word32 inSz,
const byte* nonce, word32 nonceSz,
const byte* authTag, word32 authTagSz,
@ -4118,7 +4226,7 @@ int wc_AesCcmDecrypt(Aes* aes, byte* out, const byte* in, word32 inSz,
return result;
}
#endif /* HAVE_AES_DECRYPT */
#endif /* HAVE_AESCCM */
@ -4208,6 +4316,7 @@ static int wc_AesCaviumCbcEncrypt(Aes* aes, byte* out, const byte* in,
return 0;
}
#ifdef HAVE_AES_DECRYPT
static int wc_AesCaviumCbcDecrypt(Aes* aes, byte* out, const byte* in,
word32 length)
{
@ -4242,6 +4351,7 @@ static int wc_AesCaviumCbcDecrypt(Aes* aes, byte* out, const byte* in,
}
return 0;
}
#endif /* HAVE_AES_DECRYPT */
#endif /* HAVE_CAVIUM */

View File

@ -39,10 +39,10 @@
#endif
const curve25519_set_type curve25519_sets[] = {
{
{
32,
"CURVE25519",
}
}
};
@ -79,6 +79,8 @@ int wc_curve25519_make_key(WC_RNG* rng, int keysize, curve25519_key* key)
return ret;
}
#ifdef HAVE_CURVE25519_SHARED_SECRET
int wc_curve25519_shared_secret(curve25519_key* private_key,
curve25519_key* public_key,
byte* out, word32* outlen)
@ -125,6 +127,10 @@ int wc_curve25519_shared_secret_ex(curve25519_key* private_key,
return ret;
}
#endif /* HAVE_CURVE25519_SHARED_SECRET */
#ifdef HAVE_CURVE25519_KEY_EXPORT
/* export curve25519 public key (Big endian)
* return 0 on success */
int wc_curve25519_export_public(curve25519_key* key, byte* out, word32* outLen)
@ -165,6 +171,10 @@ int wc_curve25519_export_public_ex(curve25519_key* key, byte* out,
return 0;
}
#endif /* HAVE_CURVE25519_KEY_EXPORT */
#ifdef HAVE_CURVE25519_KEY_IMPORT
/* import curve25519 public key (Big endian)
* return 0 on success */
int wc_curve25519_import_public(const byte* in, word32 inLen,
@ -204,6 +214,10 @@ int wc_curve25519_import_public_ex(const byte* in, word32 inLen,
return 0;
}
#endif /* HAVE_CURVE25519_KEY_IMPORT */
#ifdef HAVE_CURVE25519_KEY_EXPORT
/* export curve25519 private key only raw (Big endian)
* outLen is in/out size
@ -276,6 +290,9 @@ int wc_curve25519_export_key_raw_ex(curve25519_key* key,
return wc_curve25519_export_public_ex(key, pub, pubSz, endian);
}
#endif /* HAVE_CURVE25519_KEY_EXPORT */
#ifdef HAVE_CURVE25519_KEY_IMPORT
/* curve25519 private key import (Big endian)
* Public key to match private key needs to be imported too
@ -348,6 +365,9 @@ int wc_curve25519_import_private_ex(const byte* priv, word32 privSz,
return 0;
}
#endif /* HAVE_CURVE25519_KEY_IMPORT */
int wc_curve25519_init(curve25519_key* key)
{
if (key == NULL)

View File

@ -65,6 +65,7 @@ ECC Curves:
#include <wolfssl/openssl/ec.h>
#include <wolfssl/wolfcrypt/asn.h>
#include <wolfssl/wolfcrypt/error-crypt.h>
#include <wolfssl/wolfcrypt/logging.h>
#ifdef HAVE_ECC_ENCRYPT
#include <wolfssl/wolfcrypt/hmac.h>
@ -3017,6 +3018,7 @@ int wc_ecc_import_x963(const byte* in, word32 inLen, ecc_key* key)
}
}
if (ecc_sets[x].size == 0) {
WOLFSSL_MSG("ecc_set size not found");
err = ASN_PARSE_E;
} else {
/* set the idx */
@ -3257,6 +3259,7 @@ int wc_ecc_import_raw(ecc_key* key, const char* qx, const char* qy,
}
}
if (ecc_sets[x].size == 0) {
WOLFSSL_MSG("ecc_set curve name not found");
err = ASN_PARSE_E;
} else {
/* set the curve */

View File

@ -79,6 +79,7 @@ int wc_ed25519_make_key(WC_RNG* rng, int keySz, ed25519_key* key)
}
#ifdef HAVE_ED25519_SIGN
/*
in contains the message to sign
inlen is the length of the message to sign
@ -164,6 +165,9 @@ int wc_ed25519_sign_msg(const byte* in, word32 inlen, byte* out,
return ret;
}
#endif /* HAVE_ED25519_SIGN */
#ifdef HAVE_ED25519_VERIFY
/*
sig is array of bytes containing the signature
@ -238,6 +242,8 @@ int wc_ed25519_verify_msg(byte* sig, word32 siglen, const byte* msg,
return ret;
}
#endif /* HAVE_ED25519_VERIFY */
/* initialize information and memory for key */
int wc_ed25519_init(ed25519_key* key)
@ -261,6 +267,8 @@ void wc_ed25519_free(ed25519_key* key)
}
#ifdef HAVE_ED25519_KEY_EXPORT
/*
outLen should contain the size of out buffer when input. outLen is than set
to the final output length.
@ -283,7 +291,10 @@ int wc_ed25519_export_public(ed25519_key* key, byte* out, word32* outLen)
return 0;
}
#endif /* HAVE_ED25519_KEY_EXPORT */
#ifdef HAVE_ED25519_KEY_IMPORT
/*
Imports a compressed/uncompressed public key.
in the byte array containing the public key
@ -357,6 +368,10 @@ int wc_ed25519_import_private_key(const byte* priv, word32 privSz,
return ret;
}
#endif /* HAVE_ED25519_KEY_IMPORT */
#ifdef HAVE_ED25519_KEY_EXPORT
/*
export private key only (secret part so 32 bytes)
@ -424,6 +439,9 @@ int wc_ed25519_export_key(ed25519_key* key,
return ret;
}
#endif /* HAVE_ED25519_KEY_EXPORT */
/* returns the private key size (secret only) in bytes */
int wc_ed25519_size(ed25519_key* key)
{

View File

@ -43,6 +43,7 @@ EXTRA_DIST += wolfcrypt/src/port/ti/ti-aes.c \
wolfcrypt/src/port/ti/ti-des3.c \
wolfcrypt/src/port/ti/ti-hash.c \
wolfcrypt/src/port/ti/ti-ccm.c \
wolfcrypt/src/port/pic32/pic32mz-hash.c
wolfcrypt/src/port/pic32/pic32mz-hash.c \
wolfcrypt/src/port/nrf51.c

View File

@ -0,0 +1,215 @@
/* nrf51.c
*
* Copyright (C) 2006-2015 wolfSSL Inc.
*
* This file is part of wolfSSL. (formerly known as CyaSSL)
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <wolfssl/wolfcrypt/settings.h>
#ifdef WOLFSSL_NRF51
#include "bsp.h"
#include "nrf_delay.h"
#include "app_uart.h"
#include "app_error.h"
#include "nrf_drv_rng.h"
#include "nrf_drv_rtc.h"
#include "nrf_drv_clock.h"
#include "nrf_ecb.h"
#ifdef SOFTDEVICE_PRESENT
#include "softdevice_handler.h"
#include "nrf_soc.h"
#endif /* SOFTDEVICE_PRESENT */
/* RTC */
#ifndef NO_CRYPT_BENCHMARK
static byte mRtcInitDone = 0;
static int mRtcSec = 0;
const nrf_drv_rtc_t rtc = NRF_DRV_RTC_INSTANCE(0); /**< Declaring an instance of nrf_drv_rtc for RTC0. */
#endif /* !NO_CRYPT_BENCHMARK */
/* AES */
#if !defined(NO_AES) && !defined(SOFTDEVICE_PRESENT)
static byte mAesInitDone = 0;
#endif
/** @brief Function for getting vector of random numbers.
*
* @param[out] p_buff Pointer to unit8_t buffer for storing the bytes.
* @param[in] length Number of bytes to take from pool and place in p_buff.
*
* @retval 0 = Success, else error
*/
int nrf51_random_generate(byte* output, word32 size)
{
int remaining = size, length, pos = 0;
uint8_t available;
uint32_t err_code;
/* Make sure RNG is running */
err_code = nrf_drv_rng_init(NULL);
if (NRF_SUCCESS != NRF_SUCCESS && err_code != NRF_ERROR_INVALID_STATE) {
return -1;
}
while (remaining > 0) {
err_code = nrf_drv_rng_bytes_available(&available);
if (err_code == NRF_SUCCESS) {
length = (remaining < available) ? remaining : available;
if (length > 0) {
err_code = nrf_drv_rng_rand(&output[pos], length);
remaining -= length;
pos += length;
}
}
if (err_code != NRF_SUCCESS) {
break;
}
}
return (err_code == NRF_SUCCESS) ? 0 : -1;
}
#if !defined(NO_AES) && defined(WOLFSSL_NRF51_AES)
#ifdef SOFTDEVICE_PRESENT
static const byte* nRF51AesKey = NULL;
#endif
int nrf51_aes_set_key(const byte* key)
{
#ifdef SOFTDEVICE_PRESENT
nRF51AesKey = key;
#else
if (!mAesInitDone) {
nrf_ecb_init();
mAesInitDone = 1;
}
nrf_ecb_set_key(key);
#endif
return 0;
}
int nrf51_aes_encrypt(const byte* in, const byte* key, word32 rounds, byte* out)
{
uint32_t err_code = 0;
#ifdef SOFTDEVICE_PRESENT
nrf_ecb_hal_data_t ecb_hal_data;
#endif
/* Set key */
nrf51_aes_set_key(key);
#ifdef SOFTDEVICE_PRESENT
/* Define ECB record */
XMEMCPY(ecb_hal_data.key, nRF51AesKey, SOC_ECB_KEY_LENGTH);
XMEMCPY(ecb_hal_data.cleartext, in, SOC_ECB_CLEARTEXT_LENGTH);
XMEMSET(ecb_hal_data.ciphertext, 0, SOC_ECB_CIPHERTEXT_LENGTH);
/* Perform block encrypt */
err_code = sd_ecb_block_encrypt(&ecb_hal_data);
if (err_code != NRF_SUCCESS) {
return -1;
}
/* Grab result */
XMEMCPY(out, ecb_hal_data.ciphertext, SOC_ECB_CIPHERTEXT_LENGTH);
#else
err_code = nrf_ecb_crypt(out, in);
err_code = err_code ? 0 : -1;
#endif
return err_code;
}
#endif /* !NO_AES && WOLFSSL_NRF51_AES */
#ifndef NO_CRYPT_BENCHMARK
static void rtc_handler(nrf_drv_rtc_int_type_t int_type)
{
if (int_type == NRF_DRV_RTC_INT_COMPARE0)
{
mRtcSec++;
nrf_drv_rtc_counter_clear(&rtc);
nrf_drv_rtc_int_enable(&rtc, RTC_CHANNEL_INT_MASK(0));
#ifdef BSP_LED_0
nrf_gpio_pin_toggle(BSP_LED_0);
#endif
}
}
static void rtc_config(void)
{
uint32_t err_code;
// Start the internal LFCLK XTAL oscillator
err_code = nrf_drv_clock_init(NULL);
APP_ERROR_CHECK(err_code);
nrf_drv_clock_lfclk_request();
// Initialize RTC instance
err_code = nrf_drv_rtc_init(&rtc, NULL, rtc_handler);
APP_ERROR_CHECK(err_code);
// Enable tick event
nrf_drv_rtc_tick_enable(&rtc, false);
// Set compare channel to trigger interrupt after 1 seconds
err_code = nrf_drv_rtc_cc_set(&rtc, 0, RTC0_CONFIG_FREQUENCY, true);
APP_ERROR_CHECK(err_code);
// Power on RTC instance
nrf_drv_rtc_enable(&rtc);
}
static int rtc_get_ms(void)
{
/* Prescaler is 12-bit for COUNTER: frequency = (32768/(PRESCALER+1)) */
int frequency = (32768 / (rtc_prescaler_get(rtc.p_reg) + 1));
int counter = nrf_drv_rtc_counter_get(&rtc);
/* Convert with rounding frequency to milliseconds */
return ((counter * 1000) + (frequency / 2) ) / frequency;
}
double current_time(int reset)
{
double time;
if (!mRtcInitDone) {
rtc_config();
mRtcInitDone = 1;
}
time = mRtcSec;
time += (double)rtc_get_ms() / 1000;
return time;
}
#endif /* !NO_CRYPT_BENCHMARK */
#endif /* WOLFSSL_NRF51 */

View File

@ -1366,6 +1366,42 @@ int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz)
return 0;
}
#elif defined(WOLFSSL_NRF51)
#include "app_error.h"
#include "nrf_drv_rng.h"
int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz)
{
int remaining = sz, length, pos = 0;
uint8_t available;
uint32_t err_code;
(void)os;
/* Make sure RNG is running */
err_code = nrf_drv_rng_init(NULL);
if (NRF_SUCCESS != NRF_SUCCESS && err_code != NRF_ERROR_INVALID_STATE) {
return -1;
}
while (remaining > 0) {
err_code = nrf_drv_rng_bytes_available(&available);
if (err_code == NRF_SUCCESS) {
length = (remaining < available) ? remaining : available;
if (length > 0) {
err_code = nrf_drv_rng_rand(&output[pos], length);
remaining -= length;
pos += length;
}
}
if (err_code != NRF_SUCCESS) {
break;
}
}
return (err_code == NRF_SUCCESS) ? 0 : -1;
}
#elif defined(CUSTOM_RAND_GENERATE)
/* Implement your own random generation function

View File

@ -141,6 +141,10 @@
#include "wolfcrypt/test/test.h"
#ifdef USE_WOLFSSL_MEMORY
#include "wolfssl/mem_track.h"
#endif
typedef struct testVector {
const char* input;
@ -258,6 +262,10 @@ int wolfcrypt_test(void* args)
((func_args*)args)->return_code = -1; /* error state */
#ifdef USE_WOLFSSL_MEMORY
InitMemoryTracker();
#endif
#ifdef HAVE_FIPS
wolfCrypt_SetCb_fips(myFipsCb);
#endif
@ -586,6 +594,10 @@ int wolfcrypt_test(void* args)
printf( "PKCS7signed test passed!\n");
#endif
#ifdef USE_WOLFSSL_MEMORY
ShowMemoryTracker();
#endif
((func_args*)args)->return_code = ret;
return ret;
@ -2607,6 +2619,11 @@ int aes_test(void)
Aes enc;
Aes dec;
byte cipher[AES_BLOCK_SIZE * 4];
byte plain [AES_BLOCK_SIZE * 4];
int ret = 0;
#ifdef HAVE_AES_CBC
const byte msg[] = { /* "Now is the time for all " w/o trailing 0 */
0x6e,0x6f,0x77,0x20,0x69,0x73,0x20,0x74,
0x68,0x65,0x20,0x74,0x69,0x6d,0x65,0x20,
@ -2622,10 +2639,6 @@ int aes_test(void)
byte key[] = "0123456789abcdef "; /* align */
byte iv[] = "1234567890abcdef "; /* align */
byte cipher[AES_BLOCK_SIZE * 4];
byte plain [AES_BLOCK_SIZE * 4];
int ret;
#ifdef HAVE_CAVIUM
if (wc_AesInitCavium(&enc, CAVIUM_DEV_ID) != 0)
return -20003;
@ -2642,13 +2655,14 @@ int aes_test(void)
ret = wc_AesCbcEncrypt(&enc, cipher, msg, AES_BLOCK_SIZE);
if (ret != 0)
return -1005;
#ifdef HAVE_AES_DECRYPT
ret = wc_AesCbcDecrypt(&dec, plain, cipher, AES_BLOCK_SIZE);
if (ret != 0)
return -1006;
if (memcmp(plain, msg, AES_BLOCK_SIZE))
return -60;
#endif /* HAVE_AES_DECRYPT */
if (memcmp(cipher, verify, AES_BLOCK_SIZE))
return -61;
@ -2656,6 +2670,8 @@ int aes_test(void)
wc_AesFreeCavium(&enc);
wc_AesFreeCavium(&dec);
#endif
#endif /* HAVE_AES_CBC */
#ifdef WOLFSSL_AES_COUNTER
{
const byte ctrKey[] =
@ -2780,7 +2796,7 @@ int aes_test(void)
}
#endif /* WOLFSSL_AESNI && WOLFSSL_AES_DIRECT */
return 0;
return ret;
}
#ifdef HAVE_AESGCM
@ -3559,6 +3575,46 @@ int idea_test(void)
#endif /* HAVE_IDEA */
static int random_rng_test(void)
{
WC_RNG rng;
byte block[32];
int ret, i;
#ifdef HAVE_CAVIUM
ret = wc_InitRngCavium(&rng, CAVIUM_DEV_ID);
if (ret != 0) return -2007;
#endif
ret = wc_InitRng(&rng);
if (ret != 0) return -39;
XMEMSET(block, 0, sizeof(block));
ret = wc_RNG_GenerateBlock(&rng, block, sizeof(block));
if (ret != 0) {
ret = -40;
goto exit;
}
/* Check for 0's */
for (i=0; i<(int)sizeof(block); i++) {
if (block[i] == 0) {
ret++;
}
}
/* All zeros count check */
if (ret >= (int)sizeof(block)) {
ret = -38;
goto exit;
}
exit:
/* Make sure and free RNG */
wc_FreeRng(&rng);
return ret;
}
#if (defined(HAVE_HASHDRBG) || defined(NO_RC4)) && !defined(CUSTOM_RAND_GENERATE_BLOCK)
int random_test(void)
@ -3632,6 +3688,9 @@ int random_test(void)
if (XMEMCMP(test2Output, output, sizeof(output)) != 0)
return -42;
/* Basic RNG generate block test */
random_rng_test();
return 0;
}
@ -3639,21 +3698,8 @@ int random_test(void)
int random_test(void)
{
WC_RNG rng;
byte block[32];
int ret;
#ifdef HAVE_CAVIUM
ret = wc_InitRngCavium(&rng, CAVIUM_DEV_ID);
if (ret != 0) return -2007;
#endif
ret = wc_InitRng(&rng);
if (ret != 0) return -39;
ret = wc_RNG_GenerateBlock(&rng, block, sizeof(block));
if (ret != 0) return -40;
wc_FreeRng(&rng);
/* Basic RNG generate block test */
random_rng_test();
return 0;
}
@ -6162,32 +6208,93 @@ int hkdf_test(void)
#ifdef HAVE_ECC
#ifndef HAVE_ECC_VECTOR_TEST
#if defined(HAVE_ECC192) || defined(HAVE_ECC224) || !defined(NO_ECC256) || \
defined(HAVE_ECC384) || defined(HAVE_ECC521) || defined(HAVE_ALL_CURVES)
#define HAVE_ECC_VECTOR_TEST
#endif
#endif
#ifdef HAVE_ECC_VECTOR_TEST
typedef struct rawEccVector {
const char* msg;
const char* msg; /* SHA-1 Encoded Message */
const char* Qx;
const char* Qy;
const char* d;
const char* d; /* Private Key */
const char* R;
const char* S;
const char* curveName;
size_t msgLen;
} rawEccVector;
static int ecc_test_raw_vector(const rawEccVector* vector, ecc_key* userA,
byte* sig, word32 sigSz)
{
int ret, verify;
word32 x;
wc_ecc_free(userA);
wc_ecc_init(userA);
memset(sig, 0, sigSz);
x = sigSz;
ret = wc_ecc_import_raw(userA, vector->Qx, vector->Qy,
vector->d, vector->curveName);
if (ret != 0)
return -1018;
ret = wc_ecc_rs_to_sig(vector->R, vector->S, sig, &x);
if (ret != 0)
return -1019;
ret = wc_ecc_verify_hash(sig, x, (byte*)vector->msg, (word32)vector->msgLen, &verify, userA);
if (ret != 0)
return -1021;
if (verify != 1)
return -1023;
return 0;
}
#endif /* HAVE_ECC_VECTOR_TEST */
int ecc_test(void)
{
WC_RNG rng;
#ifdef BENCH_EMBEDDED
byte sharedA[32];
byte sharedB[32];
#else
byte sharedA[1024];
byte sharedB[1024];
#if !defined(NO_ASN) || \
( !defined(NO_SHA) && ((defined(HAVE_ECC192) && defined(HAVE_ECC224)) \
|| defined(HAVE_ALL_CURVES)))
byte sig[1024];
int verify;
#endif
byte digest[20];
#ifdef HAVE_ECC_KEY_EXPORT
byte exportBuf[1024];
#elif !defined(NO_ECC256)
/* Export is used to test import, so if export is not enabled,
use this pre-defined value (P-256 Only) */
const byte exportBuf[] = {
0x04, 0xb6, 0x1f, 0xf9, 0x71, 0xe3, 0x5b, 0x8d, 0xa7, 0xad, 0x9c, 0xd8,
0x8f, 0x25, 0x09, 0xe7, 0x3f, 0x91, 0x10, 0xe5, 0x4e, 0x84, 0x5d, 0xee,
0xe8, 0xc6, 0x9c, 0xd9, 0x84, 0x8e, 0xd9, 0x85, 0x0d, 0x73, 0x7f, 0x6e,
0x63, 0x9a, 0x74, 0xe0, 0x1b, 0x6c, 0x55, 0x2f, 0xdd, 0xc6, 0x16, 0x72,
0x52, 0x75, 0x6c, 0x12, 0x77, 0x38, 0x56, 0xf2, 0x20, 0xef, 0xe5, 0x76,
0x59, 0x0d, 0x97, 0xd9, 0x94,
};
#endif
word32 x, y;
int i, ret;
#if defined(HAVE_ECC_VECTOR_TEST) || defined(HAVE_ECC_SIGN)
byte sig[1024];
#endif /* HAVE_ECC_VECTOR_TEST || HAVE_ECC_SIGN */
#if defined(HAVE_ECC_SIGN)
byte digest[20];
int i;
#ifdef HAVE_ECC_VERIFY
int verify;
#endif /* HAVE_ECC_VERIFY */
#endif /* HAVE_ECC_SIGN */
int ret;
ecc_key userA, userB, pubKey;
ret = wc_InitRng(&rng);
@ -6199,7 +6306,6 @@ int ecc_test(void)
wc_ecc_init(&pubKey);
ret = wc_ecc_make_key(&rng, 32, &userA);
if (ret != 0)
return -1014;
@ -6208,19 +6314,17 @@ int ecc_test(void)
return -1024;
ret = wc_ecc_make_key(&rng, 32, &userB);
if (ret != 0)
return -1002;
#ifdef HAVE_ECC_DHE
x = sizeof(sharedA);
ret = wc_ecc_shared_secret(&userA, &userB, sharedA, &x);
if (ret != 0)
return -1015;
y = sizeof(sharedB);
ret = wc_ecc_shared_secret(&userB, &userA, sharedB, &y);
if (ret != 0)
return -1003;
@ -6229,162 +6333,238 @@ int ecc_test(void)
if (memcmp(sharedA, sharedB, x))
return -1005;
#endif /* HAVE_ECC_DHE */
#if defined(HAVE_ECC_KEY_EXPORT) || (defined(HAVE_ECC_KEY_IMPORT) && !defined(NO_ECC256))
x = sizeof(exportBuf);
#ifdef HAVE_ECC_KEY_EXPORT
ret = wc_ecc_export_x963(&userA, exportBuf, &x);
if (ret != 0)
return -1006;
#endif /* HAVE_ECC_KEY_EXPORT */
#if defined(HAVE_ECC_KEY_IMPORT) && (defined(HAVE_ECC_KEY_EXPORT) || !defined(NO_ECC256))
ret = wc_ecc_import_x963(exportBuf, x, &pubKey);
if (ret != 0)
return -1007;
#endif
#if defined(HAVE_ECC_DHE) && defined(HAVE_ECC_KEY_IMPORT) && defined(HAVE_ECC_KEY_EXPORT)
y = sizeof(sharedB);
ret = wc_ecc_shared_secret(&userB, &pubKey, sharedB, &y);
if (ret != 0)
return -1008;
if (memcmp(sharedA, sharedB, y))
return -1009;
#endif /* HAVE_ECC_DHE */
#endif
#ifdef HAVE_COMP_KEY
/* try compressed export / import too */
x = sizeof(exportBuf);
#ifdef HAVE_ECC_KEY_EXPORT
ret = wc_ecc_export_x963_ex(&userA, exportBuf, &x, 1);
if (ret != 0)
return -1010;
wc_ecc_free(&pubKey);
wc_ecc_init(&pubKey);
#if HAVE_ECC_KEY_IMPORT
ret = wc_ecc_import_x963(exportBuf, x, &pubKey);
if (ret != 0)
return -1011;
#endif
#endif /* HAVE_ECC_KEY_IMPORT */
#endif /* HAVE_ECC_KEY_EXPORT */
#if defined(HAVE_ECC_DHE) && defined(HAVE_ECC_KEY_IMPORT) && defined(HAVE_ECC_KEY_EXPORT)
y = sizeof(sharedB);
ret = wc_ecc_shared_secret(&userB, &pubKey, sharedB, &y);
if (ret != 0)
return -1012;
if (memcmp(sharedA, sharedB, y))
return -1013;
#endif /* HAVE_ECC_DHE */
#endif /* HAVE_COMP_KEY */
#ifdef HAVE_ECC_SIGN
/* test DSA sign hash */
for (i = 0; i < (int)sizeof(digest); i++)
digest[i] = (byte)i;
#ifndef NO_ASN
x = sizeof(sig);
ret = wc_ecc_sign_hash(digest, sizeof(digest), sig, &x, &rng, &userA);
if (ret != 0)
return -1014;
#ifdef HAVE_ECC_VERIFY
verify = 0;
ret = wc_ecc_verify_hash(sig, x, digest, sizeof(digest), &verify, &userA);
if (ret != 0)
return -1015;
if (verify != 1)
return -1016;
#endif
#endif /* HAVE_ECC_VERIFY */
#endif /* HAVE_ECC_SIGN */
#ifdef HAVE_ECC_KEY_EXPORT
x = sizeof(exportBuf);
ret = wc_ecc_export_private_only(&userA, exportBuf, &x);
if (ret != 0)
return -1017;
#endif /* HAVE_ECC_KEY_EXPORT */
#if !defined(NO_SHA) && \
((defined(HAVE_ECC192) && defined(HAVE_ECC224)) || defined(HAVE_ALL_CURVES))
#ifdef HAVE_ECC_VECTOR_TEST
#if defined(HAVE_ECC192) || defined(HAVE_ALL_CURVES)
{
/* test raw ECC key import */
Sha sha;
byte hash[SHA_DIGEST_SIZE];
rawEccVector a, b;
rawEccVector test_ecc[2];
int times = sizeof(test_ecc) / sizeof(rawEccVector);
rawEccVector ecc192;
/* first [P-192,SHA-1] vector from FIPS 186-3 NIST vectors */
a.msg = "\xeb\xf7\x48\xd7\x48\xeb\xbc\xa7\xd2\x9f\xb4\x73\x69\x8a"
"\x6e\x6b\x4f\xb1\x0c\x86\x5d\x4a\xf0\x24\xcc\x39\xae\x3d"
"\xf3\x46\x4b\xa4\xf1\xd6\xd4\x0f\x32\xbf\x96\x18\xa9\x1b"
"\xb5\x98\x6f\xa1\xa2\xaf\x04\x8a\x0e\x14\xdc\x51\xe5\x26"
"\x7e\xb0\x5e\x12\x7d\x68\x9d\x0a\xc6\xf1\xa7\xf1\x56\xce"
"\x06\x63\x16\xb9\x71\xcc\x7a\x11\xd0\xfd\x7a\x20\x93\xe2"
"\x7c\xf2\xd0\x87\x27\xa4\xe6\x74\x8c\xc3\x2f\xd5\x9c\x78"
"\x10\xc5\xb9\x01\x9d\xf2\x1c\xdc\xc0\xbc\xa4\x32\xc0\xa3"
"\xee\xd0\x78\x53\x87\x50\x88\x77\x11\x43\x59\xce\xe4\xa0"
"\x71\xcf";
a.msgLen = 128;
a.Qx = "07008ea40b08dbe76432096e80a2494c94982d2d5bcf98e6";
a.Qy = "76fab681d00b414ea636ba215de26d98c41bd7f2e4d65477";
a.d = "e14f37b3d1374ff8b03f41b9b3fdd2f0ebccf275d660d7f3";
a.R = "6994d962bdd0d793ffddf855ec5bf2f91a9698b46258a63e";
a.S = "02ba6465a234903744ab02bc8521405b73cf5fc00e1a9f41";
a.curveName = "ECC-192";
#if 1
ecc192.msg = "\x60\x80\x79\x42\x3f\x12\x42\x1d\xe6\x16\xb7\x49\x3e\xbe\x55\x1c\xf4\xd6\x5b\x92";
ecc192.msgLen = 20;
#else
/* This is the raw message prior to SHA-1 */
ecc192.msg =
"\xeb\xf7\x48\xd7\x48\xeb\xbc\xa7\xd2\x9f\xb4\x73\x69\x8a\x6e\x6b"
"\x4f\xb1\x0c\x86\x5d\x4a\xf0\x24\xcc\x39\xae\x3d\xf3\x46\x4b\xa4"
"\xf1\xd6\xd4\x0f\x32\xbf\x96\x18\xa9\x1b\xb5\x98\x6f\xa1\xa2\xaf"
"\x04\x8a\x0e\x14\xdc\x51\xe5\x26\x7e\xb0\x5e\x12\x7d\x68\x9d\x0a"
"\xc6\xf1\xa7\xf1\x56\xce\x06\x63\x16\xb9\x71\xcc\x7a\x11\xd0\xfd"
"\x7a\x20\x93\xe2\x7c\xf2\xd0\x87\x27\xa4\xe6\x74\x8c\xc3\x2f\xd5"
"\x9c\x78\x10\xc5\xb9\x01\x9d\xf2\x1c\xdc\xc0\xbc\xa4\x32\xc0\xa3"
"\xee\xd0\x78\x53\x87\x50\x88\x77\x11\x43\x59\xce\xe4\xa0\x71\xcf";
ecc192.msgLen = 128;
#endif
ecc192.Qx = "07008ea40b08dbe76432096e80a2494c94982d2d5bcf98e6";
ecc192.Qy = "76fab681d00b414ea636ba215de26d98c41bd7f2e4d65477";
ecc192.d = "e14f37b3d1374ff8b03f41b9b3fdd2f0ebccf275d660d7f3";
ecc192.R = "6994d962bdd0d793ffddf855ec5bf2f91a9698b46258a63e";
ecc192.S = "02ba6465a234903744ab02bc8521405b73cf5fc00e1a9f41";
ecc192.curveName = "ECC-192";
ret = ecc_test_raw_vector(&ecc192, &userA, sig, sizeof(sig));
}
#endif /* HAVE_ECC192 */
#if defined(HAVE_ECC224) || defined(HAVE_ALL_CURVES)
{
rawEccVector ecc224;
/* first [P-224,SHA-1] vector from FIPS 186-3 NIST vectors */
b.msg = "\x36\xc8\xb2\x29\x86\x48\x7f\x67\x7c\x18\xd0\x97\x2a\x9e"
"\x20\x47\xb3\xaf\xa5\x9e\xc1\x62\x76\x4e\xc3\x0b\x5b\x69"
"\xe0\x63\x0f\x99\x0d\x4e\x05\xc2\x73\xb0\xe5\xa9\xd4\x28"
"\x27\xb6\x95\xfc\x2d\x64\xd9\x13\x8b\x1c\xf4\xc1\x21\x55"
"\x89\x4c\x42\x13\x21\xa7\xbb\x97\x0b\xdc\xe0\xfb\xf0\xd2"
"\xae\x85\x61\xaa\xd8\x71\x7f\x2e\x46\xdf\xe3\xff\x8d\xea"
"\xb4\xd7\x93\x23\x56\x03\x2c\x15\x13\x0d\x59\x9e\x26\xc1"
"\x0f\x2f\xec\x96\x30\x31\xac\x69\x38\xa1\x8d\x66\x45\x38"
"\xb9\x4d\xac\x55\x34\xef\x7b\x59\x94\x24\xd6\x9b\xe1\xf7"
"\x1c\x20";
b.msgLen = 128;
b.Qx = "8a4dca35136c4b70e588e23554637ae251077d1365a6ba5db9585de7";
b.Qy = "ad3dee06de0be8279d4af435d7245f14f3b4f82eb578e519ee0057b1";
b.d = "97c4b796e1639dd1035b708fc00dc7ba1682cec44a1002a1a820619f";
b.R = "147b33758321e722a0360a4719738af848449e2c1d08defebc1671a7";
b.S = "24fc7ed7f1352ca3872aa0916191289e2e04d454935d50fe6af3ad5b";
b.curveName = "ECC-224";
test_ecc[0] = a;
test_ecc[1] = b;
for (i = 0; i < times; i++) {
wc_ecc_free(&userA);
wc_ecc_init(&userA);
memset(sig, 0, sizeof(sig));
x = sizeof(sig);
/* calculate SHA-1 hash of message */
ret = wc_InitSha(&sha);
if (ret != 0)
return -1015 - i;
wc_ShaUpdate(&sha, (byte*)test_ecc[i].msg, (word32)test_ecc[i].msgLen);
wc_ShaFinal(&sha, hash);
ret = wc_ecc_import_raw(&userA, test_ecc[i].Qx, test_ecc[i].Qy,
test_ecc[i].d, test_ecc[i].curveName);
if (ret != 0)
return -1017 - i;
ret = wc_ecc_rs_to_sig(test_ecc[i].R, test_ecc[i].S, sig, &x);
if (ret != 0)
return -1019 - i;
ret = wc_ecc_verify_hash(sig, x, hash, sizeof(hash), &verify, &userA);
if (ret != 0)
return -1021 - i;
if (verify != 1)
return -1023 - i;
#if 1
ecc224.msg = "\xb9\xa3\xb8\x6d\xb0\xba\x99\xfd\xc6\xd2\x94\x6b\xfe\xbe\x9c\xe8\x3f\x10\x74\xfc";
ecc224.msgLen = 20;
#else
/* This is the raw message prior to SHA-1 */
ecc224.msg =
"\x36\xc8\xb2\x29\x86\x48\x7f\x67\x7c\x18\xd0\x97\x2a\x9e\x20\x47"
"\xb3\xaf\xa5\x9e\xc1\x62\x76\x4e\xc3\x0b\x5b\x69\xe0\x63\x0f\x99"
"\x0d\x4e\x05\xc2\x73\xb0\xe5\xa9\xd4\x28\x27\xb6\x95\xfc\x2d\x64"
"\xd9\x13\x8b\x1c\xf4\xc1\x21\x55\x89\x4c\x42\x13\x21\xa7\xbb\x97"
"\x0b\xdc\xe0\xfb\xf0\xd2\xae\x85\x61\xaa\xd8\x71\x7f\x2e\x46\xdf"
"\xe3\xff\x8d\xea\xb4\xd7\x93\x23\x56\x03\x2c\x15\x13\x0d\x59\x9e"
"\x26\xc1\x0f\x2f\xec\x96\x30\x31\xac\x69\x38\xa1\x8d\x66\x45\x38"
"\xb9\x4d\xac\x55\x34\xef\x7b\x59\x94\x24\xd6\x9b\xe1\xf7\x1c\x20";
ecc224.msgLen = 128;
#endif
ecc224.Qx = "8a4dca35136c4b70e588e23554637ae251077d1365a6ba5db9585de7";
ecc224.Qy = "ad3dee06de0be8279d4af435d7245f14f3b4f82eb578e519ee0057b1";
ecc224.d = "97c4b796e1639dd1035b708fc00dc7ba1682cec44a1002a1a820619f";
ecc224.R = "147b33758321e722a0360a4719738af848449e2c1d08defebc1671a7";
ecc224.S = "24fc7ed7f1352ca3872aa0916191289e2e04d454935d50fe6af3ad5b";
ecc224.curveName = "ECC-224";
ret = ecc_test_raw_vector(&ecc224, &userA, sig, sizeof(sig));
}
#endif /* HAVE_ECC192 */
#if !defined(NO_ECC256) || defined(HAVE_ALL_CURVES)
{
rawEccVector ecc256;
/* first [P-256,SHA-1] vector from FIPS 186-3 NIST vectors */
#if 1
ecc256.msg = "\xa3\xf9\x1a\xe2\x1b\xa6\xb3\x03\x98\x64\x47\x2f\x18\x41\x44\xc6\xaf\x62\xcd\x0e";
ecc256.msgLen = 20;
#else
/* This is the raw message prior to SHA-1 */
ecc256.msg =
"\xa2\x4b\x21\x76\x2e\x6e\xdb\x15\x3c\xc1\x14\x38\xdb\x0e\x92\xcd"
"\xf5\x2b\x86\xb0\x6c\xa9\x70\x16\x06\x27\x59\xc7\x0d\x36\xd1\x56"
"\x2c\xc9\x63\x0d\x7f\xc7\xc7\x74\xb2\x8b\x54\xe3\x1e\xf5\x58\x72"
"\xb2\xa6\x5d\xf1\xd7\xec\x26\xde\xbb\x33\xe7\xd9\x27\xef\xcc\xf4"
"\x6b\x63\xde\x52\xa4\xf4\x31\xea\xca\x59\xb0\x5d\x2e\xde\xc4\x84"
"\x5f\xff\xc0\xee\x15\x03\x94\xd6\x1f\x3d\xfe\xcb\xcd\xbf\x6f\x5a"
"\x73\x38\xd0\xbe\x3f\x2a\x77\x34\x51\x98\x3e\xba\xeb\x48\xf6\x73"
"\x8f\xc8\x95\xdf\x35\x7e\x1a\x48\xa6\x53\xbb\x35\x5a\x31\xa1\xb4"
ecc256.msgLen = 128;
#endif
ecc256.Qx = "fa2737fb93488d19caef11ae7faf6b7f4bcd67b286e3fc54e8a65c2b74aeccb0";
ecc256.Qy = "d4ccd6dae698208aa8c3a6f39e45510d03be09b2f124bfc067856c324f9b4d09";
ecc256.d = "be34baa8d040a3b991f9075b56ba292f755b90e4b6dc10dad36715c33cfdac25";
ecc256.R = "2b826f5d44e2d0b6de531ad96b51e8f0c56fdfead3c236892e4d84eacfc3b75c";
ecc256.S = "a2248b62c03db35a7cd63e8a120a3521a89d3d2f61ff99035a2148ae32e3a248";
ecc256.curveName = "nistp256";
ret = ecc_test_raw_vector(&ecc256, &userA, sig, sizeof(sig));
}
#endif /* defined(HAVE_ECC192) && defined(HAVE_ECC256) */
#endif /* !NO_ECC256 */
#if defined(HAVE_ECC384) || defined(HAVE_ALL_CURVES)
{
rawEccVector ecc384;
/* first [P-384,SHA-1] vector from FIPS 186-3 NIST vectors */
#if 1
ecc384.msg = "\x9b\x9f\x8c\x95\x35\xa5\xca\x26\x60\x5d\xb7\xf2\xfa\x57\x3b\xdf\xc3\x2e\xab\x8b";
ecc384.msgLen = 20;
#else
/* This is the raw message prior to SHA-1 */
ecc384.msg =
"\xab\xe1\x0a\xce\x13\xe7\xe1\xd9\x18\x6c\x48\xf7\x88\x9d\x51\x47"
"\x3d\x3a\x09\x61\x98\x4b\xc8\x72\xdf\x70\x8e\xcc\x3e\xd3\xb8\x16"
"\x9d\x01\xe3\xd9\x6f\xc4\xf1\xd5\xea\x00\xa0\x36\x92\xbc\xc5\xcf"
"\xfd\x53\x78\x7c\x88\xb9\x34\xaf\x40\x4c\x03\x9d\x32\x89\xb5\xba"
"\xc5\xae\x7d\xb1\x49\x68\x75\xb5\xdc\x73\xc3\x09\xf9\x25\xc1\x3d"
"\x1c\x01\xab\xda\xaf\xeb\xcd\xac\x2c\xee\x43\x39\x39\xce\x8d\x4a"
"\x0a\x5d\x57\xbb\x70\x5f\x3b\xf6\xec\x08\x47\x95\x11\xd4\xb4\xa3"
"\x21\x1f\x61\x64\x9a\xd6\x27\x43\x14\xbf\x0d\x43\x8a\x81\xe0\x60"
ecc384.msgLen = 128;
#endif
ecc384.Qx = "e55fee6c49d8d523f5ce7bf9c0425ce4ff650708b7de5cfb095901523979a7f042602db30854735369813b5c3f5ef868";
ecc384.Qy = "28f59cc5dc509892a988d38a8e2519de3d0c4fd0fbdb0993e38f18506c17606c5e24249246f1ce94983a5361c5be983e";
ecc384.d = "a492ce8fa90084c227e1a32f7974d39e9ff67a7e8705ec3419b35fb607582bebd461e0b1520ac76ec2dd4e9b63ebae71";
ecc384.R = "6820b8585204648aed63bdff47f6d9acebdea62944774a7d14f0e14aa0b9a5b99545b2daee6b3c74ebf606667a3f39b7";
ecc384.S = "491af1d0cccd56ddd520b233775d0bc6b40a6255cc55207d8e9356741f23c96c14714221078dbd5c17f4fdd89b32a907";
ecc384.curveName = "nistp384";
ret = ecc_test_raw_vector(&ecc384, &userA, sig, sizeof(sig));
}
#endif /* HAVE_ECC384 */
#if defined(HAVE_ECC521) || defined(HAVE_ALL_CURVES)
{
rawEccVector ecc521;
/* first [P-521,SHA-1] vector from FIPS 186-3 NIST vectors */
#if 1
ecc521.msg = "\x1b\xf7\x03\x9c\xca\x23\x94\x27\x3f\x11\xa1\xd4\x8d\xcc\xb4\x46\x6f\x31\x61\xdf";
ecc521.msgLen = 20;
#else
/* This is the raw message prior to SHA-1 */
ecc521.msg =
"\x50\x3f\x79\x39\x34\x0a\xc7\x23\xcd\x4a\x2f\x4e\x6c\xcc\x27\x33"
"\x38\x3a\xca\x2f\xba\x90\x02\x19\x9d\x9e\x1f\x94\x8b\xe0\x41\x21"
"\x07\xa3\xfd\xd5\x14\xd9\x0c\xd4\xf3\x7c\xc3\xac\x62\xef\x00\x3a"
"\x2d\xb1\xd9\x65\x7a\xb7\x7f\xe7\x55\xbf\x71\xfa\x59\xe4\xd9\x6e"
"\xa7\x2a\xe7\xbf\x9d\xe8\x7d\x79\x34\x3b\xc1\xa4\xbb\x14\x4d\x16"
"\x28\xd1\xe9\xe9\xc8\xed\x80\x8b\x96\x2c\x54\xe5\xf9\x6d\x53\xda"
"\x14\x7a\x96\x38\xf9\x4a\x91\x75\xd8\xed\x61\x05\x5f\x0b\xa5\x73"
"\xa8\x2b\xb7\xe0\x18\xee\xda\xc4\xea\x7b\x36\x2e\xc8\x9c\x38\x2b"
ecc521.msgLen = 128;
#endif
ecc521.Qx = "12fbcaeffa6a51f3ee4d3d2b51c5dec6d7c726ca353fc014ea2bf7cfbb9b910d32cbfa6a00fe39b6cdb8946f22775398b2e233c0cf144d78c8a7742b5c7a3bb5d23";
ecc521.Qy = "09cdef823dd7bf9a79e8cceacd2e4527c231d0ae5967af0958e931d7ddccf2805a3e618dc3039fec9febbd33052fe4c0fee98f033106064982d88f4e03549d4a64d";
ecc521.d = "1bd56bd106118eda246155bd43b42b8e13f0a6e25dd3bb376026fab4dc92b6157bc6dfec2d15dd3d0cf2a39aa68494042af48ba9601118da82c6f2108a3a203ad74";
ecc521.R = "0bd117b4807710898f9dd7778056485777668f0e78e6ddf5b000356121eb7a220e9493c7f9a57c077947f89ac45d5acb6661bbcd17abb3faea149ba0aa3bb1521be";
ecc521.S = "019cd2c5c3f9870ecdeb9b323abdf3a98cd5e231d85c6ddc5b71ab190739f7f226e6b134ba1d5889ddeb2751dabd97911dff90c34684cdbe7bb669b6c3d22f2480c";
ecc521.curveName = "nistp521";
ret = ecc_test_raw_vector(&ecc521, &userA, sig, sizeof(sig));
}
#endif /* HAVE_ECC521 */
if (ret != 0) {
return ret;
}
#endif /* HAVE_ECC_VECTOR_TEST */
#ifdef WOLFSSL_KEY_GEN
{
@ -6574,12 +6754,18 @@ int ecc_encrypt_test(void)
int curve25519_test(void)
{
WC_RNG rng;
#ifdef HAVE_CURVE25519_SHARED_SECRET
byte sharedA[32];
byte sharedB[32];
word32 y;
#endif
#ifdef HAVE_CURVE25519_KEY_EXPORT
byte exportBuf[32];
word32 x, y;
#endif
word32 x;
curve25519_key userA, userB, pubKey;
#if defined(HAVE_CURVE25519_SHARED_SECRET) && defined(HAVE_CURVE25519_KEY_IMPORT)
/* test vectors from
https://tools.ietf.org/html/draft-josefsson-tls-curve25519-03
*/
@ -6623,6 +6809,7 @@ int curve25519_test(void)
0x73,0x8B,0x99,0xF0,0x94,0x68,0xB8,0xD6,
0xB8,0x51,0x11,0x84,0xD5,0x34,0x94,0xAB
};
#endif /* HAVE_CURVE25519_SHARED_SECRET */
if (wc_InitRng(&rng) != 0)
return -1001;
@ -6638,6 +6825,7 @@ int curve25519_test(void)
if (wc_curve25519_make_key(&rng, 32, &userB) != 0)
return -1003;
#ifdef HAVE_CURVE25519_SHARED_SECRET
/* find shared secret key */
x = sizeof(sharedA);
if (wc_curve25519_shared_secret(&userA, &userB, sharedA, &x) != 0)
@ -6653,15 +6841,21 @@ int curve25519_test(void)
if (XMEMCMP(sharedA, sharedB, x))
return -1007;
#endif
#ifdef HAVE_CURVE25519_KEY_EXPORT
/* export a public key and import it for another user */
x = sizeof(exportBuf);
if (wc_curve25519_export_public(&userA, exportBuf, &x) != 0)
return -1008;
#ifdef HAVE_CURVE25519_KEY_IMPORT
if (wc_curve25519_import_public(exportBuf, x, &pubKey) != 0)
return -1009;
#endif
#endif
#if defined(HAVE_CURVE25519_SHARED_SECRET) && defined(HAVE_CURVE25519_KEY_IMPORT)
/* test shared key after importing a public key */
XMEMSET(sharedB, 0, sizeof(sharedB));
y = sizeof(sharedB);
@ -6720,6 +6914,7 @@ int curve25519_test(void)
if (XMEMCMP(sharedA, sharedB, x))
return -1023;
#endif /* HAVE_CURVE25519_SHARED_SECRET */
/* clean up keys when done */
wc_curve25519_free(&pubKey);
@ -6737,17 +6932,25 @@ int curve25519_test(void)
int ed25519_test(void)
{
WC_RNG rng;
#if defined(HAVE_ED25519_SIGN) && defined(HAVE_ED25519_KEY_EXPORT) &&\
defined(HAVE_ED25519_KEY_IMPORT)
byte out[ED25519_SIG_SIZE];
byte exportPKey[ED25519_KEY_SIZE];
byte exportSKey[ED25519_KEY_SIZE];
word32 outlen;
word32 exportPSz;
word32 exportSSz;
int i;
word32 outlen;
#ifdef HAVE_ED25519_VERIFY
int verify;
#endif /* HAVE_ED25519_VERIFY */
#endif /* HAVE_ED25519_SIGN && HAVE_ED25519_KEY_EXPORT && HAVE_ED25519_KEY_IMPORT */
word32 keySz, sigSz;
int i, verify;
ed25519_key key;
ed25519_key key2;
#if defined(HAVE_ED25519_SIGN) && defined(HAVE_ED25519_KEY_EXPORT) && \
defined(HAVE_ED25519_KEY_IMPORT)
/* test vectors from
https://tools.ietf.org/html/draft-josefsson-eddsa-ed25519-02
*/
@ -7060,6 +7263,7 @@ int ed25519_test(void)
static const byte* msgs[] = { msg1, msg2, msg3, msg1, msg1, msg4};
static const word16 msgSz[] = {0 /*sizeof(msg1)*/, sizeof(msg2), sizeof(msg3),
0 /*sizeof(msg1)*/, 0 /*sizeof(msg1)*/, sizeof(msg4)};
#endif /* HAVE_ED25519_SIGN && HAVE_ED25519_KEY_EXPORT && HAVE_ED25519_KEY_IMPORT */
/* create ed25519 keys */
wc_InitRng(&rng);
@ -7072,6 +7276,8 @@ int ed25519_test(void)
keySz = wc_ed25519_size(&key);
sigSz = wc_ed25519_sig_size(&key);
#if defined(HAVE_ED25519_SIGN) && defined(HAVE_ED25519_KEY_EXPORT) &&\
defined(HAVE_ED25519_KEY_IMPORT)
for (i = 0; i < 6; i++) {
outlen = sizeof(out);
XMEMSET(out, 0, sizeof(out));
@ -7087,6 +7293,7 @@ int ed25519_test(void)
if (XMEMCMP(out, sigs[i], 64))
return -1033 - i;
#if defined(HAVE_ED25519_VERIFY)
/* test verify on good msg */
if (wc_ed25519_verify_msg(out, outlen, msgs[i], msgSz[i], &verify,
&key) != 0 || verify != 1)
@ -7097,6 +7304,7 @@ int ed25519_test(void)
if (wc_ed25519_verify_msg(out, outlen, msgs[i], msgSz[i], &verify,
&key) == 0 || verify == 1)
return -1045 - i;
#endif /* HAVE_ED25519_VERIFY */
/* test api for import/exporting keys */
exportPSz = sizeof(exportPKey);
@ -7120,13 +7328,16 @@ int ed25519_test(void)
if (wc_ed25519_sign_msg(msgs[i], msgSz[i], out, &outlen, &key2) != 0)
return -1075 - i;
#if defined(HAVE_ED25519_VERIFY)
if (wc_ed25519_verify_msg(out, outlen, msgs[i], msgSz[i], &verify,
&key2) != 0 || verify != 1)
return -1081 - i;
if (XMEMCMP(out, sigs[i], 64))
return -1087 - i;
#endif /* HAVE_ED25519_VERIFY */
}
#endif /* HAVE_ED25519_SIGN && HAVE_ED25519_KEY_EXPORT && HAVE_ED25519_KEY_IMPORT */
/* clean up keys when done */
wc_ed25519_free(&key);

View File

@ -18,7 +18,8 @@ nobase_include_HEADERS+= \
wolfssl/version.h \
wolfssl/options.h \
wolfssl/ocsp.h \
wolfssl/crl.h
wolfssl/crl.h \
wolfssl/mem_track.h
noinst_HEADERS+= \
wolfssl/internal.h

157
wolfssl/mem_track.h 100644
View File

@ -0,0 +1,157 @@
/* mem_track.h
*
* Copyright (C) 2006-2015 wolfSSL Inc.
*
* This file is part of wolfSSL. (formerly known as CyaSSL)
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifndef WOLFSSL_MEM_TRACK_H
#define WOLFSSL_MEM_TRACK_H
#ifdef USE_WOLFSSL_MEMORY
#include "wolfssl/wolfcrypt/logging.h"
typedef struct memoryStats {
size_t totalAllocs; /* number of allocations */
size_t totalBytes; /* total number of bytes allocated */
size_t peakBytes; /* concurrent max bytes */
size_t currentBytes; /* total current bytes in use */
} memoryStats;
typedef struct memHint {
size_t thisSize; /* size of this memory */
void* thisMemory; /* actual memory for user */
} memHint;
typedef struct memoryTrack {
union {
memHint hint;
byte alignit[16]; /* make sure we have strong alignment */
} u;
} memoryTrack;
#if defined(WOLFSSL_TRACK_MEMORY)
#define DO_MEM_STATS
static memoryStats ourMemStats;
#endif
static INLINE void* TrackMalloc(size_t sz)
{
memoryTrack* mt;
if (sz == 0)
return NULL;
mt = (memoryTrack*)malloc(sizeof(memoryTrack) + sz);
if (mt == NULL)
return NULL;
mt->u.hint.thisSize = sz;
mt->u.hint.thisMemory = (byte*)mt + sizeof(memoryTrack);
#ifdef DO_MEM_STATS
ourMemStats.totalAllocs++;
ourMemStats.totalBytes += sz;
ourMemStats.currentBytes += sz;
if (ourMemStats.currentBytes > ourMemStats.peakBytes)
ourMemStats.peakBytes = ourMemStats.currentBytes;
#endif
return mt->u.hint.thisMemory;
}
static INLINE void TrackFree(void* ptr)
{
memoryTrack* mt;
if (ptr == NULL) {
return;
}
mt = (memoryTrack*)ptr;
--mt; /* same as minus sizeof(memoryTrack), removes header */
#ifdef DO_MEM_STATS
ourMemStats.currentBytes -= mt->u.hint.thisSize;
#endif
free(mt);
}
static INLINE void* TrackRealloc(void* ptr, size_t sz)
{
void* ret = TrackMalloc(sz);
if (ptr) {
/* if realloc is bigger, don't overread old ptr */
memoryTrack* mt = (memoryTrack*)ptr;
--mt; /* same as minus sizeof(memoryTrack), removes header */
if (mt->u.hint.thisSize < sz)
sz = mt->u.hint.thisSize;
}
if (ret && ptr)
memcpy(ret, ptr, sz);
if (ret)
TrackFree(ptr);
return ret;
}
static INLINE int InitMemoryTracker(void)
{
int ret = 0;
ret = wolfSSL_SetAllocators(TrackMalloc, TrackFree, TrackRealloc);
if (ret != 0) {
WOLFSSL_MSG("wolfSSL SetAllocators failed for track memory");
return ret;
}
#ifdef DO_MEM_STATS
ourMemStats.totalAllocs = 0;
ourMemStats.totalBytes = 0;
ourMemStats.peakBytes = 0;
ourMemStats.currentBytes = 0;
#endif
return ret;
}
static INLINE void ShowMemoryTracker(void)
{
#ifdef DO_MEM_STATS
printf("total Allocs = %9lu\n",
(unsigned long)ourMemStats.totalAllocs);
printf("total Bytes = %9lu\n",
(unsigned long)ourMemStats.totalBytes);
printf("peak Bytes = %9lu\n",
(unsigned long)ourMemStats.peakBytes);
printf("current Bytes = %9lu\n",
(unsigned long)ourMemStats.currentBytes);
#endif
}
#endif /* USE_WOLFSSL_MEMORY */
#endif /* WOLFSSL_MEM_TRACK_H */

View File

@ -10,6 +10,7 @@
#include <wolfssl/wolfcrypt/types.h>
#include <wolfssl/wolfcrypt/error-crypt.h>
#include <wolfssl/wolfcrypt/random.h>
#include <wolfssl/mem_track.h>
#ifdef ATOMIC_USER
#include <wolfssl/wolfcrypt/aes.h>
@ -1246,129 +1247,6 @@ static INLINE int OpenNitroxDevice(int dma_mode,int dev_id)
}
#endif /* !defined(WOLFSSL_MDK_ARM) && !defined(WOLFSSL_KEIL_FS) && !defined(WOLFSSL_TIRTOS) */
#ifdef USE_WOLFSSL_MEMORY
typedef struct memoryStats {
size_t totalAllocs; /* number of allocations */
size_t totalBytes; /* total number of bytes allocated */
size_t peakBytes; /* concurrent max bytes */
size_t currentBytes; /* total current bytes in use */
} memoryStats;
typedef struct memHint {
size_t thisSize; /* size of this memory */
void* thisMemory; /* actual memory for user */
} memHint;
typedef struct memoryTrack {
union {
memHint hint;
byte alignit[16]; /* make sure we have strong alignment */
} u;
} memoryTrack;
#if defined(WOLFSSL_TRACK_MEMORY)
#define DO_MEM_STATS
static memoryStats ourMemStats;
#endif
static INLINE void* TrackMalloc(size_t sz)
{
memoryTrack* mt;
if (sz == 0)
return NULL;
mt = (memoryTrack*)malloc(sizeof(memoryTrack) + sz);
if (mt == NULL)
return NULL;
mt->u.hint.thisSize = sz;
mt->u.hint.thisMemory = (byte*)mt + sizeof(memoryTrack);
#ifdef DO_MEM_STATS
ourMemStats.totalAllocs++;
ourMemStats.totalBytes += sz;
ourMemStats.currentBytes += sz;
if (ourMemStats.currentBytes > ourMemStats.peakBytes)
ourMemStats.peakBytes = ourMemStats.currentBytes;
#endif
return mt->u.hint.thisMemory;
}
static INLINE void TrackFree(void* ptr)
{
memoryTrack* mt;
if (ptr == NULL)
return;
mt = (memoryTrack*)ptr;
--mt; /* same as minus sizeof(memoryTrack), removes header */
#ifdef DO_MEM_STATS
ourMemStats.currentBytes -= mt->u.hint.thisSize;
#endif
free(mt);
}
static INLINE void* TrackRealloc(void* ptr, size_t sz)
{
void* ret = TrackMalloc(sz);
if (ptr) {
/* if realloc is bigger, don't overread old ptr */
memoryTrack* mt = (memoryTrack*)ptr;
--mt; /* same as minus sizeof(memoryTrack), removes header */
if (mt->u.hint.thisSize < sz)
sz = mt->u.hint.thisSize;
}
if (ret && ptr)
memcpy(ret, ptr, sz);
if (ret)
TrackFree(ptr);
return ret;
}
static INLINE void InitMemoryTracker(void)
{
if (wolfSSL_SetAllocators(TrackMalloc, TrackFree, TrackRealloc) != 0)
err_sys("wolfSSL SetAllocators failed for track memory");
#ifdef DO_MEM_STATS
ourMemStats.totalAllocs = 0;
ourMemStats.totalBytes = 0;
ourMemStats.peakBytes = 0;
ourMemStats.currentBytes = 0;
#endif
}
static INLINE void ShowMemoryTracker(void)
{
#ifdef DO_MEM_STATS
printf("total Allocs = %9lu\n",
(unsigned long)ourMemStats.totalAllocs);
printf("total Bytes = %9lu\n",
(unsigned long)ourMemStats.totalBytes);
printf("peak Bytes = %9lu\n",
(unsigned long)ourMemStats.peakBytes);
printf("current Bytes = %9lu\n",
(unsigned long)ourMemStats.currentBytes);
#endif
}
#endif /* USE_WOLFSSL_MEMORY */
#ifdef HAVE_STACK_SIZE
typedef THREAD_RETURN WOLFSSL_THREAD (*thread_func)(void* args);

View File

@ -59,4 +59,5 @@ nobase_include_HEADERS+= \
noinst_HEADERS+= \
wolfssl/wolfcrypt/port/pic32/pic32mz-crypt.h \
wolfssl/wolfcrypt/port/ti/ti-hash.h \
wolfssl/wolfcrypt/port/ti/ti-ccm.h
wolfssl/wolfcrypt/port/ti/ti-ccm.h \
wolfssl/wolfcrypt/port/nrf51.h

View File

@ -0,0 +1,43 @@
/* nrf51.h
*
* Copyright (C) 2006-2015 wolfSSL Inc.
*
* This file is part of wolfSSL. (formerly known as CyaSSL)
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifndef WOLFSSL_NRF51_PORT_H
#define WOLFSSL_NRF51_PORT_H
#ifdef __cplusplus
extern "C" {
#endif
#include <wolfssl/wolfcrypt/types.h>
/* Public Functions */
int nrf51_random_generate(byte* output, word32 sz);
int nrf51_aes_set_key(const byte* key);
int nrf51_aes_encrypt(const byte* in, const byte* key, word32 rounds, byte* out);
double current_time(int reset);
#ifdef __cplusplus
}
#endif
#endif /* WOLFSSL_NRF51_PORT_H */

View File

@ -1029,6 +1029,61 @@ static char *fgets(char *buff, int sz, FILE *fp)
#endif
#endif /* HAVE_ECC */
/* Curve255519 Configs */
#ifdef HAVE_CURVE25519
/* By default enable shared secret, key export and import */
#ifndef NO_CURVE25519_SHARED_SECRET
#undef HAVE_CURVE25519_SHARED_SECRET
#define HAVE_CURVE25519_SHARED_SECRET
#endif
#ifndef NO_CURVE25519_KEY_EXPORT
#undef HAVE_CURVE25519_KEY_EXPORT
#define HAVE_CURVE25519_KEY_EXPORT
#endif
#ifndef NO_CURVE25519_KEY_IMPORT
#undef HAVE_CURVE25519_KEY_IMPORT
#define HAVE_CURVE25519_KEY_IMPORT
#endif
#endif /* HAVE_CURVE25519 */
/* Ed255519 Configs */
#ifdef HAVE_ED25519
/* By default enable sign, verify, key export and import */
#ifndef NO_ED25519_SIGN
#undef HAVE_ED25519_SIGN
#define HAVE_ED25519_SIGN
#endif
#ifndef NO_ED25519_VERIFY
#undef HAVE_ED25519_VERIFY
#define HAVE_ED25519_VERIFY
#endif
#ifndef NO_ED25519_KEY_EXPORT
#undef HAVE_ED25519_KEY_EXPORT
#define HAVE_ED25519_KEY_EXPORT
#endif
#ifndef NO_ED25519_KEY_IMPORT
#undef HAVE_ED25519_KEY_IMPORT
#define HAVE_ED25519_KEY_IMPORT
#endif
#endif /* HAVE_ED25519 */
/* AES Config */
#ifndef NO_AES
/* By default enable all AES key sizes, decryption and CBC */
#ifndef AES_MAX_KEY_SIZE
#undef AES_MAX_KEY_SIZE
#define AES_MAX_KEY_SIZE 256
#endif
#ifndef NO_AES_DECRYPT
#undef HAVE_AES_DECRYPT
#define HAVE_AES_DECRYPT
#endif
#ifndef NO_AES_CBC
#undef HAVE_AES_CBC
#define HAVE_AES_CBC
#endif
#endif
/* if desktop type system and fastmath increase default max bits */
#ifdef WOLFSSL_X86_64_BUILD
#ifdef USE_FAST_MATH