summaryrefslogtreecommitdiff
path: root/release/src/router/cyassl/include/cyassl_int.h
diff options
context:
space:
mode:
Diffstat (limited to 'release/src/router/cyassl/include/cyassl_int.h')
-rw-r--r--release/src/router/cyassl/include/cyassl_int.h1225
1 files changed, 1225 insertions, 0 deletions
diff --git a/release/src/router/cyassl/include/cyassl_int.h b/release/src/router/cyassl/include/cyassl_int.h
new file mode 100644
index 00000000..68423755
--- /dev/null
+++ b/release/src/router/cyassl/include/cyassl_int.h
@@ -0,0 +1,1225 @@
+/* cyassl_int.h
+ *
+ * Copyright (C) 2006-2011 Sawtooth Consulting Ltd.
+ *
+ * This file is part of CyaSSL.
+ *
+ * CyaSSL 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.
+ *
+ * CyaSSL 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
+ */
+
+
+
+#ifndef CYASSL_INT_H
+#define CYASSL_INT_H
+
+
+#include "types.h"
+#include "random.h"
+#include "des3.h"
+#include "hc128.h"
+#include "rabbit.h"
+#include "asn.h"
+#include "ctc_md5.h"
+#include "ctc_aes.h"
+#ifdef HAVE_ECC
+ #include "ctc_ecc.h"
+#endif
+#ifndef NO_SHA256
+ #include "sha256.h"
+#endif
+
+#ifdef CYASSL_CALLBACKS
+ #include "cyassl_callbacks.h"
+ #include <signal.h>
+#endif
+
+#ifdef USE_WINDOWS_API
+ #include <windows.h>
+#elif defined(THREADX)
+ #ifndef SINGLE_THREADED
+ #include "tx_api.h"
+ #endif
+#elif defined(MICRIUM)
+ /* do nothing, just don't pick Unix */
+#else
+ #ifndef SINGLE_THREADED
+ #define CYASSL_PTHREADS
+ #include <pthread.h>
+ #endif
+ #if defined(OPENSSL_EXTRA) || defined(GOAHEAD_WS)
+ #include <unistd.h> /* for close of BIO */
+ #endif
+#endif
+
+#ifdef HAVE_LIBZ
+ #include "zlib.h"
+#endif
+
+#ifdef _MSC_VER
+ /* 4996 warning to use MS extensions e.g., strcpy_s instead of strncpy */
+ #pragma warning(disable: 4996)
+#endif
+
+#ifdef NO_AES
+ #if !defined (ALIGN16)
+ #define ALIGN16
+ #endif
+#endif
+
+#ifdef __cplusplus
+ extern "C" {
+#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
+ make sure to use at least one BUILD_SSL_xxx or BUILD_TLS_xxx is defined
+
+ When adding cipher suites, add name to cipher_names, idx to cipher_name_idx
+*/
+#ifndef NO_RC4
+ #define BUILD_SSL_RSA_WITH_RC4_128_SHA
+ #define BUILD_SSL_RSA_WITH_RC4_128_MD5
+ #if !defined(NO_TLS) && defined(HAVE_NTRU)
+ #define BUILD_TLS_NTRU_RSA_WITH_RC4_128_SHA
+ #endif
+#endif
+
+#ifndef NO_DES3
+ #define BUILD_SSL_RSA_WITH_3DES_EDE_CBC_SHA
+ #if !defined(NO_TLS) && defined(HAVE_NTRU)
+ #define BUILD_TLS_NTRU_RSA_WITH_3DES_EDE_CBC_SHA
+ #endif
+#endif
+
+#if !defined(NO_AES) && !defined(NO_TLS)
+ #define BUILD_TLS_RSA_WITH_AES_128_CBC_SHA
+ #define BUILD_TLS_RSA_WITH_AES_256_CBC_SHA
+ #if !defined (NO_PSK)
+ #define BUILD_TLS_PSK_WITH_AES_128_CBC_SHA
+ #define BUILD_TLS_PSK_WITH_AES_256_CBC_SHA
+ #endif
+ #if defined(HAVE_NTRU)
+ #define BUILD_TLS_NTRU_RSA_WITH_AES_128_CBC_SHA
+ #define BUILD_TLS_NTRU_RSA_WITH_AES_256_CBC_SHA
+ #endif
+#endif
+
+#if !defined(NO_HC128) && !defined(NO_TLS)
+ #define BUILD_TLS_RSA_WITH_HC_128_CBC_MD5
+ #define BUILD_TLS_RSA_WITH_HC_128_CBC_SHA
+#endif
+
+#if !defined(NO_RABBIT) && !defined(NO_TLS)
+ #define BUILD_TLS_RSA_WITH_RABBIT_CBC_SHA
+#endif
+
+#if !defined(NO_DH) && !defined(NO_AES) && !defined(NO_TLS) && defined(OPENSSL_EXTRA)
+ #define BUILD_TLS_DHE_RSA_WITH_AES_128_CBC_SHA
+ #define BUILD_TLS_DHE_RSA_WITH_AES_256_CBC_SHA
+#endif
+
+#if defined(HAVE_ECC) && !defined(NO_TLS)
+ #if !defined(NO_AES)
+ #define BUILD_TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA
+ #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
+ #endif
+ #if !defined(NO_RC4)
+ #define BUILD_TLS_ECDHE_RSA_WITH_RC4_128_SHA
+ #define BUILD_TLS_ECDHE_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
+ #endif
+#endif
+
+
+#if defined(BUILD_SSL_RSA_WITH_RC4_128_SHA) || \
+ defined(BUILD_SSL_RSA_WITH_RC4_128_MD5)
+ #define BUILD_ARC4
+#endif
+
+#if defined(BUILD_SSL_RSA_WITH_3DES_EDE_CBC_SHA)
+ #define BUILD_DES3
+#endif
+
+#if defined(BUILD_TLS_RSA_WITH_AES_128_CBC_SHA) || \
+ defined(BUILD_TLS_RSA_WITH_AES_256_CBC_SHA)
+ #define BUILD_AES
+#endif
+
+#if defined(BUILD_TLS_RSA_WITH_HC_128_CBC_SHA) || \
+ defined(BUILD_TLS_RSA_WITH_HC_128_CBC_MD5)
+ #define BUILD_HC128
+#endif
+
+#if defined(BUILD_TLS_RSA_WITH_RABBIT_CBC_SHA)
+ #define BUILD_RABBIT
+#endif
+
+#ifdef NO_DES3
+ #define DES_BLOCK_SIZE 8
+#endif
+
+#ifdef NO_AES
+ #define AES_BLOCK_SIZE 16
+#endif
+
+
+/* actual cipher values, 2nd byte */
+enum {
+ TLS_DHE_RSA_WITH_AES_256_CBC_SHA = 0x39,
+ TLS_DHE_RSA_WITH_AES_128_CBC_SHA = 0x33,
+ TLS_RSA_WITH_AES_256_CBC_SHA = 0x35,
+ TLS_RSA_WITH_AES_128_CBC_SHA = 0x2F,
+ TLS_PSK_WITH_AES_256_CBC_SHA = 0x8d,
+ TLS_PSK_WITH_AES_128_CBC_SHA = 0x8c,
+ SSL_RSA_WITH_RC4_128_SHA = 0x05,
+ SSL_RSA_WITH_RC4_128_MD5 = 0x04,
+ SSL_RSA_WITH_3DES_EDE_CBC_SHA = 0x0A,
+
+ /* ECC suites, first byte is 0xC0 (ECC_BYTE) */
+ TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA = 0x14,
+ TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA = 0x13,
+ TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA = 0x0A,
+ TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA = 0x09,
+ TLS_ECDHE_RSA_WITH_RC4_128_SHA = 0x11,
+ TLS_ECDHE_ECDSA_WITH_RC4_128_SHA = 0x07,
+ TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA = 0x12,
+ TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA = 0x08,
+
+ /* CyaSSL extension - eSTREAM */
+ TLS_RSA_WITH_HC_128_CBC_MD5 = 0xFB,
+ TLS_RSA_WITH_HC_128_CBC_SHA = 0xFC,
+ TLS_RSA_WITH_RABBIT_CBC_SHA = 0xFD,
+
+ /* CyaSSL extension - NTRU */
+ TLS_NTRU_RSA_WITH_RC4_128_SHA = 0x65,
+ TLS_NTRU_RSA_WITH_3DES_EDE_CBC_SHA = 0x66,
+ TLS_NTRU_RSA_WITH_AES_128_CBC_SHA = 0x67,
+ TLS_NTRU_RSA_WITH_AES_256_CBC_SHA = 0x68
+};
+
+
+enum Misc {
+ SERVER_END = 0,
+ CLIENT_END,
+
+ ECC_BYTE = 0xC0, /* ECC first cipher suite byte */
+
+ SEND_CERT = 1,
+ SEND_BLANK_CERT = 2,
+
+ DTLS_MAJOR = 0xfe, /* DTLS major version number */
+ DTLS_MINOR = 0xff, /* DTLS minor version number */
+ SSLv3_MAJOR = 3, /* SSLv3 and TLSv1+ major version number */
+ SSLv3_MINOR = 0, /* TLSv1 minor version number */
+ TLSv1_MINOR = 1, /* TLSv1 minor version number */
+ TLSv1_1_MINOR = 2, /* TLSv1_1 minor version number */
+ TLSv1_2_MINOR = 3, /* TLSv1_2 minor version number */
+ NO_COMPRESSION = 0,
+ ZLIB_COMPRESSION = 221, /* CyaSSL zlib compression */
+ SECRET_LEN = 48, /* pre RSA and all master */
+ ENCRYPT_LEN = 256, /* allow 2048 bit static buffer */
+ 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_UDP_SIZE = 1400, /* don't exceed MTU */
+ MAX_MSG_EXTRA = 68, /* max added to msg, mac + pad */
+ MAX_COMP_EXTRA = 1024, /* max compression extra */
+ MAX_MTU = 1500, /* max expected MTU */
+ MAX_DH_SZ = 612, /* 2240 p, pub, g + 2 byte size for each */
+ MAX_STR_VERSION = 8, /* string rep of protocol version */
+
+ PAD_MD5 = 48, /* pad length for finished */
+ PAD_SHA = 40, /* pad length for finished */
+ PEM_LINE_LEN = 80, /* PEM line max + fudge */
+ LENGTH_SZ = 2, /* length field for HMAC, data only */
+ VERSION_SZ = 2, /* length of proctocol version */
+ SEQ_SZ = 8, /* 64 bit sequence number */
+ BYTE3_LEN = 3, /* up to 24 bit byte lengths */
+ ALERT_SIZE = 2, /* level + description */
+ REQUEST_HEADER = 2, /* always use 2 bytes */
+ VERIFY_HEADER = 2, /* always use 2 bytes */
+
+ MAX_SUITE_SZ = 200, /* 100 suites for now! */
+ RAN_LEN = 32, /* random length */
+ SEED_LEN = RAN_LEN * 2, /* tls prf seed length */
+ ID_LEN = 32, /* session id length */
+ MAX_COOKIE_LEN = 32, /* max dtls cookie size */
+ SUITE_LEN = 2, /* cipher suite sz length */
+ ENUM_LEN = 1, /* always a byte */
+ COMP_LEN = 1, /* compression length */
+ CURVE_LEN = 2, /* ecc named curve length */
+
+ HANDSHAKE_HEADER_SZ = 4, /* type + length(3) */
+ RECORD_HEADER_SZ = 5, /* type + version + len(2) */
+ CERT_HEADER_SZ = 3, /* always 3 bytes */
+ REQ_HEADER_SZ = 2, /* cert request header sz */
+ HINT_LEN_SZ = 2, /* length of hint size field */
+
+ DTLS_HANDSHAKE_HEADER_SZ = 12, /* normal + seq(2) + offset(3) + length(3) */
+ DTLS_RECORD_HEADER_SZ = 13, /* normal + epoch(2) + seq_num(6) */
+ DTLS_HANDSHAKE_EXTRA = 8, /* diff from normal */
+ DTLS_RECORD_EXTRA = 8, /* diff from normal */
+
+ FINISHED_LABEL_SZ = 15, /* TLS finished label size */
+ TLS_FINISHED_SZ = 12, /* TLS has a shorter size */
+ MASTER_LABEL_SZ = 13, /* TLS master secret label sz */
+ KEY_LABEL_SZ = 13, /* TLS key block expansion sz */
+ MAX_PRF_HALF = 128, /* Maximum half secret len */
+ MAX_PRF_LABSEED = 80, /* Maximum label + seed len */
+ MAX_PRF_DIG = 148, /* Maximum digest len */
+ MAX_REQUEST_SZ = 256, /* Maximum cert req len (no auth yet */
+ SESSION_FLUSH_COUNT = 256, /* Flush session cache unless user turns off */
+
+ RC4_KEY_SIZE = 16, /* always 128bit */
+ DES_KEY_SIZE = 8, /* des */
+ DES3_KEY_SIZE = 24, /* 3 des ede */
+ DES_IV_SIZE = DES_BLOCK_SIZE,
+ AES_256_KEY_SIZE = 32, /* for 256 bit */
+ AES_192_KEY_SIZE = 24, /* for 192 bit */
+ AES_IV_SIZE = 16, /* always block size */
+ AES_128_KEY_SIZE = 16, /* for 128 bit */
+
+ HC_128_KEY_SIZE = 16, /* 128 bits */
+ HC_128_IV_SIZE = 16, /* also 128 bits */
+
+ RABBIT_KEY_SIZE = 16, /* 128 bits */
+ RABBIT_IV_SIZE = 8, /* 64 bits for iv */
+
+ EVP_SALT_SIZE = 8, /* evp salt size 64 bits */
+
+ ECDHE_SIZE = 32, /* ECHDE server size defaults to 256 bit */
+ MAX_EXPORT_ECC_SZ = 256, /* Export ANS X9.62 max future size */
+
+ MAX_HELLO_SZ = 128, /* max client or server hello */
+ MAX_CERT_VERIFY_SZ = 1024, /* max */
+ CLIENT_HELLO_FIRST = 35, /* Protocol + RAN_LEN + sizeof(id_len) */
+ MAX_SUITE_NAME = 48, /* maximum length of cipher suite string */
+ DEFAULT_TIMEOUT = 500, /* default resumption timeout in seconds */
+
+ MAX_PSK_ID_LEN = 128, /* max psk identity/hint supported */
+ MAX_PSK_KEY_LEN = 64, /* max psk key supported */
+
+ MAX_CHAIN_DEPTH = 4, /* max cert chain peer depth */
+ MAX_X509_SIZE = 2048, /* max static x509 buffer size */
+ FILE_BUFFER_SIZE = 1024, /* default static file buffer size for input,
+ will use dynamic buffer if not big enough */
+
+ MAX_NTRU_PUB_KEY_SZ = 1027, /* NTRU max for now */
+ MAX_NTRU_ENCRYPT_SZ = 1027, /* NTRU max for now */
+ MAX_NTRU_BITS = 256, /* max symmetric bit strength */
+ NO_SNIFF = 0, /* not sniffing */
+ SNIFF = 1, /* currently sniffing */
+
+ HASH_SIG_SIZE = 2, /* default SHA1 RSA */
+
+ NO_COPY = 0, /* should we copy static buffer for write */
+ COPY = 1 /* should we copy static buffer for write */
+};
+
+
+/* states */
+enum states {
+ NULL_STATE = 0,
+
+ SERVER_HELLOVERIFYREQUEST_COMPLETE,
+ SERVER_HELLO_COMPLETE,
+ SERVER_CERT_COMPLETE,
+ SERVER_KEYEXCHANGE_COMPLETE,
+ SERVER_HELLODONE_COMPLETE,
+ SERVER_FINISHED_COMPLETE,
+
+ CLIENT_HELLO_COMPLETE,
+ CLIENT_KEYEXCHANGE_COMPLETE,
+ CLIENT_FINISHED_COMPLETE,
+
+ HANDSHAKE_DONE
+};
+
+
+#ifndef SSL_TYPES_DEFINED
+ typedef struct SSL_METHOD SSL_METHOD;
+ typedef struct SSL_CTX SSL_CTX;
+ typedef struct SSL_SESSION SSL_SESSION;
+ typedef struct SSL_CIPHER SSL_CIPHER;
+ typedef struct SSL SSL;
+ typedef struct X509 X509;
+ typedef struct X509_CHAIN X509_CHAIN;
+ typedef struct BIO BIO;
+ typedef struct BIO_METHOD BIO_METHOD;
+
+ #undef X509_NAME
+ typedef struct X509_NAME X509_NAME;
+
+ typedef struct X509_STORE_CTX {
+ int error;
+ int error_depth;
+ X509* current_cert; /* stunnel dereference */
+ char* domain; /* subject CN domain name */
+ } X509_STORE_CTX;
+
+
+ typedef int (*pem_password_cb)(char*, int, int, void*);
+ typedef int (*CallbackIORecv)(char *buf, int sz, void *ctx);
+ typedef int (*CallbackIOSend)(char *buf, int sz, void *ctx);
+ typedef int (*VerifyCallback)(int, X509_STORE_CTX*);
+
+ /* make sure external "C" linkage for C++ programs with callbacks */
+ void CyaSSL_SetIORecv(SSL_CTX*, CallbackIORecv);
+ void CyaSSL_SetIOSend(SSL_CTX*, CallbackIOSend);
+
+ void CyaSSL_SetIOReadCtx(SSL* ssl, void *ctx);
+ void CyaSSL_SetIOWriteCtx(SSL* ssl, void *ctx);
+#endif /* SSL_TYPES_DEFINED */
+
+
+/* SSL Version */
+typedef struct ProtocolVersion {
+ byte major;
+ byte minor;
+} ProtocolVersion;
+
+
+ProtocolVersion MakeSSLv3(void);
+ProtocolVersion MakeTLSv1(void);
+ProtocolVersion MakeTLSv1_1(void);
+ProtocolVersion MakeTLSv1_2(void);
+
+#ifdef CYASSL_DTLS
+ ProtocolVersion MakeDTLSv1(void);
+#endif
+
+
+enum BIO_TYPE {
+ BIO_BUFFER = 1,
+ BIO_SOCKET = 2,
+ BIO_SSL = 3
+};
+
+
+/* OpenSSL BIO_METHOD type */
+struct BIO_METHOD {
+ byte type; /* method type */
+};
+
+
+/* OpenSSL BIO type */
+struct BIO {
+ byte type; /* method type */
+ byte close; /* close flag */
+ byte eof; /* eof flag */
+ SSL* ssl; /* possible associated ssl */
+ int fd; /* possible file descriptor */
+ BIO* prev; /* previous in chain */
+ BIO* next; /* next in chain */
+};
+
+
+/* OpenSSL method type */
+struct SSL_METHOD {
+ ProtocolVersion version;
+ int side; /* connection side, server or client */
+ int verifyPeer; /* request or send certificate */
+ int verifyNone; /* whether to verify certificate */
+ int failNoCert; /* fail if no certificate */
+ int downgrade; /* whether to downgrade version, default no */
+};
+
+
+/* defautls to client */
+void InitSSL_Method(SSL_METHOD*, ProtocolVersion);
+
+/* for sniffer */
+int DoFinished(SSL* ssl, const byte* input, word32* inOutIdx, int sniff);
+int DoApplicationData(SSL* ssl, byte* input, word32* inOutIdx);
+
+
+/* CyaSSL buffer type */
+typedef struct buffer {
+ word32 length;
+ byte* buffer;
+} buffer;
+
+
+enum {
+ FORCED_FREE = 1,
+ NO_FORCED_FREE = 0
+};
+
+
+/* only use compression extra if using compression */
+#ifdef HAVE_LIBZ
+ #define COMP_EXTRA MAX_COMP_EXTRA
+#else
+ #define COMP_EXTRA 0
+#endif
+
+/* only the sniffer needs space in the buffer for an extra MTU record */
+#ifdef CYASSL_SNIFFER
+ #define MTU_EXTRA MAX_MTU
+#else
+ #define MTU_EXTRA 0
+#endif
+
+/* give user option to use 16K static buffers, sniffer needs them too */
+#if defined(LARGE_STATIC_BUFFERS) || defined(CYASSL_SNIFFER)
+ #define RECORD_SIZE MAX_RECORD_SIZE
+#else
+ #ifdef CYASSL_DTLS
+ #define RECORD_SIZE 1500
+ #else
+ #define RECORD_SIZE 128
+ #endif
+#endif
+
+
+/* user option to turn off 16K output option */
+/* if using small static buffers (default) and SSL_write tries to write data
+ larger than the record we have, dynamically get it, unless user says only
+ write in static buffer chuncks */
+#ifndef STATIC_CHUNKS_ONLY
+ #define OUTPUT_RECORD_SIZE MAX_RECORD_SIZE
+#else
+ #define OUTPUT_RECORD_SIZE RECORD_SIZE
+#endif
+
+/* CyaSSL input buffer
+
+ RFC 2246:
+
+ length
+ The length (in bytes) of the following TLSPlaintext.fragment.
+ The length should not exceed 2^14.
+*/
+#define STATIC_BUFFER_LEN RECORD_HEADER_SZ + RECORD_SIZE + COMP_EXTRA + \
+ MTU_EXTRA + MAX_MSG_EXTRA
+
+typedef struct {
+ word32 length; /* total buffer length used */
+ word32 idx; /* idx to part of length already consumed */
+ byte* buffer; /* place holder for static or dynamic buffer */
+ ALIGN16 byte staticBuffer[STATIC_BUFFER_LEN];
+ word32 bufferSize; /* current buffer size */
+ byte dynamicFlag; /* dynamic memory currently in use */
+} bufferStatic;
+
+/* Cipher Suites holder */
+typedef struct Suites {
+ int setSuites; /* user set suites from default */
+ byte suites[MAX_SUITE_SZ];
+ word16 suiteSz; /* suite length in bytes */
+} Suites;
+
+
+void InitSuites(Suites*, ProtocolVersion, byte, byte, byte, byte, int);
+int SetCipherList(SSL_CTX* ctx, const char* list);
+
+#ifndef PSK_TYPES_DEFINED
+ typedef unsigned int (*psk_client_callback)(SSL*, const char*, char*,
+ unsigned int, unsigned char*, unsigned int);
+ typedef unsigned int (*psk_server_callback)(SSL*, const char*,
+ unsigned char*, unsigned int);
+#endif /* PSK_TYPES_DEFINED */
+
+
+#ifndef CYASSL_USER_IO
+ /* default IO callbacks */
+ int EmbedReceive(char *buf, int sz, void *ctx);
+ int EmbedSend(char *buf, int sz, void *ctx);
+#endif
+
+#ifdef CYASSL_DTLS
+ int IsUDP(void*);
+#endif
+
+
+/* OpenSSL Cipher type just points back to SSL */
+struct SSL_CIPHER {
+ SSL* ssl;
+};
+
+
+/* OpenSSL context type */
+struct SSL_CTX {
+ SSL_METHOD* method;
+ buffer certificate;
+ buffer privateKey;
+ Signer* caList; /* SSL_CTX owns this, SSL will reference */
+ Suites suites;
+ void* heap; /* for user memory overrides */
+ byte verifyPeer;
+ byte verifyNone;
+ byte failNoCert;
+ byte sessionCacheOff;
+ byte sessionCacheFlushOff;
+ 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 partialWrite; /* only one msg per write call */
+ byte quietShutdown; /* don't send close notify */
+ CallbackIORecv CBIORecv;
+ CallbackIOSend CBIOSend;
+ VerifyCallback verifyCallback; /* cert verification callback */
+#ifndef NO_PSK
+ byte havePSK; /* psk key set by user */
+ psk_client_callback client_psk_cb; /* client callback */
+ psk_server_callback server_psk_cb; /* server callback */
+ char server_hint[MAX_PSK_ID_LEN];
+#endif /* NO_PSK */
+#if defined(OPENSSL_EXTRA) || defined(HAVE_WEBSERVER)
+ pem_password_cb passwd_cb;
+ void* userdata;
+#endif /* OPENSSL_EXTRA */
+};
+
+
+void InitSSL_Ctx(SSL_CTX*, SSL_METHOD*);
+void FreeSSL_Ctx(SSL_CTX*);
+void SSL_CtxResourceFree(SSL_CTX*);
+
+int DeriveTlsKeys(SSL* ssl);
+int ProcessOldClientHello(SSL* ssl, const byte* input, word32* inOutIdx,
+ word32 inSz, word16 sz);
+
+/* All cipher suite related info */
+typedef struct CipherSpecs {
+ byte bulk_cipher_algorithm;
+ byte cipher_type; /* block or stream */
+ byte mac_algorithm;
+ byte kea; /* key exchange algo */
+ byte sig_algo;
+ byte hash_size;
+ byte pad_size;
+ word16 key_size;
+ word16 iv_size;
+ word16 block_size;
+} CipherSpecs;
+
+
+
+/* Supported Ciphers from page 43 */
+enum BulkCipherAlgorithm {
+ cipher_null,
+ rc4,
+ rc2,
+ des,
+ triple_des, /* leading 3 (3des) not valid identifier */
+ des40,
+ idea,
+ aes,
+ hc128, /* CyaSSL extensions */
+ rabbit
+};
+
+
+/* Supported Message Authentication Codes from page 43 */
+enum MACAlgorithm {
+ no_mac = 0,
+ md5_mac,
+ sha_mac,
+ sha224_mac,
+ sha256_mac,
+ sha384_mac,
+ sha512_mac,
+ rmd_mac
+};
+
+
+/* Supported Key Exchange Protocols */
+enum KeyExchangeAlgorithm {
+ no_kea = 0,
+ rsa_kea,
+ diffie_hellman_kea,
+ fortezza_kea,
+ psk_kea,
+ ntru_kea,
+ ecc_diffie_hellman_kea
+};
+
+
+/* Supported Authentication Schemes */
+enum SignatureAlgorithm {
+ anonymous_sa_algo = 0,
+ rsa_sa_algo,
+ dsa_sa_algo,
+ ecc_dsa_sa_algo
+};
+
+
+/* Supprted ECC Curve Types */
+enum EccCurves {
+ named_curve = 3
+};
+
+
+/* Supprted ECC Named Curves */
+enum EccNamedCurves {
+ secp256r1 = 0x17, /* default, OpenSSL also calls it prime256v1 */
+ secp384r1 = 0x18,
+ secp521r1 = 0x19,
+
+ secp160r1 = 0x10,
+ secp192r1 = 0x13, /* Openssl also call it prime192v1 */
+ secp224r1 = 0x15
+};
+
+
+/* Valid client certificate request types from page 27 */
+enum ClientCertificateType {
+ rsa_sign = 1,
+ dss_sign = 2,
+ rsa_fixed_dh = 3,
+ dss_fixed_dh = 4,
+ rsa_ephemeral_dh = 5,
+ dss_ephemeral_dh = 6,
+ fortezza_kea_cert = 20
+};
+
+
+enum CipherType { stream, block };
+
+
+/* keys and secrets */
+typedef struct Keys {
+ byte client_write_MAC_secret[SHA_DIGEST_SIZE]; /* max sizes */
+ byte server_write_MAC_secret[SHA_DIGEST_SIZE];
+ byte client_write_key[AES_256_KEY_SIZE]; /* max sizes */
+ byte server_write_key[AES_256_KEY_SIZE];
+ byte client_write_IV[AES_IV_SIZE]; /* max sizes */
+ byte server_write_IV[AES_IV_SIZE];
+
+ word32 peer_sequence_number;
+ word32 sequence_number;
+
+#ifdef CYASSL_DTLS
+ word32 dtls_sequence_number;
+ word32 dtls_peer_sequence_number;
+ word16 dtls_handshake_number;
+ word16 dtls_epoch;
+ word16 dtls_peer_epoch;
+#endif
+
+ word32 encryptSz; /* last size of encrypted data */
+ byte encryptionOn; /* true after change cipher spec */
+} Keys;
+
+
+/* cipher for now */
+typedef union {
+#ifdef BUILD_ARC4
+ Arc4 arc4;
+#endif
+#ifdef BUILD_DES3
+ Des3 des3;
+#endif
+#ifdef BUILD_AES
+ Aes aes;
+#endif
+#ifdef BUILD_HC128
+ HC128 hc128;
+#endif
+#ifdef BUILD_RABBIT
+ Rabbit rabbit;
+#endif
+} Ciphers;
+
+
+/* hashes type */
+typedef struct Hashes {
+ byte md5[MD5_DIGEST_SIZE];
+ byte sha[SHA_DIGEST_SIZE];
+} Hashes;
+
+
+/* Static x509 buffer */
+typedef struct x509_buffer {
+ int length; /* actual size */
+ byte buffer[MAX_X509_SIZE]; /* max static cert size */
+} x509_buffer;
+
+
+/* CyaSSL X509_CHAIN, for no dynamic memory SESSION_CACHE */
+struct X509_CHAIN {
+ int count; /* total number in chain */
+ x509_buffer certs[MAX_CHAIN_DEPTH]; /* only allow max depth 4 for now */
+};
+
+
+/* openSSL session type */
+struct SSL_SESSION {
+ byte sessionID[ID_LEN];
+ byte masterSecret[SECRET_LEN];
+ word32 bornOn; /* create time in seconds */
+ word32 timeout; /* timeout in seconds */
+#ifdef SESSION_CERTS
+ X509_CHAIN chain; /* peer cert chain, static */
+ ProtocolVersion version;
+ byte cipherSuite0; /* first byte, normally 0 */
+ byte cipherSuite; /* 2nd byte, actual suite */
+#endif
+};
+
+
+SSL_SESSION* GetSession(SSL*, byte*);
+int SetSession(SSL*, SSL_SESSION*);
+
+typedef void (*hmacfp) (SSL*, byte*, const byte*, word32, int, int);
+
+
+/* client connect state for nonblocking restart */
+enum ConnectState {
+ CONNECT_BEGIN = 0,
+ CLIENT_HELLO_SENT,
+ HELLO_AGAIN, /* HELLO_AGAIN s for DTLS case */
+ HELLO_AGAIN_REPLY,
+ FIRST_REPLY_DONE,
+ FIRST_REPLY_FIRST,
+ FIRST_REPLY_SECOND,
+ FIRST_REPLY_THIRD,
+ FIRST_REPLY_FOURTH,
+ FINISHED_DONE,
+ SECOND_REPLY_DONE
+};
+
+
+/* server accpet state for nonblocking restart */
+enum AcceptState {
+ ACCEPT_BEGIN = 0,
+ ACCEPT_CLIENT_HELLO_DONE,
+ HELLO_VERIFY_SENT,
+ ACCEPT_FIRST_REPLY_DONE,
+ SERVER_HELLO_SENT,
+ CERT_SENT,
+ KEY_EXCHANGE_SENT,
+ CERT_REQ_SENT,
+ SERVER_HELLO_DONE,
+ ACCEPT_SECOND_REPLY_DONE,
+ CHANGE_CIPHER_SENT,
+ ACCEPT_FINISHED_DONE,
+ ACCEPT_THIRD_REPLY_DONE
+};
+
+
+typedef struct Buffers {
+ buffer certificate; /* SSL_CTX owns */
+ buffer key; /* SSL_CTX owns */
+ buffer domainName; /* for client check */
+ buffer serverDH_P;
+ buffer serverDH_G;
+ buffer serverDH_Pub;
+ buffer serverDH_Priv;
+ bufferStatic inputBuffer;
+ bufferStatic outputBuffer;
+ buffer clearOutputBuffer;
+ int prevSent; /* previous plain text bytes sent
+ when got WANT_WRITE */
+ int plainSz; /* plain text bytes in buffer to send
+ when got WANT_WRITE */
+} Buffers;
+
+
+typedef struct Options {
+ byte sessionCacheOff;
+ byte sessionCacheFlushOff;
+ byte cipherSuite0; /* first byte, normally 0 */
+ byte cipherSuite; /* second byte, actual suite */
+ byte serverState;
+ byte clientState;
+ byte handShakeState;
+ byte side; /* client or server end */
+ byte verifyPeer;
+ byte verifyNone;
+ byte failNoCert;
+ byte downgrade; /* allow downgrade of versions */
+ byte sendVerify; /* false = 0, true = 1, sendBlank = 2 */
+ byte resuming;
+ byte tls; /* using TLS ? */
+ byte tls1_1; /* using TLSv1.1+ ? */
+ byte dtls; /* using datagrams ? */
+ byte connReset; /* has the peer reset */
+ byte isClosed; /* if we consider conn closed */
+ byte closeNotify; /* we've recieved a close notify */
+ byte sentNotify; /* we've sent a close notify */
+ byte connectState; /* nonblocking resume */
+ byte acceptState; /* nonblocking resume */
+ 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 havePeerCert; /* do we have peer's cert */
+ byte usingPSK_cipher; /* whether we're using psk as cipher */
+ byte sendAlertState; /* nonblocking resume */
+ byte processReply; /* nonblocking resume */
+ byte partialWrite; /* only one msg per write call */
+ byte quietShutdown; /* don't send close notify */
+#ifndef NO_PSK
+ byte havePSK; /* psk key set by user */
+ psk_client_callback client_psk_cb;
+ psk_server_callback server_psk_cb;
+#endif /* NO_PSK */
+} Options;
+
+
+typedef struct Arrays {
+ byte clientRandom[RAN_LEN];
+ byte serverRandom[RAN_LEN];
+ byte sessionID[ID_LEN];
+ byte preMasterSecret[ENCRYPT_LEN];
+ byte masterSecret[SECRET_LEN];
+#ifdef CYASSL_DTLS
+ byte cookie[MAX_COOKIE_LEN];
+#endif
+#ifndef NO_PSK
+ char client_identity[MAX_PSK_ID_LEN];
+ char server_hint[MAX_PSK_ID_LEN];
+ byte psk_key[MAX_PSK_KEY_LEN];
+ word32 psk_keySz; /* acutal size */
+#endif
+ word32 preMasterSz; /* differs for DH, actual size */
+} Arrays;
+
+
+#undef X509_NAME
+
+struct X509_NAME {
+ char name[ASN_NAME_MAX];
+ int sz;
+};
+
+
+struct X509 {
+ X509_NAME issuer;
+ X509_NAME subject;
+};
+
+
+/* record layer header for PlainText, Compressed, and CipherText */
+typedef struct RecordLayerHeader {
+ byte type;
+ ProtocolVersion version;
+ byte length[2];
+} RecordLayerHeader;
+
+
+/* record layer header for DTLS PlainText, Compressed, and CipherText */
+typedef struct DtlsRecordLayerHeader {
+ byte type;
+ ProtocolVersion version;
+ byte epoch[2]; /* increment on cipher state change */
+ byte sequence_number[6]; /* per record */
+ byte length[2];
+} DtlsRecordLayerHeader;
+
+
+/* OpenSSL ssl type */
+struct SSL {
+ SSL_CTX* ctx;
+ int error;
+ ProtocolVersion version; /* negotiated version */
+ ProtocolVersion chVersion; /* client hello version */
+ Suites suites;
+ Ciphers encrypt;
+ Ciphers decrypt;
+ CipherSpecs specs;
+ Keys keys;
+ int rfd; /* read file descriptor */
+ int wfd; /* write file descriptor */
+ BIO* biord; /* socket bio read to free/close */
+ BIO* biowr; /* socket bio write to free/close */
+ void* IOCB_ReadCtx;
+ void* IOCB_WriteCtx;
+ RNG rng;
+ Md5 hashMd5; /* md5 hash of handshake msgs */
+ Sha hashSha; /* sha hash of handshake msgs */
+#ifndef NO_SHA256
+ Sha256 hashSha256; /* sha256 hash of handshake msgs */
+#endif
+ Hashes verifyHashes;
+ Hashes certHashes; /* for cert verify */
+ Signer* caList; /* SSL_CTX owns */
+ Buffers buffers;
+ Options options;
+ Arrays arrays;
+ SSL_SESSION session;
+ RsaKey peerRsaKey;
+ byte peerRsaKeyPresent;
+#ifdef HAVE_NTRU
+ word16 peerNtruKeyLen;
+ byte peerNtruKey[MAX_NTRU_PUB_KEY_SZ];
+ byte peerNtruKeyPresent;
+#endif
+#ifdef HAVE_ECC
+ ecc_key peerEccKey; /* peer's ECDHE key */
+ byte peerEccKeyPresent;
+ ecc_key peerEccDsaKey; /* peer's ECDSA key */
+ byte peerEccDsaKeyPresent;
+ ecc_key eccTempKey; /* private ECDHE key */
+ byte eccTempKeyPresent;
+ ecc_key eccDsaKey; /* private ECDSA key */
+ byte eccDsaKeyPresent;
+#endif
+ hmacfp hmac;
+ void* heap; /* for user overrides */
+ RecordLayerHeader curRL;
+ word16 curSize;
+ SSL_CIPHER cipher;
+#ifdef HAVE_LIBZ
+ z_stream c_stream; /* compression stream */
+ z_stream d_stream; /* decompression stream */
+ byte didStreamInit; /* for stream init and end */
+#endif
+#ifdef CYASSL_CALLBACKS
+ HandShakeInfo handShakeInfo; /* info saved during handshake */
+ TimeoutInfo timeoutInfo; /* info saved during handshake */
+ byte hsInfoOn; /* track handshake info */
+ byte toInfoOn; /* track timeout info */
+#endif
+#ifdef OPENSSL_EXTRA
+ X509 peerCert; /* X509 peer cert */
+#endif
+};
+
+
+int InitSSL(SSL*, SSL_CTX*);
+void FreeSSL(SSL*);
+void SSL_ResourceFree(SSL*);
+
+
+enum {
+ IV_SZ = 32, /* max iv sz */
+ NAME_SZ = 80, /* max one line */
+};
+
+
+typedef struct EncryptedInfo {
+ char name[NAME_SZ];
+ byte iv[IV_SZ];
+ word32 ivSz;
+ byte set;
+} EncryptedInfo;
+
+
+#ifdef CYASSL_CALLBACKS
+ void InitHandShakeInfo(HandShakeInfo*);
+ void FinishHandShakeInfo(HandShakeInfo*, const SSL*);
+ void AddPacketName(const char*, HandShakeInfo*);
+
+ void InitTimeoutInfo(TimeoutInfo*);
+ void FreeTimeoutInfo(TimeoutInfo*, void*);
+ void AddPacketInfo(const char*, TimeoutInfo*, const byte*, int, void*);
+ void AddLateName(const char*, TimeoutInfo*);
+ void AddLateRecordHeader(const RecordLayerHeader* rl, TimeoutInfo* info);
+#endif
+
+
+/* Record Layer Header identifier from page 12 */
+enum ContentType {
+ no_type = 0,
+ change_cipher_spec = 20,
+ alert = 21,
+ handshake = 22,
+ application_data = 23
+};
+
+
+/* handshake header, same for each message type, pgs 20/21 */
+typedef struct HandShakeHeader {
+ byte type;
+ word24 length;
+} HandShakeHeader;
+
+
+/* DTLS handshake header, same for each message type */
+typedef struct DtlsHandShakeHeader {
+ byte type;
+ word24 length;
+ byte message_seq[2]; /* start at 0, restransmit gets same # */
+ word24 fragment_offset; /* bytes in previous fragments */
+ word24 fragment_length; /* length of this fragment */
+} DtlsHandShakeHeader;
+
+
+enum HandShakeType {
+ no_shake = -1,
+ hello_request = 0,
+ client_hello = 1,
+ server_hello = 2,
+ hello_verify_request = 3, /* DTLS addition */
+ certificate = 11,
+ server_key_exchange = 12,
+ certificate_request = 13,
+ server_hello_done = 14,
+ certificate_verify = 15,
+ client_key_exchange = 16,
+ finished = 20
+};
+
+
+/* Valid Alert types from page 16/17 */
+enum AlertDescription {
+ close_notify = 0,
+ unexpected_message = 10,
+ bad_record_mac = 20,
+ decompression_failure = 30,
+ handshake_failure = 40,
+ no_certificate = 41,
+ bad_certificate = 42,
+ unsupported_certificate = 43,
+ certificate_revoked = 44,
+ certificate_expired = 45,
+ certificate_unknown = 46,
+ illegal_parameter = 47,
+ decrypt_error = 51
+};
+
+
+/* I/O Callback default errors */
+enum IOerrors {
+ IO_ERR_GENERAL = -1, /* general unexpected err, not in below group */
+ IO_ERR_WANT_READ = -2, /* need to call read again */
+ IO_ERR_WANT_WRITE = -2, /* need to call write again */
+ IO_ERR_CONN_RST = -3, /* connection reset */
+ IO_ERR_ISR = -4, /* interrupt */
+ IO_ERR_CONN_CLOSE = -5 /* connection closed or epipe */
+};
+
+
+enum AlertLevel {
+ alert_warning = 1,
+ alert_fatal = 2
+};
+
+
+static const byte client[SIZEOF_SENDER] = { 0x43, 0x4C, 0x4E, 0x54 };
+static const byte server[SIZEOF_SENDER] = { 0x53, 0x52, 0x56, 0x52 };
+
+static const byte tls_client[FINISHED_LABEL_SZ + 1] = "client finished";
+static const byte tls_server[FINISHED_LABEL_SZ + 1] = "server finished";
+
+
+/* internal functions */
+int SendChangeCipher(SSL*);
+int SendData(SSL*, const void*, int);
+int SendCertificate(SSL*);
+int SendCertificateRequest(SSL*);
+int SendServerKeyExchange(SSL*);
+int SendBuffered(SSL*);
+int ReceiveData(SSL*, byte*, int);
+int SendFinished(SSL*);
+int SendAlert(SSL*, int, int);
+int ProcessReply(SSL*);
+
+int SetCipherSpecs(SSL*);
+int MakeMasterSecret(SSL*);
+
+int AddSession(SSL*);
+int DeriveKeys(SSL* ssl);
+int StoreKeys(SSL* ssl, const byte* keyData);
+
+int IsTLS(const SSL* ssl);
+int IsAtLeastTLSv1_2(const SSL* ssl);
+
+void ShrinkInputBuffer(SSL* ssl, int forcedFree);
+void ShrinkOutputBuffer(SSL* ssl);
+
+#ifndef NO_CYASSL_CLIENT
+ int SendClientHello(SSL*);
+ int SendClientKeyExchange(SSL*);
+ int SendCertificateVerify(SSL*);
+#endif /* NO_CYASSL_CLIENT */
+
+#ifndef NO_CYASSL_SERVER
+ int SendServerHello(SSL*);
+ int SendServerHelloDone(SSL*);
+ #ifdef CYASSL_DTLS
+ int SendHelloVerifyRequest(SSL*);
+ #endif
+#endif /* NO_CYASSL_SERVER */
+
+
+#ifndef NO_TLS
+
+
+#endif /* NO_TLS */
+
+
+
+typedef double timer_d;
+
+timer_d Timer(void);
+word32 LowResTimer(void);
+
+
+#ifdef SINGLE_THREADED
+ typedef int CyaSSL_Mutex;
+#else /* MULTI_THREADED */
+ #ifdef USE_WINDOWS_API
+ typedef CRITICAL_SECTION CyaSSL_Mutex;
+ #elif defined(CYASSL_PTHREADS)
+ typedef pthread_mutex_t CyaSSL_Mutex;
+ #elif defined(THREADX)
+ typedef TX_MUTEX CyaSSL_Mutex;
+ #elif defined(MICRIUM)
+ typedef OS_MUTEX CyaSSL_Mutex;
+ #else
+ #error Need a mutex type in multithreaded mode
+ #endif /* USE_WINDOWS_API */
+#endif /* SINGLE_THREADED */
+
+int InitMutex(CyaSSL_Mutex*);
+int FreeMutex(CyaSSL_Mutex*);
+int LockMutex(CyaSSL_Mutex*);
+int UnLockMutex(CyaSSL_Mutex*);
+
+
+#ifdef DEBUG_CYASSL
+
+ void CYASSL_ENTER(const char* msg);
+ void CYASSL_LEAVE(const char* msg, int ret);
+
+ void CYASSL_ERROR(int);
+ void CYASSL_MSG(const char* msg);
+
+#else /* DEBUG_CYASSL */
+
+ #define CYASSL_ENTER(m)
+ #define CYASSL_LEAVE(m, r)
+
+ #define CYASSL_ERROR(e)
+ #define CYASSL_MSG(m)
+
+#endif /* DEBUG_CYASSL */
+
+
+#ifdef __cplusplus
+ } /* extern "C" */
+#endif
+
+#endif /* CyaSSL_INT_H */
+