s3_enc.c 17.1 KB
Newer Older
R
Rich Salz 已提交
1 2
/*
 * Copyright 1995-2016 The OpenSSL Project Authors. All Rights Reserved.
3
 *
R
Rich Salz 已提交
4 5 6 7
 * Licensed under the OpenSSL license (the "License").  You may not use
 * this file except in compliance with the License.  You can obtain a copy
 * in the file LICENSE in the source distribution or at
 * https://www.openssl.org/source/license.html
8
 */
R
Rich Salz 已提交
9

10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
/* ====================================================================
 * Copyright 2005 Nokia. All rights reserved.
 *
 * The portions of the attached software ("Contribution") is developed by
 * Nokia Corporation and is licensed pursuant to the OpenSSL open source
 * license.
 *
 * The Contribution, originally written by Mika Kousa and Pasi Eronen of
 * Nokia Corporation, consists of the "PSK" (Pre-Shared Key) ciphersuites
 * support (see RFC 4279) to OpenSSL.
 *
 * No patent licenses or other rights except those expressly stated in
 * the OpenSSL open source license shall be deemed granted or received
 * expressly, by implication, estoppel, or otherwise.
 *
 * No assurances are provided by Nokia that the Contribution does not
 * infringe the patent or other intellectual property rights of any third
 * party or that the license provides you with all the necessary rights
 * to make use of the Contribution.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND. IN
 * ADDITION TO THE DISCLAIMERS INCLUDED IN THE LICENSE, NOKIA
 * SPECIFICALLY DISCLAIMS ANY LIABILITY FOR CLAIMS BROUGHT BY YOU OR ANY
 * OTHER ENTITY BASED ON INFRINGEMENT OF INTELLECTUAL PROPERTY RIGHTS OR
 * OTHERWISE.
 */
36 37 38

#include <stdio.h>
#include "ssl_locl.h"
39
#include <openssl/evp.h>
40
#include <openssl/md5.h>
41

B
Bodo Möller 已提交
42
static int ssl3_generate_key_block(SSL *s, unsigned char *km, int num)
43
{
44 45
    EVP_MD_CTX *m5;
    EVP_MD_CTX *s1;
46 47 48
    unsigned char buf[16], smd[SHA_DIGEST_LENGTH];
    unsigned char c = 'A';
    unsigned int i, j, k;
49
    int ret = 0;
50

51
#ifdef CHARSET_EBCDIC
52
    c = os_toascii[c];          /* 'A' in ASCII */
53
#endif
54
    k = 0;
55 56
    m5 = EVP_MD_CTX_new();
    s1 = EVP_MD_CTX_new();
57 58 59 60 61
    if (m5 == NULL || s1 == NULL) {
        SSLerr(SSL_F_SSL3_GENERATE_KEY_BLOCK, ERR_R_MALLOC_FAILURE);
        goto err;
    }
    EVP_MD_CTX_set_flags(m5, EVP_MD_CTX_FLAG_NON_FIPS_ALLOW);
62 63
    for (i = 0; (int)i < num; i += MD5_DIGEST_LENGTH) {
        k++;
64
        if (k > sizeof(buf)) {
65 66
            /* bug: 'buf' is too small for this ciphersuite */
            SSLerr(SSL_F_SSL3_GENERATE_KEY_BLOCK, ERR_R_INTERNAL_ERROR);
67
            goto err;
68 69 70 71 72
        }

        for (j = 0; j < k; j++)
            buf[j] = c;
        c++;
73 74 75 76 77 78 79 80 81 82 83 84
        if (!EVP_DigestInit_ex(s1, EVP_sha1(), NULL)
            || !EVP_DigestUpdate(s1, buf, k)
            || !EVP_DigestUpdate(s1, s->session->master_key,
                                 s->session->master_key_length)
            || !EVP_DigestUpdate(s1, s->s3->server_random, SSL3_RANDOM_SIZE)
            || !EVP_DigestUpdate(s1, s->s3->client_random, SSL3_RANDOM_SIZE)
            || !EVP_DigestFinal_ex(s1, smd, NULL)
            || !EVP_DigestInit_ex(m5, EVP_md5(), NULL)
            || !EVP_DigestUpdate(m5, s->session->master_key,
                                 s->session->master_key_length)
            || !EVP_DigestUpdate(m5, smd, SHA_DIGEST_LENGTH))
            goto err;
85
        if ((int)(i + MD5_DIGEST_LENGTH) > num) {
86 87
            if (!EVP_DigestFinal_ex(m5, smd, NULL))
                goto err;
88
            memcpy(km, smd, (num - i));
89 90 91 92
        } else {
            if (!EVP_DigestFinal_ex(m5, km, NULL))
                goto err;
        }
93 94 95

        km += MD5_DIGEST_LENGTH;
    }
R
Rich Salz 已提交
96
    OPENSSL_cleanse(smd, sizeof(smd));
97 98
    ret = 1;
 err:
99 100
    EVP_MD_CTX_free(m5);
    EVP_MD_CTX_free(s1);
101
    return ret;
102
}
103

