diff --git a/cyassl/ctaocrypt/types.h b/cyassl/ctaocrypt/types.h index 084078803..e8f207213 100644 --- a/cyassl/ctaocrypt/types.h +++ b/cyassl/ctaocrypt/types.h @@ -157,6 +157,8 @@ enum { #ifndef STRING_USER #include + char* mystrnstr(const char* s1, const char* s2, unsigned int n); + #define XMEMCPY(d,s,l) memcpy((d),(s),(l)) #define XMEMSET(b,c,l) memset((b),(c),(l)) #define XMEMCMP(s1,s2,n) memcmp((s1),(s2),(n)) @@ -167,6 +169,7 @@ enum { /* strstr, strncmp, and strncat only used by CyaSSL proper, not required for CTaoCrypt only */ #define XSTRSTR(s1,s2) strstr((s1),(s2)) + #define XSTRNSTR(s1,s2,n) mystrnstr((s1),(s2),(n)) #define XSTRNCMP(s1,s2,n) strncmp((s1),(s2),(n)) #define XSTRNCAT(s1,s2,n) strncat((s1),(s2),(n)) #endif diff --git a/cyassl/internal.h b/cyassl/internal.h index 02d33f52f..2cb8ef2a5 100644 --- a/cyassl/internal.h +++ b/cyassl/internal.h @@ -347,7 +347,9 @@ enum Misc { SIZEOF_SENDER = 4, /* clnt or srvr */ FINISHED_SZ = MD5_DIGEST_SIZE + SHA_DIGEST_SIZE, MAX_RECORD_SIZE = 16384, /* 2^14, max size by standard */ - MAX_MSG_EXTRA = 68, /* max added to msg, mac + pad */ + MAX_MSG_EXTRA = 70, /* max added to msg, mac + pad from */ + /* RECORD_HEADER_SZ + BLOCK_SZ (pad) + SHA_256 + digest sz + BLOC_SZ (iv) + pad byte (1) */ MAX_COMP_EXTRA = 1024, /* max compression extra */ MAX_MTU = 1500, /* max expected MTU */ MAX_UDP_SIZE = MAX_MTU - 100, /* don't exceed MTU w/ 100 byte header */ diff --git a/src/internal.c b/src/internal.c index df3584320..c959118ce 100644 --- a/src/internal.c +++ b/src/internal.c @@ -810,6 +810,8 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK, } +/* init everything to 0, NULL, default values before calling anything that may + fail so that desctructor has a "good" state to cleanup */ int InitSSL(CYASSL* ssl, CYASSL_CTX* ctx) { int ret; @@ -871,17 +873,6 @@ int InitSSL(CYASSL* ssl, CYASSL_CTX* ctx) ssl->IOCB_ReadCtx = &ssl->rfd; /* prevent invalid pointer acess if not */ ssl->IOCB_WriteCtx = &ssl->wfd; /* correctly set */ - /* increment CTX reference count */ - if (LockMutex(&ctx->countMutex) != 0) { - CYASSL_MSG("Couldn't lock CTX count mutex"); - return BAD_MUTEX_ERROR; - } - ctx->refCount++; - UnLockMutex(&ctx->countMutex); - - if ( (ret = InitRng(&ssl->rng)) != 0) - return ret; - InitMd5(&ssl->hashMd5); InitSha(&ssl->hashSha); #ifndef NO_SHA256 @@ -970,40 +961,7 @@ int InitSSL(CYASSL* ssl, CYASSL_CTX* ctx) ssl->peerCert.issuer.sz = 0; ssl->peerCert.subject.sz = 0; #endif - - /* make sure server has cert and key unless using PSK */ - if (ssl->options.side == SERVER_END && !havePSK) - if (!ssl->buffers.certificate.buffer || !ssl->buffers.key.buffer) { - CYASSL_MSG("Server missing certificate and/or private key"); - return NO_PRIVATE_KEY; - } - -#ifndef NO_PSK - ssl->arrays.client_identity[0] = 0; - if (ctx->server_hint[0]) { /* set in CTX */ - XSTRNCPY(ssl->arrays.server_hint, ctx->server_hint, MAX_PSK_ID_LEN); - ssl->arrays.server_hint[MAX_PSK_ID_LEN - 1] = '\0'; - } - else - ssl->arrays.server_hint[0] = 0; -#endif /* NO_PSK */ - -#ifdef CYASSL_CALLBACKS - ssl->hsInfoOn = 0; - ssl->toInfoOn = 0; -#endif - - /* make sure server has DH parms, and add PSK if there, add NTRU too */ - if (ssl->options.side == SERVER_END) - InitSuites(&ssl->suites, ssl->version,ssl->options.haveDH, havePSK, - ssl->options.haveNTRU, ssl->options.haveECDSA, - ssl->options.haveStaticECC, ssl->options.side); - else - InitSuites(&ssl->suites, ssl->version, TRUE, havePSK, - ssl->options.haveNTRU, ssl->options.haveECDSA, - ssl->options.haveStaticECC, ssl->options.side); - - + #ifdef SESSION_CERTS ssl->session.chain.count = 0; #endif @@ -1016,6 +974,51 @@ int InitSSL(CYASSL* ssl, CYASSL_CTX* ctx) ssl->ex_data[2] = 0; #endif +#ifdef CYASSL_CALLBACKS + ssl->hsInfoOn = 0; + ssl->toInfoOn = 0; +#endif + +#ifndef NO_PSK + ssl->arrays.client_identity[0] = 0; + if (ctx->server_hint[0]) { /* set in CTX */ + XSTRNCPY(ssl->arrays.server_hint, ctx->server_hint, MAX_PSK_ID_LEN); + ssl->arrays.server_hint[MAX_PSK_ID_LEN - 1] = '\0'; + } + else + ssl->arrays.server_hint[0] = 0; +#endif /* NO_PSK */ + + /* all done with init, now can return errors, call other stuff */ + + /* increment CTX reference count */ + if (LockMutex(&ctx->countMutex) != 0) { + CYASSL_MSG("Couldn't lock CTX count mutex"); + return BAD_MUTEX_ERROR; + } + ctx->refCount++; + UnLockMutex(&ctx->countMutex); + + if ( (ret = InitRng(&ssl->rng)) != 0) + return ret; + + /* make sure server has cert and key unless using PSK */ + if (ssl->options.side == SERVER_END && !havePSK) + if (!ssl->buffers.certificate.buffer || !ssl->buffers.key.buffer) { + CYASSL_MSG("Server missing certificate and/or private key"); + return NO_PRIVATE_KEY; + } + + /* make sure server has DH parms, and add PSK if there, add NTRU too */ + if (ssl->options.side == SERVER_END) + InitSuites(&ssl->suites, ssl->version,ssl->options.haveDH, havePSK, + ssl->options.haveNTRU, ssl->options.haveECDSA, + ssl->options.haveStaticECC, ssl->options.side); + else + InitSuites(&ssl->suites, ssl->version, TRUE, havePSK, + ssl->options.haveNTRU, ssl->options.haveECDSA, + ssl->options.haveStaticECC, ssl->options.side); + return 0; } @@ -1026,7 +1029,7 @@ void SSL_ResourceFree(CYASSL* ssl) XFREE(ssl->buffers.serverDH_Priv.buffer, ssl->heap, DYNAMIC_TYPE_DH); XFREE(ssl->buffers.serverDH_Pub.buffer, ssl->heap, DYNAMIC_TYPE_DH); /* parameters (p,g) may be owned by ctx */ - if (ssl->buffers.weOwnDH) { + if (ssl->buffers.weOwnDH || ssl->options.side == CLIENT_END) { XFREE(ssl->buffers.serverDH_G.buffer, ssl->heap, DYNAMIC_TYPE_DH); XFREE(ssl->buffers.serverDH_P.buffer, ssl->heap, DYNAMIC_TYPE_DH); } diff --git a/src/ssl.c b/src/ssl.c index 8f30c05d4..225c76254 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -77,6 +77,24 @@ #endif /* min */ +char* mystrnstr(const char* s1, const char* s2, unsigned int n) +{ + unsigned int s2_len = XSTRLEN(s2); + + if (s2_len == 0) + return (char*)s1; + + while (n >= s2_len && s1[0]) { + if (s1[0] == s2[0]) + if (XMEMCMP(s1, s2, s2_len) == 0) + return (char*)s1; + s1++; + n--; + } + + return NULL; +} + CYASSL_CTX* CyaSSL_CTX_new(CYASSL_METHOD* method) { @@ -719,12 +737,12 @@ int AddCA(CYASSL_CERT_MANAGER* cm, buffer der, int type, int verify) } /* find header */ - headerEnd = XSTRSTR((char*)buff, header); + headerEnd = XSTRNSTR((char*)buff, header, sz); if (!headerEnd && type == PRIVATEKEY_TYPE) { /* may be pkcs8 */ XSTRNCPY(header, "-----BEGIN PRIVATE KEY-----", sizeof(header)); XSTRNCPY(footer, "-----END PRIVATE KEY-----", sizeof(footer)); - headerEnd = XSTRSTR((char*)buff, header); + headerEnd = XSTRNSTR((char*)buff, header, sz); if (headerEnd) pkcs8 = 1; else { @@ -733,7 +751,7 @@ int AddCA(CYASSL_CERT_MANAGER* cm, buffer der, int type, int verify) XSTRNCPY(footer, "-----END ENCRYPTED PRIVATE KEY-----", sizeof(footer)); - headerEnd = XSTRSTR((char*)buff, header); + headerEnd = XSTRNSTR((char*)buff, header, sz); if (headerEnd) pkcs8Enc = 1; } @@ -742,7 +760,7 @@ int AddCA(CYASSL_CERT_MANAGER* cm, buffer der, int type, int verify) XSTRNCPY(header, "-----BEGIN EC PRIVATE KEY-----", sizeof(header)); XSTRNCPY(footer, "-----END EC PRIVATE KEY-----", sizeof(footer)); - headerEnd = XSTRSTR((char*)buff, header); + headerEnd = XSTRNSTR((char*)buff, header, sz); if (headerEnd) *eccKey = 1; } @@ -750,7 +768,7 @@ int AddCA(CYASSL_CERT_MANAGER* cm, buffer der, int type, int verify) XSTRNCPY(header, "-----BEGIN DSA PRIVATE KEY-----", sizeof(header)); XSTRNCPY(footer, "-----END DSA PRIVATE KEY-----", sizeof(footer)); - headerEnd = XSTRSTR((char*)buff, header); + headerEnd = XSTRNSTR((char*)buff, header, sz); } if (!headerEnd) return SSL_BAD_FILE; @@ -768,28 +786,28 @@ int AddCA(CYASSL_CERT_MANAGER* cm, buffer der, int type, int verify) { /* remove encrypted header if there */ char encHeader[] = "Proc-Type"; - char* line = XSTRSTR((char*)buff, encHeader); + char* line = XSTRNSTR((char*)buff, encHeader, PEM_LINE_LEN); if (line) { char* newline; char* finish; - char* start = XSTRSTR(line, "DES"); + char* start = XSTRNSTR(line, "DES", PEM_LINE_LEN); if (!start) - start = XSTRSTR(line, "AES"); + start = XSTRNSTR(line, "AES", PEM_LINE_LEN); if (!start) return SSL_BAD_FILE; if (!info) return SSL_BAD_FILE; - finish = XSTRSTR(start, ","); + finish = XSTRNSTR(start, ",", PEM_LINE_LEN); if (start && finish && (start < finish)) { - newline = XSTRSTR(finish, "\r"); + newline = XSTRNSTR(finish, "\r", PEM_LINE_LEN); XMEMCPY(info->name, start, finish - start); info->name[finish - start] = 0; XMEMCPY(info->iv, finish + 1, sizeof(info->iv)); - if (!newline) newline = XSTRSTR(finish, "\n"); + if (!newline) newline = XSTRNSTR(finish, "\n", PEM_LINE_LEN); if (newline && (newline > finish)) { info->ivSz = (word32)(newline - (finish + 1)); info->set = 1; @@ -809,7 +827,7 @@ int AddCA(CYASSL_CERT_MANAGER* cm, buffer der, int type, int verify) #endif /* OPENSSL_EXTRA || HAVE_WEBSERVER */ /* find footer */ - footerEnd = XSTRSTR((char*)buff, footer); + footerEnd = XSTRNSTR((char*)buff, footer, sz); if (!footerEnd) return SSL_BAD_FILE; consumedEnd = footerEnd + XSTRLEN(footer); @@ -1490,6 +1508,15 @@ int CyaSSL_CertManagerDisableCRL(CYASSL_CERT_MANAGER* cm) } +int CyaSSL_CTX_check_private_key(CYASSL_CTX* ctx) +{ + /* TODO: check private against public for RSA match */ + (void)ctx; + CYASSL_ENTER("SSL_CTX_check_private_key"); + return SSL_SUCCESS; +} + + #ifdef HAVE_CRL @@ -3302,15 +3329,6 @@ int CyaSSL_set_compression(CYASSL* ssl) } - int CyaSSL_CTX_check_private_key(CYASSL_CTX* ctx) - { - /* TODO: check private against public for RSA match */ - (void)ctx; - CYASSL_ENTER("SSL_CTX_check_private_key"); - return SSL_SUCCESS; - } - - void CyaSSL_set_bio(CYASSL* ssl, CYASSL_BIO* rd, CYASSL_BIO* wr) { CYASSL_ENTER("SSL_set_bio");