From d1f323ca58408280c8b34bd85b284c9e8b7ecbbf Mon Sep 17 00:00:00 2001 From: kaleb-himes Date: Tue, 31 Jan 2017 14:45:33 -0700 Subject: [PATCH 01/68] Adds wrapper for CTX_load_verify_locations to C# wrapper --- wrapper/CSharp/wolfSSL_CSharp/wolfSSL.cs | 29 ++++++++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/wrapper/CSharp/wolfSSL_CSharp/wolfSSL.cs b/wrapper/CSharp/wolfSSL_CSharp/wolfSSL.cs index c87288f87..5d05a6441 100644 --- a/wrapper/CSharp/wolfSSL_CSharp/wolfSSL.cs +++ b/wrapper/CSharp/wolfSSL_CSharp/wolfSSL.cs @@ -193,6 +193,8 @@ namespace wolfSSL.CSharp { [DllImport(wolfssl_dll, CallingConvention = CallingConvention.Cdecl)] private extern static int wolfSSL_CTX_use_certificate_file(IntPtr ctx, string file, int type); [DllImport(wolfssl_dll, CallingConvention = CallingConvention.Cdecl)] + private extern static int wolfSSL_CTX_load_verify_locations(IntPtr ctx, string file, string path); + [DllImport(wolfssl_dll, CallingConvention = CallingConvention.Cdecl)] private extern static int wolfSSL_CTX_use_PrivateKey_file(IntPtr ctx, string file, int type); [DllImport(wolfssl_dll, CallingConvention = CallingConvention.Cdecl)] private extern static void wolfSSL_CTX_free(IntPtr ctx); @@ -1565,6 +1567,33 @@ namespace wolfSSL.CSharp { } + /// + /// Used to load in the peer trusted root file + /// + /// CTX structure for TLS/SSL connections + /// Name of the file to load including absolute path + /// path to multiple certificates (try to load all in path) + /// 1 on success + public static int CTX_load_verify_locations(IntPtr ctx, string fileCert, string path) + { + try + { + IntPtr local_ctx = unwrap(ctx); + if (local_ctx == IntPtr.Zero) + { + log(ERROR_LOG, "CTX load verify locations certificate file error"); + return FAILURE; + } + + return wolfSSL_CTX_load_verify_locations(local_ctx, fileCert, path); + } + catch (Exception e) + { + log(ERROR_LOG, "wolfssl ctx load verify locations file error " + e.ToString()); + return FAILURE; + } + } + /// /// Used to load in the private key from a file /// From 2ef4525d4d479cefddb5f6a0310cf2d097e6b4e3 Mon Sep 17 00:00:00 2001 From: Nickolas Lapp Date: Wed, 22 Feb 2017 11:02:53 -0700 Subject: [PATCH 02/68] Changes to bring wolfssl up to date with stunnel 5.40 --- cyassl/openssl/include.am | 1 + cyassl/openssl/ssl23.h | 3 +++ src/ssl.c | 2 +- wolfssl/openssl/include.am | 1 + wolfssl/openssl/ssl23.h | 1 + wolfssl/ssl.h | 4 ++-- 6 files changed, 9 insertions(+), 3 deletions(-) create mode 100644 cyassl/openssl/ssl23.h create mode 100644 wolfssl/openssl/ssl23.h diff --git a/cyassl/openssl/include.am b/cyassl/openssl/include.am index f5c3c56e9..c0a6d125f 100644 --- a/cyassl/openssl/include.am +++ b/cyassl/openssl/include.am @@ -32,6 +32,7 @@ nobase_include_HEADERS+= \ cyassl/openssl/rand.h \ cyassl/openssl/rsa.h \ cyassl/openssl/sha.h \ + cyassl/openssl/ssl23.h \ cyassl/openssl/ssl.h \ cyassl/openssl/stack.h \ cyassl/openssl/ui.h \ diff --git a/cyassl/openssl/ssl23.h b/cyassl/openssl/ssl23.h new file mode 100644 index 000000000..f8aa85681 --- /dev/null +++ b/cyassl/openssl/ssl23.h @@ -0,0 +1,3 @@ +/* ssl23.h for openssl */ + +#include diff --git a/src/ssl.c b/src/ssl.c index a4fb30bb1..22b8ba83d 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -21223,7 +21223,7 @@ void wolfSSL_THREADID_set_numeric(void* id, unsigned long val) } -WOLFSSL_X509* wolfSSL_X509_STORE_get1_certs(WOLFSSL_X509_STORE_CTX* ctx, +STACK_OF(WOLFSSL_X509)* wolfSSL_X509_STORE_get1_certs(WOLFSSL_X509_STORE_CTX* ctx, WOLFSSL_X509_NAME* name) { WOLFSSL_ENTER("wolfSSL_X509_STORE_get1_certs"); diff --git a/wolfssl/openssl/include.am b/wolfssl/openssl/include.am index d6d743835..e4dcdf80a 100644 --- a/wolfssl/openssl/include.am +++ b/wolfssl/openssl/include.am @@ -33,6 +33,7 @@ nobase_include_HEADERS+= \ wolfssl/openssl/rand.h \ wolfssl/openssl/rsa.h \ wolfssl/openssl/sha.h \ + wolfssl/openssl/ssl23.h \ wolfssl/openssl/ssl.h \ wolfssl/openssl/stack.h \ wolfssl/openssl/ui.h \ diff --git a/wolfssl/openssl/ssl23.h b/wolfssl/openssl/ssl23.h new file mode 100644 index 000000000..fc3ddfb5f --- /dev/null +++ b/wolfssl/openssl/ssl23.h @@ -0,0 +1 @@ +/* ssl23.h for openssl */ diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index 6b94cac52..c7d8ecf55 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -2160,8 +2160,8 @@ WOLFSSL_API void wolfSSL_THREADID_set_callback(void (*threadid_func)(void*)); WOLFSSL_API void wolfSSL_THREADID_set_numeric(void* id, unsigned long val); -WOLFSSL_API WOLFSSL_X509* wolfSSL_X509_STORE_get1_certs(WOLFSSL_X509_STORE_CTX*, - WOLFSSL_X509_NAME*); +WOLFSSL_API STACK_OF(WOLFSSL_X509)* wolfSSL_X509_STORE_get1_certs( + WOLFSSL_X509_STORE_CTX*, WOLFSSL_X509_NAME*); WOLFSSL_API void wolfSSL_sk_X509_pop_free(STACK_OF(WOLFSSL_X509)* sk, void f (WOLFSSL_X509*)); #endif /* HAVE_STUNNEL */ From 9db6a27921f4e6d6e0aaefc1548610c5e820314c Mon Sep 17 00:00:00 2001 From: David Garske Date: Thu, 23 Feb 2017 14:47:36 -0800 Subject: [PATCH 03/68] =?UTF-8?q?Fixes=20for=20scan-build=20warnings.=20Fi?= =?UTF-8?q?x=20possible=20memory=20leak=20in=20wolfSSL=5FDH=5Fnew=20on=20f?= =?UTF-8?q?ailure.=20Add=20null=20checks=20in=20integer.c=20for=20destinat?= =?UTF-8?q?ion=20to=20make=20sure=20=E2=80=9Cdp=E2=80=9D=20grows=20when=20?= =?UTF-8?q?NULL=20(even=20though=20never=20happens=20in=20real-use).=20Add?= =?UTF-8?q?ed=20suppression=20of=20wc=5Fport.c=20warning=20=E2=80=9CValue?= =?UTF-8?q?=20stored=20to=20'ret'=20is=20never=20read=E2=80=9D.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/ssl.c | 1 + wolfcrypt/src/integer.c | 4 ++-- wolfcrypt/src/wc_port.c | 1 + 3 files changed, 4 insertions(+), 2 deletions(-) diff --git a/src/ssl.c b/src/ssl.c index 5fcd828fd..0b494ac03 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -16133,6 +16133,7 @@ WOLFSSL_DH* wolfSSL_DH_new(void) if (wc_InitDhKey(key) != 0) { WOLFSSL_MSG("wolfSSL_DH_new InitDhKey failure"); XFREE(key, NULL, DYNAMIC_TYPE_DH); + XFREE(external, NULL, DYNAMIC_TYPE_DH); return NULL; } external->internal = key; diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index efa0af912..067a55012 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -330,7 +330,7 @@ int mp_copy (mp_int * a, mp_int * b) } /* grow dest */ - if (b->alloc < a->used) { + if (b->alloc < a->used || b->dp == NULL) { if ((res = mp_grow (b, a->used)) != MP_OKAY) { return res; } @@ -1633,7 +1633,7 @@ int s_mp_sub (mp_int * a, mp_int * b, mp_int * c) max_a = a->used; /* init result */ - if (c->alloc < max_a) { + if (c->alloc < max_a || c->dp == NULL) { if ((res = mp_grow (c, max_a)) != MP_OKAY) { return res; } diff --git a/wolfcrypt/src/wc_port.c b/wolfcrypt/src/wc_port.c index cf82ca674..532bf107e 100644 --- a/wolfcrypt/src/wc_port.c +++ b/wolfcrypt/src/wc_port.c @@ -78,6 +78,7 @@ int wolfCrypt_Init(void) WOLFSSL_MSG(ippGetStatusString(ret)); WOLFSSL_MSG("Using default fast IPP library"); ret = 0; + (void)ret; /* suppress not read warning */ } #endif From 26bd19bbd815752e9dbb719db05ca029e516f761 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Thu, 23 Feb 2017 17:15:44 -0700 Subject: [PATCH 04/68] debug message fix --- src/ssl.c | 28 ++++++++++++++-------------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/src/ssl.c b/src/ssl.c index 5fcd828fd..7b9b3a75d 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -11127,7 +11127,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) /* printf("cipherType=%d\n", ctx->cipherType); */ if (ctx->cipherType == AES_128_CBC_TYPE || (type && XSTRNCMP(type, EVP_AES_128_CBC, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_128_CBC); + WOLFSSL_MSG("EVP_AES_128_CBC"); ctx->cipherType = AES_128_CBC_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CBC_MODE; ctx->keyLen = 16; @@ -11148,7 +11148,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) } else if (ctx->cipherType == AES_192_CBC_TYPE || (type && XSTRNCMP(type, EVP_AES_192_CBC, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_192_CBC); + WOLFSSL_MSG("EVP_AES_192_CBC"); ctx->cipherType = AES_192_CBC_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CBC_MODE; ctx->keyLen = 24; @@ -11169,7 +11169,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) } else if (ctx->cipherType == AES_256_CBC_TYPE || (type && XSTRNCMP(type, EVP_AES_256_CBC, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_256_CBC); + WOLFSSL_MSG("EVP_AES_256_CBC"); ctx->cipherType = AES_256_CBC_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CBC_MODE; ctx->keyLen = 32; @@ -11191,7 +11191,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) #ifdef WOLFSSL_AES_COUNTER else if (ctx->cipherType == AES_128_CTR_TYPE || (type && XSTRNCMP(type, EVP_AES_128_CTR, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_128_CTR); + WOLFSSL_MSG("EVP_AES_128_CTR"); ctx->cipherType = AES_128_CTR_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CTR_MODE; ctx->keyLen = 16; @@ -11212,7 +11212,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) } else if (ctx->cipherType == AES_192_CTR_TYPE || (type && XSTRNCMP(type, EVP_AES_192_CTR, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_192_CTR); + WOLFSSL_MSG("EVP_AES_192_CTR"); ctx->cipherType = AES_192_CTR_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CTR_MODE; ctx->keyLen = 24; @@ -11233,7 +11233,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) } else if (ctx->cipherType == AES_256_CTR_TYPE || (type && XSTRNCMP(type, EVP_AES_256_CTR, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_256_CTR); + WOLFSSL_MSG("EVP_AES_256_CTR"); ctx->cipherType = AES_256_CTR_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CTR_MODE; ctx->keyLen = 32; @@ -11255,7 +11255,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) #endif /* WOLFSSL_AES_CTR */ else if (ctx->cipherType == AES_128_ECB_TYPE || (type && XSTRNCMP(type, EVP_AES_128_ECB, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_128_ECB); + WOLFSSL_MSG("EVP_AES_128_ECB"); ctx->cipherType = AES_128_ECB_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_ECB_MODE; ctx->keyLen = 16; @@ -11271,7 +11271,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) } else if (ctx->cipherType == AES_192_ECB_TYPE || (type && XSTRNCMP(type, EVP_AES_192_ECB, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_192_ECB); + WOLFSSL_MSG("EVP_AES_192_ECB"); ctx->cipherType = AES_192_ECB_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_ECB_MODE; ctx->keyLen = 24; @@ -11288,7 +11288,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) } else if (ctx->cipherType == AES_256_ECB_TYPE || (type && XSTRNCMP(type, EVP_AES_256_ECB, EVP_AES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_AES_256_ECB); + WOLFSSL_MSG("EVP_AES_256_ECB"); ctx->cipherType = AES_256_ECB_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_ECB_MODE; ctx->keyLen = 32; @@ -11307,7 +11307,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) #ifndef NO_DES3 if (ctx->cipherType == DES_CBC_TYPE || (type && XSTRNCMP(type, EVP_DES_CBC, EVP_DES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_DES_CBC); + WOLFSSL_MSG("EVP_DES_CBC"); ctx->cipherType = DES_CBC_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CBC_MODE; ctx->keyLen = 8; @@ -11327,7 +11327,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) #ifdef WOLFSSL_DES_ECB else if (ctx->cipherType == DES_ECB_TYPE || (type && XSTRNCMP(type, EVP_DES_ECB, EVP_DES_SIZE) == 0)) { - WOLFSSL_MSG(EVP_DES_ECB); + WOLFSSL_MSG("EVP_DES_ECB"); ctx->cipherType = DES_ECB_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_ECB_MODE; ctx->keyLen = 8; @@ -11345,7 +11345,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) else if (ctx->cipherType == DES_EDE3_CBC_TYPE || (type && XSTRNCMP(type, EVP_DES_EDE3_CBC, EVP_DES_EDE3_SIZE) == 0)) { - WOLFSSL_MSG(EVP_DES_EDE3_CBC); + WOLFSSL_MSG("EVP_DES_EDE3_CBC"); ctx->cipherType = DES_EDE3_CBC_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CBC_MODE; ctx->keyLen = 24; @@ -11368,7 +11368,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) else if (ctx->cipherType == DES_EDE3_ECB_TYPE || (type && XSTRNCMP(type, EVP_DES_EDE3_ECB, EVP_DES_EDE3_SIZE) == 0)) { - WOLFSSL_MSG(EVP_DES_EDE3_ECB); + WOLFSSL_MSG("EVP_DES_EDE3_ECB"); ctx->cipherType = DES_EDE3_ECB_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_ECB_MODE; ctx->keyLen = 24; @@ -11399,7 +11399,7 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) #ifdef HAVE_IDEA if (ctx->cipherType == IDEA_CBC_TYPE || (type && XSTRNCMP(type, EVP_IDEA_CBC, EVP_IDEA_SIZE) == 0)) { - WOLFSSL_MSG(EVP_IDEA_CBC); + WOLFSSL_MSG("EVP_IDEA_CBC"); ctx->cipherType = IDEA_CBC_TYPE; ctx->flags = WOLFSSL_EVP_CIPH_CBC_MODE; ctx->keyLen = IDEA_KEY_SIZE; From 0ed8024bcf25fa90973302cbd07c3ec90f9d4ee2 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Tue, 28 Feb 2017 13:40:03 -0700 Subject: [PATCH 05/68] adjust return value of hash update and address warning with NO_SHA --- wolfcrypt/src/hash.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/wolfcrypt/src/hash.c b/wolfcrypt/src/hash.c index 87d4d0fe1..8bcd3a8c7 100644 --- a/wolfcrypt/src/hash.c +++ b/wolfcrypt/src/hash.c @@ -166,7 +166,7 @@ int wc_Hash(enum wc_HashType hash_type, const byte* data, if (hash_len < dig_size) { return BUFFER_E; } - + /* Suppress possible unused arg if all hashing is disabled */ (void)data; (void)data_len; @@ -283,7 +283,7 @@ int wc_HashInit(wc_HashAlg* hash, enum wc_HashType type) return BAD_FUNC_ARG; }; - return 0; + return ret; } int wc_HashUpdate(wc_HashAlg* hash, enum wc_HashType type, const byte* data, @@ -304,8 +304,8 @@ int wc_HashUpdate(wc_HashAlg* hash, enum wc_HashType type, const byte* data, #ifndef NO_SHA ret = wc_ShaUpdate(&hash->sha, data, dataSz); if (ret != 0) -#endif return ret; +#endif break; case WC_HASH_TYPE_SHA224: #ifdef WOLFSSL_SHA224 @@ -345,7 +345,7 @@ int wc_HashUpdate(wc_HashAlg* hash, enum wc_HashType type, const byte* data, return BAD_FUNC_ARG; }; - return 0; + return ret; } int wc_HashFinal(wc_HashAlg* hash, enum wc_HashType type, byte* out) From f77458992e1c766a574cee19dc7e8c1274dcad0d Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Tue, 28 Feb 2017 14:33:07 -0700 Subject: [PATCH 06/68] resolve windows warnings and add sanity check with PKCS12 parse --- wolfcrypt/src/ecc.c | 3 ++- wolfcrypt/src/hmac.c | 12 ++++-------- wolfcrypt/src/integer.c | 4 ++++ wolfcrypt/src/pkcs12.c | 4 ++++ 4 files changed, 14 insertions(+), 9 deletions(-) diff --git a/wolfcrypt/src/ecc.c b/wolfcrypt/src/ecc.c index 019b96366..ac813d280 100644 --- a/wolfcrypt/src/ecc.c +++ b/wolfcrypt/src/ecc.c @@ -7070,7 +7070,8 @@ int do_mp_jacobi(mp_int* a, mp_int* n, int* c); int do_mp_jacobi(mp_int* a, mp_int* n, int* c) { - int k, s, r, res; + int k, s, res; + int r = 0; /* initialize to help static analysis out */ mp_digit residue; /* if a < 0 return MP_VAL */ diff --git a/wolfcrypt/src/hmac.c b/wolfcrypt/src/hmac.c index c8785883d..271ccd43b 100644 --- a/wolfcrypt/src/hmac.c +++ b/wolfcrypt/src/hmac.c @@ -830,15 +830,11 @@ int wc_HKDF(int type, const byte* inKey, word32 inKeySz, saltSz = hashSz; } - do { ret = wc_HmacSetKey(&myHmac, type, localSalt, saltSz); - if (ret != 0) - break; - ret = wc_HmacUpdate(&myHmac, inKey, inKeySz); - if (ret != 0) - break; - ret = wc_HmacFinal(&myHmac, prk); - } while (0); + if (ret == 0) + ret = wc_HmacUpdate(&myHmac, inKey, inKeySz); + if (ret == 0) + ret = wc_HmacFinal(&myHmac, prk); if (ret == 0) { while (outIdx < outSz) { diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index efa0af912..9c45c7602 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -4223,6 +4223,10 @@ static int mp_div_d (mp_int * a, mp_digit b, mp_int * c, mp_digit * d) q.used = a->used; q.sign = a->sign; } + else { + mp_init(&q); /* initialize to help static analysis */ + } + w = 0; for (ix = a->used - 1; ix >= 0; ix--) { diff --git a/wolfcrypt/src/pkcs12.c b/wolfcrypt/src/pkcs12.c index edcc634d5..24877b60d 100644 --- a/wolfcrypt/src/pkcs12.c +++ b/wolfcrypt/src/pkcs12.c @@ -709,6 +709,10 @@ int wc_PKCS12_parse(WC_PKCS12* pkcs12, const char* psw, } } + if (pkcs12->safe == NULL) { + WOLFSSL_MSG("No PKCS12 safes to parse"); + return BAD_FUNC_ARG; + } /* Decode content infos */ ci = pkcs12->safe->CI; From e6434f380bc2df1b0cb939c2078d950ad8e39db1 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Thu, 22 Dec 2016 12:53:29 +1000 Subject: [PATCH 07/68] Get Nginx working with wolfSSL --- configure.ac | 62 +- examples/server/server.c | 48 +- src/internal.c | 191 ++- src/ocsp.c | 603 ++++++-- src/ssl.c | 2472 ++++++++++++++++++++++++++++---- src/tls.c | 86 +- wolfcrypt/src/asn.c | 40 +- wolfcrypt/src/ecc.c | 16 + wolfcrypt/src/evp.c | 2 +- wolfssl/internal.h | 109 +- wolfssl/ocsp.h | 50 + wolfssl/openssl/crypto.h | 7 +- wolfssl/openssl/dsa.h | 8 +- wolfssl/openssl/ec.h | 13 +- wolfssl/openssl/ecdsa.h | 8 +- wolfssl/openssl/evp.h | 22 + wolfssl/openssl/hmac.h | 3 + wolfssl/openssl/ocsp.h | 43 + wolfssl/openssl/opensslv.h | 2 +- wolfssl/openssl/rsa.h | 8 +- wolfssl/openssl/ssl.h | 162 ++- wolfssl/ssl.h | 226 ++- wolfssl/test.h | 16 + wolfssl/wolfcrypt/asn.h | 17 +- wolfssl/wolfcrypt/asn_public.h | 3 +- wolfssl/wolfcrypt/ecc.h | 2 + wolfssl/wolfcrypt/settings.h | 21 + wolfssl/wolfcrypt/types.h | 2 +- 28 files changed, 3691 insertions(+), 551 deletions(-) diff --git a/configure.ac b/configure.ac index dcb57b474..336b3ba27 100644 --- a/configure.ac +++ b/configure.ac @@ -190,6 +190,7 @@ then enable_jni=yes enable_lighty=yes enable_stunnel=yes + enable_nginx=yes enable_pwdbased=yes fi AM_CONDITIONAL([BUILD_DISTRO], [test "x$ENABLED_DISTRO" = "xyes"]) @@ -268,6 +269,12 @@ AC_ARG_ENABLE([openssh], [ENABLED_OPENSSH=$enableval], [ENABLED_OPENSSH=no]) +# nginx compatibility build +AC_ARG_ENABLE([nginx], + [ --enable-nginx Enable nginx (default: disabled)], + [ ENABLED_NGINX=$enableval ], + [ ENABLED_NGINX=no ] + ) # OPENSSL Extra Compatibility AC_ARG_ENABLE([opensslextra], @@ -275,7 +282,7 @@ AC_ARG_ENABLE([opensslextra], [ ENABLED_OPENSSLEXTRA=$enableval ], [ ENABLED_OPENSSLEXTRA=no ] ) -if test "$ENABLED_OPENSSH" = "yes" +if test "$ENABLED_OPENSSH" = "yes" || test "$ENABLED_NGINX" = "yes" then ENABLED_OPENSSLEXTRA="yes" fi @@ -761,6 +768,11 @@ AC_ARG_ENABLE([sessioncerts], [ ENABLED_SESSIONCERTS=no ] ) +if test "x$ENABLED_NGINX" = "xyes" +then + ENABLED_SESSIONCERTS=yes +fi + if test "$ENABLED_SESSIONCERTS" = "yes" then AM_CFLAGS="$AM_CFLAGS -DSESSION_CERTS" @@ -870,7 +882,7 @@ AC_ARG_ENABLE([dsa], [ ENABLED_DSA=no ] ) -if test "$ENABLED_OPENSSH" = "yes" +if test "$ENABLED_OPENSSH" = "yes" || test "$ENABLED_NGINX" = "yes" then ENABLED_DSA="yes" fi @@ -912,7 +924,7 @@ then ENABLED_ECC=no fi -if test "$ENABLED_OPENSSH" = "yes" +if test "$ENABLED_OPENSSH" = "yes" || test "$ENABLED_NGINX" = "yes" then ENABLED_ECC="yes" fi @@ -1689,6 +1701,11 @@ AC_ARG_ENABLE([ocsp], [ ENABLED_OCSP=no ], ) +if test "x$ENABLED_NGINX" = "xyes" +then + ENABLED_OCSP=yes +fi + if test "$ENABLED_OCSP" = "yes" then AM_CFLAGS="$AM_CFLAGS -DHAVE_OCSP" @@ -1718,6 +1735,11 @@ AC_ARG_ENABLE([ocspstapling], [ ENABLED_CERTIFICATE_STATUS_REQUEST=no ] ) +if test "x$ENABLED_NGINX" = "xyes" +then + ENABLED_CERTIFICATE_STATUS_REQUEST=yes +fi + if test "x$ENABLED_CERTIFICATE_STATUS_REQUEST" = "xyes" then AM_CFLAGS="$AM_CFLAGS -DHAVE_TLS_EXTENSIONS -DHAVE_CERTIFICATE_STATUS_REQUEST" @@ -1740,6 +1762,11 @@ AC_ARG_ENABLE([ocspstapling2], [ ENABLED_CERTIFICATE_STATUS_REQUEST_V2=no ] ) +if test "x$ENABLED_NGINX" = "xyes" +then + ENABLED_CERTIFICATE_STATUS_REQUEST_V2=yes +fi + if test "x$ENABLED_CERTIFICATE_STATUS_REQUEST_V2" = "xyes" then AM_CFLAGS="$AM_CFLAGS -DHAVE_TLS_EXTENSIONS -DHAVE_CERTIFICATE_STATUS_REQUEST_V2" @@ -1762,6 +1789,12 @@ AC_ARG_ENABLE([crl], [ ENABLED_CRL=no ], ) + +if test "x$ENABLED_NGINX" = "xyes" +then + ENABLED_CRL=yes +fi + if test "$ENABLED_CRL" = "yes" then AM_CFLAGS="$AM_CFLAGS -DHAVE_CRL" @@ -2034,6 +2067,11 @@ AC_ARG_ENABLE([session-ticket], [ ENABLED_SESSION_TICKET=no ] ) +if test "x$ENABLED_NGINX" = "xyes" +then + ENABLED_SESSION_TICKET=yes +fi + if test "x$ENABLED_SESSION_TICKET" = "xyes" then AM_CFLAGS="$AM_CFLAGS -DHAVE_TLS_EXTENSIONS -DHAVE_SESSION_TICKET" @@ -2058,6 +2096,11 @@ AC_ARG_ENABLE([tlsx], [ ENABLED_TLSX=no ] ) +if test "x$ENABLED_NGINX" = "xyes" +then + ENABLED_TLSX=yes +fi + if test "x$ENABLED_TLSX" = "xyes" then ENABLED_SNI=yes @@ -2302,6 +2345,16 @@ then AM_CFLAGS="$AM_CFLAGS -DHAVE_LIGHTY -DHAVE_WOLFSSL_SSL_H=1" fi +if test "$ENABLED_NGINX" = "yes" +then + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_NGINX" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_ALWAYS_VERIFY_CB" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_ALWAYS_KEEP_SNI" + AM_CFLAGS="$AM_CFLAGS -DKEEP_OUR_CERT -DKEEP_PEER_CERT" + AM_CFLAGS="$AM_CFLAGS -DHAVE_EXT_CACHE -DOPENSSL_ERR_ONE -DHAVE_EX_DATA" +fi + + # stunnel Support AC_ARG_ENABLE([stunnel], [ --enable-stunnel Enable stunnel (default: disabled)], @@ -2374,7 +2427,7 @@ then fi AM_CFLAGS="$AM_CFLAGS -DHAVE_STUNNEL -DWOLFSSL_ALWAYS_VERIFY_CB" - AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_ALWAYS_KEEP_SNI" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_ALWAYS_KEEP_SNI -DHAVE_EX_DATA" fi if test "$ENABLED_PSK" = "no" && test "$ENABLED_LEANPSK" = "no" \ @@ -3352,6 +3405,7 @@ echo " * MEMORY: $ENABLED_MEMORY" echo " * I/O POOL: $ENABLED_IOPOOL" echo " * LIGHTY: $ENABLED_LIGHTY" echo " * STUNNEL: $ENABLED_STUNNEL" +echo " * NGINX: $ENABLED_NGINX" echo " * ERROR_STRINGS: $ENABLED_ERROR_STRINGS" echo " * DTLS: $ENABLED_DTLS" echo " * SCTP: $ENABLED_SCTP" diff --git a/examples/server/server.c b/examples/server/server.c index 13bf57918..0769207df 100644 --- a/examples/server/server.c +++ b/examples/server/server.c @@ -74,7 +74,19 @@ int myHsDoneCb(WOLFSSL* ssl, void* user_ctx); #endif - +static const char webServerMsg[] = + "HTTP/1.1 200 OK\n" + "Content-Type: text/html\n" + "Connection: close\n" + "\n" + "\n" + "\n" + "Welcome to wolfSSL!\n" + "\n" + "\n" + "

wolfSSL has successfully performed handshake!

\n" + "\n" + "\n"; static int NonBlockingSSL_Accept(SSL* ssl) { @@ -253,6 +265,8 @@ static void Usage(void) #ifdef HAVE_WNR printf("-q Whitewood config file, default %s\n", wnrConfig); #endif + printf("-g Return basic HTML web page\n"); + printf("-C The number of connections to accept, default: 1\n"); } THREAD_RETURN CYASSL_THREAD server_test(void* args) @@ -269,6 +283,7 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) #else const char msg[] = "I hear you fa shizzle!\n"; #endif + int useWebServerMsg = 0; char input[80]; int ch; int version = SERVER_DEFAULT_VERSION; @@ -290,7 +305,7 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) int wc_shutdown = 0; int resume = 0; int resumeCount = 0; - int loopIndefinitely = 0; + int loops = 1; int echoData = 0; int throughput = 0; int minDhKeyBits = DEFAULT_MIN_DHKEY_BITS; @@ -376,7 +391,7 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) useAnyAddr = 1; #else while ((ch = mygetopt(argc, argv, - "?jdbstnNuGfrawPIR:p:v:l:A:c:k:Z:S:oO:D:L:ieB:E:q:")) != -1) { + "?jdbstnNuGfrawPIR:p:v:l:A:c:k:Z:S:oO:D:L:ieB:E:q:gC:")) != -1) { switch (ch) { case '?' : Usage(); @@ -541,7 +556,15 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) break; case 'i' : - loopIndefinitely = 1; + loops = -1; + break; + + case 'C' : + loops = atoi(myoptarg); + if (loops <= 0) { + Usage(); + exit(MY_EX_USAGE); + } break; case 'e' : @@ -568,6 +591,10 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) #endif break; + case 'g' : + useWebServerMsg = 1; + break; + default: Usage(); exit(MY_EX_USAGE); @@ -1096,8 +1123,15 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) err_sys("SSL_read failed"); } - if (SSL_write(ssl, msg, sizeof(msg)) != sizeof(msg)) - err_sys("SSL_write failed"); + if (!useWebServerMsg) { + if (SSL_write(ssl, msg, sizeof(msg)) != sizeof(msg)) + err_sys("SSL_write failed"); + } + else { + if (SSL_write(ssl, webServerMsg, sizeof(webServerMsg)) + != sizeof(webServerMsg)) + err_sys("SSL_write failed"); + } } else { ServerEchoData(ssl, clientfd, echoData, throughput); @@ -1139,7 +1173,7 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) } resumeCount = 0; - if(!loopIndefinitely) { + if (loops > 0 && --loops == 0) { break; /* out of while loop, done with normal and resume option */ } } /* while(1) */ diff --git a/src/internal.c b/src/internal.c index 3c5f39c7f..10971d58b 100644 --- a/src/internal.c +++ b/src/internal.c @@ -105,7 +105,7 @@ WOLFSSL_CALLBACKS needs LARGE_STATIC_BUFFERS, please add LARGE_STATIC_BUFFERS #if !defined(NO_RSA) || defined(HAVE_ECC) static int DoCertificateVerify(WOLFSSL* ssl, byte*, word32*, word32); #endif - #ifdef HAVE_STUNNEL + #if defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) static int SNI_Callback(WOLFSSL* ssl); #endif #ifdef WOLFSSL_DTLS @@ -1452,13 +1452,30 @@ void SSL_CtxResourceFree(WOLFSSL_CTX* ctx) FreeDer(&ctx->privateKey); FreeDer(&ctx->certificate); #ifdef KEEP_OUR_CERT - FreeX509(ctx->ourCert); - if (ctx->ourCert) { + if (ctx->ourCert && ctx->ownOurCert) { + FreeX509(ctx->ourCert); XFREE(ctx->ourCert, ctx->heap, DYNAMIC_TYPE_X509); } #endif /* KEEP_OUR_CERT */ FreeDer(&ctx->certChain); wolfSSL_CertManagerFree(ctx->cm); + #ifdef OPENSSL_EXTRA + while (ctx->ca_names != NULL) { + WOLFSSL_STACK *next = ctx->ca_names->next; + wolfSSL_X509_NAME_free(ctx->ca_names->data.name); + XFREE(ctx->ca_names->data.name, NULL, DYNAMIC_TYPE_OPENSSL); + XFREE(ctx->ca_names, NULL, DYNAMIC_TYPE_OPENSSL); + ctx->ca_names = next; + } + #endif + #ifdef WOLFSSL_NGINX + while (ctx->x509Chain != NULL) { + WOLFSSL_STACK *next = ctx->x509Chain->next; + wolfSSL_X509_free(ctx->x509Chain->data.x509); + XFREE(ctx->x509Chain, NULL, DYNAMIC_TYPE_OPENSSL); + ctx->x509Chain = next; + } + #endif #endif /* !NO_CERTS */ #ifdef HAVE_TLS_EXTENSIONS @@ -3079,8 +3096,15 @@ int EccMakeKey(WOLFSSL* ssl, ecc_key* key, ecc_key* peer) keySz = peer->dp->size; } - /* TODO: Implement _ex version here */ - ret = wc_ecc_make_key(ssl->rng, keySz, key); + if (ssl->ecdhCurveOID > 0) { + ret = wc_ecc_make_key_ex(ssl->rng, keySz, key, + wc_ecc_get_oid(ssl->ecdhCurveOID, NULL, NULL)); + } + else { + ret = wc_ecc_make_key(ssl->rng, keySz, key); + if (ret == 0) + ssl->ecdhCurveOID = key->dp->oidSum; + } /* Handle async pending response */ #if defined(WOLFSSL_ASYNC_CRYPT) @@ -3212,17 +3236,19 @@ int SetSSL_CTX(WOLFSSL* ssl, WOLFSSL_CTX* ctx) #ifdef HAVE_ECC ssl->eccTempKeySz = ctx->eccTempKeySz; ssl->pkCurveOID = ctx->pkCurveOID; + ssl->ecdhCurveOID = ctx->ecdhCurveOID; #endif +#ifdef OPENSSL_EXTRA + ssl->options.mask = ctx->mask; +#endif ssl->timeout = ctx->timeout; ssl->verifyCallback = ctx->verifyCallback; ssl->options.side = ctx->method->side; ssl->options.downgrade = ctx->method->downgrade; ssl->options.minDowngrade = ctx->minDowngrade; - if (ssl->options.side == WOLFSSL_SERVER_END) - ssl->options.haveDH = ctx->haveDH; - + ssl->options.haveDH = ctx->haveDH; ssl->options.haveNTRU = ctx->haveNTRU; ssl->options.haveECDSAsig = ctx->haveECDSAsig; ssl->options.haveECC = ctx->haveECC; @@ -3249,6 +3275,9 @@ int SetSSL_CTX(WOLFSSL* ssl, WOLFSSL_CTX* ctx) ssl->options.sessionCacheOff = ctx->sessionCacheOff; ssl->options.sessionCacheFlushOff = ctx->sessionCacheFlushOff; +#ifdef HAVE_EXT_CACHE + ssl->options.internalCacheOff = ctx->internalCacheOff; +#endif ssl->options.verifyPeer = ctx->verifyPeer; ssl->options.verifyNone = ctx->verifyNone; @@ -3261,10 +3290,8 @@ int SetSSL_CTX(WOLFSSL* ssl, WOLFSSL_CTX* ctx) ssl->options.groupMessages = ctx->groupMessages; #ifndef NO_DH - if (ssl->options.side == WOLFSSL_SERVER_END) { - ssl->buffers.serverDH_P = ctx->serverDH_P; - ssl->buffers.serverDH_G = ctx->serverDH_G; - } + ssl->buffers.serverDH_P = ctx->serverDH_P; + ssl->buffers.serverDH_G = ctx->serverDH_G; #endif #ifndef NO_CERTS @@ -3491,6 +3518,10 @@ int InitSSL(WOLFSSL* ssl, WOLFSSL_CTX* ctx) #endif #ifdef HAVE_ALPN ssl->alpn_client_list = NULL; + #ifdef WOLFSSL_NGINX + ssl->alpnSelect = ctx->alpnSelect; + ssl->alpnSelectArg = ctx->alpnSelectArg; + #endif #endif #ifdef HAVE_SUPPORTED_CURVES ssl->options.userCurves = ctx->userCurves; @@ -3805,6 +3836,9 @@ void SSL_ResourceFree(WOLFSSL* ssl) ssl->session.ticketLen = 0; } #endif +#ifdef HAVE_EXT_CACHE + wolfSSL_SESSION_free(ssl->extSession); +#endif #ifdef WOLFSSL_STATIC_MEMORY /* check if using fixed io buffers and free them */ @@ -6234,6 +6268,78 @@ static int CheckAltNames(DecodedCert* dCert, char* domain) } +#ifdef OPENSSL_EXTRA +/* Check that alternative names, if they exists, match the domain. + * Fail if there are wild patterns and they didn't match. + * Check the common name if no alternative names matched. + * + * dCert Decoded cert to get the alternative names from. + * domain Domain name to compare against. + * checkCN Whether to check the common name. + * returns whether there was a problem in matching. + */ +static int CheckForAltNames(DecodedCert* dCert, char* domain, int* checkCN) +{ + int match; + DNS_entry* altName = NULL; + + WOLFSSL_MSG("Checking AltNames"); + + if (dCert) + altName = dCert->altNames; + + *checkCN = altName == NULL; + match = 0; + while (altName) { + WOLFSSL_MSG("\tindividual AltName check"); + + if (MatchDomainName(altName->name, (int)XSTRLEN(altName->name), + domain)) { + match = 1; + *checkCN = 0; + break; + } + /* No matches and wild pattern match failed. */ + else if (altName->name[0] == '*' && match == 0) + match = -1; + + altName = altName->next; + } + + return match != -1; +} + +/* Check the domain name matches the subject alternative name or the subject + * name. + * + * dcert Decoded certificate. + * domainName The domain name. + * domainNameLen The length of the domain name. + * returns DOMAIN_NAME_MISMATCH when no match found and 0 on success. + */ +int CheckHostName(DecodedCert* dCert, char *domainName, size_t domainNameLen) +{ + int checkCN; + + /* Assume name is NUL terminated. */ + (void)domainNameLen; + + if (CheckForAltNames(dCert, domainName, &checkCN) == 0) { + WOLFSSL_MSG("DomainName match on alt names failed too"); + return DOMAIN_NAME_MISMATCH; + } + if (checkCN == 1) { + if (MatchDomainName(dCert->subjectCN, dCert->subjectCNLen, + domainName) == 0) { + WOLFSSL_MSG("DomainName match on common name failed"); + return DOMAIN_NAME_MISMATCH; + } + } + + return 0; +} +#endif + #if defined(KEEP_PEER_CERT) || defined(SESSION_CERTS) /* Copy parts X509 needs from Decoded cert, 0 on success */ @@ -6662,6 +6768,9 @@ static int DoCertificate(WOLFSSL* ssl, byte* input, word32* inOutIdx, } else if (ret != 0) { WOLFSSL_MSG("Failed to verify CA from chain"); + #ifdef OPENSSL_EXTRA + ssl->peerVerifyRet = X509_V_ERR_INVALID_CA; + #endif } else { WOLFSSL_MSG("Verified CA from chain and already had it"); @@ -6746,6 +6855,9 @@ static int DoCertificate(WOLFSSL* ssl, byte* input, word32* inOutIdx, } else { WOLFSSL_MSG("Failed to verify Peer's cert"); + #ifdef OPENSSL_EXTRA + ssl->peerVerifyRet = X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE; + #endif if (ssl->verifyCallback) { WOLFSSL_MSG("\tCallback override available, will continue"); fatal = 0; @@ -6808,6 +6920,9 @@ static int DoCertificate(WOLFSSL* ssl, byte* input, word32* inOutIdx, if (ret != 0) { WOLFSSL_MSG("\tOCSP Lookup not ok"); fatal = 0; + #ifdef OPENSSL_EXTRA + ssl->peerVerifyRet = X509_V_ERR_CERT_REJECTED; + #endif } } #endif /* HAVE_OCSP */ @@ -6819,6 +6934,9 @@ static int DoCertificate(WOLFSSL* ssl, byte* input, word32* inOutIdx, if (ret != 0) { WOLFSSL_MSG("\tCRL check not ok"); fatal = 0; + #ifdef OPENSSL_EXTRA + ssl->peerVerifyRet = X509_V_ERR_CERT_REJECTED; + #endif } } #endif /* HAVE_CRL */ @@ -7086,7 +7204,7 @@ static int DoCertificate(WOLFSSL* ssl, byte* input, word32* inOutIdx, #else store->current_cert = NULL; #endif -#if defined(HAVE_FORTRESS) || defined(HAVE_STUNNEL) +#if defined(HAVE_EX_DATA) || defined(HAVE_FORTRESS) store->ex_data = ssl; #endif ok = ssl->verifyCallback(0, store); @@ -7242,10 +7360,15 @@ static int DoCertificateStatus(WOLFSSL* ssl, byte* input, word32* inOutIdx, InitOcspResponse(response, status, input +*inOutIdx, status_length); - if ((OcspResponseDecode(response, ssl->ctx->cm, ssl->heap) != 0) - || (response->responseStatus != OCSP_SUCCESSFUL) - || (response->status->status != CERT_GOOD) - || (CompareOcspReqResp(request, response) != 0)) + if (OcspResponseDecode(response, ssl->ctx->cm, ssl->heap) != 0) + ret = BAD_CERTIFICATE_STATUS_ERROR; + else if (CompareOcspReqResp(request, response) != 0) + ret = BAD_CERTIFICATE_STATUS_ERROR; + else if (response->responseStatus != OCSP_SUCCESSFUL) + ret = BAD_CERTIFICATE_STATUS_ERROR; + else if (response->status->status == CERT_REVOKED) + ret = OCSP_CERT_REVOKED; + else if (response->status->status != CERT_GOOD) ret = BAD_CERTIFICATE_STATUS_ERROR; *inOutIdx += status_length; @@ -10990,6 +11113,9 @@ int SendCertificateStatus(WOLFSSL* ssl) } if (ret == 0) { + #ifdef WOLFSSL_NGINX + request->ssl = ssl; + #endif ret = CheckOcspRequest(ssl->ctx->cm->ocsp_stapling, request, &response); @@ -11088,6 +11214,9 @@ int SendCertificateStatus(WOLFSSL* ssl) } if (ret == 0) { + #ifdef WOLFSSL_NGINX + request->ssl = ssl; + #endif ret = CheckOcspRequest(ssl->ctx->cm->ocsp_stapling, request, &responses[0]); @@ -11160,6 +11289,9 @@ int SendCertificateStatus(WOLFSSL* ssl) &ssl->ctx->cm->ocsp_stapling->ocspLock); } + #ifdef WOLFSSL_NGINX + request->ssl = ssl; + #endif ret = CheckOcspRequest(ssl->ctx->cm->ocsp_stapling, request, &responses[i + 1]); @@ -11185,6 +11317,9 @@ int SendCertificateStatus(WOLFSSL* ssl) else { while (ret == 0 && NULL != (request = ssl->ctx->chainOcspRequest[i])) { + #ifdef WOLFSSL_NGINX + request->ssl = ssl; + #endif ret = CheckOcspRequest(ssl->ctx->cm->ocsp_stapling, request, &responses[++i]); @@ -13276,7 +13411,8 @@ int SetCipherList(Suites* suites, const char* list) return 0; } - if (next[0] == 0 || XSTRNCMP(next, "ALL", 3) == 0) + if (next[0] == 0 || XSTRNCMP(next, "ALL", 3) == 0 || + XSTRNCMP(next, "DEFAULT", 7) == 0) return 1; /* wolfSSL defualt */ do { @@ -14458,6 +14594,7 @@ static int DoServerKeyExchange(WOLFSSL* ssl, const byte* input, if ((curveOid = CheckCurveId(b)) < 0) { ERROR_OUT(ECC_CURVE_ERROR, exit_dske); } + ssl->ecdhCurveOID = curveOid; length = input[idx++]; if ((idx - begin) + length > size) { @@ -17029,6 +17166,7 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, idx += RAN_LEN; output[idx++] = sessIdSz; XMEMCPY(ssl->arrays->sessionID, output + idx, sessIdSz); + ssl->arrays->sessionIDSz = sessIdSz; } else { /* If resuming, use info from SSL */ @@ -17344,6 +17482,9 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, } } + ssl->options.dhKeySz = + (word16)ssl->buffers.serverDH_P.length; + ret = DhGenKeyPair(ssl, ssl->buffers.serverDH_P.buffer, ssl->buffers.serverDH_P.length, @@ -18844,6 +18985,9 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, WOLFSSL_MSG("Session lookup for resume failed"); ssl->options.resuming = 0; } else { + #ifdef HAVE_EXT_CACHE + wolfSSL_SESSION_free(session); + #endif if (MatchSuite(ssl, &clSuites) < 0) { WOLFSSL_MSG("Unsupported cipher suite, OldClientHello"); return UNSUPPORTED_SUITE; @@ -19207,9 +19351,10 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, if ((ret = TLSX_Parse(ssl, (byte *) input + i, totalExtSz, 1, &clSuites))) return ret; -#ifdef HAVE_STUNNEL +#if defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) if((ret=SNI_Callback(ssl))) return ret; + ssl->options.side = WOLFSSL_SERVER_END; #endif /*HAVE_STUNNEL*/ i += totalExtSz; @@ -19294,8 +19439,14 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, "using EMS"); return EXT_MASTER_SECRET_NEEDED_E; } +#ifdef HAVE_EXT_CACHE + wolfSSL_SESSION_free(session); +#endif } else { +#ifdef HAVE_EXT_CACHE + wolfSSL_SESSION_free(session); +#endif if (MatchSuite(ssl, &clSuites) < 0) { WOLFSSL_MSG("Unsupported cipher suite, ClientHello"); return UNSUPPORTED_SUITE; @@ -20893,7 +21044,7 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, } -#ifdef HAVE_STUNNEL +#if defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) static int SNI_Callback(WOLFSSL* ssl) { /* Stunnel supports a custom sni callback to switch an SSL's ctx diff --git a/src/ocsp.c b/src/ocsp.c index 7b69ab466..4eff1582c 100644 --- a/src/ocsp.c +++ b/src/ocsp.c @@ -244,6 +244,135 @@ static int GetOcspStatus(WOLFSSL_OCSP* ocsp, OcspRequest* request, return ret; } +/* Check that the response for validity. Store result in status. + * + * ocsp Context object for OCSP status. + * response OCSP response message data. + * responseSz Length of OCSP response message data. + * reponseBuffer Buffer object to return the response with. + * status The certificate status object. + * entry The OCSP entry for this certificate. + * returns OCSP_LOOKUP_FAIL when the response is bad and 0 otherwise. + */ +static int CheckResponse(WOLFSSL_OCSP* ocsp, byte* response, int responseSz, + buffer* responseBuffer, CertStatus* status, + OcspEntry* entry, OcspRequest* ocspRequest) +{ +#ifdef WOLFSSL_SMALL_STACK + CertStatus* newStatus; + OcspResponse* ocspResponse; +#else + CertStatus newStatus[1]; + OcspResponse ocspResponse[1]; +#endif + int ret; + int validated = 0; /* ocsp validation flag */ + +#ifdef WOLFSSL_SMALL_STACK + newStatus = (CertStatus*)XMALLOC(sizeof(CertStatus), NULL, + DYNAMIC_TYPE_TMP_BUFFER); + ocspResponse = (OcspResponse*)XMALLOC(sizeof(OcspResponse), NULL, + DYNAMIC_TYPE_TMP_BUFFER); + + if (newStatus == NULL || ocspResponse == NULL) { + if (newStatus) XFREE(newStatus, NULL, DYNAMIC_TYPE_TMP_BUFFER); + if (ocspResponse) XFREE(ocspResponse, NULL, DYNAMIC_TYPE_TMP_BUFFER); + + XFREE(request, NULL, DYNAMIC_TYPE_OCSP); + + WOLFSSL_LEAVE("CheckCertOCSP", MEMORY_ERROR); + return MEMORY_E; + } +#endif + XMEMSET(newStatus, 0, sizeof(CertStatus)); + + InitOcspResponse(ocspResponse, newStatus, response, responseSz); + ret = OcspResponseDecode(ocspResponse, ocsp->cm, ocsp->cm->heap); + if (ret != 0) { + WOLFSSL_MSG("OcspResponseDecode failed"); + goto end; + } + + if (ocspResponse->responseStatus != OCSP_SUCCESSFUL) { + WOLFSSL_MSG("OcspResponse status bad"); + goto end; + } + if (ocspRequest != NULL) { + ret = CompareOcspReqResp(ocspRequest, ocspResponse); + if (ret != 0) { + goto end; + } + } + + if (responseBuffer) { + responseBuffer->buffer = (byte*)XMALLOC(responseSz, ocsp->cm->heap, + DYNAMIC_TYPE_TMP_BUFFER); + + if (responseBuffer->buffer) { + responseBuffer->length = responseSz; + XMEMCPY(responseBuffer->buffer, response, responseSz); + } + } + + ret = xstat2err(ocspResponse->status->status); + if (ret == 0) { + validated = 1; + } + + if (wc_LockMutex(&ocsp->ocspLock) != 0) { + ret = BAD_MUTEX_E; + goto end; + } + + if (status != NULL) { + if (status->rawOcspResponse) { + XFREE(status->rawOcspResponse, ocsp->cm->heap, + DYNAMIC_TYPE_OCSP_STATUS); + } + + /* Replace existing certificate entry with updated */ + XMEMCPY(status, newStatus, sizeof(CertStatus)); + } + else { + /* Save new certificate entry */ + status = (CertStatus*)XMALLOC(sizeof(CertStatus), + ocsp->cm->heap, DYNAMIC_TYPE_OCSP_STATUS); + if (status != NULL) { + XMEMCPY(status, newStatus, sizeof(CertStatus)); + status->next = entry->status; + entry->status = status; + entry->totalStatus++; + } + } + + if (status && responseBuffer && responseBuffer->buffer) { + status->rawOcspResponse = (byte*)XMALLOC(responseBuffer->length, + ocsp->cm->heap, + DYNAMIC_TYPE_OCSP_STATUS); + + if (status->rawOcspResponse) { + status->rawOcspResponseSz = responseBuffer->length; + XMEMCPY(status->rawOcspResponse, responseBuffer->buffer, + responseBuffer->length); + } + } + + wc_UnLockMutex(&ocsp->ocspLock); + +end: + if (ret == 0 && validated == 1) { + WOLFSSL_MSG("New OcspResponse validated"); + } else if (ret != OCSP_CERT_REVOKED) { + ret = OCSP_LOOKUP_FAIL; + } + +#ifdef WOLFSSL_SMALL_STACK + XFREE(newStatus, NULL, DYNAMIC_TYPE_TMP_BUFFER); + XFREE(ocspResponse, NULL, DYNAMIC_TYPE_TMP_BUFFER); +#endif + return ret; +} + /* 0 on success */ int CheckOcspRequest(WOLFSSL_OCSP* ocsp, OcspRequest* ocspRequest, buffer* responseBuffer) @@ -257,15 +386,6 @@ int CheckOcspRequest(WOLFSSL_OCSP* ocsp, OcspRequest* ocspRequest, const char* url = NULL; int urlSz = 0; int ret = -1; - int validated = 0; /* ocsp validation flag */ - -#ifdef WOLFSSL_SMALL_STACK - CertStatus* newStatus; - OcspResponse* ocspResponse; -#else - CertStatus newStatus[1]; - OcspResponse ocspResponse[1]; -#endif WOLFSSL_ENTER("CheckOcspRequest"); @@ -282,6 +402,22 @@ int CheckOcspRequest(WOLFSSL_OCSP* ocsp, OcspRequest* ocspRequest, if (ret != OCSP_INVALID_STATUS) return ret; +#ifdef WOLFSSL_NGINX + if (ocsp->statusCb != NULL && ocspRequest->ssl != NULL) { + ret = ocsp->statusCb((WOLFSSL*)ocspRequest->ssl, NULL); + if (ret == 0) { + ret = wolfSSL_get_ocsp_response((WOLFSSL*)ocspRequest->ssl, + &response); + ret = CheckResponse(ocsp, response, ret, responseBuffer, status, + entry, NULL); + if (response != NULL) + XFREE(response, NULL, DYNAMIC_TYPE_OPENSSL); + return ret; + } + return OCSP_LOOKUP_FAIL; + } +#endif + if (ocsp->cm->ocspUseOverrideURL) { url = ocsp->cm->ocspOverrideURL; if (url != NULL && url[0] != '\0') @@ -304,120 +440,373 @@ int CheckOcspRequest(WOLFSSL_OCSP* ocsp, OcspRequest* ocspRequest, return MEMORY_ERROR; } -#ifdef WOLFSSL_SMALL_STACK - newStatus = (CertStatus*)XMALLOC(sizeof(CertStatus), NULL, - DYNAMIC_TYPE_TMP_BUFFER); - ocspResponse = (OcspResponse*)XMALLOC(sizeof(OcspResponse), NULL, - DYNAMIC_TYPE_TMP_BUFFER); - - if (newStatus == NULL || ocspResponse == NULL) { - if (newStatus) XFREE(newStatus, NULL, DYNAMIC_TYPE_TMP_BUFFER); - if (ocspResponse) XFREE(ocspResponse, NULL, DYNAMIC_TYPE_TMP_BUFFER); - - XFREE(request, NULL, DYNAMIC_TYPE_OCSP); - - WOLFSSL_LEAVE("CheckCertOCSP", MEMORY_ERROR); - return MEMORY_E; - } -#endif - requestSz = EncodeOcspRequest(ocspRequest, request, requestSz); if (requestSz > 0 && ocsp->cm->ocspIOCb) { responseSz = ocsp->cm->ocspIOCb(ocsp->cm->ocspIOCtx, url, urlSz, request, requestSz, &response); } + XFREE(request, ocsp->cm->heap, DYNAMIC_TYPE_OCSP); + if (responseSz >= 0 && response) { - XMEMSET(newStatus, 0, sizeof(CertStatus)); - - InitOcspResponse(ocspResponse, newStatus, response, responseSz); - if (OcspResponseDecode(ocspResponse, ocsp->cm, ocsp->cm->heap) != 0) { - WOLFSSL_MSG("OcspResponseDecode failed"); - } - else if (ocspResponse->responseStatus != OCSP_SUCCESSFUL) { - WOLFSSL_MSG("OcspResponse status bad"); - } - else { - if (CompareOcspReqResp(ocspRequest, ocspResponse) == 0) { - if (responseBuffer) { - responseBuffer->buffer = (byte*)XMALLOC(responseSz, - ocsp->cm->heap, DYNAMIC_TYPE_TMP_BUFFER); - - if (responseBuffer->buffer) { - responseBuffer->length = responseSz; - XMEMCPY(responseBuffer->buffer, response, responseSz); - } - } - - /* only way to get to good state */ - ret = xstat2err(ocspResponse->status->status); - if (ret == 0) { - validated = 1; - } - - if (wc_LockMutex(&ocsp->ocspLock) != 0) - ret = BAD_MUTEX_E; - else { - if (status != NULL) { - if (status->rawOcspResponse) - XFREE(status->rawOcspResponse, ocsp->cm->heap, - DYNAMIC_TYPE_OCSP_STATUS); - - /* Replace existing certificate entry with updated */ - XMEMCPY(status, newStatus, sizeof(CertStatus)); - } - else { - /* Save new certificate entry */ - status = (CertStatus*)XMALLOC(sizeof(CertStatus), - ocsp->cm->heap, DYNAMIC_TYPE_OCSP_STATUS); - if (status != NULL) { - XMEMCPY(status, newStatus, sizeof(CertStatus)); - status->next = entry->status; - entry->status = status; - entry->totalStatus++; - } - } - - if (status && responseBuffer && responseBuffer->buffer) { - status->rawOcspResponse = (byte*)XMALLOC( - responseBuffer->length, - ocsp->cm->heap, - DYNAMIC_TYPE_OCSP_STATUS); - - if (status->rawOcspResponse) { - status->rawOcspResponseSz = responseBuffer->length; - XMEMCPY(status->rawOcspResponse, - responseBuffer->buffer, - responseBuffer->length); - } - } - - wc_UnLockMutex(&ocsp->ocspLock); - } - } - } + ret = CheckResponse(ocsp, response, responseSz, responseBuffer, status, + entry, ocspRequest); } -#ifdef WOLFSSL_SMALL_STACK - XFREE(newStatus, NULL, DYNAMIC_TYPE_TMP_BUFFER); - XFREE(ocspResponse, NULL, DYNAMIC_TYPE_TMP_BUFFER); -#endif - - XFREE(request, NULL, DYNAMIC_TYPE_OCSP); - if (response != NULL && ocsp->cm->ocspRespFreeCb) ocsp->cm->ocspRespFreeCb(ocsp->cm->ocspIOCtx, response); - if (ret == 0 && validated == 1) { - WOLFSSL_MSG("New OcspResponse validated"); - } else { - ret = OCSP_LOOKUP_FAIL; - } - WOLFSSL_LEAVE("CheckOcspRequest", ret); return ret; } +#ifdef WOLFSSL_NGINX + +int wolfSSL_OCSP_resp_find_status(WOLFSSL_OCSP_BASICRESP *bs, + WOLFSSL_OCSP_CERTID* id, int* status, int* reason, + WOLFSSL_ASN1_TIME** revtime, WOLFSSL_ASN1_TIME** thisupd, + WOLFSSL_ASN1_TIME** nextupd) +{ + if (bs == NULL || id == NULL) + return SSL_FAILURE; + + /* Only supporting one certificate status in asn.c. */ + if (CompareOcspReqResp(id, bs) != 0) + return SSL_FAILURE; + + if (status != NULL) + *status = bs->status->status; + if (thisupd != NULL) + *thisupd = (WOLFSSL_ASN1_TIME*)bs->status->thisDateAsn; + if (nextupd != NULL) + *nextupd = (WOLFSSL_ASN1_TIME*)bs->status->nextDateAsn; + + /* TODO: Not needed for Nginx. */ + if (reason != NULL) + *reason = 0; + if (revtime != NULL) + *revtime = NULL; + + return SSL_SUCCESS; +} + +const char *wolfSSL_OCSP_cert_status_str(long s) +{ + switch (s) { + case CERT_GOOD: + return "good"; + case CERT_REVOKED: + return "revoked"; + case CERT_UNKNOWN: + return "unknown"; + default: + return "(UNKNOWN)"; + } +} + +int wolfSSL_OCSP_check_validity(WOLFSSL_ASN1_TIME* thisupd, + WOLFSSL_ASN1_TIME* nextupd, long sec, long maxsec) +{ + (void)thisupd; + (void)nextupd; + (void)sec; + (void)maxsec; + /* Dates validated in DecodeSingleResponse. */ + return SSL_SUCCESS; +} + +void wolfSSL_OCSP_CERTID_free(WOLFSSL_OCSP_CERTID* certId) +{ + FreeOcspRequest(certId); + XFREE(certId, NULL, DYNAMIC_TYPE_OPENSSL); +} + +WOLFSSL_OCSP_CERTID* wolfSSL_OCSP_cert_to_id( + const WOLFSSL_EVP_MD *dgst, const WOLFSSL_X509 *subject, + const WOLFSSL_X509 *issuer) +{ + WOLFSSL_OCSP_CERTID* certId; + DecodedCert cert; + WOLFSSL_CERT_MANAGER* cm; + int ret; + DerBuffer* derCert = NULL; + + (void)dgst; + + cm = wolfSSL_CertManagerNew(); + if (cm == NULL) + return NULL; + + + ret = AllocDer(&derCert, issuer->derCert->length, + issuer->derCert->type, NULL); + if (ret == 0) { + /* AddCA() frees the buffer. */ + XMEMCPY(derCert->buffer, issuer->derCert->buffer, + issuer->derCert->length); + AddCA(cm, &derCert, WOLFSSL_USER_CA, 1); + } + + certId = (WOLFSSL_OCSP_CERTID*)XMALLOC(sizeof(WOLFSSL_OCSP_CERTID), NULL, + DYNAMIC_TYPE_OPENSSL); + if (certId != NULL) { + InitDecodedCert(&cert, subject->derCert->buffer, + subject->derCert->length, NULL); + if (ParseCertRelative(&cert, CERT_TYPE, VERIFY_OCSP, cm) != 0) { + XFREE(certId, NULL, DYNAMIC_TYPE_OPENSSL); + certId = NULL; + } + else + InitOcspRequest(certId, &cert, 0, NULL); + FreeDecodedCert(&cert); + } + + wolfSSL_CertManagerFree(cm); + + return certId; +} + +void wolfSSL_OCSP_BASICRESP_free(WOLFSSL_OCSP_BASICRESP* basicResponse) +{ + wolfSSL_OCSP_RESPONSE_free(basicResponse); +} + +/* Signature verified in DecodeBasicOcspResponse. + * But no store available to verify certificate. */ +int wolfSSL_OCSP_basic_verify(WOLFSSL_OCSP_BASICRESP *bs, + STACK_OF(WOLFSSL_X509) *certs, WOLFSSL_X509_STORE *st, unsigned long flags) +{ + DecodedCert cert; + int ret = SSL_SUCCESS; + + (void)certs; + + if (flags & OCSP_NOVERIFY) + return SSL_SUCCESS; + + InitDecodedCert(&cert, bs->cert, bs->certSz, NULL); + if (ParseCertRelative(&cert, CERT_TYPE, VERIFY, st->cm) < 0) + ret = SSL_FAILURE; + FreeDecodedCert(&cert); + + return ret; +} + +void wolfSSL_OCSP_RESPONSE_free(OcspResponse* response) +{ + if (response->status != NULL) + XFREE(response->status, NULL, DYNAMIC_TYPE_TMP_BUFFER); + if (response->source != NULL) + XFREE(response->source, NULL, DYNAMIC_TYPE_TMP_BUFFER); + XFREE(response, NULL, DYNAMIC_TYPE_OPENSSL); +} + +OcspResponse* wolfSSL_d2i_OCSP_RESPONSE_bio(WOLFSSL_BIO* bio, + OcspResponse** response) +{ + byte* data; + byte* p; + int len; + int dataAlloced = 0; + OcspResponse* ret; + + if (bio == NULL) + return NULL; + + if (bio->type == BIO_MEMORY) { + len = wolfSSL_BIO_get_mem_data(bio, &data); + if (len <= 0 || data == NULL) { + return NULL; + } + } + else if (bio->type == BIO_FILE) { + long i; + long l; + + i = XFTELL(bio->file); + XFSEEK(bio->file, 0, SEEK_END); + l = XFTELL(bio->file); + XFSEEK(bio->file, i, SEEK_SET); + data = (byte*)XMALLOC(l - i, 0, DYNAMIC_TYPE_TMP_BUFFER); + if (data == NULL) + return NULL; + dataAlloced = 1; + + len = wolfSSL_BIO_read(bio, (char *)data, (int)l); + } + else + return NULL; + + p = data; + ret = wolfSSL_d2i_OCSP_RESPONSE(response, (const unsigned char **)&p, len); + + if (dataAlloced) + XFREE(data, 0, DYNAMIC_TYPE_TMP_BUFFER); + + return ret; +} + +OcspResponse* wolfSSL_d2i_OCSP_RESPONSE(OcspResponse** response, + const unsigned char** data, int len) +{ + OcspResponse *resp = NULL; + word32 idx = 0; + int length = 0; + + if (data == NULL) + return NULL; + + if (response != NULL) + resp = *response; + if (resp == NULL) { + resp = (OcspResponse*)XMALLOC(sizeof(OcspResponse), NULL, + DYNAMIC_TYPE_OPENSSL); + if (resp == NULL) + return NULL; + XMEMSET(resp, 0, sizeof(OcspResponse)); + } + + resp->source = (byte*)XMALLOC(len, NULL, DYNAMIC_TYPE_TMP_BUFFER); + if (resp->source == NULL) { + XFREE(resp, NULL, DYNAMIC_TYPE_OPENSSL); + return NULL; + } + resp->status = (CertStatus*)XMALLOC(sizeof(CertStatus), NULL, + DYNAMIC_TYPE_TMP_BUFFER); + if (resp->status == NULL) { + XFREE(resp->source, NULL, DYNAMIC_TYPE_TMP_BUFFER); + XFREE(resp, NULL, DYNAMIC_TYPE_OPENSSL); + return NULL; + } + + XMEMCPY(resp->source, *data, len); + resp->maxIdx = len; + + if (OcspResponseDecode(resp, NULL, NULL) != 0) { + wolfSSL_OCSP_RESPONSE_free(resp); + return NULL; + } + + GetSequence(*data, &idx, &length, len); + (*data) += idx + length; + + return resp; +} + +int wolfSSL_i2d_OCSP_RESPONSE(OcspResponse* response, + unsigned char** data) +{ + if (data == NULL) + return response->maxIdx; + + XMEMCPY(*data, response->source, response->maxIdx); + return response->maxIdx; +} + +int wolfSSL_OCSP_response_status(OcspResponse *response) +{ + return response->responseStatus; +} + +const char *wolfSSL_OCSP_response_status_str(long s) +{ + switch (s) { + case OCSP_SUCCESSFUL: + return "successful"; + case OCSP_MALFORMED_REQUEST: + return "malformedrequest"; + case OCSP_INTERNAL_ERROR: + return "internalerror"; + case OCSP_TRY_LATER: + return "trylater"; + case OCSP_SIG_REQUIRED: + return "sigrequired"; + case OCSP_UNAUTHROIZED: + return "unauthorized"; + default: + return "(UNKNOWN)"; + } +} + +WOLFSSL_OCSP_BASICRESP* wolfSSL_OCSP_response_get1_basic(OcspResponse* response) +{ + WOLFSSL_OCSP_BASICRESP* bs; + + bs = (WOLFSSL_OCSP_BASICRESP*)XMALLOC(sizeof(WOLFSSL_OCSP_BASICRESP), NULL, + DYNAMIC_TYPE_OPENSSL); + if (bs == NULL) + return NULL; + + XMEMCPY(bs, response, sizeof(OcspResponse)); + bs->status = (CertStatus*)XMALLOC(sizeof(CertStatus), NULL, + DYNAMIC_TYPE_TMP_BUFFER); + bs->source = (byte*)XMALLOC(bs->maxIdx, NULL, DYNAMIC_TYPE_TMP_BUFFER); + if (bs->status == NULL || bs->source == NULL) { + wolfSSL_OCSP_RESPONSE_free(bs); + bs = NULL; + } + XMEMCPY(bs->status, response->status, sizeof(CertStatus)); + XMEMCPY(bs->source, response->source, response->maxIdx); + return bs; +} + +OcspRequest* wolfSSL_OCSP_REQUEST_new(void) +{ + OcspRequest* request; + + request = (OcspRequest*)XMALLOC(sizeof(OcspRequest), NULL, + DYNAMIC_TYPE_OPENSSL); + if (request != NULL) + XMEMSET(request, 0, sizeof(OcspRequest)); + + return request; +} + +void wolfSSL_OCSP_REQUEST_free(OcspRequest* request) +{ + FreeOcspRequest(request); + XFREE(request, 0, DYNAMIC_TYPE_OPENSSL); +} + +int wolfSSL_i2d_OCSP_REQUEST(OcspRequest* request, unsigned char** data) +{ + word32 size; + + size = EncodeOcspRequest(request, NULL, 0); + if (size <= 0 || data == NULL) + return size; + + return EncodeOcspRequest(request, *data, size); +} + +WOLFSSL_OCSP_ONEREQ* wolfSSL_OCSP_request_add0_id(OcspRequest *req, + WOLFSSL_OCSP_CERTID *cid) +{ + if (req == NULL || cid == NULL) + return NULL; + + FreeOcspRequest(req); + XMEMCPY(req, cid, sizeof(OcspRequest)); + + if (cid->serial != NULL) { + req->serial = (byte*)XMALLOC(cid->serialSz, NULL, + DYNAMIC_TYPE_OCSP_REQUEST); + req->url = (byte*)XMALLOC(cid->urlSz, NULL, DYNAMIC_TYPE_OCSP_REQUEST); + if (req->serial == NULL || req->url == NULL) { + FreeOcspRequest(req); + return NULL; + } + + XMEMCPY(req->serial, cid->serial, cid->serialSz); + XMEMCPY(req->url, cid->url, cid->urlSz); + } + + wolfSSL_OCSP_REQUEST_free(cid); + + return req; +} + +#endif #else /* HAVE_OCSP */ diff --git a/src/ssl.c b/src/ssl.c index 7b9b3a75d..c32c9be6c 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -529,6 +529,19 @@ int wolfSSL_get_ciphers(char* buf, int len) return SSL_SUCCESS; } +const char* wolfSSL_get_shared_ciphers(WOLFSSL* ssl, char* buf, int len) +{ + const char* cipher; + + if (ssl == NULL) + return NULL; + + cipher = wolfSSL_get_cipher_name_from_suite(ssl->options.cipherSuite0, + ssl->options.cipherSuite); + len = min(len, (int)(XSTRLEN(cipher) + 1)); + XMEMCPY(buf, cipher, len); + return buf; +} int wolfSSL_get_fd(const WOLFSSL* ssl) { @@ -2250,7 +2263,6 @@ int wolfSSL_GetHmacSize(WOLFSSL* ssl) #endif /* ATOMIC_USER */ #ifndef NO_CERTS - int AllocDer(DerBuffer** pDer, word32 length, int type, void* heap) { int ret = BAD_FUNC_ARG; @@ -4211,9 +4223,11 @@ int ProcessBuffer(WOLFSSL_CTX* ctx, const unsigned char* buff, else if (ctx) { FreeDer(&ctx->certificate); /* Make sure previous is free'd */ #ifdef KEEP_OUR_CERT - FreeX509(ctx->ourCert); if (ctx->ourCert) { - XFREE(ctx->ourCert, ctx->heap, DYNAMIC_TYPE_X509); + if (ctx->ownOurCert) { + FreeX509(ctx->ourCert); + XFREE(ctx->ourCert, ctx->heap, DYNAMIC_TYPE_X509); + } ctx->ourCert = NULL; } #endif @@ -6644,6 +6658,9 @@ int wolfSSL_SetServerID(WOLFSSL* ssl, const byte* id, int len, int newSession) session = GetSessionClient(ssl, id, len); if (session) { if (SetSession(ssl, session) != SSL_SUCCESS) { + #ifdef HAVE_EXT_CACHE + wolfSSL_SESSION_free(session); + #endif WOLFSSL_MSG("SetSession failed"); session = NULL; } @@ -6656,6 +6673,10 @@ int wolfSSL_SetServerID(WOLFSSL* ssl, const byte* id, int len, int newSession) ssl->session.idLen = (word16)min(SERVER_ID_LEN, (word32)len); XMEMCPY(ssl->session.serverID, id, ssl->session.idLen); } + #ifdef HAVE_EXT_CACHE + else + wolfSSL_SESSION_free(session); + #endif return SSL_SUCCESS; } @@ -6983,9 +7004,14 @@ long wolfSSL_CTX_set_session_cache_mode(WOLFSSL_CTX* ctx, long mode) if (mode == SSL_SESS_CACHE_OFF) ctx->sessionCacheOff = 1; - if (mode == SSL_SESS_CACHE_NO_AUTO_CLEAR) + if ((mode & SSL_SESS_CACHE_NO_AUTO_CLEAR) != 0) ctx->sessionCacheFlushOff = 1; +#ifdef HAVE_EXT_CACHE + if ((mode & SSL_SESS_CACHE_NO_INTERNAL_STORE) != 0) + ctx->internalCacheOff = 1; +#endif + return SSL_SUCCESS; } @@ -8279,7 +8305,6 @@ int wolfSSL_SetHsDoneCb(WOLFSSL* ssl, HandShakeDoneCb cb, void* user_ctx) #endif /* NO_HANDSHAKE_DONE_CB */ - int wolfSSL_Cleanup(void) { int ret = SSL_SUCCESS; @@ -8365,6 +8390,8 @@ int wolfSSL_set_timeout(WOLFSSL* ssl, unsigned int to) if (ssl == NULL) return BAD_FUNC_ARG; + if (to == 0) + to = WOLFSSL_SESSION_TIMEOUT; ssl->timeout = to; return SSL_SUCCESS; @@ -8377,6 +8404,8 @@ int wolfSSL_CTX_set_timeout(WOLFSSL_CTX* ctx, unsigned int to) if (ctx == NULL) return BAD_FUNC_ARG; + if (to == 0) + to = WOLFSSL_SESSION_TIMEOUT; ctx->timeout = to; return SSL_SUCCESS; @@ -8396,10 +8425,26 @@ WOLFSSL_SESSION* GetSessionClient(WOLFSSL* ssl, const byte* id, int len) WOLFSSL_ENTER("GetSessionClient"); + if (ssl->ctx->sessionCacheOff) + return NULL; + if (ssl->options.side == WOLFSSL_SERVER_END) return NULL; len = min(SERVER_ID_LEN, (word32)len); + +#ifdef HAVE_EXT_CACHE + if (ssl->ctx->get_sess_cb != NULL) { + int copy = 0; + ret = ssl->ctx->get_sess_cb(ssl, (byte*)id, len, ©); + if (ret != NULL) + return ret; + } + + if (ssl->ctx->internalCacheOff) + return NULL; +#endif + row = HashSession(id, len, &error) % SESSION_ROWS; if (error != 0) { WOLFSSL_MSG("Hash session failed"); @@ -8450,6 +8495,32 @@ WOLFSSL_SESSION* GetSessionClient(WOLFSSL* ssl, const byte* id, int len) #endif /* NO_CLIENT_CACHE */ +/* Restore the master secret and session information for certificates. + * + * ssl The SSL/TLS object. + * session The cached session to restore. + * masterSecret The master secret from the cached session. + * restoreSessionCerts Restoring session certificates is required. + */ +static INLINE void RestoreSession(WOLFSSL* ssl, WOLFSSL_SESSION* session, + byte* masterSecret, byte restoreSessionCerts) +{ + (void)ssl; + (void)restoreSessionCerts; + + if (masterSecret) + XMEMCPY(masterSecret, session->masterSecret, SECRET_LEN); +#ifdef SESSION_CERTS + /* If set, we should copy the session certs into the ssl object + * from the session we are returning so we can resume */ + if (restoreSessionCerts) { + ssl->session.chain = session->chain; + ssl->session.version = session->version; + ssl->session.cipherSuite0 = session->cipherSuite0; + ssl->session.cipherSuite = session->cipherSuite; + } +#endif /* SESSION_CERTS */ +} WOLFSSL_SESSION* GetSession(WOLFSSL* ssl, byte* masterSecret, byte restoreSessionCerts) @@ -8479,6 +8550,21 @@ WOLFSSL_SESSION* GetSession(WOLFSSL* ssl, byte* masterSecret, else id = ssl->session.sessionID; +#ifdef HAVE_EXT_CACHE + if (ssl->ctx->get_sess_cb != NULL) { + int copy = 0; + /* Attempt to retrieve the session from the external cache. */ + ret = ssl->ctx->get_sess_cb(ssl, (byte*)id, ID_LEN, ©); + if (ret != NULL) { + RestoreSession(ssl, ret, masterSecret, restoreSessionCerts); + return ret; + } + } + + if (ssl->ctx->internalCacheOff) + return NULL; +#endif + row = HashSession(id, ID_LEN, &error) % SESSION_ROWS; if (error != 0) { WOLFSSL_MSG("Hash session failed"); @@ -8508,19 +8594,7 @@ WOLFSSL_SESSION* GetSession(WOLFSSL* ssl, byte* masterSecret, if (LowResTimer() < (current->bornOn + current->timeout)) { WOLFSSL_MSG("Session valid"); ret = current; - if (masterSecret) - XMEMCPY(masterSecret, current->masterSecret, SECRET_LEN); -#ifdef SESSION_CERTS - /* If set, we should copy the session certs into the ssl object - * from the session we are returning so we can resume */ - if (restoreSessionCerts) { - ssl->session.chain = ret->chain; - ssl->session.version = ret->version; - ssl->session.cipherSuite0 = ret->cipherSuite0; - ssl->session.cipherSuite = ret->cipherSuite; - } -#endif /* SESSION_CERTS */ - + RestoreSession(ssl, ret, masterSecret, restoreSessionCerts); } else { WOLFSSL_MSG("Session timed out"); } @@ -8659,12 +8733,14 @@ static int get_locked_session_stats(word32* active, word32* total, int AddSession(WOLFSSL* ssl) { - word32 row, idx; + word32 row = 0; + word32 idx = 0; int error = 0; #ifdef HAVE_SESSION_TICKET byte* tmpBuff = NULL; int ticLen = 0; #endif + WOLFSSL_SESSION* session; if (ssl->options.sessionCacheOff) return 0; @@ -8677,12 +8753,6 @@ int AddSession(WOLFSSL* ssl) return 0; #endif - row = HashSession(ssl->arrays->sessionID, ID_LEN, &error) % SESSION_ROWS; - if (error != 0) { - WOLFSSL_MSG("Hash session failed"); - return error; - } - #ifdef HAVE_SESSION_TICKET ticLen = ssl->session.ticketLen; /* Alloc Memory here so if Malloc fails can exit outside of lock */ @@ -8694,27 +8764,56 @@ int AddSession(WOLFSSL* ssl) } #endif - if (wc_LockMutex(&session_mutex) != 0) { +#ifdef HAVE_EXT_CACHE + if (ssl->options.internalCacheOff) { + /* Create a new session object to be stored. */ + session = (WOLFSSL_SESSION*)XMALLOC(sizeof(WOLFSSL_SESSION), NULL, + DYNAMIC_TYPE_OPENSSL); + if (session == NULL) { #ifdef HAVE_SESSION_TICKET - XFREE(tmpBuff, ssl->heap, DYNAMIC_TYPE_SESSION_TICK); + XFREE(tmpBuff, ssl->heap, DYNAMIC_TYPE_SESSION_TICK); #endif - return BAD_MUTEX_E; + return MEMORY_E; + } + XMEMSET(session, 0, sizeof(WOLFSSL_SESSION)); + session->isAlloced = 1; + } + else +#endif + { + /* Use the session object in the cache for external cache if required. + */ + row = HashSession(ssl->arrays->sessionID, ID_LEN, &error) % + SESSION_ROWS; + if (error != 0) { + WOLFSSL_MSG("Hash session failed"); +#ifdef HAVE_SESSION_TICKET + XFREE(tmpBuff, ssl->heap, DYNAMIC_TYPE_SESSION_TICK); +#endif + return error; + } + + if (wc_LockMutex(&session_mutex) != 0) { +#ifdef HAVE_SESSION_TICKET + XFREE(tmpBuff, ssl->heap, DYNAMIC_TYPE_SESSION_TICK); +#endif + return BAD_MUTEX_E; + } + + idx = SessionCache[row].nextIdx++; +#ifdef SESSION_INDEX + ssl->sessionIndex = (row << SESSIDX_ROW_SHIFT) | idx; +#endif + session = &SessionCache[row].Sessions[idx]; } - idx = SessionCache[row].nextIdx++; -#ifdef SESSION_INDEX - ssl->sessionIndex = (row << SESSIDX_ROW_SHIFT) | idx; -#endif + XMEMCPY(session->masterSecret, ssl->arrays->masterSecret, SECRET_LEN); + session->haveEMS = ssl->options.haveEMS; + XMEMCPY(session->sessionID, ssl->arrays->sessionID, ID_LEN); + session->sessionIDSz = ssl->arrays->sessionIDSz; - XMEMCPY(SessionCache[row].Sessions[idx].masterSecret, - ssl->arrays->masterSecret, SECRET_LEN); - SessionCache[row].Sessions[idx].haveEMS = ssl->options.haveEMS; - XMEMCPY(SessionCache[row].Sessions[idx].sessionID, ssl->arrays->sessionID, - ID_LEN); - SessionCache[row].Sessions[idx].sessionIDSz = ssl->arrays->sessionIDSz; - - SessionCache[row].Sessions[idx].timeout = ssl->timeout; - SessionCache[row].Sessions[idx].bornOn = LowResTimer(); + session->timeout = ssl->timeout; + session->bornOn = LowResTimer(); #ifdef HAVE_SESSION_TICKET /* Check if another thread modified ticket since alloc */ @@ -8724,32 +8823,28 @@ int AddSession(WOLFSSL* ssl) if (error == 0) { /* Cleanup cache row's old Dynamic buff if exists */ - if(SessionCache[row].Sessions[idx].isDynamic) { - XFREE(SessionCache[row].Sessions[idx].ticket, - ssl->heap, DYNAMIC_TYPE_SESSION_TICK); - SessionCache[row].Sessions[idx].ticket = NULL; + if(session->isDynamic) { + XFREE(session->ticket, ssl->heap, DYNAMIC_TYPE_SESSION_TICK); + session->ticket = NULL; } /* If too large to store in static buffer, use dyn buffer */ if (ticLen > SESSION_TICKET_LEN) { - SessionCache[row].Sessions[idx].ticket = tmpBuff; - SessionCache[row].Sessions[idx].isDynamic = 1; + session->ticket = tmpBuff; + session->isDynamic = 1; } else { - SessionCache[row].Sessions[idx].ticket = - SessionCache[row].Sessions[idx].staticTicket; - SessionCache[row].Sessions[idx].isDynamic = 0; + session->ticket = session->staticTicket; + session->isDynamic = 0; } } if (error == 0) { - SessionCache[row].Sessions[idx].ticketLen = ticLen; - XMEMCPY(SessionCache[row].Sessions[idx].ticket, - ssl->session.ticket, ticLen); + session->ticketLen = ticLen; + XMEMCPY(session->ticket, ssl->session.ticket, ticLen); } else { /* cleanup, reset state */ - SessionCache[row].Sessions[idx].ticket = - SessionCache[row].Sessions[idx].staticTicket; - SessionCache[row].Sessions[idx].isDynamic = 0; - SessionCache[row].Sessions[idx].ticketLen = 0; + session->ticket = session->staticTicket; + session->isDynamic = 0; + session->ticketLen = 0; if (tmpBuff) { XFREE(tmpBuff, ssl->heap, DYNAMIC_TYPE_SESSION_TICK); tmpBuff = NULL; @@ -8759,19 +8854,24 @@ int AddSession(WOLFSSL* ssl) #ifdef SESSION_CERTS if (error == 0) { - SessionCache[row].Sessions[idx].chain.count = ssl->session.chain.count; - XMEMCPY(SessionCache[row].Sessions[idx].chain.certs, - ssl->session.chain.certs, sizeof(x509_buffer) * MAX_CHAIN_DEPTH); + session->chain.count = ssl->session.chain.count; + XMEMCPY(session->chain.certs, ssl->session.chain.certs, + sizeof(x509_buffer) * MAX_CHAIN_DEPTH); - SessionCache[row].Sessions[idx].version = ssl->version; - SessionCache[row].Sessions[idx].cipherSuite0 = ssl->options.cipherSuite0; - SessionCache[row].Sessions[idx].cipherSuite = ssl->options.cipherSuite; + session->version = ssl->version; + session->cipherSuite0 = ssl->options.cipherSuite0; + session->cipherSuite = ssl->options.cipherSuite; } #endif /* SESSION_CERTS */ - if (error == 0) { - SessionCache[row].totalCount++; - if (SessionCache[row].nextIdx == SESSIONS_PER_ROW) - SessionCache[row].nextIdx = 0; +#ifdef HAVE_EXT_CACHE + if (!ssl->options.internalCacheOff) +#endif + { + if (error == 0) { + SessionCache[row].totalCount++; + if (SessionCache[row].nextIdx == SESSIONS_PER_ROW) + SessionCache[row].nextIdx = 0; + } } #ifndef NO_CLIENT_CACHE if (error == 0) { @@ -8780,48 +8880,70 @@ int AddSession(WOLFSSL* ssl) WOLFSSL_MSG("Adding client cache entry"); - SessionCache[row].Sessions[idx].idLen = ssl->session.idLen; - XMEMCPY(SessionCache[row].Sessions[idx].serverID, - ssl->session.serverID, ssl->session.idLen); + session->idLen = ssl->session.idLen; + XMEMCPY(session->serverID, ssl->session.serverID, + ssl->session.idLen); - clientRow = HashSession(ssl->session.serverID, ssl->session.idLen, - &error) % SESSION_ROWS; - if (error != 0) { - WOLFSSL_MSG("Hash session failed"); - } else { - clientIdx = ClientCache[clientRow].nextIdx++; +#ifdef HAVE_EXT_CACHE + if (!ssl->options.internalCacheOff) +#endif + { + clientRow = HashSession(ssl->session.serverID, + ssl->session.idLen, &error) % SESSION_ROWS; + if (error != 0) { + WOLFSSL_MSG("Hash session failed"); + } else { + clientIdx = ClientCache[clientRow].nextIdx++; - ClientCache[clientRow].Clients[clientIdx].serverRow = + ClientCache[clientRow].Clients[clientIdx].serverRow = (word16)row; - ClientCache[clientRow].Clients[clientIdx].serverIdx = + ClientCache[clientRow].Clients[clientIdx].serverIdx = (word16)idx; - ClientCache[clientRow].totalCount++; - if (ClientCache[clientRow].nextIdx == SESSIONS_PER_ROW) - ClientCache[clientRow].nextIdx = 0; + ClientCache[clientRow].totalCount++; + if (ClientCache[clientRow].nextIdx == SESSIONS_PER_ROW) + ClientCache[clientRow].nextIdx = 0; + } } } else - SessionCache[row].Sessions[idx].idLen = 0; + session->idLen = 0; } #endif /* NO_CLIENT_CACHE */ #if defined(WOLFSSL_SESSION_STATS) && defined(WOLFSSL_PEAK_SESSIONS) - if (error == 0) { - word32 active = 0; +#ifdef HAVE_EXT_CACHE + if (!ssl->options.internalCacheOff) +#endif + { + if (error == 0) { + word32 active = 0; - error = get_locked_session_stats(&active, NULL, NULL); - if (error == SSL_SUCCESS) { - error = 0; /* back to this function ok */ + error = get_locked_session_stats(&active, NULL, NULL); + if (error == SSL_SUCCESS) { + error = 0; /* back to this function ok */ - if (active > PeakSessions) - PeakSessions = active; + if (active > PeakSessions) + PeakSessions = active; + } } } #endif /* defined(WOLFSSL_SESSION_STATS) && defined(WOLFSSL_PEAK_SESSIONS) */ - if (wc_UnLockMutex(&session_mutex) != 0) - return BAD_MUTEX_E; +#ifdef HAVE_EXT_CACHE + if (!ssl->options.internalCacheOff) +#endif + { + if (wc_UnLockMutex(&session_mutex) != 0) + return BAD_MUTEX_E; + } + +#ifdef HAVE_EXT_CACHE + if (error == 0 && ssl->ctx->new_sess_cb != NULL) + ssl->ctx->new_sess_cb(ssl, session); + if (ssl->options.internalCacheOff) + wolfSSL_SESSION_free(session); +#endif return error; } @@ -9758,15 +9880,71 @@ int wolfSSL_set_compression(WOLFSSL* ssl) void wolfSSL_CTX_set_client_CA_list(WOLFSSL_CTX* ctx, STACK_OF(WOLFSSL_X509_NAME)* names) { - (void)ctx; - (void)names; + WOLFSSL_ENTER("wolfSSL_SSL_CTX_set_client_CA_list"); + + if (ctx != NULL) + ctx->ca_names = names; } + STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_SSL_CTX_get_client_CA_list( + const WOLFSSL_CTX *s) + { + WOLFSSL_ENTER("wolfSSL_SSL_CTX_get_client_CA_list"); + + if (s == NULL) + return NULL; + + return s->ca_names; + } STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_load_client_CA_file(const char* fname) { - (void)fname; - return 0; + WOLFSSL_STACK *list = NULL; + WOLFSSL_STACK *node; + WOLFSSL_BIO* bio; + WOLFSSL_X509 *cert = NULL; + WOLFSSL_X509_NAME *subjectName = NULL; + + WOLFSSL_ENTER("wolfSSL_load_client_CA_file"); + + bio = wolfSSL_BIO_new_file(fname, "r"); + if (bio == NULL) + return NULL; + + /* Read each certificate in the chain out of the file. */ + while (wolfSSL_PEM_read_bio_X509(bio, &cert, NULL, NULL) != NULL) { + subjectName = wolfSSL_X509_get_subject_name(cert); + if (subjectName == NULL) + break; + + node = (WOLFSSL_STACK*)XMALLOC(sizeof(WOLFSSL_STACK), NULL, + DYNAMIC_TYPE_OPENSSL); + if (node == NULL) + break; + + /* Need a persistent copy of the subject name. */ + node->data.name = (WOLFSSL_X509_NAME*)XMALLOC( + sizeof(WOLFSSL_X509_NAME), NULL, DYNAMIC_TYPE_OPENSSL); + if (node->data.name == NULL) { + XFREE(node, NULL, DYNAMIC_TYPE_OPENSSL); + break; + } + XMEMCPY(node->data.name, subjectName, sizeof(WOLFSSL_X509_NAME)); + /* Clear pointers so freeing certificate doesn't free memory. */ + XMEMSET(subjectName, 0, sizeof(WOLFSSL_X509_NAME)); + + /* Put nod on the front of the list. */ + node->num = (list == NULL) ? 1 : list->num + 1; + node->next = list; + list = node; + + wolfSSL_X509_free(cert); + cert = NULL; + } + + wolfSSL_X509_free(cert); + wolfSSL_BIO_free(bio); + return list; } @@ -9878,9 +10056,8 @@ int wolfSSL_set_compression(WOLFSSL* ssl) long wolfSSL_CTX_set_options(WOLFSSL_CTX* ctx, long opt) { - /* goahead calls with 0, do nothing */ WOLFSSL_ENTER("SSL_CTX_set_options"); - (void)ctx; + ctx->mask |= opt; return opt; } @@ -10112,12 +10289,14 @@ int wolfSSL_set_compression(WOLFSSL* ssl) } - int wolfSSL_BIO_get_mem_data(WOLFSSL_BIO* bio, const byte** p) + int wolfSSL_BIO_get_mem_data(WOLFSSL_BIO* bio, void* p) { + WOLFSSL_ENTER("wolfSSL_BIO_get_mem_data"); + if (bio == NULL || p == NULL) return SSL_FATAL_ERROR; - *p = bio->mem; + *(byte **)p = bio->mem; return bio->memLen; } @@ -10232,6 +10411,11 @@ int wolfSSL_set_compression(WOLFSSL* ssl) return (int)XFREAD(buf, 1, len, bio->file); } #endif + if (bio && bio->type == BIO_MEMORY) { + len = min(len, bio->memLen); + XMEMCPY(buf, bio->mem, len); + return len; + } /* already got eof, again is error */ if (bio && front->eof) @@ -10280,6 +10464,7 @@ int wolfSSL_set_compression(WOLFSSL* ssl) int ret; WOLFSSL* ssl = 0; WOLFSSL_BIO* front = bio; + byte* p; WOLFSSL_ENTER("wolfSSL_BIO_write"); @@ -10293,6 +10478,32 @@ int wolfSSL_set_compression(WOLFSSL* ssl) } #endif + if (bio && bio->type == BIO_MEMORY) { + /* Make buffer big enough to hold new data. */ + if (bio->mem == NULL) { + bio->mem = (byte*)XMALLOC(len, bio->heap, DYNAMIC_TYPE_OPENSSL); + if (bio->mem == NULL) + return -1; + p = bio->mem; + } + else { + p = (byte*)XMALLOC(len + bio->memLen, bio->heap, + DYNAMIC_TYPE_OPENSSL); + if (p == NULL) + return -1; + XMEMCPY(p, bio->mem, bio->memLen); + XFREE(bio->mem, bio->heap, DYNAMIC_TYPE_OPENSSL); + bio->mem = p; + p += bio->memLen; + } + + /* Put data on the end of the buffer. */ + XMEMCPY(p, data, len); + bio->memLen += len; + + return len; + } + /* already got eof, again is error */ if (bio && front->eof) return SSL_FATAL_ERROR; @@ -10372,8 +10583,15 @@ int wolfSSL_set_compression(WOLFSSL* ssl) unsigned long wolfSSL_ERR_get_error(void) { - /* TODO: */ - return 0; + WOLFSSL_ENTER("wolfSSL_ERR_clear_error"); + +#if defined(OPENSSL_ERR_ONE) + unsigned long ret = wc_last_error; + wc_last_error = 0; + return ret; +#else + return (unsigned long)(0 - NOT_COMPILED_IN); +#endif } #ifndef NO_MD5 @@ -11918,7 +12136,11 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) void wolfSSL_ERR_clear_error(void) { - /* TODO: */ + WOLFSSL_ENTER("wolfSSL_ERR_clear_error"); + +#if defined(OPENSSL_ERR_ONE) + wc_last_error = 0; +#endif } @@ -12164,14 +12386,61 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) #if defined(KEEP_PEER_CERT) + #ifdef SESSION_CERTS + /* Decode the X509 DER encoded certificate into a WOLFSSL_X509 object. + * + * x509 WOLFSSL_X509 object to decode into. + * in X509 DER data. + * len Length of the X509 DER data. + * returns the new certificate on success, otherwise NULL. + */ + static int DecodeToX509(WOLFSSL_X509* x509, const byte* in, int len) + { + int ret; + #ifdef WOLFSSL_SMALL_STACK + DecodedCert* cert = NULL; + #else + DecodedCert cert[1]; + #endif + + #ifdef WOLFSSL_SMALL_STACK + cert = (DecodedCert*)XMALLOC(sizeof(DecodedCert), NULL, + DYNAMIC_TYPE_TMP_BUFFER); + if (cert == NULL) + return NULL; + #endif + + /* Create a DecodedCert object and copy fields into WOLFSSL_X509 object. + */ + InitDecodedCert(cert, (byte*)in, len, NULL); + if ((ret = ParseCertRelative(cert, CERT_TYPE, 0, NULL)) == 0) { + InitX509(x509, 0, NULL); + ret = CopyDecodedToX509(x509, cert); + FreeDecodedCert(cert); + } + #ifdef WOLFSSL_SMALL_STACK + XFREE(cert, NULL, DYNAMIC_TYPE_TMP_BUFFER); + #endif + + return ret; + } + #endif + WOLFSSL_X509* wolfSSL_get_peer_certificate(WOLFSSL* ssl) { WOLFSSL_ENTER("SSL_get_peer_certificate"); if (ssl->peerCert.issuer.sz) return &ssl->peerCert; - else - return 0; +#ifdef SESSION_CERTS + else if (ssl->session.chain.count > 0) { + if (DecodeToX509(&ssl->peerCert, ssl->session.chain.certs[0].buffer, + ssl->session.chain.certs[0].length) == 0) { + return &ssl->peerCert; + } + } +#endif + return 0; } #endif /* KEEP_PEER_CERT */ @@ -12229,7 +12498,7 @@ static void ExternalFreeX509(WOLFSSL_X509* x509) WOLFSSL_X509_NAME* wolfSSL_X509_get_issuer_name(WOLFSSL_X509* cert) { WOLFSSL_ENTER("X509_get_issuer_name"); - if(cert) + if (cert && cert->issuer.sz != 0) return &cert->issuer; return NULL; } @@ -12238,7 +12507,7 @@ static void ExternalFreeX509(WOLFSSL_X509* x509) WOLFSSL_X509_NAME* wolfSSL_X509_get_subject_name(WOLFSSL_X509* cert) { WOLFSSL_ENTER("wolfSSL_X509_get_subject_name"); - if(cert) + if (cert && cert->subject.sz != 0) return &cert->subject; return NULL; } @@ -12853,7 +13122,6 @@ void wolfSSL_sk_X509_free(STACK_OF(WOLFSSL_X509_NAME)* sk) { } #endif /* NO_CERTS && OPENSSL_EXTRA */ - WOLFSSL_X509* wolfSSL_X509_d2i(WOLFSSL_X509** x509, const byte* in, int len) { WOLFSSL_X509 *newX509 = NULL; @@ -13119,6 +13387,7 @@ WOLFSSL_X509* wolfSSL_get_certificate(WOLFSSL* ssl) ssl->ctx->ourCert = wolfSSL_X509_d2i(NULL, ssl->ctx->certificate->buffer, ssl->ctx->certificate->length); + ssl->ctx->ownOurCert = 1; } return ssl->ctx->ourCert; } @@ -13295,8 +13564,21 @@ int wolfSSL_session_reused(WOLFSSL* ssl) #ifdef OPENSSL_EXTRA void wolfSSL_SESSION_free(WOLFSSL_SESSION* session) { + if (session == NULL) + return; + +#ifdef HAVE_EXT_CACHE + if (session->isAlloced) { + #ifdef HAVE_SESSION_TICKET + if (session->isDynamic) + XFREE(session->ticket, NULL, DYNAMIC_TYPE_SESSION_TICK); + #endif + XFREE(session, NULL, DYNAMIC_TYPE_OPENSSL); + } +#else /* No need to free since cache is static */ (void)session; +#endif } #endif @@ -13402,15 +13684,264 @@ const char* wolfSSL_get_cipher_name(WOLFSSL* ssl) return wolfSSL_get_cipher_name_internal(ssl); } +#ifdef HAVE_ECC +/* Return the name of the curve used for key exchange as a printable string. + * + * ssl The SSL/TLS object. + * returns NULL if ECDH was not used, otherwise the name as a string. + */ +const char* wolfSSL_get_curve_name(WOLFSSL* ssl) +{ + if (ssl == NULL) + return NULL; + if (ssl->specs.kea != ecdhe_psk_kea && + ssl->specs.kea != ecc_diffie_hellman_kea) + return NULL; + if (ssl->ecdhCurveOID == 0) + return NULL; + return wc_ecc_get_name(wc_ecc_get_oid(ssl->ecdhCurveOID, NULL, NULL)); +} +#endif #ifdef OPENSSL_EXTRA -char* wolfSSL_CIPHER_description(WOLFSSL_CIPHER* cipher, char* in, int len) +char* wolfSSL_CIPHER_description(const WOLFSSL_CIPHER* cipher, char* in, + int len) { - (void)cipher; - (void)in; - (void)len; - return 0; + char *ret = in; + const char *keaStr, *authStr, *encStr, *macStr; + size_t strLen; + + if (cipher == NULL || in == NULL) + return NULL; + + switch (cipher->ssl->specs.kea) { + case no_kea: + keaStr = "None"; + break; +#ifndef NO_RSA + case rsa_kea: + keaStr = "RSA"; + break; +#endif +#ifndef NO_DH + case diffie_hellman_kea: + keaStr = "DHE"; + break; +#endif + case fortezza_kea: + keaStr = "FZ"; + break; +#ifndef NO_PSK + case psk_kea: + keaStr = "PSK"; + break; + #ifndef NO_DH + case dhe_psk_kea: + keaStr = "DHEPSK"; + break; + #endif + #ifdef HAVE_ECC + case ecdhe_psk_kea: + keaStr = "ECDHEPSK"; + break; + #endif +#endif +#ifdef HAVE_NTRU + case ntru_kea: + keaStr = "NTRU"; + break; +#endif +#ifdef HAVE_ECC + case ecc_diffie_hellman_kea: + keaStr = "ECDHE"; + break; + case ecc_static_diffie_hellman_kea: + keaStr = "ECDH"; + break; +#endif + default: + keaStr = "unknown"; + break; + } + + switch (cipher->ssl->specs.sig_algo) { + case anonymous_sa_algo: + authStr = "None"; + break; +#ifndef NO_RSA + case rsa_sa_algo: + authStr = "RSA"; + break; +#endif +#ifndef NO_DSA + case dsa_sa_algo: + authStr = "DSA"; + break; +#endif +#ifdef HAVE_ECC + case ecc_dsa_sa_algo: + authStr = "ECDSA"; + break; +#endif + default: + authStr = "unknown"; + break; + } + + switch (cipher->ssl->specs.bulk_cipher_algorithm) { + case wolfssl_cipher_null: + encStr = "None"; + break; +#ifndef NO_RC4 + case wolfssl_rc4: + encStr = "RC4(128)"; + break; +#endif +#ifndef NO_DES3 + case wolfssl_triple_des: + encStr = "3DES(168)"; + break; +#endif +#ifdef HAVE_IDEA + case wolfssl_idea: + encStr = "IDEA(128)"; + break; +#endif +#ifndef NO_AES + case wolfssl_aes: + if (cipher->ssl->specs.key_size == 128) + encStr = "AES(128)"; + else if (cipher->ssl->specs.key_size == 256) + encStr = "AES(256)"; + else + encStr = "AES(?)"; + break; + #ifdef HAVE_AESGCM + case wolfssl_aes_gcm: + if (cipher->ssl->specs.key_size == 128) + encStr = "AESGCM(128)"; + else if (cipher->ssl->specs.key_size == 256) + encStr = "AESGCM(256)"; + else + encStr = "AESGCM(?)"; + break; + #endif + #ifdef HAVE_AESCCM + case wolfssl_aes_ccm: + if (cipher->ssl->specs.key_size == 128) + encStr = "AESCCM(128)"; + else if (cipher->ssl->specs.key_size == 256) + encStr = "AESCCM(256)"; + else + encStr = "AESCCM(?)"; + break; + #endif +#endif +#ifdef HAVE_CHACHA + case wolfssl_chacha: + encStr = "CHACHA20/POLY1305(256)"; + break; +#endif +#ifdef HAVE_CAMELLIA + case wolfssl_camellia: + if (cipher->ssl->specs.key_size == 128) + encStr = "Camellia(128)"; + else if (cipher->ssl->specs.key_size == 256) + encStr = "Camellia(256)"; + else + encStr = "Camellia(?)"; + break; +#endif +#if defined(HAVE_HC128) && !defined(NO_HC128) + case wolfssl_hc128: + encStr = "HC128(128)"; + break; +#endif +#if defined(HAVE_RABBIT) && !defined(NO_RABBIT) + case wolfssl_rabbit: + encStr = "RABBIT(128)"; + break; +#endif + default: + encStr = "unknown"; + break; + } + + switch (cipher->ssl->specs.mac_algorithm) { + case no_mac: + macStr = "None"; + break; +#ifndef NO_MD5 + case md5_mac: + macStr = "MD5"; + break; +#endif +#ifndef NO_SHA + case sha_mac: + macStr = "SHA1"; + break; +#endif +#ifdef HAVE_SHA224 + case sha224_mac: + macStr = "SHA224"; + break; +#endif +#ifndef NO_SHA256 + case sha256_mac: + macStr = "SHA256"; + break; +#endif +#ifdef HAVE_SHA384 + case sha384_mac: + macStr = "SHA384"; + break; +#endif +#ifdef HAVE_SHA512 + case sha512_mac: + macStr = "SHA512"; + break; +#endif +#ifdef HAVE_BLAKE2 + case blake2b_mac: + macStr = "BLAKE2b"; + break; +#endif + default: + macStr = "unknown"; + break; + } + + /* Build up the string by copying onto the end. */ + XSTRNCPY(in, wolfSSL_CIPHER_get_name(cipher), len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + + XSTRNCPY(in, " ", len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + XSTRNCPY(in, wolfSSL_get_version(cipher->ssl), len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + + XSTRNCPY(in, " Kx=", len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + XSTRNCPY(in, keaStr, len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + + XSTRNCPY(in, " Au=", len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + XSTRNCPY(in, authStr, len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + + XSTRNCPY(in, " Enc=", len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + XSTRNCPY(in, encStr, len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + + XSTRNCPY(in, " Mac=", len); + in[len-1] = '\0'; strLen = XSTRLEN(in); len -= (int)strLen; in += strLen; + XSTRNCPY(in, macStr, len); + in[len-1] = '\0'; + + return ret; } @@ -13437,15 +13968,6 @@ void wolfSSL_X509_free(WOLFSSL_X509* x509) #endif /* NO_CERTS */ -/* was do nothing */ -/* -void OPENSSL_free(void* buf) -{ - (void)buf; -} -*/ - - int wolfSSL_OCSP_parse_url(char* url, char** host, char** port, char** path, int* ssl) { @@ -13509,7 +14031,8 @@ WOLFSSL_BIO* wolfSSL_BIO_pop(WOLFSSL_BIO* top) int wolfSSL_BIO_pending(WOLFSSL_BIO* bio) { - (void)bio; + if (bio && bio->type == BIO_MEMORY) + return bio->memLen; return 0; } @@ -13640,34 +14163,90 @@ int wolfSSL_X509_LOOKUP_add_dir(WOLFSSL_X509_LOOKUP* lookup, const char* dir, int wolfSSL_X509_LOOKUP_load_file(WOLFSSL_X509_LOOKUP* lookup, - const char* file, long len) + const char* file, long type) { +#ifndef NO_FILESYSTEM + int ret = SSL_FAILURE; + XFILE fp; + long sz; + byte* pem = NULL; + WOLFSSL_X509* x509; + + if (type != X509_FILETYPE_PEM) + return BAD_FUNC_ARG; + + fp = XFOPEN(file, "r"); + if (fp == NULL) + return BAD_FUNC_ARG; + + XFSEEK(fp, 0, XSEEK_END); + sz = XFTELL(fp); + XREWIND(fp); + + if (sz <= 0) + goto end; + + pem = (byte*)XMALLOC(sz, 0, DYNAMIC_TYPE_TMP_BUFFER); + if (pem == NULL) { + ret = MEMORY_ERROR; + goto end; + } + + /* Read in file which may be a CRL or certificate. */ + if (XFREAD(pem, (size_t)sz, 1, fp) != 1) + goto end; + + if (XSTRNSTR((char*)pem, BEGIN_X509_CRL, (unsigned int)sz) != NULL) { +#ifdef HAVE_CRL + ret = wolfSSL_CertManagerLoadCRLBuffer(lookup->store->cm, pem, sz, + SSL_FILETYPE_PEM); +#endif + } + else { + x509 = wolfSSL_X509_load_certificate_buffer(pem, (int)sz, + SSL_FILETYPE_PEM); + if (x509 == NULL) + goto end; + ret = wolfSSL_X509_STORE_add_cert(lookup->store, x509); + } + +end: + if (pem != NULL) + XFREE(pem, 0, DYNAMIC_TYPE_TMP_BUFFER); + XFCLOSE(fp); + return ret; +#else (void)lookup; (void)file; - (void)len; - return 0; + (void)type; + return SSL_FAILURE; +#endif } WOLFSSL_X509_LOOKUP_METHOD* wolfSSL_X509_LOOKUP_hash_dir(void) { - return 0; + /* Method implementation in functions. */ + static WOLFSSL_X509_LOOKUP_METHOD meth = { 1 }; + return &meth; } - WOLFSSL_X509_LOOKUP_METHOD* wolfSSL_X509_LOOKUP_file(void) { - return 0; + /* Method implementation in functions. */ + static WOLFSSL_X509_LOOKUP_METHOD meth = { 0 }; + return &meth; } - WOLFSSL_X509_LOOKUP* wolfSSL_X509_STORE_add_lookup(WOLFSSL_X509_STORE* store, WOLFSSL_X509_LOOKUP_METHOD* m) { - (void)store; + /* Method is a dummy value and is not needed. */ (void)m; - return 0; + /* Make sure the lookup has a back reference to the store. */ + store->lookup.store = store; + return &store->lookup; } @@ -13675,7 +14254,7 @@ WOLFSSL_X509_LOOKUP* wolfSSL_X509_STORE_add_lookup(WOLFSSL_X509_STORE* store, WOLFSSL_X509* wolfSSL_d2i_X509_bio(WOLFSSL_BIO* bio, WOLFSSL_X509** x509) { WOLFSSL_X509* localX509 = NULL; - const unsigned char* mem = NULL; + unsigned char* mem = NULL; int ret; word32 size; @@ -13710,7 +14289,7 @@ WOLFSSL_X509* wolfSSL_d2i_X509_bio(WOLFSSL_BIO* bio, WOLFSSL_X509** x509) WC_PKCS12* wolfSSL_d2i_PKCS12_bio(WOLFSSL_BIO* bio, WC_PKCS12** pkcs12) { WC_PKCS12* localPkcs12 = NULL; - const unsigned char* mem = NULL; + unsigned char* mem = NULL; int ret; word32 size; @@ -14074,6 +14653,8 @@ WOLFSSL_X509_STORE* wolfSSL_X509_STORE_new(void) XFREE(store, NULL, DYNAMIC_TYPE_X509_STORE); store = NULL; } + else + store->isDynamic = 1; } return store; @@ -14082,7 +14663,7 @@ WOLFSSL_X509_STORE* wolfSSL_X509_STORE_new(void) void wolfSSL_X509_STORE_free(WOLFSSL_X509_STORE* store) { - if (store != NULL) { + if (store != NULL && store->isDynamic) { if (store->cm != NULL) wolfSSL_CertManagerFree(store->cm); XFREE(store, NULL, DYNAMIC_TYPE_X509_STORE); @@ -14147,7 +14728,9 @@ int wolfSSL_X509_STORE_CTX_init(WOLFSSL_X509_STORE_CTX* ctx, ctx->current_cert = x509; ctx->chain = sk; ctx->domain = NULL; +#ifdef HAVE_EX_DATA ctx->ex_data = NULL; +#endif ctx->userCtx = NULL; ctx->error = 0; ctx->error_depth = 0; @@ -14315,20 +14898,49 @@ WOLFSSL_X509_REVOKED* wolfSSL_sk_X509_REVOKED_value( WOLFSSL_ASN1_INTEGER* wolfSSL_X509_get_serialNumber(WOLFSSL_X509* x509) { - (void)x509; - return 0; + WOLFSSL_ASN1_INTEGER* a; + int i = 0; + + WOLFSSL_ENTER("wolfSSL_X509_get_serialNumber"); + + a = (WOLFSSL_ASN1_INTEGER*)XMALLOC(sizeof(WOLFSSL_ASN1_INTEGER), NULL, + DYNAMIC_TYPE_OPENSSL); + if (a == NULL) + return NULL; + + /* Make sure there is space for the data, ASN.1 type and length. */ + if (x509->serialSz > (int)(sizeof(WOLFSSL_ASN1_INTEGER) - 2)) { + XFREE(a, NULL, DYNAMIC_TYPE_OPENSSL); + return NULL; + } + + a->data[i++] = ASN_INTEGER; + a->data[i++] = (unsigned char)x509->serialSz; + XMEMCPY(&a->data[i], x509->serial, x509->serialSz); + + return a; } +#if defined(WOLFSSL_NGINX) int wolfSSL_ASN1_TIME_print(WOLFSSL_BIO* bio, const WOLFSSL_ASN1_TIME* asnTime) { - (void)bio; - (void)asnTime; + char buf[MAX_TIME_STRING_SZ]; + + WOLFSSL_ENTER("wolfSSL_ASN1_TIME_print"); + + if (bio == NULL || asnTime == NULL) + return BAD_FUNC_ARG; + + wolfSSL_ASN1_TIME_to_string((WOLFSSL_ASN1_TIME*)asnTime, buf, sizeof(buf)); + wolfSSL_BIO_write(bio, buf, (int)XSTRLEN(buf)); + return 0; } +#endif -#if defined(WOLFSSL_MYSQL_COMPATIBLE) +#if defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX) char* wolfSSL_ASN1_TIME_to_string(WOLFSSL_ASN1_TIME* time, char* buf, int len) { int format; @@ -14377,7 +14989,7 @@ long wolfSSL_ASN1_INTEGER_get(const WOLFSSL_ASN1_INTEGER* i) void* wolfSSL_X509_STORE_CTX_get_ex_data(WOLFSSL_X509_STORE_CTX* ctx, int idx) { WOLFSSL_ENTER("wolfSSL_X509_STORE_CTX_get_ex_data"); -#if defined(FORTRESS) || defined(HAVE_STUNNEL) +#if defined(HAVE_EX_DATA) || defined(FORTRESS) if (ctx != NULL && idx == 0) return ctx->ex_data; #else @@ -14405,12 +15017,23 @@ void wolfSSL_CTX_set_info_callback(WOLFSSL_CTX* ctx, unsigned long wolfSSL_ERR_peek_error(void) { + WOLFSSL_ENTER("wolfSSL_ERR_peek_error"); + +#if defined(OPENSSL_ERR_ONE) + return wc_last_error; +#else return 0; +#endif } int wolfSSL_ERR_GET_REASON(unsigned long err) { +#ifdef WOLFSSL_NGINX + /* Nginx looks for this error to know to stop parsing certificates. */ + if (err == ((ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE)) + return PEM_R_NO_START_LINE; +#endif (void)err; return 0; } @@ -14630,21 +15253,25 @@ WOLFSSL_API long wolfSSL_set_tlsext_status_ids(WOLFSSL *s, void *arg) return 0; } -/*** TBD ***/ WOLFSSL_API long wolfSSL_get_tlsext_status_ocsp_resp(WOLFSSL *s, unsigned char **resp) { - (void)s; - (void)resp; - return 0; + if (s == NULL || resp == NULL) + return 0; + + *resp = s->ocspResp; + return s->ocspRespSz; } -/*** TBD ***/ -WOLFSSL_API long wolfSSL_set_tlsext_status_ocsp_resp(WOLFSSL *s, unsigned char *resp, int len) +WOLFSSL_API long wolfSSL_set_tlsext_status_ocsp_resp(WOLFSSL *s, + unsigned char *resp, int len) { - (void)s; - (void)resp; - (void)len; - return 0; + if (s == NULL) + return SSL_FAILURE; + + s->ocspResp = resp; + s->ocspRespSz = len; + + return SSL_SUCCESS; } @@ -14744,11 +15371,13 @@ long wolfSSL_CTX_sess_number(WOLFSSL_CTX* ctx) #ifndef NO_CERTS long wolfSSL_CTX_add_extra_chain_cert(WOLFSSL_CTX* ctx, WOLFSSL_X509* x509) { - byte* chain; + byte* chain = NULL; long chainSz = 0; - int derSz; + int derSz; const byte* der; - int ret; + int ret; + int idx = 0; + DerBuffer *derBuffer = NULL; WOLFSSL_ENTER("wolfSSL_CTX_add_extra_chain_cert"); @@ -14763,37 +15392,53 @@ long wolfSSL_CTX_add_extra_chain_cert(WOLFSSL_CTX* ctx, WOLFSSL_X509* x509) return SSL_FAILURE; } - /* adding cert to existing chain */ - if (ctx->certChain != NULL && ctx->certChain->length > 0) { - chainSz += ctx->certChain->length; - } - chainSz += derSz; - - chain = (byte*)XMALLOC(chainSz, ctx->heap, DYNAMIC_TYPE_TMP_BUFFER); - if (chain == NULL) { - WOLFSSL_MSG("Memory Error"); - return SSL_FAILURE; - } - - if (ctx->certChain != NULL && ctx->certChain->length > 0) { - XMEMCPY(chain, ctx->certChain->buffer, ctx->certChain->length); - XMEMCPY(chain + ctx->certChain->length, der, derSz); + if (ctx->certificate == NULL) { + /* Process buffer makes first certificate the leaf. */ + ret = ProcessBuffer(ctx, der, derSz, SSL_FILETYPE_ASN1, CERT_TYPE, + NULL, NULL, 1); + if (ret != SSL_SUCCESS) { + WOLFSSL_LEAVE("wolfSSL_CTX_add_extra_chain_cert", ret); + return SSL_FAILURE; + } } else { - XMEMCPY(chain, der, derSz); - } + /* TODO: Do this elsewhere. */ + AllocDer(&derBuffer, derSz, CERT_TYPE, ctx->heap); + XMEMCPY(derBuffer->buffer, der, derSz); + AddCA(ctx->cm, &derBuffer, WOLFSSL_USER_CA, !ctx->verifyNone); - ret = ProcessBuffer(ctx, chain, chainSz, SSL_FILETYPE_ASN1, CERT_TYPE, - NULL, NULL, 1); - if (ret != SSL_SUCCESS) { - WOLFSSL_LEAVE("wolfSSL_CTX_add_extra_chain_cert", ret); - XFREE(chain, ctx->heap, DYNAMIC_TYPE_TMP_BUFFER); - return SSL_FAILURE; + /* adding cert to existing chain */ + if (ctx->certChain != NULL && ctx->certChain->length > 0) { + chainSz += ctx->certChain->length; + } + chainSz += OPAQUE24_LEN + derSz; + + chain = (byte*)XMALLOC(chainSz, ctx->heap, DYNAMIC_TYPE_TMP_BUFFER); + if (chain == NULL) { + WOLFSSL_MSG("Memory Error"); + return SSL_FAILURE; + } + + if (ctx->certChain != NULL && ctx->certChain->length > 0) { + XMEMCPY(chain, ctx->certChain->buffer, ctx->certChain->length); + idx = ctx->certChain->length; + } + c32to24(derSz, chain + idx); + idx += OPAQUE24_LEN, + XMEMCPY(chain + idx, der, derSz); + idx += derSz; + + FreeDer(&ctx->certChain); + ret = AllocDer(&ctx->certChain, idx, CERT_TYPE, ctx->heap); + if (ret == 0) { + XMEMCPY(ctx->certChain->buffer, chain, idx); + } } /* on success WOLFSSL_X509 memory is responsibility of ctx */ wolfSSL_X509_free(x509); - XFREE(chain, ctx->heap, DYNAMIC_TYPE_TMP_BUFFER); + if (chain != NULL) + XFREE(chain, ctx->heap, CERT_TYPE); return SSL_SUCCESS; } @@ -15031,6 +15676,47 @@ int wolfSSL_ASN1_UTCTIME_print(WOLFSSL_BIO* bio, const WOLFSSL_ASN1_UTCTIME* a) return 0; } +/* Return the month as a string. + * + * n The number of the month as a two characters (1 based). + * returns the month as a string. + */ +static INLINE const char* MonthStr(const char* n) +{ + static const char monthStr[12][4] = { + "Jan", "Feb", "Mar", "Apr", "May", "Jun", + "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" }; + return monthStr[(n[0] - '0') * 10 + (n[1] - '0') - 1]; +} + +int wolfSSL_ASN1_GENERALIZEDTIME_print(WOLFSSL_BIO* bio, + const WOLFSSL_ASN1_GENERALIZEDTIME* asnTime) +{ + const char* p = (const char *)(asnTime->data + 2); + WOLFSSL_ENTER("wolfSSL_ASN1_GENERALIZEDTIME_print"); + + if (bio == NULL || asnTime == NULL) + return BAD_FUNC_ARG; + + /* GetTimeString not always available. */ + wolfSSL_BIO_write(bio, MonthStr(p + 4), 3); + wolfSSL_BIO_write(bio, " ", 1); + /* Day */ + wolfSSL_BIO_write(bio, p + 6, 2); + wolfSSL_BIO_write(bio, " ", 1); + /* Hour */ + wolfSSL_BIO_write(bio, p + 8, 2); + wolfSSL_BIO_write(bio, ":", 1); + /* Min */ + wolfSSL_BIO_write(bio, p + 10, 2); + wolfSSL_BIO_write(bio, ":", 1); + /* Secs */ + wolfSSL_BIO_write(bio, p + 12, 2); + wolfSSL_BIO_write(bio, " ", 1); + wolfSSL_BIO_write(bio, p, 4); + + return 0; +} int wolfSSL_sk_num(WOLFSSL_X509_REVOKED* rev) { @@ -15051,43 +15737,295 @@ void* wolfSSL_sk_value(WOLFSSL_X509_REVOKED* rev, int i) void wolfSSL_CTX_sess_set_get_cb(WOLFSSL_CTX* ctx, WOLFSSL_SESSION*(*f)(WOLFSSL*, unsigned char*, int, int*)) { +#ifdef HAVE_EXT_CACHE + ctx->get_sess_cb = f; +#else (void)ctx; (void)f; +#endif } void wolfSSL_CTX_sess_set_new_cb(WOLFSSL_CTX* ctx, int (*f)(WOLFSSL*, WOLFSSL_SESSION*)) { +#ifdef HAVE_EXT_CACHE + ctx->new_sess_cb = f; +#else (void)ctx; (void)f; +#endif } void wolfSSL_CTX_sess_set_remove_cb(WOLFSSL_CTX* ctx, void (*f)(WOLFSSL_CTX*, WOLFSSL_SESSION*)) { +#ifdef HAVE_EXT_CACHE + ctx->rem_sess_cb = f; +#else (void)ctx; (void)f; +#endif } +#ifdef HAVE_EXT_CACHE +/* convert 32 bit integer to opaque */ +static INLINE void c32toa(word32 u32, byte* c) +{ + c[0] = (u32 >> 24) & 0xff; + c[1] = (u32 >> 16) & 0xff; + c[2] = (u32 >> 8) & 0xff; + c[3] = u32 & 0xff; +} + +static INLINE void c16toa(word16 u16, byte* c) +{ + c[0] = (u16 >> 8) & 0xff; + c[1] = u16 & 0xff; +} +#endif int wolfSSL_i2d_SSL_SESSION(WOLFSSL_SESSION* sess, unsigned char** p) { + int size = 0; +#ifdef HAVE_EXT_CACHE + int idx = 0; +#ifdef SESSION_CERTS + int i; +#endif + unsigned char *data; + + /* bornOn | timeout | sessionID len | sessionID | masterSecret | haveEMS */ + size += OPAQUE32_LEN + OPAQUE32_LEN + OPAQUE8_LEN + sess->sessionIDSz + + SECRET_LEN + OPAQUE8_LEN; +#ifdef SESSION_CERTS + /* Peer chain */ + size += OPAQUE8_LEN; + for (i = 0; i < sess->chain.count; i++) + size += OPAQUE16_LEN + sess->chain.certs[i].length; + /* Protocol version + cipher suite */ + size += OPAQUE16_LEN + OPAQUE16_LEN; +#endif +#ifndef NO_CLIENT_CACHE + /* ServerID len | ServerID */ + size += OPAQUE16_LEN + sess->idLen; +#endif +#ifdef HAVE_SESSION_TICKET + /* ticket len | ticket */ + size += OPAQUE16_LEN + sess->ticketLen; +#endif + + if (p != NULL) { + if (*p == NULL) + *p = (unsigned char*)XMALLOC(size, NULL, DYNAMIC_TYPE_OPENSSL); + if (*p == NULL) + return 0; + data = *p; + + c32toa(sess->bornOn, data + idx); idx += OPAQUE32_LEN; + c32toa(sess->timeout, data + idx); idx += OPAQUE32_LEN; + data[idx++] = sess->sessionIDSz; + XMEMCPY(data + idx, sess->sessionID, sess->sessionIDSz); + idx += sess->sessionIDSz; + XMEMCPY(data + idx, sess->masterSecret, SECRET_LEN); idx += SECRET_LEN; + data[idx++] = sess->haveEMS; +#ifdef SESSION_CERTS + data[idx++] = sess->chain.count; + for (i = 0; i < sess->chain.count; i++) { + c16toa(sess->chain.certs[i].length, data + idx); + idx += OPAQUE16_LEN; + XMEMCPY(data + idx, sess->chain.certs[i].buffer, + sess->chain.certs[i].length); + idx += sess->chain.certs[i].length; + } + data[idx++] = sess->version.major; + data[idx++] = sess->version.minor; + data[idx++] = sess->cipherSuite0; + data[idx++] = sess->cipherSuite; +#endif +#ifndef NO_CLIENT_CACHE + c16toa(sess->idLen, data + idx); idx += OPAQUE16_LEN; + XMEMCPY(data + idx, sess->serverID, sess->idLen); + idx += sess->idLen; +#endif +#ifdef HAVE_SESSION_TICKET + c16toa(sess->ticketLen, data + idx); idx += OPAQUE16_LEN; + XMEMCPY(data + idx, sess->ticket, sess->ticketLen); + idx += sess->ticketLen; +#endif + } +#endif + (void)sess; (void)p; - return sizeof(WOLFSSL_SESSION); +#ifdef HAVE_EXT_CACHE + (void)idx; +#endif + + return size; } +#ifdef HAVE_EXT_CACHE +/* convert opaque to 16 bit integer */ +static INLINE void ato16(const byte* c, word16* u16) +{ + *u16 = (word16) ((c[0] << 8) | (c[1])); +} +/* convert opaque to 32 bit integer */ +static INLINE void ato32(const byte* c, word32* u32) +{ + *u32 = (c[0] << 24) | (c[1] << 16) | (c[2] << 8) | c[3]; +} +#endif + +/* TODO: no function to free new session. */ WOLFSSL_SESSION* wolfSSL_d2i_SSL_SESSION(WOLFSSL_SESSION** sess, const unsigned char** p, long i) { + WOLFSSL_SESSION* s = NULL; + int ret = 0; +#if defined(HAVE_EXT_CACHE) + int idx; + byte* data; +#ifdef SESSION_CERTS + int j; + word16 length; +#endif +#endif + (void)p; (void)i; - if (sess) - return *sess; - return NULL; + (void)ret; + + if (sess != NULL) + s = *sess; + +#ifdef HAVE_EXT_CACHE + if (p == NULL || *p == NULL) + return NULL; + + if (s == NULL) { + s = (WOLFSSL_SESSION*)XMALLOC(sizeof(WOLFSSL_SESSION), NULL, + DYNAMIC_TYPE_OPENSSL); + if (s == NULL) + return NULL; + s->isAlloced = 1; + s->isDynamic = 0; + } + + idx = 0; + data = (byte*)*p; + + /* bornOn | timeout | sessionID len */ + if (i < OPAQUE32_LEN + OPAQUE32_LEN + OPAQUE8_LEN) { + ret = BUFFER_ERROR; + goto end; + } + ato32(data + idx, &s->bornOn); idx += OPAQUE32_LEN; + ato32(data + idx, &s->timeout); idx += OPAQUE32_LEN; + s->sessionIDSz = data[idx++]; + + /* sessionID | secret | haveEMS */ + if (i - idx < s->sessionIDSz + SECRET_LEN + OPAQUE8_LEN) { + ret = BUFFER_ERROR; + goto end; + } + XMEMCPY(s->sessionID, data + idx, s->sessionIDSz); + idx += s->sessionIDSz; + XMEMCPY(s->masterSecret, data + idx, SECRET_LEN); idx += SECRET_LEN; + s->haveEMS = data[idx++]; + +#ifdef SESSION_CERTS + /* Certificate chain */ + if (i - idx == 0) { + ret = BUFFER_ERROR; + goto end; + } + s->chain.count = data[idx++]; + for (j = 0; j < s->chain.count; j++) { + if (i - idx < OPAQUE16_LEN) { + ret = BUFFER_ERROR; + goto end; + } + ato16(data + idx, &length); idx += OPAQUE16_LEN; + s->chain.certs[j].length = length; + if (i - idx < length) { + ret = BUFFER_ERROR; + goto end; + } + XMEMCPY(s->chain.certs[j].buffer, data + idx, length); + idx += length; + } + + /* Protocol Version | Cipher suite */ + if (i - idx < OPAQUE16_LEN + OPAQUE16_LEN) { + ret = BUFFER_ERROR; + goto end; + } + s->version.major = data[idx++]; + s->version.minor = data[idx++]; + s->cipherSuite0 = data[idx++]; + s->cipherSuite = data[idx++]; +#endif +#ifndef NO_CLIENT_CACHE + /* ServerID len */ + if (i - idx < OPAQUE16_LEN) { + ret = BUFFER_ERROR; + goto end; + } + ato16(data + idx, &s->idLen); idx += OPAQUE16_LEN; + + /* ServerID */ + if (i - idx < s->idLen) { + ret = BUFFER_ERROR; + goto end; + } + XMEMCPY(s->serverID, data + idx, s->idLen); idx += s->idLen; +#endif +#ifdef HAVE_SESSION_TICKET + /* ticket len */ + if (i - idx < OPAQUE16_LEN) { + ret = BUFFER_ERROR; + goto end; + } + ato16(data + idx, &s->ticketLen); idx += OPAQUE16_LEN; + + /* Dispose of ol dynamic ticket and ensure space for new ticket. */ + if (s->isDynamic) + XFREE(s->ticket, NULL, DYNAMIC_TYPE_SESSION_TICK); + if (s->ticketLen <= SESSION_TICKET_LEN) + s->ticket = s->staticTicket; + else { + s->ticket = (byte*)XMALLOC(s->ticketLen, NULL, + DYNAMIC_TYPE_SESSION_TICK); + if (s->ticket == NULL) { + ret = MEMORY_ERROR; + goto end; + } + s->isDynamic = 1; + } + + /* ticket */ + if (i - idx < s->ticketLen) { + ret = BUFFER_ERROR; + goto end; + } + XMEMCPY(s->ticket, data + idx, s->ticketLen); idx += s->ticketLen; +#endif + (void)idx; + + if (sess != NULL) + *sess = s; + + *p += idx; + +end: + if (ret != 0 && (sess == NULL || *sess != s)) + wolfSSL_SESSION_free(s); +#endif + return s; } @@ -17534,6 +18472,14 @@ void wolfSSL_HMAC_Init(WOLFSSL_HMAC_CTX* ctx, const void* key, int keylen, } } +int wolfSSL_HMAC_Init_ex(WOLFSSL_HMAC_CTX* ctx, const void* key, int len, + const EVP_MD* md, void* impl) +{ + (void)impl; + wolfSSL_HMAC_Init(ctx, key, len, md); + return 1; +} + void wolfSSL_HMAC_Update(WOLFSSL_HMAC_CTX* ctx, const unsigned char* data, int len) @@ -17821,7 +18767,47 @@ int wolfSSL_EVP_CIPHER_CTX_iv_length(const WOLFSSL_EVP_CIPHER_CTX* ctx) return 0; } +int wolfSSL_EVP_CIPHER_iv_length(const WOLFSSL_EVP_CIPHER* cipher) +{ + const char *name = (const char *)cipher; + WOLFSSL_MSG("wolfSSL_EVP_CIPHER_iv_length"); +#ifndef NO_AES + if ((XSTRNCMP(name, EVP_AES_128_CBC, XSTRLEN(EVP_AES_128_CBC)) == 0) || + (XSTRNCMP(name, EVP_AES_192_CBC, XSTRLEN(EVP_AES_192_CBC)) == 0) || + (XSTRNCMP(name, EVP_AES_256_CBC, XSTRLEN(EVP_AES_256_CBC)) == 0)) { + return AES_BLOCK_SIZE; + } +#ifdef WOLFSSL_AES_COUNTER + if ((XSTRNCMP(name, EVP_AES_128_CTR, XSTRLEN(EVP_AES_128_CTR)) == 0) || + (XSTRNCMP(name, EVP_AES_192_CTR, XSTRLEN(EVP_AES_192_CTR)) == 0) || + (XSTRNCMP(name, EVP_AES_256_CTR, XSTRLEN(EVP_AES_256_CTR)) == 0)) { + return AES_BLOCK_SIZE; + } +#endif +#endif + +#ifndef NO_DES3 + if ((XSTRNCMP(name, EVP_DES_CBC, XSTRLEN(EVP_DES_CBC)) == 0) || + (XSTRNCMP(name, EVP_DES_EDE3_CBC, XSTRLEN(EVP_DES_EDE3_CBC)) == 0)) { + return DES_BLOCK_SIZE; + } +#endif + +#ifdef HAVE_IDEA + if (XSTRNCMP(name, EVP_IDEA_CBC, XSTRLEN(EVP_IDEA_CBC)) == 0) + return IDEA_BLOCK_SIZE; +#endif + + (void)name; + + return 0; +} + +/* Free the dynamically allocated data. + * + * p Pointer to dynamically allocated memory. + */ void wolfSSL_OPENSSL_free(void* p) { WOLFSSL_MSG("wolfSSL_OPENSSL_free"); @@ -18251,7 +19237,8 @@ static int SetECKeyExternal(WOLFSSL_EC_KEY* eckey) key = (ecc_key*)eckey->internal; - /* set group (nid and idx) */ + /* set group (OID, nid and idx) */ + eckey->group->curve_oid = ecc_sets[key->idx].oidSum; eckey->group->curve_nid = ecc_sets[key->idx].id; eckey->group->curve_idx = key->idx; @@ -18425,6 +19412,7 @@ WOLFSSL_EC_KEY *wolfSSL_EC_KEY_new_by_curve_name(int nid) for (x = 0; ecc_sets[x].size != 0; x++) if (ecc_sets[x].id == key->group->curve_nid) { key->group->curve_idx = x; + key->group->curve_oid = ecc_sets[x].oidSum; break; } @@ -18758,6 +19746,7 @@ WOLFSSL_EC_GROUP *wolfSSL_EC_GROUP_new_by_curve_name(int nid) for (x = 0; ecc_sets[x].size != 0; x++) if (ecc_sets[x].id == g->curve_nid) { g->curve_idx = x; + g->curve_oid = ecc_sets[x].oidSum; break; } @@ -20293,10 +21282,13 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) #ifndef NO_CERTS WOLFSSL_X509 *wolfSSL_PEM_read_bio_X509(WOLFSSL_BIO *bp, WOLFSSL_X509 **x, - pem_password_cb *cb, void *u) { + pem_password_cb *cb, void *u) + { +#ifndef NO_FILESYSTEM WOLFSSL_X509* x509 = NULL; - const unsigned char* pem = NULL; + unsigned char* pem = NULL; int pemSz; + int pemAlloced = 0; WOLFSSL_ENTER("wolfSSL_PEM_read_bio_X509"); @@ -20305,12 +21297,45 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) return NULL; } - pemSz = wolfSSL_BIO_get_mem_data(bp, &pem); - if (pemSz <= 0 || pem == NULL) { - WOLFSSL_MSG("Issue getting WOLFSSL_BIO mem"); - WOLFSSL_LEAVE("wolfSSL_PEM_read_bio_X509", pemSz); - return NULL; + if (bp->type == BIO_MEMORY) { + pemSz = wolfSSL_BIO_get_mem_data(bp, &pem); + if (pemSz <= 0 || pem == NULL) { + WOLFSSL_MSG("Issue getting WOLFSSL_BIO mem"); + WOLFSSL_LEAVE("wolfSSL_PEM_read_bio_X509", pemSz); + return NULL; + } } + else if (bp->type == BIO_FILE) { + long i; + long l; + + /* Read in next certificate from file but no more. */ + i = XFTELL(bp->file); + XFSEEK(bp->file, 0, SEEK_END); + l = XFTELL(bp->file); + XFSEEK(bp->file, i, SEEK_SET); + pem = (unsigned char*)XMALLOC(l - i, 0, DYNAMIC_TYPE_TMP_BUFFER); + if (pem == NULL) + return NULL; + pemAlloced = 1; + + i = 0; + /* TODO: Inefficient + * reading in one byte at a time until see END_CERT + */ + while ((l = wolfSSL_BIO_read(bp, (char *)&pem[i], 1)) == 1) { + i++; + if (i > 26 && XMEMCMP((char *)&pem[i-26], END_CERT, 25) == 0) + break; + } + #ifdef WOLFSSL_NGINX + if (l == 0) + wc_last_error = ((ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE); + #endif + pemSz = (int)i; + } + else + return NULL; x509 = wolfSSL_X509_load_certificate_buffer(pem, pemSz, SSL_FILETYPE_PEM); @@ -20319,10 +21344,20 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) *x = x509; } + if (pemAlloced) + XFREE(pem, NULL, DYNAMIC_TYPE_TMP_BUFFER); + (void)cb; (void)u; return x509; +#else + (void)bp; + (void)x; + (void)cb; + (void)u; + return NULL; +#endif } @@ -20346,7 +21381,16 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) } #endif /* ifndef NO_CERTS */ -#if defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(HAVE_STUNNEL) +#if defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) || defined(OPENSSL_EXTRA) + #ifndef NO_CERTS + void wolfSSL_X509_NAME_free(WOLFSSL_X509_NAME *name){ + FreeX509Name(name, NULL); + WOLFSSL_ENTER("wolfSSL_X509_NAME_free"); + } + #endif /* NO_CERTS */ +#endif + +#if defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) unsigned char *wolfSSL_SHA1(const unsigned char *d, size_t n, unsigned char *md) { @@ -20357,13 +21401,41 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) return NULL; } - char wolfSSL_CTX_use_certificate(WOLFSSL_CTX *ctx, WOLFSSL_X509 *x) { - (void)ctx; - (void)x; - WOLFSSL_ENTER("wolfSSL_CTX_use_certificate"); - WOLFSSL_STUB("wolfSSL_CTX_use_certificate"); + char wolfSSL_CTX_use_certificate(WOLFSSL_CTX *ctx, WOLFSSL_X509 *x) + { + int ret; - return 0; + WOLFSSL_ENTER("wolfSSL_CTX_use_certificate"); + + FreeDer(&ctx->certificate); /* Make sure previous is free'd */ + ret = AllocDer(&ctx->certificate, x->derCert->length, CERT_TYPE, + ctx->heap); + if (ret != 0) + return 0; + + XMEMCPY(ctx->certificate->buffer, x->derCert->buffer, + x->derCert->length); +#ifdef KEEP_OUR_CERT + if (ctx->ourCert != NULL && ctx->ownOurCert) { + FreeX509(ctx->ourCert); + XFREE(ctx->ourCert, ctx->heap, DYNAMIC_TYPE_X509); + } + ctx->ourCert = x; + ctx->ownOurCert = 0; +#endif + + /* Update the available options with public keys. */ + switch (x->pubKeyOID) { + case RSAk: + ctx->haveRSA = 1; + break; + case ECDSAk: + ctx->haveECC = 1; + ctx->pkCurveOID = x->pkCurveOID; + break; + } + + return SSL_SUCCESS; } int wolfSSL_BIO_read_filename(WOLFSSL_BIO *b, const char *name) { @@ -20401,6 +21473,11 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) int i; WOLFSSL_ENTER("wolfSSL_OBJ_osn2nid"); + /* Nginx uses this OpenSSL string. */ + if (XSTRNCMP(sn, "prime256v1", 10) == 0) + sn = "SECP256R1"; + if (XSTRNCMP(sn, "secp384r1", 10) == 0) + sn = "SECP384R1"; /* find based on name and return NID */ for (i = 0; i < ecc_sets[i].size; i++) { if (XSTRNCMP(sn, ecc_sets[i].name, ECC_MAXNAME) == 0) { @@ -20420,6 +21497,14 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) } + void wolfSSL_set_verify_depth(WOLFSSL *ssl, int depth) { + (void)ssl; + (void)depth; + WOLFSSL_ENTER("wolfSSL_set_verify_depth"); + WOLFSSL_STUB("wolfSSL_set_verify_depth"); + + } + void* wolfSSL_get_app_data( const WOLFSSL *ssl) { /* checkout exdata stuff... */ @@ -20476,14 +21561,6 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) return NULL; } -#ifndef NO_CERTS - void wolfSSL_X509_NAME_free(WOLFSSL_X509_NAME *name){ - FreeX509Name(name, NULL); - WOLFSSL_ENTER("wolfSSL_X509_NAME_free"); - WOLFSSL_STUB("wolfSSL_X509_NAME_free"); - } -#endif /* NO_CERTS */ - void wolfSSL_sk_X509_NAME_pop_free(STACK_OF(WOLFSSL_X509_NAME)* sk, void f (WOLFSSL_X509_NAME*)){ (void) sk; (void) f; @@ -20523,7 +21600,7 @@ unsigned long wolfSSL_ERR_peek_last_error_line(const char **file, int *line) (void)line; (void)file; -#if defined(DEBUG_WOLFSSL) +#if defined(WOLFSSL_NGINX) || defined(DEBUG_WOLFSSL) { int ret; @@ -20558,7 +21635,7 @@ int wolfSSL_CTX_use_PrivateKey(WOLFSSL_CTX *ctx, WOLFSSL_EVP_PKEY *pkey) void* wolfSSL_CTX_get_ex_data(const WOLFSSL_CTX* ctx, int idx) { WOLFSSL_ENTER("wolfSSL_CTX_get_ex_data"); - #ifdef HAVE_STUNNEL + #ifdef HAVE_EX_DATA if(ctx != NULL && idx < MAX_EX_DATA && idx >= 0) { return ctx->ex_data[idx]; } @@ -20569,24 +21646,26 @@ void* wolfSSL_CTX_get_ex_data(const WOLFSSL_CTX* ctx, int idx) return NULL; } - int wolfSSL_CTX_get_ex_new_index(long idx, void* arg, void* a, void* b, void* c) { + static int ctx_idx = 0; + WOLFSSL_ENTER("wolfSSL_CTX_get_ex_new_index"); (void)idx; (void)arg; (void)a; (void)b; (void)c; - return 0; + + return ctx_idx++; } int wolfSSL_CTX_set_ex_data(WOLFSSL_CTX* ctx, int idx, void* data) { WOLFSSL_ENTER("wolfSSL_CTX_set_ex_data"); - #ifdef HAVE_STUNNEL + #ifdef HAVE_EX_DATA if (ctx != NULL && idx < MAX_EX_DATA) { ctx->ex_data[idx] = data; @@ -20604,7 +21683,7 @@ int wolfSSL_CTX_set_ex_data(WOLFSSL_CTX* ctx, int idx, void* data) int wolfSSL_set_ex_data(WOLFSSL* ssl, int idx, void* data) { WOLFSSL_ENTER("wolfSSL_set_ex_data"); -#if defined(FORTRESS) || defined(HAVE_STUNNEL) +#if defined(HAVE_EX_DATA) || defined(FORTRESS) if (ssl != NULL && idx < MAX_EX_DATA) { ssl->ex_data[idx] = data; @@ -20622,20 +21701,23 @@ int wolfSSL_set_ex_data(WOLFSSL* ssl, int idx, void* data) int wolfSSL_get_ex_new_index(long idx, void* data, void* cb1, void* cb2, void* cb3) { + static int ssl_idx = 0; + WOLFSSL_ENTER("wolfSSL_get_ex_new_index"); (void)idx; (void)data; (void)cb1; (void)cb2; (void)cb3; - return 0; + + return ssl_idx++; } void* wolfSSL_get_ex_data(const WOLFSSL* ssl, int idx) { WOLFSSL_ENTER("wolfSSL_get_ex_data"); -#if defined(FORTRESS) || defined(HAVE_STUNNEL) +#if defined(HAVE_EX_DATA) || defined(FORTRESS) if (ssl != NULL && idx < MAX_EX_DATA && idx >= 0) return ssl->ex_data[idx]; #else @@ -20652,7 +21734,7 @@ WOLFSSL_DSA *wolfSSL_PEM_read_bio_DSAparams(WOLFSSL_BIO *bp, WOLFSSL_DSA **x, WOLFSSL_DSA* dsa; DsaKey* key; int length; - const unsigned char* buf; + unsigned char* buf; word32 bufSz; int ret; word32 idx = 0; @@ -20766,38 +21848,202 @@ int wolfSSL_OBJ_txt2nid(const char* s) { } -WOLFSSL_BIO *wolfSSL_BIO_new_file(const char *filename, const char *mode) { +WOLFSSL_BIO *wolfSSL_BIO_new_file(const char *filename, const char *mode) +{ +#ifndef NO_FILESYSTEM + WOLFSSL_BIO* bio; + XFILE fp; + + WOLFSSL_ENTER("wolfSSL_BIO_new_file"); + + fp = XFOPEN(filename, mode); + if (fp == NULL) + return NULL; + + bio = wolfSSL_BIO_new(wolfSSL_BIO_s_file()); + if (bio == NULL) + return bio; + + if (wolfSSL_BIO_set_fp(bio, fp, BIO_CLOSE) != SSL_SUCCESS) { + wolfSSL_BIO_free(bio); + bio = NULL; + } + + return bio; +#else (void)filename; (void)mode; - WOLFSSL_ENTER("wolfSSL_BIO_new_file"); - WOLFSSL_STUB("wolfSSL_BIO_new_file"); - return NULL; +#endif } -WOLFSSL_DH *wolfSSL_PEM_read_bio_DHparams(WOLFSSL_BIO *bp, WOLFSSL_DH **x, +#ifndef NO_DH +WOLFSSL_DH *wolfSSL_PEM_read_bio_DHparams(WOLFSSL_BIO *bio, WOLFSSL_DH **x, pem_password_cb *cb, void *u) { - (void) bp; - (void) x; - (void) cb; - (void) u; +#ifndef NO_FILESYSTEM + WOLFSSL_DH* localDh = NULL; + unsigned char* mem = NULL; + word32 size; + long sz; + int ret; + DerBuffer *der = NULL; + byte* p = NULL; + byte* g = NULL; + word32 pSz = MAX_DH_SIZE; + word32 gSz = MAX_DH_SIZE; + int memAlloced = 0; WOLFSSL_ENTER("wolfSSL_PEM_read_bio_DHparams"); - WOLFSSL_STUB("wolfSSL_PEM_read_bio_DHparams"); + (void)cb; + (void)u; - return NULL; -} + if (bio == NULL) { + WOLFSSL_MSG("Bad Function Argument bio is NULL"); + return NULL; + } + if (bio->type == BIO_MEMORY) { + /* Use the buffer directly. */ + ret = wolfSSL_BIO_get_mem_data(bio, &mem); + if (mem == NULL || ret <= 0) { + WOLFSSL_MSG("Failed to get data from bio struct"); + goto end; + } + size = ret; + } + else if (bio->type == BIO_FILE) { + /* Read whole file into a new buffer. */ + XFSEEK(bio->file, 0, SEEK_END); + sz = XFTELL(bio->file); + XFSEEK(bio->file, 0, SEEK_SET); + if (sz <= 0L) + goto end; + mem = (unsigned char*)XMALLOC(sz, NULL, DYNAMIC_TYPE_TMP_BUFFER); + if (mem == NULL) + goto end; + memAlloced = 1; -int wolfSSL_PEM_write_bio_X509(WOLFSSL_BIO *bp, WOLFSSL_X509 *x) { - (void)bp; + if (wolfSSL_BIO_read(bio, (char *)mem, (int)sz) <= 0) + goto end; + size = (word32)sz; + } + else { + WOLFSSL_MSG("BIO type not supported for reading DH parameters"); + goto end; + } + + ret = PemToDer(mem, size, DH_PARAM_TYPE, &der, NULL, NULL, NULL); + if (ret != 0) + goto end; + + /* Use the object passed in, otherwise allocate a new object */ + if (x != NULL) + localDh = *x; + if (localDh == NULL) { + localDh = (WOLFSSL_DH*)XMALLOC(sizeof(WOLFSSL_DH), NULL, + DYNAMIC_TYPE_OPENSSL); + if (localDh == NULL) + goto end; + XMEMSET(localDh, 0, sizeof(WOLFSSL_DH)); + } + + /* Load data in manually */ + p = (byte*)XMALLOC(pSz, NULL, DYNAMIC_TYPE_TMP_BUFFER); + g = (byte*)XMALLOC(gSz, NULL, DYNAMIC_TYPE_TMP_BUFFER); + if (p == NULL || g == NULL) + goto end; + + /* Extract the p and g as data from the DER encoded DH parameters. */ + ret = wc_DhParamsLoad(der->buffer, der->length, p, &pSz, g, &gSz); + if (ret != 0) { + if (x != NULL && localDh != *x) + XFREE(localDh, NULL, DYNAMIC_TYPE_OPENSSL); + localDh = NULL; + goto end; + } + + if (x != NULL) + *x = localDh; + + /* Put p and g in as big numbers. */ + if (localDh->p != NULL) { + wolfSSL_BN_free(localDh->p); + localDh->p = NULL; + } + if (localDh->g != NULL) { + wolfSSL_BN_free(localDh->g); + localDh->g = NULL; + } + localDh->p = wolfSSL_BN_bin2bn(p, pSz, NULL); + localDh->g = wolfSSL_BN_bin2bn(g, gSz, NULL); + if (localDh->p == NULL || localDh->g == NULL) { + if (x != NULL && localDh != *x) + wolfSSL_DH_free(localDh); + localDh = NULL; + } + +end: + if (memAlloced) XFREE(mem, NULL, DYNAMIC_TYPE_TMP_BUFFER); + if (der != NULL) FreeDer(&der); + XFREE(p, NULL, DYNAMIC_TYPE_TMP_BUFFER); + XFREE(g, NULL, DYNAMIC_TYPE_TMP_BUFFER); + return localDh; +#else + (void)bio; (void)x; - WOLFSSL_ENTER("wolfSSL_PEM_write_bio_X509"); - WOLFSSL_STUB("wolfSSL_PEM_write_bio_X509"); + (void)cb; + (void)u; + return NULL; +#endif +} +#endif - return 0; + +int wolfSSL_PEM_write_bio_X509(WOLFSSL_BIO *bio, WOLFSSL_X509 *cert) +{ + byte* certDer; + int derSz; + int pemSz; + int ret; + + WOLFSSL_ENTER("wolfSSL_PEM_write_bio_X509"); + + if (bio == NULL || cert == NULL) { + return SSL_FAILURE; + } + + if (bio->type != BIO_MEMORY) { + WOLFSSL_MSG("BIO type not supported for writing X509 as PEM"); + return SSL_FAILURE; + } + + certDer = cert->derCert->buffer; + derSz = cert->derCert->length; + + /* Get PEM encoded length and allocate memory for it. */ + pemSz = wc_DerToPem(certDer, derSz, NULL, 0, CERT_TYPE); + if (pemSz < 0) { + WOLFSSL_LEAVE("wolfSSL_PEM_write_bio_X509", pemSz); + return SSL_FAILURE; + } + if (bio->mem != NULL) { + XFREE(bio->mem, NULL, DYNAMIC_TYPE_OPENSSL); + } + bio->mem = (byte*)XMALLOC(pemSz, NULL, DYNAMIC_TYPE_OPENSSL); + if (bio->mem != NULL) { + return SSL_FAILURE; + } + bio->memLen = pemSz; + + ret = wc_DerToPemEx(certDer, derSz, bio->mem, bio->memLen, NULL, CERT_TYPE); + if (ret < 0) { + WOLFSSL_LEAVE("wolfSSL_PEM_write_bio_X509", ret); + return SSL_FAILURE; + } + + return SSL_SUCCESS; } @@ -20847,7 +22093,7 @@ long wolfSSL_CTX_set_tmp_dh(WOLFSSL_CTX* ctx, WOLFSSL_DH* dh) /* stunnel compatibility functions*/ -#if defined(OPENSSL_EXTRA) && defined(HAVE_STUNNEL) +#if defined(OPENSSL_EXTRA) && (defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX)) void WOLFSSL_ERR_remove_thread_state(void* pid) { (void) pid; @@ -20863,10 +22109,12 @@ void wolfSSL_print_all_errors_fp(XFILE *fp) int wolfSSL_SESSION_set_ex_data(WOLFSSL_SESSION* session, int idx, void* data) { WOLFSSL_ENTER("wolfSSL_SESSION_set_ex_data"); +#ifdef HAVE_EX_DATA if(session != NULL && idx < MAX_EX_DATA) { session->ex_data[idx] = data; return SSL_SUCCESS; } +#endif return SSL_FAILURE; } @@ -20892,8 +22140,10 @@ int wolfSSL_SESSION_get_ex_new_index(long idx, void* data, void* cb1, void* wolfSSL_SESSION_get_ex_data(const WOLFSSL_SESSION* session, int idx) { WOLFSSL_ENTER("wolfSSL_SESSION_get_ex_data"); +#ifdef HAVE_EX_DATA if (session != NULL && idx < MAX_EX_DATA && idx >= 0) return session->ex_data[idx]; +#endif return NULL; } @@ -20949,11 +22199,13 @@ void wolfSSL_ERR_load_crypto_strings(void) unsigned long wolfSSL_ERR_peek_last_error(void) { - unsigned long l = 0UL; WOLFSSL_ENTER("wolfSSL_ERR_peek_last_error"); - WOLFSSL_STUB("wolfSSL_ERR_peek_last_error"); - return l; +#if defined(OPENSSL_ERR_ONE) + return wc_last_error; +#else + return (unsigned long)(0 - NOT_COMPILED_IN); +#endif } @@ -21001,35 +22253,40 @@ int wolfSSL_CIPHER_get_bits(const WOLFSSL_CIPHER *c, int *alg_bits) int wolfSSL_sk_X509_NAME_num(const STACK_OF(WOLFSSL_X509_NAME) *s) { - (void) s; WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_num"); - WOLFSSL_STUB("wolfSSL_sk_X509_NAME_num"); - return SSL_FAILURE; + if (s == NULL) + return -1; + return (int)s->num; } int wolfSSL_sk_X509_num(const STACK_OF(WOLFSSL_X509) *s) { - (void) s; WOLFSSL_ENTER("wolfSSL_sk_X509_num"); - WOLFSSL_STUB("wolfSSL_sk_X509_num"); - return SSL_FAILURE; + if (s == NULL) + return -1; + return (int)s->num; } -int wolfSSL_X509_NAME_print_ex(WOLFSSL_BIO* bio, WOLFSSL_X509_NAME* nm, +int wolfSSL_X509_NAME_print_ex(WOLFSSL_BIO* bio, WOLFSSL_X509_NAME* name, int indent, unsigned long flags) { - (void)bio; - (void)nm; - (void)indent; + int i; (void)flags; WOLFSSL_ENTER("wolfSSL_X509_NAME_print_ex"); - WOLFSSL_STUB("wolfSSL_X509_NAME_print_ex"); - return SSL_FAILURE; + for (i = 0; i < indent; i++) + BIO_write(bio, " ", 1); + + if (flags == XN_FLAG_RFC2253) + BIO_write(bio, name->name + 1, name->sz - 2); + else + BIO_write(bio, name->name, name->sz); + + return SSL_SUCCESS; } @@ -21066,23 +22323,27 @@ int wolfSSL_get_state(const WOLFSSL* ssl) void* wolfSSL_sk_X509_NAME_value(const STACK_OF(WOLFSSL_X509_NAME)* sk, int i) { - (void)sk; - (void)i; WOLFSSL_ENTER("wolfSSL_sk_X509_NAME_value"); - WOLFSSL_STUB("wolfSSL_sk_X509_NAME_value"); - return NULL; + for (; sk != NULL && i > 0; i--) + sk = sk->next; + + if (i != 0 || sk == NULL) + return NULL; + return sk->data.name; } void* wolfSSL_sk_X509_value(STACK_OF(WOLFSSL_X509)* sk, int i) { - (void)sk; - (void)i; WOLFSSL_ENTER("wolfSSL_sk_X509_value"); - WOLFSSL_STUB("wolfSSL_sk_X509_value"); - return NULL; + for (; sk != NULL && i > 0; i--) + sk = sk->next; + + if (i != 0 || sk == NULL) + return NULL; + return sk->data.x509; } @@ -21200,6 +22461,16 @@ void wolfSSL_CTX_set_servername_callback(WOLFSSL_CTX* ctx, CallbackSniRecv cb) ctx->sniRecvCb = cb; } +int wolfSSL_CTX_set_tlsext_servername_callback(WOLFSSL_CTX* ctx, + CallbackSniRecv cb) +{ + WOLFSSL_ENTER("wolfSSL_CTX_set_tlsext_servername_callback"); + if (ctx) { + ctx->sniRecvCb = cb; + return 1; + } + return 0; +} void wolfSSL_CTX_set_servername_arg(WOLFSSL_CTX* ctx, void* arg) { @@ -21257,7 +22528,7 @@ void wolfSSL_sk_X509_pop_free(STACK_OF(WOLFSSL_X509)* sk, void f (WOLFSSL_X509*) #if (defined(OPENSSL_EXTRA) && defined(HAVE_STUNNEL)) \ - || defined(WOLFSSL_MYSQL_COMPATIBLE) + || defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX) int wolfSSL_CTX_get_verify_mode(WOLFSSL_CTX* ctx) { int mode = 0; @@ -21672,6 +22943,697 @@ int wolfSSL_AsyncPoll(WOLFSSL* ssl, WOLF_EVENT_FLAG flags) } #endif /* WOLFSSL_ASYNC_CRYPT */ +#if defined(WOLFSSL_NGINX) +void wolfSSL_OPENSSL_config(char *config_name) +{ + WOLFSSL_STUB("wolfSSL_OPENSSL_config"); + (void)config_name; +} + +int wolfSSL_X509_get_ex_new_index(int idx, void *arg, void *a, void *b, void *c) +{ + static int x509_idx = 0; + + WOLFSSL_ENTER("wolfSSL_X509_get_ex_new_index"); + (void)idx; + (void)arg; + (void)a; + (void)b; + (void)c; + + return x509_idx++; +} + +void *wolfSSL_X509_get_ex_data(X509 *x509, int idx) +{ + WOLFSSL_ENTER("wolfSSL_X509_get_ex_data"); + #ifdef HAVE_EX_DATA + if (x509 != NULL && idx < MAX_EX_DATA && idx >= 0) { + return x509->ex_data[idx]; + } + #else + (void)x509; + (void)idx; + #endif + return NULL; +} +int wolfSSL_X509_set_ex_data(X509 *x509, int idx, void *data) +{ + WOLFSSL_ENTER("wolfSSL_X509_set_ex_data"); + #ifdef HAVE_EX_DATA + if (x509 != NULL && idx < MAX_EX_DATA) + { + x509->ex_data[idx] = data; + return SSL_SUCCESS; + } + #else + (void)x509; + (void)idx; + (void)data; + #endif + return SSL_FAILURE; +} +int wolfSSL_X509_NAME_digest(const WOLFSSL_X509_NAME *name, + const WOLFSSL_EVP_MD *type, unsigned char *md, unsigned int *len) +{ + WOLFSSL_ENTER("wolfSSL_X509_NAME_digest"); + + if (name == NULL || type == NULL) + return SSL_FAILURE; + + return wolfSSL_EVP_Digest((unsigned char*)name->fullName.fullName, + name->fullName.fullNameLen, md, len, type, NULL); +} + +long wolfSSL_SSL_CTX_get_timeout(const WOLFSSL_CTX *ctx) +{ + WOLFSSL_ENTER("wolfSSL_SSL_CTX_get_timeout"); + + if (ctx == NULL) + return 0; + + return ctx->timeout; +} + +#ifdef HAVE_ECC +int wolfSSL_SSL_CTX_set_tmp_ecdh(WOLFSSL_CTX *ctx, WOLFSSL_EC_KEY *ecdh) +{ + WOLFSSL_ENTER("wolfSSL_SSL_CTX_set_tmp_ecdh"); + + if (ctx == NULL || ecdh == NULL) + return BAD_FUNC_ARG; + + ctx->ecdhCurveOID = ecdh->group->curve_oid; + + return SSL_SUCCESS; +} +#endif + +/* Assumes that the session passed in is from the cache. */ +int wolfSSL_SSL_CTX_remove_session(WOLFSSL_CTX *ctx, WOLFSSL_SESSION *s) +{ + WOLFSSL_ENTER("wolfSSL_SSL_CTX_remove_session"); + + if (ctx == NULL || s == NULL) + return BAD_FUNC_ARG; + +#ifdef HAVE_EXT_CACHE + if (!ctx->internalCacheOff) +#endif + { + /* Don't remove session just timeout session. */ + s->timeout = 0; + } + +#ifdef HAVE_EXT_CACHE + if (ctx->rem_sess_cb != NULL) + ctx->rem_sess_cb(ctx, s); +#endif + + return 0; +} + +BIO *wolfSSL_SSL_get_rbio(const WOLFSSL *s) +{ + WOLFSSL_ENTER("wolfSSL_SSL_get_rbio"); + (void)s; + /* Nginx sets the buffer size if the read BIO is different to write BIO. + * The setting buffer size doesn't do anything so return NULL for both. + */ + return NULL; +} +BIO *wolfSSL_SSL_get_wbio(const WOLFSSL *s) +{ + WOLFSSL_ENTER("wolfSSL_SSL_get_wbio"); + (void)s; + /* Nginx sets the buffer size if the read BIO is different to write BIO. + * The setting buffer size doesn't do anything so return NULL for both. + */ + return NULL; +} + +int wolfSSL_SSL_do_handshake(WOLFSSL *s) +{ + WOLFSSL_ENTER("wolfSSL_SSL_do_handshake"); + + if (s == NULL) + return SSL_FAILURE; + + if (s->options.side == WOLFSSL_CLIENT_END) + return wolfSSL_connect(s); + return wolfSSL_accept(s); +} + +int wolfSSL_SSL_in_init(WOLFSSL *s) +{ + WOLFSSL_ENTER("wolfSSL_SSL_in_init"); + + if (s == NULL) + return SSL_FAILURE; + + if (s->options.side == WOLFSSL_CLIENT_END) + return s->options.connectState < SECOND_REPLY_DONE; + return s->options.acceptState < ACCEPT_THIRD_REPLY_DONE; +} + +WOLFSSL_SESSION *wolfSSL_SSL_get0_session(const WOLFSSL *ssl) +{ + WOLFSSL_SESSION *session; + + WOLFSSL_ENTER("wolfSSL_SSL_get0_session"); + + if (ssl == NULL) { + return NULL; + } + + session = wolfSSL_get_session((WOLFSSL*)ssl); + +#ifdef HAVE_EXT_CACHE + ((WOLFSSL*)ssl)->extSession = session; +#endif + + return session; +} + +int wolfSSL_X509_check_host(X509 *x, const char *chk, size_t chklen, + unsigned int flags, char **peername) +{ + int ret; + DecodedCert dCert; + + WOLFSSL_ENTER("wolfSSL_X509_check_host"); + + /* flags and peername not needed for Nginx. */ + (void)flags; + (void)peername; + + InitDecodedCert(&dCert, x->derCert->buffer, x->derCert->length, NULL); + ret = ParseCertRelative(&dCert, CERT_TYPE, 0, NULL); + if (ret != 0) + return SSL_FAILURE; + + ret = CheckHostName(&dCert, (char *)chk, chklen); + FreeDecodedCert(&dCert); + if (ret != 0) + return SSL_FAILURE; + return SSL_SUCCESS; +} + +int wolfSSL_i2a_ASN1_INTEGER(BIO *bp, const WOLFSSL_ASN1_INTEGER *a) +{ + static char num[16] = { '0', '1', '2', '3', '4', '5', '6', '7', + '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' }; + int i; + word32 j; + word32 len = 0; + + WOLFSSL_ENTER("wolfSSL_i2a_ASN1_INTEGER"); + + if (bp == NULL || a == NULL) + return SSL_FAILURE; + + /* Skip ASN.1 INTEGER (type) byte. */ + i = 1; + /* When indefinte length, can't determine length with data available. */ + if (a->data[i] == 0x80) + return 0; + /* One length byte if less than 0x80. */ + if (a->data[i] < 0x80) + len = a->data[i++]; + /* Multiple length byte if greater than 0x80. */ + else if (a->data[i] > 0x80) { + switch (a->data[i++] - 0x80) { + case 4: + len |= a->data[i++] << 24; + case 3: + len |= a->data[i++] << 16; + case 2: + len |= a->data[i++] << 8; + case 1: + len |= a->data[i++]; + break; + default: + /* Not supporting greater than 4 bytes of length. */ + return 0; + } + } + + /* Zero length integer is the value zero. */ + if (len == 0) { + wolfSSL_BIO_write(bp, "00", 2); + return 2; + } + + /* Don't do negative - just write out every byte. */ + for (j = 0; j < len; i++,j++) { + wolfSSL_BIO_write(bp, &num[a->data[i] >> 4], 1); + wolfSSL_BIO_write(bp, &num[a->data[i] & 0xf], 1); + } + + /* Two nibbles written for each byte. */ + return len * 2; +} + +unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, int *line, + const char **data, int *flags) +{ + WOLFSSL_ENTER("wolfSSL_ERR_peek_error_line_data"); + + (void)line; + (void)file; + + /* No data or flags stored - error display only in Nginx. */ + if (data != NULL) { + *data = ""; + } + if (flags != NULL) { + *flags = 0; + } + +#if defined(OPENSSL_ERR_ONE) + if (line != NULL) { + *line = (int)wc_last_error_line; + } + if (file != NULL) { + *file = (char*)wc_last_error_file; + } + return wc_last_error; +#else + return (unsigned long)(0 - NOT_COMPILED_IN); +#endif + +} + +#ifdef HAVE_SESSION_TICKET +/* The ticket key callback as used in OpenSSL is stored here. */ +static int (*ticketKeyCb)(WOLFSSL *ssl, unsigned char *name, unsigned char *iv, + WOLFSSL_EVP_CIPHER_CTX *ectx, WOLFSSL_HMAC_CTX *hctx, int enc) = NULL; + +/* Implementation of session ticket encryption/decryption using OpenSSL + * callback to initialize the cipher and HMAC. + * + * ssl The SSL/TLS object. + * keyName The key name - used to identify the key to be used. + * iv The IV to use. + * mac The MAC of the encrypted data. + * enc Encrypt ticket. + * encTicket The ticket data. + * encTicketLen The length of the ticket data. + * encLen The encrypted/decrypted ticket length - output length. + * ctx Ignored. Application specific data. + * returns WOLFSSL_TICKET_RET_OK to indicate success, + * WOLFSSL_TICKET_RET_CREATE if a new ticket is required and + * WOLFSSL_TICKET_RET_FATAL on error. + */ +static int wolfSSL_TicketKeyCb(WOLFSSL* ssl, + unsigned char keyName[WOLFSSL_TICKET_NAME_SZ], + unsigned char iv[WOLFSSL_TICKET_IV_SZ], + unsigned char mac[WOLFSSL_TICKET_MAC_SZ], + int enc, unsigned char* encTicket, + int encTicketLen, int* encLen, void* ctx) +{ + byte digest[MAX_DIGEST_SIZE]; + WOLFSSL_EVP_CIPHER_CTX evpCtx; + WOLFSSL_HMAC_CTX hmacCtx; + unsigned int mdSz = 0; + int len = 0; + int ret = WOLFSSL_TICKET_RET_FATAL; + int res; + + (void)ctx; + + wolfSSL_EVP_CIPHER_CTX_init(&evpCtx); + /* Initialize the cipher and HMAC. */ + res = ticketKeyCb(ssl, keyName, iv, &evpCtx, &hmacCtx, enc); + if (res != 1 && res != 2) + return WOLFSSL_TICKET_RET_FATAL; + + if (enc) + { + /* Encrypt in place. */ + if (!wolfSSL_EVP_CipherUpdate(&evpCtx, encTicket, &len, + encTicket, encTicketLen)) + goto end; + encTicketLen = len; + if (!wolfSSL_EVP_EncryptFinal(&evpCtx, &encTicket[encTicketLen], &len)) + goto end; + /* Total length of encrypted data. */ + encTicketLen += len; + *encLen = encTicketLen; + + /* HMAC the encrypted data into the parameter 'mac'. */ + wolfSSL_HMAC_Update(&hmacCtx, encTicket, encTicketLen); + wolfSSL_HMAC_Final(&hmacCtx, mac, &mdSz); + } + else + { + /* HMAC the encrypted data and compare it to the passed in data. */ + wolfSSL_HMAC_Update(&hmacCtx, encTicket, encTicketLen); + wolfSSL_HMAC_Final(&hmacCtx, digest, &mdSz); + if (XMEMCMP(mac, digest, mdSz) != 0) + goto end; + + /* Decrypt the ticket data in place. */ + if (!wolfSSL_EVP_CipherUpdate(&evpCtx, encTicket, &len, + encTicket, encTicketLen)) + goto end; + encTicketLen = len; + if (!wolfSSL_EVP_DecryptFinal(&evpCtx, &encTicket[encTicketLen], &len)) + goto end; + /* Total length of decrypted data. */ + *encLen = encTicketLen + len; + } + + ret = (res == 2) ? WOLFSSL_TICKET_RET_CREATE : WOLFSSL_TICKET_RET_OK; +end: + return ret; +} + +/* Set the callback to use when encrypting/decrypting tickets. + * + * ctx The SSL/TLS context object. + * cb The OpenSSL session ticket callback. + * returns SSL_SUCCESS to indicate success. + */ +int wolfSSL_CTX_set_tlsext_ticket_key_cb(WOLFSSL_CTX *ctx, int (*cb)( + WOLFSSL *ssl, unsigned char *name, unsigned char *iv, + WOLFSSL_EVP_CIPHER_CTX *ectx, WOLFSSL_HMAC_CTX *hctx, int enc)) +{ + /* Store callback in a global. */ + ticketKeyCb = cb; + /* Set the ticket encryption callback to be a wrapper around OpenSSL + * callback. + */ + ctx->ticketEncCb = wolfSSL_TicketKeyCb; + + return SSL_SUCCESS; +} +#endif /* HAVE_SESSION_TICKET */ + +#ifdef HAVE_OCSP +/* Not an OpenSSL API. */ +int wolfSSL_get_ocsp_response(WOLFSSL* ssl, byte** response) +{ + *response = ssl->ocspResp; + return ssl->ocspRespSz; +} + +/* Not an OpenSSL API. */ +char* wolfSSL_get_ocsp_url(WOLFSSL* ssl) +{ + return ssl->url; +} + +/* Not an OpenSSL API. */ +int wolfSSL_set_ocsp_url(WOLFSSL* ssl, char* url) +{ + if (ssl == NULL) + return SSL_FAILURE; + + ssl->url = url; + return SSL_SUCCESS; +} + +static INLINE void ato24(const byte* c, word32* u24) +{ + *u24 = (c[0] << 16) | (c[1] << 8) | c[2]; +} + +int wolfSSL_CTX_get_extra_chain_certs(WOLFSSL_CTX* ctx, STACK_OF(X509)** chain) +{ + word32 idx; + word32 length; + WOLFSSL_STACK* node; + WOLFSSL_STACK* last = NULL; + + if (ctx == NULL || chain == NULL) { + chain = NULL; + return SSL_FAILURE; + } + if (ctx->x509Chain != NULL) { + *chain = ctx->x509Chain; + return SSL_SUCCESS; + } + + /* If there are no chains then success! */ + *chain = NULL; + if (ctx->certChain == NULL || ctx->certChain->length == 0) { + return SSL_SUCCESS; + } + + /* Create a new stack of WOLFSSL_X509 object from chain buffer. */ + for (idx = 0; idx < ctx->certChain->length; ) { + node = (WOLFSSL_STACK*)XMALLOC(sizeof(WOLFSSL_STACK), NULL, + DYNAMIC_TYPE_OPENSSL); + if (node == NULL) + return SSL_FAILURE; + node->next = NULL; + + /* 3 byte length | X509 DER data */ + ato24(ctx->certChain->buffer + idx, &length); + idx += 3; + + /* Create a new X509 from DER encoded data. */ + node->data.x509 = wolfSSL_X509_d2i(NULL, ctx->certChain->buffer + idx, + length); + if (node->data.x509 == NULL) { + XFREE(node, NULL, DYNAMIC_TYPE_OPENSSL); + /* Return as much of the chain as we created. */ + ctx->x509Chain = *chain; + return SSL_FAILURE; + } + idx += length; + + /* Add object to the end of the stack. */ + if (last == NULL) { + node->num = 1; + *chain = node; + } + else { + (*chain)->num++; + last->next = node; + } + + last = node; + } + + ctx->x509Chain = *chain; + + return SSL_SUCCESS; +} + +int wolfSSL_CTX_set_tlsext_status_cb(WOLFSSL_CTX* ctx, + int(*cb)(WOLFSSL*, void*)) +{ + if (ctx == NULL || ctx->cm == NULL) + return SSL_FAILURE; + + /* Ensure stapling is on for callback to be used. */ + wolfSSL_CTX_EnableOCSPStapling(ctx); + + if (ctx->cm->ocsp_stapling == NULL) + return SSL_FAILURE; + + ctx->cm->ocsp_stapling->statusCb = cb; + return SSL_SUCCESS; +} + +int wolfSSL_X509_STORE_CTX_get1_issuer(WOLFSSL_X509 **issuer, + WOLFSSL_X509_STORE_CTX *ctx, WOLFSSL_X509 *x) +{ + WOLFSSL_STACK* node; + Signer* ca = NULL; +#ifdef WOLFSSL_SMALL_STACK + DecodedCert* cert = NULL; +#else + DecodedCert cert[1]; +#endif + + if (issuer == NULL || ctx == NULL || x == NULL) + return SSL_FATAL_ERROR; + + if (ctx->chain != NULL) { + for (node = ctx->chain; node != NULL; node = node->next) { + if (wolfSSL_X509_check_issued(node->data.x509, x) == X509_V_OK) { + *issuer = x; + return SSL_SUCCESS; + } + } + } + + +#ifdef WOLFSSL_SMALL_STACK + cert = (DecodedCert*)XMALLOC(sizeof(DecodedCert), NULL, + DYNAMIC_TYPE_TMP_BUFFER); + if (cert == NULL) + return NULL; +#endif + + /* Use existing CA retrieval APIs that use DecodedCert. */ + InitDecodedCert(cert, x->derCert->buffer, x->derCert->length, NULL); + if (ParseCertRelative(cert, CERT_TYPE, 0, NULL) == 0) { + #ifndef NO_SKID + if (cert->extAuthKeyIdSet) + ca = GetCA(ctx->store->cm, cert->extAuthKeyId); + if (ca == NULL) + ca = GetCAByName(ctx->store->cm, cert->issuerHash); + #else /* NO_SKID */ + ca = GetCA(ctx->store->cm, cert->issuerHash); + #endif /* NO SKID */ + } + FreeDecodedCert(cert); +#ifdef WOLFSSL_SMALL_STACK + XFREE(cert, NULL, DYNAMIC_TYPE_TMP_BUFFER); +#endif + + if (ca == NULL) + return SSL_FAILURE; + + *issuer = (WOLFSSL_X509 *)XMALLOC(sizeof(WOLFSSL_X509), 0, + DYNAMIC_TYPE_OPENSSL); + if (*issuer == NULL) + return SSL_FAILURE; + + /* Create an empty certificate as CA doesn't have a certificate. */ + XMEMSET(*issuer, 0, sizeof(WOLFSSL_X509)); + /* TODO: store the full certificate and dup when required. */ + + /* Result is ignored when passed to wolfSSL_OCSP_cert_to_id(). */ + + return SSL_SUCCESS; +} + +void wolfSSL_X509_email_free(STACK_OF(WOLFSSL_STRING) *sk) +{ + WOLFSSL_STACK *curr; + + while (sk != NULL) { + curr = sk; + sk = sk->next; + + XFREE(curr, NULL, DYNAMIC_TYPE_OPENSSL); + } +} + +STACK_OF(WOLFSSL_STRING) *wolfSSL_X509_get1_ocsp(WOLFSSL_X509 *x) +{ + WOLFSSL_STACK *list = NULL; + + if (x->authInfoSz == 0) + return NULL; + + list = (WOLFSSL_STACK*)XMALLOC(sizeof(WOLFSSL_STACK), NULL, + DYNAMIC_TYPE_OPENSSL); + if (list == NULL) + return NULL; + + list->data.string = (char*)x->authInfo; + list->next = NULL; + + return list; +} + +int wolfSSL_X509_check_issued(WOLFSSL_X509 *issuer, WOLFSSL_X509 *subject) +{ + WOLFSSL_X509_NAME *issuerName = wolfSSL_X509_get_issuer_name(subject); + WOLFSSL_X509_NAME *subjectName = wolfSSL_X509_get_subject_name(issuer); + + if (issuerName == NULL || subjectName == NULL) + return X509_V_ERR_SUBJECT_ISSUER_MISMATCH; + + /* Literal matching of encoded names and key ids. */ + if (issuerName->sz != subjectName->sz || + XMEMCMP(issuerName->name, subjectName->name, subjectName->sz) != 0) { + return X509_V_ERR_SUBJECT_ISSUER_MISMATCH; + } + + if (subject->authKeyId != NULL && issuer->subjKeyId != NULL) { + if (subject->authKeyIdSz != issuer->subjKeyIdSz || + XMEMCMP(subject->authKeyId, issuer->subjKeyId, + issuer->subjKeyIdSz) != 0) { + return X509_V_ERR_SUBJECT_ISSUER_MISMATCH; + } + } + + return X509_V_OK; +} + +WOLFSSL_X509* wolfSSL_X509_dup(WOLFSSL_X509 *x) +{ + return wolfSSL_X509_d2i(NULL, x->derCert->buffer, x->derCert->length); +} + +char* wolfSSL_sk_WOLFSSL_STRING_value(STACK_OF(WOLFSSL_STRING)* strings, + int idx) +{ + for (; idx > 0 && strings != NULL; idx--) + strings = strings->next; + if (strings == NULL) + return NULL; + return strings->data.string; +} +#endif /* HAVE_OCSP */ + +#ifdef HAVE_ALPN +void wolfSSL_get0_alpn_selected(const WOLFSSL *ssl, const unsigned char **data, + unsigned int *len) +{ + word16 nameLen; + + if (ssl != NULL && data != NULL && len != NULL) { + TLSX_ALPN_GetRequest(ssl->extensions, (void **)data, &nameLen); + *len = nameLen; + } +} + +int wolfSSL_select_next_proto(unsigned char **out, unsigned char *outLen, + const unsigned char *in, unsigned int inLen, + const unsigned char *clientNames, + unsigned int clientLen) +{ + unsigned int i, j; + byte lenIn, lenClient; + + if (out == NULL || outLen == NULL || in == NULL || clientNames == NULL) + return OPENSSL_NPN_UNSUPPORTED; + + for (i = 0; i < inLen; i += lenIn) { + lenIn = in[i++]; + for (j = 0; j < clientLen; j += lenClient) { + lenClient = clientNames[j++]; + + if (lenIn != lenClient) + continue; + + if (XMEMCMP(in + i, clientNames + j, lenIn) == 0) { + *out = (unsigned char *)(in + i); + *outLen = lenIn; + return OPENSSL_NPN_NEGOTIATED; + } + } + } + + *out = (unsigned char *)clientNames + 1; + *outLen = clientNames[0]; + return OPENSSL_NPN_NO_OVERLAP; +} + +void wolfSSL_CTX_set_alpn_select_cb(WOLFSSL_CTX *ctx, + int (*cb) (WOLFSSL *ssl, + const unsigned char **out, + unsigned char *outlen, + const unsigned char *in, + unsigned int inlen, + void *arg), void *arg) +{ + if (ctx != NULL) { + ctx->alpnSelect = cb; + ctx->alpnSelectArg = arg; + } +} +#endif /* HAVE_ALPN */ + +#endif /* WOLFSSL_NGINX */ #ifdef OPENSSL_EXTRA int wolfSSL_CTX_set_msg_callback(WOLFSSL_CTX *ctx, SSL_Msg_Cb cb) diff --git a/src/tls.c b/src/tls.c index 3aa5a781b..050067601 100644 --- a/src/tls.c +++ b/src/tls.c @@ -1095,23 +1095,42 @@ static int TLSX_ALPN_ParseAndSet(WOLFSSL *ssl, byte *input, word16 length, TLSX *extension; ALPN *alpn = NULL, *list; + if (OPAQUE16_LEN > length) + return BUFFER_ERROR; + + ato16(input, &size); + offset += OPAQUE16_LEN; + extension = TLSX_Find(ssl->extensions, TLSX_APPLICATION_LAYER_PROTOCOL); if (extension == NULL) extension = TLSX_Find(ssl->ctx->extensions, TLSX_APPLICATION_LAYER_PROTOCOL); +#ifdef WOLFSSL_NGINX + if (ssl->alpnSelect != NULL) { + const byte* out; + unsigned char outLen; + + if (ssl->alpnSelect(ssl, &out, &outLen, input + offset, size, + ssl->alpnSelectArg) == 0) { + WOLFSSL_MSG("ALPN protocol match"); + if (TLSX_UseALPN(&ssl->extensions, (char*)out, outLen, 0, ssl->heap) + == SSL_SUCCESS) { + if (extension == NULL) { + extension = TLSX_Find(ssl->extensions, + TLSX_APPLICATION_LAYER_PROTOCOL); + } + } + } + } +#endif + if (extension == NULL || extension->data == NULL) { WOLFSSL_MSG("No ALPN extensions not used or bad"); return isRequest ? 0 /* not using ALPN */ : BUFFER_ERROR; /* unexpected ALPN response */ } - if (OPAQUE16_LEN > length) - return BUFFER_ERROR; - - ato16(input, &size); - offset += OPAQUE16_LEN; - /* validating alpn list length */ if (length != OPAQUE16_LEN + size) return BUFFER_ERROR; @@ -2232,9 +2251,13 @@ int TLSX_CSR_ForceRequest(WOLFSSL* ssl) if (csr) { switch (csr->status_type) { case WOLFSSL_CSR_OCSP: - if (ssl->ctx->cm->ocspEnabled) + if (ssl->ctx->cm->ocspEnabled) { + #ifdef WOLFSSL_NGINX + csr->request.ocsp.ssl = ssl; + #endif return CheckOcspRequest(ssl->ctx->cm->ocsp, &csr->request.ocsp, NULL); + } else return OCSP_LOOKUP_FAIL; } @@ -2640,9 +2663,13 @@ int TLSX_CSR2_ForceRequest(WOLFSSL* ssl) /* followed by */ case WOLFSSL_CSR2_OCSP_MULTI: - if (ssl->ctx->cm->ocspEnabled) + if (ssl->ctx->cm->ocspEnabled) { + #ifdef WOLFSSL_NGINX + csr2->request.ocsp[0].ssl = ssl; + #endif return CheckOcspRequest(ssl->ctx->cm->ocsp, &csr2->request.ocsp[0], NULL); + } else return OCSP_LOOKUP_FAIL; } @@ -2861,12 +2888,10 @@ int TLSX_ValidateEllipticCurves(WOLFSSL* ssl, byte first, byte second) { : NULL; EllipticCurve* curve = NULL; word32 oid = 0; - word16 octets = 0; /* according to 'ecc_set_type ecc_sets[];' */ int sig = 0; /* validate signature */ int key = 0; /* validate key */ (void)oid; - (void)octets; if (!extension) return 1; /* no suite restriction */ @@ -2879,63 +2904,66 @@ int TLSX_ValidateEllipticCurves(WOLFSSL* ssl, byte first, byte second) { switch (curve->name) { #if defined(HAVE_ECC160) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP160R1: oid = ECC_SECP160R1_OID; octets = 20; break; + case WOLFSSL_ECC_SECP160R1: oid = ECC_SECP160R1_OID; break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_SECPR2 - case WOLFSSL_ECC_SECP160R2: oid = ECC_SECP160R2_OID; octets = 20; break; + case WOLFSSL_ECC_SECP160R2: oid = ECC_SECP160R2_OID; break; #endif /* HAVE_ECC_SECPR2 */ #ifdef HAVE_ECC_KOBLITZ - case WOLFSSL_ECC_SECP160K1: oid = ECC_SECP160K1_OID; octets = 20; break; + case WOLFSSL_ECC_SECP160K1: oid = ECC_SECP160K1_OID; break; #endif /* HAVE_ECC_KOBLITZ */ #endif #if defined(HAVE_ECC192) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP192R1: oid = ECC_SECP192R1_OID; octets = 24; break; + case WOLFSSL_ECC_SECP192R1: oid = ECC_SECP192R1_OID; break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_KOBLITZ - case WOLFSSL_ECC_SECP192K1: oid = ECC_SECP192K1_OID; octets = 24; break; + case WOLFSSL_ECC_SECP192K1: oid = ECC_SECP192K1_OID; break; #endif /* HAVE_ECC_KOBLITZ */ #endif #if defined(HAVE_ECC224) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP224R1: oid = ECC_SECP224R1_OID; octets = 28; break; + case WOLFSSL_ECC_SECP224R1: oid = ECC_SECP224R1_OID; break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_KOBLITZ - case WOLFSSL_ECC_SECP224K1: oid = ECC_SECP224K1_OID; octets = 28; break; + case WOLFSSL_ECC_SECP224K1: oid = ECC_SECP224K1_OID; break; #endif /* HAVE_ECC_KOBLITZ */ #endif #if !defined(NO_ECC256) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP256R1: oid = ECC_SECP256R1_OID; octets = 32; break; + case WOLFSSL_ECC_SECP256R1: oid = ECC_SECP256R1_OID; break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_KOBLITZ - case WOLFSSL_ECC_SECP256K1: oid = ECC_SECP256K1_OID; octets = 32; break; + case WOLFSSL_ECC_SECP256K1: oid = ECC_SECP256K1_OID; break; #endif /* HAVE_ECC_KOBLITZ */ #ifdef HAVE_ECC_BRAINPOOL - case WOLFSSL_ECC_BRAINPOOLP256R1: oid = ECC_BRAINPOOLP256R1_OID; octets = 32; break; + case WOLFSSL_ECC_BRAINPOOLP256R1: oid = ECC_BRAINPOOLP256R1_OID; break; #endif /* HAVE_ECC_BRAINPOOL */ #endif #if defined(HAVE_ECC384) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP384R1: oid = ECC_SECP384R1_OID; octets = 48; break; + case WOLFSSL_ECC_SECP384R1: oid = ECC_SECP384R1_OID; break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_BRAINPOOL - case WOLFSSL_ECC_BRAINPOOLP384R1: oid = ECC_BRAINPOOLP384R1_OID; octets = 48; break; + case WOLFSSL_ECC_BRAINPOOLP384R1: oid = ECC_BRAINPOOLP384R1_OID; break; #endif /* HAVE_ECC_BRAINPOOL */ #endif #if defined(HAVE_ECC512) || defined(HAVE_ALL_CURVES) #ifdef HAVE_ECC_BRAINPOOL - case WOLFSSL_ECC_BRAINPOOLP512R1: oid = ECC_BRAINPOOLP512R1_OID; octets = 64; break; + case WOLFSSL_ECC_BRAINPOOLP512R1: oid = ECC_BRAINPOOLP512R1_OID; break; #endif /* HAVE_ECC_BRAINPOOL */ #endif #if defined(HAVE_ECC521) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP521R1: oid = ECC_SECP521R1_OID; octets = 66; break; + case WOLFSSL_ECC_SECP521R1: oid = ECC_SECP521R1_OID; break; #endif /* !NO_ECC_SECP */ #endif default: continue; /* unsupported curve */ } + if (ssl->ecdhCurveOID == 0) + ssl->ecdhCurveOID = oid; + if (first == ECC_BYTE) { switch (second) { /* ECDHE_ECDSA */ @@ -2950,7 +2978,7 @@ int TLSX_ValidateEllipticCurves(WOLFSSL* ssl, byte first, byte second) { case TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: case TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: sig |= ssl->pkCurveOID == oid; - key |= ssl->eccTempKeySz == octets; + key |= ssl->ecdhCurveOID == oid; break; #ifdef WOLFSSL_STATIC_DH @@ -2978,7 +3006,7 @@ int TLSX_ValidateEllipticCurves(WOLFSSL* ssl, byte first, byte second) { case TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: case TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: sig = 1; - key |= ssl->eccTempKeySz == octets; + key |= ssl->ecdhCurveOID == oid; break; #ifdef WOLFSSL_STATIC_DH @@ -3010,14 +3038,14 @@ int TLSX_ValidateEllipticCurves(WOLFSSL* ssl, byte first, byte second) { case TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256 : case TLS_ECDHE_ECDSA_WITH_CHACHA20_OLD_POLY1305_SHA256 : sig |= ssl->pkCurveOID == oid; - key |= ssl->eccTempKeySz == octets; + key |= ssl->ecdhCurveOID == oid; break; #ifndef NO_RSA /* ECDHE_RSA */ case TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256 : case TLS_ECDHE_RSA_WITH_CHACHA20_OLD_POLY1305_SHA256 : sig = 1; - key |= ssl->eccTempKeySz == octets; + key |= ssl->ecdhCurveOID == oid; break; #endif default: @@ -4568,6 +4596,7 @@ int TLSX_PopulateExtensions(WOLFSSL* ssl, byte isServer) #if defined(HAVE_ECC) && defined(HAVE_SUPPORTED_CURVES) if (!ssl->options.userCurves && !ssl->ctx->userCurves) { + #ifndef HAVE_FIPS #if defined(HAVE_ECC160) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP ret = TLSX_UseSupportedCurve(&ssl->extensions, WOLFSSL_ECC_SECP160R1, ssl->heap); @@ -4592,6 +4621,7 @@ int TLSX_PopulateExtensions(WOLFSSL* ssl, byte isServer) if (ret != SSL_SUCCESS) return ret; #endif #endif + #endif #if defined(HAVE_ECC224) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP ret = TLSX_UseSupportedCurve(&ssl->extensions, WOLFSSL_ECC_SECP224R1, ssl->heap); diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 509364825..992bdae85 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -3418,7 +3418,7 @@ static INLINE int DateLessThan(const struct tm* a, const struct tm* b) } -#if defined(WOLFSSL_MYSQL_COMPATIBLE) +#if defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX) int GetTimeString(byte* date, int format, char* buf, int len) { struct tm t; @@ -5808,7 +5808,7 @@ const char* END_DSA_PRIV = "-----END DSA PRIVATE KEY-----"; const char* BEGIN_PUB_KEY = "-----BEGIN PUBLIC KEY-----"; const char* END_PUB_KEY = "-----END PUBLIC KEY-----"; -#if defined(WOLFSSL_KEY_GEN) || defined(WOLFSSL_CERT_GEN) +#if defined(WOLFSSL_KEY_GEN) || defined(WOLFSSL_CERT_GEN) || defined(OPENSSL_EXTRA) /* Used for compatibility API */ int wc_DerToPem(const byte* der, word32 derSz, @@ -9498,6 +9498,9 @@ static int DecodeSingleResponse(byte* source, return ASN_PARSE_E; } +#ifdef WOLFSSL_NGINX + cs->thisDateAsn = source + idx; +#endif if (GetBasicDate(source, &idx, cs->thisDate, &cs->thisDateFormat, size) < 0) return ASN_PARSE_E; @@ -9513,6 +9516,9 @@ static int DecodeSingleResponse(byte* source, idx++; if (GetLength(source, &idx, &length, size) < 0) return ASN_PARSE_E; +#ifdef WOLFSSL_NGINX + cs->nextDateAsn = source + idx; +#endif if (GetBasicDate(source, &idx, cs->nextDate, &cs->nextDateFormat, size) < 0) return ASN_PARSE_E; @@ -9759,7 +9765,9 @@ static int DecodeBasicOcspResponse(byte* source, word32* ioIndex, return ASN_PARSE_E; InitDecodedCert(&cert, resp->cert, resp->certSz, heap); - ret = ParseCertRelative(&cert, CERT_TYPE, VERIFY, cm); + /* Don't verify if we don't have access to Cert Manager. */ + ret = ParseCertRelative(&cert, CERT_TYPE, + cm == NULL ? NO_VERIFY : VERIFY, cm); if (ret < 0) { WOLFSSL_MSG("\tOCSP Responder certificate parsing failed"); FreeDecodedCert(&cert); @@ -9818,6 +9826,7 @@ void InitOcspResponse(OcspResponse* resp, CertStatus* status, int OcspResponseDecode(OcspResponse* resp, void* cm, void* heap) { + int ret; int length = 0; word32 idx = 0; byte* source = resp->source; @@ -9860,8 +9869,9 @@ int OcspResponseDecode(OcspResponse* resp, void* cm, void* heap) if (GetLength(source, &idx, &length, size) < 0) return ASN_PARSE_E; - if (DecodeBasicOcspResponse(source, &idx, resp, size, cm, heap) < 0) - return ASN_PARSE_E; + ret = DecodeBasicOcspResponse(source, &idx, resp, size, cm, heap); + if (ret < 0) + return ret; return 0; } @@ -9871,8 +9881,8 @@ word32 EncodeOcspRequestExtensions(OcspRequest* req, byte* output, word32 size) { static const byte NonceObjId[] = { 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x30, 0x01, 0x02 }; - byte seqArray[6][MAX_SEQ_SZ]; - word32 seqSz[6], totalSz = (word32)sizeof(NonceObjId); + byte seqArray[5][MAX_SEQ_SZ]; + word32 seqSz[5], totalSz = (word32)sizeof(NonceObjId); WOLFSSL_ENTER("SetOcspReqExtensions"); @@ -9886,16 +9896,12 @@ word32 EncodeOcspRequestExtensions(OcspRequest* req, byte* output, word32 size) totalSz += seqSz[2] = 1 + SetLength(sizeof(NonceObjId), &seqArray[2][1]); totalSz += seqSz[3] = SetSequence(totalSz, seqArray[3]); totalSz += seqSz[4] = SetSequence(totalSz, seqArray[4]); - totalSz += seqSz[5] = SetExplicit(2, totalSz, seqArray[5]); if (totalSz > size) return 0; totalSz = 0; - XMEMCPY(output + totalSz, seqArray[5], seqSz[5]); - totalSz += seqSz[5]; - XMEMCPY(output + totalSz, seqArray[4], seqSz[4]); totalSz += seqSz[4]; @@ -9946,8 +9952,14 @@ int EncodeOcspRequest(OcspRequest* req, byte* output, word32 size) snSz = SetSerialNumber(req->serial, req->serialSz, snArray); extSz = 0; - if (req->nonceSz) - extSz = EncodeOcspRequestExtensions(req, extArray, OCSP_NONCE_EXT_SZ); + if (req->nonceSz) { + /* TLS Extensions use this function too - put extensions after + * ASN.1: Context Specific [2]. + */ + extSz = EncodeOcspRequestExtensions(req, extArray + 2, + OCSP_NONCE_EXT_SZ); + extSz += SetExplicit(2, extSz, extArray); + } totalSz = algoSz + issuerSz + issuerKeySz + snSz; for (i = 4; i >= 0; i--) { @@ -9956,6 +9968,8 @@ int EncodeOcspRequest(OcspRequest* req, byte* output, word32 size) if (i == 2) totalSz += extSz; } + if (output == NULL) + return totalSz; if (totalSz > size) return BUFFER_E; diff --git a/wolfcrypt/src/ecc.c b/wolfcrypt/src/ecc.c index 019b96366..7687b3691 100644 --- a/wolfcrypt/src/ecc.c +++ b/wolfcrypt/src/ecc.c @@ -1195,6 +1195,22 @@ void wc_ecc_curve_cache_free(void) #endif /* WOLFSSL_ATECC508A */ +/* Retrieve the curve name for the ECC curve id. + * + * curve_id The id of the curve. + * returns the name stored from the curve if available, otherwise NULL. + */ +const char* wc_ecc_get_name(int curve_id) +{ + int x; + + for (x = 0; ecc_sets[x].size != 0; x++) { + if (curve_id == ecc_sets[x].id) + return ecc_sets[x].name; + } + + return NULL; +} static int wc_ecc_set_curve(ecc_key* key, int keysize, int curve_id) { diff --git a/wolfcrypt/src/evp.c b/wolfcrypt/src/evp.c index fb9e56edc..9df026163 100644 --- a/wolfcrypt/src/evp.c +++ b/wolfcrypt/src/evp.c @@ -277,7 +277,7 @@ WOLFSSL_API int wolfSSL_EVP_CipherUpdate(WOLFSSL_EVP_CIPHER_CTX *ctx, blocks = inl / ctx->block_size; if (blocks > 0) { /* process blocks */ - if (evpCipherBlock(ctx, out, ctx->buf, blocks) == 0) + if (evpCipherBlock(ctx, out, in, blocks*ctx->block_size) == 0) return 0; PRINT_BUF(ctx->buf, ctx->block_size); PRINT_BUF(out, ctx->block_size); diff --git a/wolfssl/internal.h b/wolfssl/internal.h index a752edeee..2fb249f56 100644 --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -1058,8 +1058,8 @@ enum Misc { MAX_WOLFSSL_FILE_SIZE = 1024 * 1024 * 4, /* 4 mb file size alloc limit */ -#if defined(FORTRESS) || defined (HAVE_STUNNEL) - MAX_EX_DATA = 3, /* allow for three items of ex_data */ +#if defined(HAVE_EX_DATA) || defined(FORTRESS) + MAX_EX_DATA = 4, /* allow for four items of ex_data */ #endif MAX_X509_SIZE = 2048, /* max static x509 buffer size */ @@ -1463,6 +1463,9 @@ struct WOLFSSL_OCSP { WOLFSSL_CERT_MANAGER* cm; /* pointer back to cert manager */ OcspEntry* ocspList; /* OCSP response list */ wolfSSL_Mutex ocspLock; /* OCSP list lock */ +#ifdef WOLFSSL_NGINX + int(*statusCb)(WOLFSSL*, void*); +#endif }; #ifndef MAX_DATE_SIZE @@ -1944,11 +1947,18 @@ struct WOLFSSL_CTX { DerBuffer* certificate; DerBuffer* certChain; /* chain after self, in DER, with leading size for each cert */ + #ifdef OPENSSL_EXTRA + STACK_OF(WOLFSSL_X509_NAME)* ca_names; + #endif + #ifdef WOLFSSL_NGINX + STACK_OF(WOLFSSL_X509)* x509Chain; + #endif DerBuffer* privateKey; WOLFSSL_CERT_MANAGER* cm; /* our cert manager, ctx owns SSL will use */ #endif #ifdef KEEP_OUR_CERT WOLFSSL_X509* ourCert; /* keep alive a X509 struct of cert */ + int ownOurCert; /* Dispose of certificate if we own */ #endif Suites* suites; /* make dynamic, user may not need/set */ void* heap; /* for user memory overrides */ @@ -1958,6 +1968,9 @@ struct WOLFSSL_CTX { byte failNoCertxPSK; /* fail if no cert with the exception of PSK*/ byte sessionCacheOff; byte sessionCacheFlushOff; +#ifdef HAVE_EXT_CACHE + byte internalCacheOff; +#endif byte sendVerify; /* for client side */ byte haveRSA; /* RSA available */ byte haveECC; /* ECC available */ @@ -1982,6 +1995,9 @@ struct WOLFSSL_CTX { #endif #ifdef HAVE_ECC short minEccKeySz; /* minimum ECC key size */ +#endif +#ifdef OPENSSL_EXTRA + unsigned long mask; /* store SSL_OP_ flags */ #endif CallbackIORecv CBIORecv; CallbackIOSend CBIOSend; @@ -1997,6 +2013,7 @@ struct WOLFSSL_CTX { word32 timeout; /* session timeout */ #ifdef HAVE_ECC word16 eccTempKeySz; /* in octets 20 - 66 */ + word32 ecdhCurveOID; /* curve Ecc_Sum */ word32 pkCurveOID; /* curve Ecc_Sum */ #endif #ifndef NO_PSK @@ -2015,8 +2032,14 @@ struct WOLFSSL_CTX { byte readAhead; void* userPRFArg; /* passed to prf callback */ #endif /* OPENSSL_EXTRA */ -#ifdef HAVE_STUNNEL +#ifdef HAVE_EX_DATA void* ex_data[MAX_EX_DATA]; +#endif +#if defined(HAVE_ALPN) && defined(WOLFSSL_NGINX) + CallbackALPNSelect alpnSelect; + void* alpnSelectArg; +#endif +#if defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) CallbackSniRecv sniRecvCb; void* sniRecvCbArg; #endif @@ -2064,6 +2087,11 @@ struct WOLFSSL_CTX { #ifdef HAVE_WOLF_EVENT WOLF_EVENT_QUEUE event_queue; #endif /* HAVE_WOLF_EVENT */ +#ifdef HAVE_EXT_CACHE + WOLFSSL_SESSION*(*get_sess_cb)(WOLFSSL*, unsigned char*, int, int*); + int (*new_sess_cb)(WOLFSSL*, WOLFSSL_SESSION*); + void (*rem_sess_cb)(WOLFSSL_CTX*, WOLFSSL_SESSION*); +#endif }; @@ -2261,30 +2289,33 @@ struct WOLFSSL_X509_CHAIN { /* wolfSSL session type */ struct WOLFSSL_SESSION { - word32 bornOn; /* create time in seconds */ - word32 timeout; /* timeout in seconds */ - byte sessionID[ID_LEN]; /* id for protocol */ - byte sessionIDSz; - byte masterSecret[SECRET_LEN]; /* stored secret */ - word16 haveEMS; /* ext master secret flag */ + word32 bornOn; /* create time in seconds */ + word32 timeout; /* timeout in seconds */ + byte sessionID[ID_LEN]; /* id for protocol */ + byte sessionIDSz; + byte masterSecret[SECRET_LEN]; /* stored secret */ + word16 haveEMS; /* ext master secret flag */ #ifdef SESSION_CERTS - WOLFSSL_X509_CHAIN chain; /* peer cert chain, static */ - ProtocolVersion version; /* which version was used */ - byte cipherSuite0; /* first byte, normally 0 */ - byte cipherSuite; /* 2nd byte, actual suite */ + WOLFSSL_X509_CHAIN chain; /* peer cert chain, static */ + ProtocolVersion version; /* which version was used */ + byte cipherSuite0; /* first byte, normally 0 */ + byte cipherSuite; /* 2nd byte, actual suite */ #endif #ifndef NO_CLIENT_CACHE - word16 idLen; /* serverID length */ - byte serverID[SERVER_ID_LEN]; /* for easier client lookup */ + word16 idLen; /* serverID length */ + byte serverID[SERVER_ID_LEN]; /* for easier client lookup */ #endif #ifdef HAVE_SESSION_TICKET - byte* ticket; - word16 ticketLen; - byte staticTicket[SESSION_TICKET_LEN]; - byte isDynamic; + byte* ticket; + word16 ticketLen; + byte staticTicket[SESSION_TICKET_LEN]; + byte isDynamic; #endif -#ifdef HAVE_STUNNEL - void* ex_data[MAX_EX_DATA]; +#ifdef HAVE_EXT_CACHE + byte isAlloced; +#endif +#ifdef HAVE_EX_DATA + void* ex_data[MAX_EX_DATA]; #endif }; @@ -2402,6 +2433,9 @@ typedef struct Options { word16 sendVerify:2; /* false = 0, true = 1, sendBlank = 2 */ word16 sessionCacheOff:1; word16 sessionCacheFlushOff:1; +#ifdef HAVE_EXT_CACHE + word16 internalCacheOff:1; +#endif word16 side:1; /* client or server end */ word16 verifyPeer:1; word16 verifyNone:1; @@ -2522,9 +2556,11 @@ struct WOLFSSL_STACK { unsigned long num; /* number of nodes in stack * (saftey measure for freeing and shortcut for count) */ union { - WOLFSSL_X509* x509; - WOLFSSL_BIO* bio; + WOLFSSL_X509* x509; + WOLFSSL_X509_NAME* name; + WOLFSSL_BIO* bio; WOLFSSL_ASN1_OBJECT* obj; + char* string; } data; WOLFSSL_STACK* next; }; @@ -2593,6 +2629,9 @@ struct WOLFSSL_X509 { int certPoliciesNb; #endif /* WOLFSSL_CERT_EXT */ #ifdef OPENSSL_EXTRA +#ifdef HAVE_EX_DATA + void* ex_data[MAX_EX_DATA]; +#endif word32 pathLength; word16 keyUsage; byte CRLdistSet; @@ -2752,6 +2791,9 @@ struct WOLFSSL { Ciphers decrypt; Buffers buffers; WOLFSSL_SESSION session; +#ifdef HAVE_EXT_CACHE + WOLFSSL_SESSION* extSession; +#endif WOLFSSL_ALERT_HISTORY alert_history; int error; int rfd; /* read file descriptor */ @@ -2803,6 +2845,7 @@ struct WOLFSSL { ecc_key* peerEccDsaKey; /* peer's ECDSA key */ ecc_key* eccTempKey; /* private ECDHE key */ word32 pkCurveOID; /* curve Ecc_Sum */ + word32 ecdhCurveOID; /* curve Ecc_Sum */ word16 eccTempKeySz; /* in octets 20 - 66 */ byte peerEccKeyPresent; byte peerEccDsaKeyPresent; @@ -2847,8 +2890,8 @@ struct WOLFSSL { flag found in buffers.weOwnCert) */ #endif byte keepCert; /* keep certificate after handshake */ -#if defined(FORTRESS) || defined(HAVE_STUNNEL) - void* ex_data[MAX_EX_DATA]; /* external data, for Fortress */ +#if defined(HAVE_EX_DATA) || defined(FORTRESS) + void* ex_data[MAX_EX_DATA]; /* external data, for Fortress */ #endif int devId; /* async device id to use */ #ifdef HAVE_ONE_TIME_AUTH @@ -2874,6 +2917,10 @@ struct WOLFSSL { #endif /* user turned on */ #ifdef HAVE_ALPN char* alpn_client_list; /* keep the client's list */ + #ifdef WOLFSSL_NGINX + CallbackALPNSelect alpnSelect; + void* alpnSelectArg; + #endif #endif /* of accepted protocols */ #if !defined(NO_WOLFSSL_CLIENT) && defined(HAVE_SESSION_TICKET) CallbackSessionTicket session_ticket_cb; @@ -2881,6 +2928,13 @@ struct WOLFSSL { byte expect_session_ticket; #endif #endif /* HAVE_TLS_EXTENSIONS */ +#ifdef OPENSSL_EXTRA + byte* ocspResp; + int ocspRespSz; +#ifdef WOLFSSL_NGINX + char* url; +#endif +#endif #ifdef HAVE_NETX NetX_Ctx nxCtx; /* NetX IO Context */ #endif @@ -2957,6 +3011,11 @@ typedef struct EncryptedInfo { WOLFSSL_LOCAL int ProcessFile(WOLFSSL_CTX* ctx, const char* fname, int format, int type, WOLFSSL* ssl, int userChain, WOLFSSL_CRL* crl); + + #ifdef OPENSSL_EXTRA + WOLFSSL_LOCAL int CheckHostName(DecodedCert* dCert, char *domainName, + size_t domainNameLen); + #endif #endif diff --git a/wolfssl/ocsp.h b/wolfssl/ocsp.h index 5331245c9..03d50fb92 100644 --- a/wolfssl/ocsp.h +++ b/wolfssl/ocsp.h @@ -37,6 +37,14 @@ typedef struct WOLFSSL_OCSP WOLFSSL_OCSP; +#ifdef WOLFSSL_NGINX +typedef struct OcspResponse WOLFSSL_OCSP_BASICRESP; + +typedef struct OcspRequest WOLFSSL_OCSP_CERTID; + +typedef struct OcspRequest WOLFSSL_OCSP_ONEREQ; +#endif + WOLFSSL_LOCAL int InitOCSP(WOLFSSL_OCSP*, WOLFSSL_CERT_MANAGER*); WOLFSSL_LOCAL void FreeOCSP(WOLFSSL_OCSP*, int dynamic); @@ -45,6 +53,48 @@ WOLFSSL_LOCAL int CheckCertOCSP(WOLFSSL_OCSP*, DecodedCert*, WOLFSSL_LOCAL int CheckOcspRequest(WOLFSSL_OCSP* ocsp, OcspRequest* ocspRequest, WOLFSSL_BUFFER_INFO* responseBuffer); + +#ifdef WOLFSSL_NGINX + +WOLFSSL_API int wolfSSL_OCSP_resp_find_status(WOLFSSL_OCSP_BASICRESP *bs, + WOLFSSL_OCSP_CERTID* id, int* status, int* reason, + WOLFSSL_ASN1_TIME** revtime, WOLFSSL_ASN1_TIME** thisupd, + WOLFSSL_ASN1_TIME** nextupd); +WOLFSSL_API const char *wolfSSL_OCSP_cert_status_str(long s); +WOLFSSL_API int wolfSSL_OCSP_check_validity(WOLFSSL_ASN1_TIME* thisupd, + WOLFSSL_ASN1_TIME* nextupd, long sec, long maxsec); + +WOLFSSL_API void wolfSSL_OCSP_CERTID_free(WOLFSSL_OCSP_CERTID* certId); +WOLFSSL_API WOLFSSL_OCSP_CERTID* wolfSSL_OCSP_cert_to_id( + const WOLFSSL_EVP_MD *dgst, const WOLFSSL_X509 *subject, + const WOLFSSL_X509 *issuer); + +WOLFSSL_API void wolfSSL_OCSP_BASICRESP_free(WOLFSSL_OCSP_BASICRESP* basicResponse); +WOLFSSL_API int wolfSSL_OCSP_basic_verify(WOLFSSL_OCSP_BASICRESP *bs, + STACK_OF(WOLFSSL_X509) *certs, WOLFSSL_X509_STORE *st, unsigned long flags); + +WOLFSSL_API void wolfSSL_OCSP_RESPONSE_free(OcspResponse* response); +WOLFSSL_API OcspResponse* wolfSSL_d2i_OCSP_RESPONSE_bio(WOLFSSL_BIO* bio, + OcspResponse** response); +WOLFSSL_API OcspResponse* wolfSSL_d2i_OCSP_RESPONSE(OcspResponse** response, + const unsigned char** data, int len); +WOLFSSL_API int wolfSSL_i2d_OCSP_RESPONSE(OcspResponse* response, + unsigned char** data); +WOLFSSL_API int wolfSSL_OCSP_response_status(OcspResponse *response); +WOLFSSL_API const char *wolfSSL_OCSP_response_status_str(long s); +WOLFSSL_API WOLFSSL_OCSP_BASICRESP* wolfSSL_OCSP_response_get1_basic( + OcspResponse* response); + +WOLFSSL_API OcspRequest* wolfSSL_OCSP_REQUEST_new(void); +WOLFSSL_API void wolfSSL_OCSP_REQUEST_free(OcspRequest* request); +WOLFSSL_API int wolfSSL_i2d_OCSP_REQUEST(OcspRequest* request, + unsigned char** data); +WOLFSSL_API WOLFSSL_OCSP_ONEREQ* wolfSSL_OCSP_request_add0_id(OcspRequest *req, + WOLFSSL_OCSP_CERTID *cid); + +#endif + + #ifdef __cplusplus } /* extern "C" */ #endif diff --git a/wolfssl/openssl/crypto.h b/wolfssl/openssl/crypto.h index 7032c24df..04afe897a 100644 --- a/wolfssl/openssl/crypto.h +++ b/wolfssl/openssl/crypto.h @@ -3,6 +3,7 @@ #ifndef WOLFSSL_CRYPTO_H_ #define WOLFSSL_CRYPTO_H_ +#include #include @@ -23,7 +24,7 @@ WOLFSSL_API unsigned long wolfSSLeay(void); #define SSLEAY_VERSION 0x0090600fL #define SSLEAY_VERSION_NUMBER SSLEAY_VERSION -#ifdef HAVE_STUNNEL +#if defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) #define CRYPTO_set_mem_ex_functions wolfSSL_CRYPTO_set_mem_ex_functions #define FIPS_mode wolfSSL_FIPS_mode #define FIPS_mode_set wolfSSL_FIPS_mode_set @@ -41,7 +42,9 @@ typedef void (CRYPTO_free_func)(void*parent, void*ptr, CRYPTO_EX_DATA *ad, int i #define CRYPTO_THREAD_r_lock wc_LockMutex #define CRYPTO_THREAD_unlock wc_UnLockMutex -#endif /* HAVE_STUNNEL */ +#define OPENSSL_malloc(a) XMALLOC(a, NULL, DYNAMIC_TYPE_OPENSSL) + +#endif /* HAVE_STUNNEL || WOLFSSL_NGINX */ #endif /* header */ diff --git a/wolfssl/openssl/dsa.h b/wolfssl/openssl/dsa.h index 98048bd9c..a4c4a5f54 100644 --- a/wolfssl/openssl/dsa.h +++ b/wolfssl/openssl/dsa.h @@ -4,13 +4,19 @@ #ifndef WOLFSSL_DSA_H_ #define WOLFSSL_DSA_H_ -#include #include #ifdef __cplusplus extern "C" { #endif +#ifndef WOLFSSL_DSA_TYPE_DEFINED /* guard on redeclaration */ +typedef struct WOLFSSL_DSA WOLFSSL_DSA; +#define WOLFSSL_DSA_TYPE_DEFINED +#endif + +typedef WOLFSSL_DSA DSA; + struct WOLFSSL_DSA { WOLFSSL_BIGNUM* p; WOLFSSL_BIGNUM* q; diff --git a/wolfssl/openssl/ec.h b/wolfssl/openssl/ec.h index 27fa7a600..9802c3db3 100644 --- a/wolfssl/openssl/ec.h +++ b/wolfssl/openssl/ec.h @@ -3,7 +3,6 @@ #ifndef WOLFSSL_EC_H_ #define WOLFSSL_EC_H_ -#include #include #include @@ -44,6 +43,17 @@ enum { OPENSSL_EC_NAMED_CURVE = 0x001 }; +#ifndef WOLFSSL_EC_TYPE_DEFINED /* guard on redeclaration */ +typedef struct WOLFSSL_EC_KEY WOLFSSL_EC_KEY; +typedef struct WOLFSSL_EC_POINT WOLFSSL_EC_POINT; +typedef struct WOLFSSL_EC_GROUP WOLFSSL_EC_GROUP; +#define WOLFSSL_EC_TYPE_DEFINED +#endif + +typedef WOLFSSL_EC_KEY EC_KEY; +typedef WOLFSSL_EC_GROUP EC_GROUP; +typedef WOLFSSL_EC_POINT EC_POINT; + struct WOLFSSL_EC_POINT { WOLFSSL_BIGNUM *X; WOLFSSL_BIGNUM *Y; @@ -57,6 +67,7 @@ struct WOLFSSL_EC_POINT { struct WOLFSSL_EC_GROUP { int curve_idx; /* index of curve, used by WolfSSL as reference */ int curve_nid; /* NID of curve, used by OpenSSL/OpenSSH as reference */ + int curve_oid; /* OID of curve, used by OpenSSL/OpenSSH as reference */ }; struct WOLFSSL_EC_KEY { diff --git a/wolfssl/openssl/ecdsa.h b/wolfssl/openssl/ecdsa.h index a92841fff..a56d26d3a 100644 --- a/wolfssl/openssl/ecdsa.h +++ b/wolfssl/openssl/ecdsa.h @@ -3,7 +3,6 @@ #ifndef WOLFSSL_ECDSA_H_ #define WOLFSSL_ECDSA_H_ -#include #include @@ -11,6 +10,13 @@ extern "C" { #endif +#ifndef WOLFSSL_ECDSA_TYPE_DEFINED /* guard on redeclaration */ +typedef struct WOLFSSL_ECDSA_SIG WOLFSSL_ECDSA_SIG; +#define WOLFSSL_ECDSA_TYPE_DEFINED +#endif + +typedef WOLFSSL_ECDSA_SIG ECDSA_SIG; + struct WOLFSSL_ECDSA_SIG { WOLFSSL_BIGNUM *r; WOLFSSL_BIGNUM *s; diff --git a/wolfssl/openssl/evp.h b/wolfssl/openssl/evp.h index 086e82c4c..bdd01b733 100644 --- a/wolfssl/openssl/evp.h +++ b/wolfssl/openssl/evp.h @@ -56,6 +56,7 @@ #endif typedef char WOLFSSL_EVP_CIPHER; +typedef char WOLFSSL_EVP_MD; #ifndef NO_MD5 WOLFSSL_API const WOLFSSL_EVP_MD* wolfSSL_EVP_md5(void); @@ -173,6 +174,24 @@ typedef struct WOLFSSL_EVP_CIPHER_CTX { int lastUsed; } WOLFSSL_EVP_CIPHER_CTX; + +#ifndef WOLFSSL_EVP_PKEY_TYPE_DEFINED /* guard on redeclaration */ +typedef struct WOLFSSL_EVP_PKEY WOLFSSL_EVP_PKEY; +#define WOLFSSL_EVP_PKEY_TYPE_DEFINED +#endif + +struct WOLFSSL_EVP_PKEY { + int type; /* openssh dereference */ + int save_type; /* openssh dereference */ + int pkey_sz; + union { + char* ptr; /* der format of key / or raw for NTRU */ + } pkey; + #ifdef HAVE_ECC + int pkey_curve; + #endif +}; + typedef int WOLFSSL_ENGINE ; typedef WOLFSSL_ENGINE ENGINE; @@ -210,6 +229,7 @@ WOLFSSL_API void wolfSSL_EVP_CIPHER_CTX_init(WOLFSSL_EVP_CIPHER_CTX* ctx); WOLFSSL_API int wolfSSL_EVP_CIPHER_CTX_cleanup(WOLFSSL_EVP_CIPHER_CTX* ctx); WOLFSSL_API int wolfSSL_EVP_CIPHER_CTX_iv_length(const WOLFSSL_EVP_CIPHER_CTX*); +WOLFSSL_API int wolfSSL_EVP_CIPHER_iv_length(const WOLFSSL_EVP_CIPHER*); WOLFSSL_API int wolfSSL_EVP_CipherInit(WOLFSSL_EVP_CIPHER_CTX* ctx, @@ -370,6 +390,8 @@ typedef WOLFSSL_EVP_CIPHER_CTX EVP_CIPHER_CTX; #define EVP_CIPHER_CTX_set_key_length wolfSSL_EVP_CIPHER_CTX_set_key_length #define EVP_CIPHER_CTX_mode wolfSSL_EVP_CIPHER_CTX_mode +#define EVP_CIPHER_iv_length wolfSSL_EVP_CIPHER_iv_length + #define EVP_CipherInit wolfSSL_EVP_CipherInit #define EVP_CipherInit_ex wolfSSL_EVP_CipherInit_ex #define EVP_EncryptInit wolfSSL_EVP_EncryptInit diff --git a/wolfssl/openssl/hmac.h b/wolfssl/openssl/hmac.h index 76d2481bf..3cf92fe1c 100644 --- a/wolfssl/openssl/hmac.h +++ b/wolfssl/openssl/hmac.h @@ -57,6 +57,8 @@ typedef struct WOLFSSL_HMAC_CTX { WOLFSSL_API void wolfSSL_HMAC_Init(WOLFSSL_HMAC_CTX* ctx, const void* key, int keylen, const EVP_MD* type); +WOLFSSL_API int wolfSSL_HMAC_Init_ex(WOLFSSL_HMAC_CTX* ctx, const void* key, + int len, const EVP_MD* md, void* impl); WOLFSSL_API void wolfSSL_HMAC_Update(WOLFSSL_HMAC_CTX* ctx, const unsigned char* data, int len); WOLFSSL_API void wolfSSL_HMAC_Final(WOLFSSL_HMAC_CTX* ctx, unsigned char* hash, @@ -69,6 +71,7 @@ typedef struct WOLFSSL_HMAC_CTX HMAC_CTX; #define HMAC(a,b,c,d,e,f,g) wolfSSL_HMAC((a),(b),(c),(d),(e),(f),(g)) #define HMAC_Init wolfSSL_HMAC_Init +#define HMAC_Init_ex wolfSSL_HMAC_Init_ex #define HMAC_Update wolfSSL_HMAC_Update #define HMAC_Final wolfSSL_HMAC_Final #define HMAC_cleanup wolfSSL_HMAC_cleanup diff --git a/wolfssl/openssl/ocsp.h b/wolfssl/openssl/ocsp.h index 7463eec96..98f2c9c81 100644 --- a/wolfssl/openssl/ocsp.h +++ b/wolfssl/openssl/ocsp.h @@ -1 +1,44 @@ /* ocsp.h for libcurl */ + +#ifndef WOLFSSL_OCSP_H_ +#define WOLFSSL_OCSP_H_ + +#ifdef HAVE_OCSP +#include + +#define OCSP_REQUEST OcspRequest +#define OCSP_RESPONSE OcspResponse +#define OCSP_BASICRESP WOLFSSL_OCSP_BASICRESP +#define OCSP_CERTID WOLFSSL_OCSP_CERTID +#define OCSP_ONEREQ WOLFSSL_OCSP_ONEREQ + +#define OCSP_RESPONSE_STATUS_SUCCESSFUL 0 +#define V_OCSP_CERTSTATUS_GOOD 0 + +#define OCSP_resp_find_status wolfSSL_OCSP_resp_find_status +#define OCSP_cert_status_str wolfSSL_OCSP_cert_status_str +#define OCSP_check_validity wolfSSL_OCSP_check_validity + +#define OCSP_CERTID_free wolfSSL_OCSP_CERTID_free +#define OCSP_cert_to_id wolfSSL_OCSP_cert_to_id + +#define OCSP_BASICRESP_free wolfSSL_OCSP_BASICRESP_free +#define OCSP_basic_verify wolfSSL_OCSP_basic_verify + +#define OCSP_RESPONSE_free wolfSSL_OCSP_RESPONSE_free +#define d2i_OCSP_RESPONSE_bio wolfSSL_d2i_OCSP_RESPONSE_bio +#define d2i_OCSP_RESPONSE wolfSSL_d2i_OCSP_RESPONSE +#define i2d_OCSP_RESPONSE wolfSSL_i2d_OCSP_RESPONSE +#define OCSP_response_status wolfSSL_OCSP_response_status +#define OCSP_response_status_str wolfSSL_OCSP_response_status_str +#define OCSP_response_get1_basic wolfSSL_OCSP_response_get1_basic + +#define OCSP_REQUEST_new wolfSSL_OCSP_REQUEST_new +#define OCSP_REQUEST_free wolfSSL_OCSP_REQUEST_free +#define i2d_OCSP_REQUEST wolfSSL_i2d_OCSP_REQUEST +#define OCSP_request_add0_id wolfSSL_OCSP_request_add0_id + +#endif /* HAVE_OCSP */ + +#endif /* WOLFSSL_OCSP_H_ */ + diff --git a/wolfssl/openssl/opensslv.h b/wolfssl/openssl/opensslv.h index 48955f9ec..80f9a799c 100644 --- a/wolfssl/openssl/opensslv.h +++ b/wolfssl/openssl/opensslv.h @@ -5,7 +5,7 @@ /* api version compatibility */ -#if defined(HAVE_STUNNEL) || defined(HAVE_LIGHTY) +#if defined(HAVE_STUNNEL) || defined(HAVE_LIGHTY) || defined(WOLFSSL_NGINX) /* version number can be increased for Lighty after compatibility for ECDH is added */ #define OPENSSL_VERSION_NUMBER 0x10001000L diff --git a/wolfssl/openssl/rsa.h b/wolfssl/openssl/rsa.h index 210a24e4c..7c8d4e63e 100644 --- a/wolfssl/openssl/rsa.h +++ b/wolfssl/openssl/rsa.h @@ -4,7 +4,6 @@ #ifndef WOLFSSL_RSA_H_ #define WOLFSSL_RSA_H_ -#include #include @@ -24,6 +23,13 @@ enum { NID_sha512 = 674 }; +#ifndef WOLFSSL_RSA_TYPE_DEFINED /* guard on redeclaration */ +typedef struct WOLFSSL_RSA WOLFSSL_RSA; +#define WOLFSSL_RSA_TYPE_DEFINED +#endif + +typedef WOLFSSL_RSA RSA; + struct WOLFSSL_RSA { WOLFSSL_BIGNUM* n; WOLFSSL_BIGNUM* e; diff --git a/wolfssl/openssl/ssl.h b/wolfssl/openssl/ssl.h index 6e63fed55..60b1ea647 100644 --- a/wolfssl/openssl/ssl.h +++ b/wolfssl/openssl/ssl.h @@ -32,6 +32,8 @@ /* wolfssl_openssl compatibility layer */ #include +#include + #ifdef __cplusplus extern "C" { #endif @@ -61,39 +63,34 @@ typedef WOLFSSL_X509_CHAIN X509_CHAIN; #define WOLFSSL_TYPES_DEFINED -typedef WOLFSSL_EVP_PKEY EVP_PKEY; -typedef WOLFSSL_RSA RSA; -typedef WOLFSSL_DSA DSA; -typedef WOLFSSL_EC_KEY EC_KEY; -typedef WOLFSSL_EC_GROUP EC_GROUP; -typedef WOLFSSL_EC_POINT EC_POINT; -typedef WOLFSSL_ECDSA_SIG ECDSA_SIG; -typedef WOLFSSL_BIO BIO; -typedef WOLFSSL_BIO_METHOD BIO_METHOD; -typedef WOLFSSL_CIPHER SSL_CIPHER; -typedef WOLFSSL_X509_LOOKUP X509_LOOKUP; -typedef WOLFSSL_X509_LOOKUP_METHOD X509_LOOKUP_METHOD; -typedef WOLFSSL_X509_CRL X509_CRL; -typedef WOLFSSL_X509_EXTENSION X509_EXTENSION; -typedef WOLFSSL_ASN1_TIME ASN1_TIME; -typedef WOLFSSL_ASN1_INTEGER ASN1_INTEGER; -typedef WOLFSSL_ASN1_OBJECT ASN1_OBJECT; -typedef WOLFSSL_ASN1_STRING ASN1_STRING; -typedef WOLFSSL_dynlock_value CRYPTO_dynlock_value; -typedef WOLFSSL_BUF_MEM BUF_MEM; +typedef WOLFSSL_EVP_PKEY EVP_PKEY; +typedef WOLFSSL_BIO BIO; +typedef WOLFSSL_BIO_METHOD BIO_METHOD; +typedef WOLFSSL_CIPHER SSL_CIPHER; +typedef WOLFSSL_X509_LOOKUP X509_LOOKUP; +typedef WOLFSSL_X509_LOOKUP_METHOD X509_LOOKUP_METHOD; +typedef WOLFSSL_X509_CRL X509_CRL; +typedef WOLFSSL_X509_EXTENSION X509_EXTENSION; +typedef WOLFSSL_ASN1_TIME ASN1_TIME; +typedef WOLFSSL_ASN1_INTEGER ASN1_INTEGER; +typedef WOLFSSL_ASN1_OBJECT ASN1_OBJECT; +typedef WOLFSSL_ASN1_STRING ASN1_STRING; +typedef WOLFSSL_dynlock_value CRYPTO_dynlock_value; +typedef WOLFSSL_BUF_MEM BUF_MEM; /* GENERAL_NAME and BASIC_CONSTRAINTS structs may need implemented as * compatibility layer expands. For now treating them as an ASN1_OBJECT */ typedef WOLFSSL_ASN1_OBJECT GENERAL_NAME; typedef WOLFSSL_ASN1_OBJECT BASIC_CONSTRAINTS; -#define ASN1_UTCTIME WOLFSSL_ASN1_TIME +#define ASN1_UTCTIME WOLFSSL_ASN1_TIME +#define ASN1_GENERALIZEDTIME WOLFSSL_ASN1_TIME typedef WOLFSSL_MD4_CTX MD4_CTX; typedef WOLFSSL_COMP_METHOD COMP_METHOD; -typedef WOLFSSL_X509_STORE X509_STORE; typedef WOLFSSL_X509_REVOKED X509_REVOKED; typedef WOLFSSL_X509_OBJECT X509_OBJECT; +typedef WOLFSSL_X509_STORE X509_STORE; typedef WOLFSSL_X509_STORE_CTX X509_STORE_CTX; #define CRYPTO_free XFREE @@ -104,7 +101,7 @@ typedef WOLFSSL_X509_STORE_CTX X509_STORE_CTX; #define SSL_get_cipher_list(ctx,i) wolfSSL_get_cipher_list((i)) #define SSL_get_cipher_name(ctx) wolfSSL_get_cipher((ctx)) #define SSL_get_shared_ciphers(ctx,buf,len) \ - strncpy(buf, "Not Implemented, SSLv2 only", len) + wolfSSL_get_shared_ciphers((ctx),(buf),(len)) #define ERR_print_errors_fp(file) wolfSSL_ERR_dump_errors_fp((file)) @@ -335,7 +332,8 @@ typedef WOLFSSL_X509_STORE_CTX X509_STORE_CTX; #define X509_get_serialNumber wolfSSL_X509_get_serialNumber -#define ASN1_TIME_print wolfSSL_ASN1_TIME_print +#define ASN1_TIME_print wolfSSL_ASN1_TIME_print +#define ASN1_GENERALIZEDTIME_print wolfSSL_ASN1_GENERALIZEDTIME_print #define ASN1_INTEGER_cmp wolfSSL_ASN1_INTEGER_cmp #define ASN1_INTEGER_get wolfSSL_ASN1_INTEGER_get @@ -343,6 +341,7 @@ typedef WOLFSSL_X509_STORE_CTX X509_STORE_CTX; #define SSL_load_client_CA_file wolfSSL_load_client_CA_file +#define SSL_CTX_get_client_CA_list wolfSSL_SSL_CTX_get_client_CA_list #define SSL_CTX_set_client_CA_list wolfSSL_CTX_set_client_CA_list #define SSL_CTX_set_cert_store wolfSSL_CTX_set_cert_store #define SSL_CTX_get_cert_store wolfSSL_CTX_get_cert_store @@ -472,7 +471,9 @@ typedef WOLFSSL_X509_STORE_CTX X509_STORE_CTX; /* Lighthttp compatibility */ -#if defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(HAVE_STUNNEL) +#if defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) \ + || defined(HAVE_STUNNEL) \ + || defined(WOLFSSL_NGINX) typedef WOLFSSL_X509_NAME_ENTRY X509_NAME_ENTRY; #define X509_NAME_free wolfSSL_X509_NAME_free @@ -484,6 +485,7 @@ typedef WOLFSSL_X509_NAME_ENTRY X509_NAME_ENTRY; #define OBJ_obj2nid wolfSSL_OBJ_obj2nid #define OBJ_sn2nid wolfSSL_OBJ_sn2nid #define SSL_CTX_set_verify_depth wolfSSL_CTX_set_verify_depth +#define SSL_set_verify_depth wolfSSL_set_verify_depth #define SSL_get_app_data wolfSSL_get_app_data #define SSL_set_app_data wolfSSL_set_app_data #define X509_NAME_entry_count wolfSSL_X509_NAME_entry_count @@ -501,16 +503,17 @@ typedef WOLFSSL_X509_NAME_ENTRY X509_NAME_ENTRY; #define NID_commonName 0x03 /* matchs ASN_COMMON_NAME in asn.h */ #endif -#if defined(HAVE_STUNNEL) || defined(HAVE_LIGHTY) \ - || defined(WOLFSSL_MYSQL_COMPATIBLE) +#if defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) \ + || defined(HAVE_STUNNEL) \ + || defined(WOLFSSL_NGINX) #define OBJ_nid2ln wolfSSL_OBJ_nid2ln #define OBJ_txt2nid wolfSSL_OBJ_txt2nid #define PEM_read_bio_DHparams wolfSSL_PEM_read_bio_DHparams #define PEM_read_bio_DSAparams wolfSSL_PEM_read_bio_DSAparams -#define PEM_write_bio_X509 PEM_write_bio_WOLFSSL_X509 +#define PEM_write_bio_X509 wolfSSL_PEM_write_bio_X509 -#endif /* HAVE_STUNNEL || HAVE_LIGHTY || WOLFSSL_MYSQL_COMPATIBLE */ +#endif /* HAVE_STUNNEL || HAVE_LIGHTY || WOLFSSL_MYSQL_COMPATIBLE || WOLFSSL_NGINX */ #define SSL_CTX_set_tmp_dh wolfSSL_CTX_set_tmp_dh #define BIO_new_file wolfSSL_BIO_new_file @@ -590,15 +593,18 @@ typedef WOLFSSL_X509_NAME_ENTRY X509_NAME_ENTRY; #define SSL_CTRL_GET_READ_AHEAD 40 #define SSL_CTRL_SET_READ_AHEAD 41 +#define SSL_CTRL_SET_TLSEXT_STATUS_REQ_CB 63 #define SSL_CTRL_SET_TLSEXT_STATUS_REQ_CB_ARG 64 +#define SSL_CTRL_GET_EXTRA_CHAIN_CERTS 82 + #define SSL_ctrl wolfSSL_ctrl #define SSL_CTX_ctrl wolfSSL_CTX_ctrl #define X509_V_FLAG_CRL_CHECK WOLFSSL_CRL_CHECK #define X509_V_FLAG_CRL_CHECK_ALL WOLFSSL_CRL_CHECKALL -#ifdef HAVE_STUNNEL +#if defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) #include #define SSL2_VERSION 0x0002 @@ -646,7 +652,7 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; #define SSL_get_servername wolfSSL_get_servername #define SSL_set_SSL_CTX wolfSSL_set_SSL_CTX #define SSL_CTX_get_verify_callback wolfSSL_CTX_get_verify_callback -#define SSL_CTX_set_tlsext_servername_callback wolfSSL_CTX_set_servername_callback +#define SSL_CTX_set_tlsext_servername_callback wolfSSL_CTX_set_tlsext_servername_callback #define SSL_CTX_set_tlsext_servername_arg wolfSSL_CTX_set_servername_arg #define PSK_MAX_PSK_LEN 256 @@ -655,7 +661,7 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; #define SSL_CTX_clear_options wolfSSL_CTX_clear_options -#endif /* HAVE_STUNNEL */ +#endif /* HAVE_STUNNEL || WOLFSSL_NGINX */ #define SSL_CTX_get_default_passwd_cb wolfSSL_CTX_get_default_passwd_cb #define SSL_CTX_get_default_passwd_cb_userdata wolfSSL_CTX_get_default_passwd_cb_userdata @@ -683,6 +689,98 @@ typedef WOLFSSL_ASN1_BIT_STRING ASN1_BIT_STRING; #define SSL_CTX_set_msg_callback_arg wolfSSL_CTX_set_msg_callback_arg #define SSL_set_msg_callback_arg wolfSSL_set_msg_callback_arg +/* certificate extension NIDs */ +#define NID_basic_constraints 133 +#define NID_key_usage 129 /* 2.5.29.15 */ +#define NID_ext_key_usage 151 /* 2.5.29.37 */ +#define NID_subject_key_identifier 128 +#define NID_authority_key_identifier 149 +#define NID_private_key_usage_period 130 /* 2.5.29.16 */ +#define NID_subject_alt_name 131 +#define NID_issuer_alt_name 132 +#define NID_info_access 69 +#define NID_sinfo_access 79 /* id-pe 11 */ +#define NID_name_constraints 144 /* 2.5.29.30 */ +#define NID_certificate_policies 146 +#define NID_policy_mappings 147 +#define NID_policy_constraints 150 +#define NID_inhibit_any_policy 168 /* 2.5.29.54 */ +#define NID_tlsfeature 92 /* id-pe 24 */ + +#ifdef WOLFSSL_NGINX +#include + +#define OPENSSL_STRING WOLFSSL_STRING + +#define TLSEXT_TYPE_application_layer_protocol_negotiation 16 + +#define OPENSSL_NPN_UNSUPPORTED 0 +#define OPENSSL_NPN_NEGOTIATED 1 +#define OPENSSL_NPN_NO_OVERLAP 2 + + +/* Nginx checks these to see if the error was a handshake error. */ +#define SSL_R_BAD_CHANGE_CIPHER_SPEC LENGTH_ERROR +#define SSL_R_BLOCK_CIPHER_PAD_IS_WRONG BUFFER_E +#define SSL_R_DIGEST_CHECK_FAILED VERIFY_MAC_ERROR +#define SSL_R_ERROR_IN_RECEIVED_CIPHER_LIST SUITES_ERROR +#define SSL_R_EXCESSIVE_MESSAGE_SIZE BUFFER_ERROR +#define SSL_R_LENGTH_MISMATCH LENGTH_ERROR +#define SSL_R_NO_CIPHERS_SPECIFIED SUITES_ERROR +#define SSL_R_NO_COMPRESSION_SPECIFIED COMPRESSION_ERROR +#define SSL_R_NO_SHARED_CIPHER MATCH_SUITE_ERROR +#define SSL_R_RECORD_LENGTH_MISMATCH HANDSHAKE_SIZE_ERROR +#define SSL_R_UNEXPECTED_MESSAGE OUT_OF_ORDER_E +#define SSL_R_UNEXPECTED_RECORD SANITY_MSG_E +#define SSL_R_UNKNOWN_ALERT_TYPE BUFFER_ERROR +#define SSL_R_UNKNOWN_PROTOCOL VERSION_ERROR +#define SSL_R_WRONG_VERSION_NUMBER VERSION_ERROR +#define SSL_R_DECRYPTION_FAILED_OR_BAD_RECORD_MAC ENCRYPT_ERROR + +/* Nginx uses this to determine if reached end of certs in file. + * PEM_read_bio_X509 is called and the return error is lost. + * The error that needs to be detected is: SSL_NO_PEM_HEADER. + */ +#define ERR_GET_LIB(l) (int)((((unsigned long)l)>>24L)&0xffL) +#define PEM_R_NO_START_LINE 108 +#define ERR_LIB_PEM 9 + +#ifdef HAVE_SESSION_TICKET +#define SSL_CTRL_SET_TLSEXT_TICKET_KEY_CB 72 +#endif + +#define OPENSSL_config wolfSSL_OPENSSL_config +#define X509_get_ex_new_index wolfSSL_X509_get_ex_new_index +#define X509_get_ex_data wolfSSL_X509_get_ex_data +#define X509_set_ex_data wolfSSL_X509_set_ex_data +#define X509_NAME_digest wolfSSL_X509_NAME_digest +#define SSL_CTX_get_timeout wolfSSL_SSL_CTX_get_timeout +#define SSL_CTX_set_tmp_ecdh wolfSSL_SSL_CTX_set_tmp_ecdh +#define SSL_CTX_remove_session wolfSSL_SSL_CTX_remove_session +#define SSL_get_rbio wolfSSL_SSL_get_rbio +#define SSL_get_wbio wolfSSL_SSL_get_wbio +#define SSL_do_handshake wolfSSL_SSL_do_handshake +#define SSL_in_init wolfSSL_SSL_in_init +#define SSL_get0_session wolfSSL_SSL_get0_session +#define X509_check_host wolfSSL_X509_check_host +#define i2a_ASN1_INTEGER wolfSSL_i2a_ASN1_INTEGER +#define ERR_peek_error_line_data wolfSSL_ERR_peek_error_line_data +#define SSL_CTX_set_tlsext_ticket_key_cb wolfSSL_CTX_set_tlsext_ticket_key_cb +#define X509_email_free wolfSSL_X509_email_free +#define X509_get1_ocsp wolfSSL_X509_get1_ocsp +#define SSL_CTX_set_tlsext_status_cb wolfSSL_CTX_set_tlsext_status_cb +#define X509_check_issued wolfSSL_X509_check_issued +#define X509_dup wolfSSL_X509_dup +#define X509_STORE_CTX_new wolfSSL_X509_STORE_CTX_new +#define X509_STORE_CTX_free wolfSSL_X509_STORE_CTX_free +#define SSL_CTX_get_extra_chain_certs wolfSSL_CTX_get_extra_chain_certs +#define X509_STORE_CTX_get1_issuer wolfSSL_X509_STORE_CTX_get1_issuer +#define sk_OPENSSL_STRING_value wolfSSL_sk_WOLFSSL_STRING_value +#define SSL_get0_alpn_selected wolfSSL_get0_alpn_selected +#define SSL_select_next_proto wolfSSL_select_next_proto +#define SSL_CTX_set_alpn_select_cb wolfSSL_CTX_set_alpn_select_cb + +#endif #ifdef __cplusplus } /* extern "C" */ diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index 6b94cac52..d9d1fc9c0 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -61,6 +61,7 @@ #ifdef OPENSSL_EXTRA #include + #include #endif #ifdef __cplusplus @@ -95,15 +96,28 @@ typedef struct WOLFSSL_RSA WOLFSSL_RSA; #define WC_RNG_TYPE_DEFINED #endif +#ifndef WOLFSSL_DSA_TYPE_DEFINED /* guard on redeclaration */ typedef struct WOLFSSL_DSA WOLFSSL_DSA; +#define WOLFSSL_DSA_TYPE_DEFINED +#endif + +#ifndef WOLFSSL_EC_TYPE_DEFINED /* guard on redeclaration */ typedef struct WOLFSSL_EC_KEY WOLFSSL_EC_KEY; typedef struct WOLFSSL_EC_POINT WOLFSSL_EC_POINT; typedef struct WOLFSSL_EC_GROUP WOLFSSL_EC_GROUP; +#define WOLFSSL_EC_TYPE_DEFINED +#endif + +#ifndef WOLFSSL_ECDSA_TYPE_DEFINED /* guard on redeclaration */ typedef struct WOLFSSL_ECDSA_SIG WOLFSSL_ECDSA_SIG; +#define WOLFSSL_ECDSA_TYPE_DEFINED +#endif + typedef struct WOLFSSL_CIPHER WOLFSSL_CIPHER; typedef struct WOLFSSL_X509_LOOKUP WOLFSSL_X509_LOOKUP; typedef struct WOLFSSL_X509_LOOKUP_METHOD WOLFSSL_X509_LOOKUP_METHOD; typedef struct WOLFSSL_X509_CRL WOLFSSL_X509_CRL; +typedef struct WOLFSSL_X509_STORE WOLFSSL_X509_STORE; typedef struct WOLFSSL_BIO WOLFSSL_BIO; typedef struct WOLFSSL_BIO_METHOD WOLFSSL_BIO_METHOD; typedef struct WOLFSSL_X509_EXTENSION WOLFSSL_X509_EXTENSION; @@ -117,7 +131,8 @@ typedef struct WOLFSSL_DH WOLFSSL_DH; typedef struct WOLFSSL_ASN1_BIT_STRING WOLFSSL_ASN1_BIT_STRING; typedef unsigned char* WOLFSSL_BUF_MEM; -#define WOLFSSL_ASN1_UTCTIME WOLFSSL_ASN1_TIME +#define WOLFSSL_ASN1_UTCTIME WOLFSSL_ASN1_TIME +#define WOLFSSL_ASN1_GENERALIZEDTIME WOLFSSL_ASN1_TIME struct WOLFSSL_ASN1_INTEGER { /* size can be increased set at 20 for tag, length then to hold at least 16 @@ -126,18 +141,16 @@ struct WOLFSSL_ASN1_INTEGER { /* ASN_INTEGER | LENGTH | hex of number */ }; -typedef char WOLFSSL_EVP_MD; -typedef struct WOLFSSL_EVP_PKEY { - int type; /* openssh dereference */ - int save_type; /* openssh dereference */ - int pkey_sz; - union { - char* ptr; /* der format of key / or raw for NTRU */ - } pkey; - #ifdef HAVE_ECC - int pkey_curve; - #endif -} WOLFSSL_EVP_PKEY; +struct WOLFSSL_ASN1_TIME { + /* MAX_DATA_SIZE is 32 */ + unsigned char data[32 + 2]; + /* ASN_TIME | LENGTH | date bytes */ +}; + +#ifndef WOLFSSL_EVP_PKEY_TYPE_DEFINED /* guard on redeclaration */ +typedef struct WOLFSSL_EVP_PKEY WOLFSSL_EVP_PKEY; +#define WOLFSSL_EVP_PKEY_TYPE_DEFINED +#endif typedef struct WOLFSSL_MD4_CTX { int buffer[32]; /* big enough to hold, check size in Init */ @@ -148,11 +161,22 @@ typedef struct WOLFSSL_COMP_METHOD { int type; /* stunnel dereference */ } WOLFSSL_COMP_METHOD; +struct WOLFSSL_X509_LOOKUP_METHOD { + int type; +}; -typedef struct WOLFSSL_X509_STORE { - int cache; /* stunnel dereference */ +struct WOLFSSL_X509_LOOKUP { + WOLFSSL_X509_STORE *store; +}; + +struct WOLFSSL_X509_STORE { + int cache; /* stunnel dereference */ WOLFSSL_CERT_MANAGER* cm; -} WOLFSSL_X509_STORE; + WOLFSSL_X509_LOOKUP lookup; +#ifdef OPENSSL_EXTRA + int isDynamic; +#endif +}; typedef struct WOLFSSL_ALERT { int code; @@ -196,6 +220,7 @@ typedef struct WOLFSSL_X509_STORE_CTX { WOLFSSL_BUFFER_INFO* certs; /* peer certs */ } WOLFSSL_X509_STORE_CTX; +typedef char* WOLFSSL_STRING; /* Valid Alert types from page 16/17 */ enum AlertDescription { @@ -347,6 +372,9 @@ WOLFSSL_API int wolfSSL_set_read_fd (WOLFSSL*, int); WOLFSSL_API char* wolfSSL_get_cipher_list(int priority); WOLFSSL_API int wolfSSL_get_ciphers(char*, int); WOLFSSL_API const char* wolfSSL_get_cipher_name(WOLFSSL* ssl); +WOLFSSL_API const char* wolfSSL_get_shared_ciphers(WOLFSSL* ssl, char* buf, + int len); +WOLFSSL_API const char* wolfSSL_get_curve_name(WOLFSSL* ssl); WOLFSSL_API int wolfSSL_get_fd(const WOLFSSL*); WOLFSSL_API void wolfSSL_set_using_nonblock(WOLFSSL*, int); WOLFSSL_API int wolfSSL_get_using_nonblock(WOLFSSL*); @@ -475,7 +503,7 @@ WOLFSSL_API int wolfSSL_is_init_finished(WOLFSSL*); WOLFSSL_API const char* wolfSSL_get_version(WOLFSSL*); WOLFSSL_API int wolfSSL_get_current_cipher_suite(WOLFSSL* ssl); WOLFSSL_API WOLFSSL_CIPHER* wolfSSL_get_current_cipher(WOLFSSL*); -WOLFSSL_API char* wolfSSL_CIPHER_description(WOLFSSL_CIPHER*, char*, int); +WOLFSSL_API char* wolfSSL_CIPHER_description(const WOLFSSL_CIPHER*, char*, int); WOLFSSL_API const char* wolfSSL_CIPHER_get_name(const WOLFSSL_CIPHER* cipher); WOLFSSL_API const char* wolfSSL_SESSION_CIPHER_get_name(WOLFSSL_SESSION* session); WOLFSSL_API const char* wolfSSL_get_cipher(WOLFSSL*); @@ -517,7 +545,7 @@ WOLFSSL_API WOLFSSL_BIO_METHOD* wolfSSL_BIO_s_mem(void); WOLFSSL_API WOLFSSL_BIO_METHOD* wolfSSL_BIO_f_base64(void); WOLFSSL_API void wolfSSL_BIO_set_flags(WOLFSSL_BIO*, int); -WOLFSSL_API int wolfSSL_BIO_get_mem_data(WOLFSSL_BIO* bio,const unsigned char** p); +WOLFSSL_API int wolfSSL_BIO_get_mem_data(WOLFSSL_BIO* bio,void* p); WOLFSSL_API WOLFSSL_BIO* wolfSSL_BIO_new_mem_buf(void* buf, int len); @@ -662,6 +690,8 @@ WOLFSSL_API WOLFSSL_BIGNUM *wolfSSL_ASN1_INTEGER_to_BN(const WOLFSSL_ASN1_INTEGE WOLFSSL_API STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_load_client_CA_file(const char*); #endif +WOLFSSL_API STACK_OF(WOLFSSL_X509_NAME)* wolfSSL_SSL_CTX_get_client_CA_list( + const WOLFSSL_CTX *s); WOLFSSL_API void wolfSSL_CTX_set_client_CA_list(WOLFSSL_CTX*, STACK_OF(WOLFSSL_X509_NAME)*); WOLFSSL_API void* wolfSSL_X509_STORE_CTX_get_ex_data(WOLFSSL_X509_STORE_CTX*, int); @@ -830,18 +860,25 @@ enum { X509_LU_X509 = 9, X509_LU_CRL = 12, - X509_V_OK = 0, - X509_V_ERR_CRL_SIGNATURE_FAILURE = 13, - X509_V_ERR_ERROR_IN_CRL_NEXT_UPDATE_FIELD = 14, - X509_V_ERR_CRL_HAS_EXPIRED = 15, - X509_V_ERR_CERT_REVOKED = 16, - X509_V_ERR_CERT_CHAIN_TOO_LONG = 17, - X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT = 18, - X509_V_ERR_CERT_NOT_YET_VALID = 19, - X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD = 20, - X509_V_ERR_CERT_HAS_EXPIRED = 21, - X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD = 22, - X509_V_ERR_CERT_REJECTED = 23, + X509_V_OK = 0, + X509_V_ERR_CRL_SIGNATURE_FAILURE = 13, + X509_V_ERR_ERROR_IN_CRL_NEXT_UPDATE_FIELD = 14, + X509_V_ERR_CRL_HAS_EXPIRED = 15, + X509_V_ERR_CERT_REVOKED = 16, + X509_V_ERR_CERT_CHAIN_TOO_LONG = 17, + X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT = 18, + X509_V_ERR_CERT_NOT_YET_VALID = 19, + X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD = 20, + X509_V_ERR_CERT_HAS_EXPIRED = 21, + X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD = 22, + X509_V_ERR_CERT_REJECTED = 23, + /* Required for Nginx */ + X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT = 24, + X509_V_ERR_SELF_SIGNED_CERT_IN_CHAIN = 25, + X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY = 26, + X509_V_ERR_CERT_UNTRUSTED = 27, + X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE = 28, + X509_V_ERR_SUBJECT_ISSUER_MISMATCH = 29, /* additional X509_V_ERR_* enums not used in wolfSSL */ X509_V_ERR_UNABLE_TO_GET_CRL, X509_V_ERR_UNABLE_TO_DECRYPT_CERT_SIGNATURE, @@ -851,15 +888,9 @@ enum { X509_V_ERR_CRL_NOT_YET_VALID, X509_V_ERR_ERROR_IN_CRL_LAST_UPDATE_FIELD, X509_V_ERR_OUT_OF_MEM, - X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT, - X509_V_ERR_SELF_SIGNED_CERT_IN_CHAIN, - X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY, - X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE, X509_V_ERR_INVALID_CA, X509_V_ERR_PATH_LENGTH_EXCEEDED, X509_V_ERR_INVALID_PURPOSE, - X509_V_ERR_CERT_UNTRUSTED, - X509_V_ERR_SUBJECT_ISSUER_MISMATCH, X509_V_ERR_AKID_SKID_MISMATCH, X509_V_ERR_AKID_ISSUER_SERIAL_MISMATCH, X509_V_ERR_KEYUSAGE_NO_CERTSIGN, @@ -878,6 +909,7 @@ enum { XN_FLAG_SPC_EQ = (1 << 23), XN_FLAG_ONELINE = 0, + XN_FLAG_RFC2253 = 1, CRYPTO_LOCK = 1, CRYPTO_NUM_LOCKS = 10, @@ -924,12 +956,14 @@ enum { /* ssl Constants */ SSL_VERIFY_CLIENT_ONCE = 4, SSL_VERIFY_FAIL_EXCEPT_PSK = 8, - SSL_SESS_CACHE_OFF = 30, - SSL_SESS_CACHE_CLIENT = 31, - SSL_SESS_CACHE_SERVER = 32, - SSL_SESS_CACHE_BOTH = 33, - SSL_SESS_CACHE_NO_AUTO_CLEAR = 34, - SSL_SESS_CACHE_NO_INTERNAL_LOOKUP = 35, + SSL_SESS_CACHE_OFF = 0x0000, + SSL_SESS_CACHE_CLIENT = 0x0001, + SSL_SESS_CACHE_SERVER = 0x0002, + SSL_SESS_CACHE_BOTH = 0x0003, + SSL_SESS_CACHE_NO_AUTO_CLEAR = 0x0008, + SSL_SESS_CACHE_NO_INTERNAL_LOOKUP = 0x0100, + SSL_SESS_CACHE_NO_INTERNAL_STORE = 0x0200, + SSL_SESS_CACHE_NO_INTERNAL = 0x0300, SSL_ERROR_WANT_READ = 2, SSL_ERROR_WANT_WRITE = 3, @@ -1037,6 +1071,8 @@ WOLFSSL_API int wolfSSL_want_write(WOLFSSL*); WOLFSSL_API int wolfSSL_BIO_printf(WOLFSSL_BIO*, const char*, ...); WOLFSSL_API int wolfSSL_ASN1_UTCTIME_print(WOLFSSL_BIO*, const WOLFSSL_ASN1_UTCTIME*); +WOLFSSL_API int wolfSSL_ASN1_GENERALIZEDTIME_print(WOLFSSL_BIO*, + const WOLFSSL_ASN1_GENERALIZEDTIME*); WOLFSSL_API int wolfSSL_sk_num(WOLFSSL_X509_REVOKED*); WOLFSSL_API void* wolfSSL_sk_value(WOLFSSL_X509_REVOKED*, int); @@ -1690,6 +1726,12 @@ enum { WOLFSSL_MAX_ALPN_NUMBER = 257 }; +#ifdef WOLFSSL_NGINX +typedef int (*CallbackALPNSelect)(WOLFSSL* ssl, const unsigned char** out, + unsigned char* outLen, const unsigned char* in, unsigned int inLen, + void *arg); +#endif + WOLFSSL_API int wolfSSL_UseALPN(WOLFSSL* ssl, char *protocol_name_list, unsigned int protocol_name_listSz, unsigned char options); @@ -1960,7 +2002,7 @@ WOLFSSL_API int wolfSSL_accept_ex(WOLFSSL*, HandShakeCallBack, TimeoutCallBack, WOLFSSL_API void wolfSSL_cert_service(void); #endif -#if defined(WOLFSSL_MYSQL_COMPATIBLE) +#if defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX) WOLFSSL_API char* wolfSSL_ASN1_TIME_to_string(WOLFSSL_ASN1_TIME* time, char* buf, int len); #endif /* WOLFSSL_MYSQL_COMPATIBLE */ @@ -2028,7 +2070,10 @@ struct WOLFSSL_X509_NAME_ENTRY { int size; }; -#if defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(HAVE_STUNNEL) +#if defined(HAVE_LIGHTY) || defined(WOLFSSL_MYSQL_COMPATIBLE) \ + || defined(HAVE_STUNNEL) \ + || defined(WOLFSSL_NGINX) \ + || defined(OPENSSL_EXTRA) WOLFSSL_API void wolfSSL_X509_NAME_free(WOLFSSL_X509_NAME *name); WOLFSSL_API char wolfSSL_CTX_use_certificate(WOLFSSL_CTX *ctx, WOLFSSL_X509 *x); WOLFSSL_API int wolfSSL_BIO_read_filename(WOLFSSL_BIO *b, const char *name); @@ -2037,6 +2082,7 @@ WOLFSSL_API const char * wolfSSL_OBJ_nid2sn(int n); WOLFSSL_API int wolfSSL_OBJ_obj2nid(const WOLFSSL_ASN1_OBJECT *o); WOLFSSL_API int wolfSSL_OBJ_sn2nid(const char *sn); WOLFSSL_API void wolfSSL_CTX_set_verify_depth(WOLFSSL_CTX *ctx,int depth); +WOLFSSL_API void wolfSSL_set_verify_depth(WOLFSSL *ssl,int depth); WOLFSSL_API void* wolfSSL_get_app_data( const WOLFSSL *ssl); WOLFSSL_API void wolfSSL_set_app_data(WOLFSSL *ssl, void *arg); WOLFSSL_API WOLFSSL_ASN1_OBJECT * wolfSSL_X509_NAME_ENTRY_get_object(WOLFSSL_X509_NAME_ENTRY *ne); @@ -2070,7 +2116,7 @@ WOLFSSL_API long wolfSSL_CTX_get_options(WOLFSSL_CTX* ctx); #endif /* HAVE_STUNNEL || HAVE_LIGHTY */ -#ifdef HAVE_STUNNEL +#if defined(HAVE_STUNNEL) || defined(WOLFSSL_NGINX) #include @@ -2145,6 +2191,8 @@ WOLFSSL_API VerifyCallback wolfSSL_CTX_get_verify_callback(WOLFSSL_CTX*); WOLFSSL_API void wolfSSL_CTX_set_servername_callback(WOLFSSL_CTX *, CallbackSniRecv); +WOLFSSL_API int wolfSSL_CTX_set_tlsext_servername_callback(WOLFSSL_CTX *, + CallbackSniRecv); WOLFSSL_API void wolfSSL_CTX_set_servername_arg(WOLFSSL_CTX *, void*); @@ -2164,9 +2212,10 @@ WOLFSSL_API WOLFSSL_X509* wolfSSL_X509_STORE_get1_certs(WOLFSSL_X509_STORE_CTX*, WOLFSSL_X509_NAME*); WOLFSSL_API void wolfSSL_sk_X509_pop_free(STACK_OF(WOLFSSL_X509)* sk, void f (WOLFSSL_X509*)); -#endif /* HAVE_STUNNEL */ +#endif /* HAVE_STUNNEL || WOLFSSL_NGINX */ -#if defined(HAVE_STUNNEL) || defined(WOLFSSL_MYSQL_COMPATIBLE) +#if defined(HAVE_STUNNEL) || defined(WOLFSSL_MYSQL_COMPATIBLE) \ + || defined(WOLFSSL_NGINX) WOLFSSL_API int wolfSSL_CTX_get_verify_mode(WOLFSSL_CTX* ctx); @@ -2194,6 +2243,89 @@ WOLFSSL_API int wolfSSL_CTX_set_msg_callback_arg(WOLFSSL_CTX *ctx, void* arg); WOLFSSL_API int wolfSSL_set_msg_callback_arg(WOLFSSL *ssl, void* arg); #endif +#ifdef WOLFSSL_NGINX +/* Not an OpenSSL API. */ +WOLFSSL_LOCAL int wolfSSL_get_ocsp_response(WOLFSSL* ssl, byte** response); +/* Not an OpenSSL API. */ +WOLFSSL_LOCAL char* wolfSSL_get_ocsp_url(WOLFSSL* ssl); +/* Not an OpenSSL API. */ +WOLFSSL_API int wolfSSL_set_ocsp_url(WOLFSSL* ssl, char* url); + +WOLFSSL_API void wolfSSL_OPENSSL_config(char *config_name); +WOLFSSL_API int wolfSSL_X509_get_ex_new_index(int idx, void *arg, void *a, + void *b, void *c); +WOLFSSL_API void *wolfSSL_X509_get_ex_data(WOLFSSL_X509 *x509, int idx); +WOLFSSL_API int wolfSSL_X509_set_ex_data(WOLFSSL_X509 *x509, int idx, + void *data); + +WOLFSSL_API int wolfSSL_X509_NAME_digest(const WOLFSSL_X509_NAME *data, + const WOLFSSL_EVP_MD *type, unsigned char *md, unsigned int *len); + +WOLFSSL_API long wolfSSL_SSL_CTX_get_timeout(const WOLFSSL_CTX *ctx); +WOLFSSL_API int wolfSSL_SSL_CTX_set_tmp_ecdh(WOLFSSL_CTX *ctx, + WOLFSSL_EC_KEY *ecdh); +WOLFSSL_API int wolfSSL_SSL_CTX_remove_session(WOLFSSL_CTX *, + WOLFSSL_SESSION *c); + +WOLFSSL_API WOLFSSL_BIO *wolfSSL_SSL_get_rbio(const WOLFSSL *s); +WOLFSSL_API WOLFSSL_BIO *wolfSSL_SSL_get_wbio(const WOLFSSL *s); +WOLFSSL_API int wolfSSL_SSL_do_handshake(WOLFSSL *s); +WOLFSSL_API int wolfSSL_SSL_in_init(WOLFSSL *a); /* #define in OpenSSL */ +WOLFSSL_API WOLFSSL_SESSION *wolfSSL_SSL_get0_session(const WOLFSSL *s); +WOLFSSL_API int wolfSSL_X509_check_host(WOLFSSL_X509 *x, const char *chk, + size_t chklen, unsigned int flags, char **peername); + +WOLFSSL_API int wolfSSL_i2a_ASN1_INTEGER(WOLFSSL_BIO *bp, + const WOLFSSL_ASN1_INTEGER *a); + +WOLFSSL_API unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, + int *line, const char **data, int *flags); + +#ifdef HAVE_SESSION_TICKET +WOLFSSL_API int wolfSSL_CTX_set_tlsext_ticket_key_cb(WOLFSSL_CTX *, int (*)( + WOLFSSL *ssl, unsigned char *name, unsigned char *iv, + WOLFSSL_EVP_CIPHER_CTX *ectx, WOLFSSL_HMAC_CTX *hctx, int enc)); +#endif + +#ifdef HAVE_OCSP +WOLFSSL_API int wolfSSL_CTX_get_extra_chain_certs(WOLFSSL_CTX* ctx, + STACK_OF(X509)** chain); +WOLFSSL_API int wolfSSL_CTX_set_tlsext_status_cb(WOLFSSL_CTX* ctx, + int(*)(WOLFSSL*, void*)); + +WOLFSSL_API int wolfSSL_X509_STORE_CTX_get1_issuer(WOLFSSL_X509 **issuer, + WOLFSSL_X509_STORE_CTX *ctx, WOLFSSL_X509 *x); + +WOLFSSL_API void wolfSSL_X509_email_free(STACK_OF(WOLFSSL_STRING) *sk); +WOLFSSL_API STACK_OF(WOLFSSL_STRING) *wolfSSL_X509_get1_ocsp(WOLFSSL_X509 *x); + +WOLFSSL_API int wolfSSL_X509_check_issued(WOLFSSL_X509 *issuer, + WOLFSSL_X509 *subject); + +WOLFSSL_API WOLFSSL_X509* wolfSSL_X509_dup(WOLFSSL_X509 *x); + +WOLFSSL_API char* wolfSSL_sk_WOLFSSL_STRING_value( + STACK_OF(WOLFSSL_STRING)* strings, int idx); +#endif /* HAVE_OCSP */ + +WOLFSSL_API int PEM_write_bio_WOLFSSL_X509(WOLFSSL_BIO *bio, + WOLFSSL_X509 *cert); +#endif /* WOLFSSL_NGINX */ + +WOLFSSL_API void wolfSSL_get0_alpn_selected(const WOLFSSL *ssl, + const unsigned char **data, unsigned int *len); +WOLFSSL_API int wolfSSL_select_next_proto(unsigned char **out, + unsigned char *outlen, + const unsigned char *in, unsigned int inlen, + const unsigned char *client, + unsigned int client_len); +WOLFSSL_API void wolfSSL_CTX_set_alpn_select_cb(WOLFSSL_CTX *ctx, + int (*cb) (WOLFSSL *ssl, + const unsigned char **out, + unsigned char *outlen, + const unsigned char *in, + unsigned int inlen, + void *arg), void *arg); #ifdef __cplusplus } /* extern "C" */ diff --git a/wolfssl/test.h b/wolfssl/test.h index e0b03c3b3..61a531ce4 100644 --- a/wolfssl/test.h +++ b/wolfssl/test.h @@ -514,6 +514,12 @@ static INLINE void showPeer(WOLFSSL* ssl) { WOLFSSL_CIPHER* cipher; +#ifdef HAVE_ECC + const char *name; +#endif +#ifndef NO_DH + int bits; +#endif #ifdef KEEP_PEER_CERT WOLFSSL_X509* peer = wolfSSL_get_peer_certificate(ssl); if (peer) @@ -535,6 +541,16 @@ static INLINE void showPeer(WOLFSSL* ssl) #else printf("SSL cipher suite is %s\n", wolfSSL_CIPHER_get_name(cipher)); #endif +#ifdef HAVE_ECC + if ((name = wolfSSL_get_curve_name(ssl)) != NULL) + printf("SSL curve name is %s\n", name); +#endif +#ifndef NO_DH + if ((bits = wolfSSL_GetDhKey_Sz(ssl)) > 0) + printf("SSL DH size is %d bits\n", bits); +#endif + if (wolfSSL_session_reused(ssl)) + printf("SSL reused session\n"); #if defined(SESSION_CERTS) && defined(SHOW_CERTS) { diff --git a/wolfssl/wolfcrypt/asn.h b/wolfssl/wolfcrypt/asn.h index 1eb4b6d90..02ad51cc0 100644 --- a/wolfssl/wolfcrypt/asn.h +++ b/wolfssl/wolfcrypt/asn.h @@ -188,7 +188,7 @@ enum Misc_ASN { MAX_CERTPOL_NB = CTC_MAX_CERTPOL_NB,/* Max number of Cert Policy */ MAX_CERTPOL_SZ = CTC_MAX_CERTPOL_SZ, #endif - OCSP_NONCE_EXT_SZ = 37, /* OCSP Nonce Extension size */ + OCSP_NONCE_EXT_SZ = 35, /* OCSP Nonce Extension size */ MAX_OCSP_EXT_SZ = 58, /* Max OCSP Extension length */ MAX_OCSP_NONCE_SZ = 16, /* OCSP Nonce size */ EIGHTK_BUF = 8192, /* Tmp buffer size */ @@ -196,7 +196,10 @@ enum Misc_ASN { /* use bigger NTRU size */ HEADER_ENCRYPTED_KEY_SIZE = 88,/* Extra header size for encrypted key */ TRAILING_ZERO = 1, /* Used for size of zero pad */ - MIN_VERSION_SZ = 3 /* Min bytes needed for GetMyVersion */ + MIN_VERSION_SZ = 3, /* Min bytes needed for GetMyVersion */ +#if defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX) + MAX_TIME_STRING_SZ = 21, /* Max length of formatted time string */ +#endif }; @@ -681,7 +684,7 @@ WOLFSSL_LOCAL int ToTraditionalEnc(byte* buffer, word32 length,const char*,int); WOLFSSL_LOCAL int DecryptContent(byte* input, word32 sz,const char* psw,int pswSz); typedef struct tm wolfssl_tm; -#if defined(WOLFSSL_MYSQL_COMPATIBLE) +#if defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX) WOLFSSL_LOCAL int GetTimeString(byte* date, int format, char* buf, int len); #endif WOLFSSL_LOCAL int ExtractDate(const unsigned char* date, unsigned char format, @@ -807,6 +810,10 @@ struct CertStatus { byte nextDate[MAX_DATE_SIZE]; byte thisDateFormat; byte nextDateFormat; +#ifdef WOLFSSL_NGINX + byte* thisDateAsn; + byte* nextDateAsn; +#endif byte* rawOcspResponse; word32 rawOcspResponseSz; @@ -853,6 +860,10 @@ struct OcspRequest { byte nonce[MAX_OCSP_NONCE_SZ]; int nonceSz; void* heap; + +#ifdef WOLFSSL_NGINX + void* ssl; +#endif }; diff --git a/wolfssl/wolfcrypt/asn_public.h b/wolfssl/wolfcrypt/asn_public.h index 576d2d28f..242018ad7 100644 --- a/wolfssl/wolfcrypt/asn_public.h +++ b/wolfssl/wolfcrypt/asn_public.h @@ -240,7 +240,8 @@ WOLFSSL_API int wc_SetKeyUsage(Cert *cert, const char *value); #endif /* WOLFSSL_PEMPUBKEY_TODER_DEFINED */ #endif /* WOLFSSL_CERT_EXT || WOLFSSL_PUB_PEM_TO_DER */ -#if defined(WOLFSSL_KEY_GEN) || defined(WOLFSSL_CERT_GEN) || !defined(NO_DSA) +#if defined(WOLFSSL_KEY_GEN) || defined(WOLFSSL_CERT_GEN) || !defined(NO_DSA) \ + || defined(OPENSSL_EXTRA) WOLFSSL_API int wc_DerToPem(const byte* der, word32 derSz, byte* output, word32 outputSz, int type); WOLFSSL_API int wc_DerToPemEx(const byte* der, word32 derSz, byte* output, diff --git a/wolfssl/wolfcrypt/ecc.h b/wolfssl/wolfcrypt/ecc.h index 177d7003f..c78208b74 100644 --- a/wolfssl/wolfcrypt/ecc.h +++ b/wolfssl/wolfcrypt/ecc.h @@ -286,6 +286,8 @@ typedef struct ecc_key { /* ECC predefined curve sets */ extern const ecc_set_type ecc_sets[]; +WOLFSSL_API +const char* wc_ecc_get_name(int curve_id); WOLFSSL_API int wc_ecc_make_key(WC_RNG* rng, int keysize, ecc_key* key); diff --git a/wolfssl/wolfcrypt/settings.h b/wolfssl/wolfcrypt/settings.h index e1c93cd75..3294ee57f 100644 --- a/wolfssl/wolfcrypt/settings.h +++ b/wolfssl/wolfcrypt/settings.h @@ -1495,6 +1495,27 @@ static char *fgets(char *buff, int sz, FILE *fp) #undef HAVE_GMTIME_R /* don't trust macro with windows */ #endif /* WOLFSSL_MYSQL_COMPATIBLE */ +#ifdef WOLFSSL_NGINX + #define SSL_OP_NO_COMPRESSION SSL_OP_NO_COMPRESSION + #define OPENSSL_NO_ENGINE + #define X509_CHECK_FLAG_ALWAYS_CHECK_SUBJECT + #ifndef OPENSSL_EXTRA + #define OPENSSL_EXTRA + #endif + #ifndef HAVE_SESSION_TICKET + #define HAVE_SESSION_TICKET + #endif + #ifndef HAVE_OCSP + #define HAVE_OCSP + #endif + #ifndef KEEP_OUR_CERT + #define KEEP_OUR_CERT + #endif + #ifndef HAVE_SNI + #define HAVE_SNI + #endif + #define SSL_CTRL_SET_TLSEXT_HOSTNAME +#endif #ifdef __cplusplus } /* extern "C" */ diff --git a/wolfssl/wolfcrypt/types.h b/wolfssl/wolfcrypt/types.h index 00b184668..a8a16bfde 100644 --- a/wolfssl/wolfcrypt/types.h +++ b/wolfssl/wolfcrypt/types.h @@ -242,7 +242,7 @@ #define XSTRNCASECMP(s1,s2,n) _strnicmp((s1),(s2),(n)) #endif - #if defined(WOLFSSL_MYSQL_COMPATIBLE) + #if defined(WOLFSSL_MYSQL_COMPATIBLE) || defined(WOLFSSL_NGINX) #ifndef USE_WINDOWS_API #define XSNPRINTF snprintf #else From d4abeb56db4de7ccb483abbd0090216fda8f1004 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Thu, 9 Feb 2017 16:28:32 +1000 Subject: [PATCH 08/68] Fixes required after logging changes to master. --- configure.ac | 2 +- src/ssl.c | 73 +++++++++++++++++++++--------- wolfcrypt/src/logging.c | 89 ++++++++++++++++++++++++++++++++----- wolfssl/openssl/sha.h | 1 + wolfssl/wolfcrypt/logging.h | 22 +++++---- 5 files changed, 147 insertions(+), 40 deletions(-) diff --git a/configure.ac b/configure.ac index 336b3ba27..9c4879a28 100644 --- a/configure.ac +++ b/configure.ac @@ -2351,7 +2351,7 @@ then AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_ALWAYS_VERIFY_CB" AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_ALWAYS_KEEP_SNI" AM_CFLAGS="$AM_CFLAGS -DKEEP_OUR_CERT -DKEEP_PEER_CERT" - AM_CFLAGS="$AM_CFLAGS -DHAVE_EXT_CACHE -DOPENSSL_ERR_ONE -DHAVE_EX_DATA" + AM_CFLAGS="$AM_CFLAGS -DHAVE_EXT_CACHE -DHAVE_EX_DATA" fi diff --git a/src/ssl.c b/src/ssl.c index c32c9be6c..2f0db6cc9 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -10583,12 +10583,15 @@ int wolfSSL_set_compression(WOLFSSL* ssl) unsigned long wolfSSL_ERR_get_error(void) { - WOLFSSL_ENTER("wolfSSL_ERR_clear_error"); + WOLFSSL_ENTER("wolfSSL_ERR_get_error"); -#if defined(OPENSSL_ERR_ONE) - unsigned long ret = wc_last_error; - wc_last_error = 0; - return ret; +#if defined(WOLFSSL_NGINX) + { + unsigned long ret = wolfSSL_ERR_peek_error_line_data(NULL, NULL, + NULL, NULL); + wc_RemoveErrorNode(-1); + return ret; + } #else return (unsigned long)(0 - NOT_COMPILED_IN); #endif @@ -12138,8 +12141,8 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) { WOLFSSL_ENTER("wolfSSL_ERR_clear_error"); -#if defined(OPENSSL_ERR_ONE) - wc_last_error = 0; +#if defined(WOLFSSL_NGINX) + wc_ClearErrorNodes(); #endif } @@ -15019,8 +15022,8 @@ unsigned long wolfSSL_ERR_peek_error(void) { WOLFSSL_ENTER("wolfSSL_ERR_peek_error"); -#if defined(OPENSSL_ERR_ONE) - return wc_last_error; +#ifdef WOLFSSL_NGINX + return wolfSSL_ERR_peek_error_line_data(NULL, NULL, NULL, NULL); #else return 0; #endif @@ -21330,7 +21333,7 @@ void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl) } #ifdef WOLFSSL_NGINX if (l == 0) - wc_last_error = ((ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE); + WOLFSSL_ERROR(SSL_NO_PEM_HEADER); #endif pemSz = (int)i; } @@ -21608,6 +21611,10 @@ unsigned long wolfSSL_ERR_peek_last_error_line(const char **file, int *line) WOLFSSL_MSG("Issue peeking at error node in queue"); return 0; } + #ifdef WOLFSSL_NGINX + if (ret == -SSL_NO_PEM_HEADER) + return (ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE; + #endif return (unsigned long)ret; } #else @@ -22032,7 +22039,7 @@ int wolfSSL_PEM_write_bio_X509(WOLFSSL_BIO *bio, WOLFSSL_X509 *cert) XFREE(bio->mem, NULL, DYNAMIC_TYPE_OPENSSL); } bio->mem = (byte*)XMALLOC(pemSz, NULL, DYNAMIC_TYPE_OPENSSL); - if (bio->mem != NULL) { + if (bio->mem == NULL) { return SSL_FAILURE; } bio->memLen = pemSz; @@ -22201,8 +22208,18 @@ unsigned long wolfSSL_ERR_peek_last_error(void) { WOLFSSL_ENTER("wolfSSL_ERR_peek_last_error"); -#if defined(OPENSSL_ERR_ONE) - return wc_last_error; +#ifdef WOLFSSL_NGINX + { + int ret; + + if ((ret = wc_PeekErrorNode(-1, NULL, NULL, NULL)) < 0) { + WOLFSSL_MSG("Issue peeking at error node in queue"); + return 0; + } + if (ret == -SSL_NO_PEM_HEADER) + return (ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE; + return (unsigned long)ret; + } #else return (unsigned long)(0 - NOT_COMPILED_IN); #endif @@ -22943,7 +22960,7 @@ int wolfSSL_AsyncPoll(WOLFSSL* ssl, WOLF_EVENT_FLAG flags) } #endif /* WOLFSSL_ASYNC_CRYPT */ -#if defined(WOLFSSL_NGINX) +#ifdef WOLFSSL_NGINX void wolfSSL_OPENSSL_config(char *config_name) { WOLFSSL_STUB("wolfSSL_OPENSSL_config"); @@ -23210,14 +23227,28 @@ unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, int *line, *flags = 0; } -#if defined(OPENSSL_ERR_ONE) - if (line != NULL) { - *line = (int)wc_last_error_line; +#if defined(WOLFSSL_NGINX) + { + int ret = 0; + + while (1) { + if ((ret = wc_PeekErrorNode(-1, file, NULL, line)) < 0) { + WOLFSSL_MSG("Issue peeking at error node in queue"); + return 0; + } + ret = -ret; + + if (ret == SSL_NO_PEM_HEADER) + return (ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE; + if (ret != WANT_READ && ret != WANT_WRITE && + ret != ZERO_RETURN && ret != SSL_ERROR_ZERO_RETURN) + break; + + wc_RemoveErrorNode(-1); + } + + return (unsigned long)ret; } - if (file != NULL) { - *file = (char*)wc_last_error_file; - } - return wc_last_error; #else return (unsigned long)(0 - NOT_COMPILED_IN); #endif diff --git a/wolfcrypt/src/logging.c b/wolfcrypt/src/logging.c index 43c5a1aad..8aecf5f0b 100644 --- a/wolfcrypt/src/logging.c +++ b/wolfcrypt/src/logging.c @@ -50,6 +50,7 @@ static void* wc_error_heap; struct wc_error_queue { void* heap; /* the heap hint used with nodes creation */ struct wc_error_queue* next; + struct wc_error_queue* prev; char error[WOLFSSL_MAX_ERROR_SZ]; char file[WOLFSSL_MAX_ERROR_SZ]; int value; @@ -61,10 +62,11 @@ static struct wc_error_queue* wc_last_node; #endif -#ifdef DEBUG_WOLFSSL + +#if defined(DEBUG_WOLFSSL) /* Set these to default values initially. */ -static wolfSSL_Logging_cb log_function = 0; +static wolfSSL_Logging_cb log_function = NULL; static int loggingEnabled = 0; #endif /* DEBUG_WOLFSSL */ @@ -215,21 +217,25 @@ void WOLFSSL_LEAVE(const char* msg, int ret) wolfssl_log(LEAVE_LOG , buffer); } } - +#endif /* DEBUG_WOLFSSL */ /* * When using OPENSSL_EXTRA or DEBUG_WOLFSSL_VERBOSE macro then WOLFSSL_ERROR is * mapped to new funtion WOLFSSL_ERROR_LINE which gets the line # and function * name where WOLFSSL_ERROR is called at. */ -#if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) +#if (defined(DEBUG_WOLFSSL) || defined(WOLFSSL_NGINX)) + #if (defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE)) void WOLFSSL_ERROR_LINE(int error, const char* func, unsigned int line, const char* file, void* usrCtx) -#else + #else void WOLFSSL_ERROR(int error) -#endif + #endif { - if (loggingEnabled) { + #if defined(DEBUG_WOLFSSL) && !defined(WOLFSSL_NGINX) + if (loggingEnabled) + #endif + { char buffer[80]; #if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) (void)usrCtx; /* a user ctx for future flexibility */ @@ -254,11 +260,13 @@ void WOLFSSL_ERROR(int error) #else sprintf(buffer, "wolfSSL error occurred, error = %d", error); #endif + #ifdef DEBUG_WOLFSSL wolfssl_log(ERROR_LOG , buffer); + #endif } } -#endif /* DEBUG_WOLFSSL */ +#endif /* DEBUG_WOLFSSL || WOLFSSL_NGINX */ #if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) /* Internal function that is called by wolfCrypt_Init() */ @@ -305,7 +313,7 @@ int wc_LoggingCleanup(void) } -#ifdef DEBUG_WOLFSSL +#if defined(DEBUG_WOLFSSL) || defined(WOLFSSL_NGINX) /* peek at an error node * * index : if -1 then the most recent node is looked at, otherwise search @@ -424,13 +432,74 @@ int wc_AddErrorNode(int error, int line, char* buf, char* file) } else { wc_last_node->next = err; + err->prev = wc_last_node; wc_last_node = err; } } return 0; } -#endif /* DEBUG_WOLFSSL */ + +/* Removes the error node at the specified index. + * index : if -1 then the most recent node is looked at, otherwise search + * through queue for node at the given index + */ +void wc_RemoveErrorNode(int index) +{ + struct wc_error_queue* current; + + if (wc_LockMutex(&debug_mutex) != 0) { + WOLFSSL_MSG("Lock debug mutex failed"); + return; + } + + if (index == -1) + current = wc_last_node; + else { + current = (struct wc_error_queue*)wc_errors; + for (; current != NULL && index > 0; index--) + current = current->next; + } + if (current != NULL) { + if (current->prev != NULL) + current->prev->next = current->next; + if (wc_last_node == current) + wc_last_node = current->prev; + if (wc_errors == current) + wc_errors = current->next; + XFREE(current, current->heap, DYNAMIC_TYPE_LOG); + } + + wc_UnLockMutex(&debug_mutex); +} + +/* Clears out the list of error nodes. + */ +void wc_ClearErrorNodes(void) +{ + if (wc_LockMutex(&debug_mutex) != 0) { + WOLFSSL_MSG("Lock debug mutex failed"); + return; + } + + /* free all nodes from error queue */ + { + struct wc_error_queue* current; + struct wc_error_queue* next; + + current = (struct wc_error_queue*)wc_errors; + while (current != NULL) { + next = current->next; + XFREE(current, current->heap, DYNAMIC_TYPE_LOG); + current = next; + } + } + + wc_errors = NULL; + wc_last_node = NULL; + wc_UnLockMutex(&debug_mutex); +} +#endif /* DEBUG_WOLFSSL || WOLFSSL_NGINX */ int wc_SetLoggingHeap(void* h) diff --git a/wolfssl/openssl/sha.h b/wolfssl/openssl/sha.h index 632862089..d9e168129 100644 --- a/wolfssl/openssl/sha.h +++ b/wolfssl/openssl/sha.h @@ -5,6 +5,7 @@ #define WOLFSSL_SHA_H_ #include +#include #ifdef WOLFSSL_PREFIX #include "prefix_sha.h" diff --git a/wolfssl/wolfcrypt/logging.h b/wolfssl/wolfcrypt/logging.h index c8f9a657a..811b89d6e 100644 --- a/wolfssl/wolfcrypt/logging.h +++ b/wolfssl/wolfcrypt/logging.h @@ -53,6 +53,8 @@ WOLFSSL_API int wolfSSL_SetLoggingCb(wolfSSL_Logging_cb log_function); char* file); WOLFSSL_LOCAL int wc_PeekErrorNode(int index, const char **file, const char **reason, int *line); + WOLFSSL_LOCAL void wc_RemoveErrorNode(int index); + WOLFSSL_LOCAL void wc_ClearErrorNodes(void); WOLFSSL_API int wc_SetLoggingHeap(void* h); #if !defined(NO_FILESYSTEM) && !defined(NO_STDIO_FILESYSTEM) WOLFSSL_API void wc_ERR_print_errors_fp(FILE* fp); @@ -68,13 +70,6 @@ WOLFSSL_API int wolfSSL_SetLoggingCb(wolfSSL_Logging_cb log_function); #define WOLFSSL_STUB(m) \ WOLFSSL_MSG(WOLFSSL_LOG_CAT(wolfSSL Stub, m, not implemented)) -#if defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) - void WOLFSSL_ERROR_LINE(int err, const char* func, unsigned int line, - const char* file, void* ctx); - #define WOLFSSL_ERROR(x) WOLFSSL_ERROR_LINE((x), __func__, __LINE__, __FILE__,NULL) -#else - void WOLFSSL_ERROR(int); -#endif void WOLFSSL_MSG(const char* msg); void WOLFSSL_BUFFER(byte* buffer, word32 length); @@ -84,12 +79,23 @@ WOLFSSL_API int wolfSSL_SetLoggingCb(wolfSSL_Logging_cb log_function); #define WOLFSSL_LEAVE(m, r) #define WOLFSSL_STUB(m) - #define WOLFSSL_ERROR(e) #define WOLFSSL_MSG(m) #define WOLFSSL_BUFFER(b, l) #endif /* DEBUG_WOLFSSL */ +#if (defined(DEBUG_WOLFSSL) || defined(WOLFSSL_NGINX)) + #if (defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE)) + void WOLFSSL_ERROR_LINE(int err, const char* func, unsigned int line, + const char* file, void* ctx); + #define WOLFSSL_ERROR(x) WOLFSSL_ERROR_LINE((x), __func__, __LINE__, __FILE__,NULL) + #else + void WOLFSSL_ERROR(int); + #endif +#else + #define WOLFSSL_ERROR(e) +#endif + #ifdef __cplusplus } #endif From 13e6217fd51dc63870d6432b380d6124581299df Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Tue, 28 Feb 2017 12:22:28 +1000 Subject: [PATCH 09/68] Changes from code review --- src/internal.c | 6 +- src/ocsp.c | 4 +- src/ssl.c | 138 ++++++++++++++++++++++++---------------- wolfcrypt/src/asn.c | 10 +-- wolfssl/ssl.h | 8 ++- wolfssl/wolfcrypt/asn.h | 2 +- 6 files changed, 98 insertions(+), 70 deletions(-) diff --git a/src/internal.c b/src/internal.c index 10971d58b..00c51fa70 100644 --- a/src/internal.c +++ b/src/internal.c @@ -7360,7 +7360,7 @@ static int DoCertificateStatus(WOLFSSL* ssl, byte* input, word32* inOutIdx, InitOcspResponse(response, status, input +*inOutIdx, status_length); - if (OcspResponseDecode(response, ssl->ctx->cm, ssl->heap) != 0) + if (OcspResponseDecode(response, ssl->ctx->cm, ssl->heap, 0) != 0) ret = BAD_CERTIFICATE_STATUS_ERROR; else if (CompareOcspReqResp(request, response) != 0) ret = BAD_CERTIFICATE_STATUS_ERROR; @@ -7442,8 +7442,8 @@ static int DoCertificateStatus(WOLFSSL* ssl, byte* input, word32* inOutIdx, InitOcspResponse(response, status, input +*inOutIdx, status_length); - if ((OcspResponseDecode(response, ssl->ctx->cm, ssl->heap) - != 0) + if ((OcspResponseDecode(response, ssl->ctx->cm, ssl->heap, + 0) != 0) || (response->responseStatus != OCSP_SUCCESSFUL) || (response->status->status != CERT_GOOD)) ret = BAD_CERTIFICATE_STATUS_ERROR; diff --git a/src/ocsp.c b/src/ocsp.c index 4eff1582c..efbae86c8 100644 --- a/src/ocsp.c +++ b/src/ocsp.c @@ -287,7 +287,7 @@ static int CheckResponse(WOLFSSL_OCSP* ocsp, byte* response, int responseSz, XMEMSET(newStatus, 0, sizeof(CertStatus)); InitOcspResponse(ocspResponse, newStatus, response, responseSz); - ret = OcspResponseDecode(ocspResponse, ocsp->cm, ocsp->cm->heap); + ret = OcspResponseDecode(ocspResponse, ocsp->cm, ocsp->cm->heap, 0); if (ret != 0) { WOLFSSL_MSG("OcspResponseDecode failed"); goto end; @@ -682,7 +682,7 @@ OcspResponse* wolfSSL_d2i_OCSP_RESPONSE(OcspResponse** response, XMEMCPY(resp->source, *data, len); resp->maxIdx = len; - if (OcspResponseDecode(resp, NULL, NULL) != 0) { + if (OcspResponseDecode(resp, NULL, NULL, 1) != 0) { wolfSSL_OCSP_RESPONSE_free(resp); return NULL; } diff --git a/src/ssl.c b/src/ssl.c index 2f0db6cc9..ec90a6433 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -9933,7 +9933,7 @@ int wolfSSL_set_compression(WOLFSSL* ssl) /* Clear pointers so freeing certificate doesn't free memory. */ XMEMSET(subjectName, 0, sizeof(WOLFSSL_X509_NAME)); - /* Put nod on the front of the list. */ + /* Put node on the front of the list. */ node->num = (list == NULL) ? 1 : list->num + 1; node->next = list; list = node; @@ -10585,7 +10585,7 @@ int wolfSSL_set_compression(WOLFSSL* ssl) { WOLFSSL_ENTER("wolfSSL_ERR_get_error"); -#if defined(WOLFSSL_NGINX) +#ifdef WOLFSSL_NGINX { unsigned long ret = wolfSSL_ERR_peek_error_line_data(NULL, NULL, NULL, NULL); @@ -15022,7 +15022,7 @@ unsigned long wolfSSL_ERR_peek_error(void) { WOLFSSL_ENTER("wolfSSL_ERR_peek_error"); -#ifdef WOLFSSL_NGINX +#ifdef OPENSSL_EXTRA return wolfSSL_ERR_peek_error_line_data(NULL, NULL, NULL, NULL); #else return 0; @@ -15406,9 +15406,17 @@ long wolfSSL_CTX_add_extra_chain_cert(WOLFSSL_CTX* ctx, WOLFSSL_X509* x509) } else { /* TODO: Do this elsewhere. */ - AllocDer(&derBuffer, derSz, CERT_TYPE, ctx->heap); + ret = AllocDer(&derBuffer, derSz, CERT_TYPE, ctx->heap); + if (ret != 0) { + WOLFSSL_MSG("Memory Error"); + return SSL_FAILURE; + } XMEMCPY(derBuffer->buffer, der, derSz); - AddCA(ctx->cm, &derBuffer, WOLFSSL_USER_CA, !ctx->verifyNone); + ret = AddCA(ctx->cm, &derBuffer, WOLFSSL_USER_CA, !ctx->verifyNone); + if (ret != SSL_SUCCESS) { + WOLFSSL_LEAVE("wolfSSL_CTX_add_extra_chain_cert", ret); + return SSL_FAILURE; + } /* adding cert to existing chain */ if (ctx->certChain != NULL && ctx->certChain->length > 0) { @@ -22295,13 +22303,18 @@ int wolfSSL_X509_NAME_print_ex(WOLFSSL_BIO* bio, WOLFSSL_X509_NAME* name, (void)flags; WOLFSSL_ENTER("wolfSSL_X509_NAME_print_ex"); - for (i = 0; i < indent; i++) - BIO_write(bio, " ", 1); + for (i = 0; i < indent; i++) { + if (wolfSSL_BIO_write(bio, " ", 1) != 1) + return SSL_FAILURE; + } - if (flags == XN_FLAG_RFC2253) - BIO_write(bio, name->name + 1, name->sz - 2); - else - BIO_write(bio, name->name, name->sz); + if (flags == XN_FLAG_RFC2253) { + if (wolfSSL_BIO_write(bio, name->name + 1, name->sz - 2) + != name->sz - 2) + return SSL_FAILURE; + } + else if (wolfSSL_BIO_write(bio, name->name, name->sz) != name->sz) + return SSL_FAILURE; return SSL_SUCCESS; } @@ -22960,6 +22973,51 @@ int wolfSSL_AsyncPoll(WOLFSSL* ssl, WOLF_EVENT_FLAG flags) } #endif /* WOLFSSL_ASYNC_CRYPT */ +#ifdef OPENSSL_EXTRA +unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, int *line, + const char **data, int *flags) +{ + WOLFSSL_ENTER("wolfSSL_ERR_peek_error_line_data"); + + (void)line; + (void)file; + + /* No data or flags stored - error display only in Nginx. */ + if (data != NULL) { + *data = ""; + } + if (flags != NULL) { + *flags = 0; + } + +#if defined(WOLFSSL_NGINX) + { + int ret = 0; + + while (1) { + if ((ret = wc_PeekErrorNode(-1, file, NULL, line)) < 0) { + WOLFSSL_MSG("Issue peeking at error node in queue"); + return 0; + } + ret = -ret; + + if (ret == SSL_NO_PEM_HEADER) + return (ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE; + if (ret != WANT_READ && ret != WANT_WRITE && + ret != ZERO_RETURN && ret != SSL_ERROR_ZERO_RETURN) + break; + + wc_RemoveErrorNode(-1); + } + + return (unsigned long)ret; + } +#else + return (unsigned long)(0 - NOT_COMPILED_IN); +#endif +} +#endif + #ifdef WOLFSSL_NGINX void wolfSSL_OPENSSL_config(char *config_name) { @@ -23211,51 +23269,15 @@ int wolfSSL_i2a_ASN1_INTEGER(BIO *bp, const WOLFSSL_ASN1_INTEGER *a) return len * 2; } -unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, int *line, - const char **data, int *flags) -{ - WOLFSSL_ENTER("wolfSSL_ERR_peek_error_line_data"); - - (void)line; - (void)file; - - /* No data or flags stored - error display only in Nginx. */ - if (data != NULL) { - *data = ""; - } - if (flags != NULL) { - *flags = 0; - } - -#if defined(WOLFSSL_NGINX) - { - int ret = 0; - - while (1) { - if ((ret = wc_PeekErrorNode(-1, file, NULL, line)) < 0) { - WOLFSSL_MSG("Issue peeking at error node in queue"); - return 0; - } - ret = -ret; - - if (ret == SSL_NO_PEM_HEADER) - return (ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE; - if (ret != WANT_READ && ret != WANT_WRITE && - ret != ZERO_RETURN && ret != SSL_ERROR_ZERO_RETURN) - break; - - wc_RemoveErrorNode(-1); - } - - return (unsigned long)ret; - } -#else - return (unsigned long)(0 - NOT_COMPILED_IN); -#endif - -} #ifdef HAVE_SESSION_TICKET +/* Expected return values from implementations of OpenSSL ticket key callback. + */ +#define TICKET_KEY_CB_RET_FAILURE -1 +#define TICKET_KEY_CB_RET_NOT_FOUND 0 +#define TICKET_KEY_CB_RET_OK 1 +#define TICKET_KEY_CB_RET_RENEW 2 + /* The ticket key callback as used in OpenSSL is stored here. */ static int (*ticketKeyCb)(WOLFSSL *ssl, unsigned char *name, unsigned char *iv, WOLFSSL_EVP_CIPHER_CTX *ectx, WOLFSSL_HMAC_CTX *hctx, int enc) = NULL; @@ -23293,10 +23315,13 @@ static int wolfSSL_TicketKeyCb(WOLFSSL* ssl, (void)ctx; + if (ticketKeyCb == NULL) + return WOLFSSL_TICKET_RET_FATAL; + wolfSSL_EVP_CIPHER_CTX_init(&evpCtx); /* Initialize the cipher and HMAC. */ res = ticketKeyCb(ssl, keyName, iv, &evpCtx, &hmacCtx, enc); - if (res != 1 && res != 2) + if (res != TICKET_KEY_CB_RET_OK && res != TICKET_KEY_CB_RET_RENEW) return WOLFSSL_TICKET_RET_FATAL; if (enc) @@ -23335,7 +23360,8 @@ static int wolfSSL_TicketKeyCb(WOLFSSL* ssl, *encLen = encTicketLen + len; } - ret = (res == 2) ? WOLFSSL_TICKET_RET_CREATE : WOLFSSL_TICKET_RET_OK; + ret = (res == TICKET_KEY_CB_RET_RENEW) ? WOLFSSL_TICKET_RET_CREATE : + WOLFSSL_TICKET_RET_OK; end: return ret; } diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 992bdae85..7755b2679 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -9708,7 +9708,7 @@ static int DecodeCerts(byte* source, static int DecodeBasicOcspResponse(byte* source, word32* ioIndex, - OcspResponse* resp, word32 size, void* cm, void* heap) + OcspResponse* resp, word32 size, void* cm, void* heap, int noVerify) { int length; word32 idx = *ioIndex; @@ -9766,8 +9766,8 @@ static int DecodeBasicOcspResponse(byte* source, word32* ioIndex, InitDecodedCert(&cert, resp->cert, resp->certSz, heap); /* Don't verify if we don't have access to Cert Manager. */ - ret = ParseCertRelative(&cert, CERT_TYPE, - cm == NULL ? NO_VERIFY : VERIFY, cm); + ret = ParseCertRelative(&cert, CERT_TYPE, noVerify ? NO_VERIFY : VERIFY, + cm); if (ret < 0) { WOLFSSL_MSG("\tOCSP Responder certificate parsing failed"); FreeDecodedCert(&cert); @@ -9824,7 +9824,7 @@ void InitOcspResponse(OcspResponse* resp, CertStatus* status, } -int OcspResponseDecode(OcspResponse* resp, void* cm, void* heap) +int OcspResponseDecode(OcspResponse* resp, void* cm, void* heap, int noVerify) { int ret; int length = 0; @@ -9869,7 +9869,7 @@ int OcspResponseDecode(OcspResponse* resp, void* cm, void* heap) if (GetLength(source, &idx, &length, size) < 0) return ASN_PARSE_E; - ret = DecodeBasicOcspResponse(source, &idx, resp, size, cm, heap); + ret = DecodeBasicOcspResponse(source, &idx, resp, size, cm, heap, noVerify); if (ret < 0) return ret; diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index d9d1fc9c0..c095ba280 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -2243,6 +2243,11 @@ WOLFSSL_API int wolfSSL_CTX_set_msg_callback_arg(WOLFSSL_CTX *ctx, void* arg); WOLFSSL_API int wolfSSL_set_msg_callback_arg(WOLFSSL *ssl, void* arg); #endif +#ifdef OPENSSL_EXTRA +WOLFSSL_API unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, + int *line, const char **data, int *flags); +#endif + #ifdef WOLFSSL_NGINX /* Not an OpenSSL API. */ WOLFSSL_LOCAL int wolfSSL_get_ocsp_response(WOLFSSL* ssl, byte** response); @@ -2278,9 +2283,6 @@ WOLFSSL_API int wolfSSL_X509_check_host(WOLFSSL_X509 *x, const char *chk, WOLFSSL_API int wolfSSL_i2a_ASN1_INTEGER(WOLFSSL_BIO *bp, const WOLFSSL_ASN1_INTEGER *a); -WOLFSSL_API unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, - int *line, const char **data, int *flags); - #ifdef HAVE_SESSION_TICKET WOLFSSL_API int wolfSSL_CTX_set_tlsext_ticket_key_cb(WOLFSSL_CTX *, int (*)( WOLFSSL *ssl, unsigned char *name, unsigned char *iv, diff --git a/wolfssl/wolfcrypt/asn.h b/wolfssl/wolfcrypt/asn.h index 02ad51cc0..23930faeb 100644 --- a/wolfssl/wolfcrypt/asn.h +++ b/wolfssl/wolfcrypt/asn.h @@ -868,7 +868,7 @@ struct OcspRequest { WOLFSSL_LOCAL void InitOcspResponse(OcspResponse*, CertStatus*, byte*, word32); -WOLFSSL_LOCAL int OcspResponseDecode(OcspResponse*, void*, void* heap); +WOLFSSL_LOCAL int OcspResponseDecode(OcspResponse*, void*, void* heap, int); WOLFSSL_LOCAL int InitOcspRequest(OcspRequest*, DecodedCert*, byte, void*); WOLFSSL_LOCAL void FreeOcspRequest(OcspRequest*); From 455fb96faa863fd2d11414f2d25372327aba9e9e Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Wed, 11 Jan 2017 17:56:46 +1000 Subject: [PATCH 10/68] Extend testing for coverage --- certs/test/cert-ext-ia.cfg | 18 + certs/test/cert-ext-ia.der | Bin 0 -> 1030 bytes certs/test/cert-ext-nc.cfg | 18 + certs/test/cert-ext-nc.der | Bin 0 -> 1052 bytes certs/test/cert-ext-ns.der | Bin 0 -> 4677 bytes certs/test/gen-ext-certs.sh | 69 + wolfcrypt/src/asn.c | 66 +- wolfcrypt/src/hash.c | 39 +- wolfcrypt/src/tfm.c | 33 +- wolfcrypt/src/wc_port.c | 2 +- wolfcrypt/test/test.c | 2466 +++++++++++++++++++++++++++++-- wolfcrypt/user-crypto/src/rsa.c | 2 +- 12 files changed, 2522 insertions(+), 191 deletions(-) create mode 100644 certs/test/cert-ext-ia.cfg create mode 100644 certs/test/cert-ext-ia.der create mode 100644 certs/test/cert-ext-nc.cfg create mode 100644 certs/test/cert-ext-nc.der create mode 100644 certs/test/cert-ext-ns.der create mode 100644 certs/test/gen-ext-certs.sh diff --git a/certs/test/cert-ext-ia.cfg b/certs/test/cert-ext-ia.cfg new file mode 100644 index 000000000..8721916b3 --- /dev/null +++ b/certs/test/cert-ext-ia.cfg @@ -0,0 +1,18 @@ +[ req ] +distinguished_name = req_distinguished_name +prompt = no +x509_extensions = v3_ca + +[ req_distinguished_name ] +C = AU +ST = Queensland +L = Brisbane +O = wolfSSL Inc +OU = Engineering +CN = www.wolfssl.com +emailAddress = support@www.wolfsssl.com + +[ v3_ca ] +inhibitAnyPolicy = critical,1 +nsComment = "Testing inhibit any" + diff --git a/certs/test/cert-ext-ia.der b/certs/test/cert-ext-ia.der new file mode 100644 index 0000000000000000000000000000000000000000..73ea7c0a86f18a8789a72c2caa3c83bed8189f9e GIT binary patch literal 1030 zcmXqLVqr39VtTcJnTe5!iIbr(#&5IIjlRPMylk9WZ60mkc^MhGSs4r(ml$#zaI!In zvaks=Iffbv8wi3p96VfsrKzcT#W{(2DTaau{2)Pg9uB9X%;KcPyi`LG10j$Q7Y}!N zeok6&u#bXgUNTISn}^#qFFi9aHMJ-+FWpeWKn$donTNl;yj%~YzPLC?FF8NgP~AWk z?i@}=F^S^Rf`a^_5(k7jh(ZH7ab81n14BatBV$uTV~Z#-*T}#U${i}+Xkt`CjsQkh z2IeM4eg=akMlPl%Mn;AMQ#l@nJANw6-G0f{QJpdMnCrSvdsGZ|Og*RXckP=@$DW$` zzgMK!|BIOuSo*!|6#H{i{r-o0s}JbctWH@W{^wL|^{xksPmA>O_1bPsExxrzI(TQi z{dGxRRsV;{$${P6DfVlfcPy2OG15l{hJoZvo~b(!`yh8J<7!wIhi{}E(z>RIjnVI z;WV#353fi?A760bU~&b&i@AZ(v<4&PsSC?@316CC{3urSWESsX%Y-FcHe@h0Cq`ZtQ8D3=)Z&uNymW=kyo}7G%o2sfyh`MNL0f|TgW5%ZY(4k9ek#@4{;;((KuleILhQK(Z#_@muUjOyO0#;Qv`t_^?xBN= zJr;fyJiebdI}Yd6l|NKGCBXQ( z^iEdj!!u9yF6=z6ZS+ey`@?Y^{WUop+T|R-O%gNSMa54l;d(ng#Kf4xurD*^c1X2o zjqjo`YuQ~EyQg@hg|I~!uqiB4my}qv*PK^V;EKPWz1Y;-=dTII#GgL8Yk_oL5>NP} z^A7J`=bez?oAJEb=e)_eyGOPNRJ~U!KRGE;*KFF$Ex%oi5AMA1YPEyTyx(avJe$4% E0I0os$^ZZW literal 0 HcmV?d00001 diff --git a/certs/test/cert-ext-nc.cfg b/certs/test/cert-ext-nc.cfg new file mode 100644 index 000000000..b27f3f4fe --- /dev/null +++ b/certs/test/cert-ext-nc.cfg @@ -0,0 +1,18 @@ +[ req ] +distinguished_name = req_distinguished_name +prompt = no +x509_extensions = v3_ca + +[ req_distinguished_name ] +C = AU +ST = Queensland +L = Brisbane +O = wolfSSL Inc +OU = Engineering +CN = www.wolfssl.com +emailAddress = support@www.wolfsssl.com + +[ v3_ca ] +nameConstraints = critical,permitted;email:.wolfssl.com +nsComment = "Testing name constraints" + diff --git a/certs/test/cert-ext-nc.der b/certs/test/cert-ext-nc.der new file mode 100644 index 0000000000000000000000000000000000000000..ff944476d5564054aec33f6ea7572170d309cfd6 GIT binary patch literal 1052 zcmXqLVv#UtVrE#t%*4pV#L2L$Fxht+|JyDDUN%mxHjlRNyo`+8tPBQ?OANUUIN6v( zS=fY`977F-4Fo|P4j!(+($v(v;+(|16hlD+evlwL4~J7xW^qztUaFypfe=WDi-)^B zKPN3X*hj%LFBvAv&BN`Qm!6rInp%{Zmu@IwAO=#)%)?(^UakjHUtFA{mzBO}9ssT>c(9X}Q3ZolN}sLq&r%yr$TJt_t}rk>OHyY@|{V^7We z-z(DV|HaG+EdAbfiv78%e*eS0)d%!zR;R2G|8pv~de;NRr$u`CdTlqR7T;PU9lSH% z{<DSDi+1cs*E-U6|H0xPBy_CLi<2*a}%>~i5DXwo9Nl#xl?QLxgcR}<2 zmrruO-n@O!;+0H(_`Z@$p(lO4+W)jen5Hgla(r;MD1(vr7Y}p9@1$;t=P{M$HjlrZo$z(84Mu(JIBz$}-i;$jr(-#VXapDk;gzB+<&q(8|=pDmld}IoZlA z$;ucc2sSb}Gd(Y{q_iki!7(R2zbLaLBiBlyI3v+8JhLPtDA>_8FS)3)pd>Rt53C$y zjc0LjX=;&`g0q6HLTIp#g1>^Tf>Ky&Q6|VN9R<(4WIZJv1^-Y5TLqY?LP$|*afyOo zYDsy1Q8rXkNh4WP!N|bC46Y2KSwUC9Ex$-1v9u&3zbLaRHASJcI8`A(FQ-yTN5R<- z*;wbC#NuKFV}*dyq@2uTg@B^W+{B_v1w`0p=I1FmLJTUYRM1s$H-&p6EHNiDC9|Xw zE&%eIUw(;#Q)*g%QL2@KUw)Z_f`x*CffX1*oa*iyf}z1Ntt7Qb!AilaG)KYEOu@+5 z%GA=z)KbC7z}QRySwnDXQdVkm$&e2^s6SxA?wwkx;F*_}kD3~xaRQP=N?Jw5iCB^p zDCj{LqDR*|wbDvK!^ptILLn)$1d;YZN4SskOT-D7+58ySs9sF8CZaj zk)@S+qLs0!m1U}xnSqr-vQ=WDRjRp_2{;#^#3e{K2%Dr@r6gOKCtD>YTNx)?nV4D` zCWG>kQIb`vfmK?nm64^Dfss|3rIo2U4mVg>B^q0qnOIqvS{a&J8JSz9nOdb8S|z4f zC0ke-8(LXdTA8L;85x0cC{{NZC4$_UXl7+%WR+xWWszo;W?_|NX=Q3^m1J&}WC$Wn zl0Z^v(DDQ1a%60gW@VmgWnd0+WNNZiYMPaau~kZvm6@59nGwiUW`xU25y+fW3oCO2 zD^o)&lN3;iXJKh&W{KSw=1Eq`<{-ssW}x6oNwzXHvNAUT1%-JMC>BhTtW3?UQjD!E z&9Ix0lm-eeb90b`lMJlVOso=(tc*;p(u_bU%`n-@(#Xop+{(}bX$GK(OH2dVXl@D$d1GUcrG_b>?Wnyk+VFAikW|meK z#vn`6QbB@ADWDW$o@!;1W|eGeWoe2%E)r9%3{tHuQ>;=L8YA%i!+lI zob&UFONtUR^Gb@X6q1WFOEQxab1>|5cC-o!3Ux&hhZ+MacSDO4(^K(jN3=l{AeFas zkPn!JVxpm*v7VWpp`NLpsh+u>p`M|Ul>&+aP_bhWuNSKqZ4hY?ZV;-cmzkTGo~oao znP#A9pl6_`r>Cul0lru_73as??bMn*k^~zFAJqfFbK%VtXNzDVbs6b5<6ty7NnY&rJ7+aZ{S~;3qIU8BIxLCP5 zTRAydxfxg)8(0}wTDcj6${AxzD>p|_9&~gAB@bgmD`R7@S)kA%v6-Y`X$-1`OcFsh zn5Kcs&g3*ufohm&Wocn$lm^ON6OG_V9^4AV4F znU!J&Y6u!xfI=kA$jZPFRM{96m7jmYFpc>W8(#pud${+<) z5*VjinWb2nrGhfF0hj>}E>Mswq*z#`nt{qaOG7IY15ojpWC^NDk`1j=Q>;?bKqasV z*ydCNP`)!Vuu4WQ!;@1$UNSVbGPba?Fa*h2nt*aaC86jWoFB!b$-Cg5r?IS~{<2>ljD zpi0Le31muQBB;POG`BLg1eMh(Nmk}*pjL#12`C7S5<%saMItB)k@TB^!p}4n zW@=@MT;>|2SXr1^nVVTzCWAuWJkcu63=~eL$sh)(&@}=jCu3t!1euyxC7FTJ2*Ury zX;x+yRv^_zpjMDcBB(WGYyoO}SQvw>N-+c#(MI4}FEQE5(9kLcx$aA}0Hrf<(}ByN ziRH3E6Z7r`%uI|-Oacjy?R%d*|C}Nur786L^>0xcB41;Uo^*5aHLJ zry@gI)t+kiOV5A(b>YNA#-2Bvle2=nFZI7D2=u+!nOS|j;M?XqLM6AWW4*&JPunkA zzHq~rMXI0H%S=j_c>0Bn<^6=6PZ*xuwc0BApJ~?@n|BYoUz>No`Eq^Dr*9u@*WWFj zXe=o!<8Zn}MN)C{O_6_Vw1STJUuE%p(wpqwVUyW>`k(t=?K=OXQ`hm$y>ij{Kzi|G z5std2_VbH(7;~MEwKr*>*7YvJw|jq45g*_cCRg&7(Dv#=U4Gcx`+ z-~$Qpg9KQZnHbp&a@jbv*%(<_*%^6Q5)I-P#x8(X@M4^qNEN)i0XrM3HXk#S6pKjz z)5}tAYkK>#51((yy5b?BQ!S}ypeja81rN?jvV1IJEF$%nQ~0!Et=fI`F*!}?y54~UeYb;a>=oZHPb7?KjBneQx-SVDphgIt+(r+ zx1?%K?b_RRFRoFnSy$l9y}v7(v~o4%dAW}~eJ-UY`S6QizQES0f1W$B8r?oOH!x0P z+q~Ax(eIbmx;hl~ZRgA8WBYAv>QT63u6p;8)Og;uvN$TMP 2>&1 + + if [ "$?" = "0" -a -f $OUT ]; then + echo "Created: $OUT" + else + cat $TMP + echo "Failed: $OUT" + fi + + rm $TMP +} + +OUT=certs/test/cert-ext-nc.der +KEYFILE=certs/test/cert-ext-nc-key.der +CONFIG=certs/test/cert-ext-nc.cfg +tee >$CONFIG <$CONFIG <md5); + ret = 0; #endif break; case WC_HASH_TYPE_SHA: #ifndef NO_SHA ret = wc_InitSha(&hash->sha); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA224: #ifdef WOLFSSL_SHA224 ret = wc_InitSha224(&hash->sha224); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA256: #ifndef NO_SHA256 ret = wc_InitSha256(&hash->sha256); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA384: #ifdef WOLFSSL_SHA384 ret = wc_InitSha384(&hash->sha384); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA512: #ifdef WOLFSSL_SHA512 ret = wc_InitSha512(&hash->sha512); - if (ret != 0) - return ret; #endif break; @@ -280,7 +271,7 @@ int wc_HashInit(wc_HashAlg* hash, enum wc_HashType type) case WC_HASH_TYPE_MD4: case WC_HASH_TYPE_NONE: default: - return BAD_FUNC_ARG; + ret = BAD_FUNC_ARG; }; return ret; @@ -298,6 +289,7 @@ int wc_HashUpdate(wc_HashAlg* hash, enum wc_HashType type, const byte* data, case WC_HASH_TYPE_MD5: #ifndef NO_MD5 wc_Md5Update(&hash->md5, data, dataSz); + ret = 0; #endif break; case WC_HASH_TYPE_SHA: @@ -310,29 +302,21 @@ int wc_HashUpdate(wc_HashAlg* hash, enum wc_HashType type, const byte* data, case WC_HASH_TYPE_SHA224: #ifdef WOLFSSL_SHA224 ret = wc_Sha224Update(&hash->sha224, data, dataSz); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA256: #ifndef NO_SHA256 ret = wc_Sha256Update(&hash->sha256, data, dataSz); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA384: #ifdef WOLFSSL_SHA384 ret = wc_Sha384Update(&hash->sha384, data, dataSz); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA512: #ifdef WOLFSSL_SHA512 ret = wc_Sha512Update(&hash->sha512, data, dataSz); - if (ret != 0) - return ret; #endif break; @@ -342,7 +326,7 @@ int wc_HashUpdate(wc_HashAlg* hash, enum wc_HashType type, const byte* data, case WC_HASH_TYPE_MD4: case WC_HASH_TYPE_NONE: default: - return BAD_FUNC_ARG; + ret = BAD_FUNC_ARG; }; return ret; @@ -359,41 +343,32 @@ int wc_HashFinal(wc_HashAlg* hash, enum wc_HashType type, byte* out) case WC_HASH_TYPE_MD5: #ifndef NO_MD5 wc_Md5Final(&hash->md5, out); + ret = 0; #endif break; case WC_HASH_TYPE_SHA: #ifndef NO_SHA ret = wc_ShaFinal(&hash->sha, out); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA224: #ifdef WOLFSSL_SHA224 ret = wc_Sha224Final(&hash->sha224, out); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA256: #ifndef NO_SHA256 ret = wc_Sha256Final(&hash->sha256, out); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA384: #ifdef WOLFSSL_SHA384 ret = wc_Sha384Final(&hash->sha384, out); - if (ret != 0) - return ret; #endif break; case WC_HASH_TYPE_SHA512: #ifdef WOLFSSL_SHA512 ret = wc_Sha512Final(&hash->sha512, out); - if (ret != 0) - return ret; #endif break; @@ -403,10 +378,10 @@ int wc_HashFinal(wc_HashAlg* hash, enum wc_HashType type, byte* out) case WC_HASH_TYPE_MD4: case WC_HASH_TYPE_NONE: default: - return BAD_FUNC_ARG; + ret = BAD_FUNC_ARG; }; - return 0; + return ret; } diff --git a/wolfcrypt/src/tfm.c b/wolfcrypt/src/tfm.c index f39728546..7fba9c64c 100644 --- a/wolfcrypt/src/tfm.c +++ b/wolfcrypt/src/tfm.c @@ -2043,26 +2043,26 @@ int fp_leading_bit(fp_int *a) void fp_lshd(fp_int *a, int x) { - int y; + int y; - /* move up and truncate as required */ - y = MIN(a->used + x - 1, (int)(FP_SIZE-1)); + /* move up and truncate as required */ + y = MIN(a->used + x - 1, (int)(FP_SIZE-1)); - /* store new size */ - a->used = y + 1; + /* store new size */ + a->used = y + 1; - /* move digits */ - for (; y >= x; y--) { - a->dp[y] = a->dp[y-x]; - } + /* move digits */ + for (; y >= x; y--) { + a->dp[y] = a->dp[y-x]; + } - /* zero lower digits */ - for (; y >= 0; y--) { - a->dp[y] = 0; - } + /* zero lower digits */ + for (; y >= 0; y--) { + a->dp[y] = 0; + } - /* clamp digits */ - fp_clamp(a); + /* clamp digits */ + fp_clamp(a); } @@ -2095,6 +2095,9 @@ void fp_rshb(fp_int *c, int x) /* set the carry to the carry bits of the current word found above */ r = rr; } + + /* clamp digits */ + fp_clamp(c); } diff --git a/wolfcrypt/src/wc_port.c b/wolfcrypt/src/wc_port.c index cf82ca674..a5d4511cc 100644 --- a/wolfcrypt/src/wc_port.c +++ b/wolfcrypt/src/wc_port.c @@ -130,7 +130,7 @@ wolfSSL_Mutex* wc_InitAndAllocMutex() { wolfSSL_Mutex* m = (wolfSSL_Mutex*) XMALLOC(sizeof(wolfSSL_Mutex), NULL, DYNAMIC_TYPE_MUTEX); - if(m && wc_InitMutex(m)) + if(m && wc_InitMutex(m) == 0) return m; XFREE(m, NULL, DYNAMIC_TYPE_MUTEX); m = NULL; diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 24aaaecc8..d072ff8d5 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -39,6 +39,9 @@ #define HEAP_HINT NULL #endif /* WOLFSSL_STATIC_MEMORY */ +#include +#include + #ifdef WOLFSSL_TEST_CERT #include #else @@ -59,9 +62,11 @@ #endif #include +#include #include #include #include +#include #include #include #include @@ -173,6 +178,9 @@ typedef struct testVector { size_t outLen; } testVector; +int error_test(void); +int base64_test(void); +int asn_test(void); int md2_test(void); int md5_test(void); int md4_test(void); @@ -181,6 +189,7 @@ int sha224_test(void); int sha256_test(void); int sha512_test(void); int sha384_test(void); +int hash_test(void); int hmac_md5_test(void); int hmac_sha_test(void); int hmac_sha224_test(void); @@ -245,6 +254,9 @@ int scrypt_test(void); int pkcs7signed_test(void); int pkcs7encrypted_test(void); #endif +#if !defined(NO_ASN_TIME) && defined(WOLFSSL_TEST_CERT) +int cert_test(void); +#endif #if defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_TEST_CERT) int certext_test(void); #endif @@ -254,6 +266,14 @@ int idea_test(void); #ifdef WOLFSSL_STATIC_MEMORY int memory_test(void); #endif +#ifdef HAVE_VALGRIND +int mp_test(void); +#endif +int logging_test(void); +int mutex_test(void); +#ifdef USE_WOLFSSL_MEMORY +int memcb_test(void); +#endif #if defined(DEBUG_WOLFSSL) && !defined(HAVE_VALGRIND) && !defined(OPENSSL_EXTRA) int wolfSSL_Debugging_ON(void); @@ -356,6 +376,25 @@ int wolfcrypt_test(void* args) (void)devId; #endif /* WOLFSSL_ASYNC_CRYPT */ + if ( (ret = error_test()) != 0) + return err_sys("error test failed!\n", ret); + else + printf( "error test passed!\n"); + +#ifndef NO_CODING + if ( (ret = base64_test()) != 0) + return err_sys("base64 test failed!\n", ret); + else + printf( "base64 test passed!\n"); +#endif + +#ifndef NO_ASN + if ( (ret = asn_test()) != 0) + return err_sys("base64 test failed!\n", ret); + else + printf( "base64 test passed!\n"); +#endif + #ifndef NO_MD5 if ( (ret = md5_test()) != 0) return err_sys("MD5 test failed!\n", ret); @@ -412,6 +451,11 @@ int wolfcrypt_test(void* args) printf( "SHA-512 test passed!\n"); #endif + if ( (ret = hash_test()) != 0) + return err_sys("Hash test failed!\n", ret); + else + printf( "Hash test passed!\n"); + #ifdef WOLFSSL_RIPEMD if ( (ret = ripemd_test()) != 0) return err_sys("RIPEMD test failed!\n", ret); @@ -616,6 +660,13 @@ int wolfcrypt_test(void* args) printf( "RSA test passed!\n"); #endif +#if !defined(NO_ASN_TIME) && defined(WOLFSSL_TEST_CERT) + if ( (ret = cert_test()) != 0) + return err_sys("CERT test failed!\n", ret); + else + printf( "CERT test passed!\n"); +#endif + #if defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_TEST_CERT) if ( (ret = certext_test()) != 0) return err_sys("CERT EXT test failed!\n", ret); @@ -728,6 +779,32 @@ int wolfcrypt_test(void* args) printf( "PKCS7encrypted test passed!\n"); #endif +#ifdef HAVE_VALGRIND + if ( (ret = mp_test()) != 0) + return err_sys("mp test failed!\n", ret); + else + printf( "mp test passed!\n"); +#endif + +#ifdef HAVE_VALGRIND + if ( (ret = logging_test()) != 0) + return err_sys("logging test failed!\n", ret); + else + printf( "logging test passed!\n"); +#endif + + if ( (ret = mutex_test()) != 0) + return err_sys("mutex test failed!\n", ret); + else + printf( "mutex test passed!\n"); + +#ifdef USE_WOLFSSL_MEMORY + if ( (ret = memcb_test()) != 0) + return err_sys("memcb test failed!\n", ret); + else + printf( "memcb test passed!\n"); +#endif + #if defined(USE_WOLFSSL_MEMORY) && defined(WOLFSSL_TRACK_MEMORY) ShowMemoryTracker(); #endif @@ -775,6 +852,190 @@ int wolfcrypt_test(void* args) #endif /* NO_MAIN_DRIVER */ +int error_test() +{ + const char* errStr; + char out[WOLFSSL_MAX_ERROR_SZ]; + const char* unknownStr = wc_GetErrorString(0); + +#ifdef NO_ERROR_STRINGS + /* Ensure a valid error code's string matches an invalid code's. + * The string is that error strings are not available. + */ + errStr = wc_GetErrorString(OPEN_RAN_E); + wc_ErrorString(OPEN_RAN_E, out); + if (XSTRNCMP(errStr, unknownStr, XSTRLEN(unknownStr)) != 0) + return -10; + if (XSTRNCMP(out, unknownStr, XSTRLEN(unknownStr)) != 0) + return -11; +#else + int i; + int j = 0; + /* Values that are not or no longer error codes. */ + int missing[] = { -122, -123, -124, -127, -128, -129, + -161, -162, -163, -164, -165, -166, -167, -168, -169, + -178, -179, -233, + 0 }; + + /* Check that all errors have a string and it's the same through the two + * APIs. Check that the values that are not errors map to the unknown + * string. + */ + for (i = OPEN_RAN_E; i >= ECC_CDH_KAT_FIPS_E; i--) { + errStr = wc_GetErrorString(i); + wc_ErrorString(i, out); + + if (i != missing[j]) { + if (XSTRNCMP(errStr, unknownStr, XSTRLEN(unknownStr)) == 0) + return -10; + if (XSTRNCMP(out, unknownStr, XSTRLEN(unknownStr)) == 0) + return -11; + if (XSTRNCMP(errStr, out, XSTRLEN(errStr)) != 0) + return -12; + } + else { + j++; + if (XSTRNCMP(errStr, unknownStr, XSTRLEN(unknownStr)) != 0) + return -13; + if (XSTRNCMP(out, unknownStr, XSTRLEN(unknownStr)) != 0) + return -14; + } + } + + /* Check if the next possible value has been given a string. */ + errStr = wc_GetErrorString(i); + wc_ErrorString(i, out); + if (XSTRNCMP(errStr, unknownStr, XSTRLEN(unknownStr)) != 0) + return -15; + if (XSTRNCMP(out, unknownStr, XSTRLEN(unknownStr)) != 0) + return -16; +#endif + + return 0; +} + +#ifndef NO_CODING +int base64_test() +{ + int ret; + const byte good[] = "A+Gd\0\0\0"; + const byte goodEnd[] = "A+Gd \r\n"; + byte out[128]; + word32 outLen; + byte data[3]; + word32 dataLen; + byte longData[79] = { 0 }; + const byte symbols[] = "+/A="; + const byte badSmall[] = "AAA Gdj="; + const byte badLarge[] = "AAA~Gdj="; + const byte badEOL[] = "A+Gd "; + int i; + + /* Good Base64 encodings. */ + outLen = sizeof(out); + ret = Base64_Decode(good, sizeof(good), out, &outLen); + if (ret != 0) + return -20; + outLen = sizeof(out); + ret = Base64_Decode(goodEnd, sizeof(goodEnd), out, &outLen); + if (ret != 0) + return -21; + + /* Bad parameters. */ + outLen = 1; + ret = Base64_Decode(good, sizeof(good), out, &outLen); + if (ret != BAD_FUNC_ARG) + return -22; + + outLen = sizeof(out); + ret = Base64_Decode(badEOL, sizeof(badEOL), out, &outLen); + if (ret != ASN_INPUT_E) + return -23; + /* Bad character at each offset 0-3. */ + for (i = 0; i < 4; i++) { + outLen = sizeof(out); + ret = Base64_Decode(badSmall + i, 4, out, &outLen); + if (ret != ASN_INPUT_E) + return -24 - i; + ret = Base64_Decode(badLarge + i, 4, out, &outLen); + if (ret != ASN_INPUT_E) + return -28 - i; + } + + /* Decode and encode all symbols - non-alphanumeric. */ + dataLen = sizeof(data); + ret = Base64_Decode(symbols, sizeof(symbols), data, &dataLen); + if (ret != 0) + return -40; + outLen = sizeof(out); + ret = Base64_Encode(data, dataLen, NULL, &outLen); + if (ret != LENGTH_ONLY_E) + return -41; + outLen = sizeof(out); + ret = Base64_Encode(data, dataLen, out, &outLen); + if (ret != 0) + return -42; + outLen = 7; + ret = Base64_EncodeEsc(data, dataLen, out, &outLen); + if (ret != BUFFER_E) + return -43; + outLen = sizeof(out); + ret = Base64_EncodeEsc(data, dataLen, NULL, &outLen); + if (ret != LENGTH_ONLY_E) + return -44; + outLen = sizeof(out); + ret = Base64_EncodeEsc(data, dataLen, out, &outLen); + if (ret != 0) + return -45; + outLen = sizeof(out); + ret = Base64_Encode_NoNl(data, dataLen, out, &outLen); + if (ret != 0) + return -46; + + /* Data that results in an encoding longer than one line. */ + outLen = sizeof(out); + dataLen = sizeof(longData); + ret = Base64_Encode(longData, dataLen, out, &outLen); + if (ret != 0) + return -47; + outLen = sizeof(out); + ret = Base64_EncodeEsc(longData, dataLen, out, &outLen); + if (ret != 0) + return -48; + outLen = sizeof(out); + ret = Base64_Encode_NoNl(longData, dataLen, out, &outLen); + if (ret != 0) + return -49; + + return 0; +} +#endif + +#ifndef NO_ASN +int asn_test() +{ +#ifndef NO_ASN_TIME + { + time_t now; + + /* Parameter Validation tests. */ + if (wc_GetTime(NULL, sizeof(now)) != BAD_FUNC_ARG) + return -100; + if (wc_GetTime(&now, 0) != BUFFER_E) + return -101; + + now = 0; + if (wc_GetTime(&now, sizeof(now)) != 0) + return -102; + if (now == 0) + return -103; + } +#endif + + return 0; +} +#endif + #ifdef WOLFSSL_MD2 int md2_test() { @@ -855,6 +1116,7 @@ int md2_test() int md5_test(void) { Md5 md5; + Md5 partialMd5; byte hash[MD5_DIGEST_SIZE]; testVector a, b, c, d, e; @@ -909,6 +1171,26 @@ int md5_test(void) return -5 - i; } + /* Position restoration and getting the hash doesn't invalidate state. */ + wc_InitMd5(&md5); + wc_InitMd5(&partialMd5); + wc_Md5Update(&partialMd5, (byte*)a.input, 1); + wc_Md5RestorePos(&md5, &partialMd5); + wc_Md5GetHash(&partialMd5, hash); + wc_Md5Update(&partialMd5, (byte*)a.input + 1, (word32)a.inLen - 1); + wc_Md5Update(&md5, (byte*)a.input + 1, (word32)a.inLen - 1); + wc_Md5Final(&partialMd5, hash); + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -10; + XMEMSET(hash, 0, a.outLen); + wc_Md5Final(&md5, hash); + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -11; + if (wc_Md5Hash((byte*)a.input, (word32)a.inLen, hash) != 0) + return -12; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -13; + return 0; } #endif /* NO_MD5 */ @@ -997,6 +1279,7 @@ int md4_test(void) int sha_test(void) { Sha sha; + Sha partialSha; byte hash[SHA_DIGEST_SIZE]; testVector a, b, c, d; @@ -1048,6 +1331,43 @@ int sha_test(void) return -10 - i; } + /* Position restoration and getting the hash doesn't invalidate state. */ + ret = wc_InitSha(&sha); + if (ret != 0) + return -20; + ret = wc_InitSha(&partialSha); + if (ret != 0) + return -21; + ret = wc_ShaUpdate(&partialSha, (byte*)a.input, 1); + if (ret != 0) + return -22; + wc_ShaRestorePos(&sha, &partialSha); + ret = wc_ShaGetHash(&partialSha, hash); + if (ret != 0) + return -23; + ret = wc_ShaUpdate(&partialSha, (byte*)a.input + 1, (word32)a.inLen - 1); + if (ret != 0) + return -24; + ret = wc_ShaUpdate(&sha, (byte*)a.input + 1, (word32)a.inLen - 1); + if (ret != 0) + return -25; + ret = wc_ShaFinal(&partialSha, hash); + if (ret != 0) + return -26; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -27; + XMEMSET(hash, 0, a.outLen); + ret = wc_ShaFinal(&sha, hash); + if (ret != 0) + return -28; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -29; + ret = wc_ShaHash((byte*)a.input, (word32)a.inLen, hash); + if (ret != 0) + return -30; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -31; + return 0; } @@ -1225,6 +1545,30 @@ int sha224_test(void) return -10 - i; } + /* Getting the hash doesn't invalidate state. */ + ret = wc_InitSha224(&sha); + if (ret != 0) + return -20; + ret = wc_Sha224Update(&sha, (byte*)a.input, 1); + if (ret != 0) + return -21; + ret = wc_Sha224GetHash(&sha, hash); + if (ret != 0) + return -22; + ret = wc_Sha224Update(&sha, (byte*)a.input + 1, a.inLen - 1); + if (ret != 0) + return -23; + ret = wc_Sha224Final(&sha, hash); + if (ret != 0) + return -24; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -25; + ret = wc_Sha224Hash((byte*)a.input, a.inLen, hash); + if (ret != 0) + return -26; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -27; + return 0; } #endif @@ -1234,6 +1578,7 @@ int sha224_test(void) int sha256_test(void) { Sha256 sha; + Sha256 partialSha; byte hash[SHA256_DIGEST_SIZE]; testVector a, b; @@ -1274,6 +1619,44 @@ int sha256_test(void) return -10 - i; } + /* Position restoration and getting the hash doesn't invalidate state. */ + ret = wc_InitSha256(&sha); + if (ret != 0) + return -20; + ret = wc_InitSha256(&partialSha); + if (ret != 0) + return -21; + ret = wc_Sha256Update(&partialSha, (byte*)a.input, 1); + if (ret != 0) + return -22; + wc_Sha256RestorePos(&sha, &partialSha); + ret = wc_Sha256GetHash(&partialSha, hash); + if (ret != 0) + return -23; + ret = wc_Sha256Update(&partialSha, (byte*)a.input + 1, (word32)a.inLen - 1); + if (ret != 0) + return -24; + ret = wc_Sha256Update(&sha, (byte*)a.input + 1, (word32)a.inLen - 1); + if (ret != 0) + return -25; + ret = wc_Sha256Final(&partialSha, hash); + if (ret != 0) + return -26; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -27; + XMEMSET(hash, 0, a.outLen); + ret = wc_Sha256Final(&sha, hash); + if (ret != 0) + return -28; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -29; + XMEMSET(hash, 0, a.outLen); + ret = wc_Sha256Hash((byte*)a.input, (word32)a.inLen, hash); + if (ret != 0) + return -30; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -31; + return 0; } #endif @@ -1329,6 +1712,30 @@ int sha512_test(void) return -10 - i; } + /* Getting the hash doesn't invalidate state. */ + ret = wc_InitSha512(&sha); + if (ret != 0) + return -20; + ret = wc_Sha512Update(&sha, (byte*)a.input, 1); + if (ret != 0) + return -21; + ret = wc_Sha512GetHash(&sha, hash); + if (ret != 0) + return -22; + ret = wc_Sha512Update(&sha, (byte*)a.input + 1, (word32)a.inLen - 1); + if (ret != 0) + return -23; + ret = wc_Sha512Final(&sha, hash); + if (ret != 0) + return -24; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -15; + ret = wc_Sha512Hash((byte*)a.input, (word32)a.inLen, hash); + if (ret != 0) + return -26; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -27; + return 0; } #endif @@ -1382,10 +1789,196 @@ int sha384_test(void) return -10 - i; } + /* Getting the hash doesn't invalidate state. */ + ret = wc_InitSha384(&sha); + if (ret != 0) + return -20; + ret = wc_Sha384Update(&sha, (byte*)a.input, 1); + if (ret != 0) + return -21; + ret = wc_Sha384GetHash(&sha, hash); + if (ret != 0) + return -22; + ret = wc_Sha384Update(&sha, (byte*)a.input + 1, a.inLen - 1); + if (ret != 0) + return -23; + ret = wc_Sha384Final(&sha, hash); + if (ret != 0) + return -24; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -25; + XMEMSET(hash, 0, a.outLen); + ret = wc_Sha384Hash((byte*)a.input, a.inLen, hash); + if (ret != 0) + return -26; + if (XMEMCMP(hash, a.output, a.outLen) != 0) + return -27; + return 0; } #endif /* WOLFSSL_SHA384 */ +int hash_test(void) +{ + wc_HashAlg hash; + int ret, exp_ret; + int i, j; + byte data[] = "0123456789abcdef0123456789abcdef012345"; + byte out[MAX_DIGEST_SIZE]; + enum wc_HashType typesGood[] = { WC_HASH_TYPE_MD5, WC_HASH_TYPE_SHA, + WC_HASH_TYPE_SHA224, WC_HASH_TYPE_SHA384, + WC_HASH_TYPE_SHA512, WC_HASH_TYPE_SHA256 }; + enum wc_HashType typesNoImpl[] = { +#ifdef NO_MD5 + WC_HASH_TYPE_MD5, +#endif +#ifdef NO_SHA + WC_HASH_TYPE_SHA, +#endif +#ifndef WOLFSSL_SHA224 + WC_HASH_TYPE_SHA224, +#endif +#ifdef NO_SHA256 + WC_HASH_TYPE_SHA256, +#endif +#ifndef WOLFSSL_SHA384 + WC_HASH_TYPE_SHA384, +#endif +#ifndef WOLFSSL_SHA512 + WC_HASH_TYPE_SHA512, +#endif + WC_HASH_TYPE_NONE + }; + enum wc_HashType typesBad[] = { WC_HASH_TYPE_NONE, WC_HASH_TYPE_MD5_SHA, + WC_HASH_TYPE_MD2, WC_HASH_TYPE_MD4 }; + + /* Parameter Validation testing. */ + ret = wc_HashInit(NULL, WC_HASH_TYPE_SHA256); + if (ret != BAD_FUNC_ARG) + return -4100; + ret = wc_HashUpdate(NULL, WC_HASH_TYPE_SHA256, NULL, sizeof(data)); + if (ret != BAD_FUNC_ARG) + return -4101; + ret = wc_HashUpdate(&hash, WC_HASH_TYPE_SHA256, NULL, sizeof(data)); + if (ret != BAD_FUNC_ARG) + return -4102; + ret = wc_HashUpdate(NULL, WC_HASH_TYPE_SHA256, data, sizeof(data)); + if (ret != BAD_FUNC_ARG) + return -4103; + ret = wc_HashFinal(NULL, WC_HASH_TYPE_SHA256, NULL); + if (ret != BAD_FUNC_ARG) + return -4104; + ret = wc_HashFinal(&hash, WC_HASH_TYPE_SHA256, NULL); + if (ret != BAD_FUNC_ARG) + return -4105; + ret = wc_HashFinal(NULL, WC_HASH_TYPE_SHA256, out); + if (ret != BAD_FUNC_ARG) + return -4106; + + /* Try invalid hash algorithms. */ + for (i = 0; i < (int)(sizeof(typesBad)/sizeof(*typesBad)); i++) { + ret = wc_HashInit(&hash, typesBad[i]); + if (ret != BAD_FUNC_ARG) + return -4110 - i; + ret = wc_HashUpdate(&hash, typesBad[i], data, sizeof(data)); + if (ret != BAD_FUNC_ARG) + return -4120 - i; + ret = wc_HashFinal(&hash, typesBad[i], data); + if (ret != BAD_FUNC_ARG) + return -4130 - i; + } + + /* Try valid hash algorithms. */ + for (i = 0, j = 0; i < (int)(sizeof(typesGood)/sizeof(*typesGood)); i++) { + exp_ret = 0; + if (typesGood[i] == typesNoImpl[j]) { + /* Recognized but no implementation compiled in. */ + exp_ret = HASH_TYPE_E; + j++; + } + ret = wc_HashInit(&hash, typesGood[i]); + if (ret != exp_ret) + return -4140 - i; + ret = wc_HashUpdate(&hash, typesGood[i], data, sizeof(data)); + if (ret != exp_ret) + return -4150 - i; + ret = wc_HashFinal(&hash, typesGood[i], data); + if (ret != exp_ret) + return -4160 - i; + ret = wc_HashGetOID(typesGood[i]); + if (ret == BAD_FUNC_ARG || + (exp_ret == 0 && ret == HASH_TYPE_E) || + (exp_ret != 0 && ret != HASH_TYPE_E)) { + return -4170 - i; + } + } + + ret = wc_HashGetOID(WC_HASH_TYPE_MD2); +#ifdef WOLFSSL_MD2 + if (ret == HASH_TYPE_E || ret == BAD_FUNC_ARG) + return -4180; +#else + if (ret != HASH_TYPE_E) + return -4180; +#endif + ret = wc_HashGetOID(WC_HASH_TYPE_MD5_SHA); +#ifndef NO_MD5 + if (ret == HASH_TYPE_E || ret == BAD_FUNC_ARG) + return -4181; +#else + if (ret != HASH_TYPE_E) + return -4181; +#endif + ret = wc_HashGetOID(WC_HASH_TYPE_MD4); + if (ret != BAD_FUNC_ARG) + return -4182; + ret = wc_HashGetOID(WC_HASH_TYPE_NONE); + if (ret != BAD_FUNC_ARG) + return -4183; + +#ifndef NO_ASN +#ifdef WOLFSSL_MD2 + ret = wc_GetCTC_HashOID(MD2); + if (ret == 0) + return -4190; +#endif +#ifndef NO_MD5 + ret = wc_GetCTC_HashOID(MD5); + if (ret == 0) + return -4191; +#endif +#ifndef NO_SHA + ret = wc_GetCTC_HashOID(SHA); + if (ret == 0) + return -4192; +#endif +#ifdef WOLFSSL_SHA224 + ret = wc_GetCTC_HashOID(SHA224); + if (ret == 0) + return -4193; +#endif +#ifndef NO_SHA256 + ret = wc_GetCTC_HashOID(SHA256); + if (ret == 0) + return -4194; +#endif +#ifdef WOLFSSL_SHA384 + ret = wc_GetCTC_HashOID(SHA384); + if (ret == 0) + return -4195; +#endif +#ifdef WOLFSSL_SHA512 + ret = wc_GetCTC_HashOID(SHA512); + if (ret == 0) + return -4196; +#endif + ret = wc_GetCTC_HashOID(-1); + if (ret != 0) + return -4197; +#endif + + return 0; +} #if !defined(NO_HMAC) && !defined(NO_MD5) int hmac_md5_test(void) @@ -1463,6 +2056,11 @@ int hmac_md5_test(void) #endif } +#ifndef HAVE_FIPS + if (wc_HmacSizeByType(MD5) != MD5_DIGEST_SIZE) + return -4018; +#endif + return 0; } #endif /* NO_HMAC && NO_MD5 */ @@ -1540,6 +2138,11 @@ int hmac_sha_test(void) #endif } +#ifndef HAVE_FIPS + if (wc_HmacSizeByType(SHA) != SHA_DIGEST_SIZE) + return -4021; +#endif + return 0; } #endif @@ -1618,6 +2221,11 @@ int hmac_sha224_test(void) #endif } +#ifndef HAVE_FIPS + if (wc_HmacSizeByType(SHA224) != SHA224_DIGEST_SIZE) + return -4024; +#endif + return 0; } #endif @@ -1699,6 +2307,15 @@ int hmac_sha256_test(void) #endif } +#ifndef HAVE_FIPS + if (wc_HmacSizeByType(SHA256) != SHA256_DIGEST_SIZE) + return -4024; + if (wc_HmacSizeByType(20) != BAD_FUNC_ARG) + return -4025; +#endif + if (wolfSSL_GetHmacMaxSize() != MAX_DIGEST_SIZE) + return -4026; + return 0; } #endif @@ -1785,6 +2402,11 @@ int hmac_blake2b_test(void) #endif } +#ifndef HAVE_FIPS + if (wc_HmacSizeByType(BLAKE2B_ID) != BLAKE2B_OUTBYTES) + return -4027; +#endif + return 0; } #endif @@ -1862,6 +2484,11 @@ int hmac_sha384_test(void) return -20 - i; } +#ifndef HAVE_FIPS + if (wc_HmacSizeByType(SHA384) != SHA384_DIGEST_SIZE) + return -4030; +#endif + return 0; } #endif @@ -1942,6 +2569,11 @@ int hmac_sha512_test(void) return -20 - i; } +#ifndef HAVE_FIPS + if (wc_HmacSizeByType(SHA512) != SHA512_DIGEST_SIZE) + return -4033; +#endif + return 0; } #endif @@ -2653,6 +3285,59 @@ int chacha20_poly1305_aead_test(void) XMEMSET(generatedAuthTag, 0, sizeof(generatedAuthTag)); XMEMSET(generatedPlaintext, 0, sizeof(generatedPlaintext)); + /* Parameter Validation testing */ + /* Encrypt */ + err = wc_ChaCha20Poly1305_Encrypt(NULL, iv1, aad1, sizeof(aad1), plaintext1, + sizeof(plaintext1), generatedCiphertext, generatedAuthTag); + if (err != BAD_FUNC_ARG) + return -1050; + err = wc_ChaCha20Poly1305_Encrypt(key1, NULL, aad1, sizeof(aad1), + plaintext1, sizeof(plaintext1), generatedCiphertext, + generatedAuthTag); + if (err != BAD_FUNC_ARG) + return -1051; + err = wc_ChaCha20Poly1305_Encrypt(key1, iv1, aad1, sizeof(aad1), NULL, + sizeof(plaintext1), generatedCiphertext, generatedAuthTag); + if (err != BAD_FUNC_ARG) + return -1052; + err = wc_ChaCha20Poly1305_Encrypt(key1, iv1, aad1, sizeof(aad1), plaintext1, + sizeof(plaintext1), NULL, generatedAuthTag); + if (err != BAD_FUNC_ARG) + return -1053; + err = wc_ChaCha20Poly1305_Encrypt(key1, iv1, aad1, sizeof(aad1), plaintext1, + sizeof(plaintext1), generatedCiphertext, NULL); + if (err != BAD_FUNC_ARG) + return -1054; + err = wc_ChaCha20Poly1305_Encrypt(key1, iv1, aad1, sizeof(aad1), plaintext1, + 0, generatedCiphertext, generatedAuthTag); + if (err != BAD_FUNC_ARG) + return -1055; + /* Decrypt */ + err = wc_ChaCha20Poly1305_Decrypt(NULL, iv2, aad2, sizeof(aad2), cipher2, + sizeof(cipher2), authTag2, generatedPlaintext); + if (err != BAD_FUNC_ARG) + return -1056; + err = wc_ChaCha20Poly1305_Decrypt(key2, NULL, aad2, sizeof(aad2), cipher2, + sizeof(cipher2), authTag2, generatedPlaintext); + if (err != BAD_FUNC_ARG) + return -1057; + err = wc_ChaCha20Poly1305_Decrypt(key2, iv2, aad2, sizeof(aad2), NULL, + sizeof(cipher2), authTag2, generatedPlaintext); + if (err != BAD_FUNC_ARG) + return -1058; + err = wc_ChaCha20Poly1305_Decrypt(key2, iv2, aad2, sizeof(aad2), cipher2, + sizeof(cipher2), NULL, generatedPlaintext); + if (err != BAD_FUNC_ARG) + return -1059; + err = wc_ChaCha20Poly1305_Decrypt(key2, iv2, aad2, sizeof(aad2), cipher2, + sizeof(cipher2), authTag2, NULL); + if (err != BAD_FUNC_ARG) + return -1060; + err = wc_ChaCha20Poly1305_Decrypt(key2, iv2, aad2, sizeof(aad2), cipher2, + 0, authTag2, generatedPlaintext); + if (err != BAD_FUNC_ARG) + return -1061; + /* Test #1 */ err = wc_ChaCha20Poly1305_Encrypt(key1, iv1, @@ -2875,6 +3560,132 @@ int des3_test(void) #ifndef NO_AES +static int aes_key_size_test(void) +{ + int ret; + Aes aes; + byte key16[] = { 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, + 0x38, 0x39, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66 }; + byte key24[] = { 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, + 0x38, 0x39, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37 }; + byte key32[] = { 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, + 0x38, 0x39, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, + 0x38, 0x39, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66 }; + byte iv[] = "1234567890abcdef"; +#ifndef HAVE_FIPS + word32 keySize; +#endif + +#ifdef WC_INITAES_H + ret = wc_InitAes_h(NULL, NULL); + if (ret != BAD_FUNC_ARG) + return -1100; + ret = wc_InitAes_h(&aes, NULL); + if (ret != 0) + return -1100; +#endif + +#ifndef HAVE_FIPS + /* Parameter Validation testing. */ + ret = wc_AesGetKeySize(NULL, NULL); + if (ret != BAD_FUNC_ARG) + return -1100; + ret = wc_AesGetKeySize(&aes, NULL); + if (ret != BAD_FUNC_ARG) + return -1101; + ret = wc_AesGetKeySize(NULL, &keySize); + if (ret != BAD_FUNC_ARG) + return -1102; + /* Crashes in FIPS */ + ret = wc_AesSetKey(NULL, key16, sizeof(key16), iv, AES_ENCRYPTION); + if (ret != BAD_FUNC_ARG) + return -1103; +#endif + /* NULL IV indicates to use all zeros IV. */ + ret = wc_AesSetKey(&aes, key16, sizeof(key16), NULL, AES_ENCRYPTION); + if (ret != 0) + return -1104; + ret = wc_AesSetKey(&aes, key32, sizeof(key32) - 1, iv, AES_ENCRYPTION); + if (ret != BAD_FUNC_ARG) + return -1111; +#ifndef HAVE_FIPS + /* Force invalid rounds */ + aes.rounds = 16; + ret = wc_AesGetKeySize(&aes, &keySize); + if (ret != BAD_FUNC_ARG) + return -1112; +#endif + + ret = wc_AesSetKey(&aes, key16, sizeof(key16), iv, AES_ENCRYPTION); + if (ret != 0) + return -1105; +#ifndef HAVE_FIPS + ret = wc_AesGetKeySize(&aes, &keySize); + if (ret != 0 || keySize != sizeof(key16)) + return -1106; +#endif + + ret = wc_AesSetKey(&aes, key24, sizeof(key24), iv, AES_ENCRYPTION); + if (ret != 0) + return -1107; +#ifndef HAVE_FIPS + ret = wc_AesGetKeySize(&aes, &keySize); + if (ret != 0 || keySize != sizeof(key24)) + return -1108; +#endif + + ret = wc_AesSetKey(&aes, key32, sizeof(key32), iv, AES_ENCRYPTION); + if (ret != 0) + return -1109; +#ifndef HAVE_FIPS + ret = wc_AesGetKeySize(&aes, &keySize); + if (ret != 0 || keySize != sizeof(key32)) + return -1110; +#endif + + return 0; +} + +#if defined(HAVE_AES_CBC) +static int aes_cbc_test(void) +{ + byte cipher[AES_BLOCK_SIZE]; + byte plain[AES_BLOCK_SIZE]; + int ret; + 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, + 0x66,0x6f,0x72,0x20,0x61,0x6c,0x6c,0x20 + }; + byte key[] = "0123456789abcdef "; /* align */ + byte iv[] = "1234567890abcdef "; /* align */ + + /* Parameter Validation testing. */ + ret = wc_AesCbcEncryptWithKey(cipher, msg, AES_BLOCK_SIZE, key, 17, NULL); + if (ret != BAD_FUNC_ARG) + return -1120; + ret = wc_AesCbcDecryptWithKey(plain, cipher, AES_BLOCK_SIZE, key, 17, NULL); + if (ret != BAD_FUNC_ARG) + return -1121; + + ret = wc_AesCbcEncryptWithKey(cipher, msg, AES_BLOCK_SIZE, key, + AES_BLOCK_SIZE, iv); + if (ret != 0) + return -1130; + ret = wc_AesCbcDecryptWithKey(plain, cipher, AES_BLOCK_SIZE, key, + AES_BLOCK_SIZE, iv); + if (ret != 0) + return -1131; + + if (XMEMCMP(plain, msg, AES_BLOCK_SIZE) != 0) + return -1132; + + return 0; +} +#endif + int aes_test(void) { #if defined(HAVE_AES_CBC) || defined(WOLFSSL_AES_COUNTER) @@ -3231,6 +4042,16 @@ int aes_test(void) } #endif /* WOLFSSL_AES_DIRECT */ + ret = aes_key_size_test(); + if (ret != 0) + return ret; + +#if defined(HAVE_AES_CBC) + ret = aes_cbc_test(); + if (ret != 0) + return ret; +#endif + return ret; } @@ -4228,7 +5049,12 @@ static int random_rng_test(void) ret = -38; goto exit; } - ret = 0; + + ret = wc_RNG_GenerateByte(&rng, block); + if (ret != 0) { + ret = -41; + goto exit; + } exit: /* Make sure and free RNG */ @@ -4544,6 +5370,65 @@ byte GetEntropy(ENTROPY_CMD cmd, byte* out) #endif #endif +#if !defined(NO_ASN_TIME) && defined(WOLFSSL_TEST_CERT) +int cert_test(void) +{ + DecodedCert cert; + byte* tmp; + size_t bytes; + FILE *file; + int ret; + + tmp = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); + if (tmp == NULL) + return -200; + + /* Certificate with Name Constraints extension. */ +#ifdef FREESCALE_MQX + file = fopen(".\\certs\\test\\cert-ext-nc.der", "rb"); +#else + file = fopen("./certs/test/cert-ext-nc.der", "rb"); +#endif + if (!file) { + ret = -201; + goto done; + } + bytes = fread(tmp, 1, FOURK_BUF, file); + fclose(file); + InitDecodedCert(&cert, tmp, (word32)bytes, 0); + ret = ParseCert(&cert, CERT_TYPE, NO_VERIFY, NULL); + if (ret != 0) { + ret = -202; + goto done; + } + FreeDecodedCert(&cert); + + /* Certificate with Inhibit Any Policy extension. */ +#ifdef FREESCALE_MQX + file = fopen(".\\certs\\test\\cert-ext-ia.der", "rb"); +#else + file = fopen("./certs/test/cert-ext-ia.der", "rb"); +#endif + if (!file) { + ret = -201; + goto done; + } + bytes = fread(tmp, 1, FOURK_BUF, file); + fclose(file); + InitDecodedCert(&cert, tmp, (word32)bytes, 0); + ret = ParseCert(&cert, CERT_TYPE, NO_VERIFY, NULL); + if (ret != 0) { + ret = -204; + goto done; + } + +done: + FreeDecodedCert(&cert); + XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); + + return ret; +} +#endif #if defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_TEST_CERT) int certext_test(void) @@ -4739,6 +5624,447 @@ int certext_test(void) } #endif /* WOLFSSL_CERT_EXT && WOLFSSL_TEST_CERT */ +static int rsa_flatten_test(RsaKey* key) +{ + int ret; + byte e[256]; + byte n[256]; + word32 eSz = sizeof(e); + word32 nSz = sizeof(n); + + /* Parameter Validation testing. */ + ret = wc_RsaFlattenPublicKey(NULL, e, &eSz, n, &nSz); +#ifdef HAVE_USER_RSA + /* Implementation using IPP Libraries returns: + * -101 = USER_CRYPTO_ERROR + */ + if (ret == 0) +#else + if (ret != BAD_FUNC_ARG) +#endif + return -480; + ret = wc_RsaFlattenPublicKey(key, NULL, &eSz, n, &nSz); +#ifdef HAVE_USER_RSA + /* Implementation using IPP Libraries returns: + * -101 = USER_CRYPTO_ERROR + */ + if (ret == 0) +#else + if (ret != BAD_FUNC_ARG) +#endif + return -481; + ret = wc_RsaFlattenPublicKey(key, e, NULL, n, &nSz); +#ifdef HAVE_USER_RSA + /* Implementation using IPP Libraries returns: + * -101 = USER_CRYPTO_ERROR + */ + if (ret == 0) +#else + if (ret != BAD_FUNC_ARG) +#endif + return -482; + ret = wc_RsaFlattenPublicKey(key, e, &eSz, NULL, &nSz); +#ifdef HAVE_USER_RSA + /* Implementation using IPP Libraries returns: + * -101 = USER_CRYPTO_ERROR + */ + if (ret == 0) +#else + if (ret != BAD_FUNC_ARG) +#endif + return -483; + ret = wc_RsaFlattenPublicKey(key, e, &eSz, n, NULL); +#ifdef HAVE_USER_RSA + /* Implementation using IPP Libraries returns: + * -101 = USER_CRYPTO_ERROR + */ + if (ret == 0) +#else + if (ret != BAD_FUNC_ARG) +#endif + return -484; + ret = wc_RsaFlattenPublicKey(key, e, &eSz, n, &nSz); + if (ret != 0) + return -485; + eSz = 0; + ret = wc_RsaFlattenPublicKey(key, e, &eSz, n, &nSz); +#ifdef HAVE_USER_RSA + /* Implementation using IPP Libraries returns: + * -101 = USER_CRYPTO_ERROR + */ + if (ret == 0) +#elif defined(HAVE_FIPS) + if (ret != 0) +#else + if (ret != RSA_BUFFER_E) +#endif + return -486; + eSz = sizeof(e); + nSz = 0; + ret = wc_RsaFlattenPublicKey(key, e, &eSz, n, &nSz); +#ifdef HAVE_USER_RSA + /* Implementation using IPP Libraries returns: + * -101 = USER_CRYPTO_ERROR + */ + if (ret == 0) +#else + if (ret != RSA_BUFFER_E) +#endif + return -487; + + return 0; +} + +static int rsa_sig_test(RsaKey* key, word32 keyLen, int modLen, WC_RNG* rng) +{ + int ret; + word32 sigSz; + byte in[] = "Everyone gets Friday off."; + word32 inLen = (word32)XSTRLEN((char*)in); + byte out[256]; + + /* Parameter Validation testing. */ + ret = wc_SignatureGetSize(WC_SIGNATURE_TYPE_NONE, key, keyLen); + if (ret != BAD_FUNC_ARG) + return -490; + ret = wc_SignatureGetSize(WC_SIGNATURE_TYPE_RSA, key, 0); + if (ret != BAD_FUNC_ARG) + return -491; + + sigSz = modLen; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, NULL, + inLen, out, &sigSz, key, keyLen, rng); + if (ret != BAD_FUNC_ARG) + return -492; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + 0, out, &sigSz, key, keyLen, rng); + if (ret != BAD_FUNC_ARG) + return -493; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, NULL, &sigSz, key, keyLen, rng); + if (ret != BAD_FUNC_ARG) + return -494; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, NULL, key, keyLen, rng); + if (ret != BAD_FUNC_ARG) + return -495; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, &sigSz, NULL, keyLen, rng); + if (ret != BAD_FUNC_ARG) + return -496; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, &sigSz, key, 0, rng); + if (ret != BAD_FUNC_ARG) + return -497; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, &sigSz, key, keyLen, NULL); +#ifdef HAVE_USER_RSA + /* Implementation using IPP Libraries returns: + * -101 = USER_CRYPTO_ERROR + */ + if (ret == 0) +#elif defined(HAVE_FIPS) + /* FIPS140 implementation doesn't do blinding. */ + if (ret != 0) +#else + if (ret != MISSING_RNG_E) +#endif + return -498; + sigSz = 0; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, &sigSz, key, keyLen, rng); + if (ret != BAD_FUNC_ARG) + return -499; + + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, NULL, + inLen, out, modLen, key, keyLen); + if (ret != BAD_FUNC_ARG) + return -500; + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + 0, out, modLen, key, keyLen); + if (ret != BAD_FUNC_ARG) + return -501; + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, NULL, modLen, key, keyLen); + if (ret != BAD_FUNC_ARG) + return -502; + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, 0, key, keyLen); + if (ret != BAD_FUNC_ARG) + return -503; + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, modLen, NULL, keyLen); + if (ret != BAD_FUNC_ARG) + return -504; + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, modLen, key, 0); + if (ret != BAD_FUNC_ARG) + return -505; + +#ifndef HAVE_ECC + ret = wc_SignatureGetSize(WC_SIGNATURE_TYPE_ECC, key, keyLen); + if (ret != SIG_TYPE_E) + return -506; +#endif + + /* Use APIs. */ + ret = wc_SignatureGetSize(WC_SIGNATURE_TYPE_RSA, key, keyLen); + if (ret != modLen) + return -507; + ret = wc_SignatureGetSize(WC_SIGNATURE_TYPE_RSA_W_ENC, key, keyLen); + if (ret != modLen) + return -508; + + sigSz = ret; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, &sigSz, key, keyLen, rng); + if (ret != 0) + return -509; + + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, modLen, key, keyLen); + if (ret != 0) + return -510; + + sigSz = sizeof(out); + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA_W_ENC, + in, inLen, out, &sigSz, key, keyLen, rng); + if (ret != 0) + return -511; + + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA_W_ENC, + in, inLen, out, modLen, key, keyLen); + if (ret != 0) + return -512; + + /* Wrong signature type. */ + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_RSA, in, + inLen, out, modLen, key, keyLen); + if (ret == 0) + return -513; + + return 0; +} + +#ifndef HAVE_USER_RSA +static int rsa_decode_test(void) +{ + int ret; + word32 inSz; + word32 inOutIdx; + RsaKey keyPub; + const byte n[2] = { 0x00, 0x23 }; + const byte e[2] = { 0x00, 0x03 }; + const byte good[] = { 0x30, 0x06, 0x02, 0x01, 0x23, 0x02, 0x1, 0x03 }; + const byte goodAlgId[] = { 0x30, 0x0f, 0x30, 0x0d, 0x06, 0x00, + 0x03, 0x09, 0x00, 0x30, 0x06, 0x02, 0x01, 0x23, 0x02, 0x1, 0x03 }; + const byte goodBitStrNoZero[] = { 0x30, 0x0e, 0x30, 0x0c, 0x06, 0x00, + 0x03, 0x08, 0x30, 0x06, 0x02, 0x01, 0x23, 0x02, 0x1, 0x03 }; + const byte goodAlgIdNull[] = { 0x30, 0x11, 0x30, 0x0f, 0x06, 0x00, + 0x05, 0x00, 0x03, 0x09, 0x00, 0x30, 0x06, 0x02, 0x01, 0x23, + 0x02, 0x1, 0x03 }; + const byte badAlgIdNull[] = { 0x30, 0x12, 0x30, 0x10, 0x06, 0x00, + 0x05, 0x01, 0x00, 0x03, 0x09, 0x00, 0x30, 0x06, 0x02, 0x01, 0x23, + 0x02, 0x1, 0x03 }; + const byte badNotBitString[] = { 0x30, 0x0f, 0x30, 0x0d, 0x06, 0x00, + 0x04, 0x09, 0x00, 0x30, 0x06, 0x02, 0x01, 0x23, 0x02, 0x1, 0x03 }; + const byte badBitStringLen[] = { 0x30, 0x0f, 0x30, 0x0d, 0x06, 0x00, + 0x03, 0x0a, 0x00, 0x30, 0x06, 0x02, 0x01, 0x23, 0x02, 0x1, 0x03 }; + const byte badNoSeq[] = { 0x30, 0x0d, 0x30, 0x0b, 0x06, 0x00, 0x03, 0x07, + 0x00, 0x02, 0x01, 0x23, 0x02, 0x1, 0x03 }; + const byte badNoObj[] = { + 0x30, 0x0f, 0x30, 0x0d, 0x05, 0x00, 0x03, 0x09, 0x00, 0x30, 0x06, + 0x02, 0x01, 0x23, 0x02, 0x1, 0x03 }; + const byte badIntN[] = { 0x30, 0x06, 0x02, 0x05, 0x23, 0x02, 0x1, 0x03 }; + const byte badNotIntE[] = { 0x30, 0x06, 0x02, 0x01, 0x23, 0x04, 0x1, 0x03 }; + const byte badLength[] = { 0x30, 0x04, 0x02, 0x01, 0x23, 0x02, 0x1, 0x03 }; + + ret = wc_InitRsaKey(&keyPub, NULL); + if (ret != 0) + return -520; + + /* Parameter Validation testing. */ + ret = wc_RsaPublicKeyDecodeRaw(NULL, sizeof(n), e, sizeof(e), &keyPub); + if (ret != BAD_FUNC_ARG) { + ret = -521; + goto done; + } + ret = wc_RsaPublicKeyDecodeRaw(n, sizeof(n), NULL, sizeof(e), &keyPub); + if (ret != BAD_FUNC_ARG) { + ret = -522; + goto done; + } + ret = wc_RsaPublicKeyDecodeRaw(n, sizeof(n), e, sizeof(e), NULL); + if (ret != BAD_FUNC_ARG) { + ret = -523; + goto done; + } + /* TODO: probably should fail when length is -1! */ + ret = wc_RsaPublicKeyDecodeRaw(n, -1, e, sizeof(e), &keyPub); + if (ret != 0) { + ret = -525; + goto done; + } + ret = wc_RsaPublicKeyDecodeRaw(n, sizeof(n), e, -1, &keyPub); + if (ret != 0) { + ret = -526; + goto done; + } + + /* Use API. */ + ret = wc_RsaPublicKeyDecodeRaw(n, sizeof(n), e, sizeof(e), &keyPub); + if (ret != 0) { + ret = -527; + goto done; + } + + /* Parameter Validation testing. */ + inSz = sizeof(good); + ret = wc_RsaPublicKeyDecode(NULL, &inOutIdx, &keyPub, inSz); + if (ret != BAD_FUNC_ARG) { + ret = -531; + goto done; + } + ret = wc_RsaPublicKeyDecode(good, NULL, &keyPub, inSz); + if (ret != BAD_FUNC_ARG) { + ret = -532; + goto done; + } + ret = wc_RsaPublicKeyDecode(good, &inOutIdx, NULL, inSz); + if (ret != BAD_FUNC_ARG) { + ret = -533; + goto done; + } + + /* Use good data and offest to bad data. */ + inOutIdx = 2; + inSz = sizeof(good) - inOutIdx; + ret = wc_RsaPublicKeyDecode(good, &inOutIdx, &keyPub, inSz); + if (ret != ASN_PARSE_E) { + ret = -540; + goto done; + } + inOutIdx = 2; + inSz = sizeof(goodAlgId) - inOutIdx; + ret = wc_RsaPublicKeyDecode(goodAlgId, &inOutIdx, &keyPub, inSz); + if (ret != ASN_PARSE_E) { + ret = -541; + goto done; + } + /* Try different bad data. */ + inSz = sizeof(badAlgIdNull); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(badAlgIdNull, &inOutIdx, &keyPub, inSz); + if (ret != ASN_EXPECT_0_E) { + ret = -542; + goto done; + } + inSz = sizeof(badNotBitString); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(badNotBitString, &inOutIdx, &keyPub, inSz); + if (ret != ASN_BITSTR_E) { + ret = -543; + goto done; + } + inSz = sizeof(badBitStringLen); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(badBitStringLen, &inOutIdx, &keyPub, inSz); + if (ret != ASN_PARSE_E) { + ret = -544; + goto done; + } + inSz = sizeof(badNoSeq); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(badNoSeq, &inOutIdx, &keyPub, inSz); + if (ret != ASN_PARSE_E) { + ret = -545; + goto done; + } + inSz = sizeof(badNoObj); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(badNoObj, &inOutIdx, &keyPub, inSz); + if (ret != ASN_PARSE_E) { + ret = -546; + goto done; + } + inSz = sizeof(badIntN); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(badIntN, &inOutIdx, &keyPub, inSz); + if (ret != ASN_RSA_KEY_E) { + ret = -547; + goto done; + } + inSz = sizeof(badNotIntE); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(badNotIntE, &inOutIdx, &keyPub, inSz); + if (ret != ASN_RSA_KEY_E) { + ret = -548; + goto done; + } + /* TODO: Shouldn't pass as the sequence length is too small. */ + inSz = sizeof(badLength); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(badLength, &inOutIdx, &keyPub, inSz); + if (ret != 0) { + ret = -549; + goto done; + } + /* TODO: Shouldn't ignore object id's data. */ + + /* Valid data cases. */ + inSz = sizeof(good); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(good, &inOutIdx, &keyPub, inSz); + if (ret != 0) { + ret = -550; + goto done; + } + if (inOutIdx != inSz) { + ret = -551; + goto done; + } + + inSz = sizeof(goodAlgId); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(goodAlgId, &inOutIdx, &keyPub, inSz); + if (ret != 0) { + ret = -552; + goto done; + } + if (inOutIdx != inSz) { + ret = -553; + goto done; + } + + inSz = sizeof(goodAlgIdNull); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(goodAlgIdNull, &inOutIdx, &keyPub, inSz); + if (ret != 0) { + ret = -554; + goto done; + } + if (inOutIdx != inSz) { + ret = -555; + goto done; + } + + inSz = sizeof(goodBitStrNoZero); + inOutIdx = 0; + ret = wc_RsaPublicKeyDecode(goodBitStrNoZero, &inOutIdx, &keyPub, inSz); + if (ret != 0) { + ret = -556; + goto done; + } + if (inOutIdx != inSz) { + ret = -557; + goto done; + } + +done: + wc_FreeRsaKey(&keyPub); + return ret; +} +#endif int rsa_test(void) { @@ -4755,6 +6081,7 @@ int rsa_test(void) word32 inLen = (word32)XSTRLEN((char*)in); byte out[256]; byte plain[256]; + byte* res; #if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) FILE *file, *file2; #endif @@ -4762,6 +6089,12 @@ int rsa_test(void) DecodedCert cert; #endif +#ifndef HAVE_USER_RSA + ret = rsa_decode_test(); + if (ret != 0) + return ret; +#endif + tmp = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); if (tmp == NULL) return -40; @@ -4802,6 +6135,10 @@ int rsa_test(void) return -42; } + ret = rsa_sig_test(&key, sizeof(RsaKey), wc_RsaEncryptSize(&key), &rng); + if (ret != 0) + return ret; + do { #if defined(WOLFSSL_ASYNC_CRYPT) ret = wc_RsaAsyncWait(ret, &key); @@ -4849,6 +6186,20 @@ int rsa_test(void) wc_FreeRng(&rng); return -45; } + do { +#if defined(WOLFSSL_ASYNC_CRYPT) + ret = wc_RsaAsyncWait(ret, key); +#endif + if (ret >= 0) { + ret = wc_RsaPrivateDecryptInline(out, idx, &res, &key); + } + } while (ret == WC_PENDING_E); + if (ret < 0) + return -473; + if (ret != (int)inLen) + return -473; + if (XMEMCMP(res, in, inLen)) + return -474; do { #if defined(WOLFSSL_ASYNC_CRYPT) @@ -4970,6 +6321,22 @@ int rsa_test(void) return -245; } + do { +#if defined(WOLFSSL_ASYNC_CRYPT) + ret = wc_RsaAsyncWait(ret, key); +#endif + if (ret >= 0) { + ret = wc_RsaPrivateDecryptInline_ex(out, idx, &res, &key, + WC_RSA_OAEP_PAD, WC_HASH_TYPE_SHA256, WC_MGF1SHA256, NULL, 0); + } + } while (ret == WC_PENDING_E); + if (ret < 0) + return -473; + if (ret != (int)inLen) + return -474; + if (XMEMCMP(res, in, inLen)) + return -475; + /* check fails if not using the same optional label */ XMEMSET(plain, 0, sizeof(plain)); do { @@ -5155,18 +6522,22 @@ int rsa_test(void) } while (ret == WC_PENDING_E); if (ret < 0) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -444; } if (XMEMCMP(plain, in, inLen)) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -445; } #endif /* !HAVE_FAST_RSA && !HAVE_FIPS */ #endif /* WC_NO_RSA_OAEP */ + ret = rsa_flatten_test(&key); + if (ret != 0) + return ret; + #if defined(WOLFSSL_MDK_ARM) #define sizeof(s) XSTRLEN((char *)(s)) #endif @@ -5181,7 +6552,7 @@ int rsa_test(void) file2 = fopen(clientCert, "rb"); if (!file2) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -49; } @@ -5223,7 +6594,7 @@ int rsa_test(void) err_sys("can't open ./certs/client-keyPub.der, " "Please run from wolfSSL home dir", -40); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -50; } @@ -5234,7 +6605,7 @@ int rsa_test(void) ret = wc_InitRsaKey(&keypub, HEAP_HINT); if (ret != 0) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -51; } idx = 0; @@ -5243,7 +6614,7 @@ int rsa_test(void) if (ret != 0) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&keypub); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -52; } #endif /* WOLFSSL_CERT_EXT */ @@ -5262,13 +6633,13 @@ int rsa_test(void) ret = wc_InitRsaKey(&genKey, HEAP_HINT); if (ret != 0) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -300; } ret = wc_MakeRsaKey(&genKey, 1024, 65537, &rng); if (ret != 0) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -301; } @@ -5276,7 +6647,7 @@ int rsa_test(void) if (der == NULL) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -307; } pem = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -5284,7 +6655,7 @@ int rsa_test(void) XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -308; } @@ -5293,7 +6664,7 @@ int rsa_test(void) XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -302; } @@ -5307,7 +6678,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -303; } ret = (int)fwrite(der, 1, derSz, keyFile); @@ -5317,7 +6688,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -313; } @@ -5327,7 +6698,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -304; } @@ -5341,7 +6712,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -305; } ret = (int)fwrite(pem, 1, pemSz, pemFile); @@ -5351,7 +6722,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -314; } @@ -5361,7 +6732,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -3060; } idx = 0; @@ -5372,7 +6743,7 @@ int rsa_test(void) XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&derIn); wc_FreeRsaKey(&genKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -306; } @@ -5401,14 +6772,14 @@ int rsa_test(void) DYNAMIC_TYPE_TMP_BUFFER); if (derCert == NULL) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -309; } pem = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT,DYNAMIC_TYPE_TMP_BUFFER); if (pem == NULL) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -310; } @@ -5437,7 +6808,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -398; } @@ -5446,7 +6817,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -399; } @@ -5455,7 +6826,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -400; } #endif /* WOLFSSL_CERT_EXT */ @@ -5465,7 +6836,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -401; } @@ -5476,7 +6847,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -402; } FreeDecodedCert(&decode); @@ -5491,7 +6862,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -403; } ret = (int)fwrite(derCert, 1, certSz, derFile); @@ -5500,7 +6871,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -414; } @@ -5509,7 +6880,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -404; } @@ -5522,7 +6893,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -405; } ret = (int)fwrite(pem, 1, pemSz, pemFile); @@ -5531,7 +6902,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -406; } XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -5558,14 +6929,14 @@ int rsa_test(void) DYNAMIC_TYPE_TMP_BUFFER); if (derCert == NULL) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -311; } pem = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT,DYNAMIC_TYPE_TMP_BUFFER); if (pem == NULL) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -312; } @@ -5575,7 +6946,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -412; } @@ -5587,7 +6958,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -411; } ret = wc_RsaPrivateKeyDecode(tmp, &idx3, &caKey, (word32)bytes3); @@ -5596,7 +6967,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -413; } @@ -5625,7 +6996,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -398; } @@ -5634,7 +7005,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -399; } @@ -5643,7 +7014,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -400; } #endif /* WOLFSSL_CERT_EXT */ @@ -5654,7 +7025,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -405; } @@ -5664,7 +7035,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -407; } @@ -5675,7 +7046,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -408; } @@ -5687,7 +7058,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -409; } FreeDecodedCert(&decode); @@ -5703,7 +7074,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -410; } ret = (int)fwrite(derCert, 1, certSz, derFile); @@ -5713,7 +7084,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -416; } @@ -5723,7 +7094,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -411; } @@ -5737,7 +7108,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -412; } ret = (int)fwrite(pem, 1, pemSz, pemFile); @@ -5747,7 +7118,7 @@ int rsa_test(void) XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); fclose(pemFile); wc_FreeRsaKey(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -415; } fclose(pemFile); @@ -5780,14 +7151,14 @@ int rsa_test(void) DYNAMIC_TYPE_TMP_BUFFER); if (derCert == NULL) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5311; } pem = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT,DYNAMIC_TYPE_TMP_BUFFER); if (pem == NULL) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5312; } @@ -5797,7 +7168,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5412; } @@ -5810,7 +7181,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5413; } @@ -5839,7 +7210,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5500; } @@ -5851,7 +7222,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5501; } @@ -5862,7 +7233,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKeyPub); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5502; } @@ -5872,7 +7243,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKeyPub); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5503; } @@ -5882,7 +7253,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKeyPub); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5504; } wc_ecc_free(&caKeyPub); @@ -5892,7 +7263,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5505; } #endif /* WOLFSSL_CERT_EXT */ @@ -5903,7 +7274,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5405; } @@ -5913,7 +7284,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5407; } @@ -5924,7 +7295,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5408; } @@ -5936,7 +7307,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5409; } FreeDecodedCert(&decode); @@ -5952,7 +7323,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5410; } ret = (int)fwrite(derCert, 1, certSz, derFile); @@ -5962,7 +7333,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5414; } @@ -5972,7 +7343,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5411; } @@ -5986,7 +7357,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5412; } ret = (int)fwrite(pem, 1, pemSz, pemFile); @@ -5995,7 +7366,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_ecc_free(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -5415; } @@ -6025,14 +7396,14 @@ int rsa_test(void) DYNAMIC_TYPE_TMP_BUFFER); if (derCert == NULL) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -311; } pem = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT,DYNAMIC_TYPE_TMP_BUFFER); if (pem == NULL) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -312; } @@ -6050,7 +7421,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -448; } @@ -6061,7 +7432,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -449; } @@ -6072,7 +7443,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -450; } @@ -6082,7 +7453,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -451; } @@ -6092,7 +7463,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -452; } @@ -6104,7 +7475,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -453; } ret = wc_RsaPrivateKeyDecode(tmp, &idx3, &caKey, (word32)bytes); @@ -6112,7 +7483,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -454; } @@ -6135,7 +7506,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -496; } @@ -6144,7 +7515,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -495; } @@ -6154,7 +7525,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -494; } #endif /* WOLFSSL_CERT_EXT */ @@ -6165,7 +7536,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -455; } @@ -6176,7 +7547,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -456; } @@ -6187,7 +7558,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -457; } @@ -6199,7 +7570,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -458; } FreeDecodedCert(&decode); @@ -6209,7 +7580,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -459; } ret = (int)fwrite(derCert, 1, certSz, derFile); @@ -6218,7 +7589,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -473; } @@ -6227,7 +7598,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -460; } @@ -6236,7 +7607,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -461; } ret = (int)fwrite(pem, 1, pemSz, pemFile); @@ -6245,7 +7616,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -474; } @@ -6254,7 +7625,7 @@ int rsa_test(void) XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -462; } ret = (int)fwrite(private_key, 1, private_key_len, ntruPrivFile); @@ -6263,7 +7634,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -475; } XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6282,14 +7653,14 @@ int rsa_test(void) der = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT,DYNAMIC_TYPE_TMP_BUFFER); if (der == NULL) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -463; } pem = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT,DYNAMIC_TYPE_TMP_BUFFER); if (pem == NULL) { XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -464; } @@ -6313,7 +7684,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -496; } @@ -6323,7 +7694,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -494; } #endif /* WOLFSSL_CERT_EXT */ @@ -6333,7 +7704,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -465; } @@ -6343,7 +7714,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -466; } @@ -6352,7 +7723,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -467; } @@ -6365,7 +7736,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -468; } @@ -6375,7 +7746,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -471; } @@ -6388,7 +7759,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -469; } ret = (int)fwrite(pem, 1, pemSz, reqFile); @@ -6397,7 +7768,7 @@ int rsa_test(void) XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); - wc_FreeRng(&rng); + wc_FreeRng(&rng); return -470; } @@ -6435,6 +7806,48 @@ int rsa_test(void) #endif #endif +static int dh_generate_test(WC_RNG *rng) +{ + int ret; + DhKey smallKey; + byte p[2] = { 0, 5 }; + byte g[2] = { 0, 2 }; + byte priv[2]; + word32 privSz = sizeof(priv); + byte pub[2]; + word32 pubSz = sizeof(pub); + + wc_InitDhKey(&smallKey); + + /* Parameter Validation testing. */ + ret = wc_DhSetKey(NULL, p, sizeof(p), g, sizeof(g)); + if (ret != BAD_FUNC_ARG) + return -100; + ret = wc_DhSetKey(&smallKey, NULL, sizeof(p), g, sizeof(g)); + if (ret != BAD_FUNC_ARG) + return -100; + ret = wc_DhSetKey(&smallKey, p, 0, g, sizeof(g)); + if (ret != BAD_FUNC_ARG) + return -100; + ret = wc_DhSetKey(&smallKey, p, sizeof(p), NULL, sizeof(g)); + if (ret != BAD_FUNC_ARG) + return -100; + ret = wc_DhSetKey(&smallKey, p, sizeof(p), g, 0); + if (ret != BAD_FUNC_ARG) + return -100; + ret = wc_DhSetKey(&smallKey, p, sizeof(p), g, sizeof(g)); + if (ret != 0) + return -101; + + /* Use API. */ + ret = wc_DhGenerateKeyPair(&smallKey, rng, priv, &privSz, pub, &pubSz); + wc_FreeDhKey(&smallKey); + if (ret != 0) + return -102; + + return 0; +} + int dh_test(void) { int ret; @@ -6516,6 +7929,10 @@ int dh_test(void) if (XMEMCMP(agree, agree2, agreeSz)) return -56; + ret = dh_generate_test(&rng); + if (ret != 0) + return -57; + wc_FreeDhKey(&key); wc_FreeDhKey(&key2); wc_FreeRng(&rng); @@ -7482,7 +8899,7 @@ int openssl_test(void) return -3407; total += outlen; if(total != 32) - return 3408; + return -3408; total = 0; EVP_CIPHER_CTX_init(&de); @@ -7514,7 +8931,7 @@ int openssl_test(void) total += outlen; if(total != 18) - return 3427; + return -3427; if (XMEMCMP(plain, cbcPlain, 18)) return -3428; @@ -8451,7 +9868,7 @@ static int ecc_test_curve_size(WC_RNG* rng, int keySize, int testVerifyCount, #ifdef HAVE_ECC_KEY_EXPORT x = sizeof(exportBuf); - ret = wc_ecc_export_x963(&userA, exportBuf, &x); + ret = wc_ecc_export_x963_ex(&userA, exportBuf, &x, 0); if (ret != 0) goto done; @@ -8590,11 +10007,529 @@ static int ecc_test_curve(WC_RNG* rng, int keySize) return 0; } +#if !defined(WOLFSSL_ATECC508A) && defined(HAVE_ECC_KEY_IMPORT) && \ + defined(HAVE_ECC_KEY_EXPORT) +static int ecc_point_test() +{ + int ret; + ecc_point* point; + ecc_point* point2; + word32 outLen; + byte out[65]; + byte der[] = { 0x04, /* = Uncompressed */ + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 }; +#ifdef HAVE_COMP_KEY + byte derComp0[] = { 0x02, /* = Compressed, y even */ + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 }; + byte derComp1[] = { 0x03, /* = Compressed, y odd */ + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 }; +#endif + byte altDer[] = { 0x04, /* = Uncompressed */ + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07 }; + + outLen = sizeof(out); + point = wc_ecc_new_point(); + if (point == NULL) + return -1035; + point2 = wc_ecc_new_point(); + if (point2 == NULL) { + wc_ecc_del_point(point); + return -1036; + } + + /* Parameter Validation testing. */ + wc_ecc_del_point(NULL); + ret = wc_ecc_import_point_der(NULL, sizeof(der), 6, point); + if (ret != ECC_BAD_ARG_E) { + ret = -1037; + goto done; + } + ret = wc_ecc_import_point_der(der, sizeof(der), -1, point); + if (ret != ECC_BAD_ARG_E) { + ret = -1038; + goto done; + } + ret = wc_ecc_import_point_der(der, sizeof(der), 6, NULL); + if (ret != ECC_BAD_ARG_E) { + ret = -1039; + goto done; + } + ret = wc_ecc_export_point_der(-1, point, out, &outLen); + if (ret != ECC_BAD_ARG_E) { + ret = -1040; + goto done; + } + ret = wc_ecc_export_point_der(6, NULL, out, &outLen); + if (ret != ECC_BAD_ARG_E) { + ret = -1041; + goto done; + } + ret = wc_ecc_export_point_der(6, point, NULL, &outLen); + if (ret != LENGTH_ONLY_E || outLen != sizeof(out)) { + ret = -1043; + goto done; + } + ret = wc_ecc_export_point_der(6, point, out, NULL); + if (ret != ECC_BAD_ARG_E) { + ret = -1043; + goto done; + } + outLen = 0; + ret = wc_ecc_export_point_der(6, point, out, &outLen); + if (ret != BUFFER_E) { + ret = -1044; + goto done; + } + ret = wc_ecc_copy_point(NULL, NULL); + if (ret != ECC_BAD_ARG_E) { + ret = -1045; + goto done; + } + ret = wc_ecc_copy_point(NULL, point2); + if (ret != ECC_BAD_ARG_E) { + ret = -1046; + goto done; + } + ret = wc_ecc_copy_point(point, NULL); + if (ret != ECC_BAD_ARG_E) { + ret = -1047; + goto done; + } + ret = wc_ecc_cmp_point(NULL, NULL); + if (ret != BAD_FUNC_ARG) { + ret = -1048; + goto done; + } + ret = wc_ecc_cmp_point(NULL, point2); + if (ret != BAD_FUNC_ARG) { + ret = -1049; + goto done; + } + ret = wc_ecc_cmp_point(point, NULL); + if (ret != BAD_FUNC_ARG) { + ret = -1050; + goto done; + } + + /* Use API. */ + ret = wc_ecc_import_point_der(der, sizeof(der), 6, point); + if (ret != 0) { + ret = -1051; + goto done; + } + + outLen = sizeof(out); + ret = wc_ecc_export_point_der(6, point, out, &outLen); + if (ret != 0) { + ret = -1052; + goto done; + } + if (outLen != sizeof(der)) { + ret = -1053; + goto done; + } + if (XMEMCMP(out, der, outLen) != 0) { + ret = -1054; + goto done; + } + + ret = wc_ecc_copy_point(point2, point); + if (ret != MP_OKAY) { + ret = -1055; + goto done; + } + ret = wc_ecc_cmp_point(point2, point); + if (ret != MP_EQ) { + ret = -1056; + goto done; + } + + ret = wc_ecc_import_point_der(altDer, sizeof(altDer), 6, point2); + if (ret != 0) { + ret = -1057; + goto done; + } + ret = wc_ecc_cmp_point(point2, point); + if (ret != MP_GT) { + ret = -1058; + goto done; + } + +#ifdef HAVE_COMP_KEY + /* TODO: Doesn't work. */ + ret = wc_ecc_import_point_der(derComp0, sizeof(der), 6, point); + if (ret != 0) { + ret = -1059; + goto done; + } + + ret = wc_ecc_import_point_der(derComp1, sizeof(der), 6, point); + if (ret != 0) { + ret = -1060; + goto done; + } +#endif + +done: + wc_ecc_del_point(point2); + wc_ecc_del_point(point); + + return ret; +} +#endif /* !WOLFSSL_ATECC508A && HAVE_ECC_KEY_IMPORT && HAVE_ECC_KEY_EXPORT */ + +#ifndef NO_SIG_WRAPPER +static int ecc_sig_test(WC_RNG* rng, ecc_key* key) +{ + int ret; + word32 sigSz; + int size; + byte out[65]; + byte in[] = "Everyone gets Friday off."; + word32 inLen = (word32)XSTRLEN((char*)in); + + size = wc_ecc_sig_size(key); + + ret = wc_SignatureGetSize(WC_SIGNATURE_TYPE_ECC, key, sizeof(*key)); + if (ret != size) + return -1030; + + sigSz = ret; + ret = wc_SignatureGenerate(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_ECC, in, + inLen, out, &sigSz, key, sizeof(*key), rng); + if (ret != 0) + return -1031; + + ret = wc_SignatureVerify(WC_HASH_TYPE_SHA256, WC_SIGNATURE_TYPE_ECC, in, + inLen, out, sigSz, key, sizeof(*key)); + if (ret != 0) + return -1032; + + return 0; +} +#endif + +#if defined(HAVE_ECC_KEY_IMPORT) && defined(HAVE_ECC_KEY_EXPORT) +static int ecc_exp_imp_test(ecc_key* key) +{ + int ret; + ecc_key keyImp; + byte priv[32]; + word32 privLen; + byte pub[65]; + word32 pubLen; + const char qx[] = "01020304050607080102030405060708" + "01020304050607080102030405060708"; + const char qy[] = "01020304050607080102030405060708" + "01020304050607080102030405060708"; + const char d[] = "01020304050607080102030405060708"; + + wc_ecc_init(&keyImp); + + privLen = sizeof(priv); + ret = wc_ecc_export_private_only(key, priv, &privLen); + if (ret != 0) { + ret = -1070; + goto done; + } + pubLen = sizeof(pub); + ret = wc_ecc_export_point_der(key->idx, &key->pubkey, pub, &pubLen); + if (ret != 0) { + ret = -1071; + goto done; + } + + ret = wc_ecc_import_private_key(priv, privLen, pub, pubLen, &keyImp); + if (ret != 0) { + ret = -1072; + goto done; + } + + ret = wc_ecc_import_raw_ex(&keyImp, qx, qy, d, ECC_SECP256R1); + if (ret != 0) { + ret = -1073; + goto done; + } + +done: + wc_ecc_free(&keyImp); + return ret; +} +#endif /* HAVE_ECC_KEY_IMPORT && HAVE_ECC_KEY_EXPORT */ + +#ifdef HAVE_ECC_KEY_IMPORT +static int ecc_mulmod_test(ecc_key* key1) +{ + int ret; + ecc_key key2; + ecc_key key3; + + wc_ecc_init(&key2); + wc_ecc_init(&key3); + + /* TODO: Use test data. */ + /* Need base point (Gx,Gy) and parameter A - load them as the public and + * private key in key2. + */ + ret = wc_ecc_import_raw_ex(&key2, key1->dp->Gx, key1->dp->Gy, key1->dp->Af, + ECC_SECP256R1); + if (ret != 0) + goto done; + + /* Need a point (Gx,Gy) and prime - load them as the public and private key + * in key3. + */ + ret = wc_ecc_import_raw_ex(&key3, key1->dp->Gx, key1->dp->Gy, + key1->dp->prime, ECC_SECP256R1); + if (ret != 0) + goto done; + + ret = wc_ecc_mulmod(&key1->k, &key2.pubkey, &key3.pubkey, &key2.k, &key3.k, + 1); + if (ret != 0) { + ret = -1080; + goto done; + } + +done: + wc_ecc_free(&key3); + wc_ecc_free(&key2); + return ret; +} +#endif + +#ifndef WOLFSSL_ATECC508A +static int ecc_ssh_test(ecc_key* key) +{ + int ret; + byte out[128]; + word32 outLen = sizeof(out); + + /* Parameter Validation testing. */ + ret = wc_ecc_shared_secret_ssh(NULL, &key->pubkey, out, &outLen); + if (ret != BAD_FUNC_ARG) + return -1090; + ret = wc_ecc_shared_secret_ssh(key, NULL, out, &outLen); + if (ret != BAD_FUNC_ARG) + return -1091; + ret = wc_ecc_shared_secret_ssh(key, &key->pubkey, NULL, &outLen); + if (ret != BAD_FUNC_ARG) + return -1092; + ret = wc_ecc_shared_secret_ssh(key, &key->pubkey, out, NULL); + if (ret != BAD_FUNC_ARG) + return -1093; + + /* Use API. */ + ret = wc_ecc_shared_secret_ssh(key, &key->pubkey, out, &outLen); + if (ret != 0) + return -1094; + return 0; +} +#endif + +static int ecc_def_curve_test(WC_RNG *rng) +{ + int ret; + ecc_key key; + + wc_ecc_init(&key); + + ret = wc_ecc_make_key(rng, 32, &key); + if (ret != 0) { + ret = -1030; + goto done; + } + +#ifndef NO_SIG_WRAPPER + ret = ecc_sig_test(rng, &key); + if (ret < 0) + goto done; +#endif +#if defined(HAVE_ECC_KEY_IMPORT) && defined(HAVE_ECC_KEY_EXPORT) + ret = ecc_exp_imp_test(&key); + if (ret < 0) + goto done; +#endif +#ifdef HAVE_ECC_KEY_IMPORT + ret = ecc_mulmod_test(&key); + if (ret < 0) + goto done; +#endif +#ifndef WOLFSSL_ATECC508A + ret = ecc_ssh_test(&key); + if (ret < 0) + goto done; +#endif +done: + wc_ecc_free(&key); + return ret; +} + +static int ecc_decode_test(void) +{ + int ret; + word32 inSz; + word32 inOutIdx; + ecc_key key; + const byte good[] = { 0x30, 0x0d, 0x30, 0x0b, 0x06, 0x00, 0x06, 0x01, 0x01, + 0x03, 0x04, 0x00, 0x04, 0x01, 0x01 }; + const byte badNoObjId[] = { 0x30, 0x08, 0x30, 0x06, 0x03, 0x04, + 0x00, 0x04, 0x01, 0x01 }; + const byte badOneObjId[] = { 0x30, 0x0a, 0x30, 0x08, 0x06, 0x00, 0x03, 0x04, + 0x00, 0x04, 0x01, 0x01 }; + const byte badObjId1Len[] = { 0x30, 0x0c, 0x30, 0x0a, 0x06, 0x09, + 0x06, 0x00, 0x03, 0x04, 0x00, 0x04, 0x01, 0x01 }; + const byte badObj2d1Len[] = { 0x30, 0x0c, 0x30, 0x0a, 0x06, 0x00, + 0x06, 0x07, 0x03, 0x04, 0x00, 0x04, 0x01, 0x01 }; + const byte badNotBitStr[] = { 0x30, 0x0d, 0x30, 0x0b, 0x06, 0x00, + 0x06, 0x01, 0x01, 0x04, 0x04, 0x00, 0x04, 0x01, 0x01 }; + const byte badBitStrLen[] = { 0x30, 0x0d, 0x30, 0x0b, 0x06, 0x00, + 0x06, 0x01, 0x01, 0x03, 0x05, 0x00, 0x04, 0x01, 0x01 }; + const byte badNoBitStrZero[] = { 0x30, 0x0c, 0x30, 0x0a, 0x06, 0x00, + 0x06, 0x01, 0x01, 0x03, 0x03, 0x04, 0x01, 0x01 }; + const byte badPoint[] = { 0x30, 0x0b, 0x30, 0x09, 0x06, 0x00, 0x06, 0x01, + 0x01, 0x03, 0x03, 0x00, 0x04, 0x01 }; + + XMEMSET(&key, 0, sizeof(key)); + wc_ecc_init(&key); + + inSz = sizeof(good); + ret = wc_EccPublicKeyDecode(NULL, &inOutIdx, &key, inSz); + if (ret != BAD_FUNC_ARG) { + ret = -1100; + goto done; + } + ret = wc_EccPublicKeyDecode(good, NULL, &key, inSz); + if (ret != BAD_FUNC_ARG) { + ret = -1101; + goto done; + } + ret = wc_EccPublicKeyDecode(good, &inOutIdx, NULL, inSz); + if (ret != BAD_FUNC_ARG) { + ret = -1102; + goto done; + } + ret = wc_EccPublicKeyDecode(good, &inOutIdx, &key, 0); + if (ret != BAD_FUNC_ARG) { + ret = -1103; + goto done; + } + + /* Change offset to produce bad input data. */ + inOutIdx = 2; + inSz = sizeof(good) - inOutIdx; + ret = wc_EccPublicKeyDecode(good, &inOutIdx, &key, inSz); + if (ret != ASN_PARSE_E) { + ret = -1104; + goto done; + } + inOutIdx = 4; + inSz = sizeof(good) - inOutIdx; + ret = wc_EccPublicKeyDecode(good, &inOutIdx, &key, inSz); + if (ret != ASN_PARSE_E) { + ret = -1105; + goto done; + } + /* Bad data. */ + inSz = sizeof(badNoObjId); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(badNoObjId, &inOutIdx, &key, inSz); + if (ret != ASN_OBJECT_ID_E) { + ret = -1106; + goto done; + } + inSz = sizeof(badOneObjId); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(badOneObjId, &inOutIdx, &key, inSz); + if (ret != ASN_OBJECT_ID_E) { + ret = -1107; + goto done; + } + inSz = sizeof(badObjId1Len); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(badObjId1Len, &inOutIdx, &key, inSz); + if (ret != ASN_PARSE_E) { + ret = -1108; + goto done; + } + inSz = sizeof(badObj2d1Len); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(badObj2d1Len, &inOutIdx, &key, inSz); + if (ret != ASN_PARSE_E) { + ret = -1109; + goto done; + } + inSz = sizeof(badNotBitStr); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(badNotBitStr, &inOutIdx, &key, inSz); + if (ret != ASN_BITSTR_E) { + ret = -1110; + goto done; + } + inSz = sizeof(badBitStrLen); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(badBitStrLen, &inOutIdx, &key, inSz); + if (ret != ASN_PARSE_E) { + ret = -1111; + goto done; + } + inSz = sizeof(badNoBitStrZero); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(badNoBitStrZero, &inOutIdx, &key, inSz); + if (ret != ASN_EXPECT_0_E) { + ret = -1112; + goto done; + } + inSz = sizeof(badPoint); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(badPoint, &inOutIdx, &key, inSz); + if (ret != ASN_ECC_KEY_E) { + ret = -1113; + goto done; + } + + inSz = sizeof(good); + inOutIdx = 0; + ret = wc_EccPublicKeyDecode(good, &inOutIdx, &key, inSz); + if (ret != 0) { + ret = -1120; + goto done; + } + +done: + wc_ecc_free(&key); + return ret; +} + int ecc_test(void) { int ret; WC_RNG rng; + ret = ecc_decode_test(); + if (ret < 0) + return ret; + ret = wc_InitRng(&rng); if (ret != 0) return -1001; @@ -8640,6 +10575,17 @@ int ecc_test(void) if (ret < 0) { goto done; } +#if !defined(WOLFSSL_ATECC508A) && defined(HAVE_ECC_KEY_IMPORT) && \ + defined(HAVE_ECC_KEY_EXPORT) + ret = ecc_point_test(); + if (ret < 0) { + goto done; + } +#endif + ret = ecc_def_curve_test(&rng); + if (ret < 0) { + goto done; + } #endif /* !NO_ECC256 */ #if defined(HAVE_ECC320) || defined(HAVE_ALL_CURVES) ret = ecc_test_curve(&rng, 40); @@ -10529,6 +12475,318 @@ int pkcs7signed_test(void) #endif /* HAVE_PKCS7 */ +#ifdef HAVE_VALGRIND +/* Need a static build to have access to symbols. */ + +/* Maximum number of bytes in a number to test. */ +#define MP_MAX_TEST_BYTE_LEN 16 + +#if defined(HAVE_ECC) || defined(WOLFSSL_KEY_GEN) +static int randNum(mp_int* n, int len, WC_RNG* rng, void* heap) +{ + byte d[MP_MAX_TEST_BYTE_LEN]; + int ret; + + (void)heap; + + do { + ret = wc_RNG_GenerateBlock(rng, d, len); + if (ret != 0) + return ret; + ret = mp_read_unsigned_bin(n, d, len); + if (ret != 0) + return ret; + } while (mp_iszero(n)); + + return 0; +} +#endif + +int mp_test() +{ + WC_RNG rng; + int ret; +#if defined(HAVE_ECC) || defined(WOLFSSL_KEY_GEN) + int i, j, k; +#endif + mp_int a, b, r1, r2, p; + mp_digit d; + + ret = mp_init_multi(&a, &b, &r1, &r2, NULL, NULL); + if (ret != 0) + return -10000; + + mp_init_copy(&p, &a); + + ret = wc_InitRng(&rng); + if (ret != 0) + goto done; + +#if defined(HAVE_ECC) || defined(WOLFSSL_KEY_GEN) + mp_set_int(&a, 0); + if (a.used != 0 || a.dp[0] != 0) + return -10001; + + for (j = 1; j <= MP_MAX_TEST_BYTE_LEN; j++) { + for (i = 0; i < 4 * j; i++) { + /* New values to use. */ + ret = randNum(&p, j, &rng, NULL); + if (ret != 0) + return -11000; + ret = randNum(&a, j, &rng, NULL); + if (ret != 0) + return -11001; + ret = randNum(&b, j, &rng, NULL); + if (ret != 0) + return -11002; + ret = wc_RNG_GenerateBlock(&rng, (byte*)&d, sizeof(d)); + if (ret != 0) + return -11003; + + /* Ensure sqrmod produce same result as mulmod. */ + ret = mp_sqrmod(&a, &p, &r1); + if (ret != 0) + return -11005; + ret = mp_mulmod(&a, &a, &p, &r2); + if (ret != 0) + return -11006; + if (mp_cmp(&r1, &r2) != 0) + return -11007; + + /* Ensure add with mod produce same result as sub with mod. */ + ret = mp_addmod(&a, &b, &p, &r1); + if (ret != 0) + return -11010; + b.sign ^= 1; + ret = mp_submod(&a, &b, &p, &r2); + if (ret != 0) + return -11011; + if (mp_cmp(&r1, &r2) != 0) + return -11012; + + /* Ensure add digit produce same result as sub digit. */ + ret = mp_add_d(&a, d, &r1); + if (ret != 0) + return -11015; + ret = mp_sub_d(&r1, d, &r2); + if (ret != 0) + return -11016; + if (mp_cmp(&a, &r2) != 0) + return -11017; + + /* Invert - if p is even it will use the slow impl. + * - if p and a are even it will fail. + */ + ret = mp_invmod(&a, &p, &r1); + if (ret != 0 && ret != FP_VAL) + return -11019; + ret = 0; + + /* Shift up and down number all bits in a digit. */ + for (k = 0; k < DIGIT_BIT; k++) { + mp_mul_2d(&a, k, &r1); + mp_div_2d(&r1, k, &r2, &p); + if (mp_cmp(&a, &r2) != 0) + return -11020; + if (!mp_iszero(&p)) + return -11021; + mp_rshb(&r1, k); + if (mp_cmp(&a, &r1) != 0) + return -11022; + } + } + } + + /* Check that setting a digit works. */ + mp_set_int(&a, d); + if (a.used != 1 || a.dp[0] != d) + return -11025; + + /* Check setting a bit and testing a bit works. */ + for (i = 0; i < MP_MAX_TEST_BYTE_LEN * 8; i++) { + mp_zero(&a); + mp_set_bit(&a, i); + if (!mp_is_bit_set(&a, i)) + return -11030; + } +#endif + +done: + mp_clear(&p); + mp_clear(&r2); + mp_clear(&r1); + mp_clear(&a); + wc_FreeRng(&rng); + return ret; +} +#endif + +#ifdef HAVE_VALGRIND +/* Need a static build to have access to symbols. */ + +#ifndef WOLFSSL_SSL_H +/* APIs hiding in ssl.h */ +extern int wolfSSL_Debugging_ON(void); +extern void wolfSSL_Debugging_OFF(void); +#endif + +#ifdef DEBUG_WOLFSSL +static int log_cnt = 0; +static void my_Logging_cb(const int logLevel, const char *const logMessage) +{ + (void)logLevel; + (void)logMessage; + log_cnt++; +} +#endif + +int logging_test() +{ +#ifdef DEBUG_WOLFSSL + const char* msg = "Testing, testing. 1, 2, 3, 4 ..."; + byte a[8] = { 1, 2, 3, 4, 5, 6, 7, 8 }; + byte b[256]; + size_t i; + + for (i = 0; i < sizeof(b); i++) + b[i] = i; + + if (wolfSSL_Debugging_ON() != 0) + return -12000; + if (wolfSSL_SetLoggingCb(NULL) != BAD_FUNC_ARG) + return -12002; + + WOLFSSL_MSG(msg); + WOLFSSL_BUFFER(a, sizeof(a)); + WOLFSSL_BUFFER(b, sizeof(b)); + WOLFSSL_BUFFER(NULL, 0); + + wolfSSL_Debugging_OFF(); + + WOLFSSL_MSG(msg); + WOLFSSL_BUFFER(b, sizeof(b)); + + if (wolfSSL_SetLoggingCb(my_Logging_cb) != 0) + return -12003; + + wolfSSL_Debugging_OFF(); + + WOLFSSL_MSG(msg); + WOLFSSL_BUFFER(b, sizeof(b)); + + if (log_cnt != 0) + return -12005; + if (wolfSSL_Debugging_ON() != 0) + return -12006; + + WOLFSSL_MSG(msg); + WOLFSSL_BUFFER(b, sizeof(b)); + + /* One call for each line of output. */ + if (log_cnt != 17) + return -12007; +#else + if (wolfSSL_Debugging_ON() != NOT_COMPILED_IN) + return -12000; + wolfSSL_Debugging_OFF(); + if (wolfSSL_SetLoggingCb(NULL) != NOT_COMPILED_IN) + return -12001; +#endif + return 0; +} +#endif + +int mutex_test() +{ +#ifdef WOLFSSL_PTHREADS + wolfSSL_Mutex m; +#endif + wolfSSL_Mutex *mm = wc_InitAndAllocMutex(); + if (mm == NULL) + return -12020; + wc_FreeMutex(mm); + XFREE(mm, NULL, DYNAMIC_TYPE_MUTEX); + +#ifdef WOLFSSL_PTHREADS + if (wc_InitMutex(&m) != 0) + return -12021; + if (wc_LockMutex(&m) != 0) + return -12022; + if (wc_FreeMutex(&m) != BAD_MUTEX_E) + return -12023; + if (wc_UnLockMutex(&m) != 0) + return -12024; + if (wc_FreeMutex(&m) != 0) + return -12025; + if (wc_LockMutex(&m) != BAD_MUTEX_E) + return -12026; + if (wc_UnLockMutex(&m) != BAD_MUTEX_E) + return -12027; +#endif + + return 0; +} + +#ifdef USE_WOLFSSL_MEMORY +static int malloc_cnt = 0; +static int realloc_cnt = 0; +static int free_cnt = 0; + +static void *my_Malloc_cb(size_t size) +{ + malloc_cnt++; + return malloc(size); +} +static void my_Free_cb(void *ptr) +{ + free_cnt++; + free(ptr); +} +static void *my_Realloc_cb(void *ptr, size_t size) +{ + realloc_cnt++; + return realloc(ptr, size); +} + +int memcb_test() +{ + byte* b = NULL; + + b = (byte*)XREALLOC(b, 1024, NULL, DYNAMIC_TYPE_TMP_BUFFER); + XFREE(b, NULL, DYNAMIC_TYPE_TMP_BUFFER); + b = NULL; + + /* Parameter Validation testing. */ + if (wolfSSL_SetAllocators(NULL, (wolfSSL_Free_cb)&my_Free_cb, + (wolfSSL_Realloc_cb)&my_Realloc_cb) != BAD_FUNC_ARG) + return -12100; + if (wolfSSL_SetAllocators((wolfSSL_Malloc_cb)&my_Malloc_cb, NULL, + (wolfSSL_Realloc_cb)&my_Realloc_cb) != BAD_FUNC_ARG) + return -12101; + if (wolfSSL_SetAllocators((wolfSSL_Malloc_cb)&my_Malloc_cb, + (wolfSSL_Free_cb)&my_Free_cb, NULL) != BAD_FUNC_ARG) + return -12102; + + /* Use API. */ + if (wolfSSL_SetAllocators((wolfSSL_Malloc_cb)&my_Malloc_cb, + (wolfSSL_Free_cb)&my_Free_cb, (wolfSSL_Realloc_cb)my_Realloc_cb) + != 0) + return -12100; + + b = (byte*)XMALLOC(1024, NULL, DYNAMIC_TYPE_TMP_BUFFER); + b = (byte*)XREALLOC(b, 1024, NULL, DYNAMIC_TYPE_TMP_BUFFER); + XFREE(b, NULL, DYNAMIC_TYPE_TMP_BUFFER); + +#ifndef WOLFSSL_STATIC_MEMORY + if (malloc_cnt != 1 || free_cnt != 1 || realloc_cnt != 1) +#else + if (malloc_cnt != 0 || free_cnt != 0 || realloc_cnt != 0) +#endif + return -12110; + return 0; +} +#endif + #undef ERROR_OUT #else diff --git a/wolfcrypt/user-crypto/src/rsa.c b/wolfcrypt/user-crypto/src/rsa.c index fdee5f5a2..2533a94a8 100644 --- a/wolfcrypt/user-crypto/src/rsa.c +++ b/wolfcrypt/user-crypto/src/rsa.c @@ -1950,7 +1950,7 @@ int wc_RsaFlattenPublicKey(RsaKey* key, byte* e, word32* eSz, byte* n, if (key == NULL || e == NULL || eSz == NULL || n == NULL || nSz == NULL) return USER_CRYPTO_ERROR; - bytSz = sizeof(byte); + bytSz = sizeof(byte) * 8; ret = ippsExtGet_BN(NULL, &sz, NULL, key->e); if (ret != ippStsNoErr) return USER_CRYPTO_ERROR; From 292a17fff86786df41af7117405f057d28160786 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Tue, 28 Feb 2017 11:31:52 +1000 Subject: [PATCH 11/68] wc_EccPublicKeyDecode changes from review --- wolfcrypt/src/asn.c | 2 ++ wolfcrypt/test/test.c | 4 ++++ 2 files changed, 6 insertions(+) diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 74c92ad87..3ed4c87cc 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -9190,6 +9190,7 @@ int wc_EccPrivateKeyDecode(const byte* input, word32* inOutIdx, ecc_key* key, return ret; } +#ifdef WOLFSSL_CERT_EXT int wc_EccPublicKeyDecode(const byte* input, word32* inOutIdx, ecc_key* key, word32 inSz) { @@ -9243,6 +9244,7 @@ int wc_EccPublicKeyDecode(const byte* input, word32* inOutIdx, return 0; } +#endif #ifdef WOLFSSL_KEY_GEN diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index d072ff8d5..afa4a475e 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -10385,6 +10385,7 @@ done: return ret; } +#ifdef WOLFSSL_CERT_EXT static int ecc_decode_test(void) { int ret; @@ -10520,15 +10521,18 @@ done: wc_ecc_free(&key); return ret; } +#endif /* WOLFSSL_CERT_EXT */ int ecc_test(void) { int ret; WC_RNG rng; +#ifdef WOLFSSL_CERT_EXT ret = ecc_decode_test(); if (ret < 0) return ret; +#endif ret = wc_InitRng(&rng); if (ret != 0) From 7ca19f9fff5c260f1ba2611207b1376bb4a34615 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Wed, 1 Mar 2017 08:48:36 +1000 Subject: [PATCH 12/68] Protect other call to wc_EccPublicKeyDecode --- wolfcrypt/test/test.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index afa4a475e..7fbebb1a9 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -10854,6 +10854,7 @@ int ecc_test_buffers() { if (XMEMCMP(plain, in, ret)) return -48; +#ifdef WOLFSSL_CERT_EXT idx = 0; bytes = sizeof_ecc_clikeypub_der_256; @@ -10862,6 +10863,7 @@ int ecc_test_buffers() { (word32) bytes); if (ret != 0) return -52; +#endif return 0; } From 2d612da9f400f68b555c40284881d31b0389cba0 Mon Sep 17 00:00:00 2001 From: toddouska Date: Wed, 1 Mar 2017 10:25:54 -0800 Subject: [PATCH 13/68] fix signer memory takeover on malformed data --- src/ssl.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/src/ssl.c b/src/ssl.c index 7b9b3a75d..4e8b3cc50 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -3354,10 +3354,14 @@ int AddCA(WOLFSSL_CERT_MANAGER* cm, DerBuffer** pDer, int type, int verify) ret = MEMORY_ERROR; else { signer->keyOID = cert->keyOID; - signer->publicKey = cert->publicKey; - signer->pubKeySize = cert->pubKeySize; - signer->nameLen = cert->subjectCNLen; - signer->name = cert->subjectCN; + if (cert->pubKeyStored) { + signer->publicKey = cert->publicKey; + signer->pubKeySize = cert->pubKeySize; + } + if (cert->subjectCNStored) { + signer->nameLen = cert->subjectCNLen; + signer->name = cert->subjectCN; + } signer->pathLength = cert->pathLength; signer->pathLengthSet = cert->pathLengthSet; #ifndef IGNORE_NAME_CONSTRAINTS From 9ab28f9756c0ff33b87dfb1b1782f1029c468d88 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Wed, 1 Mar 2017 11:39:00 -0700 Subject: [PATCH 14/68] account for static memory IO_POOL free when general memory was used --- wolfcrypt/src/memory.c | 37 ++++++++++++++++++++----------------- 1 file changed, 20 insertions(+), 17 deletions(-) diff --git a/wolfcrypt/src/memory.c b/wolfcrypt/src/memory.c index 3d38265cf..c5f0e47b9 100644 --- a/wolfcrypt/src/memory.c +++ b/wolfcrypt/src/memory.c @@ -539,7 +539,9 @@ void* wolfSSL_Malloc(size_t size, void* heap, int type) } /* case of using fixed IO buffers */ - if (mem->flag & WOLFMEM_IO_POOL_FIXED) { + if (mem->flag & WOLFMEM_IO_POOL_FIXED && + (type == DYNAMIC_TYPE_OUT_BUFFER || + type == DYNAMIC_TYPE_IN_BUFFER)) { if (type == DYNAMIC_TYPE_OUT_BUFFER) { pt = hint->outBuf; } @@ -547,25 +549,26 @@ void* wolfSSL_Malloc(size_t size, void* heap, int type) pt = hint->inBuf; } } - - /* check if using IO pool flag */ - if (mem->flag & WOLFMEM_IO_POOL && pt == NULL && + else { + /* check if using IO pool flag */ + if (mem->flag & WOLFMEM_IO_POOL && (type == DYNAMIC_TYPE_OUT_BUFFER || type == DYNAMIC_TYPE_IN_BUFFER)) { - if (mem->io != NULL) { - pt = mem->io; - mem->io = pt->next; + if (mem->io != NULL) { + pt = mem->io; + mem->io = pt->next; + } } - } - /* general static memory */ - if (pt == NULL) { - for (i = 0; i < WOLFMEM_MAX_BUCKETS; i++) { - if ((word32)size < mem->sizeList[i]) { - if (mem->ava[i] != NULL) { - pt = mem->ava[i]; - mem->ava[i] = pt->next; - break; + /* general static memory */ + if (pt == NULL) { + for (i = 0; i < WOLFMEM_MAX_BUCKETS; i++) { + if ((word32)size < mem->sizeList[i]) { + if (mem->ava[i] != NULL) { + pt = mem->ava[i]; + mem->ava[i] = pt->next; + break; + } } } } @@ -672,7 +675,7 @@ void wolfSSL_Free(void *ptr, void* heap, int type) /* fixed IO pools are free'd at the end of SSL lifetime using FreeFixedIO(WOLFSSL_HEAP* heap, wc_Memory** io) */ } - else if (mem->flag & WOLFMEM_IO_POOL && + else if (mem->flag & WOLFMEM_IO_POOL && pt->sz == WOLFMEM_IO_SZ && (type == DYNAMIC_TYPE_OUT_BUFFER || type == DYNAMIC_TYPE_IN_BUFFER)) { pt->next = mem->io; From c1c7c903458b83a9e4ec0bcf01ba65e80805b617 Mon Sep 17 00:00:00 2001 From: toddouska Date: Wed, 1 Mar 2017 11:17:24 -0800 Subject: [PATCH 15/68] add defined for default AES AUTH_TAG_MIN_SZ --- wolfcrypt/src/aes.c | 10 ++++++++++ wolfcrypt/test/test.c | 26 -------------------------- wolfssl/wolfcrypt/settings.h | 6 ++++++ 3 files changed, 16 insertions(+), 26 deletions(-) diff --git a/wolfcrypt/src/aes.c b/wolfcrypt/src/aes.c index 09c78bd4e..7b8c4b40a 100644 --- a/wolfcrypt/src/aes.c +++ b/wolfcrypt/src/aes.c @@ -4238,6 +4238,11 @@ int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz, uint32_t keySize; status_t status; + if (authTagSz < WOLFSSL_MIN_AUTH_TAG_SZ) { + WOLFSSL_MSG("GcmEncrypt authTagSz too small error"); + return BAD_FUNC_ARG; + } + key = (byte*)aes->key; status = wc_AesGetKeySize(aes, &keySize); @@ -4265,6 +4270,11 @@ int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz, if (authTagSz > AES_BLOCK_SIZE) return BAD_FUNC_ARG; + if (authTagSz < WOLFSSL_MIN_AUTH_TAG_SZ) { + WOLFSSL_MSG("GcmEncrypt authTagSz too small error"); + return BAD_FUNC_ARG; + } + #ifdef WOLFSSL_AESNI if (haveAESNI) { AES_GCM_encrypt(in, out, authIn, iv, authTag, diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 24aaaecc8..2e0cebb5a 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -3432,26 +3432,6 @@ int gmac_test(void) 0x8d, 0x83, 0xb0, 0xbb, 0x14, 0xb6, 0x91 }; - const byte k3[] = - { - 0xb8, 0xe4, 0x9a, 0x5e, 0x37, 0xf9, 0x98, 0x2b, - 0xb9, 0x6d, 0xd0, 0xc9, 0xb6, 0xab, 0x26, 0xac - }; - const byte iv3[] = - { - 0xe4, 0x4a, 0x42, 0x18, 0x8c, 0xae, 0x94, 0x92, - 0x6a, 0x9c, 0x26, 0xb0 - }; - const byte a3[] = - { - 0x9d, 0xb9, 0x61, 0x68, 0xa6, 0x76, 0x7a, 0x31, - 0xf8, 0x29, 0xe4, 0x72, 0x61, 0x68, 0x3f, 0x8a - }; - const byte t3[] = - { - 0x23, 0xe2, 0x9f, 0x66, 0xe4, 0xc6, 0x52, 0x48 - }; - byte tag[16]; XMEMSET(tag, 0, sizeof(tag)); @@ -3466,12 +3446,6 @@ int gmac_test(void) if (XMEMCMP(t2, tag, sizeof(t2)) != 0) return -127; - XMEMSET(tag, 0, sizeof(tag)); - wc_GmacSetKey(&gmac, k3, sizeof(k3)); - wc_GmacUpdate(&gmac, iv3, sizeof(iv3), a3, sizeof(a3), tag, sizeof(t3)); - if (XMEMCMP(t3, tag, sizeof(t3)) != 0) - return -128; - return 0; } #endif /* HAVE_AESGCM */ diff --git a/wolfssl/wolfcrypt/settings.h b/wolfssl/wolfcrypt/settings.h index e1c93cd75..e8d7f1fc9 100644 --- a/wolfssl/wolfcrypt/settings.h +++ b/wolfssl/wolfcrypt/settings.h @@ -1396,6 +1396,12 @@ static char *fgets(char *buff, int sz, FILE *fp) #define NO_OLD_TLS #endif + +/* Default AES minimum auth tag sz, allow user to override */ +#ifndef WOLFSSL_MIN_AUTH_TAG_SZ + #define WOLFSSL_MIN_AUTH_TAG_SZ 12 +#endif + /* If not forcing ARC4 as the DRBG or using custom RNG block gen, enable Hash_DRBG */ #undef HAVE_HASHDRBG #if !defined(WOLFSSL_FORCE_RC4_DRBG) && !defined(CUSTOM_RAND_GENERATE_BLOCK) From d903059e054363dcdf1f5d7cd1123ee32fa55667 Mon Sep 17 00:00:00 2001 From: David Garske Date: Wed, 1 Mar 2017 19:07:13 -0800 Subject: [PATCH 16/68] Fixes to allow signature_algorithms extension to send SHA1 (if enabled) and NO_OLD_TLS is defined. This resolves an issue connected to ISS servers. --- src/internal.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/internal.c b/src/internal.c index 3c5f39c7f..55a19d9fc 100644 --- a/src/internal.c +++ b/src/internal.c @@ -1672,7 +1672,7 @@ static void InitSuitesHashSigAlgo(Suites* suites, int haveECDSAsig, suites->hashSigAlgo[idx++] = sha256_mac; suites->hashSigAlgo[idx++] = ecc_dsa_sa_algo; #endif - #if !defined(NO_SHA) && !defined(NO_OLD_TLS) + #if !defined(NO_SHA) suites->hashSigAlgo[idx++] = sha_mac; suites->hashSigAlgo[idx++] = ecc_dsa_sa_algo; #endif @@ -1691,7 +1691,7 @@ static void InitSuitesHashSigAlgo(Suites* suites, int haveECDSAsig, suites->hashSigAlgo[idx++] = sha256_mac; suites->hashSigAlgo[idx++] = rsa_sa_algo; #endif - #if !defined(NO_SHA) && !defined(NO_OLD_TLS) + #if !defined(NO_SHA) suites->hashSigAlgo[idx++] = sha_mac; suites->hashSigAlgo[idx++] = rsa_sa_algo; #endif @@ -14749,7 +14749,7 @@ static int DoServerKeyExchange(WOLFSSL* ssl, const byte* input, #endif break; case sha_mac: - #ifndef NO_OLD_TLS + #ifndef NO_SHA hashType = WC_HASH_TYPE_SHA; #endif break; @@ -17756,7 +17756,7 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, #endif break; case sha_mac: - #ifndef NO_OLD_TLS + #ifndef NO_SHA hashType = WC_HASH_TYPE_SHA; #endif break; @@ -17850,7 +17850,7 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, #endif break; case sha_mac: - #ifndef NO_OLD_TLS + #ifndef NO_SHA typeH = SHAh; #endif break; @@ -18020,7 +18020,7 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, #endif break; case sha_mac: - #ifndef NO_OLD_TLS + #ifndef NO_SHA hashType = WC_HASH_TYPE_SHA; #endif break; @@ -18109,7 +18109,7 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, #endif break; case sha_mac: - #ifndef NO_OLD_TLS + #ifndef NO_SHA typeH = SHAh; #endif break; From ec1d8c7090c5ba07fa185fd819fcc3be3160a137 Mon Sep 17 00:00:00 2001 From: John Safranek Date: Thu, 2 Mar 2017 10:05:24 -0800 Subject: [PATCH 17/68] Fixed where the client was using NULL instead of ssl->heap when allocating memory during SendClientKeyExchange(). Failing on an embedded static build. --- src/internal.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/internal.c b/src/internal.c index 3c5f39c7f..cc7378f21 100644 --- a/src/internal.c +++ b/src/internal.c @@ -15728,7 +15728,7 @@ int SendClientKeyExchange(WOLFSSL* ssl) case KEYSHARE_BUILD: { encSz = MAX_ENCRYPT_SZ; - encSecret = (byte*)XMALLOC(MAX_ENCRYPT_SZ, NULL, + encSecret = (byte*)XMALLOC(MAX_ENCRYPT_SZ, ssl->heap, DYNAMIC_TYPE_TMP_BUFFER); if (encSecret == NULL) { ERROR_OUT(MEMORY_E, exit_scke); @@ -15755,8 +15755,8 @@ int SendClientKeyExchange(WOLFSSL* ssl) case diffie_hellman_kea: { ssl->buffers.sig.length = ENCRYPT_LEN; - ssl->buffers.sig.buffer = (byte*)XMALLOC(ENCRYPT_LEN, NULL, - DYNAMIC_TYPE_TMP_BUFFER); + ssl->buffers.sig.buffer = (byte*)XMALLOC(ENCRYPT_LEN, + ssl->heap, DYNAMIC_TYPE_TMP_BUFFER); if (ssl->buffers.sig.buffer == NULL) { ERROR_OUT(MEMORY_E, exit_scke); } @@ -15816,8 +15816,8 @@ int SendClientKeyExchange(WOLFSSL* ssl) } ssl->buffers.sig.length = ENCRYPT_LEN; - ssl->buffers.sig.buffer = (byte*)XMALLOC(ENCRYPT_LEN, NULL, - DYNAMIC_TYPE_TMP_BUFFER); + ssl->buffers.sig.buffer = (byte*)XMALLOC(ENCRYPT_LEN, + ssl->heap, DYNAMIC_TYPE_TMP_BUFFER); if (ssl->buffers.sig.buffer == NULL) { ERROR_OUT(MEMORY_E, exit_scke); } From 67a8626430737d821a36eddcc574a54a7266e661 Mon Sep 17 00:00:00 2001 From: David Garske Date: Thu, 2 Mar 2017 15:56:31 -0800 Subject: [PATCH 18/68] =?UTF-8?q?Fix=20for=20scan-build=20warning=20with?= =?UTF-8?q?=20=E2=80=9C->dp=20=3D=3D=20NULL=E2=80=9D.=20Scenario=20can?= =?UTF-8?q?=E2=80=99t=20happen,=20but=20adding=20sanity=20check=20to=20sup?= =?UTF-8?q?press=20warning.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- wolfcrypt/src/integer.c | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index 067a55012..c5026bf6d 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -330,12 +330,16 @@ int mp_copy (mp_int * a, mp_int * b) } /* grow dest */ - if (b->alloc < a->used || b->dp == NULL) { + if (b->alloc < a->used) { if ((res = mp_grow (b, a->used)) != MP_OKAY) { return res; } } + /* sanity check on destination */ + if (b->dp == NULL) + return MP_VAL; + /* zero b and copy the parameters over */ { mp_digit *tmpa, *tmpb; @@ -1633,11 +1637,16 @@ int s_mp_sub (mp_int * a, mp_int * b, mp_int * c) max_a = a->used; /* init result */ - if (c->alloc < max_a || c->dp == NULL) { + if (c->alloc < max_a) { if ((res = mp_grow (c, max_a)) != MP_OKAY) { return res; } } + + /* sanity check on destination */ + if (c->dp == NULL) + return MP_VAL; + olduse = c->used; c->used = max_a; From b5fe3ddbfa12640d9b1a2aa616be0162c1d1adcb Mon Sep 17 00:00:00 2001 From: David Garske Date: Thu, 2 Mar 2017 18:18:05 -0800 Subject: [PATCH 19/68] =?UTF-8?q?Fix=20to=20allow=20connection=20to=20IIS?= =?UTF-8?q?=20server=20which=20requires=20SHA1=20hash=20algo=20to=20be=20p?= =?UTF-8?q?resent=20in=20signature=5Falgos=20extension.=20Issue=20only=20e?= =?UTF-8?q?xists=20when=20NO=5FOLD=5FTLS=20is=20defined.=20To=20enable=20S?= =?UTF-8?q?HA1=20with=20TLS=201.2=20define=20"WOLFSSL=5FALLOW=5FTLS=5FSHA1?= =?UTF-8?q?=E2=80=9D.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/internal.c | 26 +++++++++++++++++++------- 1 file changed, 19 insertions(+), 7 deletions(-) diff --git a/src/internal.c b/src/internal.c index 55a19d9fc..08d11f997 100644 --- a/src/internal.c +++ b/src/internal.c @@ -1672,7 +1672,8 @@ static void InitSuitesHashSigAlgo(Suites* suites, int haveECDSAsig, suites->hashSigAlgo[idx++] = sha256_mac; suites->hashSigAlgo[idx++] = ecc_dsa_sa_algo; #endif - #if !defined(NO_SHA) + #if !defined(NO_SHA) && (!defined(NO_OLD_TLS) || \ + defined(WOLFSSL_ALLOW_TLS_SHA1)) suites->hashSigAlgo[idx++] = sha_mac; suites->hashSigAlgo[idx++] = ecc_dsa_sa_algo; #endif @@ -1691,7 +1692,8 @@ static void InitSuitesHashSigAlgo(Suites* suites, int haveECDSAsig, suites->hashSigAlgo[idx++] = sha256_mac; suites->hashSigAlgo[idx++] = rsa_sa_algo; #endif - #if !defined(NO_SHA) + #if !defined(NO_SHA) && (!defined(NO_OLD_TLS) || \ + defined(WOLFSSL_ALLOW_TLS_SHA1)) suites->hashSigAlgo[idx++] = sha_mac; suites->hashSigAlgo[idx++] = rsa_sa_algo; #endif @@ -14749,7 +14751,9 @@ static int DoServerKeyExchange(WOLFSSL* ssl, const byte* input, #endif break; case sha_mac: - #ifndef NO_SHA + #if !defined(NO_SHA) && \ + (!defined(NO_OLD_TLS) || \ + defined(WOLFSSL_ALLOW_TLS_SHA1)) hashType = WC_HASH_TYPE_SHA; #endif break; @@ -17756,7 +17760,9 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, #endif break; case sha_mac: - #ifndef NO_SHA + #if !defined(NO_SHA) && \ + (!defined(NO_OLD_TLS) || \ + defined(WOLFSSL_ALLOW_TLS_SHA1)) hashType = WC_HASH_TYPE_SHA; #endif break; @@ -17850,7 +17856,9 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, #endif break; case sha_mac: - #ifndef NO_SHA + #if !defined(NO_SHA) && \ + (!defined(NO_OLD_TLS) || \ + defined(WOLFSSL_ALLOW_TLS_SHA1)) typeH = SHAh; #endif break; @@ -18020,7 +18028,9 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, #endif break; case sha_mac: - #ifndef NO_SHA + #if !defined(NO_SHA) && \ + (!defined(NO_OLD_TLS) || \ + defined(WOLFSSL_ALLOW_TLS_SHA1)) hashType = WC_HASH_TYPE_SHA; #endif break; @@ -18109,7 +18119,9 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, #endif break; case sha_mac: - #ifndef NO_SHA + #if !defined(NO_SHA) && \ + (!defined(NO_OLD_TLS) || \ + defined(WOLFSSL_ALLOW_TLS_SHA1)) typeH = SHAh; #endif break; From 0182d99efbdfcbba23ceee85a220183f5cf24ca4 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Fri, 3 Mar 2017 16:38:29 +1000 Subject: [PATCH 20/68] Updates for nginx 1.10.3 Don't return global error when: SOCKET_PEER_CLOSED_E or SOCKET_ERROR_E Increase max ex_data items to 5 --- src/ssl.c | 3 ++- wolfssl/internal.h | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/src/ssl.c b/src/ssl.c index ec90a6433..693fc7c08 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -23004,7 +23004,8 @@ unsigned long wolfSSL_ERR_peek_error_line_data(const char **file, int *line, if (ret == SSL_NO_PEM_HEADER) return (ERR_LIB_PEM << 24) | PEM_R_NO_START_LINE; if (ret != WANT_READ && ret != WANT_WRITE && - ret != ZERO_RETURN && ret != SSL_ERROR_ZERO_RETURN) + ret != ZERO_RETURN && ret != SSL_ERROR_ZERO_RETURN && + ret != SOCKET_PEER_CLOSED_E && ret != SOCKET_ERROR_E) break; wc_RemoveErrorNode(-1); diff --git a/wolfssl/internal.h b/wolfssl/internal.h index 2fb249f56..e86cdb3a5 100644 --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -1059,7 +1059,7 @@ enum Misc { MAX_WOLFSSL_FILE_SIZE = 1024 * 1024 * 4, /* 4 mb file size alloc limit */ #if defined(HAVE_EX_DATA) || defined(FORTRESS) - MAX_EX_DATA = 4, /* allow for four items of ex_data */ + MAX_EX_DATA = 5, /* allow for five items of ex_data */ #endif MAX_X509_SIZE = 2048, /* max static x509 buffer size */ From 431f36352067c839ed6abfd829588940006c11e4 Mon Sep 17 00:00:00 2001 From: David Garske Date: Fri, 3 Mar 2017 07:35:26 -0800 Subject: [PATCH 21/68] Better fixes for suppressing scan-build warning with normal math enabled. --- wolfcrypt/src/integer.c | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index c5026bf6d..380b5bccf 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -336,10 +336,6 @@ int mp_copy (mp_int * a, mp_int * b) } } - /* sanity check on destination */ - if (b->dp == NULL) - return MP_VAL; - /* zero b and copy the parameters over */ { mp_digit *tmpa, *tmpb; @@ -358,7 +354,7 @@ int mp_copy (mp_int * a, mp_int * b) } /* clear high digits */ - for (; n < b->used; n++) { + for (; n < b->used && b->dp; n++) { *tmpb++ = 0; } } @@ -3776,7 +3772,7 @@ int s_mp_mul_high_digs (mp_int * a, mp_int * b, mp_int * c, int digs) pa = a->used; pb = b->used; - for (ix = 0; ix < pa; ix++) { + for (ix = 0; ix < pa && a->dp; ix++) { /* clear the carry */ u = 0; @@ -3849,7 +3845,7 @@ int fast_s_mp_mul_high_digs (mp_int * a, mp_int * b, mp_int * c, int digs) /* number of output digits to produce */ pa = a->used + b->used; _W = 0; - for (ix = digs; ix < pa; ix++) { + for (ix = digs; ix < pa && a->dp; ix++) { int tx, ty, iy; mp_digit *tmpx, *tmpy; From 7bcd26e32192375339365b93f1c7f47104e0d34e Mon Sep 17 00:00:00 2001 From: toddouska Date: Fri, 3 Mar 2017 11:30:38 -0800 Subject: [PATCH 22/68] add check dh public key to agree() --- wolfcrypt/src/dh.c | 56 +++++++++++++++++++++++++++++++++ wolfcrypt/src/error.c | 3 ++ wolfssl/wolfcrypt/dh.h | 1 + wolfssl/wolfcrypt/error-crypt.h | 1 + 4 files changed, 61 insertions(+) diff --git a/wolfcrypt/src/dh.c b/wolfcrypt/src/dh.c index 4d4427652..4bddf485b 100644 --- a/wolfcrypt/src/dh.c +++ b/wolfcrypt/src/dh.c @@ -184,6 +184,57 @@ int wc_DhGenerateKeyPair(DhKey* key, WC_RNG* rng, byte* priv, word32* privSz, return (ret != 0) ? ret : GeneratePublic(key, priv, *privSz, pub, pubSz); } + +/* Check DH Public Key for invalid numbers + * + * key DH key group parameters. + * pub Public Key. + * pubSz Public Key size. + * + * returns 0 on success or error code + */ +int wc_DhCheckPubKey(DhKey* key, const byte* pub, word32 pubSz) +{ + int ret = 0; + + mp_int x; + mp_int y; + + if (key == NULL || pub == NULL) { + return BAD_FUNC_ARG; + } + + if (mp_init_multi(&x, &y, NULL, NULL, NULL, NULL) != MP_OKAY) { + return MP_INIT_E; + } + + if (mp_read_unsigned_bin(&x, pub, pubSz) != MP_OKAY) { + ret = MP_READ_E; + } + + /* pub should not be 0 or 1 */ + if (ret == 0 && mp_cmp_d(&x, 2) == MP_LT) { + ret = MP_CMP_E; + } + + /* pub shouldn't be greater than or equal to p - 1 */ + if (ret == 0 && mp_copy(&key->p, &y) != MP_OKAY) { + ret = MP_INIT_E; + } + if (ret == 0 && mp_sub_d(&y, 2, &y) != MP_OKAY) { + ret = MP_SUB_E; + } + if (ret == 0 && mp_cmp(&x, &y) == MP_GT) { + ret = MP_CMP_E; + } + + mp_clear(&y); + mp_clear(&x); + + return ret; +} + + int wc_DhAgree(DhKey* key, byte* agree, word32* agreeSz, const byte* priv, word32 privSz, const byte* otherPub, word32 pubSz) { @@ -193,6 +244,11 @@ int wc_DhAgree(DhKey* key, byte* agree, word32* agreeSz, const byte* priv, mp_int y; mp_int z; + if (wc_DhCheckPubKey(key, otherPub, pubSz) != 0) { + WOLFSSL_MSG("wc_DhAgree wc_DhCheckPubKey failed"); + return DH_CHECK_PUB_E; + } + if (mp_init_multi(&x, &y, &z, 0, 0, 0) != MP_OKAY) return MP_INIT_E; diff --git a/wolfcrypt/src/error.c b/wolfcrypt/src/error.c index be37b7275..d49734474 100644 --- a/wolfcrypt/src/error.c +++ b/wolfcrypt/src/error.c @@ -416,6 +416,9 @@ const char* wc_GetErrorString(int error) case ECC_CDH_KAT_FIPS_E: return "wolfcrypt FIPS ECC CDH Known Answer Test Failure"; + case DH_CHECK_PUB_E: + return "DH Check Public Key failure"; + default: return "unknown error number"; diff --git a/wolfssl/wolfcrypt/dh.h b/wolfssl/wolfcrypt/dh.h index 332d460f0..2410ab777 100644 --- a/wolfssl/wolfcrypt/dh.h +++ b/wolfssl/wolfcrypt/dh.h @@ -56,6 +56,7 @@ WOLFSSL_API int wc_DhSetKey(DhKey* key, const byte* p, word32 pSz, const byte* g word32 gSz); WOLFSSL_API int wc_DhParamsLoad(const byte* input, word32 inSz, byte* p, word32* pInOutSz, byte* g, word32* gInOutSz); +WOLFSSL_API int wc_DhCheckPubKey(DhKey* key, const byte* pub, word32 pubSz); #ifdef __cplusplus diff --git a/wolfssl/wolfcrypt/error-crypt.h b/wolfssl/wolfcrypt/error-crypt.h index 8a5080d57..8e0c73230 100644 --- a/wolfssl/wolfcrypt/error-crypt.h +++ b/wolfssl/wolfcrypt/error-crypt.h @@ -183,6 +183,7 @@ enum { BAD_KEYWRAP_IV_E = -240, /* Decrypted AES key wrap IV incorrect */ WC_CLEANUP_E = -241, /* wolfcrypt cleanup failed */ ECC_CDH_KAT_FIPS_E = -242, /* ECC CDH Known Answer Test failure */ + DH_CHECK_PUB_E = -243, /* DH Check Pub Key error */ MIN_CODE_E = -300 /* errors -101 - -299 */ From a348898e96b46d5edb595180f0df7bf3d9be7c1d Mon Sep 17 00:00:00 2001 From: toddouska Date: Fri, 3 Mar 2017 11:42:24 -0800 Subject: [PATCH 23/68] add AUTH_SZ size check to ti and armv8 ports --- wolfcrypt/src/port/arm/armv8-aes.c | 5 +++++ wolfcrypt/src/port/ti/ti-aes.c | 3 +++ 2 files changed, 8 insertions(+) diff --git a/wolfcrypt/src/port/arm/armv8-aes.c b/wolfcrypt/src/port/arm/armv8-aes.c index e59bd2571..c189b3eda 100644 --- a/wolfcrypt/src/port/arm/armv8-aes.c +++ b/wolfcrypt/src/port/arm/armv8-aes.c @@ -2532,6 +2532,11 @@ int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz, return BAD_FUNC_ARG; } + if (authTagSz < WOLFSSL_MIN_AUTH_TAG_SZ) { + WOLFSSL_MSG("GcmEncrypt authTagSz too small error"); + return BAD_FUNC_ARG; + } + switch (aes->rounds) { case 10: return Aes128GcmEncrypt(aes, out, in, sz, iv, ivSz, diff --git a/wolfcrypt/src/port/ti/ti-aes.c b/wolfcrypt/src/port/ti/ti-aes.c index 5b982c41d..cd8d2eed9 100644 --- a/wolfcrypt/src/port/ti/ti-aes.c +++ b/wolfcrypt/src/port/ti/ti-aes.c @@ -490,6 +490,9 @@ WOLFSSL_API int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz byte* authTag, word32 authTagSz, const byte* authIn, word32 authInSz) { + if (authTagSz < WOLFSSL_MIN_AUTH_TAG_SZ) { + return BAD_FUNC_ARG; + } return AesAuthEncrypt(aes, out, in, sz, iv, ivSz, authTag, authTagSz, authIn, authInSz, AES_CFG_MODE_GCM_HY0CALC) ; } From ae6fbb220f73ecafcfa2fe56085e4d3030f29ec7 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Mon, 6 Mar 2017 10:58:25 +1000 Subject: [PATCH 24/68] Pass the context to statusCb (needed in Nginx 1.10.3) --- src/ocsp.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ocsp.c b/src/ocsp.c index efbae86c8..bcf973b54 100644 --- a/src/ocsp.c +++ b/src/ocsp.c @@ -404,7 +404,7 @@ int CheckOcspRequest(WOLFSSL_OCSP* ocsp, OcspRequest* ocspRequest, #ifdef WOLFSSL_NGINX if (ocsp->statusCb != NULL && ocspRequest->ssl != NULL) { - ret = ocsp->statusCb((WOLFSSL*)ocspRequest->ssl, NULL); + ret = ocsp->statusCb((WOLFSSL*)ocspRequest->ssl, ocsp->cm->ocspIOCtx); if (ret == 0) { ret = wolfSSL_get_ocsp_response((WOLFSSL*)ocspRequest->ssl, &response); From be42a575dabc1e4fed295955b3d2d55524dc86d6 Mon Sep 17 00:00:00 2001 From: David Garske Date: Mon, 6 Mar 2017 13:19:52 -0800 Subject: [PATCH 25/68] Fix additional integer.c report of possible use of NULL dp (after normal math performance improvement to defer dp pointer alloc commit bdbb98ed20620618eebff003adc11fba4dee3041 --- wolfcrypt/src/integer.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index 380b5bccf..ce6353ecc 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -4133,7 +4133,7 @@ static const int lnz[16] = { int mp_cnt_lsb(mp_int *a) { int x; - mp_digit q, qq; + mp_digit q = 0, qq; /* easy out */ if (mp_iszero(a) == MP_YES) { @@ -4142,7 +4142,8 @@ int mp_cnt_lsb(mp_int *a) /* scan lower digits until non-zero */ for (x = 0; x < a->used && a->dp[x] == 0; x++) {} - q = a->dp[x]; + if (a->dp) + q = a->dp[x]; x *= DIGIT_BIT; /* now scan this digit until a 1 is found */ From e115205d18319be9a7228d23efa144dd1b33194b Mon Sep 17 00:00:00 2001 From: David Garske Date: Tue, 7 Mar 2017 13:45:02 -0800 Subject: [PATCH 26/68] Fix to reduce ECC memory usage when async crypt is not enabled. Fix uses local for r and s instead of key->r and key->s. --- wolfcrypt/src/ecc.c | 109 +++++++++++++++++++++++++++------------- wolfssl/wolfcrypt/ecc.h | 3 +- 2 files changed, 74 insertions(+), 38 deletions(-) diff --git a/wolfcrypt/src/ecc.c b/wolfcrypt/src/ecc.c index 019b96366..45ad700dd 100644 --- a/wolfcrypt/src/ecc.c +++ b/wolfcrypt/src/ecc.c @@ -2976,22 +2976,29 @@ int wc_ecc_make_key(WC_RNG* rng, int keysize, ecc_key* key) return wc_ecc_make_key_ex(rng, keysize, key, ECC_CURVE_DEF); } -static void wc_ecc_free_rs(ecc_key* key) +static INLINE void wc_ecc_free_rs(ecc_key* key, mp_int** r, mp_int** s) { - if (key->r) { + if (*r) { #ifndef USE_FAST_MATH - mp_clear(key->r); + mp_clear(*r); #endif - XFREE(key->r, key->heap, DYNAMIC_TYPE_BIGINT); + #ifdef WOLFSSL_ASYNC_CRYPT + XFREE(*r, key->heap, DYNAMIC_TYPE_BIGINT); key->r = NULL; - } - if (key->s) { - #ifndef USE_FAST_MATH - mp_clear(key->s); #endif - XFREE(key->s, key->heap, DYNAMIC_TYPE_BIGINT); - key->s = NULL; + *r = NULL; } + if (*s) { + #ifndef USE_FAST_MATH + mp_clear(*s); + #endif + #ifdef WOLFSSL_ASYNC_CRYPT + XFREE(*s, key->heap, DYNAMIC_TYPE_BIGINT); + key->s = NULL; + #endif + *s = NULL; + } + (void)key; } /* Setup dynamic pointers if using normal math for proper freeing */ @@ -3081,6 +3088,12 @@ int wc_ecc_sign_hash(const byte* in, word32 inlen, byte* out, word32 *outlen, WC_RNG* rng, ecc_key* key) { int err; + mp_int *r = NULL, *s = NULL; +#ifndef WOLFSSL_ASYNC_CRYPT + mp_int r_lcl, s_lcl; + r = &r_lcl; + s = &s_lcl; +#endif if (in == NULL || out == NULL || outlen == NULL || key == NULL || rng == NULL) { @@ -3111,24 +3124,28 @@ int wc_ecc_sign_hash(const byte* in, word32 inlen, byte* out, word32 *outlen, case ECC_STATE_NONE: case ECC_STATE_SIGN_DO: key->state = ECC_STATE_SIGN_DO; - if (key->r == NULL) - key->r = (mp_int*)XMALLOC(sizeof(mp_int), key->heap, + + #ifdef WOLFSSL_ASYNC_CRYPT + if (r == NULL) + r = (mp_int*)XMALLOC(sizeof(mp_int), key->heap, DYNAMIC_TYPE_BIGINT); - if (key->s == NULL) - key->s = (mp_int*)XMALLOC(sizeof(mp_int), key->heap, + if (s == NULL) + s = (mp_int*)XMALLOC(sizeof(mp_int), key->heap, DYNAMIC_TYPE_BIGINT); - if (key->r == NULL || key->s == NULL) { + if (r == NULL || s == NULL) { err = MEMORY_E; break; } - XMEMSET(key->r, 0, sizeof(mp_int)); - XMEMSET(key->s, 0, sizeof(mp_int)); + key->r = r; + key->s = s; + #endif + XMEMSET(r, 0, sizeof(mp_int)); + XMEMSET(s, 0, sizeof(mp_int)); - if ((err = mp_init_multi(key->r, key->s, NULL, NULL, NULL, NULL)) + if ((err = mp_init_multi(r, s, NULL, NULL, NULL, NULL)) != MP_OKAY) { break; } - #ifdef WOLFSSL_ATECC508A /* Check args */ if (inlen != ATECC_KEY_SIZE || *outlen < SIGN_RSP_SIZE) { @@ -3142,23 +3159,23 @@ int wc_ecc_sign_hash(const byte* in, word32 inlen, byte* out, word32 *outlen, } /* Load R and S */ - err = mp_read_unsigned_bin(key->r, &out[0], ATECC_KEY_SIZE); + err = mp_read_unsigned_bin(r, &out[0], ATECC_KEY_SIZE); if (err != MP_OKAY) { return err; } - err = mp_read_unsigned_bin(key->s, &out[ATECC_KEY_SIZE], ATECC_KEY_SIZE); + err = mp_read_unsigned_bin(s, &out[ATECC_KEY_SIZE], ATECC_KEY_SIZE); if (err != MP_OKAY) { return err; } /* Check for zeros */ - if (mp_iszero(key->r) || mp_iszero(key->s)) { + if (mp_iszero(r) || mp_iszero(s)) { return MP_ZERO_E; } #else - err = wc_ecc_sign_hash_ex(in, inlen, rng, key, key->r, key->s); + err = wc_ecc_sign_hash_ex(in, inlen, rng, key, r, s); if (err < 0) { break; } @@ -3169,8 +3186,13 @@ int wc_ecc_sign_hash(const byte* in, word32 inlen, byte* out, word32 *outlen, case ECC_STATE_SIGN_ENCODE: key->state = ECC_STATE_SIGN_ENCODE; + #ifdef WOLFSSL_ASYNC_CRYPT + r = key->r; + s = key->s; + #endif + /* encoded with DSA header */ - err = StoreECC_DSA_Sig(out, outlen, key->r, key->s); + err = StoreECC_DSA_Sig(out, outlen, r, s); break; default: @@ -3183,7 +3205,7 @@ int wc_ecc_sign_hash(const byte* in, word32 inlen, byte* out, word32 *outlen, return err; } - wc_ecc_free_rs(key); + wc_ecc_free_rs(key, &r, &s); key->state = ECC_STATE_NONE; @@ -3323,8 +3345,8 @@ void wc_ecc_free(ecc_key* key) if (key->asyncDev.marker == WOLFSSL_ASYNC_MARKER_RSA) { wolfAsync_DevCtxFree(&key->asyncDev); } + wc_ecc_free_rs(key, &key->r, &key->s); #endif - wc_ecc_free_rs(key); #ifdef WOLFSSL_ATECC508A atmel_ecc_free(key->slot); @@ -3594,6 +3616,12 @@ int wc_ecc_verify_hash(const byte* sig, word32 siglen, const byte* hash, word32 hashlen, int* stat, ecc_key* key) { int err; + mp_int *r = NULL, *s = NULL; +#ifndef WOLFSSL_ASYNC_CRYPT + mp_int r_lcl, s_lcl; + r = &r_lcl; + s = &s_lcl; +#endif if (sig == NULL || hash == NULL || stat == NULL || key == NULL) { return ECC_BAD_ARG_E; @@ -3631,20 +3659,24 @@ int wc_ecc_verify_hash(const byte* sig, word32 siglen, const byte* hash, * If either of those don't allocate correctly, none of * the rest of this function will execute, and everything * gets cleaned up at the end. */ - if (key->r == NULL) - key->r = (mp_int*)XMALLOC(sizeof(mp_int), key->heap, + #ifdef WOLFSSL_ASYNC_CRYPT + if (r == NULL) + r = (mp_int*)XMALLOC(sizeof(mp_int), key->heap, DYNAMIC_TYPE_BIGINT); - if (key->s == NULL) - key->s = (mp_int*)XMALLOC(sizeof(mp_int), key->heap, + if (s == NULL) + s = (mp_int*)XMALLOC(sizeof(mp_int), key->heap, DYNAMIC_TYPE_BIGINT); - if (key->r == NULL || key->s == NULL) { + if (r == NULL || s == NULL) { err = MEMORY_E; break; } - XMEMSET(key->r, 0, sizeof(mp_int)); - XMEMSET(key->s, 0, sizeof(mp_int)); + key->r = r; + key->s = s; + #endif + XMEMSET(r, 0, sizeof(mp_int)); + XMEMSET(s, 0, sizeof(mp_int)); /* decode DSA header */ - err = DecodeECC_DSA_Sig(sig, siglen, key->r, key->s); + err = DecodeECC_DSA_Sig(sig, siglen, r, s); if (err < 0) { break; } @@ -3653,7 +3685,12 @@ int wc_ecc_verify_hash(const byte* sig, word32 siglen, const byte* hash, case ECC_STATE_VERIFY_DO: key->state = ECC_STATE_VERIFY_DO; - err = wc_ecc_verify_hash_ex(key->r, key->s, hash, hashlen, stat, + #ifdef WOLFSSL_ASYNC_CRYPT + r = key->r; + s = key->s; + #endif + + err = wc_ecc_verify_hash_ex(r, s, hash, hashlen, stat, key); if (err < 0) { break; @@ -3675,7 +3712,7 @@ int wc_ecc_verify_hash(const byte* sig, word32 siglen, const byte* hash, return err; } - wc_ecc_free_rs(key); + wc_ecc_free_rs(key, &r, &s); key->state = ECC_STATE_NONE; diff --git a/wolfssl/wolfcrypt/ecc.h b/wolfssl/wolfcrypt/ecc.h index 177d7003f..59e2edb0f 100644 --- a/wolfssl/wolfcrypt/ecc.h +++ b/wolfssl/wolfcrypt/ecc.h @@ -274,10 +274,9 @@ typedef struct ecc_key { ecc_point pubkey; /* public key */ mp_int k; /* private key */ #endif +#ifdef WOLFSSL_ASYNC_CRYPT mp_int* r; /* sign/verify temps */ mp_int* s; - -#ifdef WOLFSSL_ASYNC_CRYPT AsyncCryptDev asyncDev; #endif } ecc_key; From a0effa6329b531b6a735fb86e7378a2dfbb5ef09 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Wed, 8 Mar 2017 11:26:16 -0700 Subject: [PATCH 27/68] call mp_clear to match call to mp_init --- wolfcrypt/src/integer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index 9c45c7602..10134550e 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -4249,8 +4249,8 @@ static int mp_div_d (mp_int * a, mp_digit b, mp_int * c, mp_digit * d) if (c != NULL) { mp_clamp(&q); mp_exch(&q, c); - mp_clear(&q); } + mp_clear(&q); return res; } From a55ebb4c180030c5536598dc43d475b9c2dd074e Mon Sep 17 00:00:00 2001 From: David Garske Date: Wed, 8 Mar 2017 11:21:11 -0800 Subject: [PATCH 28/68] Fixes for building CRL with Windows. Refactor load_verify_buffer and LoadCRL to use new wc_ReadDir* functions. Added new directory/file API's: wc_ReadDirFirst(), wc_ReadDirNext(), wc_ReadDirClose(). Moved MAX_PATH and MAX_FILENAME_SZ to wc_port.h. Moved BAD_PATH_ERROR into error-crypt.h. The wc_ReadDir is only supported when NO_WOLFSSL_DIR and NO_FILESYSTEM are not defined. Add map to __FUNCTION__ macro in Windows with debug enabled (to resolve build error with VS and __func__ missing). Fix cast warning on response from EncodeOcspRequestExtensions. Fix for cast to call to BuildCertificateStatus. --- src/crl.c | 98 +++++++++++------------ src/internal.c | 4 +- src/ssl.c | 107 ++++--------------------- src/tls.c | 4 +- wolfcrypt/src/error.c | 3 + wolfcrypt/src/wc_port.c | 133 ++++++++++++++++++++++++++++++++ wolfssl/error-ssl.h | 2 +- wolfssl/internal.h | 1 - wolfssl/test.h | 4 - wolfssl/wolfcrypt/error-crypt.h | 1 + wolfssl/wolfcrypt/logging.h | 4 + wolfssl/wolfcrypt/wc_port.h | 41 +++++++++- 12 files changed, 245 insertions(+), 157 deletions(-) mode change 100644 => 100755 src/crl.c mode change 100644 => 100755 src/tls.c diff --git a/src/crl.c b/src/crl.c old mode 100644 new mode 100755 index 8d3729ec1..e4a876aad --- a/src/crl.c +++ b/src/crl.c @@ -34,11 +34,6 @@ #include #include -#ifndef NO_FILESYSTEM - #include - #include -#endif - #include #ifdef HAVE_CRL_MONITOR @@ -790,74 +785,62 @@ static int StartMonitorCRL(WOLFSSL_CRL* crl) #endif /* HAVE_CRL_MONITOR */ -#ifndef NO_FILESYSTEM +#if !defined(NO_FILESYSTEM) && !defined(NO_WOLFSSL_DIR) /* Load CRL path files of type, SSL_SUCCESS on ok */ int LoadCRL(WOLFSSL_CRL* crl, const char* path, int type, int monitor) { - struct dirent* entry; - DIR* dir; int ret = SSL_SUCCESS; + char* name = NULL; #ifdef WOLFSSL_SMALL_STACK - char* name; + ReadDirCtx* readCtx = NULL; #else - char name[MAX_FILENAME_SZ]; + ReadDirCtx readCtx[1]; #endif WOLFSSL_ENTER("LoadCRL"); if (crl == NULL) return BAD_FUNC_ARG; - dir = opendir(path); - if (dir == NULL) { - WOLFSSL_MSG("opendir path crl load failed"); - return BAD_PATH_ERROR; - } - #ifdef WOLFSSL_SMALL_STACK - name = (char*)XMALLOC(MAX_FILENAME_SZ, NULL, DYNAMIC_TYPE_TMP_BUFFER); + ReadDirCtx* readCtx = NULL; + readCtx = (char*)XMALLOC(sizeof(ReadDirCtx), ctx->heap, + DYNAMIC_TYPE_TMP_BUFFER); if (name == NULL) return MEMORY_E; #endif - while ( (entry = readdir(dir)) != NULL) { - struct stat s; - - XMEMSET(name, 0, MAX_FILENAME_SZ); - XSTRNCPY(name, path, MAX_FILENAME_SZ/2 - 2); - XSTRNCAT(name, "/", 1); - XSTRNCAT(name, entry->d_name, MAX_FILENAME_SZ/2); - - if (stat(name, &s) != 0) { - WOLFSSL_MSG("stat on name failed"); - continue; - } - if (s.st_mode & S_IFREG) { - - if (type == SSL_FILETYPE_PEM) { - if (XSTRSTR(entry->d_name, ".pem") == NULL) { - WOLFSSL_MSG("not .pem file, skipping"); - continue; - } - } - else { - if (XSTRSTR(entry->d_name, ".der") == NULL && - XSTRSTR(entry->d_name, ".crl") == NULL) { - - WOLFSSL_MSG("not .der or .crl file, skipping"); - continue; - } - } - - if (ProcessFile(NULL, name, type, CRL_TYPE, NULL, 0, crl) - != SSL_SUCCESS) { - WOLFSSL_MSG("CRL file load failed, continuing"); + /* try to load each regular file in path */ + ret = wc_ReadDirFirst(readCtx, path, &name); + while (ret == 0 && name) { + int skip = 0; + if (type == SSL_FILETYPE_PEM) { + if (XSTRSTR(name, ".pem") == NULL) { + WOLFSSL_MSG("not .pem file, skipping"); + skip = 1; } } + else { + if (XSTRSTR(name, ".der") == NULL && + XSTRSTR(name, ".crl") == NULL) + { + WOLFSSL_MSG("not .der or .crl file, skipping"); + skip = 1; + } + } + + if (!skip && ProcessFile(NULL, name, type, CRL_TYPE, NULL, 0, crl) + != SSL_SUCCESS) { + WOLFSSL_MSG("CRL file load failed, continuing"); + } + + ret = wc_ReadDirNext(readCtx, path, &name); } + wc_ReadDirClose(readCtx); + ret = SSL_SUCCESS; /* load failures not reported, for backwards compat */ #ifdef WOLFSSL_SMALL_STACK - XFREE(name, NULL, DYNAMIC_TYPE_TMP_BUFFER); + XFREE(readCtx, ctx->heap, DYNAMIC_TYPE_TMP_BUFFER); #endif if (monitor & WOLFSSL_CRL_MONITOR) { @@ -901,12 +884,21 @@ int LoadCRL(WOLFSSL_CRL* crl, const char* path, int type, int monitor) } } - closedir(dir); - return ret; } -#endif /* NO_FILESYSTEM */ +#else +int LoadCRL(WOLFSSL_CRL* crl, const char* path, int type, int monitor) +{ + (void)crl; + (void)path; + (void)type; + (void)monitor; + + /* stub for scenario where file system is not supported */ + return NOT_COMPILED_IN; +} +#endif /* !NO_FILESYSTEM && !NO_WOLFSSL_DIR */ #endif /* HAVE_CRL */ #endif /* !WOLFCRYPT_ONLY */ diff --git a/src/internal.c b/src/internal.c index e2aafa840..d9d454259 100644 --- a/src/internal.c +++ b/src/internal.c @@ -11201,7 +11201,7 @@ int SendCertificateStatus(WOLFSSL* ssl) if (responses[0].buffer) { if (ret == 0) ret = BuildCertificateStatus(ssl, status_type, - responses, i + 1); + responses, (byte)i + 1); for (i = 0; i < 1 + MAX_CHAIN_DEPTH; i++) if (responses[i].buffer) @@ -11713,8 +11713,6 @@ const char* wolfSSL_ERR_reason_error_string(unsigned long e) case NOT_CA_ERROR: return "Not a CA by basic constraint error"; - case BAD_PATH_ERROR: - return "Bad path for opendir error"; case BAD_CERT_MANAGER_ERROR: return "Bad Cert Manager error"; diff --git a/src/ssl.c b/src/ssl.c index 7951cc8bb..73ac73ea0 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -93,18 +93,6 @@ #include #endif -#ifndef NO_FILESYSTEM - #if !defined(USE_WINDOWS_API) && !defined(NO_WOLFSSL_DIR) \ - && !defined(EBSNET) - #include - #include - #endif - #ifdef EBSNET - #include "vfapi.h" - #include "vfile.h" - #endif -#endif /* NO_FILESYSTEM */ - #if defined(WOLFSSL_DTLS) && !defined(WOLFSSL_HAVE_MAX) #define WOLFSSL_HAVE_MAX @@ -5079,7 +5067,6 @@ int wolfSSL_CTX_load_verify_locations(WOLFSSL_CTX* ctx, const char* file, int ret = SSL_SUCCESS; WOLFSSL_ENTER("wolfSSL_CTX_load_verify_locations"); - (void)path; if (ctx == NULL || (file == NULL && path == NULL) ) return SSL_FAILURE; @@ -5088,94 +5075,30 @@ int wolfSSL_CTX_load_verify_locations(WOLFSSL_CTX* ctx, const char* file, ret = ProcessFile(ctx, file, SSL_FILETYPE_PEM, CA_TYPE, NULL, 0, NULL); if (ret == SSL_SUCCESS && path) { - /* try to load each regular file in path */ - #ifdef USE_WINDOWS_API - WIN32_FIND_DATAA FindFileData; - HANDLE hFind; + char* name = NULL; #ifdef WOLFSSL_SMALL_STACK - char* name = NULL; - #else - char name[MAX_FILENAME_SZ]; - #endif - - #ifdef WOLFSSL_SMALL_STACK - name = (char*)XMALLOC(MAX_FILENAME_SZ, NULL, DYNAMIC_TYPE_TMP_BUFFER); + ReadDirCtx* readCtx = NULL; + readCtx = (ReadDirCtx*)XMALLOC(sizeof(ReadDirCtx), ctx->heap, + DYNAMIC_TYPE_TMP_BUFFER); if (name == NULL) return MEMORY_E; - #endif - - XMEMSET(name, 0, MAX_FILENAME_SZ); - XSTRNCPY(name, path, MAX_FILENAME_SZ - 4); - XSTRNCAT(name, "\\*", 3); - - hFind = FindFirstFileA(name, &FindFileData); - if (hFind == INVALID_HANDLE_VALUE) { - WOLFSSL_MSG("FindFirstFile for path verify locations failed"); - #ifdef WOLFSSL_SMALL_STACK - XFREE(name, NULL, DYNAMIC_TYPE_TMP_BUFFER); - #endif - return BAD_PATH_ERROR; - } - - do { - if (FindFileData.dwFileAttributes != FILE_ATTRIBUTE_DIRECTORY) { - XSTRNCPY(name, path, MAX_FILENAME_SZ/2 - 3); - XSTRNCAT(name, "\\", 2); - XSTRNCAT(name, FindFileData.cFileName, MAX_FILENAME_SZ/2); - - ret = ProcessFile(ctx, name, SSL_FILETYPE_PEM, CA_TYPE, - NULL, 0, NULL); - } - } while (ret == SSL_SUCCESS && FindNextFileA(hFind, &FindFileData)); - - #ifdef WOLFSSL_SMALL_STACK - XFREE(name, NULL, DYNAMIC_TYPE_TMP_BUFFER); - #endif - - FindClose(hFind); - #elif !defined(NO_WOLFSSL_DIR) - struct dirent* entry; - DIR* dir = opendir(path); - #ifdef WOLFSSL_SMALL_STACK - char* name = NULL; #else - char name[MAX_FILENAME_SZ]; + ReadDirCtx readCtx[1]; #endif - if (dir == NULL) { - WOLFSSL_MSG("opendir path verify locations failed"); - return BAD_PATH_ERROR; + /* try to load each regular file in path */ + ret = wc_ReadDirFirst(readCtx, path, &name); + while (ret == 0 && name) { + ret = ProcessFile(ctx, name, SSL_FILETYPE_PEM, CA_TYPE, + NULL, 0, NULL); + if (ret != SSL_SUCCESS) + break; + ret = wc_ReadDirNext(readCtx, path, &name); } + wc_ReadDirClose(readCtx); #ifdef WOLFSSL_SMALL_STACK - name = (char*)XMALLOC(MAX_FILENAME_SZ, NULL, DYNAMIC_TYPE_TMP_BUFFER); - if (name == NULL) { - closedir(dir); - return MEMORY_E; - } - #endif - - while ( ret == SSL_SUCCESS && (entry = readdir(dir)) != NULL) { - struct stat s; - - XMEMSET(name, 0, MAX_FILENAME_SZ); - XSTRNCPY(name, path, MAX_FILENAME_SZ/2 - 2); - XSTRNCAT(name, "/", 1); - XSTRNCAT(name, entry->d_name, MAX_FILENAME_SZ/2); - - if (stat(name, &s) != 0) { - WOLFSSL_MSG("stat on name failed"); - ret = BAD_PATH_ERROR; - } else if (s.st_mode & S_IFREG) - ret = ProcessFile(ctx, name, SSL_FILETYPE_PEM, CA_TYPE, - NULL, 0, NULL); - } - - #ifdef WOLFSSL_SMALL_STACK - XFREE(name, NULL, DYNAMIC_TYPE_TMP_BUFFER); - #endif - - closedir(dir); + XFREE(readCtx, ctx->heap, DYNAMIC_TYPE_TMP_BUFFER); #endif } diff --git a/src/tls.c b/src/tls.c old mode 100644 new mode 100755 index 3aa5a781b..3a39038bd --- a/src/tls.c +++ b/src/tls.c @@ -2044,7 +2044,7 @@ static word16 TLSX_CSR_Write(CertificateStatusRequest* csr, byte* output, /* request extensions */ if (csr->request.ocsp.nonceSz) - length = EncodeOcspRequestExtensions( + length = (word16)EncodeOcspRequestExtensions( &csr->request.ocsp, output + offset + OPAQUE16_LEN, OCSP_NONCE_EXT_SZ); @@ -2397,7 +2397,7 @@ static word16 TLSX_CSR2_Write(CertificateStatusRequestItemV2* csr2, length = 0; if (csr2->request.ocsp[0].nonceSz) - length = EncodeOcspRequestExtensions( + length = (word16)EncodeOcspRequestExtensions( &csr2->request.ocsp[0], output + offset + OPAQUE16_LEN, OCSP_NONCE_EXT_SZ); diff --git a/wolfcrypt/src/error.c b/wolfcrypt/src/error.c index d49734474..9429e4481 100644 --- a/wolfcrypt/src/error.c +++ b/wolfcrypt/src/error.c @@ -419,6 +419,9 @@ const char* wc_GetErrorString(int error) case DH_CHECK_PUB_E: return "DH Check Public Key failure"; + case BAD_PATH_ERROR: + return "Bad path for opendir error"; + default: return "unknown error number"; diff --git a/wolfcrypt/src/wc_port.c b/wolfcrypt/src/wc_port.c index 532bf107e..23f002491 100644 --- a/wolfcrypt/src/wc_port.c +++ b/wolfcrypt/src/wc_port.c @@ -28,6 +28,7 @@ #include #include #include +#include /* IPP header files for library initialization */ #ifdef HAVE_FAST_RSA @@ -126,6 +127,138 @@ int wolfCrypt_Cleanup(void) return ret; } +#if !defined(NO_FILESYSTEM) && !defined(NO_WOLFSSL_DIR) + +/* File Handling Helpers */ +int wc_ReadDirFirst(ReadDirCtx* ctx, const char* path, char** name) +{ + int ret = 0; + + if (name) + *name = NULL; + + if (ctx == NULL || path == NULL) { + return BAD_FUNC_ARG; + } + + XMEMSET(ctx->name, 0, MAX_FILENAME_SZ); + +#ifdef USE_WINDOWS_API + XSTRNCPY(ctx->name, path, MAX_FILENAME_SZ - 4); + XSTRNCAT(ctx->name, "\\*", 3); + + ctx->hFind = FindFirstFileA(ctx->name, &ctx->FindFileData); + if (ctx->hFind == INVALID_HANDLE_VALUE) { + WOLFSSL_MSG("FindFirstFile for path verify locations failed"); + return BAD_PATH_ERROR; + } + + do { + if (ctx->FindFileData.dwFileAttributes != FILE_ATTRIBUTE_DIRECTORY) { + XSTRNCPY(ctx->name, path, MAX_FILENAME_SZ/2 - 3); + XSTRNCAT(ctx->name, "\\", 2); + XSTRNCAT(ctx->name, ctx->FindFileData.cFileName, MAX_FILENAME_SZ/2); + if (name) + *name = ctx->name; + return 0; + } + } while (FindNextFileA(ctx->hFind, &ctx->FindFileData)); +#else + ctx->dir = opendir(path); + if (ctx->dir == NULL) { + WOLFSSL_MSG("opendir path verify locations failed"); + return BAD_PATH_ERROR; + } + + while ((ctx->entry = readdir(ctx->dir)) != NULL) { + XSTRNCPY(ctx->name, path, MAX_FILENAME_SZ/2 - 2); + XSTRNCAT(ctx->name, "/", 1); + XSTRNCAT(ctx->name, ctx->entry->d_name, MAX_FILENAME_SZ/2); + + if (stat(ctx->name, &ctx->s) != 0) { + WOLFSSL_MSG("stat on name failed"); + ret = BAD_PATH_ERROR; + break; + } else if (ctx->s.st_mode & S_IFREG) { + if (name) + *name = ctx->name; + return 0; + } + } +#endif + wc_ReadDirClose(ctx); + + return ret; +} + +int wc_ReadDirNext(ReadDirCtx* ctx, const char* path, char** name) +{ + int ret = -1; + + if (name) + *name = NULL; + + if (ctx == NULL || path == NULL) { + return BAD_FUNC_ARG; + } + + XMEMSET(ctx->name, 0, MAX_FILENAME_SZ); + +#ifdef USE_WINDOWS_API + while (FindNextFileA(ctx->hFind, &ctx->FindFileData)) { + if (ctx->FindFileData.dwFileAttributes != FILE_ATTRIBUTE_DIRECTORY) { + XSTRNCPY(ctx->name, path, MAX_FILENAME_SZ/2 - 3); + XSTRNCAT(ctx->name, "\\", 2); + XSTRNCAT(ctx->name, ctx->FindFileData.cFileName, MAX_FILENAME_SZ/2); + if (name) + *name = ctx->name; + return 0; + } + } +#else + while ((ctx->entry = readdir(ctx->dir)) != NULL) { + XSTRNCPY(ctx->name, path, MAX_FILENAME_SZ/2 - 2); + XSTRNCAT(ctx->name, "/", 1); + XSTRNCAT(ctx->name, ctx->entry->d_name, MAX_FILENAME_SZ/2); + + if (stat(ctx->name, &ctx->s) != 0) { + WOLFSSL_MSG("stat on name failed"); + ret = BAD_PATH_ERROR; + break; + } else if (ctx->s.st_mode & S_IFREG) { + if (name) + *name = ctx->name; + return 0; + } + } +#endif + + wc_ReadDirClose(ctx); + + return ret; +} + +void wc_ReadDirClose(ReadDirCtx* ctx) +{ + if (ctx == NULL) { + return; + } + +#ifdef USE_WINDOWS_API + if (ctx->hFind != INVALID_HANDLE_VALUE) { + FindClose(ctx->hFind); + ctx->hFind = INVALID_HANDLE_VALUE; + } +#else + if (ctx->dir) { + closedir(ctx->dir); + ctx->dir = NULL; + } +#endif +} + +#endif /* !NO_FILESYSTEM && !NO_WOLFSSL_DIR */ + wolfSSL_Mutex* wc_InitAndAllocMutex() { diff --git a/wolfssl/error-ssl.h b/wolfssl/error-ssl.h index 77d964e88..38f4a7e93 100644 --- a/wolfssl/error-ssl.h +++ b/wolfssl/error-ssl.h @@ -90,7 +90,7 @@ enum wolfSSL_ErrorCodes { ECC_EXPORT_ERROR = -354, /* Bad ECC Export Key */ ECC_SHARED_ERROR = -355, /* Bad ECC Shared Secret */ NOT_CA_ERROR = -357, /* Not a CA cert error */ - BAD_PATH_ERROR = -358, /* Bad path for opendir */ + BAD_CERT_MANAGER_ERROR = -359, /* Bad Cert Manager */ OCSP_CERT_REVOKED = -360, /* OCSP Certificate revoked */ CRL_CERT_REVOKED = -361, /* CRL Certificate revoked */ diff --git a/wolfssl/internal.h b/wolfssl/internal.h index a752edeee..63d0025b0 100644 --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -1064,7 +1064,6 @@ enum Misc { MAX_X509_SIZE = 2048, /* max static x509 buffer size */ CERT_MIN_SIZE = 256, /* min PEM cert size with header/footer */ - MAX_FILENAME_SZ = 256, /* max file name length */ FILE_BUFFER_SIZE = 1024, /* default static file buffer size for input, will use dynamic buffer if not big enough */ diff --git a/wolfssl/test.h b/wolfssl/test.h index e0b03c3b3..dd650e4ef 100644 --- a/wolfssl/test.h +++ b/wolfssl/test.h @@ -1285,10 +1285,6 @@ static INLINE void CaCb(unsigned char* der, int sz, int type) /* Wolf Root Directory Helper */ /* KEIL-RL File System does not support relative directory */ #if !defined(WOLFSSL_MDK_ARM) && !defined(WOLFSSL_KEIL_FS) && !defined(WOLFSSL_TIRTOS) - #ifndef MAX_PATH - #define MAX_PATH 256 - #endif - /* Maximum depth to search for WolfSSL root */ #define MAX_WOLF_ROOT_DEPTH 5 diff --git a/wolfssl/wolfcrypt/error-crypt.h b/wolfssl/wolfcrypt/error-crypt.h index 8e0c73230..075336911 100644 --- a/wolfssl/wolfcrypt/error-crypt.h +++ b/wolfssl/wolfcrypt/error-crypt.h @@ -184,6 +184,7 @@ enum { WC_CLEANUP_E = -241, /* wolfcrypt cleanup failed */ ECC_CDH_KAT_FIPS_E = -242, /* ECC CDH Known Answer Test failure */ DH_CHECK_PUB_E = -243, /* DH Check Pub Key error */ + BAD_PATH_ERROR = -244, /* Bad path for opendir */ MIN_CODE_E = -300 /* errors -101 - -299 */ diff --git a/wolfssl/wolfcrypt/logging.h b/wolfssl/wolfcrypt/logging.h index c8f9a657a..233e0c20d 100644 --- a/wolfssl/wolfcrypt/logging.h +++ b/wolfssl/wolfcrypt/logging.h @@ -60,6 +60,10 @@ WOLFSSL_API int wolfSSL_SetLoggingCb(wolfSSL_Logging_cb log_function); #endif /* defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) */ #ifdef DEBUG_WOLFSSL + #if defined ( WIN32 ) + #define __func__ __FUNCTION__ + #endif + /* a is prepended to m and b is appended, creating a log msg a + m + b */ #define WOLFSSL_LOG_CAT(a, m, b) #a " " m " " #b diff --git a/wolfssl/wolfcrypt/wc_port.h b/wolfssl/wolfcrypt/wc_port.h index 8d673c6c0..d12c16e5d 100644 --- a/wolfssl/wolfcrypt/wc_port.h +++ b/wolfssl/wolfcrypt/wc_port.h @@ -192,6 +192,9 @@ WOLFSSL_API int wolfCrypt_Cleanup(void); #ifndef NO_FILESYSTEM #if defined(EBSNET) + #include "vfapi.h" + #include "vfile.h" + #define XFILE int #define XFOPEN(NAME, MODE) vf_open((const char *)NAME, VO_RDONLY, 0); #define XFSEEK vf_lseek @@ -202,6 +205,7 @@ WOLFSSL_API int wolfCrypt_Cleanup(void); #define XFCLOSE vf_close #define XSEEK_END VSEEK_END #define XBADFILE -1 + #define XFGETS(b,s,f) -2 /* Not ported yet */ #elif defined(LSR_FS) #include #define XFILE struct fs_file* @@ -214,6 +218,7 @@ WOLFSSL_API int wolfCrypt_Cleanup(void); #define XFCLOSE fs_close #define XSEEK_END 0 #define XBADFILE NULL + #define XFGETS(b,s,f) -2 /* Not ported yet */ #elif defined(FREESCALE_MQX) || defined(FREESCALE_KSDK_MQX) #define XFILE MQX_FILE_PTR #define XFOPEN fopen @@ -225,6 +230,7 @@ WOLFSSL_API int wolfCrypt_Cleanup(void); #define XFCLOSE fclose #define XSEEK_END IO_SEEK_END #define XBADFILE NULL + #define XFGETS fgets #elif defined(MICRIUM) #include #define XFILE FS_FILE* @@ -237,6 +243,7 @@ WOLFSSL_API int wolfCrypt_Cleanup(void); #define XFCLOSE fs_fclose #define XSEEK_END FS_SEEK_END #define XBADFILE NULL + #define XFGETS(b,s,f) -2 /* Not ported yet */ #else /* stdio, default case */ #include @@ -255,9 +262,41 @@ WOLFSSL_API int wolfCrypt_Cleanup(void); #define XFCLOSE fclose #define XSEEK_END SEEK_END #define XBADFILE NULL + #define XFGETS fgets + + #if !defined(USE_WINDOWS_API) && !defined(NO_WOLFSSL_DIR) + #include + #include + #include + #endif #endif -#endif /* NO_FILESYSTEM */ + #ifndef MAX_FILENAME_SZ + #define MAX_FILENAME_SZ 256 /* max file name length */ + #endif + #ifndef MAX_PATH + #define MAX_PATH 256 + #endif + +#if !defined(NO_WOLFSSL_DIR) + typedef struct ReadDirCtx { + #ifdef USE_WINDOWS_API + WIN32_FIND_DATAA FindFileData; + HANDLE hFind; + #else + struct dirent* entry; + DIR* dir; + struct stat s; + #endif + char name[MAX_FILENAME_SZ]; + } ReadDirCtx; + + WOLFSSL_API int wc_ReadDirFirst(ReadDirCtx* ctx, const char* path, char** name); + WOLFSSL_API int wc_ReadDirNext(ReadDirCtx* ctx, const char* path, char** name); + WOLFSSL_API void wc_ReadDirClose(ReadDirCtx* ctx); +#endif /* !NO_WOLFSSL_DIR */ + +#endif /* !NO_FILESYSTEM */ /* Windows API defines its own min() macro. */ From fd50fd8a3e82f6afa8a23e30d6614d4beb7ffc88 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Wed, 8 Mar 2017 16:40:07 -0700 Subject: [PATCH 29/68] Add error case for critical Subject Key ID extension --- wolfcrypt/src/asn.c | 12 ++++++++++++ wolfcrypt/src/error.c | 2 +- 2 files changed, 13 insertions(+), 1 deletion(-) diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 509364825..c46c1512a 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -5300,6 +5300,18 @@ static int DecodeCertExtensions(DecodedCert* cert) #ifdef OPENSSL_EXTRA cert->extSubjKeyIdCrit = critical; #endif + #ifndef WOLFSSL_ALLOW_CRIT_SKID + /* This check is added due to RFC 5280 section 4.2.1.2 + * stating that conforming CA's must mark this extension + * as non-critical. When parsing extensions check that + * certificate was made in compliance with this. */ + if (critical) { + WOLFSSL_MSG("Critical Subject Key ID is not allowed"); + WOLFSSL_MSG("Use macro WOLFSSL_ALLOW_CRIT_SKID if wanted"); + return ASN_CRIT_EXT_E; + } + #endif + if (DecodeSubjKeyId(&input[idx], length, cert) < 0) return ASN_PARSE_E; break; diff --git a/wolfcrypt/src/error.c b/wolfcrypt/src/error.c index d49734474..78ed8e45e 100644 --- a/wolfcrypt/src/error.c +++ b/wolfcrypt/src/error.c @@ -204,7 +204,7 @@ const char* wc_GetErrorString(int error) return "ASN NTRU key decode error, invalid input"; case ASN_CRIT_EXT_E: - return "X.509 Critical extension ignored"; + return "X.509 Critical extension ignored or invalid"; case ECC_BAD_ARG_E : return "ECC input argument wrong type, invalid input"; From 5c9eedbf698e9885ffb9dece459451c112864868 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Fri, 10 Mar 2017 09:02:29 +1000 Subject: [PATCH 30/68] Fixes from merge of test coverage changes Include new certificates in distribution. Casting changes for clang. Extra error code - recognize in test. --- certs/include.am | 1 + certs/test/include.am | 12 ++++++++++++ wolfcrypt/test/test.c | 10 +++++----- 3 files changed, 18 insertions(+), 5 deletions(-) create mode 100644 certs/test/include.am diff --git a/certs/include.am b/certs/include.am index b7fad51e5..b32e88225 100644 --- a/certs/include.am +++ b/certs/include.am @@ -58,4 +58,5 @@ dist_doc_DATA+= certs/taoCert.txt EXTRA_DIST+= certs/ntru-key.raw +include certs/test/include.am include certs/test-pathlen/include.am diff --git a/certs/test/include.am b/certs/test/include.am new file mode 100644 index 000000000..1ce926d3c --- /dev/null +++ b/certs/test/include.am @@ -0,0 +1,12 @@ +# vim:ft=automake +# All paths should be given relative to the root +# + +EXTRA_DIST += \ + certs/test/cert-ext-ia.cfg \ + certs/test/cert-ext-ia.der \ + certs/test/cert-ext-nc.cfg \ + certs/test/cert-ext-nc.der \ + certs/test/cert-ext-ns.der \ + certs/test/gen-ext-certs.sh + diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 49be41814..9d9132437 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -881,7 +881,7 @@ int error_test() * APIs. Check that the values that are not errors map to the unknown * string. */ - for (i = OPEN_RAN_E; i >= ECC_CDH_KAT_FIPS_E; i--) { + for (i = OPEN_RAN_E; i >= BAD_PATH_ERROR; i--) { errStr = wc_GetErrorString(i); wc_ErrorString(i, out); @@ -1555,7 +1555,7 @@ int sha224_test(void) ret = wc_Sha224GetHash(&sha, hash); if (ret != 0) return -22; - ret = wc_Sha224Update(&sha, (byte*)a.input + 1, a.inLen - 1); + ret = wc_Sha224Update(&sha, (byte*)a.input + 1, (word32)(a.inLen - 1)); if (ret != 0) return -23; ret = wc_Sha224Final(&sha, hash); @@ -1563,7 +1563,7 @@ int sha224_test(void) return -24; if (XMEMCMP(hash, a.output, a.outLen) != 0) return -25; - ret = wc_Sha224Hash((byte*)a.input, a.inLen, hash); + ret = wc_Sha224Hash((byte*)a.input, (word32)a.inLen, hash); if (ret != 0) return -26; if (XMEMCMP(hash, a.output, a.outLen) != 0) @@ -1799,7 +1799,7 @@ int sha384_test(void) ret = wc_Sha384GetHash(&sha, hash); if (ret != 0) return -22; - ret = wc_Sha384Update(&sha, (byte*)a.input + 1, a.inLen - 1); + ret = wc_Sha384Update(&sha, (byte*)a.input + 1, (word32)(a.inLen - 1)); if (ret != 0) return -23; ret = wc_Sha384Final(&sha, hash); @@ -1808,7 +1808,7 @@ int sha384_test(void) if (XMEMCMP(hash, a.output, a.outLen) != 0) return -25; XMEMSET(hash, 0, a.outLen); - ret = wc_Sha384Hash((byte*)a.input, a.inLen, hash); + ret = wc_Sha384Hash((byte*)a.input, (word32)a.inLen, hash); if (ret != 0) return -26; if (XMEMCMP(hash, a.output, a.outLen) != 0) From e8d97c9b1e2552cd2e6aa90c024b8eaaa54251b0 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Fri, 10 Mar 2017 09:36:29 -0700 Subject: [PATCH 31/68] make test buffers large enough for results --- wolfcrypt/test/test.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 9d9132437..bc9db1198 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -1883,7 +1883,7 @@ int hash_test(void) ret = wc_HashUpdate(&hash, typesBad[i], data, sizeof(data)); if (ret != BAD_FUNC_ARG) return -4120 - i; - ret = wc_HashFinal(&hash, typesBad[i], data); + ret = wc_HashFinal(&hash, typesBad[i], out); if (ret != BAD_FUNC_ARG) return -4130 - i; } @@ -1902,7 +1902,7 @@ int hash_test(void) ret = wc_HashUpdate(&hash, typesGood[i], data, sizeof(data)); if (ret != exp_ret) return -4150 - i; - ret = wc_HashFinal(&hash, typesGood[i], data); + ret = wc_HashFinal(&hash, typesGood[i], out); if (ret != exp_ret) return -4160 - i; ret = wc_HashGetOID(typesGood[i]); @@ -10178,7 +10178,7 @@ static int ecc_sig_test(WC_RNG* rng, ecc_key* key) int ret; word32 sigSz; int size; - byte out[65]; + byte out[75]; byte in[] = "Everyone gets Friday off."; word32 inLen = (word32)XSTRLEN((char*)in); From dee3159f0fb8293410dbed05eb88f33941a53b57 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Fri, 10 Mar 2017 09:39:18 -0700 Subject: [PATCH 32/68] update byte size conversion --- wolfcrypt/user-crypto/src/rsa.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/wolfcrypt/user-crypto/src/rsa.c b/wolfcrypt/user-crypto/src/rsa.c index 2533a94a8..3040211bd 100644 --- a/wolfcrypt/user-crypto/src/rsa.c +++ b/wolfcrypt/user-crypto/src/rsa.c @@ -1956,7 +1956,7 @@ int wc_RsaFlattenPublicKey(RsaKey* key, byte* e, word32* eSz, byte* n, return USER_CRYPTO_ERROR; /* sz is in bits change to bytes */ - sz = (sz / bytSz) + (sz % bytSz); + sz = (sz / bytSz) + ((sz % bytSz)? 1 : 0); if (*eSz < (word32)sz) return USER_CRYPTO_ERROR; @@ -1973,7 +1973,7 @@ int wc_RsaFlattenPublicKey(RsaKey* key, byte* e, word32* eSz, byte* n, return USER_CRYPTO_ERROR; /* sz is in bits change to bytes */ - sz = (sz / bytSz) + (sz % bytSz); + sz = (sz / bytSz) + ((sz % bytSz)? 1: 0); if (*nSz < (word32)sz) return USER_CRYPTO_ERROR; From bb81ea804cfba4a97bfa4b77a2cae50b362b13a5 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Fri, 10 Mar 2017 09:55:27 -0700 Subject: [PATCH 33/68] add AES get key to ARMv8 port and add check for BASE 64 encode to tests --- wolfcrypt/src/port/arm/armv8-aes.c | 26 ++++++++++++++++++++++++++ wolfcrypt/test/test.c | 4 ++-- 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/wolfcrypt/src/port/arm/armv8-aes.c b/wolfcrypt/src/port/arm/armv8-aes.c index c189b3eda..250411924 100644 --- a/wolfcrypt/src/port/arm/armv8-aes.c +++ b/wolfcrypt/src/port/arm/armv8-aes.c @@ -4658,5 +4658,31 @@ int wc_AesGcmSetKey(Aes* aes, const byte* key, word32 len) #endif /* HAVE_AES_DECRYPT */ #endif /* WOLFSSL_AES_DIRECT */ +int wc_AesGetKeySize(Aes* aes, word32* keySize) +{ + int ret = 0; + + if (aes == NULL || keySize == NULL) { + return BAD_FUNC_ARG; + } + + switch (aes->rounds) { + case 10: + *keySize = 16; + break; + case 12: + *keySize = 24; + break; + case 14: + *keySize = 32; + break; + default: + *keySize = 0; + ret = BAD_FUNC_ARG; + } + + return ret; +} + #endif /* NO_AES */ diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index bc9db1198..501e0c7dd 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -381,7 +381,7 @@ int wolfcrypt_test(void* args) else printf( "error test passed!\n"); -#ifndef NO_CODING +#if !defined(NO_CODING) && defined(WOLFSSL_BASE64_ENCODE) if ( (ret = base64_test()) != 0) return err_sys("base64 test failed!\n", ret); else @@ -914,7 +914,7 @@ int error_test() return 0; } -#ifndef NO_CODING +#if !defined(NO_CODING) && defined(WOLFSSL_BASE64_ENCODE) int base64_test() { int ret; From 93f1e7cf2e59e75c18680a3386846e831ad3c95c Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Fri, 10 Mar 2017 13:16:22 -0700 Subject: [PATCH 34/68] remove magic number in test case --- wolfcrypt/test/test.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 501e0c7dd..ffbd6b552 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -10178,7 +10178,7 @@ static int ecc_sig_test(WC_RNG* rng, ecc_key* key) int ret; word32 sigSz; int size; - byte out[75]; + byte out[ECC_MAX_SIG_SIZE]; byte in[] = "Everyone gets Friday off."; word32 inLen = (word32)XSTRLEN((char*)in); From 80fe2a3524bc9af9adf17cbbdcd4f7806a7c9e04 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Sat, 11 Mar 2017 10:17:15 +1000 Subject: [PATCH 35/68] Fix elliptic curve selection. Preference by: 1. the default for the curve strength (eccTempKeySz), 2. a curve at the curve strength (eccTempKeySz), 3. the default for next higher curve strength, 4. the first curve (client order) with the next highest curve strength --- src/tls.c | 282 +++++++++++++++++++++++++++++++++++++----------------- 1 file changed, 192 insertions(+), 90 deletions(-) diff --git a/src/tls.c b/src/tls.c index 0f0f7bc6f..501248c60 100755 --- a/src/tls.c +++ b/src/tls.c @@ -2888,6 +2888,13 @@ int TLSX_ValidateEllipticCurves(WOLFSSL* ssl, byte first, byte second) { : NULL; EllipticCurve* curve = NULL; word32 oid = 0; + word32 defOid = 0; + word32 defSz = 80; /* Maximum known curve size is 66. */ + word32 nextOid = 0; + word32 nextSz = 80; /* Maximum known curve size is 66. */ + word32 currOid = ssl->ecdhCurveOID; + int ephmSuite = 0; + word16 octets = 0; /* according to 'ecc_set_type ecc_sets[];' */ int sig = 0; /* validate signature */ int key = 0; /* validate key */ @@ -2904,158 +2911,253 @@ int TLSX_ValidateEllipticCurves(WOLFSSL* ssl, byte first, byte second) { switch (curve->name) { #if defined(HAVE_ECC160) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP160R1: oid = ECC_SECP160R1_OID; break; + case WOLFSSL_ECC_SECP160R1: + oid = ECC_SECP160R1_OID; + octets = 20; + /* Default for 160-bits. */ + if (ssl->eccTempKeySz <= octets && defSz > octets) { + defOid = oid; + defSz = octets; + } + break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_SECPR2 - case WOLFSSL_ECC_SECP160R2: oid = ECC_SECP160R2_OID; break; + case WOLFSSL_ECC_SECP160R2: + oid = ECC_SECP160R2_OID; + octets = 20; + break; #endif /* HAVE_ECC_SECPR2 */ #ifdef HAVE_ECC_KOBLITZ - case WOLFSSL_ECC_SECP160K1: oid = ECC_SECP160K1_OID; break; + case WOLFSSL_ECC_SECP160K1: + oid = ECC_SECP160K1_OID; + octets = 20; + break; #endif /* HAVE_ECC_KOBLITZ */ #endif #if defined(HAVE_ECC192) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP192R1: oid = ECC_SECP192R1_OID; break; + case WOLFSSL_ECC_SECP192R1: + oid = ECC_SECP192R1_OID; + octets = 24; + /* Default for 192-bits. */ + if (ssl->eccTempKeySz <= octets && defSz > octets) { + defOid = oid; + defSz = octets; + } + break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_KOBLITZ - case WOLFSSL_ECC_SECP192K1: oid = ECC_SECP192K1_OID; break; + case WOLFSSL_ECC_SECP192K1: + oid = ECC_SECP192K1_OID; + octets = 24; + break; #endif /* HAVE_ECC_KOBLITZ */ #endif #if defined(HAVE_ECC224) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP224R1: oid = ECC_SECP224R1_OID; break; + case WOLFSSL_ECC_SECP224R1: + oid = ECC_SECP224R1_OID; + octets = 28; + /* Default for 224-bits. */ + if (ssl->eccTempKeySz <= octets && defSz > octets) { + defOid = oid; + defSz = octets; + } + break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_KOBLITZ - case WOLFSSL_ECC_SECP224K1: oid = ECC_SECP224K1_OID; break; + case WOLFSSL_ECC_SECP224K1: + oid = ECC_SECP224K1_OID; + octets = 28; + break; #endif /* HAVE_ECC_KOBLITZ */ #endif #if !defined(NO_ECC256) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP256R1: oid = ECC_SECP256R1_OID; break; + case WOLFSSL_ECC_SECP256R1: + oid = ECC_SECP256R1_OID; + octets = 32; + /* Default for 256-bits. */ + if (ssl->eccTempKeySz <= octets && defSz > octets) { + defOid = oid; + defSz = octets; + } + break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_KOBLITZ - case WOLFSSL_ECC_SECP256K1: oid = ECC_SECP256K1_OID; break; + case WOLFSSL_ECC_SECP256K1: + oid = ECC_SECP256K1_OID; + octets = 32; + break; #endif /* HAVE_ECC_KOBLITZ */ #ifdef HAVE_ECC_BRAINPOOL - case WOLFSSL_ECC_BRAINPOOLP256R1: oid = ECC_BRAINPOOLP256R1_OID; break; + case WOLFSSL_ECC_BRAINPOOLP256R1: + oid = ECC_BRAINPOOLP256R1_OID; + octets = 32; + break; #endif /* HAVE_ECC_BRAINPOOL */ #endif #if defined(HAVE_ECC384) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP384R1: oid = ECC_SECP384R1_OID; break; + case WOLFSSL_ECC_SECP384R1: + oid = ECC_SECP384R1_OID; + octets = 48; + /* Default for 384-bits. */ + if (ssl->eccTempKeySz <= octets && defSz > octets) { + defOid = oid; + defSz = octets; + } + break; #endif /* !NO_ECC_SECP */ #ifdef HAVE_ECC_BRAINPOOL - case WOLFSSL_ECC_BRAINPOOLP384R1: oid = ECC_BRAINPOOLP384R1_OID; break; + case WOLFSSL_ECC_BRAINPOOLP384R1: + oid = ECC_BRAINPOOLP384R1_OID; + octets = 48; + break; #endif /* HAVE_ECC_BRAINPOOL */ #endif #if defined(HAVE_ECC512) || defined(HAVE_ALL_CURVES) #ifdef HAVE_ECC_BRAINPOOL - case WOLFSSL_ECC_BRAINPOOLP512R1: oid = ECC_BRAINPOOLP512R1_OID; break; + case WOLFSSL_ECC_BRAINPOOLP512R1: + oid = ECC_BRAINPOOLP512R1_OID; + octets = 64; + break; #endif /* HAVE_ECC_BRAINPOOL */ #endif #if defined(HAVE_ECC521) || defined(HAVE_ALL_CURVES) #ifndef NO_ECC_SECP - case WOLFSSL_ECC_SECP521R1: oid = ECC_SECP521R1_OID; break; + case WOLFSSL_ECC_SECP521R1: + oid = ECC_SECP521R1_OID; + octets = 66; + break; #endif /* !NO_ECC_SECP */ #endif default: continue; /* unsupported curve */ } - if (ssl->ecdhCurveOID == 0) - ssl->ecdhCurveOID = oid; + if (currOid == 0 && ssl->eccTempKeySz == octets) + currOid = oid; + if ((nextOid == 0 || nextSz > octets) && ssl->eccTempKeySz <= octets) { + nextOid = oid; + nextSz = octets; + } if (first == ECC_BYTE) { - switch (second) { - /* ECDHE_ECDSA */ - case TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA: - case TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA: - case TLS_ECDHE_ECDSA_WITH_RC4_128_SHA: - case TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA: - case TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256: - case TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384: - case TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256: - case TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384: - case TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: - case TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: - sig |= ssl->pkCurveOID == oid; - key |= ssl->ecdhCurveOID == oid; - break; + switch (second) { + /* ECDHE_ECDSA */ + case TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA: + case TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA: + case TLS_ECDHE_ECDSA_WITH_RC4_128_SHA: + case TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA: + case TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256: + case TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384: + case TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256: + case TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384: + case TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: + case TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: + sig |= ssl->pkCurveOID == oid; + key |= ssl->ecdhCurveOID == oid; + ephmSuite = 1; + break; #ifdef WOLFSSL_STATIC_DH - /* ECDH_ECDSA */ - case TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA: - case TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA: - case TLS_ECDH_ECDSA_WITH_RC4_128_SHA: - case TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA: - case TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256: - case TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384: - case TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256: - case TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384: - sig |= ssl->pkCurveOID == oid; - key |= ssl->pkCurveOID == oid; - break; + /* ECDH_ECDSA */ + case TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA: + case TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA: + case TLS_ECDH_ECDSA_WITH_RC4_128_SHA: + case TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA: + case TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256: + case TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384: + case TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256: + case TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384: + sig |= ssl->pkCurveOID == oid; + key |= ssl->pkCurveOID == oid; + break; #endif /* WOLFSSL_STATIC_DH */ #ifndef NO_RSA - /* ECDHE_RSA */ - case TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA: - case TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA: - case TLS_ECDHE_RSA_WITH_RC4_128_SHA: - case TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA: - case TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256: - case TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384: - case TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: - case TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: - sig = 1; - key |= ssl->ecdhCurveOID == oid; - break; + /* ECDHE_RSA */ + case TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA: + case TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA: + case TLS_ECDHE_RSA_WITH_RC4_128_SHA: + case TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA: + case TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256: + case TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384: + case TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: + case TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: + sig = 1; + key |= ssl->ecdhCurveOID == oid; + ephmSuite = 1; + break; #ifdef WOLFSSL_STATIC_DH - /* ECDH_RSA */ - case TLS_ECDH_RSA_WITH_AES_256_CBC_SHA: - case TLS_ECDH_RSA_WITH_AES_128_CBC_SHA: - case TLS_ECDH_RSA_WITH_RC4_128_SHA: - case TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA: - case TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256: - case TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384: - case TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256: - case TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384: - sig = 1; - key |= ssl->pkCurveOID == oid; - break; + /* ECDH_RSA */ + case TLS_ECDH_RSA_WITH_AES_256_CBC_SHA: + case TLS_ECDH_RSA_WITH_AES_128_CBC_SHA: + case TLS_ECDH_RSA_WITH_RC4_128_SHA: + case TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA: + case TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256: + case TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384: + case TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256: + case TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384: + sig = 1; + key |= ssl->pkCurveOID == oid; + break; #endif /* WOLFSSL_STATIC_DH */ #endif - default: - sig = 1; - key = 1; - break; - } + default: + sig = 1; + key = 1; + break; + } } /* ChaCha20-Poly1305 ECC cipher suites */ if (first == CHACHA_BYTE) { - switch (second) { - /* ECDHE_ECDSA */ - case TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256 : - case TLS_ECDHE_ECDSA_WITH_CHACHA20_OLD_POLY1305_SHA256 : - sig |= ssl->pkCurveOID == oid; - key |= ssl->ecdhCurveOID == oid; - break; + switch (second) { + /* ECDHE_ECDSA */ + case TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256 : + case TLS_ECDHE_ECDSA_WITH_CHACHA20_OLD_POLY1305_SHA256 : + sig |= ssl->pkCurveOID == oid; + key |= ssl->ecdhCurveOID == oid; + ephmSuite = 1; + break; #ifndef NO_RSA - /* ECDHE_RSA */ - case TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256 : - case TLS_ECDHE_RSA_WITH_CHACHA20_OLD_POLY1305_SHA256 : - sig = 1; - key |= ssl->ecdhCurveOID == oid; - break; + /* ECDHE_RSA */ + case TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256 : + case TLS_ECDHE_RSA_WITH_CHACHA20_OLD_POLY1305_SHA256 : + sig = 1; + key |= ssl->ecdhCurveOID == oid; + ephmSuite = 1; + break; #endif - default: - sig = 1; - key = 1; - break; - } + default: + sig = 1; + key = 1; + break; + } } } + /* Choose the default if it is at the required strength. */ + if (ssl->ecdhCurveOID == 0 && defSz == ssl->eccTempKeySz) { + key = 1; + ssl->ecdhCurveOID = defOid; + } + /* Choose any curve at the required strength. */ + if (ssl->ecdhCurveOID == 0) { + key = 1; + ssl->ecdhCurveOID = currOid; + } + /* Choose the default if it is at the next highest strength. */ + if (ssl->ecdhCurveOID == 0 && defSz == nextSz) + ssl->ecdhCurveOID = defOid; + /* Choose any curve at the next highest strength. */ + if (ssl->ecdhCurveOID == 0) + ssl->ecdhCurveOID = nextOid; + /* No curve and ephemeral ECC suite requires a matching curve. */ + if (ssl->ecdhCurveOID == 0 && ephmSuite) + key = 0; + return sig && key; } From 614231f71c84cb65e04c37076f23a828a1300940 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Mon, 13 Mar 2017 11:33:39 +1000 Subject: [PATCH 36/68] Fixes for extended configuration testing --- src/crl.c | 13 ++++++------- src/ocsp.c | 2 -- wolfcrypt/src/integer.c | 10 +++++++--- wolfcrypt/test/test.c | 11 +++++++---- 4 files changed, 20 insertions(+), 16 deletions(-) diff --git a/src/crl.c b/src/crl.c index e4a876aad..09e633373 100755 --- a/src/crl.c +++ b/src/crl.c @@ -790,12 +790,12 @@ static int StartMonitorCRL(WOLFSSL_CRL* crl) /* Load CRL path files of type, SSL_SUCCESS on ok */ int LoadCRL(WOLFSSL_CRL* crl, const char* path, int type, int monitor) { - int ret = SSL_SUCCESS; - char* name = NULL; + int ret = SSL_SUCCESS; + char* name = NULL; #ifdef WOLFSSL_SMALL_STACK ReadDirCtx* readCtx = NULL; #else - ReadDirCtx readCtx[1]; + ReadDirCtx readCtx[1]; #endif WOLFSSL_ENTER("LoadCRL"); @@ -803,10 +803,9 @@ int LoadCRL(WOLFSSL_CRL* crl, const char* path, int type, int monitor) return BAD_FUNC_ARG; #ifdef WOLFSSL_SMALL_STACK - ReadDirCtx* readCtx = NULL; - readCtx = (char*)XMALLOC(sizeof(ReadDirCtx), ctx->heap, - DYNAMIC_TYPE_TMP_BUFFER); - if (name == NULL) + readCtx = (ReadDirCtx*)XMALLOC(sizeof(ReadDirCtx), crl->heap, + DYNAMIC_TYPE_TMP_BUFFER); + if (readCtx == NULL) return MEMORY_E; #endif diff --git a/src/ocsp.c b/src/ocsp.c index bcf973b54..0af304f34 100644 --- a/src/ocsp.c +++ b/src/ocsp.c @@ -278,8 +278,6 @@ static int CheckResponse(WOLFSSL_OCSP* ocsp, byte* response, int responseSz, if (newStatus) XFREE(newStatus, NULL, DYNAMIC_TYPE_TMP_BUFFER); if (ocspResponse) XFREE(ocspResponse, NULL, DYNAMIC_TYPE_TMP_BUFFER); - XFREE(request, NULL, DYNAMIC_TYPE_OCSP); - WOLFSSL_LEAVE("CheckCertOCSP", MEMORY_ERROR); return MEMORY_E; } diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index a9d4b9234..6736b18e4 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -542,6 +542,7 @@ void mp_rshb (mp_int *c, int x) /* set the carry to the carry bits of the current word found above */ r = rr; } + mp_clamp(c); } @@ -4100,14 +4101,17 @@ int mp_sub_d (mp_int * a, mp_digit b, mp_int * c) c->used = a->used; /* subtract first digit */ - *tmpc = *tmpa++ - b; - mu = *tmpc >> (sizeof(mp_digit) * CHAR_BIT - 1); + *tmpc = *tmpa - b; + if (b > *tmpa++) + mu = ((-*tmpc) >> DIGIT_BIT) + 1; + else + mu = *tmpc >> DIGIT_BIT; *tmpc++ &= MP_MASK; /* handle rest of the digits */ for (ix = 1; ix < a->used; ix++) { *tmpc = *tmpa++ - mu; - mu = *tmpc >> (sizeof(mp_digit) * CHAR_BIT - 1); + mu = *tmpc >> DIGIT_BIT; *tmpc++ &= MP_MASK; } } diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index ffbd6b552..169432f20 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -254,7 +254,7 @@ int scrypt_test(void); int pkcs7signed_test(void); int pkcs7encrypted_test(void); #endif -#if !defined(NO_ASN_TIME) && defined(WOLFSSL_TEST_CERT) +#if !defined(NO_ASN_TIME) && !defined(NO_RSA) && defined(WOLFSSL_TEST_CERT) int cert_test(void); #endif #if defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_TEST_CERT) @@ -660,7 +660,7 @@ int wolfcrypt_test(void* args) printf( "RSA test passed!\n"); #endif -#if !defined(NO_ASN_TIME) && defined(WOLFSSL_TEST_CERT) +#if !defined(NO_ASN_TIME) && !defined(NO_RSA) && defined(WOLFSSL_TEST_CERT) if ( (ret = cert_test()) != 0) return err_sys("CERT test failed!\n", ret); else @@ -12522,6 +12522,7 @@ int mp_test() ret = wc_RNG_GenerateBlock(&rng, (byte*)&d, sizeof(d)); if (ret != 0) return -11003; + d &= MP_MASK; /* Ensure sqrmod produce same result as mulmod. */ ret = mp_sqrmod(&a, &p, &r1); @@ -12558,7 +12559,7 @@ int mp_test() * - if p and a are even it will fail. */ ret = mp_invmod(&a, &p, &r1); - if (ret != 0 && ret != FP_VAL) + if (ret != 0 && ret != MP_VAL) return -11019; ret = 0; @@ -12577,7 +12578,8 @@ int mp_test() } } - /* Check that setting a digit works. */ + /* Check that setting a 32-bit digit works. */ + d &= 0xffffffff; mp_set_int(&a, d); if (a.used != 1 || a.dp[0] != d) return -11025; @@ -12595,6 +12597,7 @@ done: mp_clear(&p); mp_clear(&r2); mp_clear(&r1); + mp_clear(&b); mp_clear(&a); wc_FreeRng(&rng); return ret; From d4f0c79272ed7662b6a101086094e411543734b6 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Mon, 13 Mar 2017 12:18:45 +1000 Subject: [PATCH 37/68] Cast for Windows --- wolfcrypt/src/integer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index 6736b18e4..1c8fd87d3 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -4103,7 +4103,7 @@ int mp_sub_d (mp_int * a, mp_digit b, mp_int * c) /* subtract first digit */ *tmpc = *tmpa - b; if (b > *tmpa++) - mu = ((-*tmpc) >> DIGIT_BIT) + 1; + mu = (mp_digit)(((-*tmpc) >> DIGIT_BIT) + 1); else mu = *tmpc >> DIGIT_BIT; *tmpc++ &= MP_MASK; From 8ac2f5cb9ceda593d4afad989fb5ef9709b91792 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Mon, 13 Mar 2017 12:29:58 +1000 Subject: [PATCH 38/68] Windows warning about negating unsigned fix --- wolfcrypt/src/integer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index 1c8fd87d3..ab0040d0d 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -4103,7 +4103,7 @@ int mp_sub_d (mp_int * a, mp_digit b, mp_int * c) /* subtract first digit */ *tmpc = *tmpa - b; if (b > *tmpa++) - mu = (mp_digit)(((-*tmpc) >> DIGIT_BIT) + 1); + mu = ((0 - *tmpc) >> DIGIT_BIT) + 1; else mu = *tmpc >> DIGIT_BIT; *tmpc++ &= MP_MASK; From 610ac07cd81b9b2fc320ff70612cf2d8d9f4052a Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Mon, 13 Mar 2017 16:28:36 +1000 Subject: [PATCH 39/68] Add MP_MASK --- wolfssl/wolfcrypt/tfm.h | 1 + 1 file changed, 1 insertion(+) diff --git a/wolfssl/wolfcrypt/tfm.h b/wolfssl/wolfcrypt/tfm.h index 6fe7c03bb..53357b78a 100644 --- a/wolfssl/wolfcrypt/tfm.h +++ b/wolfssl/wolfcrypt/tfm.h @@ -608,6 +608,7 @@ typedef fp_int mp_int; #define MP_YES FP_YES /* yes/no result */ #define MP_ZPOS FP_ZPOS #define MP_NEG FP_NEG +#define MP_MASK FP_MASK /* Prototypes */ #define mp_zero(a) fp_zero(a) From e98a0465ae8c333485a2c99cb4a5e39e1ded2cd1 Mon Sep 17 00:00:00 2001 From: David Garske Date: Mon, 13 Mar 2017 09:48:55 -0700 Subject: [PATCH 40/68] tenAsys INtime RTOS port. Porting complete for mutex semaphores, threading, file, socket and RNG. Added projects for libwolfssl and wolfExamples. The wolfExamples project includes examples for wolfCrypt Test/Benchmark and wolfSSL TLS client/server. Provided reference user_settings.h with comments and enable/disable gates. Added README.md with overview and instructions. Fixed issue building master with NO_WOLFSSL_DIR defined. Added check if old TLS is enabled that SHA and MD5 are enabled. Cleanup of the wolfCrypt test use of USE_CERT_BUFFERS with file system enabled. --- .gitignore | 1 + IDE/INTIME-RTOS/README.md | 53 ++ IDE/INTIME-RTOS/include.am | 13 + IDE/INTIME-RTOS/libwolfssl.c | 20 + IDE/INTIME-RTOS/libwolfssl.vcxproj | 225 +++++ IDE/INTIME-RTOS/user_settings.h | 506 +++++++++++ IDE/INTIME-RTOS/wolfExamples.c | 619 +++++++++++++ IDE/INTIME-RTOS/wolfExamples.h | 47 + IDE/INTIME-RTOS/wolfExamples.sln | 43 + IDE/INTIME-RTOS/wolfExamples.vcxproj | 100 +++ IDE/include.am | 1 + cyassl/ctaocrypt/settings.h | 2 +- gencertbuf.pl | 1 + src/io.c | 9 + src/ssl.c | 4 + src/tls.c | 6 +- wolfcrypt/benchmark/benchmark.c | 2 +- wolfcrypt/src/fe_low_mem.c | 18 +- wolfcrypt/src/fe_operations.c | 4 +- wolfcrypt/src/ge_operations.c | 132 +-- wolfcrypt/src/poly1305.c | 4 +- wolfcrypt/src/random.c | 18 + wolfcrypt/src/wc_port.c | 1206 ++++++++++++++------------ wolfcrypt/test/test.c | 518 ++++++----- wolfssl/certs_test.h | 126 +++ wolfssl/internal.h | 2 + wolfssl/wolfcrypt/fe_operations.h | 4 +- wolfssl/wolfcrypt/settings.h | 18 +- wolfssl/wolfcrypt/types.h | 13 +- wolfssl/wolfcrypt/wc_port.h | 22 +- 30 files changed, 2844 insertions(+), 893 deletions(-) create mode 100755 IDE/INTIME-RTOS/README.md create mode 100644 IDE/INTIME-RTOS/include.am create mode 100755 IDE/INTIME-RTOS/libwolfssl.c create mode 100755 IDE/INTIME-RTOS/libwolfssl.vcxproj create mode 100755 IDE/INTIME-RTOS/user_settings.h create mode 100755 IDE/INTIME-RTOS/wolfExamples.c create mode 100755 IDE/INTIME-RTOS/wolfExamples.h create mode 100755 IDE/INTIME-RTOS/wolfExamples.sln create mode 100755 IDE/INTIME-RTOS/wolfExamples.vcxproj mode change 100644 => 100755 wolfcrypt/src/fe_operations.c mode change 100644 => 100755 wolfcrypt/src/wc_port.c mode change 100644 => 100755 wolfssl/internal.h diff --git a/.gitignore b/.gitignore index cd9de3c0f..f1fd0c9c9 100644 --- a/.gitignore +++ b/.gitignore @@ -190,3 +190,4 @@ wrapper/CSharp/x64/ # Visual Studio Code Workspace Files *.vscode +IDE/INTIME-RTOS/Debug_* diff --git a/IDE/INTIME-RTOS/README.md b/IDE/INTIME-RTOS/README.md new file mode 100755 index 000000000..21e137adf --- /dev/null +++ b/IDE/INTIME-RTOS/README.md @@ -0,0 +1,53 @@ +# tenAsys INtime RTOS Port + +## Overview + +This port is for the tenAsys INtime RTOS available [here](http://www.tenasys.com/tenasys-products/intime-rtos-family/overview-rtos). + +To enable use the define `INTIME_RTOS`. + +## Usage + +The wolfExamples.sln is a Visual Studio 2015 project. You must have the INtime SDK installed and an INtime RTOS agent running. + +The default configuration is set inside the `IDE/INTIME-RTOS/user_settings.h` file. + +The example application provides a simple menu interface to select difference application functions to test. + +``` +wolfExamples started +wolfExamples finished initialization + + MENU + + t. WolfCrypt Test + b. WolfCrypt Benchmark + c. WolfSSL Client Example + s. WolfSSL Server Example + l. WolfSSL Localhost Client/Server Example +Please select one of the above options: +``` + +### `t`wolfCrypt Test + +Performs testing of all crypto algorithms. + +### `b` wolfCrypt Benchmark + +Performs benchmark of crypto algorithms. + +### `c` wolfSSL Client + +To configure the host address and port modify the `TLS_HOST_REMOTE` and `TLS_PORT` macros at top of `wolfExamples.c`. This example uses TLS 1.2 to connect to a remote host. + +### `s` wolfSSL Server + +To configure the port to listen on modify `TLS_PORT` at top of `wolfExamples.c`. + +### `l` wolfSSL Localhost Server/Client + +Starts a TLS server thread listening on localhost. Starts the TLS client and performs connect, exchanges some data and disconnects. + +## References + +For more information please contact info@wolfssl.com. diff --git a/IDE/INTIME-RTOS/include.am b/IDE/INTIME-RTOS/include.am new file mode 100644 index 000000000..5828c76ec --- /dev/null +++ b/IDE/INTIME-RTOS/include.am @@ -0,0 +1,13 @@ +# vim:ft=automake +# included from Top Level Makefile.am +# All paths should be given relative to the root + +EXTRA_DIST += \ + IDE/INTIME-RTOS/README.md \ + IDE/INTIME-RTOS/user_settings.h \ + IDE/INTIME-RTOS/libwolfssl.c \ + IDE/INTIME-RTOS/libwolfssl.vcxproj \ + IDE/INTIME-RTOS/wolfExamples.c \ + IDE/INTIME-RTOS/wolfExamples.h \ + IDE/INTIME-RTOS/wolfExamples.vcxproj \ + IDE/INTIME-RTOS/wolfExamples.sln diff --git a/IDE/INTIME-RTOS/libwolfssl.c b/IDE/INTIME-RTOS/libwolfssl.c new file mode 100755 index 000000000..94d39bb24 --- /dev/null +++ b/IDE/INTIME-RTOS/libwolfssl.c @@ -0,0 +1,20 @@ +// libwolfssl.c +// Defines the entry point for the DLL application + +#include + +BOOLEAN __stdcall RslMain( RTHANDLE hModule, + DWORD ul_reason_for_call, + LPVOID lpReserved + ) +{ + switch (ul_reason_for_call) { + case RSL_PROCESS_ATTACH: + case RSL_THREAD_ATTACH: + case RSL_THREAD_DETACH: + case RSL_PROCESS_DETACH: + break; + } + + return TRUE; +} diff --git a/IDE/INTIME-RTOS/libwolfssl.vcxproj b/IDE/INTIME-RTOS/libwolfssl.vcxproj new file mode 100755 index 000000000..155da63aa --- /dev/null +++ b/IDE/INTIME-RTOS/libwolfssl.vcxproj @@ -0,0 +1,225 @@ + + + + + Debug + INtime + + + Release + INtime + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + {1731767D-573F-45C9-A466-191DA0D180CF} + 8.1 + + + + StaticLibrary + NotSet + v140 + + + StaticLibrary + false + NotSet + v140 + + + + + + + + + + + + $(Configuration)_$(ProjectName)\ + + + $(Configuration)_$(ProjectName)\ + + + + + + 21076.20052 + /SAFESEH:NO %(AdditionalOptions) + rt.lib;pcibus.lib;netlib.lib;clib.lib;vshelper.lib + $(SolutionDir)$(Configuration)\\libwolfssl.rsl + + + Async + _USRDLL;WOLFSSL_DLL;BUILDING_WOLFSSL;WOLFSSL_USER_SETTINGS;%(PreprocessorDefinitions) + $(ProjectDir);$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) + $(IntDir) + $(IntDir) + $(IntDir) + $(IntDir)vc$(PlatformToolsetVersion).pdb + + + + + + + 21076.20052 + /SAFESEH:NO %(AdditionalOptions) + rt.lib;pcibus.lib;netlib.lib;clib.lib;vshelper.lib + $(SolutionDir)$(Configuration)\\libwolfssl.rsl + + + Async + _USRDLL;WOLFSSL_DLL;BUILDING_WOLFSSL;WOLFSSL_USER_SETTINGS;%(PreprocessorDefinitions) + $(ProjectDir);$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) + $(IntDir) + $(IntDir) + $(IntDir) + $(IntDir)vc$(PlatformToolsetVersion).pdb + + + + + + diff --git a/IDE/INTIME-RTOS/user_settings.h b/IDE/INTIME-RTOS/user_settings.h new file mode 100755 index 000000000..14e78cc89 --- /dev/null +++ b/IDE/INTIME-RTOS/user_settings.h @@ -0,0 +1,506 @@ +/* Example custom user settings for wolfSSL and INtime RTOS port */ + +#ifndef WOLFSSL_USER_SETTINGS_H +#define WOLFSSL_USER_SETTINGS_H + +#ifdef __cplusplus +extern "C" { +#endif + +/* ------------------------------------------------------------------------- */ +/* Port - Platform */ +/* ------------------------------------------------------------------------- */ +#undef INTIME_RTOS +#define INTIME_RTOS + +#undef INTIME_RTOS_MUTEX_MAX +#define INTIME_RTOS_MUTEX_MAX 10 + +#undef WOLF_EXAMPLES_STACK +#define WOLF_EXAMPLES_STACK 131072 + +#undef WOLFSSL_GENERAL_ALIGNMENT +#define WOLFSSL_GENERAL_ALIGNMENT 4 + +/* platform already has min()/max() */ +#undef WOLFSSL_HAVE_MIN +#define WOLFSSL_HAVE_MIN +#undef WOLFSSL_HAVE_MAX +#define WOLFSSL_HAVE_MAX + +/* disable directory support */ +#undef NO_WOLFSSL_DIR +#define NO_WOLFSSL_DIR + +#undef NO_WRITEV +#define NO_WRITEV + +#undef NO_MAIN_DRIVER +#define NO_MAIN_DRIVER + +/* if using in single threaded mode */ +#undef SINGLE_THREADED +//#define SINGLE_THREADED + +/* reduces stack usage, by using malloc/free for stack variables over 100 bytes */ +#undef WOLFSSL_SMALL_STACK +//#define WOLFSSL_SMALL_STACK + + +/* ------------------------------------------------------------------------- */ +/* Math Configuration */ +/* ------------------------------------------------------------------------- */ +/* fast math uses stack and inline assembly to speed up math */ +#undef USE_FAST_MATH +#define USE_FAST_MATH + +#ifdef USE_FAST_MATH + /* timing resistance for side-channel attack protection */ + #undef TFM_TIMING_RESISTANT + #define TFM_TIMING_RESISTANT +#endif + + +/* ------------------------------------------------------------------------- */ +/* Crypto */ +/* ------------------------------------------------------------------------- */ +/* ECC */ +#if 1 + #undef HAVE_ECC + #define HAVE_ECC + + /* Support for custom curves */ + #define WOLFSSL_CUSTOM_CURVES + + /* Curve types */ + //#define NO_ECC_SECP + #define HAVE_ECC_SECPR2 + #define HAVE_ECC_SECPR3 + #define HAVE_ECC_BRAINPOOL + #define HAVE_ECC_KOBLITZ + + /* Curve sizes */ + #undef HAVE_ALL_CURVES + //#define HAVE_ALL_CURVES + #ifndef HAVE_ALL_CURVES + #undef ECC_USER_CURVES + #define ECC_USER_CURVES + #define HAVE_ECC192 + #define HAVE_ECC224 + //#define NO_ECC256 + #define HAVE_ECC384 + #define HAVE_ECC521 + #endif + + /* Fixed point cache (speeds repeated operations against same private key) */ + #undef FP_ECC + #define FP_ECC + #ifdef FP_ECC + /* Bits / Entries */ + #undef FP_ENTRIES + #define FP_ENTRIES 2 + #undef FP_LUT + #define FP_LUT 4 + #endif + + /* Optional ECC calculation method */ + /* Note: doubles heap usage, but slightly faster */ + #undef ECC_SHAMIR + #define ECC_SHAMIR + + /* Reduces heap usage, but slower */ + /* timing resistance for side-channel attack protection */ + #undef ECC_TIMING_RESISTANT + #define ECC_TIMING_RESISTANT + + #ifdef USE_FAST_MATH + /* use reduced size math buffers for ecc points */ + #undef ALT_ECC_SIZE + #define ALT_ECC_SIZE + + /* Enable TFM optimizations for ECC */ + #if defined(HAVE_ECC192) || defined(HAVE_ALL_CURVES) + #define TFM_ECC192 + #endif + #if defined(HAVE_ECC224) || defined(HAVE_ALL_CURVES) + #define TFM_ECC224 + #endif + #if !defined(NO_ECC256) || defined(HAVE_ALL_CURVES) + #define TFM_ECC256 + #endif + #if defined(HAVE_ECC384) || defined(HAVE_ALL_CURVES) + #define TFM_ECC384 + #endif + #if defined(HAVE_ECC521) || defined(HAVE_ALL_CURVES) + #define TFM_ECC521 + #endif + #endif +#endif + +/* RSA */ +#undef NO_RSA +#if 1 + #ifdef USE_FAST_MATH + /* Maximum math bits (Max RSA key bits * 2) */ + #undef FP_MAX_BITS + #define FP_MAX_BITS 4096 + #endif + + /* half as much memory but twice as slow */ + #undef RSA_LOW_MEM + //#define RSA_LOW_MEM + + /* RSA blinding countermeasures */ + #undef WC_RSA_BLINDING + #define WC_RSA_BLINDING +#else + #define NO_RSA +#endif + +/* AES */ +#undef NO_AES +#if 1 + #undef HAVE_AESGCM + #define HAVE_AESGCM + + #ifdef HAVE_AESGCM + /* GCM Method: GCM_SMALL, GCM_WORD32 or GCM_TABLE */ + //#define GCM_SMALL + #define GCM_TABLE + #endif + + #undef WOLFSSL_AES_COUNTER + #define WOLFSSL_AES_COUNTER + + #undef HAVE_AESCCM + #define HAVE_AESCCM + + #undef WOLFSSL_AES_DIRECT + #define WOLFSSL_AES_DIRECT + + #undef HAVE_AES_KEYWRAP + #define HAVE_AES_KEYWRAP +#else + #define NO_AES +#endif + +/* ChaCha20 / Poly1305 */ +#undef HAVE_CHACHA +#undef HAVE_POLY1305 +#if 1 + #define HAVE_CHACHA + #define HAVE_POLY1305 + + /* Needed for Poly1305 */ + #undef HAVE_ONE_TIME_AUTH + #define HAVE_ONE_TIME_AUTH +#endif + +/* Ed25519 / Curve25519 */ +#undef HAVE_CURVE25519 +#undef HAVE_ED25519 +#if 1 + #define HAVE_CURVE25519 + #define HAVE_ED25519 + + /* Optionally use small math (less flash usage, but much slower) */ + #if 0 + #define CURVED25519_SMALL + #endif +#endif + + +/* ------------------------------------------------------------------------- */ +/* Hashing */ +/* ------------------------------------------------------------------------- */ +/* Sha */ +#undef NO_SHA +#if 1 + /* 1k smaller, but 25% slower */ + //#define USE_SLOW_SHA +#else + #define NO_SHA +#endif + +/* Sha256 */ +#undef NO_SHA256 +#if 1 +#else + #define NO_SHA256 +#endif + +/* Sha512 */ +#undef WOLFSSL_SHA512 +#if 1 + #define WOLFSSL_SHA512 + + /* Sha384 */ + #undef WOLFSSL_SHA384 + #if 1 + #define WOLFSSL_SHA384 + #endif + + /* over twice as small, but 50% slower */ + //#define USE_SLOW_SHA2 +#endif + +/* MD5 */ +#undef NO_MD5 +#if 1 +#else + #define NO_MD5 +#endif + + +/* ------------------------------------------------------------------------- */ +/* Enable Features */ +/* ------------------------------------------------------------------------- */ +#undef KEEP_PEER_CERT +#define KEEP_PEER_CERT + +#undef HAVE_COMP_KEY +#define HAVE_COMP_KEY + +#undef HAVE_ECC_ENCRYPT +#define HAVE_ECC_ENCRYPT + +#undef HAVE_TLS_EXTENSIONS +#define HAVE_TLS_EXTENSIONS + +#undef HAVE_SUPPORTED_CURVES +#define HAVE_SUPPORTED_CURVES + +#undef HAVE_EXTENDED_MASTER +#define HAVE_EXTENDED_MASTER + +#undef WOLFSSL_DTLS +#define WOLFSSL_DTLS + +#undef OPENSSL_EXTRA +#define OPENSSL_EXTRA + +#undef WOLFSSL_BASE64_ENCODE +#define WOLFSSL_BASE64_ENCODE + +#undef HAVE_HKDF +#define HAVE_HKDF + +#undef WOLFSSL_CMAC +#define WOLFSSL_CMAC + +#undef WOLFSSL_KEY_GEN +#define WOLFSSL_KEY_GEN + +#undef WOLFSSL_CERT_GEN +#define WOLFSSL_CERT_GEN + +#undef WOLFSSL_CERT_REQ +#define WOLFSSL_CERT_REQ + +#undef WOLFSSL_CERT_EXT +#define WOLFSSL_CERT_EXT + +#undef HAVE_PK_CALLBACKS +#define HAVE_PK_CALLBACKS + +#undef HAVE_ALPN +#define HAVE_ALPN + +#undef HAVE_SNI +#define HAVE_SNI + +#undef HAVE_MAX_FRAGMENT +#define HAVE_MAX_FRAGMENT + +#undef HAVE_TRUNCATED_HMAC +#define HAVE_TRUNCATED_HMAC + +#undef SESSION_CERTS +#define SESSION_CERTS + +#undef HAVE_SESSION_TICKET +#define HAVE_SESSION_TICKET + +#undef WOLFCRYPT_HAVE_SRP +#define WOLFCRYPT_HAVE_SRP + +#undef WOLFSSL_HAVE_CERT_SERVICE +#define WOLFSSL_HAVE_CERT_SERVICE + +#undef HAVE_PKCS7 +#define HAVE_PKCS7 + +#undef HAVE_X963_KDF +#define HAVE_X963_KDF + +#undef WOLFSSL_HAVE_WOLFSCEP +#define WOLFSSL_HAVE_WOLFSCEP + +#undef WOLFSSL_ALWAYS_KEEP_SNI +#define WOLFSSL_ALWAYS_KEEP_SNI + +#undef WOLFSSL_ALWAYS_VERIFY_CB +#define WOLFSSL_ALWAYS_VERIFY_CB + +#undef WOLFSSL_SEP +#define WOLFSSL_SEP + +#undef ATOMIC_USER +#define ATOMIC_USER + +#undef HAVE_OCSP +#define HAVE_OCSP + +#undef HAVE_CERTIFICATE_STATUS_REQUEST +#define HAVE_CERTIFICATE_STATUS_REQUEST + +#undef HAVE_CERTIFICATE_STATUS_REQUEST_V2 +#define HAVE_CERTIFICATE_STATUS_REQUEST_V2 + +#undef HAVE_CRL +#define HAVE_CRL + +#undef PERSIST_CERT_CACHE +//#define PERSIST_CERT_CACHE + +#undef PERSIST_SESSION_CACHE +//#define PERSIST_SESSION_CACHE + +#undef WOLFSSL_DER_LOAD +//#define WOLFSSL_DER_LOAD + +#undef WOLFSSL_DES_ECB +//#define WOLFSSL_DES_ECB + +#undef HAVE_CAMELLIA +//#define HAVE_CAMELLIA + +#undef HAVE_NULL_CIPHER +//#define HAVE_NULL_CIPHER + +#undef WOLFSSL_RIPEMD +//#define WOLFSSL_RIPEMD + + +/* TLS Session Cache */ +#if 1 + #define SMALL_SESSION_CACHE + //#define MEDIUM_SESSION_CACHE + //#define BIG_SESSION_CACHE + //#define HUGE_SESSION_CACHE +#else + #define NO_SESSION_CACHE +#endif + + +/* ------------------------------------------------------------------------- */ +/* Disable Features */ +/* ------------------------------------------------------------------------- */ +#undef NO_WOLFSSL_SERVER +//#define NO_WOLFSSL_SERVER + +#undef NO_WOLFSSL_CLIENT +//#define NO_WOLFSSL_CLIENT + +/* disables TLS 1.0/1.1 support */ +#undef NO_OLD_TLS +//#define NO_OLD_TLS + +/* disable access to filesystem */ +#undef NO_FILESYSTEM +//#define NO_FILESYSTEM + +#undef NO_RC4 +#define NO_RC4 + +#undef NO_HC128 +#define NO_HC128 + +#undef NO_RABBIT +#define NO_RABBIT + +#undef NO_MD4 +#define NO_MD4 + +/* Pre-shared keys */ +#undef NO_PSK +//#define NO_PSK + +#undef NO_DSA +//#define NO_DSA + +#undef NO_DH +//#define NO_DH + +#undef NO_DES3 +//#define NO_DES3 + +#undef NO_PWDBASED +//#define NO_PWDBASED + +/* encoding/decoding support */ +#undef NO_CODING +//#define NO_CODING + +/* memory wrappers and memory callbacks */ +#undef NO_WOLFSSL_MEMORY +//#define NO_WOLFSSL_MEMORY + +/* In-lining of misc.c functions */ +/* If defined, must include wolfcrypt/src/misc.c in build */ +/* Slower, but about 1k smaller */ +#undef NO_INLINE +//#define NO_INLINE + + + +/* ------------------------------------------------------------------------- */ +/* Benchmark / Test */ +/* ------------------------------------------------------------------------- */ +#undef NO_CRYPT_TEST +//#define NO_CRYPT_TEST + +#undef NO_CRYPT_BENCHMARK +//#define NO_CRYPT_BENCHMARK + +/* Use reduced benchmark / test sizes */ +#undef BENCH_EMBEDDED +#define BENCH_EMBEDDED + +#undef USE_CERT_BUFFERS_2048 +#define USE_CERT_BUFFERS_2048 + +#undef USE_CERT_BUFFERS_256 +#define USE_CERT_BUFFERS_256 + + + +/* ------------------------------------------------------------------------- */ +/* Debugging */ +/* ------------------------------------------------------------------------- */ +#undef WOLFSSL_DEBUG +#define WOLFSSL_DEBUG +#ifdef WOLFSSL_DEBUG + /* Use this to measure / print heap usage */ + #if 0 + #undef USE_WOLFSSL_MEMORY + #define USE_WOLFSSL_MEMORY + + #undef WOLFSSL_TRACK_MEMORY + #define WOLFSSL_TRACK_MEMORY + #endif + + /* Math debugging (adds support for mp_dump) */ + #undef WOLFSSL_DEBUG_MATH + //#define WOLFSSL_DEBUG_MATH +#else + #undef NO_ERROR_STRINGS + //#define NO_ERROR_STRINGS +#endif + + +#ifdef __cplusplus +} +#endif + +#endif /* WOLFSSL_USER_SETTINGS_H */ diff --git a/IDE/INTIME-RTOS/wolfExamples.c b/IDE/INTIME-RTOS/wolfExamples.c new file mode 100755 index 000000000..fdea5eb68 --- /dev/null +++ b/IDE/INTIME-RTOS/wolfExamples.c @@ -0,0 +1,619 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "wolfExamples.h" +#include +#include +#include +#include +#include + + +/***************************************************************************** + * Globals + ****************************************************************************/ +RTHANDLE hRootProcess; +DWORD dwKtickInUsecs; +INIT_STRUCT gInit; +static int gServerExit = 0; +static int gServerReady = 0; + +static const char menu1[] = "\r\n" + "\tt. WolfCrypt Test\r\n" + "\tb. WolfCrypt Benchmark\r\n" + "\tc. WolfSSL Client Example\r\n" + "\ts. WolfSSL Server Example\r\n" + "\tl. WolfSSL Localhost Client/Server Example\r\n"; + + +/***************************************************************************** + * Configuration + ****************************************************************************/ + +#define TLS_MAXDATASIZE 4096 /* maximum acceptable amount of data */ +#define TLS_PORT 11111 /* define default port number */ +#define TLS_HOST_LOCAL "127.0.0.1" +#define TLS_HOST_REMOTE "192.168.0.112" +#define SOCK_MAX_PENDING 5 +#define THREAD_BASE_PRIO 150 + + +/***************************************************************************** + * TLS Client + ****************************************************************************/ +int wolfExample_TLSClient(const char* ip, int port) +{ + int ret = 0; + WOLFSSL_CTX* ctx = NULL; + WOLFSSL* ssl = NULL; /* create WOLFSSL object */ + int sockFd = -1; /* socket file descriptor */ + struct sockaddr_in servAddr; /* struct for server address */ + char sendBuff[TLS_MAXDATASIZE], rcvBuff[TLS_MAXDATASIZE]; + + /* wait for server to be ready */ + while (gServerReady != 1) { + RtSleep(0); + } + + sockFd = socket(AF_INET, SOCK_STREAM, 0); + if (sockFd < 0) { + printf("Failed to create socket. Error: %d\n", errno); + return errno; + } + + memset(&servAddr, 0, sizeof(servAddr)); /* clears memory block for use */ + servAddr.sin_family = AF_INET; /* sets addressfamily to internet*/ + servAddr.sin_port = htons(port); /* sets port to defined port */ + + /* looks for the server at the entered address (ip in the command line) */ + if (inet_pton(AF_INET, ip, &servAddr.sin_addr) < 1) { + /* checks validity of address */ + ret = errno; + printf("Invalid Address. Error: %d\n", ret); + goto exit; + } + + if (connect(sockFd, (struct sockaddr *)&servAddr, sizeof(servAddr)) < 0) { + /* if socket fails to connect to the server*/ + ret = errno; + printf("Connect error. Error: %d\n", ret); + goto exit; + } + + /* create and initialize WOLFSSL_CTX structure */ + if ((ctx = wolfSSL_CTX_new(wolfTLSv1_2_client_method())) == NULL) { + printf("SSL_CTX_new error.\n"); + goto exit; + } + + /* load CA certificates into wolfSSL_CTX. which will verify the server */ + ret = wolfSSL_CTX_load_verify_buffer(ctx, ca_cert_der_2048, + sizeof_ca_cert_der_2048, SSL_FILETYPE_ASN1); + if (ret != SSL_SUCCESS) { + printf("Error %d loading CA cert\n", ret); + goto exit; + } + if ((ssl = wolfSSL_new(ctx)) == NULL) { + printf("wolfSSL_new error.\n"); + goto exit; + } + wolfSSL_set_fd(ssl, sockFd); + + ret = wolfSSL_connect(ssl); + if (ret == SSL_SUCCESS) { + printf("Message for server:\t"); + fgets(sendBuff, TLS_MAXDATASIZE, stdin); + + if (wolfSSL_write(ssl, sendBuff, strlen(sendBuff)) != strlen(sendBuff)) { + /* the message is not able to send, or error trying */ + ret = wolfSSL_get_error(ssl, 0); + printf("Write error: Error: %d\n", ret); + goto exit; + } + + memset(rcvBuff, 0, TLS_MAXDATASIZE); + if (wolfSSL_read(ssl, rcvBuff, TLS_MAXDATASIZE) < 0) { + /* the server failed to send data, or error trying */ + ret = wolfSSL_get_error(ssl, 0); + printf("Read error. Error: %d\n", ret); + goto exit; + } + printf("Recieved: \t%s\n", rcvBuff); + } + +exit: + /* frees all data before client termination */ + if (sockFd != -1) + close(sockFd); + wolfSSL_free(ssl); + wolfSSL_CTX_free(ctx); + gServerExit = 1; + + return ret; +} + +/***************************************************************************** + * TLS Server + ****************************************************************************/ +int wolfExample_TLSServer(int port) +{ + int ret = 0; + WOLFSSL_CTX* ctx = NULL; + WOLFSSL* ssl = NULL; + int sockFd = -1, clientFd = -1; + struct sockaddr_in serverAddr = {0}, clientAddr = {0}; + const char reply[] = "I hear ya fa shizzle!\n"; + int addrSize = sizeof(clientAddr); + char buff[256]; + + sockFd = socket(AF_INET, SOCK_STREAM, 0); + if (sockFd < 0) { + printf("Failed to create socket. Error: %d\n", errno); + return errno; + } + + /* create and initialize WOLFSSL_CTX structure */ + if ((ctx = wolfSSL_CTX_new(wolfTLSv1_2_server_method())) == NULL) { + fprintf(stderr, "wolfSSL_CTX_new error.\n"); + goto exit; + } + + /* Load server certificate into WOLFSSL_CTX */ + ret = wolfSSL_CTX_use_certificate_buffer(ctx, server_cert_der_2048, + sizeof_server_cert_der_2048, SSL_FILETYPE_ASN1); + if (ret != SSL_SUCCESS) { + fprintf(stderr, "Error %d loading server-cert!\n", ret); + goto exit; + } + + /* Load server key into WOLFSSL_CTX */ + ret = wolfSSL_CTX_use_PrivateKey_buffer(ctx, server_key_der_2048, + sizeof_server_key_der_2048, SSL_FILETYPE_ASN1); + if (ret != SSL_SUCCESS) { + fprintf(stderr, "Error %d loading server-key!\n", ret); + goto exit; + } + + /* Initialize the server address struct to zero */ + memset((char *)&serverAddr, 0, sizeof(serverAddr)); + + /* Fill the server's address family */ + serverAddr.sin_family = AF_INET; + serverAddr.sin_addr.s_addr = INADDR_ANY; + serverAddr.sin_port = htons(port); + + /* Attach the server socket to our port */ + if (bind(sockFd, (struct sockaddr *)&serverAddr, sizeof(serverAddr)) < 0) { + printf("ERROR: failed to bind\n"); + goto exit; + } + + printf("Waiting for a connection...\n"); + gServerReady = 1; + + /* Continuously accept connects while not in an active connection */ + while (gServerExit == 0) { + /* listen for a new connection */ + ret = listen(sockFd, SOCK_MAX_PENDING); + if (ret == 0) { + /* Wait until a client connects */ + clientFd = accept(sockFd, (struct sockaddr*)&clientAddr, &addrSize); + + /* If fails to connect, loop back up and wait for a new connection */ + if (clientFd == -1) { + printf("failed to accept the connection..\n"); + } + /* If it connects, read in and reply to the client */ + else { + printf("Client connected successfully\n"); + + ssl = wolfSSL_new(ctx); + if (ssl == NULL) { + fprintf(stderr, "wolfSSL_new error.\n"); + break; + } + + /* direct our ssl to our clients connection */ + wolfSSL_set_fd(ssl, clientFd); + + printf("Using Non-Blocking I/O: %d\n", + wolfSSL_get_using_nonblock(ssl)); + + for ( ; ; ) { + /* Clear the buffer memory for anything possibly left over */ + memset(&buff, 0, sizeof(buff)); + + /* Read the client data into our buff array */ + ret = wolfSSL_read(ssl, buff, sizeof(buff) - 1); + if (ret > 0) { + /* Print any data the client sends to the console */ + printf("Client: %s\n", buff); + + /* Reply back to the client */ + ret = wolfSSL_write(ssl, reply, sizeof(reply) - 1); + if (ret < 0) { + printf("wolfSSL_write error = %d\n", + wolfSSL_get_error(ssl, ret)); + gServerExit = 1; + break; + } + } + /* if the client disconnects break the loop */ + else { + if (ret < 0) + printf("wolfSSL_read error = %d\n", + wolfSSL_get_error(ssl, ret)); + else if (ret == 0) + printf("The client has closed the connection.\n"); + gServerExit = 1; + break; + } + } + wolfSSL_free(ssl); /* Free the WOLFSSL object */ + ssl = NULL; + } + close(clientFd); /* close the connected socket */ + clientFd = -1; + } + } /* while */ + +exit: + if (clientFd != -1) + close(clientFd); + if (sockFd != -1) + close(sockFd); + wolfSSL_free(ssl); /* Free the WOLFSSL object */ + wolfSSL_CTX_free(ctx); /* Free WOLFSSL_CTX */ + + return ret; +} + +/***************************************************************************** + * TLS Local Test + ****************************************************************************/ +static void wolfSSLLocalServerThread(void* param) +{ + int port = (int)((int*)param); + wolfExample_TLSServer(port); +} + +int wolfExample_TLSLocal(int port) +{ + int ret; + RTHANDLE srvHandle; + + /* start server thread */ + srvHandle = CreateRtThread(THREAD_BASE_PRIO + 10, + (LPPROC)wolfSSLLocalServerThread, WOLF_EXAMPLES_STACK, (void*)port); + if (srvHandle == BAD_RTHANDLE) { + Fail("Cannot create server thread"); + return -1; + } + + /* run client */ + ret = wolfExample_TLSClient(TLS_HOST_LOCAL, port); + + return ret; +} + + +/***************************************************************************** + * Thread + memset(&args, 0, sizeof(args)); + ****************************************************************************/ +typedef struct func_args { + int argc; + char** argv; + int return_code; +} func_args; + +static void wolfExampleThread(void* param) +{ + func_args args; + +#ifdef DEBUG_WOLFSSL + wolfSSL_Debugging_ON(); +#endif + + /* initialize wolfSSL */ + wolfSSL_Init(); + + while (1) { + char rc; + + gServerExit = 0; + gServerReady = 0; + + printf("\r\n\t\t\t\tMENU\r\n"); + printf(menu1); + printf("Please select one of the above options: "); + + rc = getchar(); + switch (rc) { + case 't': + printf("\nCrypt Test\n"); + wolfcrypt_test(&args); + printf("Crypt Test: Return code %d\n", args.return_code); + break; + + case 'b': + printf("\nBenchmark Test\n"); + benchmark_test(&args); + printf("Benchmark Test: Return code %d\n", args.return_code); + break; + + case 'c': + wolfExample_TLSClient(TLS_HOST_REMOTE, TLS_PORT); + break; + + case 's': + wolfExample_TLSServer(TLS_PORT); + break; + + case 'l': + wolfExample_TLSLocal(TLS_PORT); + break; + + // All other cases go here + default: + if (rc != '\r' && rc != '\n') + printf("\r\nSelection %c out of range\r\n", rc); + break; + } + } + + wolfSSL_Cleanup(); +} + + +/***************************************************************************** +* FUNCTION: Catalog +* +* PARAMETERS: 1. handle of the process whose object directory must be used +* 2. the object whose handle must be cataloged +* 3. the name to be used (upto 14 characters) +* +* RETURNS: TRUE on success +* +* DESCRIPTION: If the given name already exists, +* and the existing name refers to a non-existing object, +* then the existing name is removed before cataloging. +\*****************************************************************************/ +BOOLEAN Catalog( + RTHANDLE hProcess, + RTHANDLE hObject, + LPSTR lpszName) +{ + RTHANDLE hOld; + + if (CatalogRtHandle(hProcess, hObject, lpszName)) + return TRUE; + + // something wrong: check for the case mentioned above + if (((hOld = LookupRtHandle(hProcess, lpszName, NO_WAIT)) != BAD_RTHANDLE) && + (GetRtHandleType(hOld) == INVALID_TYPE)) + { + // this is the case mentioned above: remove the old entry and try again + if (UncatalogRtHandle(hProcess, lpszName)) + return (CatalogRtHandle(hProcess, hObject, lpszName)); + } + return FALSE; +} + +/***************************************************************************** +* FUNCTION: Cleanup (local function) +* +* DESCRIPTION: +* Tell threads to delete themselves and wait a while; +* if any thread still exists, kill it. +* Remove all other objects as far as they have been created. +\*****************************************************************************/ +void Cleanup(void) +{ + // indicate that we are cleaning up + gInit.state = CLEANUP_BUSY; + gInit.bShutdown = TRUE; + +#ifdef _DEBUG + fprintf(stderr, "wolfExamples started cleaning up\n"); +#endif + + // remove our name from the root process + if (gInit.bCataloged) { + if (!UncatalogRtHandle(hRootProcess, "wolfExample")) + Fail("Cannot remove my own name"); + } + +#ifdef _DEBUG + fprintf(stderr, "wolfExamples finished cleaning up\n"); +#endif + + // lie down + exit(0); +} + +/***************************************************************************** +* FUNCTION: Fail +* +* PARAMETERS: same parameters as expected by printf +* +* DESCRIPTION: +* If in debug mode, prints the message, appending a new line and the error number. +* Then the current process is killed graciously: +* If the current thread is the main thread, this is done directly. +* if the current thread is another one, a terminate request is sent and +* the function returns to the calling thread. +\*****************************************************************************/ +void Fail(LPSTR lpszMessage, ...) +{ + EXCEPTION eh; + RTHANDLE hDelMbx; + DWORD dwTerminate; + +#ifdef _DEBUG + va_list ap; + + va_start(ap, lpszMessage); + vfprintf(stderr, lpszMessage, ap); + va_end(ap); + fprintf(stderr, "\nError nr=%x %s\n", GetLastRtError(), GetRtErrorText(GetLastRtError())); +#endif + + // make sure that exceptions are returned for inline handling + GetRtExceptionHandlerInfo(THREAD_HANDLER, &eh); + eh.ExceptionMode = 0; + SetRtExceptionHandler(&eh); + + // if we had not started initializing yet, just get out + if (BEFORE_INIT == gInit.state) + exit(0); + + if (gInit.hMain == GetRtThreadHandles(THIS_THREAD)) + { + // this is the main thread: + // if we are busy initializing, then do Cleanup + if (INIT_BUSY == gInit.state) + Cleanup(); // does not return + + // this is the main thread, but we are not initializing: just return + return; + } + + // this is not the main thread: + // ask main thread to do cleanup + // (allow some time to setup the deletion mailbox, ignore errors) + hDelMbx = LookupRtHandle(NULL_RTHANDLE, "R?EXIT_MBOX", 5000); + dwTerminate = TERMINATE; + SendRtData(hDelMbx, &dwTerminate, 4); +} + +/***************************************************************************** +* +* FUNCTION: UsecsToKticks +* +* PARAMETERS: 1. number of usecs +* +* RETURNS: number of low level ticks +* +* DESCRIPTION: returns the parameter if it is WAIT_FOREVER +* otherwise rounds up to number of low level ticks +\*****************************************************************************/ +DWORD UsecsToKticks(DWORD dwUsecs) +{ + if (dwUsecs == WAIT_FOREVER) + return WAIT_FOREVER; + + return (dwUsecs + dwKtickInUsecs - 1) / dwKtickInUsecs; +} + + +/***************************************************************************** +* FUNCTION: main +* +* DESCRIPTION: +* This is the main program module. +* It creates global objects and all threads. +* The main thread then waits for notifications and acts accordingly +\*****************************************************************************/ +int main(int argc, char* argv[]) +{ + SYSINFO sysinfo; + EVENTINFO eiEventInfo; + RTHANDLE taskHandle; + +#ifdef _DEBUG + fprintf(stderr, "wolfExamples started\n"); +#endif + + // obtain handle of root process (cannot fail) + hRootProcess = GetRtThreadHandles(ROOT_PROCESS); + + // initialize the structure for cleaning up + memset(&gInit, 0, sizeof(gInit)); + gInit.state = BEFORE_INIT; + + // get low level tick length in usecs + if (!CopyRtSystemInfo(&sysinfo)) + Fail("Cannot copy system info"); + dwKtickInUsecs = 10000 / sysinfo.KernelTickRatio; + if (dwKtickInUsecs == 0) + Fail("Invalid low level tick length"); + + // adjust process max priority (ignore error) + // TODO adjust the 2nd parameter to a value closer to zero if you want to allow more priorities + SetRtProcessMaxPriority(NULL_RTHANDLE, THREAD_BASE_PRIO); + + // obtain main thread's handle + gInit.hMain = GetRtThreadHandles(THIS_THREAD); + gInit.state = INIT_BUSY; + + // attempt to catalog the thread but ignore error + Catalog(NULL_RTHANDLE, gInit.hMain, "TMain"); + + // catalog the handle of this process in the root process + if (!Catalog(hRootProcess, GetRtThreadHandles(THIS_PROCESS), "wolfExample")) { + Fail("Cannot catalog process name"); + } + gInit.bCataloged = TRUE; + + // create thread + taskHandle = CreateRtThread(THREAD_BASE_PRIO + 20, + (LPPROC)wolfExampleThread, WOLF_EXAMPLES_STACK, 0); + if (taskHandle == BAD_RTHANDLE) { + Fail("Cannot create thread"); + } + + // indicate that initialization has finished + gInit.state = INIT_DONE; +#ifdef _DEBUG + fprintf(stderr, "wolfExamples finished initialization\n"); +#endif + + // wait for notifications + while (RtNotifyEvent(RT_SYSTEM_NOTIFICATIONS | RT_EXIT_NOTIFICATIONS, + WAIT_FOREVER, &eiEventInfo)) + { + switch(eiEventInfo.dwNotifyType) + { + case TERMINATE: + // TODO: this process should terminate + // cleanup the environment + Cleanup(); // does not return + + case NT_HOST_UP: + // TODO: react to a Windows host that has come back + break; + + case NT_BLUESCREEN: + // TODO: react to a Windows blue screen + break; + + case KERNEL_STOPPING: + // TODO: react to the INtime kernel stopping + break; + + case NT_HOST_HIBERNATE: + // TODO: react to the Windows host going in hibernation + break; + + case NT_HOST_STANDBY: + // TODO: react to the Windows host going in standby mode + break; + + case NT_HOST_SHUTDOWN_PENDING: + // TODO: react to a Windows host that is about to shutdown + break; + } + } + Fail("Notify failed"); + return 0; +} diff --git a/IDE/INTIME-RTOS/wolfExamples.h b/IDE/INTIME-RTOS/wolfExamples.h new file mode 100755 index 000000000..89ce77cda --- /dev/null +++ b/IDE/INTIME-RTOS/wolfExamples.h @@ -0,0 +1,47 @@ +#ifndef _WOLFEXAMPLES_H_ +#define _WOLFEXAMPLES_H_ + +#include + +#ifdef __cplusplus + extern "C" { +#endif + +// support functions for all threads +BOOLEAN Catalog(RTHANDLE hProcess, RTHANDLE hObject, LPSTR lpszName); +void Cleanup(void); +void Fail(LPSTR lpszMessage, ...); +DWORD UsecsToKticks(DWORD dwUsecs); + + +/* Example API's */ +int wolfExample_TLSServer(int port); +int wolfExample_TLSClient(const char* ip, int port); +int wolfExample_TLSLocal(int port); + + +// global type definitions +typedef enum { + BEFORE_INIT, + INIT_BUSY, + INIT_DONE, + CLEANUP_BUSY +} INIT_STATE; + +typedef struct { + RTHANDLE hMain; // RTHANDLE of main thread + INIT_STATE state; // main thread state + BOOLEAN bCataloged; // TRUE if we cataloged process name in root + BOOLEAN bShutdown; // TRUE if all threads have to terminate +} INIT_STRUCT; + +// global variables +extern RTHANDLE hRootProcess; // RTHANDLE of root process +extern DWORD dwKtickInUsecs; // length of one low level tick in usecs +extern INIT_STRUCT gInit; // structure describing all global objects + +#ifdef __cplusplus + } /* extern "C" */ +#endif + +#endif /* _WOLFEXAMPLES_H_ */ diff --git a/IDE/INTIME-RTOS/wolfExamples.sln b/IDE/INTIME-RTOS/wolfExamples.sln new file mode 100755 index 000000000..81666bf8e --- /dev/null +++ b/IDE/INTIME-RTOS/wolfExamples.sln @@ -0,0 +1,43 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 14 +VisualStudioVersion = 14.0.23107.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "wolfExamples", "wolfExamples.vcxproj", "{557A7EFD-2627-478A-A855-50F518DD13EE}" + ProjectSection(ProjectDependencies) = postProject + {1731767D-573F-45C9-A466-191DA0D180CF} = {1731767D-573F-45C9-A466-191DA0D180CF} + EndProjectSection +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libwolfssl", "libwolfssl.vcxproj", "{1731767D-573F-45C9-A466-191DA0D180CF}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|INtime = Debug|INtime + Release|INtime = Release|INtime + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {557A7EFD-2627-478A-A855-50F518DD13EE}.Debug|INtime.ActiveCfg = Debug|INtime + {557A7EFD-2627-478A-A855-50F518DD13EE}.Debug|INtime.Build.0 = Debug|INtime + {557A7EFD-2627-478A-A855-50F518DD13EE}.Release|INtime.ActiveCfg = Release|INtime + {557A7EFD-2627-478A-A855-50F518DD13EE}.Release|INtime.Build.0 = Release|INtime + {1731767D-573F-45C9-A466-191DA0D180CF}.Debug|INtime.ActiveCfg = Debug|INtime + {1731767D-573F-45C9-A466-191DA0D180CF}.Debug|INtime.Build.0 = Debug|INtime + {1731767D-573F-45C9-A466-191DA0D180CF}.Release|INtime.ActiveCfg = Release|INtime + {1731767D-573F-45C9-A466-191DA0D180CF}.Release|INtime.Build.0 = Release|INtime + {AA35919C-9D2D-4753-8FD1-E5D1644ABE65}.Debug|INtime.ActiveCfg = Debug|INtime + {AA35919C-9D2D-4753-8FD1-E5D1644ABE65}.Debug|INtime.Build.0 = Debug|INtime + {AA35919C-9D2D-4753-8FD1-E5D1644ABE65}.Release|INtime.ActiveCfg = Release|INtime + {AA35919C-9D2D-4753-8FD1-E5D1644ABE65}.Release|INtime.Build.0 = Release|INtime + {A7A65D11-2A66-4936-9476-16646CF896CA}.Debug|INtime.ActiveCfg = Debug|INtime + {A7A65D11-2A66-4936-9476-16646CF896CA}.Debug|INtime.Build.0 = Debug|INtime + {A7A65D11-2A66-4936-9476-16646CF896CA}.Release|INtime.ActiveCfg = Release|INtime + {A7A65D11-2A66-4936-9476-16646CF896CA}.Release|INtime.Build.0 = Release|INtime + {2359342B-C023-4443-8170-3471928C9334}.Debug|INtime.ActiveCfg = Debug|INtime + {2359342B-C023-4443-8170-3471928C9334}.Debug|INtime.Build.0 = Debug|INtime + {2359342B-C023-4443-8170-3471928C9334}.Release|INtime.ActiveCfg = Release|INtime + {2359342B-C023-4443-8170-3471928C9334}.Release|INtime.Build.0 = Release|INtime + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/IDE/INTIME-RTOS/wolfExamples.vcxproj b/IDE/INTIME-RTOS/wolfExamples.vcxproj new file mode 100755 index 000000000..81f82318e --- /dev/null +++ b/IDE/INTIME-RTOS/wolfExamples.vcxproj @@ -0,0 +1,100 @@ + + + + + Debug + INtime + + + Release + INtime + + + + + + + + + + + + + + + + {557A7EFD-2627-478A-A855-50F518DD13EE} + wolfExamples + 8.1 + + + + Application + NotSet + v140 + + + Application + false + NotSet + v140 + + + + + + + + + + + + $(Configuration)_$(ProjectName)\ + + + $(Configuration)_$(ProjectName)\ + + + + + + 21076.20053 + /SAFESEH:NO %(AdditionalOptions) + rt.lib;pcibus.lib;netlib.lib;clib.lib;vshelper.lib;libwolfssl.lib + $(SolutionDir)$(Configuration)\\wolfExamples.rta + $(ProjectDir)$(Configuration);%(AdditionalLibraryDirectories) + + + Async + WOLFSSL_USER_SETTINGS;%(PreprocessorDefinitions) + $(ProjectDir);$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) + $(IntDir) + $(IntDir) + $(IntDir)vc$(PlatformToolsetVersion).pdb + $(IntDir) + + + + + + + 21076.20053 + /SAFESEH:NO %(AdditionalOptions) + rt.lib;pcibus.lib;netlib.lib;clib.lib;vshelper.lib;libwolfssl.lib + $(SolutionDir)$(Configuration)\\wolfExamples.rta + $(ProjectDir)$(Configuration);%(AdditionalLibraryDirectories) + + + Async + WOLFSSL_USER_SETTINGS;%(PreprocessorDefinitions) + $(ProjectDir);$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) + $(IntDir) + $(IntDir) + $(IntDir)vc$(PlatformToolsetVersion).pdb + $(IntDir) + + + + + + diff --git a/IDE/include.am b/IDE/include.am index 96fa894d7..4a547bb16 100644 --- a/IDE/include.am +++ b/IDE/include.am @@ -8,5 +8,6 @@ include IDE/WIN-SGX/include.am include IDE/WORKBENCH/include.am include IDE/ROWLEY-CROSSWORKS-ARM/include.am include IDE/ARDUINO/include.am +include IDE/INTIME-RTOS/include.am EXTRA_DIST+= IDE/IAR-EWARM IDE/MDK-ARM IDE/MDK5-ARM IDE/MYSQL IDE/LPCXPRESSO diff --git a/cyassl/ctaocrypt/settings.h b/cyassl/ctaocrypt/settings.h index c12a962ff..4de8b13ca 100644 --- a/cyassl/ctaocrypt/settings.h +++ b/cyassl/ctaocrypt/settings.h @@ -246,7 +246,7 @@ /* Micrium will use Visual Studio for compilation but not the Win32 API */ #if defined(_WIN32) && !defined(MICRIUM) && !defined(FREERTOS) \ - && !defined(EBSNET) && !defined(CYASSL_EROAD) + && !defined(EBSNET) && !defined(CYASSL_EROAD) && !defined(INTIME_RTOS) #define USE_WINDOWS_API #endif diff --git a/gencertbuf.pl b/gencertbuf.pl index 09c6114c2..e7dc9f7d6 100755 --- a/gencertbuf.pl +++ b/gencertbuf.pl @@ -55,6 +55,7 @@ my @fileList_2048 = ( [ "./certs/dh2048.der", "dh_key_der_2048" ], [ "./certs/dsa2048.der", "dsa_key_der_2048" ], [ "./certs/rsa2048.der", "rsa_key_der_2048" ], + [ "./certs/ca-key.der", "ca_key_der_2048" ], [ "./certs/ca-cert.der", "ca_cert_der_2048" ], [ "./certs/server-key.der", "server_key_der_2048" ], [ "./certs/server-cert.der", "server_cert_der_2048" ] diff --git a/src/io.c b/src/io.c index 88aba2730..e90acb866 100644 --- a/src/io.c +++ b/src/io.c @@ -82,6 +82,15 @@ #include #elif defined(WOLFSSL_ATMEL) #include "socket/include/socket.h" + #elif defined(INTIME_RTOS) + #undef MIN + #undef MAX + #include + #include + #include + #include + #include + #include #else #include #include diff --git a/src/ssl.c b/src/ssl.c index e7f9cf4e6..1f94fc526 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -5089,6 +5089,7 @@ int wolfSSL_CTX_load_verify_locations(WOLFSSL_CTX* ctx, const char* file, ret = ProcessFile(ctx, file, SSL_FILETYPE_PEM, CA_TYPE, NULL, 0, NULL); if (ret == SSL_SUCCESS && path) { +#ifndef NO_WOLFSSL_DIR char* name = NULL; #ifdef WOLFSSL_SMALL_STACK ReadDirCtx* readCtx = NULL; @@ -5114,6 +5115,9 @@ int wolfSSL_CTX_load_verify_locations(WOLFSSL_CTX* ctx, const char* file, #ifdef WOLFSSL_SMALL_STACK XFREE(readCtx, ctx->heap, DYNAMIC_TYPE_TMP_BUFFER); #endif +#else + ret = NOT_COMPILED_IN; +#endif } return ret; diff --git a/src/tls.c b/src/tls.c index 501248c60..8c8437ae8 100755 --- a/src/tls.c +++ b/src/tls.c @@ -1390,7 +1390,7 @@ static word16 TLSX_SNI_GetSize(SNI* list) switch (sni->type) { case WOLFSSL_SNI_HOST_NAME: - length += XSTRLEN((char*)sni->data.host_name); + length += (word16)XSTRLEN((char*)sni->data.host_name); break; } } @@ -1412,7 +1412,7 @@ static word16 TLSX_SNI_Write(SNI* list, byte* output) switch (sni->type) { case WOLFSSL_SNI_HOST_NAME: - length = XSTRLEN((char*)sni->data.host_name); + length = (word16)XSTRLEN((char*)sni->data.host_name); c16toa(length, output + offset); /* sni length */ offset += OPAQUE16_LEN; @@ -1675,7 +1675,7 @@ word16 TLSX_SNI_GetRequest(TLSX* extensions, byte type, void** data) switch (sni->type) { case WOLFSSL_SNI_HOST_NAME: *data = sni->data.host_name; - return XSTRLEN((char*)*data); + return (word16)XSTRLEN((char*)*data); } } diff --git a/wolfcrypt/benchmark/benchmark.c b/wolfcrypt/benchmark/benchmark.c index c2696bc46..2bbdfdc44 100644 --- a/wolfcrypt/benchmark/benchmark.c +++ b/wolfcrypt/benchmark/benchmark.c @@ -2545,7 +2545,7 @@ void bench_ed25519KeySign(void) #endif /* HAVE_ED25519 */ -#ifdef _WIN32 +#if defined(_WIN32) && !defined(INTIME_RTOS) #define WIN32_LEAN_AND_MEAN #include diff --git a/wolfcrypt/src/fe_low_mem.c b/wolfcrypt/src/fe_low_mem.c index 9caffa81f..aa6a44996 100644 --- a/wolfcrypt/src/fe_low_mem.c +++ b/wolfcrypt/src/fe_low_mem.c @@ -183,7 +183,7 @@ static void raw_add(byte *x, const byte *p) for (i = 0; i < F25519_SIZE; i++) { c += ((word16)x[i]) + ((word16)p[i]); - x[i] = c; + x[i] = (byte)c; c >>= 8; } } @@ -197,11 +197,11 @@ static void raw_try_sub(byte *x, const byte *p) for (i = 0; i < F25519_SIZE; i++) { c = ((word16)x[i]) - ((word16)p[i]) - c; - minusp[i] = c; + minusp[i] = (byte)c; c = (c >> 8) & 1; } - fprime_select(x, minusp, x, c); + fprime_select(x, minusp, x, (byte)c); } @@ -271,7 +271,7 @@ void fprime_mul(byte *r, const byte *a, const byte *b, for (j = 0; j < F25519_SIZE; j++) { c |= ((word16)r[j]) << 1; - r[j] = c; + r[j] = (byte)c; c >>= 8; } raw_try_sub(r, modulus); @@ -310,7 +310,7 @@ void fe_normalize(byte *x) for (i = 0; i < F25519_SIZE; i++) { c += x[i]; - x[i] = c; + x[i] = (byte)c; c >>= 8; } @@ -322,12 +322,12 @@ void fe_normalize(byte *x) for (i = 0; i + 1 < F25519_SIZE; i++) { c += x[i]; - minusp[i] = c; + minusp[i] = (byte)c; c >>= 8; } c += ((word16)x[i]) - 128; - minusp[31] = c; + minusp[31] = (byte)c; /* Load x-p if no underflow */ fe_select(x, minusp, x, (c >> 15) & 1); @@ -355,7 +355,7 @@ void fe_add(fe r, const fe a, const fe b) for (i = 0; i < F25519_SIZE; i++) { c >>= 8; c += ((word16)a[i]) + ((word16)b[i]); - r[i] = c; + r[i] = (byte)c; } /* Reduce with 2^255 = 19 mod p */ @@ -364,7 +364,7 @@ void fe_add(fe r, const fe a, const fe b) for (i = 0; i < F25519_SIZE; i++) { c += r[i]; - r[i] = c; + r[i] = (byte)c; c >>= 8; } } diff --git a/wolfcrypt/src/fe_operations.c b/wolfcrypt/src/fe_operations.c old mode 100644 new mode 100755 index 9dfeab093..a47ff3cfb --- a/wolfcrypt/src/fe_operations.c +++ b/wolfcrypt/src/fe_operations.c @@ -942,7 +942,7 @@ replace (f,g) with (f,g) if b == 0. Preconditions: b in {0,1}. */ -void fe_cswap(fe f,fe g,unsigned int b) +void fe_cswap(fe f, fe g, int b) { int32_t f0 = f[0]; int32_t f1 = f[1]; @@ -1353,7 +1353,7 @@ replace (f,g) with (f,g) if b == 0. Preconditions: b in {0,1}. */ -void fe_cmov(fe f,const fe g,unsigned int b) +void fe_cmov(fe f, const fe g, int b) { int32_t f0 = f[0]; int32_t f1 = f[1]; diff --git a/wolfcrypt/src/ge_operations.c b/wolfcrypt/src/ge_operations.c index 99eaeb2dc..109b77c82 100644 --- a/wolfcrypt/src/ge_operations.c +++ b/wolfcrypt/src/ge_operations.c @@ -274,38 +274,38 @@ void sc_reduce(byte* s) carry9 = s9 >> 21; s10 += carry9; s9 -= carry9 << 21; carry10 = s10 >> 21; s11 += carry10; s10 -= carry10 << 21; - s[0] = s0 >> 0; - s[1] = s0 >> 8; - s[2] = (s0 >> 16) | (s1 << 5); - s[3] = s1 >> 3; - s[4] = s1 >> 11; - s[5] = (s1 >> 19) | (s2 << 2); - s[6] = s2 >> 6; - s[7] = (s2 >> 14) | (s3 << 7); - s[8] = s3 >> 1; - s[9] = s3 >> 9; - s[10] = (s3 >> 17) | (s4 << 4); - s[11] = s4 >> 4; - s[12] = s4 >> 12; - s[13] = (s4 >> 20) | (s5 << 1); - s[14] = s5 >> 7; - s[15] = (s5 >> 15) | (s6 << 6); - s[16] = s6 >> 2; - s[17] = s6 >> 10; - s[18] = (s6 >> 18) | (s7 << 3); - s[19] = s7 >> 5; - s[20] = s7 >> 13; - s[21] = s8 >> 0; - s[22] = s8 >> 8; - s[23] = (s8 >> 16) | (s9 << 5); - s[24] = s9 >> 3; - s[25] = s9 >> 11; - s[26] = (s9 >> 19) | (s10 << 2); - s[27] = s10 >> 6; - s[28] = (s10 >> 14) | (s11 << 7); - s[29] = s11 >> 1; - s[30] = s11 >> 9; - s[31] = s11 >> 17; + s[0] = (byte)(s0 >> 0); + s[1] = (byte)(s0 >> 8); + s[2] = (byte)((s0 >> 16) | (s1 << 5)); + s[3] = (byte)(s1 >> 3); + s[4] = (byte)(s1 >> 11); + s[5] = (byte)((s1 >> 19) | (s2 << 2)); + s[6] = (byte)(s2 >> 6); + s[7] = (byte)((s2 >> 14) | (s3 << 7)); + s[8] = (byte)(s3 >> 1); + s[9] = (byte)(s3 >> 9); + s[10] = (byte)((s3 >> 17) | (s4 << 4)); + s[11] = (byte)(s4 >> 4); + s[12] = (byte)(s4 >> 12); + s[13] = (byte)((s4 >> 20) | (s5 << 1)); + s[14] = (byte)(s5 >> 7); + s[15] = (byte)((s5 >> 15) | (s6 << 6)); + s[16] = (byte)(s6 >> 2); + s[17] = (byte)(s6 >> 10); + s[18] = (byte)((s6 >> 18) | (s7 << 3)); + s[19] = (byte)(s7 >> 5); + s[20] = (byte)(s7 >> 13); + s[21] = (byte)(s8 >> 0); + s[22] = (byte)(s8 >> 8); + s[23] = (byte)((s8 >> 16) | (s9 << 5)); + s[24] = (byte)(s9 >> 3); + s[25] = (byte)(s9 >> 11); + s[26] = (byte)((s9 >> 19) | (s10 << 2)); + s[27] = (byte)(s10 >> 6); + s[28] = (byte)((s10 >> 14) | (s11 << 7)); + s[29] = (byte)(s11 >> 1); + s[30] = (byte)(s11 >> 9); + s[31] = (byte)(s11 >> 17); /* hush warnings after setting values to 0 */ (void)s12; @@ -640,38 +640,38 @@ void sc_muladd(byte* s, const byte* a, const byte* b, const byte* c) carry9 = s9 >> 21; s10 += carry9; s9 -= carry9 << 21; carry10 = s10 >> 21; s11 += carry10; s10 -= carry10 << 21; - s[0] = s0 >> 0; - s[1] = s0 >> 8; - s[2] = (s0 >> 16) | (s1 << 5); - s[3] = s1 >> 3; - s[4] = s1 >> 11; - s[5] = (s1 >> 19) | (s2 << 2); - s[6] = s2 >> 6; - s[7] = (s2 >> 14) | (s3 << 7); - s[8] = s3 >> 1; - s[9] = s3 >> 9; - s[10] = (s3 >> 17) | (s4 << 4); - s[11] = s4 >> 4; - s[12] = s4 >> 12; - s[13] = (s4 >> 20) | (s5 << 1); - s[14] = s5 >> 7; - s[15] = (s5 >> 15) | (s6 << 6); - s[16] = s6 >> 2; - s[17] = s6 >> 10; - s[18] = (s6 >> 18) | (s7 << 3); - s[19] = s7 >> 5; - s[20] = s7 >> 13; - s[21] = s8 >> 0; - s[22] = s8 >> 8; - s[23] = (s8 >> 16) | (s9 << 5); - s[24] = s9 >> 3; - s[25] = s9 >> 11; - s[26] = (s9 >> 19) | (s10 << 2); - s[27] = s10 >> 6; - s[28] = (s10 >> 14) | (s11 << 7); - s[29] = s11 >> 1; - s[30] = s11 >> 9; - s[31] = s11 >> 17; + s[0] = (byte)(s0 >> 0); + s[1] = (byte)(s0 >> 8); + s[2] = (byte)((s0 >> 16) | (s1 << 5)); + s[3] = (byte)(s1 >> 3); + s[4] = (byte)(s1 >> 11); + s[5] = (byte)((s1 >> 19) | (s2 << 2)); + s[6] = (byte)(s2 >> 6); + s[7] = (byte)((s2 >> 14) | (s3 << 7)); + s[8] = (byte)(s3 >> 1); + s[9] = (byte)(s3 >> 9); + s[10] = (byte)((s3 >> 17) | (s4 << 4)); + s[11] = (byte)(s4 >> 4); + s[12] = (byte)(s4 >> 12); + s[13] = (byte)((s4 >> 20) | (s5 << 1)); + s[14] = (byte)(s5 >> 7); + s[15] = (byte)((s5 >> 15) | (s6 << 6)); + s[16] = (byte)(s6 >> 2); + s[17] = (byte)(s6 >> 10); + s[18] = (byte)((s6 >> 18) | (s7 << 3)); + s[19] = (byte)(s7 >> 5); + s[20] = (byte)(s7 >> 13); + s[21] = (byte)(s8 >> 0); + s[22] = (byte)(s8 >> 8); + s[23] = (byte)((s8 >> 16) | (s9 << 5)); + s[24] = (byte)(s9 >> 3); + s[25] = (byte)(s9 >> 11); + s[26] = (byte)((s9 >> 19) | (s10 << 2)); + s[27] = (byte)(s10 >> 6); + s[28] = (byte)((s10 >> 14) | (s11 << 7)); + s[29] = (byte)(s11 >> 1); + s[30] = (byte)(s11 >> 9); + s[31] = (byte)(s11 >> 17); /* hush warnings after setting values to 0 */ (void)s12; @@ -754,7 +754,7 @@ static unsigned char negative(signed char b) unsigned long long x = b; /* 18446744073709551361..18446744073709551615: yes; 0..255: no */ x >>= 63; /* 1: yes; 0: no */ - return x; + return (unsigned char)x; } @@ -2272,7 +2272,7 @@ where a = a[0]+256*a[1]+...+256^31 a[31]. and b = b[0]+256*b[1]+...+256^31 b[31]. B is the Ed25519 base point (x,4/5) with x positive. */ -int ge_double_scalarmult_vartime(ge_p2 *r, const unsigned char *a, +int ge_double_scalarmult_vartime(ge_p2 *r, const unsigned char *a, const ge_p3 *A, const unsigned char *b) { signed char aslide[256]; diff --git a/wolfcrypt/src/poly1305.c b/wolfcrypt/src/poly1305.c index 637106b63..1a932dc4f 100644 --- a/wolfcrypt/src/poly1305.c +++ b/wolfcrypt/src/poly1305.c @@ -600,7 +600,7 @@ int wc_Poly1305_MAC(Poly1305* ctx, byte* additional, word32 addSz, if ((ret = wc_Poly1305Update(ctx, additional, addSz)) != 0) { return ret; } - paddingLen = -addSz & (WC_POLY1305_PAD_SZ - 1); + paddingLen = -((int)addSz) & (WC_POLY1305_PAD_SZ - 1); if (paddingLen) { if ((ret = wc_Poly1305Update(ctx, padding, paddingLen)) != 0) { return ret; @@ -611,7 +611,7 @@ int wc_Poly1305_MAC(Poly1305* ctx, byte* additional, word32 addSz, if ((ret = wc_Poly1305Update(ctx, input, sz)) != 0) { return ret; } - paddingLen = -sz & (WC_POLY1305_PAD_SZ - 1); + paddingLen = -((int)sz) & (WC_POLY1305_PAD_SZ - 1); if (paddingLen) { if ((ret = wc_Poly1305Update(ctx, padding, paddingLen)) != 0) { return ret; diff --git a/wolfcrypt/src/random.c b/wolfcrypt/src/random.c index 5ea961538..02bbe14e5 100644 --- a/wolfcrypt/src/random.c +++ b/wolfcrypt/src/random.c @@ -1674,6 +1674,24 @@ int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz) return ret; } +#elif defined(INTIME_RTOS) + int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz) + { + int ret = 0; + + (void)os; + + if (output == NULL) { + return BUFFER_E; + } + + /* Note: Investigate better solution */ + /* no return to check */ + arc4random_buf(output, sz); + + return ret; + } + #elif defined(NO_DEV_RANDOM) #error "you need to write an os specific wc_GenerateSeed() here" diff --git a/wolfcrypt/src/wc_port.c b/wolfcrypt/src/wc_port.c old mode 100644 new mode 100755 index aa1dac6f8..2ca371924 --- a/wolfcrypt/src/wc_port.c +++ b/wolfcrypt/src/wc_port.c @@ -264,13 +264,15 @@ wolfSSL_Mutex* wc_InitAndAllocMutex() { wolfSSL_Mutex* m = (wolfSSL_Mutex*) XMALLOC(sizeof(wolfSSL_Mutex), NULL, DYNAMIC_TYPE_MUTEX); - if(m && wc_InitMutex(m) == 0) + if (m && wc_InitMutex(m) == 0) return m; + XFREE(m, NULL, DYNAMIC_TYPE_MUTEX); m = NULL; return m; } + #if WOLFSSL_CRYPT_HW_MUTEX /* Mutex for protection of cryptography hardware */ static wolfSSL_Mutex wcCryptHwMutex; @@ -310,654 +312,738 @@ int wolfSSL_CryptHwMutexUnLock(void) { #endif /* WOLFSSL_CRYPT_HW_MUTEX */ +/* ---------------------------------------------------------------------------*/ +/* Mutex Ports */ +/* ---------------------------------------------------------------------------*/ #ifdef SINGLE_THREADED -int wc_InitMutex(wolfSSL_Mutex* m) -{ - (void)m; - return 0; -} + int wc_InitMutex(wolfSSL_Mutex* m) + { + (void)m; + return 0; + } -int wc_FreeMutex(wolfSSL_Mutex *m) -{ - (void)m; - return 0; -} + int wc_FreeMutex(wolfSSL_Mutex *m) + { + (void)m; + return 0; + } -int wc_LockMutex(wolfSSL_Mutex *m) -{ - (void)m; - return 0; -} + int wc_LockMutex(wolfSSL_Mutex *m) + { + (void)m; + return 0; + } -int wc_UnLockMutex(wolfSSL_Mutex *m) -{ - (void)m; - return 0; -} + int wc_UnLockMutex(wolfSSL_Mutex *m) + { + (void)m; + return 0; + } -#else /* MULTI_THREAD */ +#elif defined(FREERTOS) || defined(FREERTOS_TCP) || \ + defined(FREESCALE_FREE_RTOS) - #if defined(FREERTOS) || defined(FREERTOS_TCP) || \ - defined(FREESCALE_FREE_RTOS) + int wc_InitMutex(wolfSSL_Mutex* m) + { + int iReturn; - int wc_InitMutex(wolfSSL_Mutex* m) - { - int iReturn; + *m = ( wolfSSL_Mutex ) xSemaphoreCreateMutex(); + if( *m != NULL ) + iReturn = 0; + else + iReturn = BAD_MUTEX_E; - *m = ( wolfSSL_Mutex ) xSemaphoreCreateMutex(); - if( *m != NULL ) - iReturn = 0; - else - iReturn = BAD_MUTEX_E; + return iReturn; + } - return iReturn; - } + int wc_FreeMutex(wolfSSL_Mutex* m) + { + vSemaphoreDelete( *m ); + return 0; + } + + int wc_LockMutex(wolfSSL_Mutex* m) + { + /* Assume an infinite block, or should there be zero block? */ + xSemaphoreTake( *m, portMAX_DELAY ); + return 0; + } + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + xSemaphoreGive( *m ); + return 0; + } + +#elif defined(WOLFSSL_SAFERTOS) + + int wc_InitMutex(wolfSSL_Mutex* m) + { + vSemaphoreCreateBinary(m->mutexBuffer, m->mutex); + if (m->mutex == NULL) + return BAD_MUTEX_E; + + return 0; + } + + int wc_FreeMutex(wolfSSL_Mutex* m) + { + (void)m; + return 0; + } + + int wc_LockMutex(wolfSSL_Mutex* m) + { + /* Assume an infinite block */ + xSemaphoreTake(m->mutex, portMAX_DELAY); + return 0; + } + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + xSemaphoreGive(m->mutex); + return 0; + } + +#elif defined(USE_WINDOWS_API) + + int wc_InitMutex(wolfSSL_Mutex* m) + { + InitializeCriticalSection(m); + return 0; + } - int wc_FreeMutex(wolfSSL_Mutex* m) - { - vSemaphoreDelete( *m ); + int wc_FreeMutex(wolfSSL_Mutex* m) + { + DeleteCriticalSection(m); + return 0; + } + + + int wc_LockMutex(wolfSSL_Mutex* m) + { + EnterCriticalSection(m); + return 0; + } + + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + LeaveCriticalSection(m); + return 0; + } + +#elif defined(WOLFSSL_PTHREADS) + + int wc_InitMutex(wolfSSL_Mutex* m) + { + if (pthread_mutex_init(m, 0) == 0) return 0; - } + else + return BAD_MUTEX_E; + } - int wc_LockMutex(wolfSSL_Mutex* m) - { - /* Assume an infinite block, or should there be zero block? */ - xSemaphoreTake( *m, portMAX_DELAY ); + + int wc_FreeMutex(wolfSSL_Mutex* m) + { + if (pthread_mutex_destroy(m) == 0) return 0; - } + else + return BAD_MUTEX_E; + } - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - xSemaphoreGive( *m ); + + int wc_LockMutex(wolfSSL_Mutex* m) + { + if (pthread_mutex_lock(m) == 0) return 0; - } + else + return BAD_MUTEX_E; + } - #elif defined(WOLFSSL_SAFERTOS) - - int wc_InitMutex(wolfSSL_Mutex* m) - { - vSemaphoreCreateBinary(m->mutexBuffer, m->mutex); - if (m->mutex == NULL) - return BAD_MUTEX_E; + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + if (pthread_mutex_unlock(m) == 0) return 0; - } + else + return BAD_MUTEX_E; + } - int wc_FreeMutex(wolfSSL_Mutex* m) - { - (void)m; +#elif defined(THREADX) + + int wc_InitMutex(wolfSSL_Mutex* m) + { + if (tx_mutex_create(m, "wolfSSL Mutex", TX_NO_INHERIT) == 0) return 0; - } + else + return BAD_MUTEX_E; + } - int wc_LockMutex(wolfSSL_Mutex* m) - { - /* Assume an infinite block */ - xSemaphoreTake(m->mutex, portMAX_DELAY); + + int wc_FreeMutex(wolfSSL_Mutex* m) + { + if (tx_mutex_delete(m) == 0) return 0; - } + else + return BAD_MUTEX_E; + } - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - xSemaphoreGive(m->mutex); + + int wc_LockMutex(wolfSSL_Mutex* m) + { + if (tx_mutex_get(m, TX_WAIT_FOREVER) == 0) return 0; - } + else + return BAD_MUTEX_E; + } - - #elif defined(USE_WINDOWS_API) - - int wc_InitMutex(wolfSSL_Mutex* m) - { - InitializeCriticalSection(m); + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + if (tx_mutex_put(m) == 0) return 0; - } + else + return BAD_MUTEX_E; + } +#elif defined(MICRIUM) - int wc_FreeMutex(wolfSSL_Mutex* m) - { - DeleteCriticalSection(m); - return 0; - } - - - int wc_LockMutex(wolfSSL_Mutex* m) - { - EnterCriticalSection(m); - return 0; - } - - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - LeaveCriticalSection(m); - return 0; - } - - #elif defined(WOLFSSL_PTHREADS) - - int wc_InitMutex(wolfSSL_Mutex* m) - { - if (pthread_mutex_init(m, 0) == 0) + int wc_InitMutex(wolfSSL_Mutex* m) + { + #if (NET_SECURE_MGR_CFG_EN == DEF_ENABLED) + if (NetSecure_OS_MutexCreate(m) == 0) return 0; else return BAD_MUTEX_E; - } + #else + return 0; + #endif + } - - int wc_FreeMutex(wolfSSL_Mutex* m) - { - if (pthread_mutex_destroy(m) == 0) + int wc_FreeMutex(wolfSSL_Mutex* m) + { + #if (NET_SECURE_MGR_CFG_EN == DEF_ENABLED) + if (NetSecure_OS_wc_FreeMutex(m) == 0) return 0; else return BAD_MUTEX_E; - } + #else + return 0; + #endif + } - - int wc_LockMutex(wolfSSL_Mutex* m) - { - if (pthread_mutex_lock(m) == 0) + int wc_LockMutex(wolfSSL_Mutex* m) + { + #if (NET_SECURE_MGR_CFG_EN == DEF_ENABLED) + if (NetSecure_OS_wc_LockMutex(m) == 0) return 0; else return BAD_MUTEX_E; - } + #else + return 0; + #endif + } - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - if (pthread_mutex_unlock(m) == 0) + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + #if (NET_SECURE_MGR_CFG_EN == DEF_ENABLED) + if (NetSecure_OS_wc_UnLockMutex(m) == 0) return 0; else return BAD_MUTEX_E; + #else + return 0; + #endif + + } + +#elif defined(EBSNET) + + int wc_InitMutex(wolfSSL_Mutex* m) + { + if (rtp_sig_mutex_alloc(m, "wolfSSL Mutex") == -1) + return BAD_MUTEX_E; + else + return 0; + } + + int wc_FreeMutex(wolfSSL_Mutex* m) + { + rtp_sig_mutex_free(*m); + return 0; + } + + int wc_LockMutex(wolfSSL_Mutex* m) + { + if (rtp_sig_mutex_claim_timed(*m, RTIP_INF) == 0) + return 0; + else + return BAD_MUTEX_E; + } + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + rtp_sig_mutex_release(*m); + return 0; + } + +#elif defined(FREESCALE_MQX) || defined(FREESCALE_KSDK_MQX) + + int wc_InitMutex(wolfSSL_Mutex* m) + { + if (_mutex_init(m, NULL) == MQX_EOK) + return 0; + else + return BAD_MUTEX_E; + } + + int wc_FreeMutex(wolfSSL_Mutex* m) + { + if (_mutex_destroy(m) == MQX_EOK) + return 0; + else + return BAD_MUTEX_E; + } + + int wc_LockMutex(wolfSSL_Mutex* m) + { + if (_mutex_lock(m) == MQX_EOK) + return 0; + else + return BAD_MUTEX_E; + } + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + if (_mutex_unlock(m) == MQX_EOK) + return 0; + else + return BAD_MUTEX_E; + } + +#elif defined(WOLFSSL_TIRTOS) + #include + + int wc_InitMutex(wolfSSL_Mutex* m) + { + Semaphore_Params params; + Error_Block eb; + + Error_init(&eb); + Semaphore_Params_init(¶ms); + params.mode = Semaphore_Mode_BINARY; + + *m = Semaphore_create(1, ¶ms, &eb); + if (Error_check(&eb)) { + Error_raise(&eb, Error_E_generic, "Failed to Create the semaphore.", + NULL); + return BAD_MUTEX_E; } + else + return 0; + } - #elif defined(THREADX) + int wc_FreeMutex(wolfSSL_Mutex* m) + { + Semaphore_delete(m); - int wc_InitMutex(wolfSSL_Mutex* m) - { - if (tx_mutex_create(m, "wolfSSL Mutex", TX_NO_INHERIT) == 0) - return 0; - else - return BAD_MUTEX_E; + return 0; + } + + int wc_LockMutex(wolfSSL_Mutex* m) + { + Semaphore_pend(*m, BIOS_WAIT_FOREVER); + + return 0; + } + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + Semaphore_post(*m); + + return 0; + } + +#elif defined(WOLFSSL_uITRON4) + + int wc_InitMutex(wolfSSL_Mutex* m) + { + int iReturn; + m->sem.sematr = TA_TFIFO; + m->sem.isemcnt = 1; + m->sem.maxsem = 1; + m->sem.name = NULL; + + m->id = acre_sem(&m->sem); + if( m->id != E_OK ) + iReturn = 0; + else + iReturn = BAD_MUTEX_E; + + return iReturn; + } + + int wc_FreeMutex(wolfSSL_Mutex* m) + { + del_sem( m->id ); + return 0; + } + + int wc_LockMutex(wolfSSL_Mutex* m) + { + wai_sem(m->id); + return 0; + } + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + sig_sem(m->id); + return 0; + } + + /**** uITRON malloc/free ***/ + static ID ID_wolfssl_MPOOL = 0; + static T_CMPL wolfssl_MPOOL = {TA_TFIFO, 0, NULL, "wolfSSL_MPOOL"}; + + int uITRON4_minit(size_t poolsz) { + ER ercd; + wolfssl_MPOOL.mplsz = poolsz; + ercd = acre_mpl(&wolfssl_MPOOL); + if (ercd > 0) { + ID_wolfssl_MPOOL = ercd; + return 0; + } else { + return -1; } + } - - int wc_FreeMutex(wolfSSL_Mutex* m) - { - if (tx_mutex_delete(m) == 0) - return 0; - else - return BAD_MUTEX_E; - } - - - int wc_LockMutex(wolfSSL_Mutex* m) - { - if (tx_mutex_get(m, TX_WAIT_FOREVER) == 0) - return 0; - else - return BAD_MUTEX_E; - } - - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - if (tx_mutex_put(m) == 0) - return 0; - else - return BAD_MUTEX_E; - } - - #elif defined(MICRIUM) - - int wc_InitMutex(wolfSSL_Mutex* m) - { - #if (NET_SECURE_MGR_CFG_EN == DEF_ENABLED) - if (NetSecure_OS_MutexCreate(m) == 0) - return 0; - else - return BAD_MUTEX_E; - #else - return 0; - #endif - } - - - int wc_FreeMutex(wolfSSL_Mutex* m) - { - #if (NET_SECURE_MGR_CFG_EN == DEF_ENABLED) - if (NetSecure_OS_wc_FreeMutex(m) == 0) - return 0; - else - return BAD_MUTEX_E; - #else - return 0; - #endif - } - - - int wc_LockMutex(wolfSSL_Mutex* m) - { - #if (NET_SECURE_MGR_CFG_EN == DEF_ENABLED) - if (NetSecure_OS_wc_LockMutex(m) == 0) - return 0; - else - return BAD_MUTEX_E; - #else - return 0; - #endif - } - - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - #if (NET_SECURE_MGR_CFG_EN == DEF_ENABLED) - if (NetSecure_OS_wc_UnLockMutex(m) == 0) - return 0; - else - return BAD_MUTEX_E; - #else - return 0; - #endif - - } - - #elif defined(EBSNET) - - int wc_InitMutex(wolfSSL_Mutex* m) - { - if (rtp_sig_mutex_alloc(m, "wolfSSL Mutex") == -1) - return BAD_MUTEX_E; - else - return 0; - } - - int wc_FreeMutex(wolfSSL_Mutex* m) - { - rtp_sig_mutex_free(*m); + void *uITRON4_malloc(size_t sz) { + ER ercd; + void *p; + ercd = get_mpl(ID_wolfssl_MPOOL, sz, (VP)&p); + if (ercd == E_OK) { + return p; + } else { return 0; } + } - int wc_LockMutex(wolfSSL_Mutex* m) - { - if (rtp_sig_mutex_claim_timed(*m, RTIP_INF) == 0) - return 0; - else - return BAD_MUTEX_E; - } - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - rtp_sig_mutex_release(*m); - return 0; - } - - #elif defined(FREESCALE_MQX) || defined(FREESCALE_KSDK_MQX) - - int wc_InitMutex(wolfSSL_Mutex* m) - { - if (_mutex_init(m, NULL) == MQX_EOK) - return 0; - else - return BAD_MUTEX_E; - } - - int wc_FreeMutex(wolfSSL_Mutex* m) - { - if (_mutex_destroy(m) == MQX_EOK) - return 0; - else - return BAD_MUTEX_E; - } - - int wc_LockMutex(wolfSSL_Mutex* m) - { - if (_mutex_lock(m) == MQX_EOK) - return 0; - else - return BAD_MUTEX_E; - } - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - if (_mutex_unlock(m) == MQX_EOK) - return 0; - else - return BAD_MUTEX_E; - } - - #elif defined (WOLFSSL_TIRTOS) - #include - int wc_InitMutex(wolfSSL_Mutex* m) - { - Semaphore_Params params; - Error_Block eb; - Error_init(&eb); - Semaphore_Params_init(¶ms); - params.mode = Semaphore_Mode_BINARY; - - *m = Semaphore_create(1, ¶ms, &eb); - if( Error_check( &eb ) ) - { - Error_raise( &eb, Error_E_generic, "Failed to Create the semaphore.",NULL); - return BAD_MUTEX_E; - } else return 0; - } - - int wc_FreeMutex(wolfSSL_Mutex* m) - { - Semaphore_delete(m); - - return 0; - } - - int wc_LockMutex(wolfSSL_Mutex* m) - { - Semaphore_pend(*m, BIOS_WAIT_FOREVER); - - return 0; - } - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - Semaphore_post(*m); - - return 0; - } - - #elif defined(WOLFSSL_uITRON4) - #include "stddef.h" - #include "kernel.h" - int wc_InitMutex(wolfSSL_Mutex* m) - { - int iReturn; - m->sem.sematr = TA_TFIFO ; - m->sem.isemcnt = 1 ; - m->sem.maxsem = 1 ; - m->sem.name = NULL ; - - m->id = acre_sem(&m->sem); - if( m->id != E_OK ) - iReturn = 0; - else - iReturn = BAD_MUTEX_E; - - return iReturn; - } - - int wc_FreeMutex(wolfSSL_Mutex* m) - { - del_sem( m->id ); - return 0; - } - - int wc_LockMutex(wolfSSL_Mutex* m) - { - wai_sem(m->id); - return 0; - } - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - sig_sem(m->id); - return 0; - } - - /**** uITRON malloc/free ***/ - static ID ID_wolfssl_MPOOL = 0 ; - static T_CMPL wolfssl_MPOOL = {TA_TFIFO, 0, NULL, "wolfSSL_MPOOL"}; - - int uITRON4_minit(size_t poolsz) { - ER ercd; - wolfssl_MPOOL.mplsz = poolsz ; - ercd = acre_mpl(&wolfssl_MPOOL); - if (ercd > 0) { - ID_wolfssl_MPOOL = ercd; - return 0; - } else { - return -1; - } - } - - void *uITRON4_malloc(size_t sz) { - ER ercd; - void *p ; - ercd = get_mpl(ID_wolfssl_MPOOL, sz, (VP)&p); - if (ercd == E_OK) { - return p; - } else { - return 0 ; - } - } - - void *uITRON4_realloc(void *p, size_t sz) { - ER ercd; - void *newp ; - if(p) { - ercd = get_mpl(ID_wolfssl_MPOOL, sz, (VP)&newp); + void *uITRON4_realloc(void *p, size_t sz) { + ER ercd; + void *newp; + if(p) { + ercd = get_mpl(ID_wolfssl_MPOOL, sz, (VP)&newp); + if (ercd == E_OK) { + XMEMCPY(newp, p, sz); + ercd = rel_mpl(ID_wolfssl_MPOOL, (VP)p); if (ercd == E_OK) { - XMEMCPY(newp, p, sz) ; - ercd = rel_mpl(ID_wolfssl_MPOOL, (VP)p); - if (ercd == E_OK) { - return newp; - } + return newp; } } - return 0 ; - } + } + return 0; + } - void uITRON4_free(void *p) { - ER ercd; - ercd = rel_mpl(ID_wolfssl_MPOOL, (VP)p); - if (ercd == E_OK) { - return ; - } else { - return ; - } + void uITRON4_free(void *p) { + ER ercd; + ercd = rel_mpl(ID_wolfssl_MPOOL, (VP)p); + if (ercd == E_OK) { + return; + } else { + return; } + } #elif defined(WOLFSSL_uTKERNEL2) - #include "tk/tkernel.h" - int wc_InitMutex(wolfSSL_Mutex* m) - { - int iReturn; - m->sem.sematr = TA_TFIFO ; - m->sem.isemcnt = 1 ; - m->sem.maxsem = 1 ; - m->id = tk_cre_sem(&m->sem); - if( m->id != NULL ) - iReturn = 0; - else - iReturn = BAD_MUTEX_E; + int wc_InitMutex(wolfSSL_Mutex* m) + { + int iReturn; + m->sem.sematr = TA_TFIFO; + m->sem.isemcnt = 1; + m->sem.maxsem = 1; - return iReturn; + m->id = tk_cre_sem(&m->sem); + if( m->id != NULL ) + iReturn = 0; + else + iReturn = BAD_MUTEX_E; + + return iReturn; + } + + int wc_FreeMutex(wolfSSL_Mutex* m) + { + tk_del_sem( m->id ); + return 0; + } + + int wc_LockMutex(wolfSSL_Mutex* m) + { + tk_wai_sem(m->id, 1, TMO_FEVR); + return 0; + } + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + tk_sig_sem(m->id, 1); + return 0; + } + + /**** uT-Kernel malloc/free ***/ + static ID ID_wolfssl_MPOOL = 0; + static T_CMPL wolfssl_MPOOL = + {(void *)NULL, + TA_TFIFO , 0, "wolfSSL_MPOOL"}; + + int uTKernel_init_mpool(unsigned int sz) { + ER ercd; + wolfssl_MPOOL.mplsz = sz; + ercd = tk_cre_mpl(&wolfssl_MPOOL); + if (ercd > 0) { + ID_wolfssl_MPOOL = ercd; + return 0; + } else { + return -1; } + } - int wc_FreeMutex(wolfSSL_Mutex* m) - { - tk_del_sem( m->id ); + void *uTKernel_malloc(unsigned int sz) { + ER ercd; + void *p; + ercd = tk_get_mpl(ID_wolfssl_MPOOL, sz, (VP)&p, TMO_FEVR); + if (ercd == E_OK) { + return p; + } else { return 0; } + } - int wc_LockMutex(wolfSSL_Mutex* m) - { - tk_wai_sem(m->id, 1, TMO_FEVR); - return 0; - } - - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - tk_sig_sem(m->id, 1); - return 0; - } - - /**** uT-Kernel malloc/free ***/ - static ID ID_wolfssl_MPOOL = 0 ; - static T_CMPL wolfssl_MPOOL = - {(void *)NULL, - TA_TFIFO , 0, "wolfSSL_MPOOL"}; - - int uTKernel_init_mpool(unsigned int sz) { - ER ercd; - wolfssl_MPOOL.mplsz = sz ; - ercd = tk_cre_mpl(&wolfssl_MPOOL); - if (ercd > 0) { - ID_wolfssl_MPOOL = ercd; - return 0; - } else { - return -1; - } - } - - void *uTKernel_malloc(unsigned int sz) { - ER ercd; - void *p ; - ercd = tk_get_mpl(ID_wolfssl_MPOOL, sz, (VP)&p, TMO_FEVR); - if (ercd == E_OK) { - return p; - } else { - return 0 ; - } - } - - void *uTKernel_realloc(void *p, unsigned int sz) { - ER ercd; - void *newp ; - if(p) { - ercd = tk_get_mpl(ID_wolfssl_MPOOL, sz, (VP)&newp, TMO_FEVR); + void *uTKernel_realloc(void *p, unsigned int sz) { + ER ercd; + void *newp; + if(p) { + ercd = tk_get_mpl(ID_wolfssl_MPOOL, sz, (VP)&newp, TMO_FEVR); + if (ercd == E_OK) { + XMEMCPY(newp, p, sz); + ercd = tk_rel_mpl(ID_wolfssl_MPOOL, (VP)p); if (ercd == E_OK) { - XMEMCPY(newp, p, sz) ; - ercd = tk_rel_mpl(ID_wolfssl_MPOOL, (VP)p); - if (ercd == E_OK) { - return newp; - } + return newp; } } - return 0 ; - } + } + return 0; + } - void uTKernel_free(void *p) { - ER ercd; - ercd = tk_rel_mpl(ID_wolfssl_MPOOL, (VP)p); - if (ercd == E_OK) { - return ; - } else { - return ; - } - } - #elif defined (WOLFSSL_FROSTED) - int wc_InitMutex(wolfSSL_Mutex* m) - { - *m = mutex_init(); - if (*m) - return 0; - else - return -1; + void uTKernel_free(void *p) { + ER ercd; + ercd = tk_rel_mpl(ID_wolfssl_MPOOL, (VP)p); + if (ercd == E_OK) { + return; + } else { + return; } + } - int wc_FreeMutex(wolfSSL_Mutex* m) - { - mutex_destroy(*m); - return(0) ; - } +#elif defined (WOLFSSL_FROSTED) - int wc_LockMutex(wolfSSL_Mutex* m) - { - mutex_lock(*m); + int wc_InitMutex(wolfSSL_Mutex* m) + { + *m = mutex_init(); + if (*m) return 0; - } + else + return -1; + } - int wc_UnLockMutex(wolfSSL_Mutex* m) - { - mutex_unlock(*m); + int wc_FreeMutex(wolfSSL_Mutex* m) + { + mutex_destroy(*m); + return(0); + } + + int wc_LockMutex(wolfSSL_Mutex* m) + { + mutex_lock(*m); + return 0; + } + + int wc_UnLockMutex(wolfSSL_Mutex* m) + { + mutex_unlock(*m); + return 0; + } + +#elif defined(WOLFSSL_CMSIS_RTOS) + + #define CMSIS_NMUTEX 10 + osMutexDef(wolfSSL_mt0); osMutexDef(wolfSSL_mt1); osMutexDef(wolfSSL_mt2); + osMutexDef(wolfSSL_mt3); osMutexDef(wolfSSL_mt4); osMutexDef(wolfSSL_mt5); + osMutexDef(wolfSSL_mt6); osMutexDef(wolfSSL_mt7); osMutexDef(wolfSSL_mt8); + osMutexDef(wolfSSL_mt9); + + static const osMutexDef_t *CMSIS_mutex[] = { osMutex(wolfSSL_mt0), + osMutex(wolfSSL_mt1), osMutex(wolfSSL_mt2), osMutex(wolfSSL_mt3), + osMutex(wolfSSL_mt4), osMutex(wolfSSL_mt5), osMutex(wolfSSL_mt6), + osMutex(wolfSSL_mt7), osMutex(wolfSSL_mt8), osMutex(wolfSSL_mt9) }; + + static osMutexId CMSIS_mutexID[CMSIS_NMUTEX] = {0}; + + int wc_InitMutex(wolfSSL_Mutex* m) + { + int i; + for (i=0; i /* initialize and Mutex for TI Crypt Engine */ #include /* md5, sha1, sha224, sha256 */ #endif diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index ffbd6b552..28d2bc1bf 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -5258,91 +5258,93 @@ byte GetEntropy(ENTROPY_CMD cmd, byte* out) #endif /* HAVE_NTRU */ -#ifndef NO_RSA - -#if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) - #ifdef FREESCALE_MQX - static const char* clientKey = "a:\\certs\\client-key.der"; - static const char* clientCert = "a:\\certs\\client-cert.der"; - #ifdef HAVE_PKCS7 - static const char* eccClientKey = "a:\\certs\\ecc-client-key.der"; - static const char* eccClientCert = "a:\\certs\\client-ecc-cert.der"; - #endif - #ifdef WOLFSSL_CERT_EXT - static const char* clientKeyPub = "a:\\certs\\client-keyPub.der"; - #endif - #ifdef WOLFSSL_CERT_GEN - static const char* caKeyFile = "a:\\certs\\ca-key.der"; - #ifdef WOLFSSL_CERT_EXT - static const char* caKeyPubFile = "a:\\certs\\ca-keyPub.der"; - #endif - static const char* caCertFile = "a:\\certs\\ca-cert.pem"; - #ifdef HAVE_ECC - static const char* eccCaKeyFile = "a:\\certs\\ecc-key.der"; - #ifdef WOLFSSL_CERT_EXT - static const char* eccCaKeyPubFile = "a:\\certs\\ecc-keyPub.der"; - #endif - static const char* eccCaCertFile = "a:\\certs\\server-ecc.pem"; - #endif - #endif - #elif defined(WOLFSSL_MKD_SHELL) - static char* clientKey = "certs/client-key.der"; - static char* clientCert = "certs/client-cert.der"; - void set_clientKey(char *key) { clientKey = key ; } - void set_clientCert(char *cert) { clientCert = cert ; } - #ifdef HAVE_PKCS7 - static const char* eccClientKey = "certs/ecc-client-key.der"; - static const char* eccClientCert = "certs/client-ecc-cert.der"; - void set_eccClientKey(char* key) { eccClientKey = key ; } - void set_eccClientCert(char* cert) { eccClientCert = cert ; } - #endif - #ifdef WOLFSSL_CERT_EXT - static const char* clientKeyPub = "certs/client-keyPub.der"; - void set_clientKeyPub(char *key) { clientKeyPub = key ; } - #endif - #ifdef WOLFSSL_CERT_GEN - static char* caKeyFile = "certs/ca-key.der"; - #ifdef WOLFSSL_CERT_EXT - static const char* caKeyPubFile = "certs/ca-keyPub.der"; - void set_caKeyPubFile (char * key) { caKeyPubFile = key ; } - #endif - static char* caCertFile = "certs/ca-cert.pem"; - void set_caKeyFile (char * key) { caKeyFile = key ; } - void set_caCertFile(char * cert) { caCertFile = cert ; } - #ifdef HAVE_ECC - static const char* eccCaKeyFile = "certs/ecc-key.der"; - #ifdef WOLFSSL_CERT_EXT - static const char* eccCaKeyPubFile = "certs/ecc-keyPub.der"; - void set_eccCaKeyPubFile(char * key) { eccCaKeyPubFile = key ; } - #endif - static const char* eccCaCertFile = "certs/server-ecc.pem"; - void set_eccCaKeyFile (char * key) { eccCaKeyFile = key ; } - void set_eccCaCertFile(char * cert) { eccCaCertFile = cert ; } - #endif - #endif - #else - static const char* clientKey = "./certs/client-key.der"; - static const char* clientCert = "./certs/client-cert.der"; - #ifdef HAVE_PKCS7 - static const char* eccClientKey = "./certs/ecc-client-key.der"; - static const char* eccClientCert = "./certs/client-ecc-cert.der"; - #endif - #ifdef WOLFSSL_CERT_EXT - static const char* clientKeyPub = "./certs/client-keyPub.der"; - #endif - #ifdef WOLFSSL_CERT_GEN - static const char* caKeyFile = "./certs/ca-key.der"; - static const char* caCertFile = "./certs/ca-cert.pem"; - #ifdef HAVE_ECC - static const char* eccCaKeyFile = "./certs/ecc-key.der"; - #ifdef WOLFSSL_CERT_EXT - static const char* eccCaKeyPubFile = "./certs/ecc-keyPub.der"; - #endif - static const char* eccCaCertFile = "./certs/server-ecc.pem"; - #endif - #endif - #endif +/* Cert Paths */ +#ifdef FREESCALE_MQX + #define CERT_PREFIX "a:\\" + #define CERT_PATH_SEP "\\" +#elif defined(WOLFSSL_MKD_SHELL) + #define CERT_PREFIX "" + #define CERT_PATH_SEP "/" +#else + #define CERT_PREFIX "./" + #define CERT_PATH_SEP "/" #endif +#define CERT_ROOT CERT_PREFIX "certs" CERT_PATH_SEP + +/* Generated Test Certs */ +#if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) && \ + !defined(NO_ASN) + #ifndef NO_RSA + static const char* clientKey = CERT_ROOT "client-key.der"; + static const char* clientCert = CERT_ROOT "client-cert.der"; + #ifdef HAVE_PKCS7 + static const char* eccClientKey = CERT_ROOT "ecc-client-key.der"; + static const char* eccClientCert = CERT_ROOT "client-ecc-cert.der"; + #endif + #ifdef WOLFSSL_CERT_EXT + static const char* clientKeyPub = CERT_ROOT "client-keyPub.der"; + #endif + #ifdef WOLFSSL_CERT_GEN + static const char* caKeyFile = CERT_ROOT "ca-key.der"; + static const char* caCertFile = CERT_ROOT "ca-cert.pem"; + #endif + #endif /* !NO_RSA */ + #ifndef NO_DH + static const char* dhKey = CERT_ROOT "dh2048.der"; + #endif + #ifndef NO_DSA + static const char* dsaKey = CERT_ROOT "dsa2048.der"; + #endif +#endif /* !USE_CERT_BUFFER_* */ +#if !defined(USE_CERT_BUFFERS_256) && !defined(NO_ASN) + #ifdef HAVE_ECC + #ifdef WOLFSSL_CERT_GEN + static const char* eccCaCertFile = CERT_ROOT "server-ecc.pem"; + #endif + #ifdef WOLFSSL_CERT_EXT + static const char* eccCaKeyPubFile = CERT_ROOT "ecc-keyPub.der"; + #endif + #endif /* HAVE_ECC */ +#endif /* !USE_CERT_BUFFER_* */ + +/* Temporary Cert Files */ +#ifdef HAVE_ECC + #ifdef WOLFSSL_CERT_GEN + static const char* certEccPemFile = CERT_PREFIX "certecc.pem"; + #endif + #ifdef WOLFSSL_KEY_GEN + static const char* eccCaKeyPemFile = CERT_PREFIX "ecc-key.pem"; + static const char* eccPubKeyDerFile = CERT_PREFIX "ecc-public-key.der"; + #endif + #if defined(WOLFSSL_CERT_GEN) || defined(WOLFSSL_KEY_GEN) + static const char* eccCaKeyFile = CERT_PREFIX "ecc-key.der"; + #endif + #if defined(WOLFSSL_CERT_GEN) || \ + (defined(WOLFSSL_CERT_EXT) && defined(WOLFSSL_TEST_CERT)) + static const char* certEccDerFile = CERT_PREFIX "certecc.der"; + #endif +#endif /* HAVE_ECC */ + +#ifndef NO_RSA + #if defined(WOLFSSL_CERT_GEN) || defined(WOLFSSL_CERT_EXT) + static const char* otherCertDerFile = CERT_PREFIX "othercert.der"; + static const char* certDerFile = CERT_PREFIX "cert.der"; + #endif + #ifdef WOLFSSL_CERT_GEN + static const char* otherCertPemFile = CERT_PREFIX "othercert.pem"; + static const char* certPemFile = CERT_PREFIX "cert.pem"; + #endif + #ifdef WOLFSSL_KEY_GEN + static const char* keyDerFile = CERT_PREFIX "key.der"; + static const char* keyPemFile = CERT_PREFIX "key.pem"; + #endif + #ifdef WOLFSSL_CERT_REQ + static const char* certReqDerFile = CERT_PREFIX "certreq.der"; + static const char* certReqPemFile = CERT_PREFIX "certreq.pem"; + #endif +#endif /* !NO_RSA */ + +#ifndef NO_RSA #if !defined(NO_ASN_TIME) && defined(WOLFSSL_TEST_CERT) int cert_test(void) @@ -5435,12 +5437,8 @@ int certext_test(void) if (tmp == NULL) return -200; - /* load othercert.pem (Cert signed by an authority) */ -#ifdef FREESCALE_MQX - file = fopen("a:\\certs\\othercert.der", "rb"); -#else - file = fopen("./othercert.der", "rb"); -#endif + /* load othercert.der (Cert signed by an authority) */ + file = fopen(otherCertDerFile, "rb"); if (!file) { XFREE(tmp, HEAP_HINT ,DYNAMIC_TYPE_TMP_BUFFER); return -200; @@ -5486,12 +5484,8 @@ int certext_test(void) FreeDecodedCert(&cert); #ifdef HAVE_ECC - /* load certecc.pem (Cert signed by an authority) */ -#ifdef FREESCALE_MQX - file = fopen("a:\\certs\\certecc.der", "rb"); -#else - file = fopen("./certecc.der", "rb"); -#endif + /* load certecc.der (Cert signed by an authority) */ + file = fopen(certEccDerFile, "rb"); if (!file) { XFREE(tmp, HEAP_HINT ,DYNAMIC_TYPE_TMP_BUFFER); return -210; @@ -5540,12 +5534,8 @@ int certext_test(void) FreeDecodedCert(&cert); #endif /* HAVE_ECC */ - /* load cert.pem (self signed certificate) */ -#ifdef FREESCALE_MQX - file = fopen("a:\\certs\\cert.der", "rb"); -#else - file = fopen("./cert.der", "rb"); -#endif + /* load cert.der (self signed certificate) */ + file = fopen(certDerFile, "rb"); if (!file) { XFREE(tmp, HEAP_HINT ,DYNAMIC_TYPE_TMP_BUFFER); return -220; @@ -6081,7 +6071,6 @@ int rsa_test(void) bytes = sizeof_client_key_der_2048; #else file = fopen(clientKey, "rb"); - if (!file) { err_sys("can't open ./certs/client-key.der, " "Please run from wolfSSL home dir", -40); @@ -6601,8 +6590,10 @@ int rsa_test(void) int pemSz = 0; RsaKey derIn; RsaKey genKey; + #ifndef NO_FILESYSTEM FILE* keyFile; FILE* pemFile; + #endif ret = wc_InitRsaKey(&genKey, HEAP_HINT); if (ret != 0) { @@ -6642,11 +6633,8 @@ int rsa_test(void) return -302; } -#ifdef FREESCALE_MQX - keyFile = fopen("a:\\certs\\key.der", "wb"); -#else - keyFile = fopen("./key.der", "wb"); -#endif + #ifndef NO_FILESYSTEM + keyFile = fopen(keyDerFile, "wb"); if (!keyFile) { XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6665,6 +6653,7 @@ int rsa_test(void) wc_FreeRng(&rng); return -313; } + #endif pemSz = wc_DerToPem(der, derSz, pem, FOURK_BUF, PRIVATEKEY_TYPE); if (pemSz < 0) { @@ -6676,11 +6665,8 @@ int rsa_test(void) return -304; } -#ifdef FREESCALE_MQX - pemFile = fopen("a:\\certs\\key.pem", "wb"); -#else - pemFile = fopen("./key.pem", "wb"); -#endif + #ifndef NO_FILESYSTEM + pemFile = fopen(keyPemFile, "wb"); if (!pemFile) { XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6699,6 +6685,7 @@ int rsa_test(void) wc_FreeRng(&rng); return -314; } + #endif ret = wc_InitRsaKey(&derIn, HEAP_HINT); if (ret != 0) { @@ -6769,7 +6756,7 @@ int rsa_test(void) myCert.isCA = 1; myCert.sigType = CTC_SHA256wRSA; -#ifdef WOLFSSL_CERT_EXT + #ifdef WOLFSSL_CERT_EXT /* add Policies */ strncpy(myCert.certPolicies[0], "2.16.840.1.101.3.4.1.42", CTC_MAX_CERTPOL_SZ); @@ -6803,7 +6790,7 @@ int rsa_test(void) wc_FreeRng(&rng); return -400; } -#endif /* WOLFSSL_CERT_EXT */ + #endif /* WOLFSSL_CERT_EXT */ certSz = wc_MakeSelfCert(&myCert, derCert, FOURK_BUF, &key, &rng); if (certSz < 0) { @@ -6814,7 +6801,7 @@ int rsa_test(void) return -401; } -#ifdef WOLFSSL_TEST_CERT + #ifdef WOLFSSL_TEST_CERT InitDecodedCert(&decode, derCert, certSz, HEAP_HINT); ret = ParseCert(&decode, CERT_TYPE, NO_VERIFY, 0); if (ret != 0) { @@ -6825,13 +6812,10 @@ int rsa_test(void) return -402; } FreeDecodedCert(&decode); -#endif + #endif -#ifdef FREESCALE_MQX - derFile = fopen("a:\\certs\\cert.der", "wb"); -#else - derFile = fopen("./cert.der", "wb"); -#endif + #ifndef NO_FILESYSTEM + derFile = fopen(certDerFile, "wb"); if (!derFile) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6848,6 +6832,7 @@ int rsa_test(void) wc_FreeRng(&rng); return -414; } + #endif pemSz = wc_DerToPem(derCert, certSz, pem, FOURK_BUF, CERT_TYPE); if (pemSz < 0) { @@ -6858,11 +6843,8 @@ int rsa_test(void) return -404; } -#ifdef FREESCALE_MQX - pemFile = fopen("a:\\certs\\cert.pem", "wb"); -#else - pemFile = fopen("./cert.pem", "wb"); -#endif + #ifndef NO_FILESYSTEM + pemFile = fopen(certPemFile, "wb"); if (!pemFile) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6879,6 +6861,8 @@ int rsa_test(void) wc_FreeRng(&rng); return -406; } + #endif + XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); } @@ -6894,10 +6878,12 @@ int rsa_test(void) int pemSz; size_t bytes3; word32 idx3 = 0; - FILE* file3 ; -#ifdef WOLFSSL_TEST_CERT + #if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) + FILE* file3; + #endif + #ifdef WOLFSSL_TEST_CERT DecodedCert decode; -#endif + #endif derCert = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6914,8 +6900,14 @@ int rsa_test(void) return -312; } + #ifdef USE_CERT_BUFFERS_1024 + XMEMCPY(tmp, ca_key_der_1024, sizeof_ca_key_der_1024); + bytes3 = sizeof_ca_key_der_1024; + #elif defined(USE_CERT_BUFFERS_2048) + XMEMCPY(tmp, ca_key_der_2048, sizeof_ca_key_der_2048); + bytes3 = sizeof_ca_key_der_2048; + #else file3 = fopen(caKeyFile, "rb"); - if (!file3) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6926,6 +6918,7 @@ int rsa_test(void) bytes3 = fread(tmp, 1, FOURK_BUF, file3); fclose(file3); + #endif /* USE_CERT_BUFFERS */ ret = wc_InitRsaKey(&caKey, HEAP_HINT); if (ret != 0) { @@ -6947,9 +6940,9 @@ int rsa_test(void) wc_InitCert(&myCert); -#ifdef NO_SHA + #ifdef NO_SHA myCert.sigType = CTC_SHA256wRSA; -#endif + #endif strncpy(myCert.subject.country, "US", CTC_NAME_SIZE); strncpy(myCert.subject.state, "OR", CTC_NAME_SIZE); @@ -6959,7 +6952,7 @@ int rsa_test(void) strncpy(myCert.subject.commonName, "www.yassl.com", CTC_NAME_SIZE); strncpy(myCert.subject.email, "info@yassl.com", CTC_NAME_SIZE); -#ifdef WOLFSSL_CERT_EXT + #ifdef WOLFSSL_CERT_EXT /* add Policies */ strncpy(myCert.certPolicies[0], "2.16.840.1.101.3.4.1.42", CTC_MAX_CERTPOL_SZ); @@ -6975,7 +6968,16 @@ int rsa_test(void) } /* add AKID from the CA certificate */ - if (wc_SetAuthKeyId(&myCert, caCertFile) != 0) { + #if defined(USE_CERT_BUFFERS_2048) + ret = wc_SetAuthKeyIdFromCert(&myCert, ca_cert_der_2048, + sizeof_ca_cert_der_2048); + #elif defined(USE_CERT_BUFFERS_1024) + ret = wc_SetAuthKeyIdFromCert(&myCert, ca_cert_der_1024, + sizeof_ca_cert_der_1024); + #else + ret = wc_SetAuthKeyId(&myCert, caCertFile); + #endif + if (ret != 0) { XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6991,9 +6993,17 @@ int rsa_test(void) wc_FreeRng(&rng); return -400; } -#endif /* WOLFSSL_CERT_EXT */ + #endif /* WOLFSSL_CERT_EXT */ + #if defined(USE_CERT_BUFFERS_2048) + ret = wc_SetIssuerBuffer(&myCert, ca_cert_der_2048, + sizeof_ca_cert_der_2048); + #elif defined(USE_CERT_BUFFERS_1024) + ret = wc_SetIssuerBuffer(&myCert, ca_cert_der_1024, + sizeof_ca_cert_der_1024); + #else ret = wc_SetIssuer(&myCert, caCertFile); + #endif if (ret < 0) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7024,7 +7034,7 @@ int rsa_test(void) return -408; } -#ifdef WOLFSSL_TEST_CERT + #ifdef WOLFSSL_TEST_CERT InitDecodedCert(&decode, derCert, certSz, HEAP_HINT); ret = ParseCert(&decode, CERT_TYPE, NO_VERIFY, 0); if (ret != 0) { @@ -7036,13 +7046,10 @@ int rsa_test(void) return -409; } FreeDecodedCert(&decode); -#endif + #endif -#ifdef FREESCALE_MQX - derFile = fopen("a:\\certs\\othercert.der", "wb"); -#else - derFile = fopen("./othercert.der", "wb"); -#endif +#ifndef NO_FILESYSTEM + derFile = fopen(otherCertDerFile, "wb"); if (!derFile) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7072,11 +7079,7 @@ int rsa_test(void) return -411; } -#ifdef FREESCALE_MQX - pemFile = fopen("a:\\certs\\othercert.pem", "wb"); -#else - pemFile = fopen("./othercert.pem", "wb"); -#endif + pemFile = fopen(otherCertPemFile, "wb"); if (!pemFile) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7096,6 +7099,8 @@ int rsa_test(void) return -415; } fclose(pemFile); +#endif /* !NO_FILESYSTEM */ + XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); wc_FreeRsaKey(&caKey); @@ -7113,13 +7118,15 @@ int rsa_test(void) int pemSz; size_t bytes3; word32 idx3 = 0; + #ifndef USE_CERT_BUFFERS_256 FILE* file3; -#ifdef WOLFSSL_CERT_EXT + #endif + #ifdef WOLFSSL_CERT_EXT ecc_key caKeyPub; -#endif -#ifdef WOLFSSL_TEST_CERT + #endif + #ifdef WOLFSSL_TEST_CERT DecodedCert decode; -#endif + #endif derCert = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7136,6 +7143,10 @@ int rsa_test(void) return -5312; } + #ifdef USE_CERT_BUFFERS_256 + XMEMCPY(tmp, ecc_key_der_256, sizeof_ecc_key_der_256); + bytes3 = sizeof_ecc_key_der_256; + #else file3 = fopen(eccCaKeyFile, "rb"); if (!file3) { @@ -7148,6 +7159,7 @@ int rsa_test(void) bytes3 = fread(tmp, 1, FOURK_BUF, file3); fclose(file3); + #endif /* USE_CERT_BUFFERS_256 */ wc_ecc_init(&caKey); ret = wc_EccPrivateKeyDecode(tmp, &idx3, &caKey, (word32)bytes3); @@ -7178,7 +7190,10 @@ int rsa_test(void) CTC_MAX_CERTPOL_SZ); myCert.certPoliciesNb = 2; - + #ifdef USE_CERT_BUFFERS_256 + XMEMCPY(tmp, ecc_key_pub_der_256, sizeof_ecc_key_pub_der_256); + bytes3 = sizeof_ecc_key_pub_der_256; + #else file3 = fopen(eccCaKeyPubFile, "rb"); if (!file3) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7190,6 +7205,7 @@ int rsa_test(void) bytes3 = fread(tmp, 1, FOURK_BUF, file3); fclose(file3); + #endif wc_ecc_init(&caKeyPub); if (ret != 0) { @@ -7242,7 +7258,12 @@ int rsa_test(void) } #endif /* WOLFSSL_CERT_EXT */ + #if defined(USE_CERT_BUFFERS_256) + ret = wc_SetIssuerBuffer(&myCert, serv_ecc_der_256, + sizeof_serv_ecc_der_256); + #else ret = wc_SetIssuer(&myCert, eccCaCertFile); + #endif if (ret < 0) { XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7287,11 +7308,7 @@ int rsa_test(void) FreeDecodedCert(&decode); #endif -#ifdef FREESCALE_MQX - derFile = fopen("a:\\certs\\certecc.der", "wb"); -#else - derFile = fopen("./certecc.der", "wb"); -#endif + derFile = fopen(certEccDerFile, "wb"); if (!derFile) { XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7321,11 +7338,7 @@ int rsa_test(void) return -5411; } -#ifdef FREESCALE_MQX - pemFile = fopen("a:\\certs\\certecc.pem", "wb"); -#else - pemFile = fopen("./certecc.pem", "wb"); -#endif + pemFile = fopen(certEccPemFile, "wb"); if (!pemFile) { XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7358,14 +7371,16 @@ int rsa_test(void) byte* pem; FILE* derFile; FILE* pemFile; + #if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) FILE* caFile; + #endif FILE* ntruPrivFile; int certSz; int pemSz; word32 idx3 = 0; -#ifdef WOLFSSL_TEST_CERT + #ifdef WOLFSSL_TEST_CERT DecodedCert decode; -#endif + #endif derCert = (byte*)XMALLOC(FOURK_BUF, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); if (derCert == NULL) { @@ -7431,8 +7446,14 @@ int rsa_test(void) return -451; } + #ifdef USE_CERT_BUFFERS_1024 + XMEMCPY(tmp, ca_key_der_1024, sizeof_ca_key_der_1024); + bytes = sizeof_ca_key_der_1024; + #elif defined(USE_CERT_BUFFERS_2048) + XMEMCPY(tmp, ca_key_der_2048, sizeof_ca_key_der_2048); + bytes = sizeof_ca_key_der_2048; + #else caFile = fopen(caKeyFile, "rb"); - if (!caFile) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7443,6 +7464,7 @@ int rsa_test(void) bytes = fread(tmp, 1, FOURK_BUF, caFile); fclose(caFile); + #endif /* USE_CERT_BUFFERS */ ret = wc_InitRsaKey(&caKey, HEAP_HINT); if (ret != 0) { @@ -7472,8 +7494,7 @@ int rsa_test(void) strncpy(myCert.subject.email, "info@yassl.com", CTC_NAME_SIZE); myCert.daysValid = 1000; -#ifdef WOLFSSL_CERT_EXT - + #ifdef WOLFSSL_CERT_EXT /* add SKID from the Public Key */ if (wc_SetSubjectKeyIdFromNtruPublicKey(&myCert, public_key, public_key_len) != 0) { @@ -7485,7 +7506,16 @@ int rsa_test(void) } /* add AKID from the CA certificate */ - if (wc_SetAuthKeyId(&myCert, caCertFile) != 0) { + #if defined(USE_CERT_BUFFERS_2048) + ret = wc_SetAuthKeyIdFromCert(&myCert, ca_cert_der_2048, + sizeof_ca_cert_der_2048); + #elif defined(USE_CERT_BUFFERS_1024) + ret = wc_SetAuthKeyIdFromCert(&myCert, ca_cert_der_1024, + sizeof_ca_cert_der_1024); + #else + ret = wc_SetAuthKeyId(&myCert, caCertFile); + #endif + if (ret != 0) { XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7502,9 +7532,17 @@ int rsa_test(void) wc_FreeRng(&rng); return -494; } -#endif /* WOLFSSL_CERT_EXT */ + #endif /* WOLFSSL_CERT_EXT */ + #if defined(USE_CERT_BUFFERS_2048) + ret = wc_SetIssuerBuffer(&myCert, ca_cert_der_2048, + sizeof_ca_cert_der_2048); + #elif defined(USE_CERT_BUFFERS_1024) + ret = wc_SetIssuerBuffer(&myCert, ca_cert_der_1024, + sizeof_ca_cert_der_1024); + #else ret = wc_SetIssuer(&myCert, caCertFile); + #endif if (ret < 0) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7537,7 +7575,7 @@ int rsa_test(void) } -#ifdef WOLFSSL_TEST_CERT + #ifdef WOLFSSL_TEST_CERT InitDecodedCert(&decode, derCert, certSz, HEAP_HINT); ret = ParseCert(&decode, CERT_TYPE, NO_VERIFY, 0); if (ret != 0) { @@ -7548,7 +7586,9 @@ int rsa_test(void) return -458; } FreeDecodedCert(&decode); -#endif + #endif + + #ifndef NO_FILESYSTEM derFile = fopen("./ntru-cert.der", "wb"); if (!derFile) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7566,6 +7606,7 @@ int rsa_test(void) wc_FreeRng(&rng); return -473; } + #endif pemSz = wc_DerToPem(derCert, certSz, pem, FOURK_BUF, CERT_TYPE); if (pemSz < 0) { @@ -7576,6 +7617,7 @@ int rsa_test(void) return -460; } + #ifndef NO_FILESYSTEM pemFile = fopen("./ntru-cert.pem", "wb"); if (!pemFile) { XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7611,6 +7653,8 @@ int rsa_test(void) wc_FreeRng(&rng); return -475; } + #endif + XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(derCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); } @@ -7652,7 +7696,7 @@ int rsa_test(void) strncpy(req.subject.email, "info@yassl.com", CTC_NAME_SIZE); req.sigType = CTC_SHA256wRSA; -#ifdef WOLFSSL_CERT_EXT + #ifdef WOLFSSL_CERT_EXT /* add SKID from the Public Key */ if (wc_SetSubjectKeyIdFromPublicKey(&req, &keypub, NULL) != 0) { XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7671,7 +7715,7 @@ int rsa_test(void) wc_FreeRng(&rng); return -494; } -#endif /* WOLFSSL_CERT_EXT */ + #endif /* WOLFSSL_CERT_EXT */ derSz = wc_MakeCertReq(&req, der, FOURK_BUF, &key, NULL); if (derSz < 0) { @@ -7701,11 +7745,8 @@ int rsa_test(void) return -467; } -#ifdef FREESCALE_MQX - reqFile = fopen("a:\\certs\\certreq.der", "wb"); -#else - reqFile = fopen("./certreq.der", "wb"); -#endif + #ifndef NO_FILESYSTEM + reqFile = fopen(certReqDerFile, "wb"); if (!reqFile) { XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7724,11 +7765,7 @@ int rsa_test(void) return -471; } -#ifdef FREESCALE_MQX - reqFile = fopen("a:\\certs\\certreq.pem", "wb"); -#else - reqFile = fopen("./certreq.pem", "wb"); -#endif + reqFile = fopen(certReqPemFile, "wb"); if (!reqFile) { XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7745,6 +7782,7 @@ int rsa_test(void) wc_FreeRng(&rng); return -470; } + #endif XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -7770,16 +7808,6 @@ int rsa_test(void) #ifndef NO_DH -#if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) - #ifdef FREESCALE_MQX - static const char* dhKey = "a:\\certs\\dh2048.der"; - #elif defined(NO_ASN) - /* don't use file, no DER parsing */ - #else - static const char* dhKey = "./certs/dh2048.der"; - #endif -#endif - static int dh_generate_test(WC_RNG *rng) { int ret; @@ -7848,7 +7876,6 @@ int dh_test(void) /* don't use file, no DER parsing */ #else FILE* file = fopen(dhKey, "rb"); - if (!file) return -50; @@ -7919,14 +7946,6 @@ int dh_test(void) #ifndef NO_DSA -#if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) - #ifdef FREESCALE_MQX - static const char* dsaKey = "a:\\certs\\dsa2048.der"; - #else - static const char* dsaKey = "./certs/dsa2048.der"; - #endif -#endif - int dsa_test(void) { int ret, answer; @@ -7939,7 +7958,6 @@ int dsa_test(void) byte hash[SHA_DIGEST_SIZE]; byte signature[40]; - #ifdef USE_CERT_BUFFERS_1024 XMEMCPY(tmp, dsa_key_der_1024, sizeof_dsa_key_der_1024); bytes = sizeof_dsa_key_der_1024; @@ -7948,7 +7966,6 @@ int dsa_test(void) bytes = sizeof_dsa_key_der_2048; #else FILE* file = fopen(dsaKey, "rb"); - if (!file) return -60; @@ -7988,8 +8005,10 @@ int dsa_test(void) int pemSz = 0; DsaKey derIn; DsaKey genKey; +#ifndef NO_FILESYSTEM FILE* keyFile; FILE* pemFile; +#endif ret = wc_InitDsaKey(&genKey); if (ret != 0) return -361; @@ -8025,11 +8044,8 @@ int dsa_test(void) return -366; } -#ifdef FREESCALE_MQX - keyFile = fopen("a:\\certs\\key.der", "wb"); -#else - keyFile = fopen("./key.der", "wb"); -#endif +#ifndef NO_FILESYSTEM + keyFile = fopen(keyDerFile, "wb"); if (!keyFile) { XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -8044,6 +8060,7 @@ int dsa_test(void) wc_FreeDsaKey(&genKey); return -368; } +#endif pemSz = wc_DerToPem(der, derSz, pem, FOURK_BUF, DSA_PRIVATEKEY_TYPE); if (pemSz < 0) { @@ -8053,11 +8070,8 @@ int dsa_test(void) return -369; } -#ifdef FREESCALE_MQX - pemFile = fopen("a:\\certs\\key.pem", "wb"); -#else - pemFile = fopen("./key.pem", "wb"); -#endif +#ifndef NO_FILESYSTEM + pemFile = fopen(keyPemFile, "wb"); if (!pemFile) { XFREE(der, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); XFREE(pem, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -8072,6 +8086,7 @@ int dsa_test(void) wc_FreeDsaKey(&genKey); return -371; } +#endif ret = wc_InitDsaKey(&derIn); if (ret != 0) { @@ -9677,8 +9692,10 @@ static int ecc_test_key_gen(WC_RNG* rng, int keySize) int derSz, pemSz; byte der[FOURK_BUF]; byte pem[FOURK_BUF]; +#ifndef NO_FILESYSTEM FILE* keyFile; FILE* pemFile; +#endif ecc_key userA; @@ -9697,7 +9714,8 @@ static int ecc_test_key_gen(WC_RNG* rng, int keySize) ERROR_OUT(derSz, done); } - keyFile = fopen("./ecc-key.der", "wb"); +#ifndef NO_FILESYSTEM + keyFile = fopen(eccCaKeyFile, "wb"); if (!keyFile) { ERROR_OUT(-1025, done); } @@ -9706,13 +9724,15 @@ static int ecc_test_key_gen(WC_RNG* rng, int keySize) if (ret != derSz) { ERROR_OUT(-1026, done); } +#endif pemSz = wc_DerToPem(der, derSz, pem, FOURK_BUF, ECC_PRIVATEKEY_TYPE); if (pemSz < 0) { ERROR_OUT(pemSz, done); } - pemFile = fopen("./ecc-key.pem", "wb"); +#ifndef NO_FILESYSTEM + pemFile = fopen(eccCaKeyPemFile, "wb"); if (!pemFile) { ERROR_OUT(-1028, done); } @@ -9721,6 +9741,7 @@ static int ecc_test_key_gen(WC_RNG* rng, int keySize) if (ret != pemSz) { ERROR_OUT(-1029, done); } +#endif /* test export of public key */ derSz = wc_EccPublicKeyToDer(&userA, der, FOURK_BUF, 1); @@ -9730,11 +9751,9 @@ static int ecc_test_key_gen(WC_RNG* rng, int keySize) if (derSz == 0) { ERROR_OUT(-5416, done); } -#ifdef FREESCALE_MQX - keyFile = fopen("a:\\certs\\ecc-public-key.der", "wb"); -#else - keyFile = fopen("./ecc-public-key.der", "wb"); -#endif + +#ifndef NO_FILESYSTEM + keyFile = fopen(eccPubKeyDerFile, "wb"); if (!keyFile) { ERROR_OUT(-5417, done); } @@ -9743,6 +9762,8 @@ static int ecc_test_key_gen(WC_RNG* rng, int keySize) if (ret != derSz) { ERROR_OUT(-5418, done); } +#endif + ret = 0; done: @@ -10760,9 +10781,6 @@ int ecc_test_buffers() { size_t bytes; ecc_key cliKey; ecc_key servKey; -#ifdef WOLFSSL_CERT_EXT - ecc_key keypub; -#endif WC_RNG rng; word32 idx = 0; int ret; @@ -11938,8 +11956,10 @@ int pkcs7enveloped_test(void) size_t rsaPrivKeySz = 0; size_t eccPrivKeySz = 0; +#if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) FILE* certFile; FILE* keyFile; +#endif #ifndef NO_RSA /* read client RSA cert and key in DER format */ @@ -11953,6 +11973,13 @@ int pkcs7enveloped_test(void) return -202; } +#ifdef USE_CERT_BUFFERS_1024 + XMEMCPY(rsaCert, client_cert_der_1024, sizeof_client_cert_der_1024); + rsaCertSz = sizeof_client_cert_der_1024; +#elif defined(USE_CERT_BUFFERS_2048) + XMEMCPY(rsaCert, client_cert_der_2048, sizeof_client_cert_der_2048); + rsaCertSz = sizeof_client_cert_der_2048; +#else certFile = fopen(clientCert, "rb"); if (!certFile) { XFREE(rsaCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -11964,7 +11991,15 @@ int pkcs7enveloped_test(void) rsaCertSz = fread(rsaCert, 1, FOURK_BUF, certFile); fclose(certFile); +#endif +#ifdef USE_CERT_BUFFERS_1024 + XMEMCPY(rsaPrivKey, client_key_der_1024, sizeof_client_key_der_1024); + rsaPrivKeySz = sizeof_client_key_der_1024; +#elif defined(USE_CERT_BUFFERS_2048) + XMEMCPY(rsaPrivKey, client_key_der_2048, sizeof_client_key_der_2048); + rsaPrivKeySz = sizeof_client_key_der_2048; +#else keyFile = fopen(clientKey, "rb"); if (!keyFile) { XFREE(rsaCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -11976,6 +12011,8 @@ int pkcs7enveloped_test(void) rsaPrivKeySz = fread(rsaPrivKey, 1, FOURK_BUF, keyFile); fclose(keyFile); +#endif /* USE_CERT_BUFFERS */ + #endif /* NO_RSA */ #ifdef HAVE_ECC @@ -11995,6 +12032,10 @@ int pkcs7enveloped_test(void) return -206; } +#ifdef USE_CERT_BUFFERS_256 + XMEMCPY(eccCert, cliecc_cert_der_256, sizeof_cliecc_cert_der_256); + eccCertSz = sizeof_cliecc_cert_der_256; +#else certFile = fopen(eccClientCert, "rb"); if (!certFile) { XFREE(rsaCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -12005,10 +12046,14 @@ int pkcs7enveloped_test(void) "Please run from wolfSSL home dir", -42); return -207; } - eccCertSz = fread(eccCert, 1, FOURK_BUF, certFile); fclose(certFile); +#endif /* USE_CERT_BUFFERS_256 */ +#ifdef USE_CERT_BUFFERS_256 + XMEMCPY(eccPrivKey, ecc_clikey_der_256, sizeof_ecc_clikey_der_256); + eccPrivKeySz = sizeof_ecc_clikey_der_256; +#else keyFile = fopen(eccClientKey, "rb"); if (!keyFile) { XFREE(rsaCert, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -12019,9 +12064,9 @@ int pkcs7enveloped_test(void) "Please run from wolfSSL home dir", -43); return -208; } - eccPrivKeySz = fread(eccPrivKey, 1, FOURK_BUF, keyFile); fclose(keyFile); +#endif /* USE_CERT_BUFFERS_256 */ #endif /* HAVE_ECC */ ret = pkcs7enveloped_run_vectors(rsaCert, (word32)rsaCertSz, @@ -12248,8 +12293,9 @@ int pkcs7encrypted_test(void) int pkcs7signed_test(void) { int ret = 0; - +#if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) FILE* file; +#endif byte* certDer; byte* keyDer; byte* out; @@ -12300,6 +12346,13 @@ int pkcs7signed_test(void) } /* read in DER cert of recipient, into cert of size certSz */ +#ifdef USE_CERT_BUFFERS_1024 + XMEMCPY(certDer, client_cert_der_1024, sizeof_client_cert_der_1024); + certDerSz = sizeof_client_cert_der_1024; +#elif defined(USE_CERT_BUFFERS_2048) + XMEMCPY(certDer, client_cert_der_2048, sizeof_client_cert_der_2048); + certDerSz = sizeof_client_cert_der_2048; +#else file = fopen(clientCert, "rb"); if (!file) { XFREE(certDer, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -12311,7 +12364,15 @@ int pkcs7signed_test(void) } certDerSz = (word32)fread(certDer, 1, FOURK_BUF, file); fclose(file); +#endif /* USE_CERT_BUFFER_ */ +#ifdef USE_CERT_BUFFERS_1024 + XMEMCPY(keyDer, client_key_der_1024, sizeof_client_key_der_1024); + keyDerSz = sizeof_client_key_der_1024; +#elif defined(USE_CERT_BUFFERS_2048) + XMEMCPY(keyDer, client_key_der_2048, sizeof_client_key_der_2048); + keyDerSz = sizeof_client_key_der_2048; +#else file = fopen(clientKey, "rb"); if (!file) { XFREE(certDer, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -12323,6 +12384,7 @@ int pkcs7signed_test(void) } keyDerSz = (word32)fread(keyDer, 1, FOURK_BUF, file); fclose(file); +#endif /* USE_CERT_BUFFER_ */ ret = wc_InitRng(&rng); if (ret != 0) { diff --git a/wolfssl/certs_test.h b/wolfssl/certs_test.h index 2d52511d7..64d10e50d 100644 --- a/wolfssl/certs_test.h +++ b/wolfssl/certs_test.h @@ -1219,6 +1219,132 @@ static const unsigned char rsa_key_der_2048[] = }; static const int sizeof_rsa_key_der_2048 = sizeof(rsa_key_der_2048); +/* ./certs/ca-key.der, 2048-bit */ +static const unsigned char ca_key_der_2048[] = +{ + 0x30, 0x82, 0x04, 0xA4, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, + 0x01, 0x00, 0xBF, 0x0C, 0xCA, 0x2D, 0x14, 0xB2, 0x1E, 0x84, + 0x42, 0x5B, 0xCD, 0x38, 0x1F, 0x4A, 0xF2, 0x4D, 0x75, 0x10, + 0xF1, 0xB6, 0x35, 0x9F, 0xDF, 0xCA, 0x7D, 0x03, 0x98, 0xD3, + 0xAC, 0xDE, 0x03, 0x66, 0xEE, 0x2A, 0xF1, 0xD8, 0xB0, 0x7D, + 0x6E, 0x07, 0x54, 0x0B, 0x10, 0x98, 0x21, 0x4D, 0x80, 0xCB, + 0x12, 0x20, 0xE7, 0xCC, 0x4F, 0xDE, 0x45, 0x7D, 0xC9, 0x72, + 0x77, 0x32, 0xEA, 0xCA, 0x90, 0xBB, 0x69, 0x52, 0x10, 0x03, + 0x2F, 0xA8, 0xF3, 0x95, 0xC5, 0xF1, 0x8B, 0x62, 0x56, 0x1B, + 0xEF, 0x67, 0x6F, 0xA4, 0x10, 0x41, 0x95, 0xAD, 0x0A, 0x9B, + 0xE3, 0xA5, 0xC0, 0xB0, 0xD2, 0x70, 0x76, 0x50, 0x30, 0x5B, + 0xA8, 0xE8, 0x08, 0x2C, 0x7C, 0xED, 0xA7, 0xA2, 0x7A, 0x8D, + 0x38, 0x29, 0x1C, 0xAC, 0xC7, 0xED, 0xF2, 0x7C, 0x95, 0xB0, + 0x95, 0x82, 0x7D, 0x49, 0x5C, 0x38, 0xCD, 0x77, 0x25, 0xEF, + 0xBD, 0x80, 0x75, 0x53, 0x94, 0x3C, 0x3D, 0xCA, 0x63, 0x5B, + 0x9F, 0x15, 0xB5, 0xD3, 0x1D, 0x13, 0x2F, 0x19, 0xD1, 0x3C, + 0xDB, 0x76, 0x3A, 0xCC, 0xB8, 0x7D, 0xC9, 0xE5, 0xC2, 0xD7, + 0xDA, 0x40, 0x6F, 0xD8, 0x21, 0xDC, 0x73, 0x1B, 0x42, 0x2D, + 0x53, 0x9C, 0xFE, 0x1A, 0xFC, 0x7D, 0xAB, 0x7A, 0x36, 0x3F, + 0x98, 0xDE, 0x84, 0x7C, 0x05, 0x67, 0xCE, 0x6A, 0x14, 0x38, + 0x87, 0xA9, 0xF1, 0x8C, 0xB5, 0x68, 0xCB, 0x68, 0x7F, 0x71, + 0x20, 0x2B, 0xF5, 0xA0, 0x63, 0xF5, 0x56, 0x2F, 0xA3, 0x26, + 0xD2, 0xB7, 0x6F, 0xB1, 0x5A, 0x17, 0xD7, 0x38, 0x99, 0x08, + 0xFE, 0x93, 0x58, 0x6F, 0xFE, 0xC3, 0x13, 0x49, 0x08, 0x16, + 0x0B, 0xA7, 0x4D, 0x67, 0x00, 0x52, 0x31, 0x67, 0x23, 0x4E, + 0x98, 0xED, 0x51, 0x45, 0x1D, 0xB9, 0x04, 0xD9, 0x0B, 0xEC, + 0xD8, 0x28, 0xB3, 0x4B, 0xBD, 0xED, 0x36, 0x79, 0x02, 0x03, + 0x01, 0x00, 0x01, 0x02, 0x82, 0x01, 0x00, 0x3D, 0x6E, 0x4E, + 0x60, 0x1A, 0x84, 0x7F, 0x9D, 0x85, 0x7C, 0xE1, 0x4B, 0x07, + 0x7C, 0xE0, 0xD6, 0x99, 0x2A, 0xDE, 0x9D, 0xF9, 0x36, 0x34, + 0x0E, 0x77, 0x0E, 0x3E, 0x08, 0xEA, 0x4F, 0xE5, 0x06, 0x26, + 0xD4, 0xF6, 0x38, 0xF7, 0xDF, 0x0D, 0x0F, 0x1C, 0x2E, 0x06, + 0xA2, 0xF4, 0x2A, 0x68, 0x9C, 0x63, 0x72, 0xE3, 0x35, 0xE6, + 0x04, 0x91, 0x91, 0xB5, 0xC1, 0xB1, 0xA4, 0x54, 0xAC, 0xD7, + 0xC6, 0xFB, 0x41, 0xA0, 0xD6, 0x75, 0x6F, 0xBD, 0x0B, 0x4E, + 0xBF, 0xB1, 0x52, 0xE8, 0x5F, 0x49, 0x26, 0x98, 0x56, 0x47, + 0xC7, 0xDE, 0xE9, 0xEA, 0x3C, 0x60, 0x01, 0xBF, 0x28, 0xDC, + 0x31, 0xBF, 0x49, 0x5F, 0x93, 0x49, 0x87, 0x7A, 0x81, 0x5B, + 0x96, 0x4B, 0x4D, 0xCA, 0x5C, 0x38, 0x4F, 0xB7, 0xE1, 0xB2, + 0xD3, 0xC7, 0x21, 0xDA, 0x3C, 0x12, 0x87, 0x07, 0xE4, 0x1B, + 0xDC, 0x43, 0xEC, 0xE8, 0xEC, 0x54, 0x61, 0xE7, 0xF6, 0xED, + 0xA6, 0x0B, 0x2E, 0xF5, 0xDF, 0x82, 0x7F, 0xC6, 0x1F, 0x61, + 0x19, 0x9C, 0xA4, 0x83, 0x39, 0xDF, 0x21, 0x85, 0x89, 0x6F, + 0x77, 0xAF, 0x86, 0x15, 0x32, 0x08, 0xA2, 0x5A, 0x0B, 0x26, + 0x61, 0xFB, 0x70, 0x0C, 0xCA, 0x9C, 0x38, 0x7D, 0xBC, 0x22, + 0xEE, 0xEB, 0xA3, 0xA8, 0x16, 0x00, 0xF9, 0x8A, 0x80, 0x1E, + 0x00, 0x84, 0xA8, 0x4A, 0x41, 0xF8, 0x84, 0x03, 0x67, 0x2F, + 0x23, 0x5B, 0x2F, 0x9B, 0x6B, 0x26, 0xC3, 0x07, 0x34, 0x94, + 0xA3, 0x03, 0x3B, 0x72, 0xD5, 0x9F, 0x72, 0xE0, 0xAD, 0xCC, + 0x34, 0xAB, 0xBD, 0xC7, 0xD5, 0xF5, 0x26, 0x30, 0x85, 0x0F, + 0x30, 0x23, 0x39, 0x52, 0xFF, 0x3C, 0xCB, 0x99, 0x21, 0x4D, + 0x88, 0xA5, 0xAB, 0xEE, 0x62, 0xB9, 0xC7, 0xE0, 0xBB, 0x47, + 0x87, 0xC1, 0x69, 0xCF, 0x73, 0xF3, 0x30, 0xBE, 0xCE, 0x39, + 0x04, 0x9C, 0xE5, 0x02, 0x81, 0x81, 0x00, 0xE1, 0x76, 0x45, + 0x80, 0x59, 0xB6, 0xD3, 0x49, 0xDF, 0x0A, 0xEF, 0x12, 0xD6, + 0x0F, 0xF0, 0xB7, 0xCB, 0x2A, 0x37, 0xBF, 0xA7, 0xF8, 0xB5, + 0x4D, 0xF5, 0x31, 0x35, 0xAD, 0xE4, 0xA3, 0x94, 0xA1, 0xDB, + 0xF1, 0x96, 0xAD, 0xB5, 0x05, 0x64, 0x85, 0x83, 0xFC, 0x1B, + 0x5B, 0x29, 0xAA, 0xBE, 0xF8, 0x26, 0x3F, 0x76, 0x7E, 0xAD, + 0x1C, 0xF0, 0xCB, 0xD7, 0x26, 0xB4, 0x1B, 0x05, 0x8E, 0x56, + 0x86, 0x7E, 0x08, 0x62, 0x21, 0xC1, 0x86, 0xD6, 0x47, 0x79, + 0x3E, 0xB7, 0x5D, 0xA4, 0xC6, 0x3A, 0xD7, 0xB1, 0x74, 0x20, + 0xF6, 0x50, 0x97, 0x41, 0x04, 0x53, 0xED, 0x3F, 0x26, 0xD6, + 0x6F, 0x91, 0xFA, 0x68, 0x26, 0xEC, 0x2A, 0xDC, 0x9A, 0xF1, + 0xE7, 0xDC, 0xFB, 0x73, 0xF0, 0x79, 0x43, 0x1B, 0x21, 0xA3, + 0x59, 0x04, 0x63, 0x52, 0x07, 0xC9, 0xD7, 0xE6, 0xD1, 0x1B, + 0x5D, 0x5E, 0x96, 0xFA, 0x53, 0x02, 0x81, 0x81, 0x00, 0xD8, + 0xED, 0x4E, 0x64, 0x61, 0x6B, 0x91, 0x0C, 0x61, 0x01, 0xB5, + 0x0F, 0xBB, 0x44, 0x67, 0x53, 0x1E, 0xDC, 0x07, 0xC4, 0x24, + 0x7E, 0x9E, 0x6C, 0x84, 0x23, 0x91, 0x0C, 0xE4, 0x12, 0x04, + 0x16, 0x4D, 0x78, 0x98, 0xCC, 0x96, 0x3D, 0x20, 0x4E, 0x0F, + 0x45, 0x9A, 0xB6, 0xF8, 0xB3, 0x93, 0x0D, 0xB2, 0xA2, 0x1B, + 0x29, 0xF2, 0x26, 0x79, 0xC8, 0xC5, 0xD2, 0x78, 0x7E, 0x5E, + 0x73, 0xF2, 0xD7, 0x70, 0x61, 0xBB, 0x40, 0xCE, 0x61, 0x05, + 0xFE, 0x69, 0x1E, 0x82, 0x29, 0xE6, 0x14, 0xB8, 0xA1, 0xE7, + 0x96, 0xD0, 0x23, 0x3F, 0x05, 0x93, 0x00, 0xF2, 0xE1, 0x4D, + 0x7E, 0xED, 0xB7, 0x96, 0x6C, 0xF7, 0xF0, 0xE4, 0xD1, 0xCF, + 0x01, 0x98, 0x4F, 0xDC, 0x74, 0x54, 0xAA, 0x6D, 0x5E, 0x5A, + 0x41, 0x31, 0xFE, 0xFF, 0x9A, 0xB6, 0xA0, 0x05, 0xDD, 0xA9, + 0x10, 0x54, 0xF8, 0x6B, 0xD0, 0xAA, 0x83, 0x02, 0x81, 0x80, + 0x21, 0xD3, 0x04, 0x8A, 0x44, 0xEB, 0x50, 0xB7, 0x7C, 0x66, + 0xBF, 0x87, 0x2B, 0xE6, 0x28, 0x4E, 0xEA, 0x83, 0xE2, 0xE9, + 0x35, 0xE1, 0xF2, 0x11, 0x47, 0xFF, 0xA1, 0xF5, 0xFC, 0x9F, + 0x2D, 0xE5, 0x3A, 0x81, 0xFC, 0x01, 0x03, 0x6F, 0x53, 0xAD, + 0x54, 0x27, 0xB6, 0x52, 0xEE, 0xE5, 0x56, 0xD1, 0x13, 0xAB, + 0xE1, 0xB3, 0x0F, 0x75, 0x90, 0x0A, 0x84, 0xB4, 0xA1, 0xC0, + 0x8C, 0x0C, 0xD6, 0x9E, 0x46, 0xBA, 0x2B, 0x3E, 0xB5, 0x31, + 0xED, 0x63, 0xBB, 0xA4, 0xD5, 0x0D, 0x8F, 0x72, 0xCD, 0xD1, + 0x1E, 0x26, 0x35, 0xEB, 0xBE, 0x1B, 0x72, 0xFD, 0x9B, 0x39, + 0xB4, 0x87, 0xB7, 0x13, 0xF5, 0xEA, 0x83, 0x45, 0x93, 0x98, + 0xBA, 0x8F, 0xE4, 0x4A, 0xCC, 0xB4, 0x4C, 0xA8, 0x7F, 0x08, + 0xBA, 0x41, 0x49, 0xA8, 0x49, 0x28, 0x3D, 0x5E, 0x3D, 0xC1, + 0xCE, 0x37, 0x00, 0xCB, 0xF9, 0x2C, 0xDD, 0x51, 0x02, 0x81, + 0x81, 0x00, 0xA1, 0x57, 0x9F, 0x3E, 0xB9, 0xD6, 0xAF, 0x83, + 0x6D, 0x83, 0x3F, 0x8F, 0xFB, 0xD0, 0xDC, 0xA8, 0xCE, 0x03, + 0x09, 0x23, 0xB1, 0xA1, 0x1B, 0x63, 0xCA, 0xC4, 0x49, 0x56, + 0x35, 0x2B, 0xD1, 0x2E, 0x65, 0x60, 0x95, 0x05, 0x55, 0x99, + 0x11, 0x35, 0xFD, 0xD5, 0xDF, 0x44, 0xC7, 0xA5, 0x88, 0x72, + 0x5F, 0xB2, 0x82, 0x51, 0xA8, 0x71, 0x45, 0x93, 0x36, 0xCF, + 0x5C, 0x1F, 0x61, 0x51, 0x0C, 0x05, 0x80, 0xE8, 0xAF, 0xC5, + 0x7B, 0xBA, 0x5E, 0x22, 0xE3, 0x3C, 0x75, 0xC3, 0x84, 0x05, + 0x55, 0x6D, 0xD6, 0x3A, 0x2D, 0x84, 0x89, 0x93, 0x33, 0xCB, + 0x38, 0xDA, 0xAA, 0x31, 0x05, 0xCD, 0xCE, 0x6C, 0x2D, 0xDD, + 0x55, 0xD3, 0x57, 0x0B, 0xF0, 0xA5, 0x35, 0x6A, 0xB0, 0xAE, + 0x31, 0xBA, 0x43, 0x96, 0xCA, 0x00, 0xC7, 0x4B, 0xE3, 0x19, + 0x12, 0x43, 0xD3, 0x42, 0xFA, 0x6F, 0xEA, 0x80, 0xC0, 0xD1, + 0x02, 0x81, 0x81, 0x00, 0xB9, 0xDB, 0x89, 0x20, 0x34, 0x27, + 0x70, 0x62, 0x34, 0xEA, 0x5F, 0x25, 0x62, 0x12, 0xF3, 0x9D, + 0x81, 0xBF, 0x48, 0xEE, 0x9A, 0x0E, 0xC1, 0x8D, 0x10, 0xFF, + 0x65, 0x9A, 0x9D, 0x2D, 0x1A, 0x8A, 0x94, 0x5A, 0xC8, 0xC0, + 0xA5, 0xA5, 0x84, 0x61, 0x9E, 0xD4, 0x24, 0xB9, 0xEF, 0xA9, + 0x9D, 0xC9, 0x77, 0x0B, 0xC7, 0x70, 0x66, 0x3D, 0xBA, 0xC8, + 0x54, 0xDF, 0xD2, 0x33, 0xE1, 0xF5, 0x7F, 0xF9, 0x27, 0x61, + 0xBE, 0x57, 0x45, 0xDD, 0xB7, 0x45, 0x17, 0x24, 0xF5, 0x23, + 0xE4, 0x38, 0x0E, 0x91, 0x27, 0xEE, 0xE3, 0x20, 0xD8, 0x14, + 0xC8, 0x94, 0x47, 0x77, 0x40, 0x77, 0x45, 0x18, 0x9E, 0x0D, + 0xCE, 0x79, 0x3F, 0x57, 0x31, 0x56, 0x09, 0x49, 0x67, 0xBE, + 0x94, 0x58, 0x4F, 0xF6, 0xC4, 0xAB, 0xE2, 0x89, 0xE3, 0xE3, + 0x8A, 0xC0, 0x05, 0x55, 0x2C, 0x24, 0xC0, 0x4A, 0x97, 0x04, + 0x27, 0x9A +}; +static const int sizeof_ca_key_der_2048 = sizeof(ca_key_der_2048); + /* ./certs/ca-cert.der, 2048-bit */ static const unsigned char ca_cert_der_2048[] = { diff --git a/wolfssl/internal.h b/wolfssl/internal.h old mode 100644 new mode 100755 index 2db8bd95f..19cb6710f --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -140,6 +140,8 @@ #elif defined(MBED) #elif defined(WOLFSSL_TIRTOS) /* do nothing */ +#elif defined(INTIME_RTOS) + #include #else #ifndef SINGLE_THREADED #define WOLFSSL_PTHREADS diff --git a/wolfssl/wolfcrypt/fe_operations.h b/wolfssl/wolfcrypt/fe_operations.h index ae15dab1f..0696b6789 100644 --- a/wolfssl/wolfcrypt/fe_operations.h +++ b/wolfssl/wolfcrypt/fe_operations.h @@ -71,9 +71,9 @@ WOLFSSL_LOCAL void fe_tobytes(unsigned char *, const fe); WOLFSSL_LOCAL void fe_sq(fe, const fe); WOLFSSL_LOCAL void fe_sq2(fe,const fe); WOLFSSL_LOCAL void fe_frombytes(fe,const unsigned char *); -WOLFSSL_LOCAL void fe_cswap(fe,fe,unsigned int); +WOLFSSL_LOCAL void fe_cswap(fe, fe, int); WOLFSSL_LOCAL void fe_mul121666(fe,fe); -WOLFSSL_LOCAL void fe_cmov(fe,const fe,unsigned int); +WOLFSSL_LOCAL void fe_cmov(fe,const fe, int); WOLFSSL_LOCAL void fe_pow22523(fe,const fe); /* 64 type needed for SHA512 */ diff --git a/wolfssl/wolfcrypt/settings.h b/wolfssl/wolfcrypt/settings.h index 897247fcb..b1387b3de 100644 --- a/wolfssl/wolfcrypt/settings.h +++ b/wolfssl/wolfcrypt/settings.h @@ -440,7 +440,7 @@ /* Micrium will use Visual Studio for compilation but not the Win32 API */ #if defined(_WIN32) && !defined(MICRIUM) && !defined(FREERTOS) && \ !defined(FREERTOS_TCP) && !defined(EBSNET) && !defined(WOLFSSL_EROAD) && \ - !defined(WOLFSSL_UTASKER) + !defined(WOLFSSL_UTASKER) && !defined(INTIME_RTOS) #define USE_WINDOWS_API #endif @@ -730,12 +730,12 @@ static char *fgets(char *buff, int sz, FILE *fp) /* WOLFSSL_DH_CONST */ #define NO_FILESYSTEM #define WOLFSSL_CRYPT_HW_MUTEX 1 - + #if !defined(XMALLOC_USER) && !defined(NO_WOLFSSL_MEMORY) #define XMALLOC(s, h, type) pvPortMalloc((s)) #define XFREE(p, h, type) vPortFree((p)) #endif - + //#define USER_TICKS /* Allows use of DH with fixed points if uncommented and NO_DH is removed */ /* WOLFSSL_DH_CONST */ @@ -854,7 +854,7 @@ static char *fgets(char *buff, int sz, FILE *fp) #if defined(FSL_FEATURE_LTC_HAS_GCM) && FSL_FEATURE_LTC_HAS_GCM #define FREESCALE_LTC_AES_GCM #endif - + #if defined(FSL_FEATURE_LTC_HAS_SHA) && FSL_FEATURE_LTC_HAS_SHA #define FREESCALE_LTC_SHA #endif @@ -869,12 +869,12 @@ static char *fgets(char *buff, int sz, FILE *fp) #define LTC_MAX_INT_BYTES (256) #endif - /* This FREESCALE_LTC_TFM_RSA_4096_ENABLE macro can be defined. + /* This FREESCALE_LTC_TFM_RSA_4096_ENABLE macro can be defined. * In such a case both software and hardware algorithm * for TFM is linked in. The decision for which algorithm is used is determined at runtime * from size of inputs. If inputs and result can fit into LTC (see LTC_MAX_INT_BYTES) * then we call hardware algorithm, otherwise we call software algorithm. - * + * * Chinese reminder theorem is used to break RSA 4096 exponentiations (both public and private key) * into several computations with 2048-bit modulus and exponents. */ @@ -886,7 +886,7 @@ static char *fgets(char *buff, int sz, FILE *fp) #define ECC_TIMING_RESISTANT /* the LTC PKHA hardware limit is 512 bits (64 bytes) for ECC. - the LTC_MAX_ECC_BITS defines the size of local variables that hold ECC parameters + the LTC_MAX_ECC_BITS defines the size of local variables that hold ECC parameters and point coordinates */ #ifndef LTC_MAX_ECC_BITS #define LTC_MAX_ECC_BITS (384) @@ -1493,6 +1493,10 @@ static char *fgets(char *buff, int sz, FILE *fp) #endif #endif +#if !defined(NO_OLD_TLS) && (defined(NO_SHA) || defined(NO_MD5)) + #error old TLS requires MD5 and SHA +#endif + /* Place any other flags or defines here */ diff --git a/wolfssl/wolfcrypt/types.h b/wolfssl/wolfcrypt/types.h index a8a16bfde..bf458fe39 100644 --- a/wolfssl/wolfcrypt/types.h +++ b/wolfssl/wolfcrypt/types.h @@ -133,7 +133,8 @@ /* set up rotate style */ - #if (defined(_MSC_VER) || defined(__BCPLUSPLUS__)) && !defined(WOLFSSL_SGX) + #if (defined(_MSC_VER) || defined(__BCPLUSPLUS__)) && \ + !defined(WOLFSSL_SGX) && !defined(INTIME_RTOS) #define INTEL_INTRINSICS #define FAST_ROTATE #elif defined(__MWERKS__) && TARGET_CPU_PPC @@ -148,7 +149,10 @@ /* set up thread local storage if available */ #ifdef HAVE_THREAD_LS - #if defined(_MSC_VER) + #if defined(INTIME_RTOS) + /* Thread local storage not supported */ + #define THREAD_LS_T + #elif defined(_MSC_VER) #define THREAD_LS_T __declspec(thread) /* Thread local storage only in FreeRTOS v8.2.1 and higher */ #elif defined(FREERTOS) @@ -163,7 +167,8 @@ /* Micrium will use Visual Studio for compilation but not the Win32 API */ #if defined(_WIN32) && !defined(MICRIUM) && !defined(FREERTOS) && \ - !defined(FREERTOS_TCP) && !defined(EBSNET) && !defined(WOLFSSL_UTASKER) + !defined(FREERTOS_TCP) && !defined(EBSNET) && \ + !defined(WOLFSSL_UTASKER) && !defined(INTIME_RTOS) #define USE_WINDOWS_API #endif @@ -252,7 +257,7 @@ #if defined(WOLFSSL_CERT_EXT) || defined(HAVE_ALPN) /* use only Thread Safe version of strtok */ - #ifndef USE_WINDOWS_API + #if !defined(USE_WINDOWS_API) && !defined(INTIME_RTOS) #define XSTRTOK strtok_r #else #define XSTRTOK strtok_s diff --git a/wolfssl/wolfcrypt/wc_port.h b/wolfssl/wolfcrypt/wc_port.h index d12c16e5d..574700b69 100644 --- a/wolfssl/wolfcrypt/wc_port.h +++ b/wolfssl/wolfcrypt/wc_port.h @@ -38,14 +38,14 @@ #ifndef WIN32_LEAN_AND_MEAN #define WIN32_LEAN_AND_MEAN #endif - #ifndef WOLFSSL_SGX - #if defined(_WIN32_WCE) || defined(WIN32_LEAN_AND_MEAN) - /* On WinCE winsock2.h must be included before windows.h */ - #include - #endif - #include + #ifndef WOLFSSL_SGX + #if defined(_WIN32_WCE) || defined(WIN32_LEAN_AND_MEAN) + /* On WinCE winsock2.h must be included before windows.h */ + #include + #endif + #include + #endif /* WOLFSSL_SGX */ #endif - #endif /* WOLFSSL_SGX */ #elif defined(THREADX) #ifndef SINGLE_THREADED #include "tx_api.h" @@ -61,12 +61,13 @@ #elif defined(FREESCALE_FREE_RTOS) #include "fsl_os_abstraction.h" #elif defined(WOLFSSL_uITRON4) + #include "stddef.h" #include "kernel.h" #elif defined(WOLFSSL_uTKERNEL2) #include "tk/tkernel.h" #elif defined(WOLFSSL_MDK_ARM) #if defined(WOLFSSL_MDK5) - #include "cmsis_os.h" + #include "cmsis_os.h" #else #include #endif @@ -77,6 +78,9 @@ #include #elif defined(WOLFSSL_FROSTED) #include +#elif defined(INTIME_RTOS) + #include + #include #else #ifndef SINGLE_THREADED #define WOLFSSL_PTHREADS @@ -146,6 +150,8 @@ typedef ti_sysbios_knl_Semaphore_Handle wolfSSL_Mutex; #elif defined(WOLFSSL_FROSTED) typedef mutex_t * wolfSSL_Mutex; + #elif defined(INTIME_RTOS) + typedef RTHANDLE wolfSSL_Mutex; #else #error Need a mutex type in multithreaded mode #endif /* USE_WINDOWS_API */ From 8a562c817ce0003dd39b34d9123d138ac28cc019 Mon Sep 17 00:00:00 2001 From: David Garske Date: Mon, 13 Mar 2017 12:22:44 -0700 Subject: [PATCH 41/68] =?UTF-8?q?Fix=20build=20issues=20with=20DEBUG=5FWOL?= =?UTF-8?q?FSSL=20defined.=20Fix=20typo=20in=20user=5Fsettings.h=20for=20D?= =?UTF-8?q?EBUG=5FWOLFSSL.=20Fix=20issue=20with=20example=20client=20waiti?= =?UTF-8?q?ng=20on=20local=20server=20(shouldn=E2=80=99t=20be).=20Updated?= =?UTF-8?q?=20README.md=20with=20example=20output.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- IDE/INTIME-RTOS/README.md | 105 ++++++++++++++++++++++ IDE/INTIME-RTOS/user_settings.h | 15 +++- IDE/INTIME-RTOS/wolfExamples.c | 10 +-- IDE/INTIME-RTOS/wolfExamples.sln | 12 --- IDE/ROWLEY-CROSSWORKS-ARM/user_settings.h | 11 ++- wolfssl/wolfcrypt/logging.h | 8 +- 6 files changed, 134 insertions(+), 27 deletions(-) mode change 100644 => 100755 wolfssl/wolfcrypt/logging.h diff --git a/IDE/INTIME-RTOS/README.md b/IDE/INTIME-RTOS/README.md index 21e137adf..e747efdde 100755 --- a/IDE/INTIME-RTOS/README.md +++ b/IDE/INTIME-RTOS/README.md @@ -32,10 +32,104 @@ Please select one of the above options: Performs testing of all crypto algorithms. +``` +Crypt Test +error test passed! +base64 test passed! +base64 test passed! +MD5 test passed! +SHA test passed! +SHA-256 test passed! +SHA-384 test passed! +SHA-512 test passed! +Hash test passed! +HMAC-MD5 test passed! +HMAC-SHA test passed! +HMAC-SHA256 test passed! +HMAC-SHA384 test passed! +HMAC-SHA512 test passed! +HMAC-KDF test passed! +X963-KDF test passed! +GMAC test passed! +Chacha test passed! +POLY1305 test passed! +ChaCha20-Poly1305 AEAD test passed! +DES test passed! +DES3 test passed! +AES test passed! +AES-GCM test passed! +AES-CCM test passed! +AES Key Wrap test passed! +RANDOM test passed! +RSA test passed! +DH test passed! +DSA test passed! +SRP test passed! +PWDBASED test passed! +openSSL extra test +OPENSSL test passed! +ECC test passed! +ECC Enc test passed! +ECC buffer test passed! +CURVE25519 test passed! +ED25519 test passed! +CMAC test passed! +PKCS7enveloped test passed! +PKCS7signed test passed! +PKCS7encrypted test passed! +mutex test passed! +memcb test passed! +Crypt Test: Return code 0 +``` + ### `b` wolfCrypt Benchmark Performs benchmark of crypto algorithms. +``` +Benchmark Test +RNG 25 kB took 0.002 seconds, 11.017 MB/s +AES enc 25 kB took 0.002 seconds, 15.090 MB/s +AES dec 25 kB took 0.002 seconds, 15.119 MB/s +AES-GCM 25 kB took 0.003 seconds, 9.433 MB/s +AES-CTR 25 kB took 0.001 seconds, 22.378 MB/s +AES-CCM 25 kB took 0.002 seconds, 15.306 MB/s +CHACHA 25 kB took 0.002 seconds, 16.063 MB/s +CHA-POLY 25 kB took 0.001 seconds, 20.447 MB/s +3DES 25 kB took 0.002 seconds, 10.717 MB/s + +MD5 25 kB took 0.00 seconds, 31.576 MB/s +POLY1305 25 kB took 0.000 seconds, 201.575 MB/s +SHA 25 kB took 0.00 seconds, 43.761 MB/s +SHA-256 25 kB took 0.001 seconds, 19.299 MB/s +SHA-384 25 kB took 0.002 seconds, 14.577 MB/s +SHA-512 25 kB took 0.001 seconds, 21.718 MB/s +AES-CMAC 25 kB took 0.00 seconds, 34.925 MB/s + +RSA 2048 public 2.445 milliseconds, avg over 1 iterations +RSA 2048 private 64.711 milliseconds, avg over 1 iterations + +RSA 1024 key generation 318.755 milliseconds, avg over 5 iterations +RSA 2048 key generation 22648.396 milliseconds, avg over 5 iterations +DH 2048 key generation 23.119 milliseconds, avg over 1 iterations +DH 2048 key agreement 26.756 milliseconds, avg over 1 iterations + +ECC 256 key generation 2.984 milliseconds, avg over 5 iterations +EC-DHE key agreement 2.967 milliseconds, avg over 5 iterations +EC-DSA sign time 1.448 milliseconds, avg over 5 iterations +EC-DSA verify time 3.304 milliseconds, avg over 5 iterations +ECC encrypt 5.860 milliseconds, avg over 1 iterations +ECC decrypt 6.360 milliseconds, avg over 1 iterations + +CURVE25519 256 key generation 1.416 milliseconds, avg over 5 iterations +CURVE25519 key agreement 1.332 milliseconds, avg over 5 iterations + +ED25519 key generation 0.320 milliseconds, avg over 5 iterations +ED25519 sign time 0.595 milliseconds, avg over 5 iterations +ED25519 verify time 1.310 milliseconds, avg over 5 iterations +Benchmark Test: Return code 0 +``` + ### `c` wolfSSL Client To configure the host address and port modify the `TLS_HOST_REMOTE` and `TLS_PORT` macros at top of `wolfExamples.c`. This example uses TLS 1.2 to connect to a remote host. @@ -48,6 +142,17 @@ To configure the port to listen on modify `TLS_PORT` at top of `wolfExamples.c`. Starts a TLS server thread listening on localhost. Starts the TLS client and performs connect, exchanges some data and disconnects. +``` +Waiting for a connection... +Client connected successfully +Using Non-Blocking I/O: 0 +Message for server: Client: + +Recieved: I hear ya fa shizzle! + +The client has closed the connection. +``` + ## References For more information please contact info@wolfssl.com. diff --git a/IDE/INTIME-RTOS/user_settings.h b/IDE/INTIME-RTOS/user_settings.h index 14e78cc89..dfff66834 100755 --- a/IDE/INTIME-RTOS/user_settings.h +++ b/IDE/INTIME-RTOS/user_settings.h @@ -17,7 +17,7 @@ extern "C" { #define INTIME_RTOS_MUTEX_MAX 10 #undef WOLF_EXAMPLES_STACK -#define WOLF_EXAMPLES_STACK 131072 +#define WOLF_EXAMPLES_STACK 65536 #undef WOLFSSL_GENERAL_ALIGNMENT #define WOLFSSL_GENERAL_ALIGNMENT 4 @@ -32,9 +32,11 @@ extern "C" { #undef NO_WOLFSSL_DIR #define NO_WOLFSSL_DIR +/* disable writev */ #undef NO_WRITEV #define NO_WRITEV +/* we provide main entry point */ #undef NO_MAIN_DRIVER #define NO_MAIN_DRIVER @@ -83,8 +85,13 @@ extern "C" { #undef HAVE_ALL_CURVES //#define HAVE_ALL_CURVES #ifndef HAVE_ALL_CURVES + /* allows enabling custom curve sizes */ #undef ECC_USER_CURVES #define ECC_USER_CURVES + + //#define HAVE_ECC112 + //#define HAVE_ECC128 + //#define HAVE_ECC160 #define HAVE_ECC192 #define HAVE_ECC224 //#define NO_ECC256 @@ -478,9 +485,9 @@ extern "C" { /* ------------------------------------------------------------------------- */ /* Debugging */ /* ------------------------------------------------------------------------- */ -#undef WOLFSSL_DEBUG -#define WOLFSSL_DEBUG -#ifdef WOLFSSL_DEBUG +#undef DEBUG_WOLFSSL +//#define DEBUG_WOLFSSL +#ifdef DEBUG_WOLFSSL /* Use this to measure / print heap usage */ #if 0 #undef USE_WOLFSSL_MEMORY diff --git a/IDE/INTIME-RTOS/wolfExamples.c b/IDE/INTIME-RTOS/wolfExamples.c index fdea5eb68..d7b801ee7 100755 --- a/IDE/INTIME-RTOS/wolfExamples.c +++ b/IDE/INTIME-RTOS/wolfExamples.c @@ -59,11 +59,6 @@ int wolfExample_TLSClient(const char* ip, int port) struct sockaddr_in servAddr; /* struct for server address */ char sendBuff[TLS_MAXDATASIZE], rcvBuff[TLS_MAXDATASIZE]; - /* wait for server to be ready */ - while (gServerReady != 1) { - RtSleep(0); - } - sockFd = socket(AF_INET, SOCK_STREAM, 0); if (sockFd < 0) { printf("Failed to create socket. Error: %d\n", errno); @@ -299,6 +294,11 @@ int wolfExample_TLSLocal(int port) return -1; } + /* wait for server to be ready */ + while (gServerReady != 1) { + RtSleep(0); + } + /* run client */ ret = wolfExample_TLSClient(TLS_HOST_LOCAL, port); diff --git a/IDE/INTIME-RTOS/wolfExamples.sln b/IDE/INTIME-RTOS/wolfExamples.sln index 81666bf8e..ab478bf6d 100755 --- a/IDE/INTIME-RTOS/wolfExamples.sln +++ b/IDE/INTIME-RTOS/wolfExamples.sln @@ -24,18 +24,6 @@ Global {1731767D-573F-45C9-A466-191DA0D180CF}.Debug|INtime.Build.0 = Debug|INtime {1731767D-573F-45C9-A466-191DA0D180CF}.Release|INtime.ActiveCfg = Release|INtime {1731767D-573F-45C9-A466-191DA0D180CF}.Release|INtime.Build.0 = Release|INtime - {AA35919C-9D2D-4753-8FD1-E5D1644ABE65}.Debug|INtime.ActiveCfg = Debug|INtime - {AA35919C-9D2D-4753-8FD1-E5D1644ABE65}.Debug|INtime.Build.0 = Debug|INtime - {AA35919C-9D2D-4753-8FD1-E5D1644ABE65}.Release|INtime.ActiveCfg = Release|INtime - {AA35919C-9D2D-4753-8FD1-E5D1644ABE65}.Release|INtime.Build.0 = Release|INtime - {A7A65D11-2A66-4936-9476-16646CF896CA}.Debug|INtime.ActiveCfg = Debug|INtime - {A7A65D11-2A66-4936-9476-16646CF896CA}.Debug|INtime.Build.0 = Debug|INtime - {A7A65D11-2A66-4936-9476-16646CF896CA}.Release|INtime.ActiveCfg = Release|INtime - {A7A65D11-2A66-4936-9476-16646CF896CA}.Release|INtime.Build.0 = Release|INtime - {2359342B-C023-4443-8170-3471928C9334}.Debug|INtime.ActiveCfg = Debug|INtime - {2359342B-C023-4443-8170-3471928C9334}.Debug|INtime.Build.0 = Debug|INtime - {2359342B-C023-4443-8170-3471928C9334}.Release|INtime.ActiveCfg = Release|INtime - {2359342B-C023-4443-8170-3471928C9334}.Release|INtime.Build.0 = Release|INtime EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/IDE/ROWLEY-CROSSWORKS-ARM/user_settings.h b/IDE/ROWLEY-CROSSWORKS-ARM/user_settings.h index ae3e57858..5641973c9 100644 --- a/IDE/ROWLEY-CROSSWORKS-ARM/user_settings.h +++ b/IDE/ROWLEY-CROSSWORKS-ARM/user_settings.h @@ -232,14 +232,17 @@ extern "C" { #undef USE_CERT_BUFFERS_2048 #define USE_CERT_BUFFERS_2048 +#undef USE_CERT_BUFFERS_256 +#define USE_CERT_BUFFERS_256 + /* ------------------------------------------------------------------------- */ /* Debugging */ /* ------------------------------------------------------------------------- */ -#undef WOLFSSL_DEBUG -//#define WOLFSSL_DEBUG +#undef DEBUG_WOLFSSL +//#define DEBUG_WOLFSSL -#ifdef WOLFSSL_DEBUG +#ifdef DEBUG_WOLFSSL #define fprintf(file, format, ...) printf(format, ##__VA_ARGS__) /* Use this to measure / print heap usage */ @@ -255,7 +258,7 @@ extern "C" { #define NO_WOLFSSL_MEMORY #undef NO_ERROR_STRINGS - #define NO_ERROR_STRINGS + //#define NO_ERROR_STRINGS #endif diff --git a/wolfssl/wolfcrypt/logging.h b/wolfssl/wolfcrypt/logging.h old mode 100644 new mode 100755 index 66e90127b..43df62ff6 --- a/wolfssl/wolfcrypt/logging.h +++ b/wolfssl/wolfcrypt/logging.h @@ -62,8 +62,12 @@ WOLFSSL_API int wolfSSL_SetLoggingCb(wolfSSL_Logging_cb log_function); #endif /* defined(OPENSSL_EXTRA) || defined(DEBUG_WOLFSSL_VERBOSE) */ #ifdef DEBUG_WOLFSSL - #if defined ( WIN32 ) - #define __func__ __FUNCTION__ + #if defined(_WIN32) + #if defined(INTIME_RTOS) + #define __func__ NULL + #else + #define __func__ __FUNCTION__ + #endif #endif /* a is prepended to m and b is appended, creating a log msg a + m + b */ From 81731df72f51b2d495d9a4e008b1566606e0169e Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Tue, 14 Mar 2017 09:47:34 +1000 Subject: [PATCH 42/68] Fix valgrind issues Test program was re-using RSA and ECC key with multiple imports ops. wc_RsaPublicKeyDecode() leaked if n parseable but not e. --- wolfcrypt/src/asn.c | 6 ++++-- wolfcrypt/test/test.c | 33 ++++++++++++++++++++++++++++++++- 2 files changed, 36 insertions(+), 3 deletions(-) diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 94e01aac1..6ed0f6987 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -2220,8 +2220,10 @@ int wc_RsaPublicKeyDecode(const byte* input, word32* inOutIdx, RsaKey* key, } #endif /* OPENSSL_EXTRA */ - if (GetInt(&key->n, input, inOutIdx, inSz) < 0 || - GetInt(&key->e, input, inOutIdx, inSz) < 0) { + if (GetInt(&key->n, input, inOutIdx, inSz) < 0) + return ASN_RSA_KEY_E; + if (GetInt(&key->e, input, inOutIdx, inSz) < 0) { + mp_clear(&key->n); return ASN_RSA_KEY_E; } diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index ffbd6b552..bcb4f6620 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -5879,11 +5879,19 @@ static int rsa_decode_test(void) ret = -525; goto done; } + wc_FreeRsaKey(&keyPub); + ret = wc_InitRsaKey(&keyPub, NULL); + if (ret != 0) + return -520; ret = wc_RsaPublicKeyDecodeRaw(n, sizeof(n), e, -1, &keyPub); if (ret != 0) { ret = -526; goto done; } + wc_FreeRsaKey(&keyPub); + ret = wc_InitRsaKey(&keyPub, NULL); + if (ret != 0) + return -520; /* Use API. */ ret = wc_RsaPublicKeyDecodeRaw(n, sizeof(n), e, sizeof(e), &keyPub); @@ -5891,6 +5899,10 @@ static int rsa_decode_test(void) ret = -527; goto done; } + wc_FreeRsaKey(&keyPub); + ret = wc_InitRsaKey(&keyPub, NULL); + if (ret != 0) + return -520; /* Parameter Validation testing. */ inSz = sizeof(good); @@ -5984,6 +5996,10 @@ static int rsa_decode_test(void) goto done; } /* TODO: Shouldn't ignore object id's data. */ + wc_FreeRsaKey(&keyPub); + ret = wc_InitRsaKey(&keyPub, NULL); + if (ret != 0) + return -520; /* Valid data cases. */ inSz = sizeof(good); @@ -5997,6 +6013,10 @@ static int rsa_decode_test(void) ret = -551; goto done; } + wc_FreeRsaKey(&keyPub); + ret = wc_InitRsaKey(&keyPub, NULL); + if (ret != 0) + return -520; inSz = sizeof(goodAlgId); inOutIdx = 0; @@ -6009,6 +6029,10 @@ static int rsa_decode_test(void) ret = -553; goto done; } + wc_FreeRsaKey(&keyPub); + ret = wc_InitRsaKey(&keyPub, NULL); + if (ret != 0) + return -520; inSz = sizeof(goodAlgIdNull); inOutIdx = 0; @@ -6021,6 +6045,10 @@ static int rsa_decode_test(void) ret = -555; goto done; } + wc_FreeRsaKey(&keyPub); + ret = wc_InitRsaKey(&keyPub, NULL); + if (ret != 0) + return -520; inSz = sizeof(goodBitStrNoZero); inOutIdx = 0; @@ -10239,6 +10267,9 @@ static int ecc_exp_imp_test(ecc_key* key) goto done; } + wc_ecc_free(&keyImp); + wc_ecc_init(&keyImp); + ret = wc_ecc_import_raw_ex(&keyImp, qx, qy, d, ECC_SECP256R1); if (ret != 0) { ret = -1073; @@ -12558,7 +12589,7 @@ int mp_test() * - if p and a are even it will fail. */ ret = mp_invmod(&a, &p, &r1); - if (ret != 0 && ret != FP_VAL) + if (ret != 0 && ret != MP_VAL) return -11019; ret = 0; From 72728b21af081267b0082f9fc26a712d30ba275c Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Tue, 14 Mar 2017 10:23:13 +1000 Subject: [PATCH 43/68] Undo as mp_digit is not allowed to get as large as tested --- wolfcrypt/src/integer.c | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index ab0040d0d..669d54d43 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -4101,17 +4101,14 @@ int mp_sub_d (mp_int * a, mp_digit b, mp_int * c) c->used = a->used; /* subtract first digit */ - *tmpc = *tmpa - b; - if (b > *tmpa++) - mu = ((0 - *tmpc) >> DIGIT_BIT) + 1; - else - mu = *tmpc >> DIGIT_BIT; + *tmpc = *tmpa++ - b; + mu = *tmpc >> (sizeof(mp_digit) * CHAR_BIT - 1); *tmpc++ &= MP_MASK; /* handle rest of the digits */ for (ix = 1; ix < a->used; ix++) { *tmpc = *tmpa++ - mu; - mu = *tmpc >> DIGIT_BIT; + mu = *tmpc >> (sizeof(mp_digit) * CHAR_BIT - 1); *tmpc++ &= MP_MASK; } } From 0eb01698f4595fabde080b4d34717a6be81e1cc3 Mon Sep 17 00:00:00 2001 From: David Garske Date: Mon, 13 Mar 2017 19:58:15 -0700 Subject: [PATCH 44/68] =?UTF-8?q?Fix=20for=20wolfCrypt=20ECC=20import/expo?= =?UTF-8?q?rt=20point=20test=20to=20not=20use=20const=20idx=20and=20instea?= =?UTF-8?q?d=20lookup=20using=20the=20=E2=80=9Cecc=5Fcurve=5Fid=E2=80=9D?= =?UTF-8?q?=20enum=20value.=20Added=20new=20=E2=80=9Cwc=5Fecc=5Fget=5Fcurv?= =?UTF-8?q?e=5Fidx=E2=80=9D=20and=20=E2=80=9Cwc=5Fecc=5Fget=5Fcurve=5Fid?= =?UTF-8?q?=E2=80=9D=20API=E2=80=99s.=20Redirected=20duplicate=20ECC=20fun?= =?UTF-8?q?ction=20=E2=80=9Cwc=5Fecc=5Fget=5Fcurve=5Fname=5Ffrom=5Fid?= =?UTF-8?q?=E2=80=9D=20to=20=E2=80=9Cwc=5Fecc=5Fget=5Fname=E2=80=9D.=20Add?= =?UTF-8?q?ed=20=E2=80=9CECC=5FCURVE=5FINVALID=E2=80=9D=20to=20indicate=20?= =?UTF-8?q?invalid=20curve=5Fid.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- wolfcrypt/src/ecc.c | 71 +++++++++++++++-------------------------- wolfcrypt/test/test.c | 31 ++++++++++-------- wolfssl/wolfcrypt/ecc.h | 8 +++-- 3 files changed, 49 insertions(+), 61 deletions(-) diff --git a/wolfcrypt/src/ecc.c b/wolfcrypt/src/ecc.c index 32dd99836..5f095f5a5 100644 --- a/wolfcrypt/src/ecc.c +++ b/wolfcrypt/src/ecc.c @@ -1102,12 +1102,8 @@ static int wc_ecc_curve_load(const ecc_set_type* dp, ecc_curve_spec** pCurve, return BAD_FUNC_ARG; #ifdef ECC_CACHE_CURVE - /* find ecc_set index based on curve_id */ - for (x = 0; ecc_sets[x].size != 0; x++) { - if (dp->id == ecc_sets[x].id) - break; /* found index */ - } - if (ecc_sets[x].size == 0) + x = wc_ecc_get_curve_idx(dp->id); + if (x == ECC_CURVE_INVALID) return ECC_BAD_ARG_E; /* make sure cache has been allocated */ @@ -1195,6 +1191,7 @@ void wc_ecc_curve_cache_free(void) #endif /* WOLFSSL_ATECC508A */ + /* Retrieve the curve name for the ECC curve id. * * curve_id The id of the curve. @@ -1202,14 +1199,10 @@ void wc_ecc_curve_cache_free(void) */ const char* wc_ecc_get_name(int curve_id) { - int x; - - for (x = 0; ecc_sets[x].size != 0; x++) { - if (curve_id == ecc_sets[x].id) - return ecc_sets[x].name; - } - - return NULL; + int curve_idx = wc_ecc_get_curve_idx(curve_id); + if (curve_idx == ECC_CURVE_INVALID) + return NULL; + return ecc_sets[curve_idx].name; } static int wc_ecc_set_curve(ecc_key* key, int keysize, int curve_id) @@ -2468,52 +2461,38 @@ int wc_ecc_is_valid_idx(int n) return 0; } - -/* - * Returns the curve name that corresponds to an ecc_curve_id identifier - * - * id curve id, from ecc_curve_id enum in ecc.h - * return const char* representing curve name, from ecc_sets[] on success, - * otherwise NULL if id not found. - */ -const char* wc_ecc_get_curve_name_from_id(int id) +int wc_ecc_get_curve_idx(int curve_id) { - int i; - - for (i = 0; ecc_sets[i].size != 0; i++) { - if (id == ecc_sets[i].id) + int curve_idx; + for (curve_idx = 0; ecc_sets[curve_idx].size != 0; curve_idx++) { + if (curve_id == ecc_sets[curve_idx].id) break; } - - if (ecc_sets[i].size == 0) { - WOLFSSL_MSG("ecc_set curve not found"); - return NULL; + if (ecc_sets[curve_idx].size == 0) { + return ECC_CURVE_INVALID; } - - return ecc_sets[i].name; + return curve_idx; } +int wc_ecc_get_curve_id(int curve_idx) +{ + if (wc_ecc_is_valid_idx(curve_idx)) { + return ecc_sets[curve_idx].id; + } + return ECC_CURVE_INVALID; +} /* Returns the curve size that corresponds to a given ecc_curve_id identifier * * id curve id, from ecc_curve_id enum in ecc.h * return curve size, from ecc_sets[] on success, negative on error */ -int wc_ecc_get_curve_size_from_id(int id) +int wc_ecc_get_curve_size_from_id(int curve_id) { - int i; - - for (i = 0; ecc_sets[i].size != 0; i++) { - if (id == ecc_sets[i].id) - break; - } - - if (ecc_sets[i].size == 0) { - WOLFSSL_MSG("ecc_set curve not found"); + int curve_idx = wc_ecc_get_curve_idx(curve_id); + if (curve_idx == ECC_CURVE_INVALID) return ECC_BAD_ARG_E; - } - - return ecc_sets[i].size; + return ecc_sets[curve_idx].size; } diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index ffbd6b552..e3fc7af2a 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -10020,6 +10020,11 @@ static int ecc_point_test() 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07 }; + int curve_idx = wc_ecc_get_curve_idx(ECC_SECP256R1); + + /* if curve P256 is not enabled then test should not fail */ + if (curve_idx == ECC_CURVE_INVALID) + return 0; outLen = sizeof(out); point = wc_ecc_new_point(); @@ -10033,17 +10038,17 @@ static int ecc_point_test() /* Parameter Validation testing. */ wc_ecc_del_point(NULL); - ret = wc_ecc_import_point_der(NULL, sizeof(der), 6, point); + ret = wc_ecc_import_point_der(NULL, sizeof(der), curve_idx, point); if (ret != ECC_BAD_ARG_E) { ret = -1037; goto done; } - ret = wc_ecc_import_point_der(der, sizeof(der), -1, point); + ret = wc_ecc_import_point_der(der, sizeof(der), ECC_CURVE_INVALID, point); if (ret != ECC_BAD_ARG_E) { ret = -1038; goto done; } - ret = wc_ecc_import_point_der(der, sizeof(der), 6, NULL); + ret = wc_ecc_import_point_der(der, sizeof(der), curve_idx, NULL); if (ret != ECC_BAD_ARG_E) { ret = -1039; goto done; @@ -10053,23 +10058,23 @@ static int ecc_point_test() ret = -1040; goto done; } - ret = wc_ecc_export_point_der(6, NULL, out, &outLen); + ret = wc_ecc_export_point_der(curve_idx, NULL, out, &outLen); if (ret != ECC_BAD_ARG_E) { ret = -1041; goto done; } - ret = wc_ecc_export_point_der(6, point, NULL, &outLen); + ret = wc_ecc_export_point_der(curve_idx, point, NULL, &outLen); if (ret != LENGTH_ONLY_E || outLen != sizeof(out)) { - ret = -1043; + ret = -1042; goto done; } - ret = wc_ecc_export_point_der(6, point, out, NULL); + ret = wc_ecc_export_point_der(curve_idx, point, out, NULL); if (ret != ECC_BAD_ARG_E) { ret = -1043; goto done; } outLen = 0; - ret = wc_ecc_export_point_der(6, point, out, &outLen); + ret = wc_ecc_export_point_der(curve_idx, point, out, &outLen); if (ret != BUFFER_E) { ret = -1044; goto done; @@ -10106,14 +10111,14 @@ static int ecc_point_test() } /* Use API. */ - ret = wc_ecc_import_point_der(der, sizeof(der), 6, point); + ret = wc_ecc_import_point_der(der, sizeof(der), curve_idx, point); if (ret != 0) { ret = -1051; goto done; } outLen = sizeof(out); - ret = wc_ecc_export_point_der(6, point, out, &outLen); + ret = wc_ecc_export_point_der(curve_idx, point, out, &outLen); if (ret != 0) { ret = -1052; goto done; @@ -10138,7 +10143,7 @@ static int ecc_point_test() goto done; } - ret = wc_ecc_import_point_der(altDer, sizeof(altDer), 6, point2); + ret = wc_ecc_import_point_der(altDer, sizeof(altDer), curve_idx, point2); if (ret != 0) { ret = -1057; goto done; @@ -10151,13 +10156,13 @@ static int ecc_point_test() #ifdef HAVE_COMP_KEY /* TODO: Doesn't work. */ - ret = wc_ecc_import_point_der(derComp0, sizeof(der), 6, point); + ret = wc_ecc_import_point_der(derComp0, sizeof(der), curve_idx, point); if (ret != 0) { ret = -1059; goto done; } - ret = wc_ecc_import_point_der(derComp1, sizeof(der), 6, point); + ret = wc_ecc_import_point_der(derComp1, sizeof(der), curve_idx, point); if (ret != 0) { ret = -1060; goto done; diff --git a/wolfssl/wolfcrypt/ecc.h b/wolfssl/wolfcrypt/ecc.h index baf33637b..49203bc2f 100644 --- a/wolfssl/wolfcrypt/ecc.h +++ b/wolfssl/wolfcrypt/ecc.h @@ -110,7 +110,8 @@ enum { /* Curve Types */ typedef enum ecc_curve_id { - ECC_CURVE_DEF, /* NIST or SECP */ + ECC_CURVE_INVALID = -1, + ECC_CURVE_DEF = 0, /* NIST or SECP */ /* NIST Prime Curves */ ECC_SECP192R1, @@ -343,7 +344,10 @@ void wc_ecc_fp_free(void); WOLFSSL_API int wc_ecc_is_valid_idx(int n); WOLFSSL_API -const char* wc_ecc_get_curve_name_from_id(int curve_id); +int wc_ecc_get_curve_idx(int curve_id); +WOLFSSL_API +int wc_ecc_get_curve_id(int curve_idx); +#define wc_ecc_get_curve_name_from_id wc_ecc_get_name WOLFSSL_API int wc_ecc_get_curve_size_from_id(int curve_id); From 2fbce65975fb8625649e49cb4ded0536308493de Mon Sep 17 00:00:00 2001 From: David Garske Date: Mon, 13 Mar 2017 20:03:09 -0700 Subject: [PATCH 45/68] =?UTF-8?q?Revert=20change=20in=20types.h=20for=20IN?= =?UTF-8?q?TIME=5FRTOS.=20HAVE=5FTHREAD=5FLS=20is=20not=20supported=20here?= =?UTF-8?q?,=20so=20don=E2=80=99t=20define=20out.=20Added=20note=20in=20IN?= =?UTF-8?q?time=20RTOS=20user=5Fsettings.h=20to=20indicate=20this.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- IDE/INTIME-RTOS/user_settings.h | 1 + wolfssl/wolfcrypt/types.h | 5 +---- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/IDE/INTIME-RTOS/user_settings.h b/IDE/INTIME-RTOS/user_settings.h index dfff66834..fa4867fe1 100755 --- a/IDE/INTIME-RTOS/user_settings.h +++ b/IDE/INTIME-RTOS/user_settings.h @@ -43,6 +43,7 @@ extern "C" { /* if using in single threaded mode */ #undef SINGLE_THREADED //#define SINGLE_THREADED +/* Note: HAVE_THREAD_LS is not support for INtime RTOS */ /* reduces stack usage, by using malloc/free for stack variables over 100 bytes */ #undef WOLFSSL_SMALL_STACK diff --git a/wolfssl/wolfcrypt/types.h b/wolfssl/wolfcrypt/types.h index bf458fe39..5e405dd21 100644 --- a/wolfssl/wolfcrypt/types.h +++ b/wolfssl/wolfcrypt/types.h @@ -149,10 +149,7 @@ /* set up thread local storage if available */ #ifdef HAVE_THREAD_LS - #if defined(INTIME_RTOS) - /* Thread local storage not supported */ - #define THREAD_LS_T - #elif defined(_MSC_VER) + #if defined(_MSC_VER) #define THREAD_LS_T __declspec(thread) /* Thread local storage only in FreeRTOS v8.2.1 and higher */ #elif defined(FREERTOS) From e2930b0a4368a83c8efaec1f85a73cb9e9f6338b Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Fri, 10 Feb 2017 08:45:10 +1000 Subject: [PATCH 46/68] Changes for WPA Supplicant --- configure.ac | 51 +++++++++++--- src/internal.c | 79 ++++++++++++++++------ src/ssl.c | 143 +++++++++++++++++++++++++++++++++------- wolfcrypt/src/ecc.c | 2 +- wolfcrypt/src/tfm.c | 10 +++ wolfssl/ssl.h | 61 +++++++++-------- wolfssl/wolfcrypt/ecc.h | 3 + wolfssl/wolfcrypt/tfm.h | 2 + 8 files changed, 270 insertions(+), 81 deletions(-) diff --git a/configure.ac b/configure.ac index 9c4879a28..5c33c2ec9 100644 --- a/configure.ac +++ b/configure.ac @@ -332,6 +332,21 @@ fi AM_CONDITIONAL([BUILD_IPV6], [test "x$ENABLED_IPV6" = "xyes"]) +# wpa_supplicant support +AC_ARG_ENABLE([wpas], + [ --enable-wpas Enable wpa_supplicant support (default: disabled)], + [ ENABLED_WPAS=$enableval ], + [ ENABLED_WPAS=no ] + ) +if test "$ENABLED_WPAS" = "yes" +then + enable_shared=no + enable_static=yes + AM_CFLAGS="$AM_CFLAGS -DHAVE_SECRET_CALLBACK -DWOLFSSL_STATIC_RSA" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_WPAS" +fi + + # Fortress build AC_ARG_ENABLE([fortress], [ --enable-fortress Enable SSL fortress build (default: disabled)], @@ -339,7 +354,7 @@ AC_ARG_ENABLE([fortress], [ ENABLED_FORTRESS=no ] ) -if test "$ENABLED_OPENSSH" = "yes" +if test "$ENABLED_OPENSSH" = "yes" || test "$ENABLED_WPAS" = "yes" then ENABLED_FORTRESS="yes" fi @@ -882,7 +897,7 @@ AC_ARG_ENABLE([dsa], [ ENABLED_DSA=no ] ) -if test "$ENABLED_OPENSSH" = "yes" || test "$ENABLED_NGINX" = "yes" +if test "$ENABLED_OPENSSH" = "yes" || test "$ENABLED_NGINX" = "yes" || test "$ENABLED_WPAS" = "yes" then ENABLED_DSA="yes" fi @@ -960,6 +975,10 @@ AC_ARG_ENABLE([compkey], [ ENABLED_COMPKEY=no ] ) +if test "$ENABLED_WPAS" = "yes" +then + ENABLED_COMPKEY=yes +fi if test "$ENABLED_COMPKEY" = "yes" then AM_CFLAGS="$AM_CFLAGS -DHAVE_COMP_KEY" @@ -1227,7 +1246,10 @@ AC_ARG_ENABLE([anon], [ ENABLED_ANON=no ] ) - +if test "x$ENABLED_WPAS" = "xyes" +then + ENABLED_ANON=yes +fi if test "x$ENABLED_ANON" = "xyes" then if test "x$ENABLED_DH" != "xyes" @@ -1392,7 +1414,7 @@ AC_ARG_ENABLE([arc4], [ ENABLED_ARC4=no ] ) -if test "$ENABLED_OPENSSH" = "yes" +if test "$ENABLED_OPENSSH" = "yes" || test "$ENABLED_WPAS" = "yes" then ENABLED_ARC4="yes" fi @@ -1463,6 +1485,11 @@ AC_ARG_ENABLE([cmac], [ ENABLED_CMAC=no ] ) +if test "$ENABLED_WPAS" = "yes" +then + ENABLED_CMAC=yes +fi + AS_IF([test "x$ENABLED_CMAC" = "xyes"], [AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_CMAC -DWOLFSSL_AES_DIRECT"]) @@ -1735,7 +1762,7 @@ AC_ARG_ENABLE([ocspstapling], [ ENABLED_CERTIFICATE_STATUS_REQUEST=no ] ) -if test "x$ENABLED_NGINX" = "xyes" +if test "x$ENABLED_NGINX" = "xyes" || test "x$ENABLED_WPAS" = "xyes" then ENABLED_CERTIFICATE_STATUS_REQUEST=yes fi @@ -1762,7 +1789,7 @@ AC_ARG_ENABLE([ocspstapling2], [ ENABLED_CERTIFICATE_STATUS_REQUEST_V2=no ] ) -if test "x$ENABLED_NGINX" = "xyes" +if test "x$ENABLED_NGINX" = "xyes" || test "x$ENABLED_WPAS" = "xyes" then ENABLED_CERTIFICATE_STATUS_REQUEST_V2=yes fi @@ -2067,7 +2094,7 @@ AC_ARG_ENABLE([session-ticket], [ ENABLED_SESSION_TICKET=no ] ) -if test "x$ENABLED_NGINX" = "xyes" +if test "x$ENABLED_NGINX" = "xyes" || test "$ENABLED_WPAS" = "yes" then ENABLED_SESSION_TICKET=yes fi @@ -2327,7 +2354,6 @@ then fi fi - # lighty Support AC_ARG_ENABLE([lighty], [ --enable-lighty Enable lighttpd/lighty (default: disabled)], @@ -2361,6 +2387,10 @@ AC_ARG_ENABLE([stunnel], [ ENABLED_STUNNEL=$enableval ], [ ENABLED_STUNNEL=no ] ) +if test "$ENABLED_WPAS" = "yes" +then + ENABLED_STUNNEL="yes" +fi if test "$ENABLED_STUNNEL" = "yes" then # Requires opensslextra make sure on @@ -2972,6 +3002,11 @@ AC_ARG_ENABLE([aeskeywrap], [ ENABLED_AESKEYWRAP=no ] ) +if test "$ENABLED_WPAS" = "yes" +then + ENABLED_AESKEYWRAP="yes" +fi + if test "$ENABLED_AESKEYWRAP" = "yes" then AM_CFLAGS="$AM_CFLAGS -DHAVE_AES_KEYWRAP -DWOLFSSL_AES_DIRECT" diff --git a/src/internal.c b/src/internal.c index 1ad94f99b..c20646f37 100644 --- a/src/internal.c +++ b/src/internal.c @@ -7234,7 +7234,11 @@ static int DoCertificate(WOLFSSL* ssl, byte* input, word32* inOutIdx, int ok; store->error = ret; +#ifdef WOLFSSL_WPAS + store->error_depth = 0; +#else store->error_depth = totalCerts; +#endif store->discardSessionCerts = 0; store->domain = domain; store->userCtx = ssl->verifyCbCtx; @@ -18798,8 +18802,34 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, } #ifndef NO_WOLFSSL_SERVER + static int CompareSuites(WOLFSSL* ssl, Suites* peerSuites, word16 i, + word16 j) + { + if (ssl->suites->suites[i] == peerSuites->suites[j] && + ssl->suites->suites[i+1] == peerSuites->suites[j+1] ) { + + if (VerifyServerSuite(ssl, i)) { + int result; + WOLFSSL_MSG("Verified suite validity"); + ssl->options.cipherSuite0 = ssl->suites->suites[i]; + ssl->options.cipherSuite = ssl->suites->suites[i+1]; + result = SetCipherSpecs(ssl); + if (result == 0) + PickHashSigAlgo(ssl, peerSuites->hashSigAlgo, + peerSuites->hashSigAlgoSz); + return result; + } + else { + WOLFSSL_MSG("Could not verify suite validity, continue"); + } + } + + return MATCH_SUITE_ERROR; + } + static int MatchSuite(WOLFSSL* ssl, Suites* peerSuites) { + int ret; word16 i, j; WOLFSSL_ENTER("MatchSuite"); @@ -18810,27 +18840,38 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, if (ssl->suites == NULL) return SUITES_ERROR; - /* start with best, if a match we are good */ - for (i = 0; i < ssl->suites->suiteSz; i += 2) - for (j = 0; j < peerSuites->suiteSz; j += 2) - if (ssl->suites->suites[i] == peerSuites->suites[j] && - ssl->suites->suites[i+1] == peerSuites->suites[j+1] ) { - if (VerifyServerSuite(ssl, i)) { - int result; - WOLFSSL_MSG("Verified suite validity"); - ssl->options.cipherSuite0 = ssl->suites->suites[i]; - ssl->options.cipherSuite = ssl->suites->suites[i+1]; - result = SetCipherSpecs(ssl); - if (result == 0) - PickHashSigAlgo(ssl, peerSuites->hashSigAlgo, - peerSuites->hashSigAlgoSz); - return result; - } - else { - WOLFSSL_MSG("Could not verify suite validity, continue"); - } +#ifdef OPENSSL_EXTRA + if (ssl->options.mask | SSL_OP_CIPHER_SERVER_PREFERENCE) { + /* Server order */ + for (i = 0; i < ssl->suites->suiteSz; i += 2) { + for (j = 0; j < peerSuites->suiteSz; j += 2) { + ret = CompareSuites(ssl, peerSuites, i, j); + if (ret != MATCH_SUITE_ERROR) + return ret; } + } + } + else { + /* Client order */ + for (j = 0; j < peerSuites->suiteSz; j += 2) { + for (i = 0; i < ssl->suites->suiteSz; i += 2) { + ret = CompareSuites(ssl, peerSuites, i, j); + if (ret != MATCH_SUITE_ERROR) + return ret; + } + } + } +#else + /* Server order */ + for (i = 0; i < ssl->suites->suiteSz; i += 2) { + for (j = 0; j < peerSuites->suiteSz; j += 2) { + ret = CompareSuites(ssl, peerSuites, i, j); + if (ret != MATCH_SUITE_ERROR) + return ret; + } + } +#endif return MATCH_SUITE_ERROR; } diff --git a/src/ssl.c b/src/ssl.c index 1f94fc526..14c960355 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -990,8 +990,10 @@ int wolfSSL_SetTmpDH(WOLFSSL* ssl, const unsigned char* p, int pSz, if (pSz < ssl->options.minDhKeySz) return DH_KEY_SIZE_E; + #ifndef WOLFSSL_WPAS if (ssl->options.side != WOLFSSL_SERVER_END) return SIDE_ERROR; + #endif if (ssl->buffers.serverDH_P.buffer && ssl->buffers.weOwnDH) { XFREE(ssl->buffers.serverDH_P.buffer, ssl->heap, DYNAMIC_TYPE_DH); @@ -1770,7 +1772,8 @@ WOLFSSL_API int wolfSSL_get_SessionTicket(WOLFSSL* ssl, return SSL_SUCCESS; } -WOLFSSL_API int wolfSSL_set_SessionTicket(WOLFSSL* ssl, byte* buf, word32 bufSz) +WOLFSSL_API int wolfSSL_set_SessionTicket(WOLFSSL* ssl, const byte* buf, + word32 bufSz) { if (ssl == NULL || (buf == NULL && bufSz > 0)) return BAD_FUNC_ARG; @@ -2362,6 +2365,7 @@ void wolfSSL_CertManagerFree(WOLFSSL_CERT_MANAGER* cm) #ifdef HAVE_OCSP if (cm->ocsp) FreeOCSP(cm->ocsp, 1); + XFREE(cm->ocspOverrideURL, cm->heap, DYNAMIC_TYPE_URL); #if defined(HAVE_CERTIFICATE_STATUS_REQUEST) \ || defined(HAVE_CERTIFICATE_STATUS_REQUEST_V2) if (cm->ocsp_stapling) @@ -4478,6 +4482,25 @@ static int ProcessChainBuffer(WOLFSSL_CTX* ctx, const unsigned char* buff, ret = ProcessBuffer(ctx, buff + used, sz - used, format, type, ssl, &consumed, 0); +#ifdef WOLFSSL_WPAS +#ifdef HAVE_CRL + if (ret < 0) { + DerBuffer* der = NULL; + EncryptedInfo info; + + WOLFSSL_MSG("Trying a CRL"); + if (PemToDer(buff + used, sz - used, CRL_TYPE, &der, NULL, &info, + NULL) == 0) { + WOLFSSL_MSG(" Proccessed a CRL"); + wolfSSL_CertManagerLoadCRLBuffer(ctx->cm, der->buffer, + der->length,SSL_FILETYPE_ASN1); + FreeDer(&der); + used += info.consumed; + continue; + } + } +#endif +#endif if (ret < 0) { if(consumed > 0) { /* Made progress in file */ @@ -7882,6 +7905,7 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl, } #endif /* NO_HANDSHAKE_DONE_CB */ +#ifndef WOLFSSL_WPAS if (!ssl->options.dtls) { FreeHandshakeResources(ssl); } @@ -7890,6 +7914,7 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl, ssl->options.dtlsHsRetain = 1; } #endif /* WOLFSSL_DTLS */ +#endif WOLFSSL_LEAVE("SSL_connect()", SSL_SUCCESS); return SSL_SUCCESS; @@ -9613,6 +9638,14 @@ int wolfSSL_set_compression(WOLFSSL* ssl) FreeDer(&der); ret = PemToDer(buf, sz, DH_PARAM_TYPE, &der, ctx->heap, NULL, NULL); +#ifdef WOLFSSL_WPAS + #ifndef NO_DSA + if (ret < 0) { + ret = PemToDer(buf, sz, DSA_PARAM_TYPE, &der, ctx->heap, + NULL, NULL); + } + #endif +#endif } if (ret == 0) { @@ -9924,6 +9957,27 @@ int wolfSSL_set_compression(WOLFSSL* ssl) word16 havePSK = 0; WOLFSSL_ENTER("SSL_set_accept_state"); + if (ssl->options.side == WOLFSSL_CLIENT_END) { + ecc_key key; + word32 idx = 0; + + if (ssl->options.haveStaticECC && ssl->buffers.key != NULL) { + wc_ecc_init(&key); + if (wc_EccPrivateKeyDecode(ssl->buffers.key->buffer, &idx, &key, + ssl->buffers.key->length) != 0) { + ssl->options.haveECDSAsig = 0; + ssl->options.haveECC = 0; + ssl->options.haveStaticECC = 0; + } + wc_ecc_free(&key); + } + + if (!ssl->options.haveDH && ssl->ctx->haveDH) { + ssl->buffers.serverDH_P = ssl->ctx->serverDH_P; + ssl->buffers.serverDH_G = ssl->ctx->serverDH_G; + ssl->options.haveDH = 1; + } + } ssl->options.side = WOLFSSL_SERVER_END; /* reset suites in case user switched */ @@ -12206,8 +12260,47 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md) int wolfSSL_clear(WOLFSSL* ssl) { - (void)ssl; - /* TODO: GetErrors().Remove(); */ + ssl->options.isClosed = 0; + ssl->options.connReset = 0; + ssl->options.sentNotify = 0; + + ssl->options.serverState = NULL_STATE; + ssl->options.clientState = NULL_STATE; + ssl->options.connectState = CONNECT_BEGIN; + ssl->options.acceptState = ACCEPT_BEGIN; + ssl->options.handShakeState = NULL_STATE; + ssl->options.handShakeDone = 0; + /* ssl->options.processReply = doProcessInit; */ + + ssl->keys.encryptionOn = 0; + XMEMSET(&ssl->msgsReceived, 0, sizeof(ssl->msgsReceived)); + +#ifndef NO_OLD_TLS +#ifndef NO_MD5 + wc_InitMd5(&ssl->hsHashes->hashMd5); +#endif +#ifndef NO_SHA + if (wc_InitSha(&ssl->hsHashes->hashSha) != 0) + return SSL_FAILURE; +#endif +#endif +#ifndef NO_SHA256 + if (wc_InitSha256(&ssl->hsHashes->hashSha256) != 0) + return SSL_FAILURE; +#endif +#ifdef WOLFSSL_SHA384 + if (wc_InitSha384(&ssl->hsHashes->hashSha384) != 0) + return SSL_FAILURE; +#endif +#ifdef WOLFSSL_SHA512 + if (wc_InitSha512(&ssl->hsHashes->hashSha512) != 0) + return SSL_FAILURE; +#endif + +#ifdef KEEP_PEER_CERT + FreeX509(&ssl->peerCert); +#endif + return SSL_SUCCESS; } @@ -12699,7 +12792,8 @@ static void ExternalFreeX509(WOLFSSL_X509* x509) if (name->fullName.fullName && name->fullName.fullNameLen > 0) { switch (nid) { case ASN_COMMON_NAME: - ret = name->fullName.cnIdx; + if (pos != name->fullName.cnIdx) + ret = name->fullName.cnIdx; break; default: WOLFSSL_MSG("NID not yet implemented"); @@ -15029,33 +15123,40 @@ unsigned long wolfSSL_set_options(WOLFSSL* ssl, unsigned long op) op |= SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS; } + ssl->options.mask |= op; /* by default cookie exchange is on with DTLS */ - if ((op & SSL_OP_COOKIE_EXCHANGE) == SSL_OP_COOKIE_EXCHANGE) { + if ((ssl->options.mask & SSL_OP_COOKIE_EXCHANGE) == SSL_OP_COOKIE_EXCHANGE) { WOLFSSL_MSG("\tSSL_OP_COOKIE_EXCHANGE : on by default"); } - if ((op & SSL_OP_NO_SSLv2) == SSL_OP_NO_SSLv2) { + if ((ssl->options.mask & SSL_OP_NO_SSLv2) == SSL_OP_NO_SSLv2) { WOLFSSL_MSG("\tSSL_OP_NO_SSLv2 : wolfSSL does not support SSLv2"); } - if ((op & SSL_OP_NO_SSLv3) == SSL_OP_NO_SSLv3) { + if ((ssl->options.mask & SSL_OP_NO_TLSv1_2) == SSL_OP_NO_TLSv1_2) { + WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_2"); + if (ssl->version.minor == TLSv1_2_MINOR) + ssl->version.minor = TLSv1_1_MINOR; + } + + if ((ssl->options.mask & SSL_OP_NO_TLSv1_1) == SSL_OP_NO_TLSv1_1) { + WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_1"); + if (ssl->version.minor == TLSv1_1_MINOR) + ssl->version.minor = TLSv1_MINOR; + } + + if ((ssl->options.mask & SSL_OP_NO_TLSv1) == SSL_OP_NO_TLSv1) { + WOLFSSL_MSG("\tSSL_OP_NO_TLSv1"); + if (ssl->version.minor == TLSv1_MINOR) + ssl->version.minor = SSLv3_MINOR; + } + + if ((ssl->options.mask & SSL_OP_NO_SSLv3) == SSL_OP_NO_SSLv3) { WOLFSSL_MSG("\tSSL_OP_NO_SSLv3"); } - if ((op & SSL_OP_NO_TLSv1) == SSL_OP_NO_TLSv1) { - WOLFSSL_MSG("\tSSL_OP_NO_TLSv1"); - } - - if ((op & SSL_OP_NO_TLSv1_1) == SSL_OP_NO_TLSv1_1) { - WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_1"); - } - - if ((op & SSL_OP_NO_TLSv1_2) == SSL_OP_NO_TLSv1_2) { - WOLFSSL_MSG("\tSSL_OP_NO_TLSv1_2"); - } - - if ((op & SSL_OP_NO_COMPRESSION) == SSL_OP_NO_COMPRESSION) { + if ((ssl->options.mask & SSL_OP_NO_COMPRESSION) == SSL_OP_NO_COMPRESSION) { #ifdef HAVE_LIBZ WOLFSSL_MSG("SSL_OP_NO_COMPRESSION"); ssl->options.usingCompression = 0; @@ -15064,8 +15165,6 @@ unsigned long wolfSSL_set_options(WOLFSSL* ssl, unsigned long op) #endif } - ssl->options.mask |= op; - return ssl->options.mask; } diff --git a/wolfcrypt/src/ecc.c b/wolfcrypt/src/ecc.c index 32dd99836..dced09b84 100644 --- a/wolfcrypt/src/ecc.c +++ b/wolfcrypt/src/ecc.c @@ -1212,7 +1212,7 @@ const char* wc_ecc_get_name(int curve_id) return NULL; } -static int wc_ecc_set_curve(ecc_key* key, int keysize, int curve_id) +int wc_ecc_set_curve(ecc_key* key, int keysize, int curve_id) { if (keysize <= 0 && curve_id <= 0) { return BAD_FUNC_ARG; diff --git a/wolfcrypt/src/tfm.c b/wolfcrypt/src/tfm.c index 7fba9c64c..6b63b6aa1 100644 --- a/wolfcrypt/src/tfm.c +++ b/wolfcrypt/src/tfm.c @@ -2353,6 +2353,11 @@ int mp_mul_2d(fp_int *a, int b, fp_int *c) return MP_OKAY; } +int mp_div(fp_int * a, fp_int * b, fp_int * c, fp_int * d) +{ + return fp_div(a, b, c, d); +} + int mp_div_2d(fp_int* a, int b, fp_int* c, fp_int* d) { fp_div_2d(a, b, c, d); @@ -2430,6 +2435,11 @@ void mp_rshb (mp_int* a, int x) fp_rshb(a, x); } +void mp_rshd (mp_int* a, int x) +{ + fp_rshd(a, x); +} + int mp_set_int(mp_int *a, mp_digit b) { fp_set(a, b); diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index 1b8dd477f..69295d99c 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -767,36 +767,35 @@ WOLFSSL_API long wolfSSL_get_verify_result(const WOLFSSL *ssl); /* seperated out from other enums because of size */ enum { - /* bit flags (ie 0001 vs 0010) : each is 2 times previous value */ - SSL_OP_MICROSOFT_SESS_ID_BUG = 1, - SSL_OP_NETSCAPE_CHALLENGE_BUG = 2, - SSL_OP_NETSCAPE_REUSE_CIPHER_CHANGE_BUG = 4, - SSL_OP_SSLREF2_REUSE_CERT_TYPE_BUG = 8, - SSL_OP_MICROSOFT_BIG_SSLV3_BUFFER = 16, - SSL_OP_MSIE_SSLV2_RSA_PADDING = 32, - SSL_OP_SSLEAY_080_CLIENT_DH_BUG = 64, - SSL_OP_TLS_D5_BUG = 128, - SSL_OP_TLS_BLOCK_PADDING_BUG = 256, - SSL_OP_TLS_ROLLBACK_BUG = 512, - SSL_OP_ALL = 1024, - SSL_OP_EPHEMERAL_RSA = 2048, - SSL_OP_NO_SSLv3 = 4096, - SSL_OP_NO_TLSv1 = 8192, - SSL_OP_PKCS1_CHECK_1 = 16384, - SSL_OP_PKCS1_CHECK_2 = 32768, - SSL_OP_NETSCAPE_CA_DN_BUG = 65536, - SSL_OP_NETSCAPE_DEMO_CIPHER_CHANGE_BUG = 131072, - SSL_OP_SINGLE_DH_USE = 262144, - SSL_OP_NO_TICKET = 524288, - SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS = 1048576, - SSL_OP_NO_QUERY_MTU = 2097152, - SSL_OP_COOKIE_EXCHANGE = 4194304, - SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION = 8388608, - SSL_OP_SINGLE_ECDH_USE = 16777216, - SSL_OP_CIPHER_SERVER_PREFERENCE = 33554432, - SSL_OP_NO_TLSv1_1 = 67108864, - SSL_OP_NO_TLSv1_2 = 134217728, - SSL_OP_NO_COMPRESSION = 268435456, + SSL_OP_MICROSOFT_SESS_ID_BUG = 0x00000001, + SSL_OP_NETSCAPE_CHALLENGE_BUG = 0x00000002, + SSL_OP_NETSCAPE_REUSE_CIPHER_CHANGE_BUG = 0x00000004, + SSL_OP_SSLREF2_REUSE_CERT_TYPE_BUG = 0x00000008, + SSL_OP_MICROSOFT_BIG_SSLV3_BUFFER = 0x00000010, + SSL_OP_MSIE_SSLV2_RSA_PADDING = 0x00000020, + SSL_OP_SSLEAY_080_CLIENT_DH_BUG = 0x00000040, + SSL_OP_TLS_D5_BUG = 0x00000080, + SSL_OP_TLS_BLOCK_PADDING_BUG = 0x00000100, + SSL_OP_TLS_ROLLBACK_BUG = 0x00000200, + SSL_OP_ALL = 0x00000400, + SSL_OP_EPHEMERAL_RSA = 0x00000800, + SSL_OP_NO_SSLv3 = 0x00001000, + SSL_OP_NO_TLSv1 = 0x00002000, + SSL_OP_PKCS1_CHECK_1 = 0x00004000, + SSL_OP_PKCS1_CHECK_2 = 0x00008000, + SSL_OP_NETSCAPE_CA_DN_BUG = 0x00010000, + SSL_OP_NETSCAPE_DEMO_CIPHER_CHANGE_BUG = 0x00020000, + SSL_OP_SINGLE_DH_USE = 0x00040000, + SSL_OP_NO_TICKET = 0x00080000, + SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS = 0x00100000, + SSL_OP_NO_QUERY_MTU = 0x00200000, + SSL_OP_COOKIE_EXCHANGE = 0x00400000, + SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION = 0x00800000, + SSL_OP_SINGLE_ECDH_USE = 0x01000000, + SSL_OP_CIPHER_SERVER_PREFERENCE = 0x02000000, + SSL_OP_NO_TLSv1_1 = 0x04000000, + SSL_OP_NO_TLSv1_2 = 0x08000000, + SSL_OP_NO_COMPRESSION = 0x10000000, }; @@ -1881,7 +1880,7 @@ WOLFSSL_API int wolfSSL_Rehandshake(WOLFSSL* ssl); WOLFSSL_API int wolfSSL_UseSessionTicket(WOLFSSL* ssl); WOLFSSL_API int wolfSSL_CTX_UseSessionTicket(WOLFSSL_CTX* ctx); WOLFSSL_API int wolfSSL_get_SessionTicket(WOLFSSL*, unsigned char*, unsigned int*); -WOLFSSL_API int wolfSSL_set_SessionTicket(WOLFSSL*, unsigned char*, unsigned int); +WOLFSSL_API int wolfSSL_set_SessionTicket(WOLFSSL*, const unsigned char*, unsigned int); typedef int (*CallbackSessionTicket)(WOLFSSL*, const unsigned char*, int, void*); WOLFSSL_API int wolfSSL_set_SessionTicket_cb(WOLFSSL*, CallbackSessionTicket, void*); diff --git a/wolfssl/wolfcrypt/ecc.h b/wolfssl/wolfcrypt/ecc.h index baf33637b..96d13e9f4 100644 --- a/wolfssl/wolfcrypt/ecc.h +++ b/wolfssl/wolfcrypt/ecc.h @@ -340,6 +340,9 @@ int wc_ecc_set_flags(ecc_key* key, word32 flags); WOLFSSL_API void wc_ecc_fp_free(void); +WOLFSSL_API +int wc_ecc_set_curve(ecc_key* key, int keysize, int curve_id); + WOLFSSL_API int wc_ecc_is_valid_idx(int n); WOLFSSL_API diff --git a/wolfssl/wolfcrypt/tfm.h b/wolfssl/wolfcrypt/tfm.h index 53357b78a..8d3d7077d 100644 --- a/wolfssl/wolfcrypt/tfm.h +++ b/wolfssl/wolfcrypt/tfm.h @@ -634,6 +634,7 @@ int mp_invmod(mp_int *a, mp_int *b, mp_int *c); int mp_exptmod (mp_int * g, mp_int * x, mp_int * p, mp_int * y); int mp_mul_2d(mp_int *a, int b, mp_int *c); +int mp_div(mp_int * a, mp_int * b, mp_int * c, mp_int * d); int mp_cmp(mp_int *a, mp_int *b); int mp_cmp_d(mp_int *a, mp_digit b); @@ -653,6 +654,7 @@ int mp_set_int(mp_int *a, mp_digit b); int mp_is_bit_set (mp_int * a, mp_digit b); int mp_set_bit (mp_int * a, mp_digit b); void mp_rshb(mp_int *a, int x); +void mp_rshd(mp_int *a, int x); int mp_toradix (mp_int *a, char *str, int radix); int mp_radix_size (mp_int * a, int radix, int *size); From fd3093f937fb6a348ae6a95b5709689464de0181 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Fri, 3 Mar 2017 08:02:10 +1000 Subject: [PATCH 47/68] Protect code with #ifdefs --- src/ssl.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/ssl.c b/src/ssl.c index 14c960355..3d61a73df 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -9958,6 +9958,7 @@ int wolfSSL_set_compression(WOLFSSL* ssl) WOLFSSL_ENTER("SSL_set_accept_state"); if (ssl->options.side == WOLFSSL_CLIENT_END) { + #ifdef HAVE_ECC ecc_key key; word32 idx = 0; @@ -9971,12 +9972,15 @@ int wolfSSL_set_compression(WOLFSSL* ssl) } wc_ecc_free(&key); } + #endif + #ifndef NO_DH if (!ssl->options.haveDH && ssl->ctx->haveDH) { ssl->buffers.serverDH_P = ssl->ctx->serverDH_P; ssl->buffers.serverDH_G = ssl->ctx->serverDH_G; ssl->options.haveDH = 1; } + #endif } ssl->options.side = WOLFSSL_SERVER_END; /* reset suites in case user switched */ From 7897d04145d273f857586cff64039b60b7e5b678 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Fri, 3 Mar 2017 11:31:16 +1000 Subject: [PATCH 48/68] Need GetHMACSize and GetIVSize for wpas 2.0 --- configure.ac | 1 + 1 file changed, 1 insertion(+) diff --git a/configure.ac b/configure.ac index 5c33c2ec9..9c9965eed 100644 --- a/configure.ac +++ b/configure.ac @@ -343,6 +343,7 @@ then enable_shared=no enable_static=yes AM_CFLAGS="$AM_CFLAGS -DHAVE_SECRET_CALLBACK -DWOLFSSL_STATIC_RSA" + AM_CFLAGS="$AM_CFLAGS -DATOMIC_USER" AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_WPAS" fi From 122f648fd8a8caf57bc48c774595a300d199e3a6 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Mon, 6 Mar 2017 09:19:01 +1000 Subject: [PATCH 49/68] Only support client preference order as default for WPAS. --- src/internal.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/internal.c b/src/internal.c index c20646f37..ac5d11d4f 100644 --- a/src/internal.c +++ b/src/internal.c @@ -18841,7 +18841,7 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, if (ssl->suites == NULL) return SUITES_ERROR; -#ifdef OPENSSL_EXTRA +#ifdef WOLFSSL_WPAS if (ssl->options.mask | SSL_OP_CIPHER_SERVER_PREFERENCE) { /* Server order */ for (i = 0; i < ssl->suites->suiteSz; i += 2) { From ac713e62c5ffaea51098da30a153d103ecd2ede8 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Tue, 7 Mar 2017 11:55:23 +1000 Subject: [PATCH 50/68] Code review fixes Put back check for server end when setting DH. Add option to keep resources rather than free after handshake. --- src/ssl.c | 23 ++++++++++++++++++----- wolfssl/internal.h | 1 + wolfssl/ssl.h | 1 + 3 files changed, 20 insertions(+), 5 deletions(-) diff --git a/src/ssl.c b/src/ssl.c index 3d61a73df..f029e8734 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -990,10 +990,8 @@ int wolfSSL_SetTmpDH(WOLFSSL* ssl, const unsigned char* p, int pSz, if (pSz < ssl->options.minDhKeySz) return DH_KEY_SIZE_E; - #ifndef WOLFSSL_WPAS if (ssl->options.side != WOLFSSL_SERVER_END) return SIDE_ERROR; - #endif if (ssl->buffers.serverDH_P.buffer && ssl->buffers.weOwnDH) { XFREE(ssl->buffers.serverDH_P.buffer, ssl->heap, DYNAMIC_TYPE_DH); @@ -2063,6 +2061,20 @@ void wolfSSL_FreeArrays(WOLFSSL* ssl) } } +/* Set option to indicate that the resources are not to be freed after + * handshake. + * + * ssl The SSL/TLS object. + */ +int wolfSSL_KeepResources(WOLFSSL* ssl) +{ + if (ssl == NULL) + return BAD_FUNC_ARG; + + ssl->options.keepResources = 1; + + return 0; +} const byte* wolfSSL_GetMacSecret(WOLFSSL* ssl, int verify) { @@ -7905,16 +7917,16 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl, } #endif /* NO_HANDSHAKE_DONE_CB */ -#ifndef WOLFSSL_WPAS if (!ssl->options.dtls) { - FreeHandshakeResources(ssl); + if (!ssl->options.keepResources) { + FreeHandshakeResources(ssl); + } } #ifdef WOLFSSL_DTLS else { ssl->options.dtlsHsRetain = 1; } #endif /* WOLFSSL_DTLS */ -#endif WOLFSSL_LEAVE("SSL_connect()", SSL_SUCCESS); return SSL_SUCCESS; @@ -23759,4 +23771,5 @@ int wolfSSL_set_msg_callback_arg(WOLFSSL *ssl, void* arg) } #endif + #endif /* WOLFCRYPT_ONLY */ diff --git a/wolfssl/internal.h b/wolfssl/internal.h index 19cb6710f..e81ca8fc1 100755 --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -2494,6 +2494,7 @@ typedef struct Options { #if defined(HAVE_TLS_EXTENSIONS) && defined(HAVE_SUPPORTED_CURVES) word16 userCurves:1; /* indicates user called wolfSSL_UseSupportedCurve */ #endif + word16 keepResources:1; /* Keep resources after handshake */ /* need full byte values for this section */ byte processReply; /* nonblocking resume */ diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index 69295d99c..768eca8d8 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -1650,6 +1650,7 @@ WOLFSSL_API void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl); WOLFSSL_API void wolfSSL_KeepArrays(WOLFSSL*); WOLFSSL_API void wolfSSL_FreeArrays(WOLFSSL*); +WOLFSSL_API int wolfSSL_KeepResources(WOLFSSL* ssl); /* async additions */ WOLFSSL_API int wolfSSL_UseAsync(WOLFSSL*, int devId); From 97b98c5c447127d5df050d00f07b36ade8461886 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Tue, 7 Mar 2017 13:02:49 +1000 Subject: [PATCH 51/68] Changes from review Add a free handshake resources API. Rename to wolfSSL_KeepHandshakeResources(). Add APIs to indicate the client's preference order is to be used when matching cipher suites. --- src/internal.c | 14 ++----------- src/ssl.c | 52 ++++++++++++++++++++++++++++++++++++++++++++-- wolfssl/internal.h | 2 ++ wolfssl/ssl.h | 6 +++++- 4 files changed, 59 insertions(+), 15 deletions(-) diff --git a/src/internal.c b/src/internal.c index ac5d11d4f..c5e4554e5 100644 --- a/src/internal.c +++ b/src/internal.c @@ -3513,6 +3513,7 @@ int InitSSL(WOLFSSL* ssl, WOLFSSL_CTX* ctx) #ifdef HAVE_EXTENDED_MASTER ssl->options.haveEMS = ctx->haveEMS; #endif + ssl->options.useClientOrder = ctx->useClientOrder; #ifdef HAVE_TLS_EXTENSIONS #ifdef HAVE_MAX_FRAGMENT @@ -18841,8 +18842,7 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, if (ssl->suites == NULL) return SUITES_ERROR; -#ifdef WOLFSSL_WPAS - if (ssl->options.mask | SSL_OP_CIPHER_SERVER_PREFERENCE) { + if (!ssl->options.useClientOrder) { /* Server order */ for (i = 0; i < ssl->suites->suiteSz; i += 2) { for (j = 0; j < peerSuites->suiteSz; j += 2) { @@ -18862,16 +18862,6 @@ int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx, } } } -#else - /* Server order */ - for (i = 0; i < ssl->suites->suiteSz; i += 2) { - for (j = 0; j < peerSuites->suiteSz; j += 2) { - ret = CompareSuites(ssl, peerSuites, i, j); - if (ret != MATCH_SUITE_ERROR) - return ret; - } - } -#endif return MATCH_SUITE_ERROR; } diff --git a/src/ssl.c b/src/ssl.c index f029e8734..9e502ea36 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -2065,8 +2065,9 @@ void wolfSSL_FreeArrays(WOLFSSL* ssl) * handshake. * * ssl The SSL/TLS object. + * returns BAD_FUNC_ARG when ssl is NULL and 0 on success. */ -int wolfSSL_KeepResources(WOLFSSL* ssl) +int wolfSSL_KeepHandshakeResources(WOLFSSL* ssl) { if (ssl == NULL) return BAD_FUNC_ARG; @@ -2076,6 +2077,51 @@ int wolfSSL_KeepResources(WOLFSSL* ssl) return 0; } +/* Free the handshake resources after handshake. + * + * ssl The SSL/TLS object. + * returns BAD_FUNC_ARG when ssl is NULL and 0 on success. + */ +int wolfSSL_FreeHandshakeResources(WOLFSSL* ssl) +{ + if (ssl == NULL) + return BAD_FUNC_ARG; + + FreeHandshakeResources(ssl); + + return 0; +} + +/* Use the client's order of preference when matching cipher suites. + * + * ssl The SSL/TLS context object. + * returns BAD_FUNC_ARG when ssl is NULL and 0 on success. + */ +int wolfSSL_CTX_UseClientSuites(WOLFSSL_CTX* ctx) +{ + if (ctx == NULL) + return BAD_FUNC_ARG; + + ctx->useClientOrder = 1; + + return 0; +} + +/* Use the client's order of preference when matching cipher suites. + * + * ssl The SSL/TLS object. + * returns BAD_FUNC_ARG when ssl is NULL and 0 on success. + */ +int wolfSSL_UseClientSuites(WOLFSSL* ssl) +{ + if (ssl == NULL) + return BAD_FUNC_ARG; + + ssl->options.useClientOrder = 1; + + return 0; +} + const byte* wolfSSL_GetMacSecret(WOLFSSL* ssl, int verify) { if (ssl == NULL) @@ -8225,7 +8271,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl, #endif /* NO_HANDSHAKE_DONE_CB */ if (!ssl->options.dtls) { - FreeHandshakeResources(ssl); + if (!ssl->options.keepResources) { + FreeHandshakeResources(ssl); + } } #ifdef WOLFSSL_DTLS else { diff --git a/wolfssl/internal.h b/wolfssl/internal.h index e81ca8fc1..c07ecf792 100755 --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -1984,6 +1984,7 @@ struct WOLFSSL_CTX { byte groupMessages; /* group handshake messages before sending */ byte minDowngrade; /* minimum downgrade version */ byte haveEMS; /* have extended master secret extension */ + byte useClientOrder; /* Use client's cipher preference order */ #if defined(WOLFSSL_SCTP) && defined(WOLFSSL_DTLS) byte dtlsSctp; /* DTLS-over-SCTP mode */ word16 dtlsMtuSz; /* DTLS MTU size */ @@ -2495,6 +2496,7 @@ typedef struct Options { word16 userCurves:1; /* indicates user called wolfSSL_UseSupportedCurve */ #endif word16 keepResources:1; /* Keep resources after handshake */ + word16 useClientOrder:1; /* Use client's cipher order */ /* need full byte values for this section */ byte processReply; /* nonblocking resume */ diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index 768eca8d8..308ea9f90 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -1650,7 +1650,11 @@ WOLFSSL_API void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl); WOLFSSL_API void wolfSSL_KeepArrays(WOLFSSL*); WOLFSSL_API void wolfSSL_FreeArrays(WOLFSSL*); -WOLFSSL_API int wolfSSL_KeepResources(WOLFSSL* ssl); +WOLFSSL_API int wolfSSL_KeepHandshakeResources(WOLFSSL* ssl); +WOLFSSL_API int wolfSSL_FreeHandshakeResources(WOLFSSL* ssl); + +WOLFSSL_API int wolfSSL_CTX_UseClientSuites(WOLFSSL_CTX* ctx); +WOLFSSL_API int wolfSSL_UseClientSuites(WOLFSSL* ssl); /* async additions */ WOLFSSL_API int wolfSSL_UseAsync(WOLFSSL*, int devId); From 003e18ecbc87536bb66c4371ada2e3b3701e07c4 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Wed, 15 Mar 2017 09:38:53 +1000 Subject: [PATCH 52/68] Fixes for scan-build --- examples/client/client.c | 4 ++++ wolfcrypt/test/test.c | 2 +- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/examples/client/client.c b/examples/client/client.c index 71c86da12..e03f0b8ff 100644 --- a/examples/client/client.c +++ b/examples/client/client.c @@ -299,6 +299,10 @@ static int ClientBenchmarkThroughput(WOLFSSL_CTX* ctx, char* host, word16 port, /* Compare TX and RX buffers */ if(XMEMCMP(tx_buffer, rx_buffer, len) != 0) { + free(tx_buffer); + tx_buffer = NULL; + free(rx_buffer); + rx_buffer = NULL; err_sys("Compare TX and RX buffers failed"); } diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 1028d4473..817ac45f4 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -10032,7 +10032,7 @@ static int ecc_test_curve(WC_RNG* rng, int keySize) #if !defined(WOLFSSL_ATECC508A) && defined(HAVE_ECC_KEY_IMPORT) && \ defined(HAVE_ECC_KEY_EXPORT) -static int ecc_point_test() +static int ecc_point_test(void) { int ret; ecc_point* point; From 5a24fd9237bc794b996ccefa7f19b3c5e6d8c208 Mon Sep 17 00:00:00 2001 From: David Garske Date: Wed, 15 Mar 2017 12:23:50 -0700 Subject: [PATCH 53/68] =?UTF-8?q?Fix=20TFM=20mp=5Fset=5Fint=20to=20handle?= =?UTF-8?q?=20long.=20Enhance=20mp=5Fset=5Fint=20to=20use=20mp=5Fset=20if?= =?UTF-8?q?=20less=20than=20max=20mp=5Fdigit.=20Added=20new=20MP=5FSET=5FC?= =?UTF-8?q?HUNK=5FBITS=20to=20eliminate=20hard=20coded=20const=E2=80=99s?= =?UTF-8?q?=20and=20allow=20build=20time=20adjustment.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- wolfcrypt/src/integer.c | 27 +++++++++++++++++---------- wolfcrypt/src/rsa.c | 2 +- wolfcrypt/src/tfm.c | 38 ++++++++++++++++++++++++++++++++++++-- wolfssl/wolfcrypt/tfm.h | 4 +++- 4 files changed, 57 insertions(+), 14 deletions(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index 669d54d43..ddaad3f59 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -3903,25 +3903,32 @@ int fast_s_mp_mul_high_digs (mp_int * a, mp_int * b, mp_int * c, int digs) } -/* set a 32-bit const */ +#ifndef MP_SET_CHUNK_BITS + #define MP_SET_CHUNK_BITS 4 +#endif int mp_set_int (mp_int * a, unsigned long b) { - int x, res; + int x, res; + + /* use direct mp_set if b is less than mp_digit max */ + if (b < MP_DIGIT_MAX) { + return mp_set (a, b); + } mp_zero (a); - /* set four bits at a time */ - for (x = 0; x < 8; x++) { - /* shift the number up four bits */ - if ((res = mp_mul_2d (a, 4, a)) != MP_OKAY) { + /* set chunk bits at a time */ + for (x = 0; x < (int)(sizeof(long) * 8) / MP_SET_CHUNK_BITS; x++) { + /* shift the number up chunk bits */ + if ((res = mp_mul_2d (a, MP_SET_CHUNK_BITS, a)) != MP_OKAY) { return res; } - /* OR in the top four bits of the source */ - a->dp[0] |= (b >> 28) & 15; + /* OR in the top bits of the source */ + a->dp[0] |= (b >> (32 - MP_SET_CHUNK_BITS)) & ((1 << MP_SET_CHUNK_BITS) - 1); - /* shift the source up to the next four bits */ - b <<= 4; + /* shift the source up to the next chunk bits */ + b <<= MP_SET_CHUNK_BITS; /* ensure that digits are not clamped off */ a->used += 1; diff --git a/wolfcrypt/src/rsa.c b/wolfcrypt/src/rsa.c index fd9840dcd..274bcc4be 100644 --- a/wolfcrypt/src/rsa.c +++ b/wolfcrypt/src/rsa.c @@ -1484,7 +1484,7 @@ int wc_MakeRsaKey(RsaKey* key, int size, long e, WC_RNG* rng) if ((err = mp_init_multi(&p, &q, &tmp1, &tmp2, &tmp3, NULL)) != MP_OKAY) return err; - err = mp_set_int(&tmp3, (mp_digit)e); + err = mp_set_int(&tmp3, e); /* make p */ if (err == MP_OKAY) { diff --git a/wolfcrypt/src/tfm.c b/wolfcrypt/src/tfm.c index 6b63b6aa1..68738b36b 100644 --- a/wolfcrypt/src/tfm.c +++ b/wolfcrypt/src/tfm.c @@ -1963,6 +1963,40 @@ void fp_set(fp_int *a, fp_digit b) a->used = a->dp[0] ? 1 : 0; } + +#ifndef MP_SET_CHUNK_BITS + #define MP_SET_CHUNK_BITS 4 +#endif +void fp_set_int(fp_int *a, unsigned long b) +{ + int x; + + /* use direct fp_set if b is less than fp_digit max */ + if (b < FP_DIGIT_MAX) { + fp_set (a, b); + return; + } + + fp_zero (a); + + /* set chunk bits at a time */ + for (x = 0; x < (int)(sizeof(long) * 8) / MP_SET_CHUNK_BITS; x++) { + fp_mul_2d (a, MP_SET_CHUNK_BITS, a); + + /* OR in the top bits of the source */ + a->dp[0] |= (b >> (32 - MP_SET_CHUNK_BITS)) & ((1 << MP_SET_CHUNK_BITS) - 1); + + /* shift the source up to the next chunk bits */ + b <<= MP_SET_CHUNK_BITS; + + /* ensure that digits are not clamped off */ + a->used += 1; + } + + /* clamp digits */ + fp_clamp(a); +} + /* check if a bit is set */ int fp_is_bit_set (fp_int *a, fp_digit b) { @@ -2440,9 +2474,9 @@ void mp_rshd (mp_int* a, int x) fp_rshd(a, x); } -int mp_set_int(mp_int *a, mp_digit b) +int mp_set_int(mp_int *a, unsigned long b) { - fp_set(a, b); + fp_set_int(a, b); return MP_OKAY; } diff --git a/wolfssl/wolfcrypt/tfm.h b/wolfssl/wolfcrypt/tfm.h index 8d3d7077d..8427412d0 100644 --- a/wolfssl/wolfcrypt/tfm.h +++ b/wolfssl/wolfcrypt/tfm.h @@ -260,6 +260,7 @@ #endif #define FP_MASK (fp_digit)(-1) +#define FP_DIGIT_MAX FP_MASK #define FP_SIZE (FP_MAX_SIZE/DIGIT_BIT) /* signs */ @@ -382,6 +383,7 @@ void fp_clear(fp_int *a); /* uses ForceZero to clear sensitive memory */ /* set to a small digit */ void fp_set(fp_int *a, fp_digit b); +void fp_set_int(fp_int *a, unsigned long b); /* check if a bit is set */ int fp_is_bit_set(fp_int *a, fp_digit b); @@ -650,7 +652,7 @@ int mp_isodd(mp_int* a); int mp_iszero(mp_int* a); int mp_count_bits(mp_int *a); int mp_leading_bit(mp_int *a); -int mp_set_int(mp_int *a, mp_digit b); +int mp_set_int(mp_int *a, unsigned long b); int mp_is_bit_set (mp_int * a, mp_digit b); int mp_set_bit (mp_int * a, mp_digit b); void mp_rshb(mp_int *a, int x); From 628f740363b724cb37595a396d61f1f2387d83bf Mon Sep 17 00:00:00 2001 From: David Garske Date: Mon, 6 Mar 2017 09:49:05 -0800 Subject: [PATCH 54/68] =?UTF-8?q?Added=20support=20for=20inline=20CRL=20lo?= =?UTF-8?q?okup=20when=20HAVE=5FCRL=5FIO=20is=20defined=20(shares=20code?= =?UTF-8?q?=20with=20OCSP=20lookup=20in=20io.c).=20Added=20http=20chunk=20?= =?UTF-8?q?transfer=20encoding=20support.=20Added=20default=20connection?= =?UTF-8?q?=20timeout=20value=20(DEFAULT=5FTIMEOUT=5FSEC)=20and=20new=20wo?= =?UTF-8?q?lfIO=5FSetTimeout()=20API=20with=20HAVE=5FIO=5FTIMEOUT.=20Added?= =?UTF-8?q?=20generic=20wolfIO=5F=20API=E2=80=99s=20for=20connect,=20selec?= =?UTF-8?q?t,=20non-blocking,=20read=20and=20write.=20Added=20new=20define?= =?UTF-8?q?=20USE=5FWOLFSSL=5FIO=20to=20enable=20access=20to=20new=20wolfI?= =?UTF-8?q?O=5F*=20socket=20wrappers=20even=20when=20WOLFSSL=5FUSER=5FIO?= =?UTF-8?q?=20is=20defined.=20Moved=20all=20API=20declarations=20for=20io.?= =?UTF-8?q?c=20into=20new=20io.h=20header.=20Added=20HAVE=5FHTTP=5FCLIENT?= =?UTF-8?q?=20to=20expose=20HTTP=20API=E2=80=99s.=20Moved=20SOCKET=5FT=20a?= =?UTF-8?q?nd=20SOCKET=5F=20defines=20into=20io.h.=20Added=20WOLFIO=5FDEBU?= =?UTF-8?q?G=20define=20to=20display=20request/responses.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- examples/client/client.c | 57 ++- src/crl.c | 37 +- src/internal.c | 2 + src/io.c | 1053 ++++++++++++++++++++++---------------- src/ssl.c | 37 ++ wolfssl/error-ssl.h | 1 + wolfssl/include.am | 3 +- wolfssl/internal.h | 15 +- wolfssl/io.h | 349 +++++++++++++ wolfssl/ssl.h | 77 +-- 10 files changed, 1083 insertions(+), 548 deletions(-) create mode 100644 wolfssl/io.h diff --git a/examples/client/client.c b/examples/client/client.c index e03f0b8ff..6774ad08a 100644 --- a/examples/client/client.c +++ b/examples/client/client.c @@ -57,6 +57,8 @@ static int devId = INVALID_DEVID; #endif +#define DEFAULT_TIMEOUT_SEC 2 + /* Note on using port 0: the client standalone example doesn't utilize the * port 0 port sharing; that is used by (1) the server in external control * test mode and (2) the testsuite which uses this code and sets up the correct @@ -277,7 +279,7 @@ static int ClientBenchmarkThroughput(WOLFSSL_CTX* ctx, char* host, word16 port, tx_time += current_time(0) - start; /* Perform RX */ - select_ret = tcp_select(sockfd, 1); /* Timeout=1 second */ + select_ret = tcp_select(sockfd, DEFAULT_TIMEOUT_SEC); if (select_ret == TEST_RECV_READY) { start = current_time(1); rx_pos = 0; @@ -1182,6 +1184,10 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) #ifdef HAVE_OCSP if (useOcsp) { + #ifdef HAVE_IO_TIMEOUT + wolfIO_SetTimeout(DEFAULT_TIMEOUT_SEC); + #endif + if (ocspUrl != NULL) { wolfSSL_CTX_SetOCSP_OverrideURL(ctx, ocspUrl); wolfSSL_CTX_EnableOCSP(ctx, WOLFSSL_OCSP_NO_NONCE @@ -1458,6 +1464,10 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) #ifdef HAVE_CRL if (disableCRL == 0) { + #ifdef HAVE_IO_TIMEOUT + wolfIO_SetTimeout(DEFAULT_TIMEOUT_SEC); + #endif + if (wolfSSL_EnableCRL(ssl, WOLFSSL_CRL_CHECKALL) != SSL_SUCCESS) { wolfSSL_free(ssl); wolfSSL_CTX_free(ctx); @@ -1527,7 +1537,7 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) } } #else - timeout.tv_sec = 2; + timeout.tv_sec = DEFAULT_TIMEOUT_SEC; timeout.tv_usec = 0; NonBlockingSSL_Connect(ssl); /* will keep retrying on timeout */ #endif @@ -1791,7 +1801,7 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) err_sys("SSL resume failed"); } #else - timeout.tv_sec = 2; + timeout.tv_sec = DEFAULT_TIMEOUT_SEC; timeout.tv_usec = 0; NonBlockingSSL_Connect(ssl); /* will keep retrying on timeout */ #endif @@ -1848,32 +1858,33 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) #endif } - input = wolfSSL_read(sslResume, reply, sizeof(reply)-1); + input = wolfSSL_read(sslResume, reply, sizeof(reply)-1); - if (input > 0) { - reply[input] = 0; - printf("Server resume response: %s\n", reply); + if (input > 0) { + reply[input] = 0; + printf("Server resume response: %s\n", reply); - if (sendGET) { /* get html */ - while (1) { - input = wolfSSL_read(sslResume, reply, sizeof(reply)-1); - if (input > 0) { - reply[input] = 0; - printf("%s\n", reply); + if (sendGET) { /* get html */ + while (1) { + input = wolfSSL_read(sslResume, reply, sizeof(reply)-1); + if (input > 0) { + reply[input] = 0; + printf("%s\n", reply); + } + else + break; } - else - break; } } - } else if (input < 0) { - int readErr = wolfSSL_get_error(sslResume, 0); - if (readErr != SSL_ERROR_WANT_READ) { - printf("wolfSSL_read error %d!\n", readErr); - wolfSSL_free(sslResume); - wolfSSL_CTX_free(ctx); - err_sys("wolfSSL_read failed"); + else if (input < 0) { + int readErr = wolfSSL_get_error(sslResume, 0); + if (readErr != SSL_ERROR_WANT_READ) { + printf("wolfSSL_read error %d!\n", readErr); + wolfSSL_free(sslResume); + wolfSSL_CTX_free(ctx); + err_sys("wolfSSL_read failed"); + } } - } /* try to send session break */ wolfSSL_write(sslResume, msg, msgSz); diff --git a/src/crl.c b/src/crl.c index 09e633373..49a152cfb 100755 --- a/src/crl.c +++ b/src/crl.c @@ -149,15 +149,12 @@ void FreeCRL(WOLFSSL_CRL* crl, int dynamic) } -/* Is the cert ok with CRL, return 0 on success */ -int CheckCertCRL(WOLFSSL_CRL* crl, DecodedCert* cert) +static int CheckCertCRLList(WOLFSSL_CRL* crl, DecodedCert* cert, int *pFoundEntry) { CRL_Entry* crle; int foundEntry = 0; int ret = 0; - WOLFSSL_ENTER("CheckCertCRL"); - if (wc_LockMutex(&crl->crlLock) != 0) { WOLFSSL_MSG("wc_LockMutex failed"); return BAD_MUTEX_E; @@ -204,9 +201,39 @@ int CheckCertCRL(WOLFSSL_CRL* crl, DecodedCert* cert) wc_UnLockMutex(&crl->crlLock); + *pFoundEntry = foundEntry; + + return ret; +} + +/* Is the cert ok with CRL, return 0 on success */ +int CheckCertCRL(WOLFSSL_CRL* crl, DecodedCert* cert) +{ + int foundEntry = 0; + int ret = 0; + + WOLFSSL_ENTER("CheckCertCRL"); + + ret = CheckCertCRLList(crl, cert, &foundEntry); + +#ifdef HAVE_CRL_IO + if (foundEntry == 0) { + /* perform embedded lookup */ + if (crl->crlIOCb) { + ret = crl->crlIOCb(crl, (const char*)cert->extCrlInfo, + cert->extCrlInfoSz); + if (ret >= 0) { + /* try again */ + ret = CheckCertCRLList(crl, cert, &foundEntry); + } + } + } +#endif + if (foundEntry == 0) { WOLFSSL_MSG("Couldn't find CRL for status check"); ret = CRL_MISSING; + if (crl->cm->cbMissingCRL) { char url[256]; @@ -219,11 +246,11 @@ int CheckCertCRL(WOLFSSL_CRL* crl, DecodedCert* cert) else { WOLFSSL_MSG("CRL url too long"); } + crl->cm->cbMissingCRL(url); } } - return ret; } diff --git a/src/internal.c b/src/internal.c index c5e4554e5..fb5b68f19 100644 --- a/src/internal.c +++ b/src/internal.c @@ -11853,6 +11853,8 @@ const char* wolfSSL_ERR_reason_error_string(unsigned long e) case NOT_CA_ERROR: return "Not a CA by basic constraint error"; + case HTTP_TIMEOUT: + return "HTTP timeout for OCSP or CRL req"; case BAD_CERT_MANAGER_ERROR: return "Bad Cert Manager error"; diff --git a/src/io.c b/src/io.c index e90acb866..692d25d49 100644 --- a/src/io.c +++ b/src/io.c @@ -36,197 +36,29 @@ #include #include +#include + +#if defined(HAVE_HTTP_CLIENT) + #include /* atoi(), strtol() */ +#endif + +/* +Possible IO enable options: + * WOLFSSL_USER_IO: Disables default Embed* callbacks and default: off + allows user to define their own using + wolfSSL_SetIORecv and wolfSSL_SetIOSend + * USE_WOLFSSL_IO: Enables the wolfSSL IO functions default: off + * HAVE_HTTP_CLIENT: Enables HTTP client API's default: off + (unless HAVE_OCSP or HAVE_CRL_IO defined) + */ /* if user writes own I/O callbacks they can define WOLFSSL_USER_IO to remove automatic setting of default I/O functions EmbedSend() and EmbedReceive() but they'll still need SetCallback xxx() at end of file */ -#ifndef WOLFSSL_USER_IO - -#ifdef HAVE_LIBZ - #include "zlib.h" -#endif - -#ifndef USE_WINDOWS_API - #ifdef WOLFSSL_LWIP - /* lwIP needs to be configured to use sockets API in this mode */ - /* LWIP_SOCKET 1 in lwip/opt.h or in build */ - #include "lwip/sockets.h" - #include - #ifndef LWIP_PROVIDE_ERRNO - #define LWIP_PROVIDE_ERRNO 1 - #endif - #elif defined(FREESCALE_MQX) - #include - #include - #elif defined(FREESCALE_KSDK_MQX) - #include - #elif defined(WOLFSSL_MDK_ARM) || defined(WOLFSSL_KEIL_TCP_NET) - #if !defined(WOLFSSL_MDK_ARM) - #include "cmsis_os.h" - #include "rl_net.h" - #else - #include - #endif - #include "errno.h" - #define SOCKET_T int - #elif defined(WOLFSSL_TIRTOS) - #include - #elif defined(FREERTOS_TCP) - #include "FreeRTOS_Sockets.h" - #elif defined(WOLFSSL_IAR_ARM) - /* nothing */ - #elif defined(WOLFSSL_VXWORKS) - #include - #include - #elif defined(WOLFSSL_ATMEL) - #include "socket/include/socket.h" - #elif defined(INTIME_RTOS) - #undef MIN - #undef MAX - #include - #include - #include - #include - #include - #include - #else - #include - #include - #ifndef EBSNET - #include - #endif - #include - - #if defined(HAVE_RTP_SYS) - #include - #elif defined(EBSNET) - #include "rtipapi.h" /* errno */ - #include "socket.h" - #elif !defined(DEVKITPRO) && !defined(WOLFSSL_PICOTCP) - #include - #include - #include - #include - #ifdef __PPU - #include - #else - #include - #endif - #endif - #endif -#endif /* USE_WINDOWS_API */ - -#ifdef __sun - #include -#endif - -#ifdef USE_WINDOWS_API - /* no epipe yet */ - #ifndef WSAEPIPE - #define WSAEPIPE -12345 - #endif - #define SOCKET_EWOULDBLOCK WSAEWOULDBLOCK - #define SOCKET_EAGAIN WSAETIMEDOUT - #define SOCKET_ECONNRESET WSAECONNRESET - #define SOCKET_EINTR WSAEINTR - #define SOCKET_EPIPE WSAEPIPE - #define SOCKET_ECONNREFUSED WSAENOTCONN - #define SOCKET_ECONNABORTED WSAECONNABORTED - #define close(s) closesocket(s) -#elif defined(__PPU) - #define SOCKET_EWOULDBLOCK SYS_NET_EWOULDBLOCK - #define SOCKET_EAGAIN SYS_NET_EAGAIN - #define SOCKET_ECONNRESET SYS_NET_ECONNRESET - #define SOCKET_EINTR SYS_NET_EINTR - #define SOCKET_EPIPE SYS_NET_EPIPE - #define SOCKET_ECONNREFUSED SYS_NET_ECONNREFUSED - #define SOCKET_ECONNABORTED SYS_NET_ECONNABORTED -#elif defined(FREESCALE_MQX) || defined(FREESCALE_KSDK_MQX) - #if MQX_USE_IO_OLD - /* RTCS old I/O doesn't have an EWOULDBLOCK */ - #define SOCKET_EWOULDBLOCK EAGAIN - #define SOCKET_EAGAIN EAGAIN - #define SOCKET_ECONNRESET RTCSERR_TCP_CONN_RESET - #define SOCKET_EINTR EINTR - #define SOCKET_EPIPE EPIPE - #define SOCKET_ECONNREFUSED RTCSERR_TCP_CONN_REFUSED - #define SOCKET_ECONNABORTED RTCSERR_TCP_CONN_ABORTED - #else - #define SOCKET_EWOULDBLOCK NIO_EWOULDBLOCK - #define SOCKET_EAGAIN NIO_EAGAIN - #define SOCKET_ECONNRESET NIO_ECONNRESET - #define SOCKET_EINTR NIO_EINTR - #define SOCKET_EPIPE NIO_EPIPE - #define SOCKET_ECONNREFUSED NIO_ECONNREFUSED - #define SOCKET_ECONNABORTED NIO_ECONNABORTED - #endif -#elif defined(WOLFSSL_MDK_ARM)|| defined(WOLFSSL_KEIL_TCP_NET) - #if !defined(WOLFSSL_MDK_ARM) - #define SOCKET_EWOULDBLOCK BSD_ERROR_WOULDBLOCK - #define SOCKET_EAGAIN BSD_ERROR_LOCKED - #define SOCKET_ECONNRESET BSD_ERROR_CLOSED - #define SOCKET_EINTR BSD_ERROR - #define SOCKET_EPIPE BSD_ERROR - #define SOCKET_ECONNREFUSED BSD_ERROR - #define SOCKET_ECONNABORTED BSD_ERROR - #else - #define SOCKET_EWOULDBLOCK SCK_EWOULDBLOCK - #define SOCKET_EAGAIN SCK_ELOCKED - #define SOCKET_ECONNRESET SCK_ECLOSED - #define SOCKET_EINTR SCK_ERROR - #define SOCKET_EPIPE SCK_ERROR - #define SOCKET_ECONNREFUSED SCK_ERROR - #define SOCKET_ECONNABORTED SCK_ERROR - #endif -#elif defined(WOLFSSL_PICOTCP) - #define SOCKET_EWOULDBLOCK PICO_ERR_EAGAIN - #define SOCKET_EAGAIN PICO_ERR_EAGAIN - #define SOCKET_ECONNRESET PICO_ERR_ECONNRESET - #define SOCKET_EINTR PICO_ERR_EINTR - #define SOCKET_EPIPE PICO_ERR_EIO - #define SOCKET_ECONNREFUSED PICO_ERR_ECONNREFUSED - #define SOCKET_ECONNABORTED PICO_ERR_ESHUTDOWN -#elif defined(FREERTOS_TCP) - #define SOCKET_EWOULDBLOCK FREERTOS_EWOULDBLOCK - #define SOCKET_EAGAIN FREERTOS_EWOULDBLOCK - #define SOCKET_ECONNRESET FREERTOS_SOCKET_ERROR - #define SOCKET_EINTR FREERTOS_SOCKET_ERROR - #define SOCKET_EPIPE FREERTOS_SOCKET_ERROR - #define SOCKET_ECONNREFUSED FREERTOS_SOCKET_ERROR - #define SOCKET_ECONNABORTED FREERTOS_SOCKET_ERROR -#else - #define SOCKET_EWOULDBLOCK EWOULDBLOCK - #define SOCKET_EAGAIN EAGAIN - #define SOCKET_ECONNRESET ECONNRESET - #define SOCKET_EINTR EINTR - #define SOCKET_EPIPE EPIPE - #define SOCKET_ECONNREFUSED ECONNREFUSED - #define SOCKET_ECONNABORTED ECONNABORTED -#endif /* USE_WINDOWS_API */ - - -#ifdef DEVKITPRO - /* from network.h */ - int net_send(int, const void*, int, unsigned int); - int net_recv(int, void*, int, unsigned int); - #define SEND_FUNCTION net_send - #define RECV_FUNCTION net_recv -#elif defined(WOLFSSL_LWIP) - #define SEND_FUNCTION lwip_send - #define RECV_FUNCTION lwip_recv -#elif defined(WOLFSSL_PICOTCP) - #define SEND_FUNCTION pico_send - #define RECV_FUNCTION pico_recv -#elif defined(FREERTOS_TCP) - #define RECV_FUNCTION(a,b,c,d) FreeRTOS_recv((Socket_t)(a),(void*)(b), (size_t)(c), (BaseType_t)(d)) - #define SEND_FUNCTION(a,b,c,d) FreeRTOS_send((Socket_t)(a),(void*)(b), (size_t)(c), (BaseType_t)(d)) -#else - #define SEND_FUNCTION send - #define RECV_FUNCTION recv -#endif +#if defined(USE_WOLFSSL_IO) || defined(HAVE_HTTP_CLIENT) /* Translates return codes returned from * send() and recv() if need be. @@ -266,14 +98,18 @@ static INLINE int LastError(void) #endif } +#endif /* USE_WOLFSSL_IO || HAVE_HTTP_CLIENT */ + + +#ifdef USE_WOLFSSL_IO + /* The receive embedded callback * return : nb bytes read, or error */ int EmbedReceive(WOLFSSL *ssl, char *buf, int sz, void *ctx) { - int recvd; - int err; int sd = *(int*)ctx; + int recvd; #ifdef WOLFSSL_DTLS { @@ -296,12 +132,9 @@ int EmbedReceive(WOLFSSL *ssl, char *buf, int sz, void *ctx) } #endif - recvd = (int)RECV_FUNCTION(sd, buf, sz, ssl->rflags); - - recvd = TranslateReturnCode(recvd, sd); - + recvd = wolfIO_Recv(sd, buf, sz, ssl->rflags); if (recvd < 0) { - err = LastError(); + int err = LastError(); WOLFSSL_MSG("Embed Receive error"); if (err == SOCKET_EWOULDBLOCK || err == SOCKET_EAGAIN) { @@ -350,15 +183,10 @@ int EmbedSend(WOLFSSL* ssl, char *buf, int sz, void *ctx) { int sd = *(int*)ctx; int sent; - int len = sz; - int err; - - sent = (int)SEND_FUNCTION(sd, &buf[sz - len], len, ssl->wflags); - - sent = TranslateReturnCode(sent, sd); + sent = wolfIO_Send(sd, buf, sz, ssl->wflags); if (sent < 0) { - err = LastError(); + int err = LastError(); WOLFSSL_MSG("Embed Send error"); if (err == SOCKET_EWOULDBLOCK || err == SOCKET_EAGAIN) { @@ -699,92 +527,166 @@ int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) #endif /* WOLFSSL_SESSION_EXPORT */ #endif /* WOLFSSL_DTLS */ -#ifdef HAVE_OCSP - -#include /* atoi() */ +#endif /* USE_WOLFSSL_IO */ -static int Word16ToString(char* d, word16 number) +#if defined(USE_WOLFSSL_IO) + +#ifndef DEFAULT_TIMEOUT_SEC + #define DEFAULT_TIMEOUT_SEC 0 /* no timeout */ +#endif + +#ifdef HAVE_IO_TIMEOUT + static int io_timeout_sec = DEFAULT_TIMEOUT_SEC; +#else + #define io_timeout_sec DEFAULT_TIMEOUT_SEC +#endif + + +void wolfIO_SetTimeout(int to_sec) +{ +#ifdef HAVE_IO_TIMEOUT + io_timeout_sec = to_sec; +#else + (void)to_sec; +#endif +} + +int wolfIO_SetBlockingMode(SOCKET_T sockfd, int non_blocking) +{ + int ret = 0; + +#ifdef USE_WINDOWS_API + unsigned long blocking = non_blocking; + ret = ioctlsocket(sockfd, FIONBIO, &blocking); + if (ret == SOCKET_ERROR) + ret = -1; +#else + ret = fcntl(sockfd, F_GETFL, 0); + if (ret >= 0) { + if (non_blocking) + ret |= O_NONBLOCK; + else + ret &= ~O_NONBLOCK; + ret = fcntl(sockfd, F_SETFL, ret); + } +#endif + if (ret < 0) { + WOLFSSL_MSG("wolfIO_SetBlockingMode failed"); + } + + return ret; +} + +#ifdef _MSC_VER + /* 4204: non-constant aggregate initializer (nfds = sockfd + 1) */ + #pragma warning(disable: 4204) +#endif +int wolfIO_Select(SOCKET_T sockfd, int to_sec) +{ + fd_set fds; + SOCKET_T nfds = sockfd + 1; + struct timeval timeout = { (to_sec > 0) ? to_sec : 0, 0}; + int ret; + + FD_ZERO(&fds); + FD_SET(sockfd, &fds); + + ret = select(nfds, &fds, &fds, NULL, &timeout); + if (ret == 0) { + #ifdef DEBUG_HTTP + printf("Timeout: %d\n", ret); + #endif + return HTTP_TIMEOUT; + } + else if (ret > 0) { + if (FD_ISSET(sockfd, &fds)) + return 0; + } + return SOCKET_ERROR_E; +} + +static int wolfIO_Word16ToString(char* d, word16 number) { int i = 0; + word16 order = 10000; + word16 digit; - if (d != NULL) { - word16 order = 10000; - word16 digit; + if (d == NULL) + return i; - if (number == 0) { - d[i++] = '0'; + if (number == 0) + d[i++] = '0'; + else { + while (order) { + digit = number / order; + if (i > 0 || digit != 0) + d[i++] = (char)digit + '0'; + if (digit != 0) + number %= digit * order; + + order = (order > 1) ? order / 10 : 0; } - else { - while (order) { - digit = number / order; - if (i > 0 || digit != 0) { - d[i++] = (char)digit + '0'; - } - if (digit != 0) - number %= digit * order; - if (order > 1) - order /= 10; - else - order = 0; - } - } - d[i] = 0; } + d[i] = 0; /* null terminate */ return i; } - -static int tcp_connect(SOCKET_T* sockfd, const char* ip, word16 port) +int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) { + int ret = 0; struct sockaddr_storage addr; int sockaddr_len = sizeof(struct sockaddr_in); XMEMSET(&addr, 0, sizeof(addr)); - #ifdef HAVE_GETADDRINFO - { - struct addrinfo hints; - struct addrinfo* answer = NULL; - char strPort[6]; +#ifdef WOLFIO_DEBUG + printf("TCP Connect: %s:%d\n", ip, port); +#endif - XMEMSET(&hints, 0, sizeof(hints)); - hints.ai_family = AF_UNSPEC; - hints.ai_socktype = SOCK_STREAM; - hints.ai_protocol = IPPROTO_TCP; +#ifdef HAVE_GETADDRINFO +{ + struct addrinfo hints; + struct addrinfo* answer = NULL; + char strPort[6]; - if (Word16ToString(strPort, port) == 0) { - WOLFSSL_MSG("invalid port number for OCSP responder"); - return -1; - } - - if (getaddrinfo(ip, strPort, &hints, &answer) < 0 || answer == NULL) { - WOLFSSL_MSG("no addr info for OCSP responder"); - return -1; - } - - sockaddr_len = answer->ai_addrlen; - XMEMCPY(&addr, answer->ai_addr, sockaddr_len); - freeaddrinfo(answer); + XMEMSET(&hints, 0, sizeof(hints)); + hints.ai_family = AF_UNSPEC; + hints.ai_socktype = SOCK_STREAM; + hints.ai_protocol = IPPROTO_TCP; + if (wolfIO_Word16ToString(strPort, port) == 0) { + WOLFSSL_MSG("invalid port number for responder"); + return -1; } - #else /* HAVE_GETADDRINFO */ - { - struct hostent* entry = gethostbyname(ip); - struct sockaddr_in *sin = (struct sockaddr_in *)&addr; - if (entry) { - sin->sin_family = AF_INET; - sin->sin_port = htons(port); - XMEMCPY(&sin->sin_addr.s_addr, entry->h_addr_list[0], - entry->h_length); - } - else { - WOLFSSL_MSG("no addr info for OCSP responder"); - return -1; - } + if (getaddrinfo(ip, strPort, &hints, &answer) < 0 || answer == NULL) { + WOLFSSL_MSG("no addr info for responder"); + return -1; } - #endif /* HAVE_GETADDRINFO */ + + sockaddr_len = answer->ai_addrlen; + XMEMCPY(&addr, answer->ai_addr, sockaddr_len); + freeaddrinfo(answer); + +} +#else /* HAVE_GETADDRINFO */ +{ + struct hostent* entry = gethostbyname(ip); + struct sockaddr_in *sin = (struct sockaddr_in *)&addr; + + if (entry) { + sin->sin_family = AF_INET; + sin->sin_port = htons(port); + XMEMCPY(&sin->sin_addr.s_addr, entry->h_addr_list[0], + entry->h_length); + } + else { + WOLFSSL_MSG("no addr info for responder"); + return -1; + } +} +#endif /* HAVE_GETADDRINFO */ *sockfd = (SOCKET_T)socket(addr.ss_family, SOCK_STREAM, 0); @@ -800,248 +702,420 @@ static int tcp_connect(SOCKET_T* sockfd, const char* ip, word16 port) } #endif - if (connect(*sockfd, (struct sockaddr *)&addr, sockaddr_len) != 0) { - WOLFSSL_MSG("OCSP responder tcp connect failed"); +#ifdef HAVE_IO_TIMEOUT + /* if timeout value provided then set socket non-blocking */ + if (to_sec > 0) { + wolfIO_SetBlockingMode(*sockfd, 1); + } +#else + (void)to_sec; +#endif + + ret = connect(*sockfd, (struct sockaddr *)&addr, sockaddr_len); +#ifdef HAVE_IO_TIMEOUT + if (ret != 0) { + if ((errno == EINPROGRESS) && (to_sec > 0)) { + /* wait for connect to complete */ + ret = wolfIO_Select(*sockfd, to_sec); + + /* restore blocking mode */ + wolfIO_SetBlockingMode(*sockfd, 0); + } + } +#endif + if (ret != 0) { + WOLFSSL_MSG("Responder tcp connect failed"); return -1; } - return 0; + return ret; } - -static int build_http_request(const char* domainName, const char* path, - int ocspReqSz, byte* buf, int bufSize) +int wolfIO_Recv(SOCKET_T sd, char *buf, int sz, int rdFlags) { - word32 domainNameLen, pathLen, ocspReqSzStrLen, completeLen; - char ocspReqSzStr[6]; + int recvd; - domainNameLen = (word32)XSTRLEN(domainName); - pathLen = (word32)XSTRLEN(path); - ocspReqSzStrLen = Word16ToString(ocspReqSzStr, (word16)ocspReqSz); + recvd = (int)RECV_FUNCTION(sd, buf, sz, rdFlags); + recvd = TranslateReturnCode(recvd, sd); - completeLen = domainNameLen + pathLen + ocspReqSzStrLen + 84; - if (completeLen > (word32)bufSize) - return 0; - - XSTRNCPY((char*)buf, "POST ", 5); - buf += 5; - XSTRNCPY((char*)buf, path, pathLen); - buf += pathLen; - XSTRNCPY((char*)buf, " HTTP/1.1\r\nHost: ", 17); - buf += 17; - XSTRNCPY((char*)buf, domainName, domainNameLen); - buf += domainNameLen; - XSTRNCPY((char*)buf, "\r\nContent-Length: ", 18); - buf += 18; - XSTRNCPY((char*)buf, ocspReqSzStr, ocspReqSzStrLen); - buf += ocspReqSzStrLen; - XSTRNCPY((char*)buf, - "\r\nContent-Type: application/ocsp-request\r\n\r\n", 44); - - return completeLen; + return recvd; } +int wolfIO_Send(SOCKET_T sd, char *buf, int sz, int wrFlags) +{ + int sent; + int len = sz; -static int decode_url(const char* url, int urlSz, - char* outName, char* outPath, word16* outPort) + sent = (int)SEND_FUNCTION(sd, &buf[sz - len], len, wrFlags); + sent = TranslateReturnCode(sent, sd); + + return sent; +} + +#endif /* USE_WOLFSSL_IO */ + + +#if defined(HAVE_HTTP_CLIENT) + +#ifndef HTTP_SCRATCH_BUFFER_SIZE + #define HTTP_SCRATCH_BUFFER_SIZE 512 +#endif +#ifndef MAX_URL_ITEM_SIZE + #define MAX_URL_ITEM_SIZE 80 +#endif + +int wolfIO_DecodeUrl(const char* url, int urlSz, char* outName, char* outPath, + word16* outPort) { int result = -1; - if (outName != NULL && outPath != NULL && outPort != NULL) - { - if (url == NULL || urlSz == 0) - { + if (url == NULL || urlSz == 0) { + if (outName) *outName = 0; + if (outPath) *outPath = 0; + if (outPort) *outPort = 0; + } + else { + int i, cur; + + /* need to break the url down into scheme, address, and port */ + /* "http://example.com:8080/" */ + /* "http://[::1]:443/" */ + if (XSTRNCMP(url, "http://", 7) == 0) { + cur = 7; + } else cur = 0; + + i = 0; + if (url[cur] == '[') { + cur++; + /* copy until ']' */ + while (url[cur] != 0 && url[cur] != ']' && cur < urlSz) { + if (outName) + outName[i] = url[cur]; + i++; cur++; + } + cur++; /* skip ']' */ } - else - { - int i, cur; - - /* need to break the url down into scheme, address, and port */ - /* "http://example.com:8080/" */ - /* "http://[::1]:443/" */ - if (XSTRNCMP(url, "http://", 7) == 0) { - cur = 7; - } else cur = 0; - - i = 0; - if (url[cur] == '[') { - cur++; - /* copy until ']' */ - while (url[cur] != 0 && url[cur] != ']' && cur < urlSz) { - outName[i++] = url[cur++]; - } - cur++; /* skip ']' */ - } - else { - while (url[cur] != 0 && url[cur] != ':' && - url[cur] != '/' && cur < urlSz) { - outName[i++] = url[cur++]; - } + else { + while (url[cur] != 0 && url[cur] != ':' && + url[cur] != '/' && cur < urlSz) { + if (outName) + outName[i] = url[cur]; + i++; cur++; } + } + if (outName) outName[i] = 0; - /* Need to pick out the path after the domain name */ + /* Need to pick out the path after the domain name */ - if (cur < urlSz && url[cur] == ':') { - char port[6]; - int j; - word32 bigPort = 0; - i = 0; - cur++; - while (cur < urlSz && url[cur] != 0 && url[cur] != '/' && - i < 6) { - port[i++] = url[cur++]; - } + if (cur < urlSz && url[cur] == ':') { + char port[6]; + int j; + word32 bigPort = 0; + i = 0; + cur++; + while (cur < urlSz && url[cur] != 0 && url[cur] != '/' && + i < 6) { + port[i++] = url[cur++]; + } - for (j = 0; j < i; j++) { - if (port[j] < '0' || port[j] > '9') return -1; - bigPort = (bigPort * 10) + (port[j] - '0'); - } + for (j = 0; j < i; j++) { + if (port[j] < '0' || port[j] > '9') return -1; + bigPort = (bigPort * 10) + (port[j] - '0'); + } + if (outPort) *outPort = (word16)bigPort; - } - else - *outPort = 80; - - if (cur < urlSz && url[cur] == '/') { - i = 0; - while (cur < urlSz && url[cur] != 0 && i < 80) { - outPath[i++] = url[cur++]; - } - outPath[i] = 0; - } - else { - outPath[0] = '/'; - outPath[1] = 0; - } - result = 0; } + else if (outPort) + *outPort = 80; + + + if (cur < urlSz && url[cur] == '/') { + i = 0; + while (cur < urlSz && url[cur] != 0 && i < MAX_URL_ITEM_SIZE) { + if (outPath) + outPath[i] = url[cur]; + i++; cur++; + } + if (outPath) + outPath[i] = 0; + } + else if (outPath) { + outPath[0] = '/'; + outPath[1] = 0; + } + + result = 0; } return result; } - -/* return: >0 OCSP Response Size - * -1 error */ -static int process_http_response(int sfd, byte** respBuf, - byte* httpBuf, int httpBufSz, void* heap) +static int wolfIO_HttpProcessResponseBuf(int sfd, byte **recvBuf, int* recvBufSz, + int chunkSz, char* start, int len, int dynType, void* heap) { - int result; + byte* newRecvBuf = NULL; + int newRecvSz = *recvBufSz + chunkSz; + int pos = 0; + + WOLFSSL_MSG("Processing HTTP response"); +#ifdef WOLFIO_DEBUG + printf("HTTP Chunk %d->%d\n", *recvBufSz, chunkSz); +#endif + + newRecvBuf = (byte*)XMALLOC(newRecvSz, heap, dynType); + if (newRecvBuf == NULL) { + WOLFSSL_MSG("wolfIO_HttpProcessResponseBuf malloc failed"); + return MEMORY_E; + } + + /* if buffer already exists, then we are growing it */ + if (*recvBuf) { + XMEMCPY(&newRecvBuf[pos], *recvBuf, *recvBufSz); + XFREE(*recvBuf, heap, dynType); + pos += *recvBufSz; + *recvBuf = NULL; + } + + /* copy the remainder of the httpBuf into the respBuf */ + if (len != 0) { + XMEMCPY(&newRecvBuf[pos], start, len); + pos += len; + } + + /* receive the remainder of chunk */ + while (len < chunkSz) { + int rxSz = wolfIO_Recv(sfd, (char*)&newRecvBuf[pos], chunkSz-len, 0); + if (rxSz > 0) { + len += rxSz; + pos += rxSz; + } + else { + WOLFSSL_MSG("wolfIO_HttpProcessResponseBuf recv failed"); + XFREE(newRecvBuf, heap, dynType); + return -1; + } + } + + *recvBuf = newRecvBuf; + *recvBufSz = newRecvSz; + + return 0; +} + +int wolfIO_HttpProcessResponse(int sfd, const char* appStr, + byte** respBuf, byte* httpBuf, int httpBufSz, int dynType, void* heap) +{ + int result = 0; int len = 0; char *start, *end; - byte *recvBuf = NULL; - int recvBufSz = 0; - enum phr_state { phr_init, phr_http_start, phr_have_length, - phr_have_type, phr_wait_end, phr_http_end + int respBufSz = 0; + int isChunked = 0, chunkSz = 0; + enum phr_state { phr_init, phr_http_start, phr_have_length, phr_have_type, + phr_wait_end, phr_get_chunk_len, phr_get_chunk_data, + phr_http_end } state = phr_init; + *respBuf = NULL; start = end = NULL; do { + if (state == phr_get_chunk_data) { + /* get chunk of data */ + result = wolfIO_HttpProcessResponseBuf(sfd, respBuf, &respBufSz, + chunkSz, start, len, dynType, heap); + + state = (result != 0) ? phr_http_end : phr_get_chunk_len; + end = NULL; + len = 0; + } + + /* read data if no \r\n or first time */ if (end == NULL) { - result = (int)recv(sfd, (char*)httpBuf+len, httpBufSz-len-1, 0); + result = wolfIO_Recv(sfd, (char*)httpBuf+len, httpBufSz-len-1, 0); if (result > 0) { len += result; start = (char*)httpBuf; start[len] = 0; } else { - WOLFSSL_MSG("process_http_response recv http from peer failed"); + WOLFSSL_MSG("wolfIO_HttpProcessResponse recv http from peer failed"); return -1; } } - end = XSTRSTR(start, "\r\n"); + end = XSTRSTR(start, "\r\n"); /* locate end */ + /* handle incomplete rx */ if (end == NULL) { if (len != 0) XMEMMOVE(httpBuf, start, len); start = end = NULL; } + /* when start is "\r\n" */ else if (end == start) { - if (state == phr_wait_end) { - state = phr_http_end; - len -= 2; - start += 2; + /* if waiting for end or need chunk len */ + if (state == phr_wait_end || state == phr_get_chunk_len) { + state = (isChunked) ? phr_get_chunk_len : phr_http_end; + len -= 2; start += 2; /* skip \r\n */ } else { - WOLFSSL_MSG("process_http_response header ended early"); + WOLFSSL_MSG("wolfIO_HttpProcessResponse header ended early"); return -1; } } else { - *end = 0; + *end = 0; /* null terminate */ len -= (int)(end - start) + 2; /* adjust len to remove the first line including the /r/n */ - if (XSTRNCASECMP(start, "HTTP/1", 6) == 0) { - start += 9; - if (XSTRNCASECMP(start, "200 OK", 6) != 0 || - state != phr_init) { - WOLFSSL_MSG("process_http_response not OK"); - return -1; - } - state = phr_http_start; - } - else if (XSTRNCASECMP(start, "Content-Type:", 13) == 0) { - start += 13; - while (*start == ' ' && *start != '\0') start++; - if (XSTRNCASECMP(start, "application/ocsp-response", 25) != 0) { - WOLFSSL_MSG("process_http_response not ocsp-response"); - return -1; - } + #ifdef WOLFIO_DEBUG + printf("HTTP Resp: %s\n", start); + #endif - if (state == phr_http_start) state = phr_have_type; - else if (state == phr_have_length) state = phr_wait_end; - else { - WOLFSSL_MSG("process_http_response type invalid state"); - return -1; - } - } - else if (XSTRNCASECMP(start, "Content-Length:", 15) == 0) { - start += 15; - while (*start == ' ' && *start != '\0') start++; - recvBufSz = atoi(start); - - if (state == phr_http_start) state = phr_have_length; - else if (state == phr_have_type) state = phr_wait_end; - else { - WOLFSSL_MSG("process_http_response length invalid state"); - return -1; - } - } + switch (state) { + case phr_init: + if (XSTRNCASECMP(start, "HTTP/1", 6) == 0) { + start += 9; + if (XSTRNCASECMP(start, "200 OK", 6) != 0) { + WOLFSSL_MSG("wolfIO_HttpProcessResponse not OK"); + return -1; + } + state = phr_http_start; + } + break; + case phr_http_start: + case phr_have_length: + case phr_have_type: + if (XSTRNCASECMP(start, "Content-Type:", 13) == 0) { + start += 13; + while (*start == ' ' && *start != '\0') start++; + if (XSTRNCASECMP(start, appStr, XSTRLEN(appStr)) != 0) { + WOLFSSL_MSG("wolfIO_HttpProcessResponse appstr mismatch"); + return -1; + } + state = (state == phr_http_start) ? phr_have_type : phr_wait_end; + } + else if (XSTRNCASECMP(start, "Content-Length:", 15) == 0) { + start += 15; + while (*start == ' ' && *start != '\0') start++; + chunkSz = atoi(start); + state = (state == phr_http_start) ? phr_have_length : phr_wait_end; + } + else if (XSTRNCASECMP(start, "Transfer-Encoding:", 18) == 0) { + start += 18; + while (*start == ' ' && *start != '\0') start++; + if (XSTRNCASECMP(start, "chunked", 7) == 0) { + isChunked = 1; + state = (state == phr_http_start) ? phr_have_length : phr_wait_end; + } + } + break; + case phr_get_chunk_len: + chunkSz = (int)strtol(start, NULL, 16); /* hex format */ + state = (chunkSz == 0) ? phr_http_end : phr_get_chunk_data; + break; + case phr_get_chunk_data: + /* processing for chunk data done above, since \r\n isn't required */ + case phr_wait_end: + case phr_http_end: + /* do nothing */ + break; + } /* switch (state) */ + /* skip to end plus \r\n */ start = end + 2; } } while (state != phr_http_end); - recvBuf = (byte*)XMALLOC(recvBufSz, heap, DYNAMIC_TYPE_OCSP); - if (recvBuf == NULL) { - WOLFSSL_MSG("process_http_response couldn't create response buffer"); - return -1; + if (!isChunked) { + result = wolfIO_HttpProcessResponseBuf(sfd, respBuf, &respBufSz, chunkSz, + start, len, dynType, heap); } - /* copy the remainder of the httpBuf into the respBuf */ - if (len != 0) - XMEMCPY(recvBuf, start, len); - - /* receive the OCSP response data */ - while (len < recvBufSz) { - result = (int)recv(sfd, (char*)recvBuf+len, recvBufSz-len, 0); - if (result > 0) - len += result; - else { - WOLFSSL_MSG("process_http_response recv ocsp from peer failed"); - return -1; - } + if (result >= 0) { + result = respBufSz; + } + else { + WOLFSSL_ERROR(result); } - *respBuf = recvBuf; - return recvBufSz; + return result; +} + +int wolfIO_HttpBuildRequest(const char* reqType, const char* domainName, + const char* path, int pathLen, int reqSz, const char* contentType, + byte* buf, int bufSize) +{ + word32 reqTypeLen, domainNameLen, reqSzStrLen, contentTypeLen, maxLen; + char reqSzStr[6]; + char* req = (char*)buf; + + reqTypeLen = (word32)XSTRLEN(reqType); + domainNameLen = (word32)XSTRLEN(domainName); + reqSzStrLen = wolfIO_Word16ToString(reqSzStr, (word16)reqSz); + contentTypeLen = (word32)XSTRLEN(contentType); + + /* determine max length */ + maxLen = reqTypeLen + domainNameLen + pathLen + reqSzStrLen + contentTypeLen + 56; + if (maxLen > (word32)bufSize) + return 0; + + XSTRNCPY((char*)buf, reqType, reqTypeLen); + buf += reqTypeLen; + XSTRNCPY((char*)buf, " ", 1); + buf += 1; + XSTRNCPY((char*)buf, path, pathLen); + buf += pathLen; + XSTRNCPY((char*)buf, " HTTP/1.1", 9); + buf += 9; + if (domainNameLen > 0) { + XSTRNCPY((char*)buf, "\r\nHost: ", 8); + buf += 8; + XSTRNCPY((char*)buf, domainName, domainNameLen); + buf += domainNameLen; + } + if (reqSz > 0 && reqSzStrLen > 0) { + XSTRNCPY((char*)buf, "\r\nContent-Length: ", 18); + buf += 18; + XSTRNCPY((char*)buf, reqSzStr, reqSzStrLen); + buf += reqSzStrLen; + } + if (contentTypeLen > 0) { + XSTRNCPY((char*)buf, "\r\nContent-Type: ", 16); + buf += 16; + XSTRNCPY((char*)buf, contentType, contentTypeLen); + buf += contentTypeLen; + } + XSTRNCPY((char*)buf, "\r\n\r\n", 4); + buf += 4; + +#ifdef WOLFIO_DEBUG + printf("HTTP %s: %s", reqType, req); +#endif + + /* calculate actual length based on original and new pointer */ + return (int)((char*)buf - req); } -#define SCRATCH_BUFFER_SIZE 512 +#ifdef HAVE_OCSP + +int wolfIO_HttpBuildRequestOcsp(const char* domainName, const char* path, + int ocspReqSz, byte* buf, int bufSize) +{ + return wolfIO_HttpBuildRequest("POST", domainName, path, (int)XSTRLEN(path), + ocspReqSz, "application/ocsp-request", buf, bufSize); +} + +/* return: >0 OCSP Response Size + * -1 error */ +int wolfIO_HttpProcessResponseOcsp(int sfd, byte** respBuf, + byte* httpBuf, int httpBufSz, void* heap) +{ + return wolfIO_HttpProcessResponse(sfd, "application/ocsp-response", + respBuf, httpBuf, httpBufSz, DYNAMIC_TYPE_OCSP, heap); +} /* in default wolfSSL callback ctx is the heap pointer */ int EmbedOcspLookup(void* ctx, const char* url, int urlSz, @@ -1054,19 +1128,19 @@ int EmbedOcspLookup(void* ctx, const char* url, int urlSz, char* path; char* domainName; #else - char path[80]; - char domainName[80]; + char path[MAX_URL_ITEM_SIZE]; + char domainName[MAX_URL_ITEM_SIZE]; #endif #ifdef WOLFSSL_SMALL_STACK - path = (char*)XMALLOC(80, NULL, DYNAMIC_TYPE_TMP_BUFFER); + path = (char*)XMALLOC(MAX_URL_ITEM_SIZE, NULL, DYNAMIC_TYPE_TMP_BUFFER); if (path == NULL) - return -1; + return MEMORY_E; - domainName = (char*)XMALLOC(80, NULL, DYNAMIC_TYPE_TMP_BUFFER); + domainName = (char*)XMALLOC(MAX_URL_ITEM_SIZE, NULL, DYNAMIC_TYPE_TMP_BUFFER); if (domainName == NULL) { XFREE(path, NULL, DYNAMIC_TYPE_TMP_BUFFER); - return -1; + return MEMORY_E; } #endif @@ -1076,37 +1150,37 @@ int EmbedOcspLookup(void* ctx, const char* url, int urlSz, else if (ocspRespBuf == NULL) { WOLFSSL_MSG("Cannot save OCSP response"); } - else if (decode_url(url, urlSz, domainName, path, &port) < 0) { + else if (wolfIO_DecodeUrl(url, urlSz, domainName, path, &port) < 0) { WOLFSSL_MSG("Unable to decode OCSP URL"); } else { /* Note, the library uses the EmbedOcspRespFree() callback to * free this buffer. */ - int httpBufSz = SCRATCH_BUFFER_SIZE; - byte* httpBuf = (byte*)XMALLOC(httpBufSz, ctx, - DYNAMIC_TYPE_OCSP); + int httpBufSz = HTTP_SCRATCH_BUFFER_SIZE; + byte* httpBuf = (byte*)XMALLOC(httpBufSz, ctx, DYNAMIC_TYPE_OCSP); if (httpBuf == NULL) { WOLFSSL_MSG("Unable to create OCSP response buffer"); } else { - httpBufSz = build_http_request(domainName, path, ocspReqSz, + httpBufSz = wolfIO_HttpBuildRequestOcsp(domainName, path, ocspReqSz, httpBuf, httpBufSz); - if ((tcp_connect(&sfd, domainName, port) != 0) || (sfd <= 0)) { + ret = wolfIO_TcpConnect(&sfd, domainName, port, io_timeout_sec); + if ((ret != 0) || (sfd <= 0)) { WOLFSSL_MSG("OCSP Responder connection failed"); } - else if ((int)send(sfd, (char*)httpBuf, httpBufSz, 0) != + else if (wolfIO_Send(sfd, (char*)httpBuf, httpBufSz, 0) != httpBufSz) { WOLFSSL_MSG("OCSP http request failed"); } - else if ((int)send(sfd, (char*)ocspReqBuf, ocspReqSz, 0) != + else if (wolfIO_Send(sfd, (char*)ocspReqBuf, ocspReqSz, 0) != ocspReqSz) { WOLFSSL_MSG("OCSP ocsp request failed"); } else { - ret = process_http_response(sfd, ocspRespBuf, httpBuf, - SCRATCH_BUFFER_SIZE, ctx); + ret = wolfIO_HttpProcessResponseOcsp(sfd, ocspRespBuf, httpBuf, + HTTP_SCRATCH_BUFFER_SIZE, ctx); } close(sfd); @@ -1122,7 +1196,6 @@ int EmbedOcspLookup(void* ctx, const char* url, int urlSz, return ret; } - /* in default callback ctx is heap hint */ void EmbedOcspRespFree(void* ctx, byte *resp) { @@ -1131,11 +1204,97 @@ void EmbedOcspRespFree(void* ctx, byte *resp) (void)ctx; } +#endif /* HAVE_OCSP */ +#if defined(HAVE_CRL) && defined(HAVE_CRL_IO) + +int wolfIO_HttpBuildRequestCrl(const char* url, int urlSz, + const char* domainName, byte* buf, int bufSize) +{ + return wolfIO_HttpBuildRequest("GET", domainName, url, urlSz, 0, "", + buf, bufSize); +} + +int wolfIO_HttpProcessResponseCrl(WOLFSSL_CRL* crl, int sfd, byte* httpBuf, + int httpBufSz) +{ + int result; + byte *respBuf = NULL; + + result = wolfIO_HttpProcessResponse(sfd, "application/pkix-crl", + &respBuf, httpBuf, httpBufSz, DYNAMIC_TYPE_CRL, crl->heap); + if (result >= 0) { + result = BufferLoadCRL(crl, respBuf, result, SSL_FILETYPE_ASN1); + } + XFREE(respBuf, crl->heap, DYNAMIC_TYPE_CRL); + + return result; +} + +int EmbedCrlLookup(WOLFSSL_CRL* crl, const char* url, int urlSz) +{ + SOCKET_T sfd = 0; + word16 port; + int ret = -1; +#ifdef WOLFSSL_SMALL_STACK + char* domainName; +#else + char domainName[MAX_URL_ITEM_SIZE]; #endif -#endif /* WOLFSSL_USER_IO */ +#ifdef WOLFSSL_SMALL_STACK + domainName = (char*)XMALLOC(MAX_URL_ITEM_SIZE, crl->heap, + DYNAMIC_TYPE_TMP_BUFFER); + if (domainName == NULL) { + XFREE(path, NULL, DYNAMIC_TYPE_TMP_BUFFER); + return MEMORY_E; + } +#endif + + if (wolfIO_DecodeUrl(url, urlSz, domainName, NULL, &port) < 0) { + WOLFSSL_MSG("Unable to decode CRL URL"); + } + else { + int httpBufSz = HTTP_SCRATCH_BUFFER_SIZE; + byte* httpBuf = (byte*)XMALLOC(httpBufSz, crl->heap, + DYNAMIC_TYPE_CRL); + if (httpBuf == NULL) { + WOLFSSL_MSG("Unable to create CRL response buffer"); + } + else { + httpBufSz = wolfIO_HttpBuildRequestCrl(url, urlSz, domainName, + httpBuf, httpBufSz); + + ret = wolfIO_TcpConnect(&sfd, domainName, port, io_timeout_sec); + if ((ret != 0) || (sfd <= 0)) { + WOLFSSL_MSG("CRL connection failed"); + } + else if (wolfIO_Send(sfd, (char*)httpBuf, httpBufSz, 0) + != httpBufSz) { + WOLFSSL_MSG("CRL http get failed"); + } + else { + ret = wolfIO_HttpProcessResponseCrl(crl, sfd, httpBuf, + HTTP_SCRATCH_BUFFER_SIZE); + } + + close(sfd); + XFREE(httpBuf, crl->heap, DYNAMIC_TYPE_CRL); + } + } + +#ifdef WOLFSSL_SMALL_STACK + XFREE(domainName, crl->heap, DYNAMIC_TYPE_TMP_BUFFER); +#endif + + return ret; +} +#endif /* HAVE_CRL && HAVE_CRL_IO */ + +#endif /* HAVE_HTTP_CLIENT */ + + WOLFSSL_API void wolfSSL_SetIORecv(WOLFSSL_CTX *ctx, CallbackIORecv CBIORecv) { @@ -1337,5 +1496,5 @@ void wolfSSL_SetIO_NetX(WOLFSSL* ssl, NX_TCP_SOCKET* nxSocket, ULONG waitOption) } #endif /* HAVE_NETX */ -#endif /* WOLFCRYPT_ONLY */ +#endif /* WOLFCRYPT_ONLY */ diff --git a/src/ssl.c b/src/ssl.c index 9e502ea36..19a718e69 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -4709,7 +4709,12 @@ int wolfSSL_CertManagerEnableCRL(WOLFSSL_CERT_MANAGER* cm, int options) cm->crl = NULL; return SSL_FAILURE; } + + #ifdef HAVE_CRL_IO + cm->crl->crlIOCb = EmbedCrlLookup; + #endif } + cm->crlEnabled = 1; if (options & WOLFSSL_CRL_CHECKALL) cm->crlCheckAll = 1; @@ -5377,6 +5382,17 @@ int wolfSSL_CertManagerSetCRL_Cb(WOLFSSL_CERT_MANAGER* cm, CbMissingCRL cb) return SSL_SUCCESS; } +#ifdef HAVE_CRL_IO +int wolfSSL_CertManagerSetCRL_IOCb(WOLFSSL_CERT_MANAGER* cm, CbCrlIO cb) +{ + if (cm == NULL) + return BAD_FUNC_ARG; + + cm->crl->crlIOCb = cb; + + return SSL_SUCCESS; +} +#endif int wolfSSL_CertManagerLoadCRL(WOLFSSL_CERT_MANAGER* cm, const char* path, int type, int monitor) @@ -5435,6 +5451,16 @@ int wolfSSL_SetCRL_Cb(WOLFSSL* ssl, CbMissingCRL cb) return BAD_FUNC_ARG; } +#ifdef HAVE_CRL_IO +int wolfSSL_SetCRL_IOCb(WOLFSSL* ssl, CbCrlIO cb) +{ + WOLFSSL_ENTER("wolfSSL_SetCRL_Cb"); + if (ssl) + return wolfSSL_CertManagerSetCRL_IOCb(ssl->ctx->cm, cb); + else + return BAD_FUNC_ARG; +} +#endif int wolfSSL_CTX_EnableCRL(WOLFSSL_CTX* ctx, int options) { @@ -5476,6 +5502,17 @@ int wolfSSL_CTX_SetCRL_Cb(WOLFSSL_CTX* ctx, CbMissingCRL cb) return BAD_FUNC_ARG; } +#ifdef HAVE_CRL_IO +int wolfSSL_CTX_SetCRL_IOCb(WOLFSSL_CTX* ctx, CbCrlIO cb) +{ + WOLFSSL_ENTER("wolfSSL_CTX_SetCRL_IOCb"); + if (ctx) + return wolfSSL_CertManagerSetCRL_IOCb(ctx->cm, cb); + else + return BAD_FUNC_ARG; +} +#endif + #endif /* HAVE_CRL */ diff --git a/wolfssl/error-ssl.h b/wolfssl/error-ssl.h index 38f4a7e93..236e4dfb7 100644 --- a/wolfssl/error-ssl.h +++ b/wolfssl/error-ssl.h @@ -152,6 +152,7 @@ enum wolfSSL_ErrorCodes { EXT_MASTER_SECRET_NEEDED_E = -414, /* need EMS enabled to resume */ DTLS_POOL_SZ_E = -415, /* exceeded DTLS pool size */ DECODE_E = -416, /* decode handshake message error */ + HTTP_TIMEOUT = -417, /* HTTP timeout for OCSP or CRL req */ /* add strings to wolfSSL_ERR_reason_error_string in internal.c !!!!! */ /* begin negotiation parameter errors */ diff --git a/wolfssl/include.am b/wolfssl/include.am index 03883b086..029bc3d17 100644 --- a/wolfssl/include.am +++ b/wolfssl/include.am @@ -17,7 +17,8 @@ nobase_include_HEADERS+= \ wolfssl/test.h \ wolfssl/version.h \ wolfssl/ocsp.h \ - wolfssl/crl.h + wolfssl/crl.h \ + wolfssl/io.h noinst_HEADERS+= \ wolfssl/internal.h diff --git a/wolfssl/internal.h b/wolfssl/internal.h index c07ecf792..23db8760f 100755 --- a/wolfssl/internal.h +++ b/wolfssl/internal.h @@ -189,13 +189,6 @@ #endif -#ifdef USE_WINDOWS_API - typedef unsigned int SOCKET_T; -#else - typedef int SOCKET_T; -#endif - - typedef byte word24[3]; /* Define or comment out the cipher suites you'd like to be compiled in @@ -1421,11 +1414,6 @@ int SetCipherList(Suites*, const char* list); unsigned char* exportBuffer, unsigned int sz, void* userCtx); #endif -#ifdef HAVE_NETX - WOLFSSL_LOCAL int NetX_Receive(WOLFSSL *ssl, char *buf, int sz, void *ctx); - WOLFSSL_LOCAL int NetX_Send(WOLFSSL *ssl, char *buf, int sz, void *ctx); -#endif /* HAVE_NETX */ - /* wolfSSL Cipher type just points back to SSL */ struct WOLFSSL_CIPHER { @@ -1521,6 +1509,9 @@ struct CRL_Monitor { struct WOLFSSL_CRL { WOLFSSL_CERT_MANAGER* cm; /* pointer back to cert manager */ CRL_Entry* crlList; /* our CRL list */ +#ifdef HAVE_CRL_IO + CbCrlIO crlIOCb; +#endif wolfSSL_Mutex crlLock; /* CRL list lock */ CRL_Monitor monitors[2]; /* PEM and DER possible */ #ifdef HAVE_CRL_MONITOR diff --git a/wolfssl/io.h b/wolfssl/io.h new file mode 100644 index 000000000..77a483d78 --- /dev/null +++ b/wolfssl/io.h @@ -0,0 +1,349 @@ +/* io.h + * + * Copyright (C) 2006-2016 wolfSSL Inc. + * + * This file is part of wolfSSL. + * + * 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-1335, USA + */ + + +#ifndef WOLFSSL_IO_H +#define WOLFSSL_IO_H + +#ifdef __cplusplus + extern "C" { +#endif + +/* OCSP and CRL_IO require HTTP client */ +#if defined(HAVE_OCSP) || defined(HAVE_CRL_IO) + #ifndef HAVE_HTTP_CLIENT + #define HAVE_HTTP_CLIENT + #endif +#endif + +#if !defined(WOLFSSL_USER_IO) + #ifndef USE_WOLFSSL_IO + #define USE_WOLFSSL_IO + #endif +#endif + + +#if defined(USE_WOLFSSL_IO) || defined(HAVE_HTTP_CLIENT) + +#ifdef HAVE_LIBZ + #include "zlib.h" +#endif + +#ifndef USE_WINDOWS_API + #ifdef WOLFSSL_LWIP + /* lwIP needs to be configured to use sockets API in this mode */ + /* LWIP_SOCKET 1 in lwip/opt.h or in build */ + #include "lwip/sockets.h" + #include + #ifndef LWIP_PROVIDE_ERRNO + #define LWIP_PROVIDE_ERRNO 1 + #endif + #elif defined(FREESCALE_MQX) + #include + #include + #elif defined(FREESCALE_KSDK_MQX) + #include + #elif defined(WOLFSSL_MDK_ARM) || defined(WOLFSSL_KEIL_TCP_NET) + #if !defined(WOLFSSL_MDK_ARM) + #include "cmsis_os.h" + #include "rl_net.h" + #else + #include + #endif + #include "errno.h" + #define SOCKET_T int + #elif defined(WOLFSSL_TIRTOS) + #include + #elif defined(FREERTOS_TCP) + #include "FreeRTOS_Sockets.h" + #elif defined(WOLFSSL_IAR_ARM) + /* nothing */ + #elif defined(WOLFSSL_VXWORKS) + #include + #include + #elif defined(WOLFSSL_ATMEL) + #include "socket/include/socket.h" + #elif defined(INTIME_RTOS) + #undef MIN + #undef MAX + #include + #include + #include + #include + #include + #include + #else + #include + #include + #ifndef EBSNET + #include + #endif + #include + + #if defined(HAVE_RTP_SYS) + #include + #elif defined(EBSNET) + #include "rtipapi.h" /* errno */ + #include "socket.h" + #elif !defined(DEVKITPRO) && !defined(WOLFSSL_PICOTCP) + #include + #include + #include + #include + #ifdef __PPU + #include + #else + #include + #endif + #endif + #endif +#endif /* USE_WINDOWS_API */ + +#ifdef __sun + #include +#endif + +#ifdef USE_WINDOWS_API + /* no epipe yet */ + #ifndef WSAEPIPE + #define WSAEPIPE -12345 + #endif + #define SOCKET_EWOULDBLOCK WSAEWOULDBLOCK + #define SOCKET_EAGAIN WSAETIMEDOUT + #define SOCKET_ECONNRESET WSAECONNRESET + #define SOCKET_EINTR WSAEINTR + #define SOCKET_EPIPE WSAEPIPE + #define SOCKET_ECONNREFUSED WSAENOTCONN + #define SOCKET_ECONNABORTED WSAECONNABORTED + #define close(s) closesocket(s) +#elif defined(__PPU) + #define SOCKET_EWOULDBLOCK SYS_NET_EWOULDBLOCK + #define SOCKET_EAGAIN SYS_NET_EAGAIN + #define SOCKET_ECONNRESET SYS_NET_ECONNRESET + #define SOCKET_EINTR SYS_NET_EINTR + #define SOCKET_EPIPE SYS_NET_EPIPE + #define SOCKET_ECONNREFUSED SYS_NET_ECONNREFUSED + #define SOCKET_ECONNABORTED SYS_NET_ECONNABORTED +#elif defined(FREESCALE_MQX) || defined(FREESCALE_KSDK_MQX) + #if MQX_USE_IO_OLD + /* RTCS old I/O doesn't have an EWOULDBLOCK */ + #define SOCKET_EWOULDBLOCK EAGAIN + #define SOCKET_EAGAIN EAGAIN + #define SOCKET_ECONNRESET RTCSERR_TCP_CONN_RESET + #define SOCKET_EINTR EINTR + #define SOCKET_EPIPE EPIPE + #define SOCKET_ECONNREFUSED RTCSERR_TCP_CONN_REFUSED + #define SOCKET_ECONNABORTED RTCSERR_TCP_CONN_ABORTED + #else + #define SOCKET_EWOULDBLOCK NIO_EWOULDBLOCK + #define SOCKET_EAGAIN NIO_EAGAIN + #define SOCKET_ECONNRESET NIO_ECONNRESET + #define SOCKET_EINTR NIO_EINTR + #define SOCKET_EPIPE NIO_EPIPE + #define SOCKET_ECONNREFUSED NIO_ECONNREFUSED + #define SOCKET_ECONNABORTED NIO_ECONNABORTED + #endif +#elif defined(WOLFSSL_MDK_ARM)|| defined(WOLFSSL_KEIL_TCP_NET) + #if !defined(WOLFSSL_MDK_ARM) + #define SOCKET_EWOULDBLOCK BSD_ERROR_WOULDBLOCK + #define SOCKET_EAGAIN BSD_ERROR_LOCKED + #define SOCKET_ECONNRESET BSD_ERROR_CLOSED + #define SOCKET_EINTR BSD_ERROR + #define SOCKET_EPIPE BSD_ERROR + #define SOCKET_ECONNREFUSED BSD_ERROR + #define SOCKET_ECONNABORTED BSD_ERROR + #else + #define SOCKET_EWOULDBLOCK SCK_EWOULDBLOCK + #define SOCKET_EAGAIN SCK_ELOCKED + #define SOCKET_ECONNRESET SCK_ECLOSED + #define SOCKET_EINTR SCK_ERROR + #define SOCKET_EPIPE SCK_ERROR + #define SOCKET_ECONNREFUSED SCK_ERROR + #define SOCKET_ECONNABORTED SCK_ERROR + #endif +#elif defined(WOLFSSL_PICOTCP) + #define SOCKET_EWOULDBLOCK PICO_ERR_EAGAIN + #define SOCKET_EAGAIN PICO_ERR_EAGAIN + #define SOCKET_ECONNRESET PICO_ERR_ECONNRESET + #define SOCKET_EINTR PICO_ERR_EINTR + #define SOCKET_EPIPE PICO_ERR_EIO + #define SOCKET_ECONNREFUSED PICO_ERR_ECONNREFUSED + #define SOCKET_ECONNABORTED PICO_ERR_ESHUTDOWN +#elif defined(FREERTOS_TCP) + #define SOCKET_EWOULDBLOCK FREERTOS_EWOULDBLOCK + #define SOCKET_EAGAIN FREERTOS_EWOULDBLOCK + #define SOCKET_ECONNRESET FREERTOS_SOCKET_ERROR + #define SOCKET_EINTR FREERTOS_SOCKET_ERROR + #define SOCKET_EPIPE FREERTOS_SOCKET_ERROR + #define SOCKET_ECONNREFUSED FREERTOS_SOCKET_ERROR + #define SOCKET_ECONNABORTED FREERTOS_SOCKET_ERROR +#else + #define SOCKET_EWOULDBLOCK EWOULDBLOCK + #define SOCKET_EAGAIN EAGAIN + #define SOCKET_ECONNRESET ECONNRESET + #define SOCKET_EINTR EINTR + #define SOCKET_EPIPE EPIPE + #define SOCKET_ECONNREFUSED ECONNREFUSED + #define SOCKET_ECONNABORTED ECONNABORTED +#endif /* USE_WINDOWS_API */ + + +#ifdef DEVKITPRO + /* from network.h */ + int net_send(int, const void*, int, unsigned int); + int net_recv(int, void*, int, unsigned int); + #define SEND_FUNCTION net_send + #define RECV_FUNCTION net_recv +#elif defined(WOLFSSL_LWIP) + #define SEND_FUNCTION lwip_send + #define RECV_FUNCTION lwip_recv +#elif defined(WOLFSSL_PICOTCP) + #define SEND_FUNCTION pico_send + #define RECV_FUNCTION pico_recv +#elif defined(FREERTOS_TCP) + #define RECV_FUNCTION(a,b,c,d) FreeRTOS_recv((Socket_t)(a),(void*)(b), (size_t)(c), (BaseType_t)(d)) + #define SEND_FUNCTION(a,b,c,d) FreeRTOS_send((Socket_t)(a),(void*)(b), (size_t)(c), (BaseType_t)(d)) +#else + #define SEND_FUNCTION send + #define RECV_FUNCTION recv +#endif + +#ifdef USE_WINDOWS_API + typedef unsigned int SOCKET_T; +#else + typedef int SOCKET_T; +#endif + +/* IO API's */ +WOLFSSL_API int wolfIO_SetBlockingMode(SOCKET_T sockfd, int non_blocking); +WOLFSSL_API void wolfIO_SetTimeout(int to_sec);; +WOLFSSL_API int wolfIO_Select(SOCKET_T sockfd, int to_sec); +WOLFSSL_API int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, + unsigned short port, int to_sec); +WOLFSSL_API int wolfIO_Send(SOCKET_T sd, char *buf, int sz, int wrFlags); +WOLFSSL_API int wolfIO_Recv(SOCKET_T sd, char *buf, int sz, int rdFlags); + +#endif /* USE_WOLFSSL_IO || HAVE_HTTP_CLIENT */ + + +#if defined(USE_WOLFSSL_IO) + /* default IO callbacks */ + WOLFSSL_API int EmbedReceive(WOLFSSL* ssl, char* buf, int sz, void* ctx); + WOLFSSL_API int EmbedSend(WOLFSSL* ssl, char* buf, int sz, void* ctx); + + #ifdef WOLFSSL_DTLS + WOLFSSL_API int EmbedReceiveFrom(WOLFSSL* ssl, char* buf, int sz, void*); + WOLFSSL_API int EmbedSendTo(WOLFSSL* ssl, char* buf, int sz, void* ctx); + WOLFSSL_API int EmbedGenerateCookie(WOLFSSL* ssl, unsigned char* buf, + int sz, void*); + #ifdef WOLFSSL_SESSION_EXPORT + WOLFSSL_API int EmbedGetPeer(WOLFSSL* ssl, char* ip, int* ipSz, + unsigned short* port, int* fam); + WOLFSSL_API int EmbedSetPeer(WOLFSSL* ssl, char* ip, int ipSz, + unsigned short port, int fam); + #endif /* WOLFSSL_SESSION_EXPORT */ + #endif /* WOLFSSL_DTLS */ +#endif /* USE_WOLFSSL_IO */ + +#ifdef HAVE_OCSP + WOLFSSL_API int wolfIO_HttpBuildRequestOcsp(const char* domainName, + const char* path, int ocspReqSz, unsigned char* buf, int bufSize); + WOLFSSL_API int wolfIO_HttpProcessResponseOcsp(int sfd, + unsigned char** respBuf, unsigned char* httpBuf, int httpBufSz, + void* heap); + + WOLFSSL_API int EmbedOcspLookup(void*, const char*, int, unsigned char*, + int, unsigned char**); + WOLFSSL_API void EmbedOcspRespFree(void*, unsigned char*); +#endif + +#ifdef HAVE_CRL_IO + WOLFSSL_API int wolfIO_HttpBuildRequestCrl(const char* url, int urlSz, + const char* domainName, unsigned char* buf, int bufSize); + WOLFSSL_API int wolfIO_HttpProcessResponseCrl(WOLFSSL_CRL* crl, int sfd, + unsigned char* httpBuf, int httpBufSz); + + WOLFSSL_API int EmbedCrlLookup(WOLFSSL_CRL* crl, const char* url, + int urlSz); +#endif + + +#if defined(HAVE_HTTP_CLIENT) + WOLFSSL_API int wolfIO_DecodeUrl(const char* url, int urlSz, char* outName, + char* outPath, unsigned short* outPort); + + WOLFSSL_API int wolfIO_HttpBuildRequest(const char* reqType, + const char* domainName, const char* path, int pathLen, int reqSz, + const char* contentType, unsigned char* buf, int bufSize); + WOLFSSL_API int wolfIO_HttpProcessResponse(int sfd, const char* appStr, + unsigned char** respBuf, unsigned char* httpBuf, int httpBufSz, + int dynType, void* heap); +#endif /* HAVE_HTTP_CLIENT */ + + +/* I/O callbacks */ +typedef int (*CallbackIORecv)(WOLFSSL *ssl, char *buf, int sz, void *ctx); +typedef int (*CallbackIOSend)(WOLFSSL *ssl, char *buf, int sz, void *ctx); +WOLFSSL_API void wolfSSL_SetIORecv(WOLFSSL_CTX*, CallbackIORecv); +WOLFSSL_API void wolfSSL_SetIOSend(WOLFSSL_CTX*, CallbackIOSend); + +WOLFSSL_API void wolfSSL_SetIOReadCtx( WOLFSSL* ssl, void *ctx); +WOLFSSL_API void wolfSSL_SetIOWriteCtx(WOLFSSL* ssl, void *ctx); + +WOLFSSL_API void* wolfSSL_GetIOReadCtx( WOLFSSL* ssl); +WOLFSSL_API void* wolfSSL_GetIOWriteCtx(WOLFSSL* ssl); + +WOLFSSL_API void wolfSSL_SetIOReadFlags( WOLFSSL* ssl, int flags); +WOLFSSL_API void wolfSSL_SetIOWriteFlags(WOLFSSL* ssl, int flags); + + +#ifdef HAVE_NETX + WOLFSSL_LOCAL int NetX_Receive(WOLFSSL *ssl, char *buf, int sz, void *ctx); + WOLFSSL_LOCAL int NetX_Send(WOLFSSL *ssl, char *buf, int sz, void *ctx); + + WOLFSSL_API void wolfSSL_SetIO_NetX(WOLFSSL* ssl, NX_TCP_SOCKET* nxsocket, + ULONG waitoption); +#endif /* HAVE_NETX */ + +#ifdef WOLFSSL_DTLS + typedef int (*CallbackGenCookie)(WOLFSSL* ssl, unsigned char* buf, int sz, + void* ctx); + WOLFSSL_API void wolfSSL_CTX_SetGenCookie(WOLFSSL_CTX*, CallbackGenCookie); + WOLFSSL_API void wolfSSL_SetCookieCtx(WOLFSSL* ssl, void *ctx); + WOLFSSL_API void* wolfSSL_GetCookieCtx(WOLFSSL* ssl); + + #ifdef WOLFSSL_SESSION_EXPORT + typedef int (*CallbackGetPeer)(WOLFSSL* ssl, char* ip, int* ipSz, + unsigned short* port, int* fam); + typedef int (*CallbackSetPeer)(WOLFSSL* ssl, char* ip, int ipSz, + unsigned short port, int fam); + + WOLFSSL_API void wolfSSL_CTX_SetIOGetPeer(WOLFSSL_CTX*, CallbackGetPeer); + WOLFSSL_API void wolfSSL_CTX_SetIOSetPeer(WOLFSSL_CTX*, CallbackSetPeer); + #endif /* WOLFSSL_SESSION_EXPORT */ +#endif + + +#ifdef __cplusplus + } /* extern "C" */ +#endif + +#endif /* WOLFSSL_IO_H */ diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index 308ea9f90..6e8bd8068 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -81,10 +81,13 @@ typedef struct WOLFSSL_X509_CHAIN WOLFSSL_X509_CHAIN; typedef struct WOLFSSL_CERT_MANAGER WOLFSSL_CERT_MANAGER; typedef struct WOLFSSL_SOCKADDR WOLFSSL_SOCKADDR; +typedef struct WOLFSSL_CRL WOLFSSL_CRL; /* redeclare guard */ #define WOLFSSL_TYPES_DEFINED +#include + #ifndef WOLFSSL_RSA_TYPE_DEFINED /* guard on redeclaration */ typedef struct WOLFSSL_RSA WOLFSSL_RSA; @@ -1295,9 +1298,6 @@ WOLFSSL_API int wolfSSL_make_eap_keys(WOLFSSL*, void* key, unsigned int len, WOLFSSL_API int wolfSSL_CTX_set_group_messages(WOLFSSL_CTX*); WOLFSSL_API int wolfSSL_set_group_messages(WOLFSSL*); -/* I/O callbacks */ -typedef int (*CallbackIORecv)(WOLFSSL *ssl, char *buf, int sz, void *ctx); -typedef int (*CallbackIOSend)(WOLFSSL *ssl, char *buf, int sz, void *ctx); #ifdef HAVE_FUZZER enum fuzzer_type { @@ -1314,64 +1314,7 @@ typedef int (*CallbackFuzzer)(WOLFSSL* ssl, const unsigned char* buf, int sz, WOLFSSL_API void wolfSSL_SetFuzzerCb(WOLFSSL* ssl, CallbackFuzzer cbf, void* fCtx); #endif -WOLFSSL_API void wolfSSL_SetIORecv(WOLFSSL_CTX*, CallbackIORecv); -WOLFSSL_API void wolfSSL_SetIOSend(WOLFSSL_CTX*, CallbackIOSend); -WOLFSSL_API void wolfSSL_SetIOReadCtx( WOLFSSL* ssl, void *ctx); -WOLFSSL_API void wolfSSL_SetIOWriteCtx(WOLFSSL* ssl, void *ctx); - -WOLFSSL_API void* wolfSSL_GetIOReadCtx( WOLFSSL* ssl); -WOLFSSL_API void* wolfSSL_GetIOWriteCtx(WOLFSSL* ssl); - -WOLFSSL_API void wolfSSL_SetIOReadFlags( WOLFSSL* ssl, int flags); -WOLFSSL_API void wolfSSL_SetIOWriteFlags(WOLFSSL* ssl, int flags); - -#ifndef WOLFSSL_USER_IO - /* default IO callbacks */ - WOLFSSL_API int EmbedReceive(WOLFSSL* ssl, char* buf, int sz, void* ctx); - WOLFSSL_API int EmbedSend(WOLFSSL* ssl, char* buf, int sz, void* ctx); - - #ifdef HAVE_OCSP - WOLFSSL_API int EmbedOcspLookup(void*, const char*, int, unsigned char*, - int, unsigned char**); - WOLFSSL_API void EmbedOcspRespFree(void*, unsigned char*); - #endif - - #ifdef WOLFSSL_DTLS - WOLFSSL_API int EmbedReceiveFrom(WOLFSSL* ssl, char* buf, int sz, void*); - WOLFSSL_API int EmbedSendTo(WOLFSSL* ssl, char* buf, int sz, void* ctx); - WOLFSSL_API int EmbedGenerateCookie(WOLFSSL* ssl, unsigned char* buf, - int sz, void*); - #ifdef WOLFSSL_SESSION_EXPORT - WOLFSSL_API int EmbedGetPeer(WOLFSSL* ssl, char* ip, int* ipSz, - unsigned short* port, int* fam); - WOLFSSL_API int EmbedSetPeer(WOLFSSL* ssl, char* ip, int ipSz, - unsigned short port, int fam); - - typedef int (*CallbackGetPeer)(WOLFSSL* ssl, char* ip, int* ipSz, - unsigned short* port, int* fam); - typedef int (*CallbackSetPeer)(WOLFSSL* ssl, char* ip, int ipSz, - unsigned short port, int fam); - - WOLFSSL_API void wolfSSL_CTX_SetIOGetPeer(WOLFSSL_CTX*, - CallbackGetPeer); - WOLFSSL_API void wolfSSL_CTX_SetIOSetPeer(WOLFSSL_CTX*, - CallbackSetPeer); - #endif /* WOLFSSL_SESSION_EXPORT */ - #endif /* WOLFSSL_DTLS */ -#endif /* WOLFSSL_USER_IO */ - - -#ifdef HAVE_NETX - WOLFSSL_API void wolfSSL_SetIO_NetX(WOLFSSL* ssl, NX_TCP_SOCKET* nxsocket, - ULONG waitoption); -#endif - -typedef int (*CallbackGenCookie)(WOLFSSL* ssl, unsigned char* buf, int sz, - void* ctx); -WOLFSSL_API void wolfSSL_CTX_SetGenCookie(WOLFSSL_CTX*, CallbackGenCookie); -WOLFSSL_API void wolfSSL_SetCookieCtx(WOLFSSL* ssl, void *ctx); -WOLFSSL_API void* wolfSSL_GetCookieCtx(WOLFSSL* ssl); WOLFSSL_API int wolfSSL_DTLS_SetCookieSecret(WOLFSSL*, const unsigned char*, unsigned int); @@ -1429,6 +1372,10 @@ typedef int (*CbOCSPIO)(void*, const char*, int, unsigned char*, int, unsigned char**); typedef void (*CbOCSPRespFree)(void*,unsigned char*); +#ifdef HAVE_CRL_IO +typedef int (*CbCrlIO)(WOLFSSL_CRL* crl, const char* url, int urlSz); +#endif + /* User Atomic Record Layer CallBacks */ typedef int (*CallbackMacEncrypt)(WOLFSSL* ssl, unsigned char* macOut, const unsigned char* macIn, unsigned int macInSz, int macContent, @@ -1600,6 +1547,10 @@ WOLFSSL_API void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl); const unsigned char*, long sz, int); WOLFSSL_API int wolfSSL_CertManagerSetCRL_Cb(WOLFSSL_CERT_MANAGER*, CbMissingCRL); +#ifdef HAVE_CRL_IO + WOLFSSL_API int wolfSSL_CertManagerSetCRL_IOCb(WOLFSSL_CERT_MANAGER*, + CbCrlIO); +#endif WOLFSSL_API int wolfSSL_CertManagerCheckOCSP(WOLFSSL_CERT_MANAGER*, unsigned char*, int sz); WOLFSSL_API int wolfSSL_CertManagerEnableOCSP(WOLFSSL_CERT_MANAGER*, @@ -1619,6 +1570,9 @@ WOLFSSL_API void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl); WOLFSSL_API int wolfSSL_LoadCRLBuffer(WOLFSSL*, const unsigned char*, long sz, int); WOLFSSL_API int wolfSSL_SetCRL_Cb(WOLFSSL*, CbMissingCRL); +#ifdef HAVE_CRL_IO + WOLFSSL_API int wolfSSL_SetCRL_IOCb(WOLFSSL* ssl, CbCrlIO cb); +#endif WOLFSSL_API int wolfSSL_EnableOCSP(WOLFSSL*, int options); WOLFSSL_API int wolfSSL_DisableOCSP(WOLFSSL*); WOLFSSL_API int wolfSSL_SetOCSP_OverrideURL(WOLFSSL*, const char*); @@ -1630,6 +1584,9 @@ WOLFSSL_API void* wolfSSL_GetRsaDecCtx(WOLFSSL* ssl); WOLFSSL_API int wolfSSL_CTX_LoadCRLBuffer(WOLFSSL_CTX*, const unsigned char*, long sz, int); WOLFSSL_API int wolfSSL_CTX_SetCRL_Cb(WOLFSSL_CTX*, CbMissingCRL); +#ifdef HAVE_CRL_IO + WOLFSSL_API int wolfSSL_CTX_SetCRL_IOCb(WOLFSSL_CTX*, CbCrlIO); +#endif WOLFSSL_API int wolfSSL_CTX_EnableOCSP(WOLFSSL_CTX*, int options); WOLFSSL_API int wolfSSL_CTX_DisableOCSP(WOLFSSL_CTX*); WOLFSSL_API int wolfSSL_CTX_SetOCSP_OverrideURL(WOLFSSL_CTX*, const char*); From d3a07858c09a64279292a8eea64e7ff7927aa30d Mon Sep 17 00:00:00 2001 From: David Garske Date: Fri, 10 Mar 2017 09:23:28 -0800 Subject: [PATCH 55/68] =?UTF-8?q?Fixes=20based=20on=20peer=20review=20feed?= =?UTF-8?q?back.=20Fix=20to=20only=20include=20the=20non-blocking=20/=20se?= =?UTF-8?q?lect=20timeout=20functions=20when=20HAVE=5FIO=5FTIMEOUT=20is=20?= =?UTF-8?q?defined.=20Fix=20to=20only=20include=20TCP=20connect=20if=20HAV?= =?UTF-8?q?E=5FGETADDRINFO=20or=20HAVE=5FSOCKADDR=20defined.=20Cleanup=20o?= =?UTF-8?q?f=20the=20=E2=80=9Cstruct=20sockaddr*=E2=80=9D=20to=20use=20typ?= =?UTF-8?q?edef=20with=20HAVE=5FSOCKADDR.=20Moved=20helpful=20XINET=5F*=20?= =?UTF-8?q?and=20XHTONS/XNTOHS=20macros=20to=20io.h.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/io.c | 207 ++++++++++++++++++++++--------------------------- wolfssl/io.h | 43 +++++++++- wolfssl/test.h | 14 ++-- 3 files changed, 141 insertions(+), 123 deletions(-) diff --git a/src/io.c b/src/io.c index 692d25d49..24f874878 100644 --- a/src/io.c +++ b/src/io.c @@ -239,7 +239,7 @@ int EmbedReceiveFrom(WOLFSSL *ssl, char *buf, int sz, void *ctx) int err; int sd = dtlsCtx->rfd; int dtls_timeout = wolfSSL_dtls_get_current_timeout(ssl); - struct sockaddr_storage peer; + SOCKADDR_S peer; XSOCKLENT peerSz = sizeof(peer); WOLFSSL_ENTER("EmbedReceiveFrom()"); @@ -262,7 +262,7 @@ int EmbedReceiveFrom(WOLFSSL *ssl, char *buf, int sz, void *ctx) } recvd = (int)RECVFROM_FUNCTION(sd, buf, sz, ssl->rflags, - (struct sockaddr*)&peer, &peerSz); + (SOCKADDR*)&peer, &peerSz); recvd = TranslateReturnCode(recvd, sd); @@ -324,7 +324,7 @@ int EmbedSendTo(WOLFSSL* ssl, char *buf, int sz, void *ctx) WOLFSSL_ENTER("EmbedSendTo()"); sent = (int)SENDTO_FUNCTION(sd, &buf[sz - len], len, ssl->wflags, - (const struct sockaddr*)dtlsCtx->peer.sa, + (const SOCKADDR*)dtlsCtx->peer.sa, dtlsCtx->peer.sz); sent = TranslateReturnCode(sent, sd); @@ -365,7 +365,7 @@ int EmbedSendTo(WOLFSSL* ssl, char *buf, int sz, void *ctx) int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) { int sd = ssl->wfd; - struct sockaddr_storage peer; + SOCKADDR_S peer; XSOCKLENT peerSz = sizeof(peer); byte digest[SHA_DIGEST_SIZE]; int ret = 0; @@ -373,7 +373,7 @@ int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) (void)ctx; XMEMSET(&peer, 0, sizeof(peer)); - if (getpeername(sd, (struct sockaddr*)&peer, &peerSz) != 0) { + if (getpeername(sd, (SOCKADDR*)&peer, &peerSz) != 0) { WOLFSSL_MSG("getpeername failed in EmbedGenerateCookie"); return GEN_COOKIE_E; } @@ -390,29 +390,6 @@ int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) } #ifdef WOLFSSL_SESSION_EXPORT - #ifndef XINET_NTOP - #define XINET_NTOP(a,b,c,d) inet_ntop((a),(b),(c),(d)) - #endif - #ifndef XINET_PTON - #define XINET_PTON(a,b,c) inet_pton((a),(b),(c)) - #endif - #ifndef XHTONS - #define XHTONS(a) htons((a)) - #endif - #ifndef XNTOHS - #define XNTOHS(a) ntohs((a)) - #endif - - #ifndef WOLFSSL_IP4 - #define WOLFSSL_IP4 AF_INET - #endif - #ifndef WOLFSSL_IP6 - #define WOLFSSL_IP6 AF_INET6 - #endif - - typedef struct sockaddr_storage SOCKADDR_S; - typedef struct sockaddr_in SOCKADDR_IN; - typedef struct sockaddr_in6 SOCKADDR_IN6; /* get the peer information in human readable form (ip, port, family) * default function assumes BSD sockets @@ -532,79 +509,75 @@ int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) #if defined(USE_WOLFSSL_IO) -#ifndef DEFAULT_TIMEOUT_SEC - #define DEFAULT_TIMEOUT_SEC 0 /* no timeout */ -#endif - -#ifdef HAVE_IO_TIMEOUT - static int io_timeout_sec = DEFAULT_TIMEOUT_SEC; +#ifndef HAVE_IO_TIMEOUT + #define io_timeout_sec 0 #else - #define io_timeout_sec DEFAULT_TIMEOUT_SEC -#endif - -void wolfIO_SetTimeout(int to_sec) -{ -#ifdef HAVE_IO_TIMEOUT - io_timeout_sec = to_sec; -#else - (void)to_sec; -#endif -} - -int wolfIO_SetBlockingMode(SOCKET_T sockfd, int non_blocking) -{ - int ret = 0; - -#ifdef USE_WINDOWS_API - unsigned long blocking = non_blocking; - ret = ioctlsocket(sockfd, FIONBIO, &blocking); - if (ret == SOCKET_ERROR) - ret = -1; -#else - ret = fcntl(sockfd, F_GETFL, 0); - if (ret >= 0) { - if (non_blocking) - ret |= O_NONBLOCK; - else - ret &= ~O_NONBLOCK; - ret = fcntl(sockfd, F_SETFL, ret); - } -#endif - if (ret < 0) { - WOLFSSL_MSG("wolfIO_SetBlockingMode failed"); - } - - return ret; -} - -#ifdef _MSC_VER - /* 4204: non-constant aggregate initializer (nfds = sockfd + 1) */ - #pragma warning(disable: 4204) -#endif -int wolfIO_Select(SOCKET_T sockfd, int to_sec) -{ - fd_set fds; - SOCKET_T nfds = sockfd + 1; - struct timeval timeout = { (to_sec > 0) ? to_sec : 0, 0}; - int ret; - - FD_ZERO(&fds); - FD_SET(sockfd, &fds); - - ret = select(nfds, &fds, &fds, NULL, &timeout); - if (ret == 0) { - #ifdef DEBUG_HTTP - printf("Timeout: %d\n", ret); + #ifndef DEFAULT_TIMEOUT_SEC + #define DEFAULT_TIMEOUT_SEC 0 /* no timeout */ #endif - return HTTP_TIMEOUT; + + static int io_timeout_sec = DEFAULT_TIMEOUT_SEC; + + void wolfIO_SetTimeout(int to_sec) + { + io_timeout_sec = to_sec; } - else if (ret > 0) { - if (FD_ISSET(sockfd, &fds)) - return 0; + + int wolfIO_SetBlockingMode(SOCKET_T sockfd, int non_blocking) + { + int ret = 0; + + #ifdef USE_WINDOWS_API + unsigned long blocking = non_blocking; + ret = ioctlsocket(sockfd, FIONBIO, &blocking); + if (ret == SOCKET_ERROR) + ret = -1; + #else + ret = fcntl(sockfd, F_GETFL, 0); + if (ret >= 0) { + if (non_blocking) + ret |= O_NONBLOCK; + else + ret &= ~O_NONBLOCK; + ret = fcntl(sockfd, F_SETFL, ret); + } + #endif + if (ret < 0) { + WOLFSSL_MSG("wolfIO_SetBlockingMode failed"); + } + + return ret; } - return SOCKET_ERROR_E; -} + + #ifdef _MSC_VER + /* 4204: non-constant aggregate initializer (nfds = sockfd + 1) */ + #pragma warning(disable: 4204) + #endif + int wolfIO_Select(SOCKET_T sockfd, int to_sec) + { + fd_set fds; + SOCKET_T nfds = sockfd + 1; + struct timeval timeout = { (to_sec > 0) ? to_sec : 0, 0}; + int ret; + + FD_ZERO(&fds); + FD_SET(sockfd, &fds); + + ret = select(nfds, &fds, &fds, NULL, &timeout); + if (ret == 0) { + #ifdef DEBUG_HTTP + printf("Timeout: %d\n", ret); + #endif + return HTTP_TIMEOUT; + } + else if (ret > 0) { + if (FD_ISSET(sockfd, &fds)) + return 0; + } + return SOCKET_ERROR_E; + } +#endif /* HAVE_IO_TIMEOUT */ static int wolfIO_Word16ToString(char* d, word16 number) { @@ -635,9 +608,19 @@ static int wolfIO_Word16ToString(char* d, word16 number) int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) { +#if defined(HAVE_GETADDRINFO) || defined(HAVE_SOCKADDR) int ret = 0; - struct sockaddr_storage addr; - int sockaddr_len = sizeof(struct sockaddr_in); + SOCKADDR_S addr; + int sockaddr_len = sizeof(SOCKADDR_IN); +#ifdef HAVE_GETADDRINFO + ADDRINFO hints; + ADDRINFO* answer = NULL; + char strPort[6]; +#else + HOSTENT* entry; + SOCKADDR_IN *sin; +#endif + XMEMSET(&addr, 0, sizeof(addr)); #ifdef WOLFIO_DEBUG @@ -645,11 +628,6 @@ int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) #endif #ifdef HAVE_GETADDRINFO -{ - struct addrinfo hints; - struct addrinfo* answer = NULL; - char strPort[6]; - XMEMSET(&hints, 0, sizeof(hints)); hints.ai_family = AF_UNSPEC; hints.ai_socktype = SOCK_STREAM; @@ -668,16 +646,13 @@ int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) sockaddr_len = answer->ai_addrlen; XMEMCPY(&addr, answer->ai_addr, sockaddr_len); freeaddrinfo(answer); - -} -#else /* HAVE_GETADDRINFO */ -{ - struct hostent* entry = gethostbyname(ip); - struct sockaddr_in *sin = (struct sockaddr_in *)&addr; +#else + entry = gethostbyname(ip); + sin = (SOCKADDR_IN *)&addr; if (entry) { sin->sin_family = AF_INET; - sin->sin_port = htons(port); + sin->sin_port = XHTONS(port); XMEMCPY(&sin->sin_addr.s_addr, entry->h_addr_list[0], entry->h_length); } @@ -686,7 +661,7 @@ int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) return -1; } } -#endif /* HAVE_GETADDRINFO */ +#endif *sockfd = (SOCKET_T)socket(addr.ss_family, SOCK_STREAM, 0); @@ -711,7 +686,7 @@ int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) (void)to_sec; #endif - ret = connect(*sockfd, (struct sockaddr *)&addr, sockaddr_len); + ret = connect(*sockfd, (SOCKADDR *)&addr, sockaddr_len); #ifdef HAVE_IO_TIMEOUT if (ret != 0) { if ((errno == EINPROGRESS) && (to_sec > 0)) { @@ -727,8 +702,14 @@ int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) WOLFSSL_MSG("Responder tcp connect failed"); return -1; } - return ret; +#else + (void)sockfd; + (void)ip; + (void)port; + (void)to_sec; + return -1; +#endif /* HAVE_GETADDRINFO || HAVE_SOCKADDR */ } int wolfIO_Recv(SOCKET_T sd, char *buf, int sz, int rdFlags) diff --git a/wolfssl/io.h b/wolfssl/io.h index 77a483d78..2d933ed7f 100644 --- a/wolfssl/io.h +++ b/wolfssl/io.h @@ -224,6 +224,7 @@ #else #define SEND_FUNCTION send #define RECV_FUNCTION recv + #define HAVE_SOCKADDR #endif #ifdef USE_WINDOWS_API @@ -232,10 +233,46 @@ typedef int SOCKET_T; #endif +/* Socket Addr Support */ +#ifdef HAVE_SOCKADDR + typedef struct sockaddr SOCKADDR; + typedef struct sockaddr_storage SOCKADDR_S; + typedef struct sockaddr_in SOCKADDR_IN; + typedef struct sockaddr_in6 SOCKADDR_IN6; + typedef struct hostent HOSTENT; +#endif /* HAVE_SOCKADDR */ + +#ifdef HAVE_GETADDRINFO + typedef struct addrinfo ADDRINFO; +#endif + +#ifndef XINET_NTOP + #define XINET_NTOP(a,b,c,d) inet_ntop((a),(b),(c),(d)) +#endif +#ifndef XINET_PTON + #define XINET_PTON(a,b,c) inet_pton((a),(b),(c)) +#endif +#ifndef XHTONS + #define XHTONS(a) htons((a)) +#endif +#ifndef XNTOHS + #define XNTOHS(a) ntohs((a)) +#endif + +#ifndef WOLFSSL_IP4 + #define WOLFSSL_IP4 AF_INET +#endif +#ifndef WOLFSSL_IP6 + #define WOLFSSL_IP6 AF_INET6 +#endif + + /* IO API's */ -WOLFSSL_API int wolfIO_SetBlockingMode(SOCKET_T sockfd, int non_blocking); -WOLFSSL_API void wolfIO_SetTimeout(int to_sec);; -WOLFSSL_API int wolfIO_Select(SOCKET_T sockfd, int to_sec); +#ifdef HAVE_IO_TIMEOUT + WOLFSSL_API int wolfIO_SetBlockingMode(SOCKET_T sockfd, int non_blocking); + WOLFSSL_API void wolfIO_SetTimeout(int to_sec);; + WOLFSSL_API int wolfIO_Select(SOCKET_T sockfd, int to_sec); +#endif WOLFSSL_API int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, unsigned short port, int to_sec); WOLFSSL_API int wolfIO_Send(SOCKET_T sd, char *buf, int sz, int wrFlags); diff --git a/wolfssl/test.h b/wolfssl/test.h index 2688d1993..d47300a3d 100644 --- a/wolfssl/test.h +++ b/wolfssl/test.h @@ -624,7 +624,7 @@ static INLINE void build_addr(SOCKADDR_IN_T* addr, const char* peer, #else addr->sin_family = AF_INET_V; #endif - addr->sin_port = htons(port); + addr->sin_port = XHTONS(port); if (peer == INADDR_ANY) addr->sin_addr.s_addr = INADDR_ANY; else { @@ -633,7 +633,7 @@ static INLINE void build_addr(SOCKADDR_IN_T* addr, const char* peer, } #else addr->sin6_family = AF_INET_V; - addr->sin6_port = htons(port); + addr->sin6_port = XHTONS(port); if (peer == INADDR_ANY) addr->sin6_addr = in6addr_any; else { @@ -824,9 +824,9 @@ static INLINE void tcp_listen(SOCKET_T* sockfd, word16* port, int useAnyAddr, socklen_t len = sizeof(addr); if (getsockname(*sockfd, (struct sockaddr*)&addr, &len) == 0) { #ifndef TEST_IPV6 - *port = ntohs(addr.sin_port); + *port = XNTOHS(addr.sin_port); #else - *port = ntohs(addr.sin6_port); + *port = XNTOHS(addr.sin6_port); #endif } } @@ -885,9 +885,9 @@ static INLINE void udp_accept(SOCKET_T* sockfd, SOCKET_T* clientfd, socklen_t len = sizeof(addr); if (getsockname(*sockfd, (struct sockaddr*)&addr, &len) == 0) { #ifndef TEST_IPV6 - port = ntohs(addr.sin_port); + port = XNTOHS(addr.sin_port); #else - port = ntohs(addr.sin6_port); + port = XNTOHS(addr.sin6_port); #endif } } @@ -2028,7 +2028,7 @@ static INLINE const char* mymktemp(char *tempfn, int len, int num) (void)userCtx; int ret; - word16 sLen = htons(inLen); + word16 sLen = XHTONS(inLen); byte aad[WOLFSSL_TICKET_NAME_SZ + WOLFSSL_TICKET_IV_SZ + 2]; int aadSz = WOLFSSL_TICKET_NAME_SZ + WOLFSSL_TICKET_IV_SZ + 2; byte* tmp = aad; From cf73a2244f8cd709eca16290026160a422ff0a91 Mon Sep 17 00:00:00 2001 From: David Garske Date: Fri, 10 Mar 2017 10:21:22 -0800 Subject: [PATCH 56/68] Fix for stray brace in wolfIO_TcpConnect. Fix to typedef sockaddr_in6 only when TEST_IPV6 is defined. Moved XSOCKLENT into io.h. Added useful WOLFSSL_NO_SOCK, which can be used with WOLFSSL_USER_IO. --- src/io.c | 14 ++------- wolfssl/io.h | 80 +++++++++++++++++++++++++++++++--------------------- 2 files changed, 51 insertions(+), 43 deletions(-) diff --git a/src/io.c b/src/io.c index 24f874878..1f2d32853 100644 --- a/src/io.c +++ b/src/io.c @@ -219,12 +219,6 @@ int EmbedSend(WOLFSSL* ssl, char *buf, int sz, void *ctx) #include -#ifdef USE_WINDOWS_API - #define XSOCKLENT int -#else - #define XSOCKLENT socklen_t -#endif - #define SENDTO_FUNCTION sendto #define RECVFROM_FUNCTION recvfrom @@ -608,7 +602,7 @@ static int wolfIO_Word16ToString(char* d, word16 number) int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) { -#if defined(HAVE_GETADDRINFO) || defined(HAVE_SOCKADDR) +#ifdef HAVE_SOCKADDR int ret = 0; SOCKADDR_S addr; int sockaddr_len = sizeof(SOCKADDR_IN); @@ -653,14 +647,12 @@ int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) if (entry) { sin->sin_family = AF_INET; sin->sin_port = XHTONS(port); - XMEMCPY(&sin->sin_addr.s_addr, entry->h_addr_list[0], - entry->h_length); + XMEMCPY(&sin->sin_addr.s_addr, entry->h_addr_list[0], entry->h_length); } else { WOLFSSL_MSG("no addr info for responder"); return -1; } -} #endif *sockfd = (SOCKET_T)socket(addr.ss_family, SOCK_STREAM, 0); @@ -709,7 +701,7 @@ int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) (void)port; (void)to_sec; return -1; -#endif /* HAVE_GETADDRINFO || HAVE_SOCKADDR */ +#endif /* HAVE_SOCKADDR */ } int wolfIO_Recv(SOCKET_T sd, char *buf, int sz, int rdFlags) diff --git a/wolfssl/io.h b/wolfssl/io.h index 2d933ed7f..5d715e5ed 100644 --- a/wolfssl/io.h +++ b/wolfssl/io.h @@ -90,7 +90,7 @@ #include #include #include - #else + #elif !defined(WOLFSSL_NO_SOCK) #include #include #ifndef EBSNET @@ -224,7 +224,9 @@ #else #define SEND_FUNCTION send #define RECV_FUNCTION recv - #define HAVE_SOCKADDR + #if !defined(HAVE_SOCKADDR) && !defined(WOLFSSL_NO_SOCK) + #define HAVE_SOCKADDR + #endif #endif #ifdef USE_WINDOWS_API @@ -233,38 +235,30 @@ typedef int SOCKET_T; #endif -/* Socket Addr Support */ -#ifdef HAVE_SOCKADDR - typedef struct sockaddr SOCKADDR; - typedef struct sockaddr_storage SOCKADDR_S; - typedef struct sockaddr_in SOCKADDR_IN; - typedef struct sockaddr_in6 SOCKADDR_IN6; - typedef struct hostent HOSTENT; -#endif /* HAVE_SOCKADDR */ +#ifndef WOLFSSL_NO_SOCK + #ifndef XSOCKLENT + #ifdef USE_WINDOWS_API + #define XSOCKLENT int + #else + #define XSOCKLENT socklen_t + #endif + #endif -#ifdef HAVE_GETADDRINFO - typedef struct addrinfo ADDRINFO; -#endif + /* Socket Addr Support */ + #ifdef HAVE_SOCKADDR + typedef struct sockaddr SOCKADDR; + typedef struct sockaddr_storage SOCKADDR_S; + typedef struct sockaddr_in SOCKADDR_IN; + #ifdef TEST_IPV6 + typedef struct sockaddr_in6 SOCKADDR_IN6; + #endif + typedef struct hostent HOSTENT; + #endif /* HAVE_SOCKADDR */ -#ifndef XINET_NTOP - #define XINET_NTOP(a,b,c,d) inet_ntop((a),(b),(c),(d)) -#endif -#ifndef XINET_PTON - #define XINET_PTON(a,b,c) inet_pton((a),(b),(c)) -#endif -#ifndef XHTONS - #define XHTONS(a) htons((a)) -#endif -#ifndef XNTOHS - #define XNTOHS(a) ntohs((a)) -#endif - -#ifndef WOLFSSL_IP4 - #define WOLFSSL_IP4 AF_INET -#endif -#ifndef WOLFSSL_IP6 - #define WOLFSSL_IP6 AF_INET6 -#endif + #ifdef HAVE_GETADDRINFO + typedef struct addrinfo ADDRINFO; + #endif +#endif /* WOLFSSL_NO_SOCK */ /* IO API's */ @@ -379,6 +373,28 @@ WOLFSSL_API void wolfSSL_SetIOWriteFlags(WOLFSSL* ssl, int flags); #endif + +#ifndef XINET_NTOP + #define XINET_NTOP(a,b,c,d) inet_ntop((a),(b),(c),(d)) +#endif +#ifndef XINET_PTON + #define XINET_PTON(a,b,c) inet_pton((a),(b),(c)) +#endif +#ifndef XHTONS + #define XHTONS(a) htons((a)) +#endif +#ifndef XNTOHS + #define XNTOHS(a) ntohs((a)) +#endif + +#ifndef WOLFSSL_IP4 + #define WOLFSSL_IP4 AF_INET +#endif +#ifndef WOLFSSL_IP6 + #define WOLFSSL_IP6 AF_INET6 +#endif + + #ifdef __cplusplus } /* extern "C" */ #endif From 4eb76e1d71f8a9adb4dba103a6eeec7230987bde Mon Sep 17 00:00:00 2001 From: David Garske Date: Wed, 15 Mar 2017 11:25:24 -0700 Subject: [PATCH 57/68] Fixes for building with IPV6. Added new WOLFSSL_IPV6 define to indicate IPV6 support. Fix to not include connect() and socket() calls unless HAVE_HTTP_CLIENT, HAVE_OCSP or HAVE_CRL_IO defined. Typo fixes. --- configure.ac | 4 +-- src/io.c | 55 ++++++++++++++++++------------------ wolfssl/io.h | 2 +- wolfssl/wolfcrypt/settings.h | 5 ++++ 4 files changed, 36 insertions(+), 30 deletions(-) diff --git a/configure.ac b/configure.ac index 9c9965eed..bdd9660c8 100644 --- a/configure.ac +++ b/configure.ac @@ -326,7 +326,7 @@ AC_ARG_ENABLE([ipv6], if test "$ENABLED_IPV6" = "yes" then - AM_CFLAGS="$AM_CFLAGS -DTEST_IPV6" + AM_CFLAGS="$AM_CFLAGS -DTEST_IPV6 -DWOLFSSL_IPV6" fi AM_CONDITIONAL([BUILD_IPV6], [test "x$ENABLED_IPV6" = "xyes"]) @@ -3340,7 +3340,7 @@ echo "#endif /* WOLFSSL_OPTIONS_H */" >> $OPTION_FILE echo "" >> $OPTION_FILE echo -#backwards compatability for those who have included options or version +#backwards compatibility for those who have included options or version touch cyassl/options.h echo "/* cyassl options.h" > cyassl/options.h echo " * generated from wolfssl/options.h" >> cyassl/options.h diff --git a/src/io.c b/src/io.c index 1f2d32853..38bc69e30 100644 --- a/src/io.c +++ b/src/io.c @@ -50,6 +50,7 @@ Possible IO enable options: * USE_WOLFSSL_IO: Enables the wolfSSL IO functions default: off * HAVE_HTTP_CLIENT: Enables HTTP client API's default: off (unless HAVE_OCSP or HAVE_CRL_IO defined) + * HAVE_IO_TIMEOUT: Enables support for connect timeout default: off */ @@ -421,12 +422,14 @@ int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) break; case WOLFSSL_IP6: + #ifdef WOLFSSL_IPV6 if (XINET_NTOP(*fam, &(((SOCKADDR_IN6*)&peer)->sin6_addr), ip, *ipSz) == NULL) { WOLFSSL_MSG("XINET_NTOP error"); return SOCKET_ERROR_E; } *port = XNTOHS(((SOCKADDR_IN6*)&peer)->sin6_port); + #endif /* WOLFSSL_IPV6 */ break; default: @@ -473,6 +476,7 @@ int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) break; case WOLFSSL_IP6: + #ifdef WOLFSSL_IPV6 if (XINET_PTON(addr.ss_family, ip, &(((SOCKADDR_IN6*)&addr)->sin6_addr)) <= 0) { WOLFSSL_MSG("XINET_PTON error"); @@ -486,6 +490,7 @@ int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) WOLFSSL_MSG("Import DTLS peer info error"); return ret; } + #endif /* WOLFSSL_IPV6 */ break; default: @@ -498,10 +503,32 @@ int EmbedGenerateCookie(WOLFSSL* ssl, byte *buf, int sz, void *ctx) #endif /* WOLFSSL_SESSION_EXPORT */ #endif /* WOLFSSL_DTLS */ + +int wolfIO_Recv(SOCKET_T sd, char *buf, int sz, int rdFlags) +{ + int recvd; + + recvd = (int)RECV_FUNCTION(sd, buf, sz, rdFlags); + recvd = TranslateReturnCode(recvd, sd); + + return recvd; +} + +int wolfIO_Send(SOCKET_T sd, char *buf, int sz, int wrFlags) +{ + int sent; + int len = sz; + + sent = (int)SEND_FUNCTION(sd, &buf[sz - len], len, wrFlags); + sent = TranslateReturnCode(sent, sd); + + return sent; +} + #endif /* USE_WOLFSSL_IO */ -#if defined(USE_WOLFSSL_IO) +#ifdef HAVE_HTTP_CLIENT #ifndef HAVE_IO_TIMEOUT #define io_timeout_sec 0 @@ -704,32 +731,6 @@ int wolfIO_TcpConnect(SOCKET_T* sockfd, const char* ip, word16 port, int to_sec) #endif /* HAVE_SOCKADDR */ } -int wolfIO_Recv(SOCKET_T sd, char *buf, int sz, int rdFlags) -{ - int recvd; - - recvd = (int)RECV_FUNCTION(sd, buf, sz, rdFlags); - recvd = TranslateReturnCode(recvd, sd); - - return recvd; -} - -int wolfIO_Send(SOCKET_T sd, char *buf, int sz, int wrFlags) -{ - int sent; - int len = sz; - - sent = (int)SEND_FUNCTION(sd, &buf[sz - len], len, wrFlags); - sent = TranslateReturnCode(sent, sd); - - return sent; -} - -#endif /* USE_WOLFSSL_IO */ - - -#if defined(HAVE_HTTP_CLIENT) - #ifndef HTTP_SCRATCH_BUFFER_SIZE #define HTTP_SCRATCH_BUFFER_SIZE 512 #endif diff --git a/wolfssl/io.h b/wolfssl/io.h index 5d715e5ed..c036a8327 100644 --- a/wolfssl/io.h +++ b/wolfssl/io.h @@ -249,7 +249,7 @@ typedef struct sockaddr SOCKADDR; typedef struct sockaddr_storage SOCKADDR_S; typedef struct sockaddr_in SOCKADDR_IN; - #ifdef TEST_IPV6 + #ifdef WOLFSSL_IPV6 typedef struct sockaddr_in6 SOCKADDR_IN6; #endif typedef struct hostent HOSTENT; diff --git a/wolfssl/wolfcrypt/settings.h b/wolfssl/wolfcrypt/settings.h index b1387b3de..4cf535103 100644 --- a/wolfssl/wolfcrypt/settings.h +++ b/wolfssl/wolfcrypt/settings.h @@ -1497,6 +1497,11 @@ static char *fgets(char *buff, int sz, FILE *fp) #error old TLS requires MD5 and SHA #endif +/* for backwards compatibility */ +#if defined(TEST_IPV6) && !defined(WOLFSSL_IPV6) + #define WOLFSSL_IPV6 +#endif + /* Place any other flags or defines here */ From 2c890e6827799f13664177de295f2f2123d02aef Mon Sep 17 00:00:00 2001 From: David Garske Date: Wed, 15 Mar 2017 12:34:55 -0700 Subject: [PATCH 58/68] Fix mp_set_int to use calc for 32 const. Changed it to sizeof(b) instead of sizeof(long). --- wolfcrypt/src/integer.c | 5 +++-- wolfcrypt/src/tfm.c | 5 +++-- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index ddaad3f59..a6f1a5793 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -3918,14 +3918,15 @@ int mp_set_int (mp_int * a, unsigned long b) mp_zero (a); /* set chunk bits at a time */ - for (x = 0; x < (int)(sizeof(long) * 8) / MP_SET_CHUNK_BITS; x++) { + for (x = 0; x < (int)(sizeof(b) * 8) / MP_SET_CHUNK_BITS; x++) { /* shift the number up chunk bits */ if ((res = mp_mul_2d (a, MP_SET_CHUNK_BITS, a)) != MP_OKAY) { return res; } /* OR in the top bits of the source */ - a->dp[0] |= (b >> (32 - MP_SET_CHUNK_BITS)) & ((1 << MP_SET_CHUNK_BITS) - 1); + a->dp[0] |= (b >> ((sizeof(b) * 8) - MP_SET_CHUNK_BITS)) & + ((1 << MP_SET_CHUNK_BITS) - 1); /* shift the source up to the next chunk bits */ b <<= MP_SET_CHUNK_BITS; diff --git a/wolfcrypt/src/tfm.c b/wolfcrypt/src/tfm.c index 68738b36b..c857ec795 100644 --- a/wolfcrypt/src/tfm.c +++ b/wolfcrypt/src/tfm.c @@ -1980,11 +1980,12 @@ void fp_set_int(fp_int *a, unsigned long b) fp_zero (a); /* set chunk bits at a time */ - for (x = 0; x < (int)(sizeof(long) * 8) / MP_SET_CHUNK_BITS; x++) { + for (x = 0; x < (int)(sizeof(b) * 8) / MP_SET_CHUNK_BITS; x++) { fp_mul_2d (a, MP_SET_CHUNK_BITS, a); /* OR in the top bits of the source */ - a->dp[0] |= (b >> (32 - MP_SET_CHUNK_BITS)) & ((1 << MP_SET_CHUNK_BITS) - 1); + a->dp[0] |= (b >> ((sizeof(b) * 8) - MP_SET_CHUNK_BITS)) & + ((1 << MP_SET_CHUNK_BITS) - 1); /* shift the source up to the next chunk bits */ b <<= MP_SET_CHUNK_BITS; From 0ef1b5d29866b8816efe6ab0080d60bd3ced30e0 Mon Sep 17 00:00:00 2001 From: Jacob Barthelmeh Date: Wed, 15 Mar 2017 13:40:41 -0600 Subject: [PATCH 59/68] bounds checking with adding string terminating character --- src/internal.c | 4 ++-- src/ssl.c | 6 ++++-- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/src/internal.c b/src/internal.c index c5e4554e5..57fdb6e40 100644 --- a/src/internal.c +++ b/src/internal.c @@ -1063,12 +1063,12 @@ static int ImportPeerInfo(WOLFSSL* ssl, byte* buf, word32 len, byte ver) /* import ip address idx, and ipSz are unsigned but cast for enum */ ato16(buf + idx, &ipSz); idx += DTLS_EXPORT_LEN; - if (ipSz > sizeof(ip) || (word16)(idx + ipSz + DTLS_EXPORT_LEN) > len) { + if (ipSz >= sizeof(ip) || (word16)(idx + ipSz + DTLS_EXPORT_LEN) > len) { return BUFFER_E; } XMEMSET(ip, 0, sizeof(ip)); XMEMCPY(ip, buf + idx, ipSz); idx += ipSz; - ip[ipSz] = '\0'; + ip[ipSz] = '\0'; /* with check that ipSz less than ip this is valid */ ato16(buf + idx, &port); idx += DTLS_EXPORT_LEN; /* sanity check for a function to call, then use it to import peer info */ diff --git a/src/ssl.c b/src/ssl.c index 9e502ea36..f4ebd6362 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -12832,8 +12832,10 @@ static void ExternalFreeX509(WOLFSSL_X509* x509) if (buf != NULL && text != NULL) { textSz = min(textSz, len); - XMEMCPY(buf, text, textSz); - buf[textSz] = '\0'; + if (textSz > 0) { + XMEMCPY(buf, text, textSz - 1); + buf[textSz - 1] = '\0'; + } } WOLFSSL_LEAVE("wolfSSL_X509_NAME_get_text_by_NID", textSz); From 36ecbfb1a81e1547df646d321a562bdf403ed35c Mon Sep 17 00:00:00 2001 From: toddouska Date: Wed, 15 Mar 2017 14:57:38 -0700 Subject: [PATCH 60/68] fix NO_ASN_TIME build with --enable-wpas --- src/crl.c | 14 +++++++++----- src/ocsp.c | 2 ++ wolfcrypt/src/asn.c | 17 +++++++++++++---- 3 files changed, 24 insertions(+), 9 deletions(-) diff --git a/src/crl.c b/src/crl.c index 09e633373..36942a973 100755 --- a/src/crl.c +++ b/src/crl.c @@ -177,13 +177,17 @@ int CheckCertCRL(WOLFSSL_CRL* crl, DecodedCert* cert) doNextDate = 0; /* skip */ #endif - if (doNextDate && !ValidateDate(crle->nextDate, - crle->nextDateFormat, AFTER)) { - WOLFSSL_MSG("CRL next date is no longer valid"); - ret = ASN_AFTER_DATE_E; + if (doNextDate) { + #ifndef NO_ASN_TIME + if (!ValidateDate(crle->nextDate,crle->nextDateFormat, AFTER)) { + WOLFSSL_MSG("CRL next date is no longer valid"); + ret = ASN_AFTER_DATE_E; + } + #endif } - else + if (ret == 0) { foundEntry = 1; + } break; } crle = crle->next; diff --git a/src/ocsp.c b/src/ocsp.c index 0af304f34..d481ab676 100644 --- a/src/ocsp.c +++ b/src/ocsp.c @@ -219,9 +219,11 @@ static int GetOcspStatus(WOLFSSL_OCSP* ocsp, OcspRequest* request, ret = OCSP_INVALID_STATUS; } else if (*status) { +#ifndef NO_ASN_TIME if (ValidateDate((*status)->thisDate, (*status)->thisDateFormat, BEFORE) && ((*status)->nextDate[0] != 0) && ValidateDate((*status)->nextDate, (*status)->nextDateFormat, AFTER)) +#endif { ret = xstat2err((*status)->status); diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 6ed0f6987..4ea6b412e 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -9510,8 +9510,11 @@ static int DecodeSingleResponse(byte* source, if (GetBasicDate(source, &idx, cs->thisDate, &cs->thisDateFormat, size) < 0) return ASN_PARSE_E; + +#ifndef NO_ASN_TIME if (!XVALIDATE_DATE(cs->thisDate, cs->thisDateFormat, BEFORE)) return ASN_BEFORE_DATE_E; +#endif /* The following items are optional. Only check for them if there is more * unprocessed data in the singleResponse wrapper. */ @@ -9528,8 +9531,11 @@ static int DecodeSingleResponse(byte* source, if (GetBasicDate(source, &idx, cs->nextDate, &cs->nextDateFormat, size) < 0) return ASN_PARSE_E; + +#ifndef NO_ASN_TIME if (!XVALIDATE_DATE(cs->nextDate, cs->nextDateFormat, AFTER)) return ASN_AFTER_DATE_E; +#endif } if (((int)(idx - prevIndex) < wrapperSz) && (source[idx] == (ASN_CONSTRUCTED | ASN_CONTEXT_SPECIFIC | 1))) @@ -10369,10 +10375,13 @@ int ParseCRL(DecodedCRL* dcrl, const byte* buff, word32 sz, void* cm) #endif } - if (doNextDate && !XVALIDATE_DATE(dcrl->nextDate, dcrl->nextDateFormat, - AFTER)) { - WOLFSSL_MSG("CRL after date is no longer valid"); - return ASN_AFTER_DATE_E; + if (doNextDate) { +#ifndef NO_ASN_TIME + if (!XVALIDATE_DATE(dcrl->nextDate, dcrl->nextDateFormat, AFTER)) { + WOLFSSL_MSG("CRL after date is no longer valid"); + return ASN_AFTER_DATE_E; + } +#endif } if (idx != dcrl->sigIndex && buff[idx] != CRL_EXTENSIONS) { From a13cce9213aa8d4628c686947e31d79654643478 Mon Sep 17 00:00:00 2001 From: Chris Conlon Date: Wed, 15 Mar 2017 15:50:54 -0600 Subject: [PATCH 61/68] allow ECC private key only import --- wolfcrypt/src/ecc.c | 34 +++++++++++++++++++++++++++++++--- wolfcrypt/test/test.c | 14 ++++++++++++++ 2 files changed, 45 insertions(+), 3 deletions(-) diff --git a/wolfcrypt/src/ecc.c b/wolfcrypt/src/ecc.c index aeba28eb7..d03e500b4 100644 --- a/wolfcrypt/src/ecc.c +++ b/wolfcrypt/src/ecc.c @@ -4790,10 +4790,38 @@ int wc_ecc_export_private_raw(ecc_key* key, byte* qx, word32* qxLen, #endif /* HAVE_ECC_KEY_EXPORT */ #ifdef HAVE_ECC_KEY_IMPORT -int wc_ecc_import_private_key_ex(const byte* priv, word32 privSz, const byte* pub, - word32 pubSz, ecc_key* key, int curve_id) +/* import private key, public part optional if (pub) passed as NULL */ +int wc_ecc_import_private_key_ex(const byte* priv, word32 privSz, + const byte* pub, word32 pubSz, ecc_key* key, + int curve_id) { - int ret = wc_ecc_import_x963_ex(pub, pubSz, key, curve_id); + int ret; + void* heap; + + /* public optional, NULL if only importing private */ + if (pub != NULL) { + + ret = wc_ecc_import_x963_ex(pub, pubSz, key, curve_id); + + } else { + + if (key == NULL || priv == NULL) + return BAD_FUNC_ARG; + + /* init key */ + heap = key->heap; + ret = wc_ecc_init_ex(key, NULL, INVALID_DEVID); + key->heap = heap; + + key->state = ECC_STATE_NONE; + + if (ret != 0) + return ret; + + /* set key size */ + ret = wc_ecc_set_curve(key, privSz-1, curve_id); + } + if (ret != 0) return ret; diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 3c87ed0a7..6c8d43a31 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -10261,6 +10261,7 @@ static int ecc_sig_test(WC_RNG* rng, ecc_key* key) static int ecc_exp_imp_test(ecc_key* key) { int ret; + int curve_id; ecc_key keyImp; byte priv[32]; word32 privLen; @@ -10302,6 +10303,19 @@ static int ecc_exp_imp_test(ecc_key* key) goto done; } + wc_ecc_free(&keyImp); + wc_ecc_init(&keyImp); + + curve_id = wc_ecc_get_curve_id(key->idx); + if (curve_id < 0) + return -1074; + + /* test import private only */ + ret = wc_ecc_import_private_key_ex(priv, privLen, NULL, 0, &keyImp, + curve_id); + if (ret != 0) + return -1075; + done: wc_ecc_free(&keyImp); return ret; From a7f8bdb387b00880dfec9d155d276ab3415ecf6b Mon Sep 17 00:00:00 2001 From: Chris Conlon Date: Wed, 15 Mar 2017 17:28:52 -0600 Subject: [PATCH 62/68] remove EccPublicKeyDecode() from WOLFSSL_CERT_EXT guard --- wolfcrypt/src/asn.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index 6ed0f6987..f9c73635f 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -9204,7 +9204,7 @@ int wc_EccPrivateKeyDecode(const byte* input, word32* inOutIdx, ecc_key* key, return ret; } -#ifdef WOLFSSL_CERT_EXT + int wc_EccPublicKeyDecode(const byte* input, word32* inOutIdx, ecc_key* key, word32 inSz) { @@ -9258,7 +9258,6 @@ int wc_EccPublicKeyDecode(const byte* input, word32* inOutIdx, return 0; } -#endif #ifdef WOLFSSL_KEY_GEN From d22dcdb78d963e3ab4bbaa32036f4a8eff659e33 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Thu, 16 Mar 2017 16:00:31 +1000 Subject: [PATCH 63/68] If there is no filesystem then still compile and run Defaults to 2048-bit FF and 256-bit EC keys. --- wolfcrypt/test/test.c | 32 ++++++++++++++++++++++++++++---- 1 file changed, 28 insertions(+), 4 deletions(-) diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 3c87ed0a7..b43e252e9 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -124,6 +124,16 @@ #endif +#if defined(NO_FILESYSTEM) + #if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) && \ + !defined(USE_CERT_BUFFERS_4096) + #define USE_CERT_BUFFERS_2048 + #endif + #if !defined(USE_CERT_BUFFERS_256) + #define USE_CERT_BUFFERS_256 + #endif +#endif + #include #if defined(WOLFSSL_MDK_ARM) @@ -5258,6 +5268,8 @@ byte GetEntropy(ENTROPY_CMD cmd, byte* out) #endif /* HAVE_NTRU */ +#ifndef NO_FILESYSTEM + /* Cert Paths */ #ifdef FREESCALE_MQX #define CERT_PREFIX "a:\\" @@ -5344,6 +5356,8 @@ byte GetEntropy(ENTROPY_CMD cmd, byte* out) #endif #endif /* !NO_RSA */ +#endif /* !NO_FILESYSTEM */ + #ifndef NO_RSA #if !defined(NO_ASN_TIME) && defined(WOLFSSL_TEST_CERT) @@ -6074,7 +6088,8 @@ int rsa_test(void) byte out[256]; byte plain[256]; byte* res; -#if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) +#if !defined(USE_CERT_BUFFERS_1024) && !defined(USE_CERT_BUFFERS_2048) \ + && !defined(NO_FILESYSTEM) FILE *file, *file2; #endif #ifdef WOLFSSL_TEST_CERT @@ -6097,7 +6112,7 @@ int rsa_test(void) #elif defined(USE_CERT_BUFFERS_2048) XMEMCPY(tmp, client_key_der_2048, sizeof_client_key_der_2048); bytes = sizeof_client_key_der_2048; -#else +#elif !defined(NO_FILESYSTEM) file = fopen(clientKey, "rb"); if (!file) { err_sys("can't open ./certs/client-key.der, " @@ -6108,6 +6123,9 @@ int rsa_test(void) bytes = fread(tmp, 1, FOURK_BUF, file); fclose(file); +#else + /* No key to use. */ + return -40; #endif /* USE_CERT_BUFFERS */ ret = wc_InitRsaKey_ex(&key, HEAP_HINT, devId); @@ -6539,7 +6557,7 @@ int rsa_test(void) #elif defined(USE_CERT_BUFFERS_2048) XMEMCPY(tmp, client_cert_der_2048, sizeof_client_cert_der_2048); bytes = sizeof_client_cert_der_2048; -#else +#elif !defined(NO_FILESYSTEM) file2 = fopen(clientCert, "rb"); if (!file2) { XFREE(tmp, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER); @@ -6549,6 +6567,9 @@ int rsa_test(void) bytes = fread(tmp, 1, FOURK_BUF, file2); fclose(file2); +#else + /* No certificate to use. */ + return -49; #endif #ifdef sizeof @@ -7902,13 +7923,16 @@ int dh_test(void) bytes = sizeof_dh_key_der_2048; #elif defined(NO_ASN) /* don't use file, no DER parsing */ -#else +#elif !defined(NO_FILESYSTEM) FILE* file = fopen(dhKey, "rb"); if (!file) return -50; bytes = (word32) fread(tmp, 1, sizeof(tmp), file); fclose(file); +#else + /* No DH key to use. */ + return -50; #endif /* USE_CERT_BUFFERS */ (void)idx; From 2b1b7632fc1bc4cc146ad7d750b74bd690faa910 Mon Sep 17 00:00:00 2001 From: toddouska Date: Thu, 16 Mar 2017 11:10:12 -0700 Subject: [PATCH 64/68] add keep option to fips-check.sh to keep FIPS temp folder around --- fips-check.sh | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/fips-check.sh b/fips-check.sh index a9c1ddb8e..d6d88375c 100755 --- a/fips-check.sh +++ b/fips-check.sh @@ -9,14 +9,17 @@ # This should check out all the approved versions. The command line # option selects the version. # -# $ ./fips-check [version] +# $ ./fips-check [version] [keep] # # - version: linux (default), ios, android, windows, freertos, linux-ecc # +# - keep: (default off) XXX-fips-test temp dir around for inspection +# function Usage() { - echo "Usage: $0 [platform]" + echo "Usage: $0 [platform] [keep]" echo "Where \"platform\" is one of linux (default), ios, android, windows, freertos, openrtos-3.9.2, linux-ecc" + echo "Where \"keep\" means keep (default off) XXX-fips-test temp dir around for inspection" } LINUX_FIPS_VERSION=v3.2.6 @@ -62,6 +65,8 @@ WC_SRC_PATH=ctaocrypt/src if [ "x$1" == "x" ]; then PLATFORM="linux"; else PLATFORM=$1; fi +if [ "x$2" == "xkeep" ]; then KEEP="yes"; else KEEP="no"; fi + case $PLATFORM in ios) FIPS_VERSION=$IOS_FIPS_VERSION @@ -172,5 +177,7 @@ fi # Clean up popd -rm -rf $TEST_DIR - +if [ "x$KEEP" == "xno" ]; +then + rm -rf $TEST_DIR +fi From efc2bb43d2f1b3595139c11df7e7bee201723186 Mon Sep 17 00:00:00 2001 From: Chris Conlon Date: Thu, 16 Mar 2017 15:09:24 -0600 Subject: [PATCH 65/68] add wc_GetPkcs8TraditionalOffset() --- certs/server-keyPkcs8.der | Bin 0 -> 1219 bytes tests/api.c | 53 ++++++++++++++++++++ wolfcrypt/src/asn.c | 87 ++++++++++++++++++++++++--------- wolfssl/wolfcrypt/asn.h | 2 + wolfssl/wolfcrypt/asn_public.h | 3 ++ 5 files changed, 122 insertions(+), 23 deletions(-) create mode 100644 certs/server-keyPkcs8.der diff --git a/certs/server-keyPkcs8.der b/certs/server-keyPkcs8.der new file mode 100644 index 0000000000000000000000000000000000000000..5a5873543466614225e07a472bd26f158d8872f1 GIT binary patch literal 1219 zcmXqLV%g8c$Y8+B#;Mij(e|B}k&%&=fu)IMr9l(RQYJ%9D$Lz} z$<sd-#mjmmRx;(TKP<_pw?p9Zu`>=^G8elUXSU}Z*)6{8^NYJ{i}zIPD{lRp z7Ra+VWb?z^c$q!Q#TPl5J4G%D>`XbVbz$K&uRRa1NJSrCaNuBa1;2~Afzh-EBju?J z%XbN1nqK@UR`p~S?_tY?C0jORIyrH^yuq=@SYdO7((+ZWk34*q*nITTwEH(N_^-Xr z#LURR2o8x^7fkqrl2`*6-_L)Wl6UCHEvZi}*Cz>hOgi#1>veZ&&aq01PbZ7K+EPNM zmY+U6Ywq?dvP&3F%=3G4_xP@Kv4bUhR$iOZuWcap`|W*2R^^*smV0Mpr_S1O=Sc0l zWzM2{w)HI;>vE=y=HB2YbBOlf?2%37_WozWB21b@Dx}>5cDwa-M~n1Zr!TdeUhcq8dIKa-O=gfcro{a zjPwubHJPW)Y*K3Pe39I7IALSBM|_Zfq*Z9W(E&;40Q+_4^2I;%&38EEw^r2pWaY~P zkru@TbGT|wT6q{Pzu{TR)q3dAU(w=QGdZ;~XU*p-+`oZkSx;3|zDHDu^|6h?;`g6} z+;DpGy>ijm?J+SmHzur{p?fWpFM0FgJIl^=XDwMI)YDh(p|i=`{0^H$?W=!f3$HAE zY0rCBI(~ipylK(V{0nQ=Z=OBjc6hPX+YQPt>m2>%*`0)yeNO-SBC_P__jzVD(eqc> z9Bhp*xn!yP|3b_C--V>JlA&X}rIa(b#L{4SOR0Ey=RNIN z_wz0*G5k}SQQ#*fsR?pJmt&Yl;Jo-N^SG^NEDrgU6Lw|Q%S_`|6`osHcyy2K_h-tq zsJZg&j?dfcVuFY57@i+iI}pfpZ+GdO{IEGypZngQ?>ee|=@wg-%gN$@c{AI8MDP1p z^DK3%f6j-KNB@hR>XsIN6k)r_d^O{q{SN1Xd-~qKe-}CTLGrVjxUYTQAFU5EH8%LV z{&eU$8vR8}s%y(9nKjujdBV)L`xQ;Q`n2oPqyHa2N(kGwaqhTLw)~__VbBx<=La7v zO8zEF`*5ClmZ4R+R_4C*p0L|Xm+UhwSQ2;M{|`gxOe /* wc_ecc_fp_free */ #endif +#ifndef NO_ASN + #include +#endif #include #include @@ -3026,6 +3029,52 @@ static void test_wolfSSL_BIO(void) } +/*----------------------------------------------------------------------------* + | wolfCrypt ASN + *----------------------------------------------------------------------------*/ + +static void test_wc_GetPkcs8TraditionalOffset(void) +{ +#if !defined(NO_ASN) && !defined(NO_FILESYSTEM) + int length, derSz; + word32 inOutIdx; + const char* path = "./certs/server-keyPkcs8.der"; + FILE* file; + byte der[2048]; + + printf(testingFmt, "wc_GetPkcs8TraditionalOffset"); + + file = fopen(path, "rb"); + AssertNotNull(file); + derSz = (int)fread(der, 1, sizeof(der), file); + fclose(file); + + /* valid case */ + inOutIdx = 0; + length = wc_GetPkcs8TraditionalOffset(der, &inOutIdx, derSz); + AssertIntGT(length, 0); + + /* inOutIdx > sz */ + inOutIdx = 4000; + length = wc_GetPkcs8TraditionalOffset(der, &inOutIdx, derSz); + AssertIntEQ(length, BAD_FUNC_ARG); + + /* null input */ + inOutIdx = 0; + length = wc_GetPkcs8TraditionalOffset(NULL, &inOutIdx, 0); + AssertIntEQ(length, BAD_FUNC_ARG); + + /* invalid input, fill buffer with 1's */ + XMEMSET(der, 1, sizeof(der)); + inOutIdx = 0; + length = wc_GetPkcs8TraditionalOffset(der, &inOutIdx, derSz); + AssertIntEQ(length, ASN_PARSE_E); + + printf(resultFmt, passed); +#endif /* NO_ASN */ +} + + /*----------------------------------------------------------------------------* | Main *----------------------------------------------------------------------------*/ @@ -3086,6 +3135,10 @@ void ApiTest(void) test_wolfSSL_BIO(); AssertIntEQ(test_wolfSSL_Cleanup(), SSL_SUCCESS); + + /* wolfCrypt ASN tests */ + test_wc_GetPkcs8TraditionalOffset(); + printf(" End API Tests\n"); } diff --git a/wolfcrypt/src/asn.c b/wolfcrypt/src/asn.c index a6e5e4935..c23cf87b9 100644 --- a/wolfcrypt/src/asn.c +++ b/wolfcrypt/src/asn.c @@ -1520,34 +1520,58 @@ int wc_RsaPrivateKeyDecode(const byte* input, word32* inOutIdx, RsaKey* key, #endif /* HAVE_USER_RSA */ #endif /* NO_RSA */ +/* Remove PKCS8 header, place inOutIdx at beginning of traditional, + * return traditional length on success, negative on error */ +int ToTraditionalInline(const byte* input, word32* inOutIdx, word32 sz) +{ + word32 idx, oid; + int version, length; + + if (input == NULL || inOutIdx == NULL) + return BAD_FUNC_ARG; + + idx = *inOutIdx; + + if (GetSequence(input, &idx, &length, sz) < 0) + return ASN_PARSE_E; + + if (GetMyVersion(input, &idx, &version, sz) < 0) + return ASN_PARSE_E; + + if (GetAlgoId(input, &idx, &oid, oidKeyType, sz) < 0) + return ASN_PARSE_E; + + if (input[idx] == ASN_OBJECT_ID) { + /* pkcs8 ecc uses slightly different format */ + idx++; /* past id */ + if (GetLength(input, &idx, &length, sz) < 0) + return ASN_PARSE_E; + idx += length; /* over sub id, key input will verify */ + } + + if (input[idx++] != ASN_OCTET_STRING) + return ASN_PARSE_E; + + if (GetLength(input, &idx, &length, sz) < 0) + return ASN_PARSE_E; + + *inOutIdx = idx; + + return length; +} + /* Remove PKCS8 header, move beginning of traditional to beginning of input */ int ToTraditional(byte* input, word32 sz) { - word32 inOutIdx = 0, oid; - int version, length; + word32 inOutIdx = 0; + int length; - if (GetSequence(input, &inOutIdx, &length, sz) < 0) - return ASN_PARSE_E; + if (input == NULL) + return BAD_FUNC_ARG; - if (GetMyVersion(input, &inOutIdx, &version, sz) < 0) - return ASN_PARSE_E; - - if (GetAlgoId(input, &inOutIdx, &oid, oidKeyType, sz) < 0) - return ASN_PARSE_E; - - if (input[inOutIdx] == ASN_OBJECT_ID) { - /* pkcs8 ecc uses slightly different format */ - inOutIdx++; /* past id */ - if (GetLength(input, &inOutIdx, &length, sz) < 0) - return ASN_PARSE_E; - inOutIdx += length; /* over sub id, key input will verify */ - } - - if (input[inOutIdx++] != ASN_OCTET_STRING) - return ASN_PARSE_E; - - if (GetLength(input, &inOutIdx, &length, sz) < 0) - return ASN_PARSE_E; + length = ToTraditionalInline(input, &inOutIdx, sz); + if (length < 0) + return length; XMEMMOVE(input, input + inOutIdx, length); @@ -1555,6 +1579,23 @@ int ToTraditional(byte* input, word32 sz) } +/* find beginning of traditional key inside PKCS#8 unencrypted buffer + * return traditional length on success, with inOutIdx at beginning of + * traditional + * return negative on failure/error */ +int wc_GetPkcs8TraditionalOffset(byte* input, word32* inOutIdx, word32 sz) +{ + int length; + + if (input == NULL || inOutIdx == NULL || (*inOutIdx > sz)) + return BAD_FUNC_ARG; + + length = ToTraditionalInline(input, inOutIdx, sz); + + return length; +} + + /* check that the private key is a pair for the public key in certificate * return 1 (true) on match * return 0 or negative value on failure/error diff --git a/wolfssl/wolfcrypt/asn.h b/wolfssl/wolfcrypt/asn.h index 23930faeb..f1419a1d2 100644 --- a/wolfssl/wolfcrypt/asn.h +++ b/wolfssl/wolfcrypt/asn.h @@ -680,6 +680,8 @@ WOLFSSL_LOCAL void FreeTrustedPeerTable(TrustedPeerCert**, int, void*); #endif /* WOLFSSL_TRUST_PEER_CERT */ WOLFSSL_ASN_API int ToTraditional(byte* buffer, word32 length); +WOLFSSL_LOCAL int ToTraditionalInline(const byte* input, word32* inOutIdx, + word32 length); WOLFSSL_LOCAL int ToTraditionalEnc(byte* buffer, word32 length,const char*,int); WOLFSSL_LOCAL int DecryptContent(byte* input, word32 sz,const char* psw,int pswSz); diff --git a/wolfssl/wolfcrypt/asn_public.h b/wolfssl/wolfcrypt/asn_public.h index 242018ad7..78c48c684 100644 --- a/wolfssl/wolfcrypt/asn_public.h +++ b/wolfssl/wolfcrypt/asn_public.h @@ -268,6 +268,9 @@ WOLFSSL_API word32 wc_EncodeSignature(byte* out, const byte* digest, word32 digSz, int hashOID); WOLFSSL_API int wc_GetCTC_HashOID(int type); +WOLFSSL_API int wc_GetPkcs8TraditionalOffset(byte* input, + word32* inOutIdx, word32 sz); + /* Time */ /* Returns seconds (Epoch/UTC) * timePtr: is "time_t", which is typically "long" From 141210dcc066997e2b7c899a7ad4b153bbd4061e Mon Sep 17 00:00:00 2001 From: David Garske Date: Thu, 16 Mar 2017 14:56:03 -0700 Subject: [PATCH 66/68] =?UTF-8?q?Fix=20warning=20with=20"implicit=20conver?= =?UTF-8?q?sion=20loses=20integer=20precision=E2=80=9D.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- wolfcrypt/src/integer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wolfcrypt/src/integer.c b/wolfcrypt/src/integer.c index a6f1a5793..63d5c0293 100644 --- a/wolfcrypt/src/integer.c +++ b/wolfcrypt/src/integer.c @@ -3912,7 +3912,7 @@ int mp_set_int (mp_int * a, unsigned long b) /* use direct mp_set if b is less than mp_digit max */ if (b < MP_DIGIT_MAX) { - return mp_set (a, b); + return mp_set (a, (mp_digit)b); } mp_zero (a); From 37a52414cca9e2e64960b6950ed4aac872c12168 Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Fri, 17 Mar 2017 10:23:37 +1000 Subject: [PATCH 67/68] Make MP and ECC APIs public These APIs are needed by wpa_supplicant. --- configure.ac | 3 +- wolfcrypt/src/ecc.c | 5 -- wolfssl/wolfcrypt/ecc.h | 11 +++ wolfssl/wolfcrypt/integer.h | 161 +++++++++++++++++++----------------- wolfssl/wolfcrypt/tfm.h | 119 +++++++++++++------------- 5 files changed, 159 insertions(+), 140 deletions(-) diff --git a/configure.ac b/configure.ac index 9c9965eed..2490f6b73 100644 --- a/configure.ac +++ b/configure.ac @@ -340,9 +340,8 @@ AC_ARG_ENABLE([wpas], ) if test "$ENABLED_WPAS" = "yes" then - enable_shared=no - enable_static=yes AM_CFLAGS="$AM_CFLAGS -DHAVE_SECRET_CALLBACK -DWOLFSSL_STATIC_RSA" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_PUBLIC_MP" AM_CFLAGS="$AM_CFLAGS -DATOMIC_USER" AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_WPAS" fi diff --git a/wolfcrypt/src/ecc.c b/wolfcrypt/src/ecc.c index d03e500b4..3405b39b5 100644 --- a/wolfcrypt/src/ecc.c +++ b/wolfcrypt/src/ecc.c @@ -953,11 +953,6 @@ static int wc_ecc_export_x963_compressed(ecc_key*, byte* out, word32* outLen); #ifndef WOLFSSL_ATECC508A -int ecc_map(ecc_point*, mp_int*, mp_digit); -int ecc_projective_add_point(ecc_point* P, ecc_point* Q, ecc_point* R, - mp_int* a, mp_int* modulus, mp_digit mp); -int ecc_projective_dbl_point(ecc_point* P, ecc_point* R, mp_int* a, - mp_int* modulus, mp_digit mp); static int ecc_check_pubkey_order(ecc_key* key, mp_int* a, mp_int* prime, mp_int* order); #ifdef ECC_SHAMIR static int ecc_mul2add(ecc_point* A, mp_int* kA, ecc_point* B, mp_int* kB, diff --git a/wolfssl/wolfcrypt/ecc.h b/wolfssl/wolfcrypt/ecc.h index 44c6a763f..87f9b71b6 100644 --- a/wolfssl/wolfcrypt/ecc.h +++ b/wolfssl/wolfcrypt/ecc.h @@ -289,6 +289,17 @@ extern const ecc_set_type ecc_sets[]; WOLFSSL_API const char* wc_ecc_get_name(int curve_id); +#ifndef WOLFSSL_ATECC508A + +WOLFSSL_API int ecc_map(ecc_point*, mp_int*, mp_digit); +WOLFSSL_API int ecc_projective_add_point(ecc_point* P, ecc_point* Q, + ecc_point* R, mp_int* a, + mp_int* modulus, mp_digit mp); +WOLFSSL_API int ecc_projective_dbl_point(ecc_point* P, ecc_point* R, mp_int* a, + mp_int* modulus, mp_digit mp); + +#endif + WOLFSSL_API int wc_ecc_make_key(WC_RNG* rng, int keysize, ecc_key* key); WOLFSSL_API diff --git a/wolfssl/wolfcrypt/integer.h b/wolfssl/wolfcrypt/integer.h index 52fda71b2..543a832bc 100644 --- a/wolfssl/wolfcrypt/integer.h +++ b/wolfssl/wolfcrypt/integer.h @@ -45,6 +45,12 @@ #include +#ifdef WOLFSSL_PUBLIC_MP + #define MP_API WOLFSSL_API +#else + #define MP_API +#endif + #ifndef MIN #define MIN(x,y) ((x)<(y)?(x):(y)) #endif @@ -234,114 +240,115 @@ typedef int ltm_prime_callback(unsigned char *dst, int len, void *dat); extern const char *mp_s_rmap; /* 6 functions needed by Rsa */ -int mp_init (mp_int * a); -void mp_clear (mp_int * a); -void mp_forcezero(mp_int * a); -int mp_unsigned_bin_size(mp_int * a); -int mp_read_unsigned_bin (mp_int * a, const unsigned char *b, int c); -int mp_to_unsigned_bin_at_pos(int x, mp_int *t, unsigned char *b); -int mp_to_unsigned_bin (mp_int * a, unsigned char *b); -int mp_exptmod (mp_int * G, mp_int * X, mp_int * P, mp_int * Y); +MP_API int mp_init (mp_int * a); +MP_API void mp_clear (mp_int * a); +MP_API void mp_forcezero(mp_int * a); +MP_API int mp_unsigned_bin_size(mp_int * a); +MP_API int mp_read_unsigned_bin (mp_int * a, const unsigned char *b, int c); +MP_API int mp_to_unsigned_bin_at_pos(int x, mp_int *t, unsigned char *b); +MP_API int mp_to_unsigned_bin (mp_int * a, unsigned char *b); +MP_API int mp_exptmod (mp_int * G, mp_int * X, mp_int * P, mp_int * Y); /* end functions needed by Rsa */ /* functions added to support above needed, removed TOOM and KARATSUBA */ -int mp_count_bits (mp_int * a); -int mp_leading_bit (mp_int * a); -int mp_init_copy (mp_int * a, mp_int * b); -int mp_copy (mp_int * a, mp_int * b); -int mp_grow (mp_int * a, int size); -int mp_div_2d (mp_int * a, int b, mp_int * c, mp_int * d); -void mp_zero (mp_int * a); -void mp_clamp (mp_int * a); -void mp_exch (mp_int * a, mp_int * b); -void mp_rshd (mp_int * a, int b); -void mp_rshb (mp_int * a, int b); -int mp_mod_2d (mp_int * a, int b, mp_int * c); -int mp_mul_2d (mp_int * a, int b, mp_int * c); -int mp_lshd (mp_int * a, int b); -int mp_abs (mp_int * a, mp_int * b); -int mp_invmod (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_count_bits (mp_int * a); +MP_API int mp_leading_bit (mp_int * a); +MP_API int mp_init_copy (mp_int * a, mp_int * b); +MP_API int mp_copy (mp_int * a, mp_int * b); +MP_API int mp_grow (mp_int * a, int size); +MP_API int mp_div_2d (mp_int * a, int b, mp_int * c, mp_int * d); +MP_API void mp_zero (mp_int * a); +MP_API void mp_clamp (mp_int * a); +MP_API void mp_exch (mp_int * a, mp_int * b); +MP_API void mp_rshd (mp_int * a, int b); +MP_API void mp_rshb (mp_int * a, int b); +MP_API int mp_mod_2d (mp_int * a, int b, mp_int * c); +MP_API int mp_mul_2d (mp_int * a, int b, mp_int * c); +MP_API int mp_lshd (mp_int * a, int b); +MP_API int mp_abs (mp_int * a, mp_int * b); +MP_API int mp_invmod (mp_int * a, mp_int * b, mp_int * c); int fast_mp_invmod (mp_int * a, mp_int * b, mp_int * c); -int mp_invmod_slow (mp_int * a, mp_int * b, mp_int * c); -int mp_cmp_mag (mp_int * a, mp_int * b); -int mp_cmp (mp_int * a, mp_int * b); -int mp_cmp_d(mp_int * a, mp_digit b); -int mp_set (mp_int * a, mp_digit b); -int mp_is_bit_set (mp_int * a, mp_digit b); -int mp_mod (mp_int * a, mp_int * b, mp_int * c); -int mp_div(mp_int * a, mp_int * b, mp_int * c, mp_int * d); -int mp_div_2(mp_int * a, mp_int * b); -int mp_add (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_invmod_slow (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_cmp_mag (mp_int * a, mp_int * b); +MP_API int mp_cmp (mp_int * a, mp_int * b); +MP_API int mp_cmp_d(mp_int * a, mp_digit b); +MP_API int mp_set (mp_int * a, mp_digit b); +MP_API int mp_is_bit_set (mp_int * a, mp_digit b); +MP_API int mp_mod (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_div(mp_int * a, mp_int * b, mp_int * c, mp_int * d); +MP_API int mp_div_2(mp_int * a, mp_int * b); +MP_API int mp_add (mp_int * a, mp_int * b, mp_int * c); int s_mp_add (mp_int * a, mp_int * b, mp_int * c); int s_mp_sub (mp_int * a, mp_int * b, mp_int * c); -int mp_sub (mp_int * a, mp_int * b, mp_int * c); -int mp_reduce_is_2k_l(mp_int *a); -int mp_reduce_is_2k(mp_int *a); -int mp_dr_is_modulus(mp_int *a); -int mp_exptmod_fast (mp_int * G, mp_int * X, mp_int * P, mp_int * Y, int); -int mp_montgomery_setup (mp_int * n, mp_digit * rho); +MP_API int mp_sub (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_reduce_is_2k_l(mp_int *a); +MP_API int mp_reduce_is_2k(mp_int *a); +MP_API int mp_dr_is_modulus(mp_int *a); +MP_API int mp_exptmod_fast (mp_int * G, mp_int * X, mp_int * P, mp_int * Y, + int); +MP_API int mp_montgomery_setup (mp_int * n, mp_digit * rho); int fast_mp_montgomery_reduce (mp_int * x, mp_int * n, mp_digit rho); -int mp_montgomery_reduce (mp_int * x, mp_int * n, mp_digit rho); -void mp_dr_setup(mp_int *a, mp_digit *d); -int mp_dr_reduce (mp_int * x, mp_int * n, mp_digit k); -int mp_reduce_2k(mp_int *a, mp_int *n, mp_digit d); +MP_API int mp_montgomery_reduce (mp_int * x, mp_int * n, mp_digit rho); +MP_API void mp_dr_setup(mp_int *a, mp_digit *d); +MP_API int mp_dr_reduce (mp_int * x, mp_int * n, mp_digit k); +MP_API int mp_reduce_2k(mp_int *a, mp_int *n, mp_digit d); int fast_s_mp_mul_high_digs (mp_int * a, mp_int * b, mp_int * c, int digs); int s_mp_mul_high_digs (mp_int * a, mp_int * b, mp_int * c, int digs); -int mp_reduce_2k_setup_l(mp_int *a, mp_int *d); -int mp_reduce_2k_l(mp_int *a, mp_int *n, mp_int *d); -int mp_reduce (mp_int * x, mp_int * m, mp_int * mu); -int mp_reduce_setup (mp_int * a, mp_int * b); +MP_API int mp_reduce_2k_setup_l(mp_int *a, mp_int *d); +MP_API int mp_reduce_2k_l(mp_int *a, mp_int *n, mp_int *d); +MP_API int mp_reduce (mp_int * x, mp_int * m, mp_int * mu); +MP_API int mp_reduce_setup (mp_int * a, mp_int * b); int s_mp_exptmod (mp_int * G, mp_int * X, mp_int * P, mp_int * Y, int redmode); -int mp_montgomery_calc_normalization (mp_int * a, mp_int * b); +MP_API int mp_montgomery_calc_normalization (mp_int * a, mp_int * b); int s_mp_mul_digs (mp_int * a, mp_int * b, mp_int * c, int digs); int s_mp_sqr (mp_int * a, mp_int * b); int fast_s_mp_mul_digs (mp_int * a, mp_int * b, mp_int * c, int digs); int fast_s_mp_sqr (mp_int * a, mp_int * b); -int mp_init_size (mp_int * a, int size); -int mp_div_3 (mp_int * a, mp_int *c, mp_digit * d); -int mp_mul_2(mp_int * a, mp_int * b); -int mp_mul (mp_int * a, mp_int * b, mp_int * c); -int mp_sqr (mp_int * a, mp_int * b); -int mp_mulmod (mp_int * a, mp_int * b, mp_int * c, mp_int * d); -int mp_submod (mp_int* a, mp_int* b, mp_int* c, mp_int* d); -int mp_addmod (mp_int* a, mp_int* b, mp_int* c, mp_int* d); -int mp_mul_d (mp_int * a, mp_digit b, mp_int * c); -int mp_2expt (mp_int * a, int b); -int mp_set_bit (mp_int * a, int b); -int mp_reduce_2k_setup(mp_int *a, mp_digit *d); -int mp_add_d (mp_int* a, mp_digit b, mp_int* c); -int mp_set_int (mp_int * a, unsigned long b); -int mp_sub_d (mp_int * a, mp_digit b, mp_int * c); +MP_API int mp_init_size (mp_int * a, int size); +MP_API int mp_div_3 (mp_int * a, mp_int *c, mp_digit * d); +MP_API int mp_mul_2(mp_int * a, mp_int * b); +MP_API int mp_mul (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_sqr (mp_int * a, mp_int * b); +MP_API int mp_mulmod (mp_int * a, mp_int * b, mp_int * c, mp_int * d); +MP_API int mp_submod (mp_int* a, mp_int* b, mp_int* c, mp_int* d); +MP_API int mp_addmod (mp_int* a, mp_int* b, mp_int* c, mp_int* d); +MP_API int mp_mul_d (mp_int * a, mp_digit b, mp_int * c); +MP_API int mp_2expt (mp_int * a, int b); +MP_API int mp_set_bit (mp_int * a, int b); +MP_API int mp_reduce_2k_setup(mp_int *a, mp_digit *d); +MP_API int mp_add_d (mp_int* a, mp_digit b, mp_int* c); +MP_API int mp_set_int (mp_int * a, unsigned long b); +MP_API int mp_sub_d (mp_int * a, mp_digit b, mp_int * c); /* end support added functions */ /* added */ -int mp_init_multi(mp_int* a, mp_int* b, mp_int* c, mp_int* d, mp_int* e, - mp_int* f); -int mp_toradix (mp_int *a, char *str, int radix); -int mp_radix_size (mp_int * a, int radix, int *size); +MP_API int mp_init_multi(mp_int* a, mp_int* b, mp_int* c, mp_int* d, mp_int* e, + mp_int* f); +MP_API int mp_toradix (mp_int *a, char *str, int radix); +MP_API int mp_radix_size (mp_int * a, int radix, int *size); #ifdef WOLFSSL_DEBUG_MATH - void mp_dump(const char* desc, mp_int* a, byte verbose); + MP_API void mp_dump(const char* desc, mp_int* a, byte verbose); #else #define mp_dump(desc, a, verbose) #endif #if defined(HAVE_ECC) || defined(WOLFSSL_KEY_GEN) - int mp_sqrmod(mp_int* a, mp_int* b, mp_int* c); + MP_API int mp_sqrmod(mp_int* a, mp_int* b, mp_int* c); #endif #if defined(HAVE_ECC) || defined(WOLFSSL_KEY_GEN) - int mp_read_radix(mp_int* a, const char* str, int radix); + MP_API int mp_read_radix(mp_int* a, const char* str, int radix); #endif #ifdef WOLFSSL_KEY_GEN - int mp_prime_is_prime (mp_int * a, int t, int *result); - int mp_gcd (mp_int * a, mp_int * b, mp_int * c); - int mp_lcm (mp_int * a, mp_int * b, mp_int * c); - int mp_rand_prime(mp_int* N, int len, WC_RNG* rng, void* heap); + MP_API int mp_prime_is_prime (mp_int * a, int t, int *result); + MP_API int mp_gcd (mp_int * a, mp_int * b, mp_int * c); + MP_API int mp_lcm (mp_int * a, mp_int * b, mp_int * c); + MP_API int mp_rand_prime(mp_int* N, int len, WC_RNG* rng, void* heap); #endif -int mp_cnt_lsb(mp_int *a); -int mp_mod_d(mp_int* a, mp_digit b, mp_digit* c); +MP_API int mp_cnt_lsb(mp_int *a); +MP_API int mp_mod_d(mp_int* a, mp_digit b, mp_digit* c); /* wolf big int and common functions */ diff --git a/wolfssl/wolfcrypt/tfm.h b/wolfssl/wolfcrypt/tfm.h index 8427412d0..a614169ff 100644 --- a/wolfssl/wolfcrypt/tfm.h +++ b/wolfssl/wolfcrypt/tfm.h @@ -47,6 +47,12 @@ extern "C" { #endif +#ifdef WOLFSSL_PUBLIC_MP + #define MP_API WOLFSSL_API +#else + #define MP_API +#endif + #ifndef MIN #define MIN(x,y) ((x)<(y)?(x):(y)) #endif @@ -370,8 +376,8 @@ typedef struct fp_int { /* initialize [or zero] an fp int */ void fp_init(fp_int *a); -void fp_zero(fp_int *a); -void fp_clear(fp_int *a); /* uses ForceZero to clear sensitive memory */ +MP_API void fp_zero(fp_int *a); +MP_API void fp_clear(fp_int *a); /* uses ForceZero to clear sensitive memory */ /* zero/even/odd ? */ #define fp_iszero(a) (((a)->used == 0) ? FP_YES : FP_NO) @@ -617,85 +623,86 @@ typedef fp_int mp_int; #define mp_isone(a) fp_isone(a) #define mp_iseven(a) fp_iseven(a) #define mp_isneg(a) fp_isneg(a) -int mp_init (mp_int * a); -void mp_clear (mp_int * a); +MP_API int mp_init (mp_int * a); +MP_API void mp_clear (mp_int * a); #define mp_forcezero(a) fp_clear(a) -int mp_init_multi(mp_int* a, mp_int* b, mp_int* c, mp_int* d, mp_int* e, mp_int* f); +MP_API int mp_init_multi(mp_int* a, mp_int* b, mp_int* c, mp_int* d, mp_int* e, + mp_int* f); -int mp_add (mp_int * a, mp_int * b, mp_int * c); -int mp_sub (mp_int * a, mp_int * b, mp_int * c); -int mp_add_d (mp_int * a, mp_digit b, mp_int * c); +MP_API int mp_add (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_sub (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_add_d (mp_int * a, mp_digit b, mp_int * c); -int mp_mul (mp_int * a, mp_int * b, mp_int * c); -int mp_mul_d (mp_int * a, mp_digit b, mp_int * c); -int mp_mulmod (mp_int * a, mp_int * b, mp_int * c, mp_int * d); -int mp_submod (mp_int* a, mp_int* b, mp_int* c, mp_int* d); -int mp_addmod (mp_int* a, mp_int* b, mp_int* c, mp_int* d); -int mp_mod(mp_int *a, mp_int *b, mp_int *c); -int mp_invmod(mp_int *a, mp_int *b, mp_int *c); -int mp_exptmod (mp_int * g, mp_int * x, mp_int * p, mp_int * y); -int mp_mul_2d(mp_int *a, int b, mp_int *c); +MP_API int mp_mul (mp_int * a, mp_int * b, mp_int * c); +MP_API int mp_mul_d (mp_int * a, mp_digit b, mp_int * c); +MP_API int mp_mulmod (mp_int * a, mp_int * b, mp_int * c, mp_int * d); +MP_API int mp_submod (mp_int* a, mp_int* b, mp_int* c, mp_int* d); +MP_API int mp_addmod (mp_int* a, mp_int* b, mp_int* c, mp_int* d); +MP_API int mp_mod(mp_int *a, mp_int *b, mp_int *c); +MP_API int mp_invmod(mp_int *a, mp_int *b, mp_int *c); +MP_API int mp_exptmod (mp_int * g, mp_int * x, mp_int * p, mp_int * y); +MP_API int mp_mul_2d(mp_int *a, int b, mp_int *c); -int mp_div(mp_int * a, mp_int * b, mp_int * c, mp_int * d); +MP_API int mp_div(mp_int * a, mp_int * b, mp_int * c, mp_int * d); -int mp_cmp(mp_int *a, mp_int *b); -int mp_cmp_d(mp_int *a, mp_digit b); +MP_API int mp_cmp(mp_int *a, mp_int *b); +MP_API int mp_cmp_d(mp_int *a, mp_digit b); -int mp_unsigned_bin_size(mp_int * a); -int mp_read_unsigned_bin (mp_int * a, const unsigned char *b, int c); -int mp_to_unsigned_bin_at_pos(int x, mp_int *t, unsigned char *b); -int mp_to_unsigned_bin (mp_int * a, unsigned char *b); +MP_API int mp_unsigned_bin_size(mp_int * a); +MP_API int mp_read_unsigned_bin (mp_int * a, const unsigned char *b, int c); +MP_API int mp_to_unsigned_bin_at_pos(int x, mp_int *t, unsigned char *b); +MP_API int mp_to_unsigned_bin (mp_int * a, unsigned char *b); -int mp_sub_d(fp_int *a, fp_digit b, fp_int *c); -int mp_copy(fp_int* a, fp_int* b); -int mp_isodd(mp_int* a); -int mp_iszero(mp_int* a); -int mp_count_bits(mp_int *a); -int mp_leading_bit(mp_int *a); -int mp_set_int(mp_int *a, unsigned long b); -int mp_is_bit_set (mp_int * a, mp_digit b); -int mp_set_bit (mp_int * a, mp_digit b); -void mp_rshb(mp_int *a, int x); -void mp_rshd(mp_int *a, int x); -int mp_toradix (mp_int *a, char *str, int radix); -int mp_radix_size (mp_int * a, int radix, int *size); +MP_API int mp_sub_d(fp_int *a, fp_digit b, fp_int *c); +MP_API int mp_copy(fp_int* a, fp_int* b); +MP_API int mp_isodd(mp_int* a); +MP_API int mp_iszero(mp_int* a); +MP_API int mp_count_bits(mp_int *a); +MP_API int mp_leading_bit(mp_int *a); +MP_API int mp_set_int(mp_int *a, unsigned long b); +MP_API int mp_is_bit_set (mp_int * a, mp_digit b); +MP_API int mp_set_bit (mp_int * a, mp_digit b); +MP_API void mp_rshb(mp_int *a, int x); +MP_API void mp_rshd(mp_int *a, int x); +MP_API int mp_toradix (mp_int *a, char *str, int radix); +MP_API int mp_radix_size (mp_int * a, int radix, int *size); #ifdef WOLFSSL_DEBUG_MATH - void mp_dump(const char* desc, mp_int* a, byte verbose); + MP_API void mp_dump(const char* desc, mp_int* a, byte verbose); #else #define mp_dump(desc, a, verbose) #endif #ifdef HAVE_ECC - int mp_read_radix(mp_int* a, const char* str, int radix); - int mp_sqr(fp_int *a, fp_int *b); - int mp_montgomery_reduce(fp_int *a, fp_int *m, fp_digit mp); - int mp_montgomery_setup(fp_int *a, fp_digit *rho); - int mp_div_2(fp_int * a, fp_int * b); - int mp_init_copy(fp_int * a, fp_int * b); + MP_API int mp_read_radix(mp_int* a, const char* str, int radix); + MP_API int mp_sqr(fp_int *a, fp_int *b); + MP_API int mp_montgomery_reduce(fp_int *a, fp_int *m, fp_digit mp); + MP_API int mp_montgomery_setup(fp_int *a, fp_digit *rho); + MP_API int mp_div_2(fp_int * a, fp_int * b); + MP_API int mp_init_copy(fp_int * a, fp_int * b); #endif #if defined(HAVE_ECC) || !defined(NO_RSA) || !defined(NO_DSA) - int mp_set(fp_int *a, fp_digit b); + MP_API int mp_set(fp_int *a, fp_digit b); #endif #if defined(HAVE_ECC) || defined(WOLFSSL_KEY_GEN) - int mp_sqrmod(mp_int* a, mp_int* b, mp_int* c); - int mp_montgomery_calc_normalization(mp_int *a, mp_int *b); + MP_API int mp_sqrmod(mp_int* a, mp_int* b, mp_int* c); + MP_API int mp_montgomery_calc_normalization(mp_int *a, mp_int *b); #endif #ifdef WOLFSSL_KEY_GEN -int mp_gcd(fp_int *a, fp_int *b, fp_int *c); -int mp_lcm(fp_int *a, fp_int *b, fp_int *c); -int mp_prime_is_prime(mp_int* a, int t, int* result); -int mp_rand_prime(mp_int* N, int len, WC_RNG* rng, void* heap); -int mp_exch(mp_int *a, mp_int *b); +MP_API int mp_gcd(fp_int *a, fp_int *b, fp_int *c); +MP_API int mp_lcm(fp_int *a, fp_int *b, fp_int *c); +MP_API int mp_prime_is_prime(mp_int* a, int t, int* result); +MP_API int mp_rand_prime(mp_int* N, int len, WC_RNG* rng, void* heap); +MP_API int mp_exch(mp_int *a, mp_int *b); #endif /* WOLFSSL_KEY_GEN */ -int mp_cnt_lsb(fp_int *a); -int mp_div_2d(fp_int *a, int b, fp_int *c, fp_int *d); -int mp_mod_d(fp_int* a, fp_digit b, fp_digit* c); -int mp_lshd (mp_int * a, int b); +MP_API int mp_cnt_lsb(fp_int *a); +MP_API int mp_div_2d(fp_int *a, int b, fp_int *c, fp_int *d); +MP_API int mp_mod_d(fp_int* a, fp_digit b, fp_digit* c); +MP_API int mp_lshd (mp_int * a, int b); WOLFSSL_API word32 CheckRunTimeFastMath(void); From 461f051ef15b7c52f3ee9a48d484e675bbed1bbd Mon Sep 17 00:00:00 2001 From: Sean Parkinson Date: Fri, 17 Mar 2017 10:52:38 +1000 Subject: [PATCH 68/68] Only expose ECC APIs on config define --- configure.ac | 2 +- wolfssl/wolfcrypt/ecc.h | 17 +++++++++++------ 2 files changed, 12 insertions(+), 7 deletions(-) diff --git a/configure.ac b/configure.ac index 2490f6b73..dd1c885a7 100644 --- a/configure.ac +++ b/configure.ac @@ -341,7 +341,7 @@ AC_ARG_ENABLE([wpas], if test "$ENABLED_WPAS" = "yes" then AM_CFLAGS="$AM_CFLAGS -DHAVE_SECRET_CALLBACK -DWOLFSSL_STATIC_RSA" - AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_PUBLIC_MP" + AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_PUBLIC_MP -DWOLFSSL_PUBLIC_ECC_ADD_DBL" AM_CFLAGS="$AM_CFLAGS -DATOMIC_USER" AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_WPAS" fi diff --git a/wolfssl/wolfcrypt/ecc.h b/wolfssl/wolfcrypt/ecc.h index 87f9b71b6..fb4701940 100644 --- a/wolfssl/wolfcrypt/ecc.h +++ b/wolfssl/wolfcrypt/ecc.h @@ -291,12 +291,17 @@ const char* wc_ecc_get_name(int curve_id); #ifndef WOLFSSL_ATECC508A -WOLFSSL_API int ecc_map(ecc_point*, mp_int*, mp_digit); -WOLFSSL_API int ecc_projective_add_point(ecc_point* P, ecc_point* Q, - ecc_point* R, mp_int* a, - mp_int* modulus, mp_digit mp); -WOLFSSL_API int ecc_projective_dbl_point(ecc_point* P, ecc_point* R, mp_int* a, - mp_int* modulus, mp_digit mp); +#ifdef WOLFSSL_PUBLIC_ECC_ADD_DBL + #define ECC_API WOLFSSL_API +#else + #define ECC_API WOLFSSL_LOCAL +#endif + +ECC_API int ecc_map(ecc_point*, mp_int*, mp_digit); +ECC_API int ecc_projective_add_point(ecc_point* P, ecc_point* Q, ecc_point* R, + mp_int* a, mp_int* modulus, mp_digit mp); +ECC_API int ecc_projective_dbl_point(ecc_point* P, ecc_point* R, mp_int* a, + mp_int* modulus, mp_digit mp); #endif