U
Ulf Möller 已提交
104
int ssl3_change_cipher_state(SSL *s, int which)
105 106 107 108
{
    unsigned char *p, *mac_secret;
    unsigned char exp_key[EVP_MAX_KEY_LENGTH];
    unsigned char exp_iv[EVP_MAX_IV_LENGTH];
109
    unsigned char *ms, *key, *iv;
110 111
    EVP_CIPHER_CTX *dd;
    const EVP_CIPHER *c;
112
#ifndef OPENSSL_NO_COMP
113
    COMP_METHOD *comp;
114
#endif
115
    const EVP_MD *m;
116 117
    int mdi;
    size_t n, i, j, k, cl;
118 119 120 121 122
    int reuse_dd = 0;

    c = s->s3->tmp.new_sym_enc;
    m = s->s3->tmp.new_hash;
    /* m == NULL will lead to a crash later */
123 124 125 126
    if (!ossl_assert(m != NULL)) {
        SSLerr(SSL_F_SSL3_CHANGE_CIPHER_STATE, ERR_R_INTERNAL_ERROR);
        goto err2;
    }
127
#ifndef OPENSSL_NO_COMP
128 129 130 131
    if (s->s3->tmp.new_compression == NULL)
        comp = NULL;
    else
        comp = s->s3->tmp.new_compression->method;
132
#endif
133

134 135 136
    if (which & SSL3_CC_READ) {
        if (s->enc_read_ctx != NULL)
            reuse_dd = 1;
137
        else if ((s->enc_read_ctx = EVP_CIPHER_CTX_new()) == NULL)
138 139 140
            goto err;
        else
            /*
F
FdaSilvaYY 已提交
141
             * make sure it's initialised in case we exit later with an error
142
             */
143
            EVP_CIPHER_CTX_reset(s->enc_read_ctx);
144 145
        dd = s->enc_read_ctx;

146
        if (ssl_replace_hash(&s->read_hash, m) == NULL) {
E
Emilia Kasper 已提交
147 148
            SSLerr(SSL_F_SSL3_CHANGE_CIPHER_STATE, ERR_R_INTERNAL_ERROR);
            goto err2;
M
Matt Caswell 已提交
149
        }
150
#ifndef OPENSSL_NO_COMP
151
        /* COMPRESS */
R
Rich Salz 已提交
152 153
        COMP_CTX_free(s->expand);
        s->expand = NULL;
154 155 156 157 158 159 160 161
        if (comp != NULL) {
            s->expand = COMP_CTX_new(comp);
            if (s->expand == NULL) {
                SSLerr(SSL_F_SSL3_CHANGE_CIPHER_STATE,
                       SSL_R_COMPRESSION_LIBRARY_ERROR);
                goto err2;
            }
        }
162
#endif
163
        RECORD_LAYER_reset_read_sequence(&s->rlayer);
164 165 166 167
        mac_secret = &(s->s3->read_mac_secret[0]);
    } else {
        if (s->enc_write_ctx != NULL)
            reuse_dd = 1;
168
        else if ((s->enc_write_ctx = EVP_CIPHER_CTX_new()) == NULL)
169 170 171
            goto err;
        else
            /*
F
FdaSilvaYY 已提交
172
             * make sure it's initialised in case we exit later with an error
173
             */
174
            EVP_CIPHER_CTX_reset(s->enc_write_ctx);
175
        dd = s->enc_write_ctx;
176
        if (ssl_replace_hash(&s->write_hash, m) == NULL) {
E
Emilia Kasper 已提交
177 178
            SSLerr(SSL_F_SSL3_CHANGE_CIPHER_STATE, ERR_R_INTERNAL_ERROR);
            goto err2;
M
Matt Caswell 已提交
179
        }
180
#ifndef OPENSSL_NO_COMP
181
        /* COMPRESS */
R
Rich Salz 已提交
182 183
        COMP_CTX_free(s->compress);
        s->compress = NULL;
184 185 186 187 188 189 190 191
        if (comp != NULL) {
            s->compress = COMP_CTX_new(comp);
            if (s->compress == NULL) {
                SSLerr(SSL_F_SSL3_CHANGE_CIPHER_STATE,
                       SSL_R_COMPRESSION_LIBRARY_ERROR);
                goto err2;
            }
        }
192
#endif
193
        RECORD_LAYER_reset_write_sequence(&s->rlayer);
194 195 196 197
        mac_secret = &(s->s3->write_mac_secret[0]);
    }

    if (reuse_dd)
198
        EVP_CIPHER_CTX_reset(dd);
199 200

    p = s->s3->tmp.key_block;
201 202
    mdi = EVP_MD_size(m);
    if (mdi < 0)
203
        goto err2;
204
    i = mdi;
205
    cl = EVP_CIPHER_key_length(c);
206
    j = cl;
207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232
    k = EVP_CIPHER_iv_length(c);
    if ((which == SSL3_CHANGE_CIPHER_CLIENT_WRITE) ||
        (which == SSL3_CHANGE_CIPHER_SERVER_READ)) {
        ms = &(p[0]);
        n = i + i;
        key = &(p[n]);
        n += j + j;
        iv = &(p[n]);
        n += k + k;
    } else {
        n = i;
        ms = &(p[n]);
        n += i + j;
        key = &(p[n]);
        n += j + k;
        iv = &(p[n]);
        n += k;
    }

    if (n > s->s3->tmp.key_block_length) {
        SSLerr(SSL_F_SSL3_CHANGE_CIPHER_STATE, ERR_R_INTERNAL_ERROR);
        goto err2;
    }

    memcpy(mac_secret, ms, i);

233 234
    if (!EVP_CipherInit_ex(dd, c, NULL, key, iv, (which & SSL3_CC_WRITE)))
        goto err2;
235

R
Rich Salz 已提交
236 237
    OPENSSL_cleanse(exp_key, sizeof(exp_key));
    OPENSSL_cleanse(exp_iv, sizeof(exp_iv));
238 239 240 241
    return (1);
 err:
    SSLerr(SSL_F_SSL3_CHANGE_CIPHER_STATE, ERR_R_MALLOC_FAILURE);
 err2:
R
Rich Salz 已提交
242 243
    OPENSSL_cleanse(exp_key, sizeof(exp_key));
    OPENSSL_cleanse(exp_iv, sizeof(exp_iv));
244 245
    return (0);
}
246

