Add HMAC ECC ciphersuites from RFC5289. Include SHA384 PRF support and
authorDr. Stephen Henson <steve@openssl.org>
Mon, 25 Jul 2011 20:41:32 +0000 (20:41 +0000)
committerDr. Stephen Henson <steve@openssl.org>
Mon, 25 Jul 2011 20:41:32 +0000 (20:41 +0000)
prohibit use of these ciphersuites for TLS < 1.2

ssl/s3_clnt.c
ssl/s3_lib.c
ssl/ssl.h
ssl/ssl_ciph.c
ssl/ssl_lib.c
ssl/ssl_locl.h
ssl/tls1.h

index af8db00..c821724 100644 (file)
@@ -894,6 +894,14 @@ int ssl3_get_server_hello(SSL *s)
                SSLerr(SSL_F_SSL3_GET_SERVER_HELLO,SSL_R_UNKNOWN_CIPHER_RETURNED);
                goto f_err;
                }
+       /* TLS v1.2 only ciphersuites require v1.2 or later */
+       if ((c->algorithm_ssl & SSL_TLSV1_2) && 
+               (TLS1_get_version(s) < TLS1_2_VERSION))
+               {
+               al=SSL_AD_ILLEGAL_PARAMETER;
+               SSLerr(SSL_F_SSL3_GET_SERVER_HELLO,SSL_R_WRONG_CIPHER_RETURNED);
+               goto f_err;
+               }
        p+=ssl_put_cipher_by_char(s,NULL,NULL);
 
        sk=ssl_get_ciphers_by_id(s);
index 8327756..59d68c4 100644 (file)
@@ -2370,6 +2370,140 @@ OPENSSL_GLOBAL SSL_CIPHER ssl3_ciphers[]={
        256,
        },
 #endif  /* OPENSSL_NO_SRP */
