merge fix

pull/1/head
John Safranek 2012-05-05 14:49:17 -07:00
commit f9985f5399
10 changed files with 658 additions and 91 deletions

View File

@ -6,7 +6,7 @@
#
#
AC_INIT([cyassl],[2.1.2],[http://www.yassl.com])
AC_INIT([cyassl],[2.1.3],[http://www.yassl.com])
AC_CONFIG_AUX_DIR(config)

View File

@ -1599,7 +1599,7 @@ static int GetValidity(DecodedCert* cert, int verify)
}
static int DecodeToKey(DecodedCert* cert, int verify)
int DecodeToKey(DecodedCert* cert, int verify)
{
int badDate = 0;
int ret;
@ -2017,13 +2017,12 @@ static int ConfirmSignature(DecodedCert* cert, const byte* key, word32 keySz,
}
int ParseCert(DecodedCert* cert, int type, int verify,
Signer* signers)
int ParseCert(DecodedCert* cert, int type, int verify, void* cm)
{
int ret;
char* ptr;
ret = ParseCertRelative(cert, type, verify, signers);
ret = ParseCertRelative(cert, type, verify, cm);
if (ret < 0)
return ret;
@ -2144,8 +2143,7 @@ static void IsCa(DecodedCert* cert)
#endif
int ParseCertRelative(DecodedCert* cert, int type, int verify,
Signer* signers)
int ParseCertRelative(DecodedCert* cert, int type, int verify, void* cm)
{
word32 confirmOID;
int ret;
@ -2181,7 +2179,7 @@ int ParseCertRelative(DecodedCert* cert, int type, int verify,
return ASN_SIG_OID_E;
if (verify && type != CA_TYPE) {
Signer* ca = GetCA(signers, cert->issuerHash);
Signer* ca = GetCA(cm, cert->issuerHash);
CYASSL_MSG("About to verify certificate signature");
if (ca) {

View File

@ -263,11 +263,10 @@ struct Signer {
CYASSL_TEST_API void InitDecodedCert(DecodedCert*, byte*, word32, void*);
CYASSL_TEST_API void FreeDecodedCert(DecodedCert*);
CYASSL_TEST_API int ParseCert(DecodedCert*, int type, int verify,
Signer* signer);
CYASSL_TEST_API int ParseCert(DecodedCert*, int type, int verify, void* cm);
CYASSL_LOCAL int ParseCertRelative(DecodedCert*, int type, int verify,
Signer* signer);
CYASSL_LOCAL int ParseCertRelative(DecodedCert*, int type, int verify,void* cm);
CYASSL_LOCAL int DecodeToKey(DecodedCert*, int verify);
CYASSL_LOCAL word32 EncodeSignature(byte* out, const byte* digest, word32 digSz,
int hashOID);

View File

@ -200,7 +200,8 @@ enum {
DYNAMIC_TYPE_SSL = 17,
DYNAMIC_TYPE_CTX = 18,
DYNAMIC_TYPE_WRITEV = 19,
DYNAMIC_TYPE_OPENSSL = 20
DYNAMIC_TYPE_OPENSSL = 20,
DYNAMIC_TYPE_CERT_MANAGER = 21
};
/* stack protection */

View File

@ -91,11 +91,12 @@ enum CyaSSL_ErrorCodes {
BAD_MUTEX_ERROR = -256, /* Bad mutex */
NOT_CA_ERROR = -257, /* Not a CA cert error */
BAD_PATH_ERROR = -258, /* Bad path for opendir */
BAD_CERT_MANAGER_ERROR = -259, /* Bad Cert Manager */
/* add strings to SetErrorString !!!!! */
/* begin negotiation parameter errors */
UNSUPPORTED_SUITE = -260, /* unsupported cipher suite */
MATCH_SUITE_ERROR = -261 /* can't match cipher suite */
UNSUPPORTED_SUITE = -270, /* unsupported cipher suite */
MATCH_SUITE_ERROR = -271 /* can't match cipher suite */
/* end negotiation parameter errors only 10 for now */
/* add strings to SetErrorString !!!!! */
};

View File

@ -172,14 +172,25 @@ void c32to24(word32 in, word24 out);
#define BUILD_TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA
#define BUILD_TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA
#define BUILD_TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA
#define BUILD_TLS_ECDH_RSA_WITH_AES_128_CBC_SHA
#define BUILD_TLS_ECDH_RSA_WITH_AES_256_CBC_SHA
#define BUILD_TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
#define BUILD_TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA
#endif
#if !defined(NO_RC4)
#define BUILD_TLS_ECDHE_RSA_WITH_RC4_128_SHA
#define BUILD_TLS_ECDHE_ECDSA_WITH_RC4_128_SHA
#define BUILD_TLS_ECDH_RSA_WITH_RC4_128_SHA
#define BUILD_TLS_ECDH_ECDSA_WITH_RC4_128_SHA
#endif
#if !defined(NO_DES3)
#define BUILD_TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA
#define BUILD_TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA
#define BUILD_TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA
#define BUILD_TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA
#endif
#endif
@ -238,6 +249,16 @@ enum {
TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA = 0x12,
TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA = 0x08,
/* static ECDH, first byte is 0xC0 (ECC_BYTE) */
TLS_ECDH_RSA_WITH_AES_256_CBC_SHA = 0x0F,
TLS_ECDH_RSA_WITH_AES_128_CBC_SHA = 0x0E,
TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA = 0x05,
TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA = 0x04,
TLS_ECDH_RSA_WITH_RC4_128_SHA = 0x0C,
TLS_ECDH_ECDSA_WITH_RC4_128_SHA = 0x02,
TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA = 0x0D,
TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA = 0x03,
/* CyaSSL extension - eSTREAM */
TLS_RSA_WITH_HC_128_CBC_MD5 = 0xFB,
TLS_RSA_WITH_HC_128_CBC_SHA = 0xFC,
@ -547,7 +568,7 @@ typedef struct Suites {
CYASSL_LOCAL
void InitSuites(Suites*, ProtocolVersion, byte, byte, byte, byte, int);
void InitSuites(Suites*, ProtocolVersion, byte, byte, byte, byte, byte, int);
CYASSL_LOCAL
int SetCipherList(Suites*, const char* list);
@ -601,6 +622,15 @@ CYASSL_LOCAL int LockMutex(CyaSSL_Mutex*);
CYASSL_LOCAL int UnLockMutex(CyaSSL_Mutex*);
/* CyaSSL Certificate Manager */
struct CYASSL_CERT_MANAGER {
Signer* caList; /* the CA signer list */
CyaSSL_Mutex caLock; /* CA list lock */
CallbackCACache caCacheCallback; /* CA cache addition callback */
void* heap; /* heap helper */
};
/* CyaSSL context type */
struct CYASSL_CTX {
CYASSL_METHOD* method;
@ -612,7 +642,7 @@ struct CYASSL_CTX {
buffer privateKey;
buffer serverDH_P;
buffer serverDH_G;
Signer* caList; /* CYASSL_CTX owns this, SSL will reference */
CYASSL_CERT_MANAGER* cm; /* our cert manager, ctx owns SSL will use */
Suites suites;
void* heap; /* for user memory overrides */
byte verifyPeer;
@ -623,13 +653,13 @@ struct CYASSL_CTX {
byte sendVerify; /* for client side */
byte haveDH; /* server DH parms set by user */
byte haveNTRU; /* server private NTRU key loaded */
byte haveECDSA; /* server private ECDSA key loaded */
byte haveECDSA; /* server cert signed w/ ECDSA loaded */
byte haveStaticECC; /* static server ECC private key */
byte partialWrite; /* only one msg per write call */
byte quietShutdown; /* don't send close notify */
byte groupMessages; /* group handshake messages before sending */
CallbackIORecv CBIORecv;
CallbackIOSend CBIOSend;
CallbackCACache caCacheCallback; /* CA cache addition callback */
VerifyCallback verifyCallback; /* cert verification callback */
word32 timeout; /* session timeout */
#ifdef HAVE_ECC
@ -664,9 +694,9 @@ CYASSL_LOCAL
int ProcessOldClientHello(CYASSL* ssl, const byte* input, word32* inOutIdx,
word32 inSz, word16 sz);
CYASSL_LOCAL
int AddCA(CYASSL_CTX* ctx, buffer der, int force);
int AddCA(CYASSL_CERT_MANAGER* ctx, buffer der, int type, int verify);
CYASSL_LOCAL
int AlreadySigner(CYASSL_CTX* ctx, byte* hash);
int AlreadySigner(CYASSL_CERT_MANAGER* cm, byte* hash);
/* All cipher suite related info */
typedef struct CipherSpecs {
@ -677,6 +707,7 @@ typedef struct CipherSpecs {
byte sig_algo;
byte hash_size;
byte pad_size;
byte static_ecdh;
word16 key_size;
word16 iv_size;
word16 block_size;
@ -939,7 +970,8 @@ typedef struct Options {
byte usingCompression; /* are we using compression */
byte haveDH; /* server DH parms set by user */
byte haveNTRU; /* server NTRU private key loaded */
byte haveECDSA; /* server ECDSA private key loaded */
byte haveECDSA; /* server ECDSA signed cert */
byte haveStaticECC; /* static server ECC private key */
byte havePeerCert; /* do we have peer's cert */
byte usingPSK_cipher; /* whether we're using psk as cipher */
byte sendAlertState; /* nonblocking resume */
@ -1239,7 +1271,7 @@ CYASSL_LOCAL int IsAtLeastTLSv1_2(const CYASSL* ssl);
CYASSL_LOCAL void ShrinkInputBuffer(CYASSL* ssl, int forcedFree);
CYASSL_LOCAL void ShrinkOutputBuffer(CYASSL* ssl);
CYASSL_LOCAL int SendHelloVerifyRequest(CYASSL* ssl);
CYASSL_LOCAL Signer* GetCA(Signer* signers, byte* hash);
CYASSL_LOCAL Signer* GetCA(void* cm, byte* hash);
CYASSL_LOCAL void BuildTlsFinished(CYASSL* ssl, Hashes* hashes,
const byte* sender);
#ifndef NO_TLS

View File

@ -65,6 +65,7 @@ typedef struct CYASSL_X509 CYASSL_X509;
typedef struct CYASSL_X509_NAME CYASSL_X509_NAME;
typedef struct CYASSL_X509_CHAIN CYASSL_X509_CHAIN;
typedef struct CYASSL_CERT_MANAGER CYASSL_CERT_MANAGER;
/* redeclare guard */
#define CYASSL_TYPES_DEFINED
@ -776,6 +777,14 @@ typedef void (*CallbackCACache)(unsigned char* der, int sz, int type);
CYASSL_API void CyaSSL_CTX_SetCACb(CYASSL_CTX*, CallbackCACache);
CYASSL_API CYASSL_CERT_MANAGER* CyaSSL_CertManagerNew(void);
CYASSL_API void CyaSSL_CertManagerFree(CYASSL_CERT_MANAGER*);
CYASSL_API int CyaSSL_CertManagerLoadCA(CYASSL_CERT_MANAGER*, const char* f,
const char* d);
CYASSL_API int CyaSSL_CertManagerVerify(CYASSL_CERT_MANAGER*, const char* f,
int format);
#ifdef CYASSL_CALLBACKS
/* used internally by CyaSSL while OpenSSL types aren't */

View File

@ -335,6 +335,7 @@ int InitSSL_Ctx(CYASSL_CTX* ctx, CYASSL_METHOD* method)
ctx->haveDH = 0;
ctx->haveNTRU = 0; /* start off */
ctx->haveECDSA = 0; /* start off */
ctx->haveStaticECC = 0; /* start off */
ctx->heap = ctx; /* defaults to self */
#ifndef NO_PSK
ctx->havePSK = 0;
@ -363,23 +364,23 @@ int InitSSL_Ctx(CYASSL_CTX* ctx, CYASSL_METHOD* method)
#endif
ctx->partialWrite = 0;
ctx->verifyCallback = 0;
ctx->caCacheCallback = 0;
ctx->caList = 0;
ctx->cm = CyaSSL_CertManagerNew();
#ifdef HAVE_NTRU
if (method->side == CLIENT_END)
ctx->haveNTRU = 1; /* always on cliet side */
/* server can turn on by loading key */
#endif
#ifdef HAVE_ECC
if (method->side == CLIENT_END)
ctx->haveECDSA = 1; /* always on cliet side */
/* server can turn on by loading key */
if (method->side == CLIENT_END) {
ctx->haveECDSA = 1; /* always on cliet side */
ctx->haveStaticECC = 1; /* server can turn on by loading key */
}
#endif
ctx->suites.setSuites = 0; /* user hasn't set yet */
/* remove DH later if server didn't set, add psk later */
InitSuites(&ctx->suites, method->version, TRUE, FALSE, ctx->haveNTRU,
ctx->haveECDSA, method->side);
ctx->haveECDSA, ctx->haveStaticECC, method->side);
ctx->verifyPeer = 0;
ctx->verifyNone = 0;
ctx->failNoCert = 0;
@ -396,6 +397,10 @@ int InitSSL_Ctx(CYASSL_CTX* ctx, CYASSL_METHOD* method)
CYASSL_MSG("Mutex error on CTX init");
return BAD_MUTEX_ERROR;
}
if (ctx->cm == NULL) {
CYASSL_MSG("Bad Cert Manager New");
return BAD_CERT_MANAGER_ERROR;
}
return 0;
}
@ -410,7 +415,7 @@ void SSL_CtxResourceFree(CYASSL_CTX* ctx)
XFREE(ctx->certChain.buffer, ctx->heap, DYNAMIC_TYPE_CERT);
XFREE(ctx->method, ctx->heap, DYNAMIC_TYPE_METHOD);
FreeSigners(ctx->caList, ctx->heap);
CyaSSL_CertManagerFree(ctx->cm);
#ifdef HAVE_OCSP
CyaSSL_OCSP_Cleanup(&ctx->ocsp);
@ -444,7 +449,7 @@ void FreeSSL_Ctx(CYASSL_CTX* ctx)
void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
byte haveNTRU, byte haveECDSA, int side)
byte haveNTRU, byte haveStaticECC, byte haveECDSA, int side)
{
word16 idx = 0;
int tls = pv.major == SSLv3_MAJOR && pv.minor >= TLSv1_MINOR;
@ -502,6 +507,13 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
}
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA
if (tls && haveECDSA && haveStaticECC) {
suites->suites[idx++] = ECC_BYTE;
suites->suites[idx++] = TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA;
}
#endif
#ifdef BUILD_TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA
if (tls && haveECDSA) {
suites->suites[idx++] = ECC_BYTE;
@ -509,6 +521,13 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
}
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
if (tls && haveECDSA && haveStaticECC) {
suites->suites[idx++] = ECC_BYTE;
suites->suites[idx++] = TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA;
}
#endif
#ifdef BUILD_TLS_ECDHE_ECDSA_WITH_RC4_128_SHA
if (tls && haveECDSA) {
suites->suites[idx++] = ECC_BYTE;
@ -516,6 +535,13 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
}
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_RC4_128_SHA
if (tls && haveECDSA && haveStaticECC) {
suites->suites[idx++] = ECC_BYTE;
suites->suites[idx++] = TLS_ECDH_ECDSA_WITH_RC4_128_SHA;
}
#endif
#ifdef BUILD_TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA
if (tls && haveECDSA) {
suites->suites[idx++] = ECC_BYTE;
@ -523,6 +549,13 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
}
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA
if (tls && haveECDSA && haveStaticECC) {
suites->suites[idx++] = ECC_BYTE;
suites->suites[idx++] = TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA;
}
#endif
#ifdef BUILD_TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA
if (tls && haveRSA) {
suites->suites[idx++] = ECC_BYTE;
@ -530,6 +563,13 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
}
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_AES_256_CBC_SHA
if (tls && haveRSA && haveStaticECC) {
suites->suites[idx++] = ECC_BYTE;
suites->suites[idx++] = TLS_ECDH_RSA_WITH_AES_256_CBC_SHA;
}
#endif
#ifdef BUILD_TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA
if (tls && haveRSA) {
suites->suites[idx++] = ECC_BYTE;
@ -537,6 +577,13 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
}
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_AES_128_CBC_SHA
if (tls && haveRSA && haveStaticECC) {
suites->suites[idx++] = ECC_BYTE;
suites->suites[idx++] = TLS_ECDH_RSA_WITH_AES_128_CBC_SHA;
}
#endif
#ifdef BUILD_TLS_ECDHE_RSA_WITH_RC4_128_SHA
if (tls && haveRSA) {
suites->suites[idx++] = ECC_BYTE;
@ -544,6 +591,13 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
}
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_RC4_128_SHA
if (tls && haveRSA && haveStaticECC) {
suites->suites[idx++] = ECC_BYTE;
suites->suites[idx++] = TLS_ECDH_RSA_WITH_RC4_128_SHA;
}
#endif
#ifdef BUILD_TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA
if (tls && haveRSA) {
suites->suites[idx++] = ECC_BYTE;
@ -551,6 +605,13 @@ void InitSuites(Suites* suites, ProtocolVersion pv, byte haveDH, byte havePSK,
}
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA
if (tls && haveRSA && haveStaticECC) {
suites->suites[idx++] = ECC_BYTE;
suites->suites[idx++] = TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA;
}
#endif
#ifdef BUILD_TLS_DHE_RSA_WITH_AES_256_CBC_SHA256
if (tls1_2 && haveDH && haveRSA) {
suites->suites[idx++] = 0;
@ -762,7 +823,8 @@ int InitSSL(CYASSL* ssl, CYASSL_CTX* ctx)
ssl->options.haveDH = 0;
ssl->options.haveNTRU = ctx->haveNTRU;
ssl->options.haveECDSA = ctx->haveECDSA;
ssl->options.havePeerCert = 0;
ssl->options.haveStaticECC = ctx->haveStaticECC;
ssl->options.havePeerCert = 0;
ssl->options.usingPSK_cipher = 0;
ssl->options.sendAlertState = 0;
#ifndef NO_PSK
@ -806,7 +868,7 @@ int InitSSL(CYASSL* ssl, CYASSL_CTX* ctx)
ssl->options.certOnly = 0;
ssl->options.groupMessages = ctx->groupMessages;
/* ctx still owns certificate, certChain, key, dh, and caList buffers */
/* ctx still owns certificate, certChain, key, dh, and cm */
ssl->buffers.certificate = ctx->certificate;
ssl->buffers.certChain = ctx->certChain;
ssl->buffers.key = ctx->privateKey;
@ -849,11 +911,11 @@ int InitSSL(CYASSL* ssl, CYASSL_CTX* ctx)
if (ssl->options.side == SERVER_END)
InitSuites(&ssl->suites, ssl->version,ssl->options.haveDH, havePSK,
ssl->options.haveNTRU, ssl->options.haveECDSA,
ssl->ctx->method->side);
ssl->options.haveStaticECC, ssl->ctx->method->side);
else
InitSuites(&ssl->suites, ssl->version, TRUE, havePSK,
ssl->options.haveNTRU, ssl->options.haveECDSA,
ssl->ctx->method->side);
ssl->options.haveStaticECC, ssl->ctx->method->side);
#ifdef SESSION_CERTS
@ -1561,7 +1623,7 @@ static int DoCertificate(CYASSL* ssl, byte* input, word32* inOutIdx)
InitDecodedCert(&dCert, myCert.buffer, myCert.length, ssl->heap);
ret = ParseCertRelative(&dCert, CERT_TYPE, !ssl->options.verifyNone,
ssl->ctx->caList);
ssl->ctx->cm);
if (ret == 0 && dCert.isCA == 0) {
CYASSL_MSG("Chain cert is not a CA, not adding as one");
(void)ret;
@ -1570,7 +1632,7 @@ static int DoCertificate(CYASSL* ssl, byte* input, word32* inOutIdx)
CYASSL_MSG("Chain cert not verified by option, not adding as CA");
(void)ret;
}
else if (ret == 0 && !AlreadySigner(ssl->ctx, dCert.subjectHash)) {
else if (ret == 0 && !AlreadySigner(ssl->ctx->cm, dCert.subjectHash)) {
buffer add;
add.length = myCert.length;
add.buffer = (byte*)XMALLOC(myCert.length, ssl->heap,
@ -1581,7 +1643,8 @@ static int DoCertificate(CYASSL* ssl, byte* input, word32* inOutIdx)
return MEMORY_E;
XMEMCPY(add.buffer, myCert.buffer, myCert.length);
ret = AddCA(ssl->ctx, add, CYASSL_CHAIN_CA);
ret = AddCA(ssl->ctx->cm, add, CYASSL_CHAIN_CA,
ssl->ctx->verifyPeer);
if (ret == 1) ret = 0; /* SSL_SUCCESS for external */
}
else if (ret != 0) {
@ -1610,7 +1673,7 @@ static int DoCertificate(CYASSL* ssl, byte* input, word32* inOutIdx)
InitDecodedCert(&dCert, myCert.buffer, myCert.length, ssl->heap);
ret = ParseCertRelative(&dCert, CERT_TYPE, !ssl->options.verifyNone,
ssl->ctx->caList);
ssl->ctx->cm);
if (ret == 0) {
CYASSL_MSG("Verified Peer's cert");
fatal = 0;
@ -3434,6 +3497,10 @@ void SetErrorString(int error, char* str)
XSTRNCPY(str, "Bad path for opendir error", max);
break;
case BAD_CERT_MANAGER_ERROR:
XSTRNCPY(str, "Bad Cert Manager error", max);
break;
default :
XSTRNCPY(str, "unknown error number", max);
}
@ -3555,8 +3622,41 @@ const char* const cipher_names[] =
#endif
#ifdef BUILD_TLS_DHE_RSA_WITH_AES_256_CBC_SHA256
"DHE-RSA-AES256-SHA256"
"DHE-RSA-AES256-SHA256",
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_AES_128_CBC_SHA
"ECDH-RSA-AES128-SHA",
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_AES_256_CBC_SHA
"ECDH-RSA-AES256-SHA",
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
"ECDH-ECDSA-AES128-SHA",
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA
"ECDH-ECDSA-AES256-SHA",
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_RC4_128_SHA
"ECDH-RSA-RC4-SHA",
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA
"ECDH-RSA-DES-CBC3-SHA",
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_RC4_128_SHA
"ECDH-ECDSA-RC4-SHA",
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA
"ECDH-ECDSA-DES-CBC3-SHA"
#endif
};
@ -3674,8 +3774,41 @@ int cipher_name_idx[] =
#endif
#ifdef BUILD_TLS_DHE_RSA_WITH_AES_256_CBC_SHA256
TLS_DHE_RSA_WITH_AES_256_CBC_SHA256
TLS_DHE_RSA_WITH_AES_256_CBC_SHA256,
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_AES_128_CBC_SHA
TLS_ECDH_RSA_WITH_AES_128_CBC_SHA,
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_AES_256_CBC_SHA
TLS_ECDH_RSA_WITH_AES_256_CBC_SHA,
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA
TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA,
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_RC4_128_SHA
TLS_ECDH_RSA_WITH_RC4_128_SHA,
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA
TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA,
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_RC4_128_SHA
TLS_ECDH_ECDSA_WITH_RC4_128_SHA,
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA
TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA
#endif
};
@ -4079,6 +4212,7 @@ int SetCipherList(Suites* s, const char* list)
return ret;
}
else
CYASSL_MSG("Unsupported cipher suite, DoServerHello");
return UNSUPPORTED_SUITE;
}
else {
@ -4460,14 +4594,24 @@ int SetCipherList(Suites* s, const char* list)
#endif /* HAVE_NTRU */
#ifdef HAVE_ECC
} else if (ssl->specs.kea == ecc_diffie_hellman_kea) {
ecc_key myKey;
word32 size = sizeof(encSecret);
ecc_key myKey;
ecc_key* peerKey = &myKey;
word32 size = sizeof(encSecret);
if (!ssl->peerEccKeyPresent || !ssl->peerEccKey.dp)
return NO_PEER_KEY;
if (ssl->specs.static_ecdh) {
/* TODO: EccDsa is really fixed Ecc change naming */
if (!ssl->peerEccDsaKeyPresent || !ssl->peerEccDsaKey.dp)
return NO_PEER_KEY;
peerKey = &ssl->peerEccDsaKey;
}
else {
if (!ssl->peerEccKeyPresent || !ssl->peerEccKey.dp)
return NO_PEER_KEY;
peerKey = &ssl->peerEccKey;
}
ecc_init(&myKey);
ret = ecc_make_key(&ssl->rng, ssl->peerEccKey.dp->size, &myKey);
ret = ecc_make_key(&ssl->rng, peerKey->dp->size, &myKey);
if (ret != 0)
return ECC_MAKEKEY_ERROR;
@ -4480,7 +4624,7 @@ int SetCipherList(Suites* s, const char* list)
ret = ECC_EXPORT_ERROR;
else {
size = sizeof(ssl->arrays.preMasterSecret);
ret = ecc_shared_secret(&myKey, &ssl->peerEccKey,
ret = ecc_shared_secret(&myKey, peerKey,
ssl->arrays.preMasterSecret, &size);
if (ret != 0)
ret = ECC_SHARED_ERROR;
@ -4891,9 +5035,15 @@ int SetCipherList(Suites* s, const char* list)
RsaKey rsaKey;
ecc_key dsaKey;
if (ssl->specs.static_ecdh) {
CYASSL_MSG("Using Static ECDH, not sending ServerKeyExchagne");
return 0;
}
/* curve type, named curve, length(1) */
length = ENUM_LEN + CURVE_LEN + ENUM_LEN;
/* pub key size */
CYASSL_MSG("Using ephemeral ECDH");
if (ecc_export_x963(&ssl->eccTempKey, exportBuf, &expSz) != 0)
return ECC_EXPORT_ERROR;
length += expSz;
@ -5016,6 +5166,7 @@ int SetCipherList(Suites* s, const char* list)
ret = RsaSSL_Sign(signBuffer, signSz, output + idx, sigSz,
&rsaKey, &ssl->rng);
FreeRsaKey(&rsaKey);
ecc_free(&dsaKey);
if (ret > 0)
ret = 0; /* reset on success */
else
@ -5024,9 +5175,10 @@ int SetCipherList(Suites* s, const char* list)
else if (ssl->specs.sig_algo == ecc_dsa_sa_algo) {
word32 sz = sigSz;
FreeRsaKey(&rsaKey);
ret = ecc_sign_hash(&hash[MD5_DIGEST_SIZE], SHA_DIGEST_SIZE,
output + idx, &sz, &ssl->rng, &dsaKey);
FreeRsaKey(&rsaKey);
ecc_free(&dsaKey);
if (ret < 0) return ret;
}
}
@ -5334,7 +5486,7 @@ int SetCipherList(Suites* s, const char* list)
InitSuites(&ssl->suites, ssl->version, ssl->options.haveDH, havePSK,
ssl->options.haveNTRU, ssl->options.haveECDSA,
ssl->ctx->method->side);
ssl->options.haveStaticECC, ssl->ctx->method->side);
}
/* suite size */
@ -5397,8 +5549,10 @@ int SetCipherList(Suites* s, const char* list)
ssl->options.resuming = 0;
break; /* session lookup failed */
}
if (MatchSuite(ssl, &clSuites) < 0)
if (MatchSuite(ssl, &clSuites) < 0) {
CYASSL_MSG("Unsupported cipher suite, OldClientHello");
return UNSUPPORTED_SUITE;
}
RNG_GenerateBlock(&ssl->rng, ssl->arrays.serverRandom, RAN_LEN);
if (ssl->options.tls)
@ -5462,7 +5616,7 @@ int SetCipherList(Suites* s, const char* list)
#endif
InitSuites(&ssl->suites, ssl->version, ssl->options.haveDH, havePSK,
ssl->options.haveNTRU, ssl->options.haveECDSA,
ssl->ctx->method->side);
ssl->options.haveStaticECC, ssl->ctx->method->side);
}
/* random */
XMEMCPY(ssl->arrays.clientRandom, input + i, RAN_LEN);
@ -5551,8 +5705,10 @@ int SetCipherList(Suites* s, const char* list)
CYASSL_MSG("Session lookup for resume failed");
break; /* session lookup failed */
}
if (MatchSuite(ssl, &clSuites) < 0)
if (MatchSuite(ssl, &clSuites) < 0) {
CYASSL_MSG("Unsupported cipher suite, ClientHello");
return UNSUPPORTED_SUITE;
}
RNG_GenerateBlock(&ssl->rng, ssl->arrays.serverRandom, RAN_LEN);
if (ssl->options.tls)
@ -5850,7 +6006,20 @@ int SetCipherList(Suites* s, const char* list)
ssl->peerEccKeyPresent = 1;
size = sizeof(ssl->arrays.preMasterSecret);
ret = ecc_shared_secret(&ssl->eccTempKey, &ssl->peerEccKey,
if (ssl->specs.static_ecdh) {
ecc_key staticKey;
word32 i = 0;
ecc_init(&staticKey);
ret = EccPrivateKeyDecode(ssl->buffers.key.buffer, &i,
&staticKey, ssl->buffers.key.length);
if (ret == 0)
ret = ecc_shared_secret(&staticKey, &ssl->peerEccKey,
ssl->arrays.preMasterSecret, &size);
ecc_free(&staticKey);
}
else
ret = ecc_shared_secret(&ssl->eccTempKey, &ssl->peerEccKey,
ssl->arrays.preMasterSecret, &size);
if (ret != 0)
return ECC_SHARED_ERROR;

View File

@ -48,6 +48,24 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
break;
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_AES_128_CBC_SHA
case TLS_ECDH_RSA_WITH_AES_128_CBC_SHA :
ssl->specs.bulk_cipher_algorithm = aes;
ssl->specs.cipher_type = block;
ssl->specs.mac_algorithm = sha_mac;
ssl->specs.kea = ecc_diffie_hellman_kea;
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 1;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -64,6 +82,24 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = DES3_KEY_SIZE;
ssl->specs.block_size = DES_BLOCK_SIZE;
ssl->specs.iv_size = DES_IV_SIZE;
break;
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA
case TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA :
ssl->specs.bulk_cipher_algorithm = triple_des;
ssl->specs.cipher_type = block;
ssl->specs.mac_algorithm = sha_mac;
ssl->specs.kea = ecc_diffie_hellman_kea;
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 1;
ssl->specs.key_size = DES3_KEY_SIZE;
ssl->specs.block_size = DES_BLOCK_SIZE;
ssl->specs.iv_size = DES_IV_SIZE;
@ -80,6 +116,24 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = RC4_KEY_SIZE;
ssl->specs.iv_size = 0;
ssl->specs.block_size = 0;
break;
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_RC4_128_SHA
case TLS_ECDH_RSA_WITH_RC4_128_SHA :
ssl->specs.bulk_cipher_algorithm = rc4;
ssl->specs.cipher_type = stream;
ssl->specs.mac_algorithm = sha_mac;
ssl->specs.kea = ecc_diffie_hellman_kea;
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 1;
ssl->specs.key_size = RC4_KEY_SIZE;
ssl->specs.iv_size = 0;
ssl->specs.block_size = 0;
@ -96,6 +150,24 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = ecc_dsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = DES3_KEY_SIZE;
ssl->specs.block_size = DES_BLOCK_SIZE;
ssl->specs.iv_size = DES_IV_SIZE;
break;
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA
case TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA :
ssl->specs.bulk_cipher_algorithm = triple_des;
ssl->specs.cipher_type = block;
ssl->specs.mac_algorithm = sha_mac;
ssl->specs.kea = ecc_diffie_hellman_kea;
ssl->specs.sig_algo = ecc_dsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 1;
ssl->specs.key_size = DES3_KEY_SIZE;
ssl->specs.block_size = DES_BLOCK_SIZE;
ssl->specs.iv_size = DES_IV_SIZE;
@ -112,6 +184,24 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = ecc_dsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = RC4_KEY_SIZE;
ssl->specs.iv_size = 0;
ssl->specs.block_size = 0;
break;
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_RC4_128_SHA
case TLS_ECDH_ECDSA_WITH_RC4_128_SHA :
ssl->specs.bulk_cipher_algorithm = rc4;
ssl->specs.cipher_type = stream;
ssl->specs.mac_algorithm = sha_mac;
ssl->specs.kea = ecc_diffie_hellman_kea;
ssl->specs.sig_algo = ecc_dsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 1;
ssl->specs.key_size = RC4_KEY_SIZE;
ssl->specs.iv_size = 0;
ssl->specs.block_size = 0;
@ -128,6 +218,24 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
break;
#endif
#ifdef BUILD_TLS_ECDH_RSA_WITH_AES_256_CBC_SHA
case TLS_ECDH_RSA_WITH_AES_256_CBC_SHA :
ssl->specs.bulk_cipher_algorithm = aes;
ssl->specs.cipher_type = block;
ssl->specs.mac_algorithm = sha_mac;
ssl->specs.kea = ecc_diffie_hellman_kea;
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 1;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -144,6 +252,24 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = ecc_dsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
break;
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
case TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA :
ssl->specs.bulk_cipher_algorithm = aes;
ssl->specs.cipher_type = block;
ssl->specs.mac_algorithm = sha_mac;
ssl->specs.kea = ecc_diffie_hellman_kea;
ssl->specs.sig_algo = ecc_dsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 1;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -160,6 +286,24 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = ecc_dsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
break;
#endif
#ifdef BUILD_TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA
case TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA :
ssl->specs.bulk_cipher_algorithm = aes;
ssl->specs.cipher_type = block;
ssl->specs.mac_algorithm = sha_mac;
ssl->specs.kea = ecc_diffie_hellman_kea;
ssl->specs.sig_algo = ecc_dsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 1;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -168,6 +312,7 @@ int SetCipherSpecs(CYASSL* ssl)
#endif
default:
CYASSL_MSG("Unsupported cipher suite, SetCipherSpecs ECC");
return UNSUPPORTED_SUITE;
} /* switch */
} /* if */
@ -183,6 +328,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = RC4_KEY_SIZE;
ssl->specs.iv_size = 0;
ssl->specs.block_size = 0;
@ -198,6 +344,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = ntru_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = RC4_KEY_SIZE;
ssl->specs.iv_size = 0;
ssl->specs.block_size = 0;
@ -213,6 +360,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = MD5_DIGEST_SIZE;
ssl->specs.pad_size = PAD_MD5;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = RC4_KEY_SIZE;
ssl->specs.iv_size = 0;
ssl->specs.block_size = 0;
@ -228,6 +376,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = DES3_KEY_SIZE;
ssl->specs.block_size = DES_BLOCK_SIZE;
ssl->specs.iv_size = DES_IV_SIZE;
@ -243,6 +392,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = ntru_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = DES3_KEY_SIZE;
ssl->specs.block_size = DES_BLOCK_SIZE;
ssl->specs.iv_size = DES_IV_SIZE;
@ -258,6 +408,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -273,6 +424,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = SHA256_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -288,6 +440,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = ntru_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -303,6 +456,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -318,6 +472,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = SHA256_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -333,6 +488,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = ntru_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -348,6 +504,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = psk_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -364,6 +521,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = psk_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -381,6 +539,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA256_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -397,6 +556,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA256_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -413,6 +573,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_128_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -429,6 +590,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.sig_algo = rsa_sa_algo;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = AES_256_KEY_SIZE;
ssl->specs.block_size = AES_BLOCK_SIZE;
ssl->specs.iv_size = AES_IV_SIZE;
@ -444,6 +606,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = MD5_DIGEST_SIZE;
ssl->specs.pad_size = PAD_MD5;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = HC_128_KEY_SIZE;
ssl->specs.block_size = 0;
ssl->specs.iv_size = HC_128_IV_SIZE;
@ -459,6 +622,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = HC_128_KEY_SIZE;
ssl->specs.block_size = 0;
ssl->specs.iv_size = HC_128_IV_SIZE;
@ -474,6 +638,7 @@ int SetCipherSpecs(CYASSL* ssl)
ssl->specs.kea = rsa_kea;
ssl->specs.hash_size = SHA_DIGEST_SIZE;
ssl->specs.pad_size = PAD_SHA;
ssl->specs.static_ecdh = 0;
ssl->specs.key_size = RABBIT_KEY_SIZE;
ssl->specs.block_size = 0;
ssl->specs.iv_size = RABBIT_IV_SIZE;
@ -482,7 +647,7 @@ int SetCipherSpecs(CYASSL* ssl)
#endif
default:
CYASSL_MSG("Unsupported cipher suite");
CYASSL_MSG("Unsupported cipher suite, SetCipherSpecs");
return UNSUPPORTED_SUITE;
} /* switch */
} /* if ECC / Normal suites else */

267
src/ssl.c
View File

@ -227,7 +227,7 @@ int CyaSSL_SetTmpDH(CYASSL* ssl, const unsigned char* p, int pSz,
#endif
InitSuites(&ssl->suites, ssl->version, ssl->options.haveDH,
havePSK, ssl->options.haveNTRU, ssl->options.haveECDSA,
ssl->ctx->method->side);
ssl->options.haveStaticECC, ssl->ctx->method->side);
CYASSL_LEAVE("CyaSSL_SetTmpDH", 0);
return 0;
@ -362,6 +362,45 @@ void CyaSSL_ERR_error_string_n(unsigned long e, char* buf, unsigned long len)
}
CYASSL_CERT_MANAGER* CyaSSL_CertManagerNew(void)
{
CYASSL_CERT_MANAGER* cm = NULL;
CYASSL_ENTER("CyaSSL_CertManagerNew");
cm = (CYASSL_CERT_MANAGER*) XMALLOC(sizeof(CYASSL_CERT_MANAGER), 0,
DYNAMIC_TYPE_CERT_MANAGER);
if (cm) {
cm->caList = NULL;
cm->heap = NULL;
cm->caCacheCallback = NULL;
if (InitMutex(&cm->caLock) != 0) {
CYASSL_MSG("Bad mutex init");
CyaSSL_CertManagerFree(cm);
return NULL;
}
}
return cm;
}
void CyaSSL_CertManagerFree(CYASSL_CERT_MANAGER* cm)
{
CYASSL_ENTER("CyaSSL_CertManagerFree");
if (cm) {
FreeSigners(cm->caList, NULL);
FreeMutex(&cm->caLock);
XFREE(cm, NULL, DYNAMIC_TYPE_CERT_MANAGER);
}
}
#ifndef NO_FILESYSTEM
void CyaSSL_ERR_print_errors_fp(FILE* fp, int err)
@ -395,6 +434,7 @@ int CyaSSL_CTX_set_group_messages(CYASSL_CTX* ctx)
}
#ifndef NO_CYASSL_CLIENT
/* connect enough to get peer cert chain */
int CyaSSL_connect_cert(CYASSL* ssl)
{
@ -409,6 +449,7 @@ int CyaSSL_connect_cert(CYASSL* ssl)
return ret;
}
#endif
/* trun on handshake group messages for ssl object */
@ -423,17 +464,15 @@ int CyaSSL_set_group_messages(CYASSL* ssl)
}
static CyaSSL_Mutex ca_mutex; /* CA signers mutex */
/* does CA already exist on signer list */
int AlreadySigner(CYASSL_CTX* ctx, byte* hash)
int AlreadySigner(CYASSL_CERT_MANAGER* cm, byte* hash)
{
Signer* signers;
int ret = 0;
if (LockMutex(&ca_mutex) != 0)
if (LockMutex(&cm->caLock) != 0)
return ret;
signers = ctx->caList;
signers = cm->caList;
while (signers) {
if (XMEMCMP(hash, signers->hash, SHA_DIGEST_SIZE) == 0) {
ret = 1;
@ -441,18 +480,25 @@ int AlreadySigner(CYASSL_CTX* ctx, byte* hash)
}
signers = signers->next;
}
UnLockMutex(&ca_mutex);
UnLockMutex(&cm->caLock);
return ret;
}
/* return CA if found, otherwise NULL */
Signer* GetCA(Signer* signers, byte* hash)
Signer* GetCA(void* vp, byte* hash)
{
Signer* ret = 0;
CYASSL_CERT_MANAGER* cm = (CYASSL_CERT_MANAGER*)vp;
Signer* ret = NULL;
Signer* signers;
if (LockMutex(&ca_mutex) != 0)
if (cm == NULL)
return NULL;
signers = cm->caList;
if (LockMutex(&cm->caLock) != 0)
return ret;
while (signers) {
if (XMEMCMP(hash, signers->hash, SHA_DIGEST_SIZE) == 0) {
@ -461,7 +507,7 @@ Signer* GetCA(Signer* signers, byte* hash)
}
signers = signers->next;
}
UnLockMutex(&ca_mutex);
UnLockMutex(&cm->caLock);
return ret;
}
@ -470,28 +516,28 @@ Signer* GetCA(Signer* signers, byte* hash)
/* owns der, internal now uses too */
/* type flag ids from user or from chain received during verify
don't allow chain ones to be added w/o isCA extension */
int AddCA(CYASSL_CTX* ctx, buffer der, int type)
int AddCA(CYASSL_CERT_MANAGER* cm, buffer der, int type, int verify)
{
int ret;
DecodedCert cert;
Signer* signer = 0;
CYASSL_MSG("Adding a CA");
InitDecodedCert(&cert, der.buffer, der.length, ctx->heap);
ret = ParseCert(&cert, CA_TYPE, ctx->verifyPeer, 0);
InitDecodedCert(&cert, der.buffer, der.length, cm->heap);
ret = ParseCert(&cert, CA_TYPE, verify, cm);
CYASSL_MSG(" Parsed new CA");
if (ret == 0 && cert.isCA == 0 && type != CYASSL_USER_CA) {
CYASSL_MSG(" Can't add as CA if not actually one");
ret = NOT_CA_ERROR;
}
else if (ret == 0 && AlreadySigner(ctx, cert.subjectHash)) {
else if (ret == 0 && AlreadySigner(cm, cert.subjectHash)) {
CYASSL_MSG(" Already have this CA, not adding again");
(void)ret;
}
else if (ret == 0) {
/* take over signer parts */
signer = MakeSigner(ctx->heap);
signer = MakeSigner(cm->heap);
if (!signer)
ret = MEMORY_ERROR;
else {
@ -505,17 +551,17 @@ int AddCA(CYASSL_CTX* ctx, buffer der, int type)
cert.publicKey = 0; /* don't free here */
cert.subjectCN = 0;
if (LockMutex(&ca_mutex) == 0) {
signer->next = ctx->caList;
ctx->caList = signer; /* takes ownership */
UnLockMutex(&ca_mutex);
if (ctx->caCacheCallback)
ctx->caCacheCallback(der.buffer, (int)der.length, type);
if (LockMutex(&cm->caLock) == 0) {
signer->next = cm->caList;
cm->caList = signer; /* takes ownership */
UnLockMutex(&cm->caLock);
if (cm->caCacheCallback)
cm->caCacheCallback(der.buffer, (int)der.length, type);
}
else {
CYASSL_MSG(" CA Mutex Lock failed");
ret = BAD_MUTEX_ERROR;
FreeSigners(signer, ctx->heap);
FreeSigners(signer, cm->heap);
}
}
}
@ -932,7 +978,8 @@ int AddCA(CYASSL_CTX* ctx, buffer der, int type)
#endif /* OPENSSL_EXTRA || HAVE_WEBSERVER */
if (type == CA_TYPE)
return AddCA(ctx, der, CYASSL_USER_CA); /* takes der over */
return AddCA(ctx->cm, der, CYASSL_USER_CA, ctx->verifyPeer);
/* takes der over */
else if (type == CERT_TYPE) {
if (ssl) {
if (ssl->buffers.weOwnCert && ssl->buffers.certificate.buffer)
@ -996,10 +1043,37 @@ int AddCA(CYASSL_CTX* ctx, buffer der, int type)
return SSL_BAD_FILE;
}
ecc_free(&key);
ctx->haveECDSA = 1;
ctx->haveStaticECC = 1;
if (ssl)
ssl->options.haveStaticECC = 1;
}
#endif /* HAVE_ECC */
}
else if (type == CERT_TYPE) {
int ret;
DecodedCert cert;
CYASSL_MSG("Checking cert signature type");
InitDecodedCert(&cert, der.buffer, der.length, ctx->heap);
if ((ret = DecodeToKey(&cert, 0)) < 0) {
CYASSL_MSG("Decode to key failed");
return SSL_BAD_FILE;
}
switch (cert.signatureOID) {
case CTC_SHAwECDSA:
case CTC_SHA256wECDSA:
case CTC_SHA384wECDSA:
case CTC_SHA512wECDSA:
CYASSL_MSG("ECDSA cert signature");
ctx->haveECDSA = 1;
if (ssl)
ssl->options.haveECDSA = 1;
break;
}
FreeDecodedCert(&cert);
}
return SSL_SUCCESS;
}
@ -1174,6 +1248,105 @@ int CyaSSL_CTX_load_verify_locations(CYASSL_CTX* ctx, const char* file,
}
/* Verify the ceritficate, 1 for success, < 0 for error */
int CyaSSL_CertManagerVerify(CYASSL_CERT_MANAGER* cm, const char* fname,
int format)
{
int ret = SSL_FATAL_ERROR;
int eccKey = 0; /* not used */
DecodedCert cert;
byte staticBuffer[FILE_BUFFER_SIZE];
byte* myBuffer = staticBuffer;
int dynamic = 0;
long sz = 0;
buffer der;
XFILE* file = XFOPEN(fname, "rb");
if (!file) return SSL_BAD_FILE;
XFSEEK(file, 0, XSEEK_END);
sz = XFTELL(file);
XREWIND(file);
der.buffer = NULL;
if (sz > (long)sizeof(staticBuffer)) {
CYASSL_MSG("Getting dynamic buffer");
myBuffer = (byte*) XMALLOC(sz, cm->heap, DYNAMIC_TYPE_FILE);
if (myBuffer == NULL) {
XFCLOSE(file);
return SSL_BAD_FILE;
}
dynamic = 1;
}
if ( (ret = XFREAD(myBuffer, sz, 1, file)) < 0)
ret = SSL_BAD_FILE;
else {
ret = 0; /* ok */
if (format == SSL_FILETYPE_PEM) {
EncryptedInfo info;
info.set = 0;
info.ctx = NULL;
info.consumed = 0;
ret = PemToDer(myBuffer, sz, CERT_TYPE, &der, cm->heap, &info,
&eccKey);
InitDecodedCert(&cert, der.buffer, der.length, cm->heap);
}
else
InitDecodedCert(&cert, myBuffer, sz, cm->heap);
if (ret == 0)
ret = ParseCertRelative(&cert, CERT_TYPE, 1, cm);
}
FreeDecodedCert(&cert);
XFREE(der.buffer, cm->heap, DYNAMIC_TYPE_CERT);
XFCLOSE(file);
if (dynamic) XFREE(myBuffer, ctx->heap, DYNAMIC_TYPE_FILE);
if (ret == 0)
return SSL_SUCCESS;
return ret;
}
/* like load verify locations, 1 for success, < 0 for error */
int CyaSSL_CertManagerLoadCA(CYASSL_CERT_MANAGER* cm, const char* file,
const char* path)
{
int ret = SSL_FATAL_ERROR;
CYASSL_CTX* tmp;
CYASSL_ENTER("CyaSSL_CertManagerLoadCA");
if (cm == NULL) {
CYASSL_MSG("No CertManager error");
return ret;
}
tmp = CyaSSL_CTX_new(CyaSSLv3_client_method());
if (tmp == NULL) {
CYASSL_MSG("CTX new failed");
return ret;
}
/* for tmp use */
CyaSSL_CertManagerFree(tmp->cm);
tmp->cm = cm;
ret = CyaSSL_CTX_load_verify_locations(tmp, file, path);
/* don't loose our good one */
tmp->cm = NULL;
CyaSSL_CTX_free(tmp);
return ret;
}
#ifdef CYASSL_DER_LOAD
/* Add format parameter to allow DER load of CA files */
@ -1553,8 +1726,8 @@ void CyaSSL_set_verify(CYASSL* ssl, int mode, VerifyCallback vc)
/* store context CA Cache addition callback */
void CyaSSL_CTX_SetCACb(CYASSL_CTX* ctx, CallbackCACache cb)
{
if (ctx && cb)
ctx->caCacheCallback = cb;
if (ctx && ctx->cm)
ctx->cm->caCacheCallback = cb;
}
@ -1633,7 +1806,7 @@ int CyaSSL_set_cipher_list(CYASSL* ssl, const char* list)
InitSuites(&ssl->suites, ssl->version, ssl->options.haveDH, havePSK,
ssl->options.haveNTRU, ssl->options.haveECDSA,
ssl->ctx->method->side);
ssl->options.haveStaticECC, ssl->ctx->method->side);
return SSL_SUCCESS;
}
@ -2099,6 +2272,7 @@ int CyaSSL_set_cipher_list(CYASSL* ssl, const char* list)
/* prevent multiple mutex initializations */
static volatile int initRefCount = 0;
static CyaSSL_Mutex count_mutex; /* init ref count mutex */
int CyaSSL_Init(void)
{
@ -2111,13 +2285,13 @@ int CyaSSL_Init(void)
if (InitMutex(&session_mutex) != 0)
ret = BAD_MUTEX_ERROR;
#endif
if (InitMutex(&ca_mutex) != 0)
if (InitMutex(&count_mutex) != 0)
ret = BAD_MUTEX_ERROR;
}
if (ret == 0) {
LockMutex(&ca_mutex);
LockMutex(&count_mutex);
initRefCount++;
UnLockMutex(&ca_mutex);
UnLockMutex(&count_mutex);
}
return ret;
@ -2131,13 +2305,13 @@ int CyaSSL_Cleanup(void)
CYASSL_ENTER("CyaSSL_Cleanup");
LockMutex(&ca_mutex);
LockMutex(&count_mutex);
release = initRefCount-- == 1;
if (initRefCount < 0)
initRefCount = 0;
UnLockMutex(&ca_mutex);
UnLockMutex(&count_mutex);
if (!release)
return ret;
@ -2146,7 +2320,7 @@ int CyaSSL_Cleanup(void)
if (FreeMutex(&session_mutex) != 0)
ret = BAD_MUTEX_ERROR;
#endif
if (FreeMutex(&ca_mutex) != 0)
if (FreeMutex(&count_mutex) != 0)
ret = BAD_MUTEX_ERROR;
return ret;
@ -2649,7 +2823,8 @@ int CyaSSL_set_compression(CYASSL* ssl)
ssl->options.client_psk_cb = cb;
InitSuites(&ssl->suites, ssl->version,TRUE,TRUE, ssl->options.haveNTRU,
ssl->options.haveECDSA, ssl->ctx->method->side);
ssl->options.haveECDSA, ssl->options.haveStaticECC,
ssl->ctx->method->side);
}
@ -2670,7 +2845,7 @@ int CyaSSL_set_compression(CYASSL* ssl)
InitSuites(&ssl->suites, ssl->version, ssl->options.haveDH, TRUE,
ssl->options.haveNTRU, ssl->options.haveECDSA,
ssl->ctx->method->side);
ssl->optoins.haveStaticECC, ssl->ctx->method->side);
}
@ -2904,7 +3079,7 @@ int CyaSSL_set_compression(CYASSL* ssl)
#endif
InitSuites(&ssl->suites, ssl->version, ssl->options.haveDH, havePSK,
ssl->options.haveNTRU, ssl->options.haveECDSA,
ssl->ctx->method->side);
ssl->options.haveStaticECC, ssl->ctx->method->side);
}
@ -4365,6 +4540,24 @@ int CyaSSL_set_compression(CYASSL* ssl)
return "TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA";
case TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA :
return "TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA";
case TLS_ECDH_RSA_WITH_AES_128_CBC_SHA :
return "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA";
case TLS_ECDH_RSA_WITH_AES_256_CBC_SHA :
return "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA";
case TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA :
return "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA";
case TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA :
return "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA";
case TLS_ECDH_RSA_WITH_RC4_128_SHA :
return "TLS_ECDH_RSA_WITH_RC4_128_SHA";
case TLS_ECDH_ECDSA_WITH_RC4_128_SHA :
return "TLS_ECDH_ECDSA_WITH_RC4_128_SHA";
case TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA :
return "TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA";
case TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA :
return "TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA";
default:
return "NONE";
}