U
Ulf Möller 已提交
247
int ssl3_setup_key_block(SSL *s)
248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265
{
    unsigned char *p;
    const EVP_CIPHER *c;
    const EVP_MD *hash;
    int num;
    int ret = 0;
    SSL_COMP *comp;

    if (s->s3->tmp.key_block_length != 0)
        return (1);

    if (!ssl_cipher_get_evp(s->session, &c, &hash, NULL, NULL, &comp, 0)) {
        SSLerr(SSL_F_SSL3_SETUP_KEY_BLOCK, SSL_R_CIPHER_OR_HASH_UNAVAILABLE);
        return (0);
    }

    s->s3->tmp.new_sym_enc = c;
    s->s3->tmp.new_hash = hash;
266
#ifdef OPENSSL_NO_COMP
267
    s->s3->tmp.new_compression = NULL;
268
#else
269
    s->s3->tmp.new_compression = comp;
270
#endif
271

272 273 274 275 276 277
    num = EVP_MD_size(hash);
    if (num < 0)
        return 0;

    num = EVP_CIPHER_key_length(c) + num + EVP_CIPHER_iv_length(c);
    num *= 2;
278

279
    ssl3_cleanup_key_block(s);
280

281 282
    if ((p = OPENSSL_malloc(num)) == NULL)
        goto err;
283

284 285
    s->s3->tmp.key_block_length = num;
    s->s3->tmp.key_block = p;
286

287
    ret = ssl3_generate_key_block(s, p, num);
288

289 290 291 292 293 294
    if (!(s->options & SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS)) {
        /*
         * enable vulnerability countermeasure for CBC ciphers with known-IV
         * problem (http://www.openssl.org/~bodo/tls-cbc.txt)
         */
        s->s3->need_empty_fragments = 1;
295

296 297 298
        if (s->session->cipher != NULL) {
            if (s->session->cipher->algorithm_enc == SSL_eNULL)
                s->s3->need_empty_fragments = 0;
299

300
#ifndef OPENSSL_NO_RC4
301 302
            if (s->session->cipher->algorithm_enc == SSL_RC4)
                s->s3->need_empty_fragments = 0;
303
#endif
304 305
        }
    }
306

307 308 309 310 311 312
    return ret;

 err:
    SSLerr(SSL_F_SSL3_SETUP_KEY_BLOCK, ERR_R_MALLOC_FAILURE);
    return (0);
}
313