+#ifndef OPENSSL_NO_ECDH
+
+       /* HMAC based TLS v1.2 ciphersuites from RFC5289 */
+
+       /* Cipher C023 */
+       {
+       1,
+       TLS1_TXT_ECDHE_ECDSA_WITH_AES_128_SHA256,
+       TLS1_CK_ECDHE_ECDSA_WITH_AES_128_SHA256,
+       SSL_kEECDH,
+       SSL_aECDSA,
+       SSL_AES128,
+       SSL_SHA256,
+       SSL_TLSV1_2,
+       SSL_NOT_EXP|SSL_HIGH|SSL_FIPS,
+       SSL_HANDSHAKE_MAC_SHA256|TLS1_PRF_SHA256,
+       128,
+       128,
+       },
+
+       /* Cipher C024 */
+       {
+       1,
+       TLS1_TXT_ECDHE_ECDSA_WITH_AES_256_SHA384,
+       TLS1_CK_ECDHE_ECDSA_WITH_AES_256_SHA384,
+       SSL_kEECDH,
+       SSL_aECDSA,
+       SSL_AES256,
+       SSL_SHA384,
+       SSL_TLSV1_2,
+       SSL_NOT_EXP|SSL_HIGH|SSL_FIPS,
+       SSL_HANDSHAKE_MAC_SHA384|TLS1_PRF_SHA384,
+       256,
+       256,
+       },
+
+       /* Cipher C025 */
+       {
+       1,
+       TLS1_TXT_ECDH_ECDSA_WITH_AES_128_SHA256,
+       TLS1_CK_ECDH_ECDSA_WITH_AES_128_SHA256,
+       SSL_kECDHe,
+       SSL_aECDH,
+       SSL_AES128,
+       SSL_SHA256,
+       SSL_TLSV1_2,
+       SSL_NOT_EXP|SSL_HIGH|SSL_FIPS,
+       SSL_HANDSHAKE_MAC_SHA256|TLS1_PRF_SHA256,
+       128,
+       128,
+       },
+
+       /* Cipher C026 */
+       {
+       1,
+       TLS1_TXT_ECDH_ECDSA_WITH_AES_256_SHA384,
+       TLS1_CK_ECDH_ECDSA_WITH_AES_256_SHA384,
+       SSL_kECDHe,
+       SSL_aECDH,
+       SSL_AES256,
+       SSL_SHA384,
+       SSL_TLSV1_2,
+       SSL_NOT_EXP|SSL_HIGH|SSL_FIPS,
+       SSL_HANDSHAKE_MAC_SHA384|TLS1_PRF_SHA384,
+       256,
+       256,
+       },
+
+       /* Cipher C027 */
+       {
+       1,
+       TLS1_TXT_ECDHE_RSA_WITH_AES_128_SHA256,
+       TLS1_CK_ECDHE_RSA_WITH_AES_128_SHA256,
+       SSL_kEECDH,
+       SSL_aRSA,
+       SSL_AES128,
+       SSL_SHA256,
+       SSL_TLSV1_2,
+       SSL_NOT_EXP|SSL_HIGH|SSL_FIPS,
+       SSL_HANDSHAKE_MAC_SHA256|TLS1_PRF_SHA256,
+       128,
+       128,
+       },
+
+       /* Cipher C028 */
+       {
+       1,
+       TLS1_TXT_ECDHE_RSA_WITH_AES_256_SHA384,
+       TLS1_CK_ECDHE_RSA_WITH_AES_256_SHA384,
+       SSL_kEECDH,
+       SSL_aRSA,
+       SSL_AES256,
+       SSL_SHA384,
+       SSL_TLSV1_2,
+       SSL_NOT_EXP|SSL_HIGH|SSL_FIPS,
+       SSL_HANDSHAKE_MAC_SHA384|TLS1_PRF_SHA384,
+       256,
+       256,
+       },
+
+       /* Cipher C029 */
+       {
+       1,
+       TLS1_TXT_ECDH_RSA_WITH_AES_128_SHA256,
+       TLS1_CK_ECDH_RSA_WITH_AES_128_SHA256,
+       SSL_kECDHe,
+       SSL_aECDH,
+       SSL_AES128,
+       SSL_SHA256,
+       SSL_TLSV1_2,
+       SSL_NOT_EXP|SSL_HIGH|SSL_FIPS,
+       SSL_HANDSHAKE_MAC_SHA256|TLS1_PRF_SHA256,
+       128,
+       128,
+       },
+
+       /* Cipher C02A */
+       {
+       1,
+       TLS1_TXT_ECDH_RSA_WITH_AES_256_SHA384,
+       TLS1_CK_ECDH_RSA_WITH_AES_256_SHA384,
+       SSL_kECDHe,
+       SSL_aECDH,
+       SSL_AES256,
+       SSL_SHA384,
+       SSL_TLSV1_2,
+       SSL_NOT_EXP|SSL_HIGH|SSL_FIPS,
+       SSL_HANDSHAKE_MAC_SHA384|TLS1_PRF_SHA384,
+       256,
+       256,
+       },
+
+#endif /* OPENSSL_NO_ECDH */
+
 
 #ifdef TEMP_GOST_TLS
 /* Cipher FF00 */
@@ -3226,6 +3360,8 @@ long ssl3_ctx_callback_ctrl(SSL_CTX *ctx, int cmd, void (*fp)(void))
        return(1);
        }
 
+#define DEBUG_PRINT_UNKNOWN_CIPHERSUITES
+
 /* This function needs to check if the ciphers required are actually
  * available */
 const SSL_CIPHER *ssl3_get_cipher_by_char(const unsigned char *p)