U
Ulf Möller 已提交
314
void ssl3_cleanup_key_block(SSL *s)
315
{
R
Rich Salz 已提交
316 317
    OPENSSL_clear_free(s->s3->tmp.key_block, s->s3->tmp.key_block_length);
    s->s3->tmp.key_block = NULL;
318 319
    s->s3->tmp.key_block_length = 0;
}
320

321
int ssl3_init_finished_mac(SSL *s)
322
{
323 324 325 326 327 328
    BIO *buf = BIO_new(BIO_s_mem());

    if (buf == NULL) {
        SSLerr(SSL_F_SSL3_INIT_FINISHED_MAC, ERR_R_MALLOC_FAILURE);
        return 0;
    }
329
    ssl3_free_digest_list(s);
330
    s->s3->handshake_buffer = buf;
331
    (void)BIO_set_close(s->s3->handshake_buffer, BIO_CLOSE);
332
    return 1;
333 334
}

D
Dr. Stephen Henson 已提交
335 336 337 338 339
/*
 * Free digest list. Also frees handshake buffer since they are always freed
 * together.
 */

340 341
void ssl3_free_digest_list(SSL *s)
{
D
Dr. Stephen Henson 已提交
342 343
    BIO_free(s->s3->handshake_buffer);
    s->s3->handshake_buffer = NULL;
344
    EVP_MD_CTX_free(s->s3->handshake_dgst);
345 346
    s->s3->handshake_dgst = NULL;
}
347

M
Matt Caswell 已提交
348
int ssl3_finish_mac(SSL *s, const unsigned char *buf, size_t len)
349
{
M
Matt Caswell 已提交
350 351
    if (s->s3->handshake_dgst == NULL) {
        int ret;
352
        /* Note: this writes to a memory BIO so a failure is a fatal error */
M
Matt Caswell 已提交
353 354 355 356 357
        if (len > INT_MAX)
            return 0;
        ret = BIO_write(s->s3->handshake_buffer, (void *)buf, (int)len);
        return ret > 0 && ret == (int)len;
    } else {
358
        return EVP_DigestUpdate(s->s3->handshake_dgst, buf, len);
M
Matt Caswell 已提交
359
    }
360
}
361

362
int ssl3_digest_cached_records(SSL *s, int keep)
363 364 365 366 367 368
{
    const EVP_MD *md;
    long hdatalen;
    void *hdata;

    if (s->s3->handshake_dgst == NULL) {
369 370
        hdatalen = BIO_get_mem_data(s->s3->handshake_buffer, &hdata);
        if (hdatalen <= 0) {
E
Emilia Kasper 已提交
371 372
            SSLerr(SSL_F_SSL3_DIGEST_CACHED_RECORDS,
                   SSL_R_BAD_HANDSHAKE_LENGTH);
373 374
            return 0;
        }
375

376
        s->s3->handshake_dgst = EVP_MD_CTX_new();
377 378 379 380 381 382
        if (s->s3->handshake_dgst == NULL) {
            SSLerr(SSL_F_SSL3_DIGEST_CACHED_RECORDS, ERR_R_MALLOC_FAILURE);
            return 0;
        }

        md = ssl_handshake_md(s);
E
Emilia Kasper 已提交
383 384
        if (md == NULL || !EVP_DigestInit_ex(s->s3->handshake_dgst, md, NULL)
            || !EVP_DigestUpdate(s->s3->handshake_dgst, hdata, hdatalen)) {
385 386
            SSLerr(SSL_F_SSL3_DIGEST_CACHED_RECORDS, ERR_R_INTERNAL_ERROR);
            return 0;
387 388
        }
    }
389
    if (keep == 0) {
390 391 392 393 394 395
        BIO_free(s->s3->handshake_buffer);
        s->s3->handshake_buffer = NULL;
    }

    return 1;
}
396

397 398
size_t ssl3_final_finish_mac(SSL *s, const char *sender, size_t len,
                             unsigned char *p)
399
{
400
    int ret;
401
    EVP_MD_CTX *ctx = NULL;
402

403 404
    if (!ssl3_digest_cached_records(s, 0))
        return 0;
405

406
    if (EVP_MD_CTX_type(s->s3->handshake_dgst) != NID_md5_sha1) {
D
Dr. Stephen Henson 已提交
407
        SSLerr(SSL_F_SSL3_FINAL_FINISH_MAC, SSL_R_NO_REQUIRED_DIGEST);
408 409
        return 0;
    }
410

411
    ctx = EVP_MD_CTX_new();
412 413 414 415
    if (ctx == NULL) {
        SSLerr(SSL_F_SSL3_FINAL_FINISH_MAC, ERR_R_MALLOC_FAILURE);
        return 0;
    }
416 417 418 419
    if (!EVP_MD_CTX_copy_ex(ctx, s->s3->handshake_dgst)) {
        SSLerr(SSL_F_SSL3_FINAL_FINISH_MAC, ERR_R_INTERNAL_ERROR);
        return 0;
    }
420

421
    ret = EVP_MD_CTX_size(ctx);
422
    if (ret < 0) {
423
        EVP_MD_CTX_reset(ctx);
424
        return 0;
425
    }
426

427
    if ((sender != NULL && EVP_DigestUpdate(ctx, sender, len) <= 0)
E
Emilia Kasper 已提交
428
        || EVP_MD_CTX_ctrl(ctx, EVP_CTRL_SSL3_MASTER_SECRET,
429
                           (int)s->session->master_key_length,
E
Emilia Kasper 已提交
430 431
                           s->session->master_key) <= 0
        || EVP_DigestFinal_ex(ctx, p, NULL) <= 0) {
D
Dr. Stephen Henson 已提交
432
        SSLerr(SSL_F_SSL3_FINAL_FINISH_MAC, ERR_R_INTERNAL_ERROR);
433 434
        ret = 0;
    }
435

436
    EVP_MD_CTX_free(ctx);
437

438
    return ret;
439
}
440

U
Ulf Möller 已提交
441
int ssl3_generate_master_secret(SSL *s, unsigned char *out, unsigned char *p,
442
                                size_t len, size_t *secret_size)
443 444
{
    static const unsigned char *salt[3] = {
445
#ifndef CHARSET_EBCDIC
446 447 448
        (const unsigned char *)"A",
        (const unsigned char *)"BB",
        (const unsigned char *)"CCC",
449
#else
450 451 452
        (const unsigned char *)"\x41",
        (const unsigned char *)"\x42\x42",
        (const unsigned char *)"\x43\x43\x43",
453
#endif
454 455
    };
    unsigned char buf[EVP_MAX_MD_SIZE];
456
    EVP_MD_CTX *ctx = EVP_MD_CTX_new();
457
    int i, ret = 1;
458
    unsigned int n;
459
    size_t ret_secret_size = 0;
460

461 462 463 464
    if (ctx == NULL) {
        SSLerr(SSL_F_SSL3_GENERATE_MASTER_SECRET, ERR_R_MALLOC_FAILURE);
        return 0;
    }
465
    for (i = 0; i < 3; i++) {
466
        if (EVP_DigestInit_ex(ctx, s->ctx->sha1, NULL) <= 0
E
Emilia Kasper 已提交
467 468 469 470 471 472 473
            || EVP_DigestUpdate(ctx, salt[i],
                                strlen((const char *)salt[i])) <= 0
            || EVP_DigestUpdate(ctx, p, len) <= 0
            || EVP_DigestUpdate(ctx, &(s->s3->client_random[0]),
                                SSL3_RANDOM_SIZE) <= 0
            || EVP_DigestUpdate(ctx, &(s->s3->server_random[0]),
                                SSL3_RANDOM_SIZE) <= 0
474
               /* TODO(size_t) : convert me */
E
Emilia Kasper 已提交
475 476 477 478 479
            || EVP_DigestFinal_ex(ctx, buf, &n) <= 0
            || EVP_DigestInit_ex(ctx, s->ctx->md5, NULL) <= 0
            || EVP_DigestUpdate(ctx, p, len) <= 0
            || EVP_DigestUpdate(ctx, buf, n) <= 0
            || EVP_DigestFinal_ex(ctx, out, &n) <= 0) {
480 481 482 483
            SSLerr(SSL_F_SSL3_GENERATE_MASTER_SECRET, ERR_R_INTERNAL_ERROR);
            ret = 0;
            break;
        }
484
        out += n;
485
        ret_secret_size += n;
486
    }
487
    EVP_MD_CTX_free(ctx);
488

R
Rich Salz 已提交
489
    OPENSSL_cleanse(buf, sizeof(buf));
490 491 492
    if (ret)
        *secret_size = ret_secret_size;
    return ret;
493
}
494