@@ -3317,6 +3453,11 @@ SSL_CIPHER *ssl3_choose_cipher(SSL *s, STACK_OF(SSL_CIPHER) *clnt,
                {
                c=sk_SSL_CIPHER_value(prio,i);
 
+               /* Skip TLS v1.2 only ciphersuites if lower than v1.2 */
+               if ((c->algorithm_ssl & SSL_TLSV1_2) && 
+                       (TLS1_get_version(s) < TLS1_2_VERSION))
+                       continue;
+
                ssl_set_cert_masks(cert,c);
                mask_k = cert->mask_k;
                mask_a = cert->mask_a;
index 1c1a495..244cfb2 100644 (file)
--- a/ssl/ssl.h
+++ b/ssl/ssl.h
@@ -297,6 +297,7 @@ extern "C" {
 #define SSL_TXT_GOST94         "GOST94" 
 #define SSL_TXT_GOST89MAC              "GOST89MAC" 
 #define SSL_TXT_SHA256         "SHA256"
+#define SSL_TXT_SHA384         "SHA384"
 
 #define SSL_TXT_SSLV2          "SSLv2"
 #define SSL_TXT_SSLV3          "SSLv3"
index b0542d1..224c63d 100644 (file)
@@ -180,28 +180,31 @@ static STACK_OF(SSL_COMP) *ssl_comp_methods=NULL;
 #define SSL_MD_GOST94_IDX 2
 #define SSL_MD_GOST89MAC_IDX 3
 #define SSL_MD_SHA256_IDX 4
+#define SSL_MD_SHA384_IDX 5
 /*Constant SSL_MAX_DIGEST equal to size of digests array should be 
  * defined in the
  * ssl_locl.h */
 #define SSL_MD_NUM_IDX SSL_MAX_DIGEST 
 static const EVP_MD *ssl_digest_methods[SSL_MD_NUM_IDX]={
-       NULL,NULL,NULL,NULL,NULL
+       NULL,NULL,NULL,NULL,NULL,NULL
        };
 /* PKEY_TYPE for GOST89MAC is known in advance, but, because
  * implementation is engine-provided, we'll fill it only if
  * corresponding EVP_PKEY_METHOD is found 
  */
 static int  ssl_mac_pkey_id[SSL_MD_NUM_IDX]={
-       EVP_PKEY_HMAC,EVP_PKEY_HMAC,EVP_PKEY_HMAC,NID_undef,EVP_PKEY_HMAC
+       EVP_PKEY_HMAC,EVP_PKEY_HMAC,EVP_PKEY_HMAC,NID_undef,
+       EVP_PKEY_HMAC,EVP_PKEY_HMAC
        };
 
 static int ssl_mac_secret_size[SSL_MD_NUM_IDX]={
-       0,0,0,0,0
+       0,0,0,0,0,0
        };
 
 static int ssl_handshake_digest_flag[SSL_MD_NUM_IDX]={
        SSL_HANDSHAKE_MAC_MD5,SSL_HANDSHAKE_MAC_SHA,
-       SSL_HANDSHAKE_MAC_GOST94, 0, SSL_HANDSHAKE_MAC_SHA256
+       SSL_HANDSHAKE_MAC_GOST94, 0, SSL_HANDSHAKE_MAC_SHA256,
+       SSL_HANDSHAKE_MAC_SHA384
        };
 
 #define CIPHER_ADD     1
@@ -300,6 +303,7 @@ static const SSL_CIPHER cipher_aliases[]={
        {0,SSL_TXT_GOST94,0,     0,0,0,SSL_GOST94,  0,0,0,0,0},
        {0,SSL_TXT_GOST89MAC,0,     0,0,0,SSL_GOST89MAC,  0,0,0,0,0},
        {0,SSL_TXT_SHA256,0,    0,0,0,SSL_SHA256,  0,0,0,0,0},
+       {0,SSL_TXT_SHA384,0,    0,0,0,SSL_SHA384,  0,0,0,0,0},
 
        /* protocol version aliases */
        {0,SSL_TXT_SSLV2,0,   0,0,0,0,SSL_SSLV2, 0,0,0,0},
@@ -412,6 +416,10 @@ void ssl_load_ciphers(void)
                EVP_get_digestbyname(SN_sha256);
        ssl_mac_secret_size[SSL_MD_SHA256_IDX]=
                EVP_MD_size(ssl_digest_methods[SSL_MD_SHA256_IDX]);
+       ssl_digest_methods[SSL_MD_SHA384_IDX]=
+               EVP_get_digestbyname(SN_sha384);
+       ssl_mac_secret_size[SSL_MD_SHA384_IDX]=
+               EVP_MD_size(ssl_digest_methods[SSL_MD_SHA384_IDX]);
        }
 #ifndef OPENSSL_NO_COMP
 
@@ -559,6 +567,9 @@ int ssl_cipher_get_evp(const SSL_SESSION *s, const EVP_CIPHER **enc,
        case SSL_SHA256:
                i=SSL_MD_SHA256_IDX;
                break;
+       case SSL_SHA384:
+               i=SSL_MD_SHA384_IDX;
+               break;
        case SSL_GOST94:
                i = SSL_MD_GOST94_IDX;
                break;
@@ -731,6 +742,7 @@ static void ssl_cipher_get_disabled(unsigned long *mkey, unsigned long *auth, un
        *mac |= (ssl_digest_methods[SSL_MD_MD5_IDX ] == NULL) ? SSL_MD5 :0;
        *mac |= (ssl_digest_methods[SSL_MD_SHA1_IDX] == NULL) ? SSL_SHA1:0;
        *mac |= (ssl_digest_methods[SSL_MD_SHA256_IDX] == NULL) ? SSL_SHA256:0;
+       *mac |= (ssl_digest_methods[SSL_MD_SHA384_IDX] == NULL) ? SSL_SHA384:0;
        *mac |= (ssl_digest_methods[SSL_MD_GOST94_IDX] == NULL) ? SSL_GOST94:0;
        *mac |= (ssl_digest_methods[SSL_MD_GOST89MAC_IDX] == NULL || ssl_mac_pkey_id[SSL_MD_GOST89MAC_IDX]==NID_undef)? SSL_GOST89MAC:0;
 
@@ -1524,6 +1536,8 @@ char *SSL_CIPHER_description(const SSL_CIPHER *cipher, char *buf, int len)
                ver="SSLv2";
        else if (alg_ssl & SSL_SSLV3)
                ver="SSLv3";
+       else if (alg_ssl & SSL_TLSV1_2)
+               ver="TLSv1.2";
        else
                ver="unknown";
 
@@ -1646,6 +1660,9 @@ char *SSL_CIPHER_description(const SSL_CIPHER *cipher, char *buf, int len)
        case SSL_SHA256:
                mac="SHA256";
                break;
+       case SSL_SHA384:
+               mac="SHA384";
+               break;
        default:
                mac="unknown";
                break;
index 9f25c6c..6ed9ca5 100644 (file)
@@ -1376,6 +1376,10 @@ int ssl_cipher_list_to_bytes(SSL *s,STACK_OF(SSL_CIPHER) *sk,unsigned char *p,
        for (i=0; i<sk_SSL_CIPHER_num(sk); i++)
                {
                c=sk_SSL_CIPHER_value(sk,i);
+               /* Skip TLS v1.2 only ciphersuites if lower than v1.2 */
+               if ((c->algorithm_ssl & SSL_TLSV1_2) && 
+                       (TLS1_get_version(s) < TLS1_2_VERSION))
+                       continue;
 #ifndef OPENSSL_NO_KRB5
                if (((c->algorithm_mkey & SSL_kKRB5) || (c->algorithm_auth & SSL_aKRB5)) &&
                    nokrb5)
index ca88199..726be35 100644 (file)
 #define SSL_GOST94      0x00000004L
 #define SSL_GOST89MAC   0x00000008L
 #define SSL_SHA256             0x00000010L
+#define SSL_SHA384             0x00000020L
 
 /* Bits for algorithm_ssl (protocol version) */
 #define SSL_SSLV2              0x00000001L
 #define SSL_SSLV3              0x00000002L
 #define SSL_TLSV1              SSL_SSLV3       /* for now */
+#define SSL_TLSV1_2            0x00000004L
 
 
 /* Bits for algorithm2 (handshake digests and other extra flags) */
 #define SSL_HANDSHAKE_MAC_SHA 0x20
 #define SSL_HANDSHAKE_MAC_GOST94 0x40
 #define SSL_HANDSHAKE_MAC_SHA256 0x80
+#define SSL_HANDSHAKE_MAC_SHA384 0x100
 #define SSL_HANDSHAKE_MAC_DEFAULT (SSL_HANDSHAKE_MAC_MD5 | SSL_HANDSHAKE_MAC_SHA)
 
 /* When adding new digest in the ssl_ciph.c and increment SSM_MD_NUM_IDX
  * make sure to update this constant too */
-#define SSL_MAX_DIGEST 5
+#define SSL_MAX_DIGEST 6
 
-#define TLS1_PRF_DGST_SHIFT 8
+#define TLS1_PRF_DGST_SHIFT 10
 #define TLS1_PRF_MD5 (SSL_HANDSHAKE_MAC_MD5 << TLS1_PRF_DGST_SHIFT)
 #define TLS1_PRF_SHA1 (SSL_HANDSHAKE_MAC_SHA << TLS1_PRF_DGST_SHIFT)
 #define TLS1_PRF_SHA256 (SSL_HANDSHAKE_MAC_SHA256 << TLS1_PRF_DGST_SHIFT)
+#define TLS1_PRF_SHA384 (SSL_HANDSHAKE_MAC_SHA384 << TLS1_PRF_DGST_SHIFT)
 #define TLS1_PRF_GOST94 (SSL_HANDSHAKE_MAC_GOST94 << TLS1_PRF_DGST_SHIFT)
 #define TLS1_PRF (TLS1_PRF_MD5 | TLS1_PRF_SHA1)
 
index f8d2fda..152bcc6 100644 (file)
@@ -441,6 +441,17 @@ SSL_CTX_callback_ctrl(ssl,SSL_CTRL_SET_TLSEXT_TICKET_KEY_CB,(void (*)(void))cb)
 #define TLS1_CK_SRP_SHA_RSA_WITH_AES_256_CBC_SHA       0x0300C021
 #define TLS1_CK_SRP_SHA_DSS_WITH_AES_256_CBC_SHA       0x0300C022
 
+/* ECDH HMAC based ciphersuites from RFC5289 */
+
+#define TLS1_CK_ECDHE_ECDSA_WITH_AES_128_SHA256         0x0300C023
+#define TLS1_CK_ECDHE_ECDSA_WITH_AES_256_SHA384         0x0300C024
+#define TLS1_CK_ECDH_ECDSA_WITH_AES_128_SHA256          0x0300C025
+#define TLS1_CK_ECDH_ECDSA_WITH_AES_256_SHA384          0x0300C026
+#define TLS1_CK_ECDHE_RSA_WITH_AES_128_SHA256           0x0300C027
+#define TLS1_CK_ECDHE_RSA_WITH_AES_256_SHA384           0x0300C028
+#define TLS1_CK_ECDH_RSA_WITH_AES_128_SHA256            0x0300C029
+#define TLS1_CK_ECDH_RSA_WITH_AES_256_SHA384            0x0300C02A
+
 /* XXX
  * Inconsistency alert:
  * The OpenSSL names of ciphers with ephemeral DH here include the string
@@ -557,6 +568,17 @@ SSL_CTX_callback_ctrl(ssl,SSL_CTRL_SET_TLSEXT_TICKET_KEY_CB,(void (*)(void))cb)
 #define TLS1_TXT_ADH_WITH_AES_128_SHA256               "ADH-AES128-SHA256"
 #define TLS1_TXT_ADH_WITH_AES_256_SHA256               "ADH-AES256-SHA256"
 
+/* ECDH HMAC based ciphersuites from RFC5289 */
+
+#define TLS1_TXT_ECDHE_ECDSA_WITH_AES_128_SHA256    "ECDHE-ECDSA-AES128-SHA256"
+#define TLS1_TXT_ECDHE_ECDSA_WITH_AES_256_SHA384    "ECDHE-ECDSA-AES256-SHA384"
+#define TLS1_TXT_ECDH_ECDSA_WITH_AES_128_SHA256     "ECDH-ECDSA-AES128-SHA256"
+#define TLS1_TXT_ECDH_ECDSA_WITH_AES_256_SHA384     "ECDH-ECDSA-AES256-SHA384"
+#define TLS1_TXT_ECDHE_RSA_WITH_AES_128_SHA256      "ECDHE-RSA-AES128-SHA256"
+#define TLS1_TXT_ECDHE_RSA_WITH_AES_256_SHA384      "ECDHE-RSA-AES256-SHA384"
+#define TLS1_TXT_ECDH_RSA_WITH_AES_128_SHA256       "ECDH-RSA-AES128-SHA256"
+#define TLS1_TXT_ECDH_RSA_WITH_AES_256_SHA384       "ECDH-RSA-AES256-SHA384"
+
 #define TLS_CT_RSA_SIGN                        1
 #define TLS_CT_DSS_SIGN                        2
 #define TLS_CT_RSA_FIXED_DH            3