U
Ulf Möller 已提交
495
int ssl3_alert_code(int code)
496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559
{
    switch (code) {
    case SSL_AD_CLOSE_NOTIFY:
        return (SSL3_AD_CLOSE_NOTIFY);
    case SSL_AD_UNEXPECTED_MESSAGE:
        return (SSL3_AD_UNEXPECTED_MESSAGE);
    case SSL_AD_BAD_RECORD_MAC:
        return (SSL3_AD_BAD_RECORD_MAC);
    case SSL_AD_DECRYPTION_FAILED:
        return (SSL3_AD_BAD_RECORD_MAC);
    case SSL_AD_RECORD_OVERFLOW:
        return (SSL3_AD_BAD_RECORD_MAC);
    case SSL_AD_DECOMPRESSION_FAILURE:
        return (SSL3_AD_DECOMPRESSION_FAILURE);
    case SSL_AD_HANDSHAKE_FAILURE:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_NO_CERTIFICATE:
        return (SSL3_AD_NO_CERTIFICATE);
    case SSL_AD_BAD_CERTIFICATE:
        return (SSL3_AD_BAD_CERTIFICATE);
    case SSL_AD_UNSUPPORTED_CERTIFICATE:
        return (SSL3_AD_UNSUPPORTED_CERTIFICATE);
    case SSL_AD_CERTIFICATE_REVOKED:
        return (SSL3_AD_CERTIFICATE_REVOKED);
    case SSL_AD_CERTIFICATE_EXPIRED:
        return (SSL3_AD_CERTIFICATE_EXPIRED);
    case SSL_AD_CERTIFICATE_UNKNOWN:
        return (SSL3_AD_CERTIFICATE_UNKNOWN);
    case SSL_AD_ILLEGAL_PARAMETER:
        return (SSL3_AD_ILLEGAL_PARAMETER);
    case SSL_AD_UNKNOWN_CA:
        return (SSL3_AD_BAD_CERTIFICATE);
    case SSL_AD_ACCESS_DENIED:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_DECODE_ERROR:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_DECRYPT_ERROR:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_EXPORT_RESTRICTION:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_PROTOCOL_VERSION:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_INSUFFICIENT_SECURITY:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_INTERNAL_ERROR:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_USER_CANCELLED:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_NO_RENEGOTIATION:
        return (-1);            /* Don't send it :-) */
    case SSL_AD_UNSUPPORTED_EXTENSION:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_CERTIFICATE_UNOBTAINABLE:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_UNRECOGNIZED_NAME:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_BAD_CERTIFICATE_STATUS_RESPONSE:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_BAD_CERTIFICATE_HASH_VALUE:
        return (SSL3_AD_HANDSHAKE_FAILURE);
    case SSL_AD_UNKNOWN_PSK_IDENTITY:
        return (TLS1_AD_UNKNOWN_PSK_IDENTITY);
    case SSL_AD_INAPPROPRIATE_FALLBACK:
        return (TLS1_AD_INAPPROPRIATE_FALLBACK);
560 561
    case SSL_AD_NO_APPLICATION_PROTOCOL:
        return (TLS1_AD_NO_APPLICATION_PROTOCOL);
562 563
    case SSL_AD_CERTIFICATE_REQUIRED:
        return SSL_AD_HANDSHAKE_FAILURE;
564 565 566 567
    default:
        return (-1);
    }
}