diff options
Diffstat (limited to '')
| -rw-r--r-- | src/lib/libssl/src/ssl/ssl_sess.c | 328 | ||||
| -rw-r--r-- | src/lib/libssl/ssl_sess.c | 328 |
2 files changed, 404 insertions, 252 deletions
diff --git a/src/lib/libssl/src/ssl/ssl_sess.c b/src/lib/libssl/src/ssl/ssl_sess.c index af29cfc7ff..101da82b56 100644 --- a/src/lib/libssl/src/ssl/ssl_sess.c +++ b/src/lib/libssl/src/ssl/ssl_sess.c | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: ssl_sess.c,v 1.36 2014/07/11 09:24:44 beck Exp $ */ | 1 | /* $OpenBSD: ssl_sess.c,v 1.37 2014/07/12 23:59:11 jsing Exp $ */ |
| 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) | 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
| 3 | * All rights reserved. | 3 | * All rights reserved. |
| 4 | * | 4 | * |
| @@ -135,12 +135,13 @@ | |||
| 135 | * OTHERWISE. | 135 | * OTHERWISE. |
| 136 | */ | 136 | */ |
| 137 | 137 | ||
| 138 | #include <stdio.h> | ||
| 139 | #include <openssl/lhash.h> | 138 | #include <openssl/lhash.h> |
| 140 | #include <openssl/rand.h> | 139 | #include <openssl/rand.h> |
| 140 | |||
| 141 | #ifndef OPENSSL_NO_ENGINE | 141 | #ifndef OPENSSL_NO_ENGINE |
| 142 | #include <openssl/engine.h> | 142 | #include <openssl/engine.h> |
| 143 | #endif | 143 | #endif |
| 144 | |||
| 144 | #include "ssl_locl.h" | 145 | #include "ssl_locl.h" |
| 145 | 146 | ||
| 146 | static void SSL_SESSION_list_remove(SSL_CTX *ctx, SSL_SESSION *s); | 147 | static void SSL_SESSION_list_remove(SSL_CTX *ctx, SSL_SESSION *s); |
| @@ -159,14 +160,18 @@ SSL_SESSION * | |||
| 159 | SSL_get1_session(SSL *ssl) | 160 | SSL_get1_session(SSL *ssl) |
| 160 | { | 161 | { |
| 161 | SSL_SESSION *sess; | 162 | SSL_SESSION *sess; |
| 162 | /* Need to lock this all up rather than just use CRYPTO_add so that | 163 | |
| 164 | /* | ||
| 165 | * Need to lock this all up rather than just use CRYPTO_add so that | ||
| 163 | * somebody doesn't free ssl->session between when we check it's | 166 | * somebody doesn't free ssl->session between when we check it's |
| 164 | * non-null and when we up the reference count. */ | 167 | * non-null and when we up the reference count. |
| 168 | */ | ||
| 165 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_SESSION); | 169 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_SESSION); |
| 166 | sess = ssl->session; | 170 | sess = ssl->session; |
| 167 | if (sess) | 171 | if (sess) |
| 168 | sess->references++; | 172 | sess->references++; |
| 169 | CRYPTO_w_unlock(CRYPTO_LOCK_SSL_SESSION); | 173 | CRYPTO_w_unlock(CRYPTO_LOCK_SSL_SESSION); |
| 174 | |||
| 170 | return (sess); | 175 | return (sess); |
| 171 | } | 176 | } |
| 172 | 177 | ||
| @@ -174,8 +179,8 @@ int | |||
| 174 | SSL_SESSION_get_ex_new_index(long argl, void *argp, CRYPTO_EX_new *new_func, | 179 | SSL_SESSION_get_ex_new_index(long argl, void *argp, CRYPTO_EX_new *new_func, |
| 175 | CRYPTO_EX_dup *dup_func, CRYPTO_EX_free *free_func) | 180 | CRYPTO_EX_dup *dup_func, CRYPTO_EX_free *free_func) |
| 176 | { | 181 | { |
| 177 | return CRYPTO_get_ex_new_index(CRYPTO_EX_INDEX_SSL_SESSION, argl, argp, | 182 | return CRYPTO_get_ex_new_index(CRYPTO_EX_INDEX_SSL_SESSION, |
| 178 | new_func, dup_func, free_func); | 183 | argl, argp, new_func, dup_func, free_func); |
| 179 | } | 184 | } |
| 180 | 185 | ||
| 181 | int | 186 | int |
| @@ -213,7 +218,9 @@ SSL_SESSION_new(void) | |||
| 213 | ss->tlsext_ecpointformatlist = NULL; | 218 | ss->tlsext_ecpointformatlist = NULL; |
| 214 | ss->tlsext_ellipticcurvelist_length = 0; | 219 | ss->tlsext_ellipticcurvelist_length = 0; |
| 215 | ss->tlsext_ellipticcurvelist = NULL; | 220 | ss->tlsext_ellipticcurvelist = NULL; |
| 221 | |||
| 216 | CRYPTO_new_ex_data(CRYPTO_EX_INDEX_SSL_SESSION, ss, &ss->ex_data); | 222 | CRYPTO_new_ex_data(CRYPTO_EX_INDEX_SSL_SESSION, ss, &ss->ex_data); |
| 223 | |||
| 217 | return (ss); | 224 | return (ss); |
| 218 | } | 225 | } |
| 219 | 226 | ||
| @@ -231,28 +238,34 @@ SSL_SESSION_get_compress_id(const SSL_SESSION *s) | |||
| 231 | return 0; | 238 | return 0; |
| 232 | } | 239 | } |
| 233 | 240 | ||
| 234 | /* Even with SSLv2, we have 16 bytes (128 bits) of session ID space. SSLv3/TLSv1 | 241 | /* |
| 235 | * has 32 bytes (256 bits). As such, filling the ID with random gunk repeatedly | 242 | * Even with SSLv2, we have 16 bytes (128 bits) of session ID space. |
| 236 | * until we have no conflict is going to complete in one iteration pretty much | 243 | * SSLv3/TLSv1 has 32 bytes (256 bits). As such, filling the ID with random |
| 237 | * "most" of the time (btw: understatement). So, if it takes us 10 iterations | 244 | * gunk repeatedly until we have no conflict is going to complete in one |
| 238 | * and we still can't avoid a conflict - well that's a reasonable point to call | 245 | * iteration pretty much "most" of the time (btw: understatement). So, if it |
| 239 | * it quits. Either the RAND code is broken or someone is trying to open roughly | 246 | * takes us 10 iterations and we still can't avoid a conflict - well that's a |
| 240 | * very close to 2^128 (or 2^256) SSL sessions to our server. How you might | 247 | * reasonable point to call it quits. Either the RAND code is broken or someone |
| 241 | * store that many sessions is perhaps a more interesting question ... */ | 248 | * is trying to open roughly very close to 2^128 (or 2^256) SSL sessions to our |
| 249 | * server. How you might store that many sessions is perhaps a more interesting | ||
| 250 | * question... | ||
| 251 | */ | ||
| 242 | 252 | ||
| 243 | #define MAX_SESS_ID_ATTEMPTS 10 | 253 | #define MAX_SESS_ID_ATTEMPTS 10 |
| 254 | |||
| 244 | static int | 255 | static int |
| 245 | def_generate_session_id(const SSL *ssl, unsigned char *id, | 256 | def_generate_session_id(const SSL *ssl, unsigned char *id, unsigned int *id_len) |
| 246 | unsigned int *id_len) | ||
| 247 | { | 257 | { |
| 248 | unsigned int retry = 0; | 258 | unsigned int retry = 0; |
| 249 | do | 259 | |
| 250 | if (RAND_pseudo_bytes(id, *id_len) <= 0) | 260 | do { |
| 251 | return 0; | 261 | if (RAND_pseudo_bytes(id, *id_len) <= 0) |
| 252 | while (SSL_has_matching_session_id(ssl, id, *id_len) && | 262 | return 0; |
| 253 | (++retry < MAX_SESS_ID_ATTEMPTS)); | 263 | } while (SSL_has_matching_session_id(ssl, id, *id_len) && |
| 264 | (++retry < MAX_SESS_ID_ATTEMPTS)); | ||
| 265 | |||
| 254 | if (retry < MAX_SESS_ID_ATTEMPTS) | 266 | if (retry < MAX_SESS_ID_ATTEMPTS) |
| 255 | return 1; | 267 | return 1; |
| 268 | |||
| 256 | /* else - woops a session_id match */ | 269 | /* else - woops a session_id match */ |
| 257 | /* XXX We should also check the external cache -- | 270 | /* XXX We should also check the external cache -- |
| 258 | * but the probability of a collision is negligible, and | 271 | * but the probability of a collision is negligible, and |
| @@ -268,13 +281,14 @@ def_generate_session_id(const SSL *ssl, unsigned char *id, | |||
| 268 | int | 281 | int |
| 269 | ssl_get_new_session(SSL *s, int session) | 282 | ssl_get_new_session(SSL *s, int session) |
| 270 | { | 283 | { |
| 271 | /* This gets used by clients and servers. */ | ||
| 272 | |||
| 273 | unsigned int tmp; | 284 | unsigned int tmp; |
| 274 | SSL_SESSION *ss = NULL; | 285 | SSL_SESSION *ss = NULL; |
| 275 | GEN_SESSION_CB cb = def_generate_session_id; | 286 | GEN_SESSION_CB cb = def_generate_session_id; |
| 276 | 287 | ||
| 277 | if ((ss = SSL_SESSION_new()) == NULL) return (0); | 288 | /* This gets used by clients and servers. */ |
| 289 | |||
| 290 | if ((ss = SSL_SESSION_new()) == NULL) | ||
| 291 | return (0); | ||
| 278 | 292 | ||
| 279 | /* If the context has a default timeout, use it */ | 293 | /* If the context has a default timeout, use it */ |
| 280 | if (s->session_ctx->session_timeout == 0) | 294 | if (s->session_ctx->session_timeout == 0) |
| @@ -304,19 +318,22 @@ ssl_get_new_session(SSL *s, int session) | |||
| 304 | SSL_SESSION_free(ss); | 318 | SSL_SESSION_free(ss); |
| 305 | return (0); | 319 | return (0); |
| 306 | } | 320 | } |
| 307 | /* If RFC4507 ticket use empty session ID */ | 321 | |
| 322 | /* If RFC4507 ticket use empty session ID. */ | ||
| 308 | if (s->tlsext_ticket_expected) { | 323 | if (s->tlsext_ticket_expected) { |
| 309 | ss->session_id_length = 0; | 324 | ss->session_id_length = 0; |
| 310 | goto sess_id_done; | 325 | goto sess_id_done; |
| 311 | } | 326 | } |
| 312 | /* Choose which callback will set the session ID */ | 327 | |
| 328 | /* Choose which callback will set the session ID. */ | ||
| 313 | CRYPTO_r_lock(CRYPTO_LOCK_SSL_CTX); | 329 | CRYPTO_r_lock(CRYPTO_LOCK_SSL_CTX); |
| 314 | if (s->generate_session_id) | 330 | if (s->generate_session_id) |
| 315 | cb = s->generate_session_id; | 331 | cb = s->generate_session_id; |
| 316 | else if (s->session_ctx->generate_session_id) | 332 | else if (s->session_ctx->generate_session_id) |
| 317 | cb = s->session_ctx->generate_session_id; | 333 | cb = s->session_ctx->generate_session_id; |
| 318 | CRYPTO_r_unlock(CRYPTO_LOCK_SSL_CTX); | 334 | CRYPTO_r_unlock(CRYPTO_LOCK_SSL_CTX); |
| 319 | /* Choose a session ID */ | 335 | |
| 336 | /* Choose a session ID. */ | ||
| 320 | tmp = ss->session_id_length; | 337 | tmp = ss->session_id_length; |
| 321 | if (!cb(s, ss->session_id, &tmp)) { | 338 | if (!cb(s, ss->session_id, &tmp)) { |
| 322 | /* The callback failed */ | 339 | /* The callback failed */ |
| @@ -325,8 +342,11 @@ ssl_get_new_session(SSL *s, int session) | |||
| 325 | SSL_SESSION_free(ss); | 342 | SSL_SESSION_free(ss); |
| 326 | return (0); | 343 | return (0); |
| 327 | } | 344 | } |
| 328 | /* Don't allow the callback to set the session length to zero. | 345 | |
| 329 | * nor set it higher than it was. */ | 346 | /* |
| 347 | * Don't allow the callback to set the session length to zero. | ||
| 348 | * nor set it higher than it was. | ||
| 349 | */ | ||
| 330 | if (!tmp || (tmp > ss->session_id_length)) { | 350 | if (!tmp || (tmp > ss->session_id_length)) { |
| 331 | /* The callback set an illegal length */ | 351 | /* The callback set an illegal length */ |
| 332 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, | 352 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, |
| @@ -335,7 +355,8 @@ ssl_get_new_session(SSL *s, int session) | |||
| 335 | return (0); | 355 | return (0); |
| 336 | } | 356 | } |
| 337 | ss->session_id_length = tmp; | 357 | ss->session_id_length = tmp; |
| 338 | /* Finally, check for a conflict */ | 358 | |
| 359 | /* Finally, check for a conflict. */ | ||
| 339 | if (SSL_has_matching_session_id(s, ss->session_id, | 360 | if (SSL_has_matching_session_id(s, ss->session_id, |
| 340 | ss->session_id_length)) { | 361 | ss->session_id_length)) { |
| 341 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, | 362 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, |
| @@ -343,11 +364,13 @@ ssl_get_new_session(SSL *s, int session) | |||
| 343 | SSL_SESSION_free(ss); | 364 | SSL_SESSION_free(ss); |
| 344 | return (0); | 365 | return (0); |
| 345 | } | 366 | } |
| 346 | sess_id_done: | 367 | |
| 368 | sess_id_done: | ||
| 347 | if (s->tlsext_hostname) { | 369 | if (s->tlsext_hostname) { |
| 348 | ss->tlsext_hostname = BUF_strdup(s->tlsext_hostname); | 370 | ss->tlsext_hostname = BUF_strdup(s->tlsext_hostname); |
| 349 | if (ss->tlsext_hostname == NULL) { | 371 | if (ss->tlsext_hostname == NULL) { |
| 350 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, ERR_R_INTERNAL_ERROR); | 372 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, |
| 373 | ERR_R_INTERNAL_ERROR); | ||
| 351 | SSL_SESSION_free(ss); | 374 | SSL_SESSION_free(ss); |
| 352 | return 0; | 375 | return 0; |
| 353 | } | 376 | } |
| @@ -381,6 +404,7 @@ ssl_get_new_session(SSL *s, int session) | |||
| 381 | SSL_SESSION_free(ss); | 404 | SSL_SESSION_free(ss); |
| 382 | return 0; | 405 | return 0; |
| 383 | } | 406 | } |
| 407 | |||
| 384 | memcpy(ss->sid_ctx, s->sid_ctx, s->sid_ctx_length); | 408 | memcpy(ss->sid_ctx, s->sid_ctx, s->sid_ctx_length); |
| 385 | ss->sid_ctx_length = s->sid_ctx_length; | 409 | ss->sid_ctx_length = s->sid_ctx_length; |
| 386 | s->session = ss; | 410 | s->session = ss; |
| @@ -390,7 +414,8 @@ ssl_get_new_session(SSL *s, int session) | |||
| 390 | return (1); | 414 | return (1); |
| 391 | } | 415 | } |
| 392 | 416 | ||
| 393 | /* ssl_get_prev attempts to find an SSL_SESSION to be used to resume this | 417 | /* |
| 418 | * ssl_get_prev attempts to find an SSL_SESSION to be used to resume this | ||
| 394 | * connection. It is only called by servers. | 419 | * connection. It is only called by servers. |
| 395 | * | 420 | * |
| 396 | * session_id: points at the session ID in the ClientHello. This code will | 421 | * session_id: points at the session ID in the ClientHello. This code will |
| @@ -404,29 +429,31 @@ ssl_get_new_session(SSL *s, int session) | |||
| 404 | * 0: a session may have been found. | 429 | * 0: a session may have been found. |
| 405 | * | 430 | * |
| 406 | * Side effects: | 431 | * Side effects: |
| 407 | * - If a session is found then s->session is pointed at it (after freeing an | 432 | * - If a session is found then s->session is pointed at it (after freeing |
| 408 | * existing session if need be) and s->verify_result is set from the session. | 433 | * an existing session if need be) and s->verify_result is set from the |
| 409 | * - Both for new and resumed sessions, s->tlsext_ticket_expected is set to 1 | 434 | * session. |
| 410 | * if the server should issue a new session ticket (to 0 otherwise). | 435 | * - Both for new and resumed sessions, s->tlsext_ticket_expected is set |
| 436 | * to 1 if the server should issue a new session ticket (to 0 otherwise). | ||
| 411 | */ | 437 | */ |
| 412 | int | 438 | int |
| 413 | ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | 439 | ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, |
| 414 | const unsigned char *limit) | 440 | const unsigned char *limit) |
| 415 | { | 441 | { |
| 416 | /* This is used only by servers. */ | ||
| 417 | |||
| 418 | SSL_SESSION *ret = NULL; | 442 | SSL_SESSION *ret = NULL; |
| 419 | int fatal = 0; | 443 | int fatal = 0; |
| 420 | int try_session_cache = 1; | 444 | int try_session_cache = 1; |
| 421 | int r; | 445 | int r; |
| 422 | 446 | ||
| 447 | /* This is used only by servers. */ | ||
| 448 | |||
| 423 | if (len > SSL_MAX_SSL_SESSION_ID_LENGTH) | 449 | if (len > SSL_MAX_SSL_SESSION_ID_LENGTH) |
| 424 | goto err; | 450 | goto err; |
| 425 | 451 | ||
| 426 | if (len == 0) | 452 | if (len == 0) |
| 427 | try_session_cache = 0; | 453 | try_session_cache = 0; |
| 428 | 454 | ||
| 429 | r = tls1_process_ticket(s, session_id, len, limit, &ret); /* sets s->tlsext_ticket_expected */ | 455 | /* Sets s->tlsext_ticket_expected. */ |
| 456 | r = tls1_process_ticket(s, session_id, len, limit, &ret); | ||
| 430 | switch (r) { | 457 | switch (r) { |
| 431 | case -1: /* Error during processing */ | 458 | case -1: /* Error during processing */ |
| 432 | fatal = 1; | 459 | fatal = 1; |
| @@ -442,48 +469,60 @@ ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | |||
| 442 | abort(); | 469 | abort(); |
| 443 | } | 470 | } |
| 444 | 471 | ||
| 445 | if (try_session_cache && | 472 | if (try_session_cache && ret == NULL && |
| 446 | ret == NULL && | 473 | !(s->session_ctx->session_cache_mode & |
| 447 | !(s->session_ctx->session_cache_mode & SSL_SESS_CACHE_NO_INTERNAL_LOOKUP)) { | 474 | SSL_SESS_CACHE_NO_INTERNAL_LOOKUP)) { |
| 448 | SSL_SESSION data; | 475 | SSL_SESSION data; |
| 449 | data.ssl_version = s->version; | 476 | data.ssl_version = s->version; |
| 450 | data.session_id_length = len; | 477 | data.session_id_length = len; |
| 451 | if (len == 0) | 478 | if (len == 0) |
| 452 | return 0; | 479 | return 0; |
| 453 | memcpy(data.session_id, session_id, len); | 480 | memcpy(data.session_id, session_id, len); |
| 481 | |||
| 454 | CRYPTO_r_lock(CRYPTO_LOCK_SSL_CTX); | 482 | CRYPTO_r_lock(CRYPTO_LOCK_SSL_CTX); |
| 455 | ret = lh_SSL_SESSION_retrieve(s->session_ctx->sessions, &data); | 483 | ret = lh_SSL_SESSION_retrieve(s->session_ctx->sessions, &data); |
| 456 | if (ret != NULL) { | 484 | if (ret != NULL) { |
| 457 | /* don't allow other threads to steal it: */ | 485 | /* Don't allow other threads to steal it. */ |
| 458 | CRYPTO_add(&ret->references, 1, CRYPTO_LOCK_SSL_SESSION); | 486 | CRYPTO_add(&ret->references, 1, |
| 487 | CRYPTO_LOCK_SSL_SESSION); | ||
| 459 | } | 488 | } |
| 460 | CRYPTO_r_unlock(CRYPTO_LOCK_SSL_CTX); | 489 | CRYPTO_r_unlock(CRYPTO_LOCK_SSL_CTX); |
| 490 | |||
| 461 | if (ret == NULL) | 491 | if (ret == NULL) |
| 462 | s->session_ctx->stats.sess_miss++; | 492 | s->session_ctx->stats.sess_miss++; |
| 463 | } | 493 | } |
| 464 | 494 | ||
| 465 | if (try_session_cache && | 495 | if (try_session_cache && ret == NULL && |
| 466 | ret == NULL && | 496 | s->session_ctx->get_session_cb != NULL) { |
| 467 | s->session_ctx->get_session_cb != NULL) { | ||
| 468 | int copy = 1; | 497 | int copy = 1; |
| 469 | 498 | ||
| 470 | if ((ret = s->session_ctx->get_session_cb(s, session_id, len, ©))) { | 499 | if ((ret = s->session_ctx->get_session_cb(s, session_id, |
| 500 | len, ©))) { | ||
| 471 | s->session_ctx->stats.sess_cb_hit++; | 501 | s->session_ctx->stats.sess_cb_hit++; |
| 472 | 502 | ||
| 473 | /* Increment reference count now if the session callback | 503 | /* |
| 474 | * asks us to do so (note that if the session structures | 504 | * Increment reference count now if the session |
| 475 | * returned by the callback are shared between threads, | 505 | * callback asks us to do so (note that if the session |
| 476 | * it must handle the reference count itself [i.e. copy == 0], | 506 | * structures returned by the callback are shared |
| 477 | * or things won't be thread-safe). */ | 507 | * between threads, it must handle the reference count |
| 508 | * itself [i.e. copy == 0], or things won't be | ||
| 509 | * thread-safe). | ||
| 510 | */ | ||
| 478 | if (copy) | 511 | if (copy) |
| 479 | CRYPTO_add(&ret->references, 1, CRYPTO_LOCK_SSL_SESSION); | 512 | CRYPTO_add(&ret->references, 1, |
| 480 | 513 | CRYPTO_LOCK_SSL_SESSION); | |
| 481 | /* Add the externally cached session to the internal | 514 | |
| 482 | * cache as well if and only if we are supposed to. */ | 515 | /* |
| 483 | if (!(s->session_ctx->session_cache_mode & SSL_SESS_CACHE_NO_INTERNAL_STORE)) | 516 | * Add the externally cached session to the internal |
| 484 | /* The following should not return 1, otherwise, | 517 | * cache as well if and only if we are supposed to. |
| 485 | * things are very strange */ | 518 | */ |
| 486 | SSL_CTX_add_session(s->session_ctx, ret); | 519 | if (!(s->session_ctx->session_cache_mode & |
| 520 | SSL_SESS_CACHE_NO_INTERNAL_STORE)) | ||
| 521 | /* | ||
| 522 | * The following should not return 1, | ||
| 523 | * otherwise, things are very strange. | ||
| 524 | */ | ||
| 525 | SSL_CTX_add_session(s->session_ctx, ret); | ||
| 487 | } | 526 | } |
| 488 | } | 527 | } |
| 489 | 528 | ||
| @@ -492,25 +531,28 @@ ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | |||
| 492 | 531 | ||
| 493 | /* Now ret is non-NULL and we own one of its reference counts. */ | 532 | /* Now ret is non-NULL and we own one of its reference counts. */ |
| 494 | 533 | ||
| 495 | if (ret->sid_ctx_length != s->sid_ctx_length | 534 | if (ret->sid_ctx_length != s->sid_ctx_length || |
| 496 | || timingsafe_memcmp(ret->sid_ctx, s->sid_ctx, ret->sid_ctx_length) != 0) { | 535 | timingsafe_memcmp(ret->sid_ctx, |
| 536 | s->sid_ctx, ret->sid_ctx_length) != 0) { | ||
| 497 | /* We have the session requested by the client, but we don't | 537 | /* We have the session requested by the client, but we don't |
| 498 | * want to use it in this context. */ | 538 | * want to use it in this context. */ |
| 499 | goto err; /* treat like cache miss */ | 539 | goto err; /* treat like cache miss */ |
| 500 | } | 540 | } |
| 501 | 541 | ||
| 502 | if ((s->verify_mode & SSL_VERIFY_PEER) && s->sid_ctx_length == 0) { | 542 | if ((s->verify_mode & SSL_VERIFY_PEER) && s->sid_ctx_length == 0) { |
| 503 | /* We can't be sure if this session is being used out of | 543 | /* |
| 544 | * We can't be sure if this session is being used out of | ||
| 504 | * context, which is especially important for SSL_VERIFY_PEER. | 545 | * context, which is especially important for SSL_VERIFY_PEER. |
| 505 | * The application should have used SSL[_CTX]_set_session_id_context. | 546 | * The application should have used |
| 547 | * SSL[_CTX]_set_session_id_context. | ||
| 506 | * | 548 | * |
| 507 | * For this error case, we generate an error instead of treating | 549 | * For this error case, we generate an error instead of treating |
| 508 | * the event like a cache miss (otherwise it would be easy for | 550 | * the event like a cache miss (otherwise it would be easy for |
| 509 | * applications to effectively disable the session cache by | 551 | * applications to effectively disable the session cache by |
| 510 | * accident without anyone noticing). | 552 | * accident without anyone noticing). |
| 511 | */ | 553 | */ |
| 512 | 554 | SSLerr(SSL_F_SSL_GET_PREV_SESSION, | |
| 513 | SSLerr(SSL_F_SSL_GET_PREV_SESSION, SSL_R_SESSION_ID_CONTEXT_UNINITIALIZED); | 555 | SSL_R_SESSION_ID_CONTEXT_UNINITIALIZED); |
| 514 | fatal = 1; | 556 | fatal = 1; |
| 515 | goto err; | 557 | goto err; |
| 516 | } | 558 | } |
| @@ -522,16 +564,18 @@ ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | |||
| 522 | p = buf; | 564 | p = buf; |
| 523 | l = ret->cipher_id; | 565 | l = ret->cipher_id; |
| 524 | l2n(l, p); | 566 | l2n(l, p); |
| 567 | |||
| 525 | if ((ret->ssl_version >> 8) >= SSL3_VERSION_MAJOR) | 568 | if ((ret->ssl_version >> 8) >= SSL3_VERSION_MAJOR) |
| 526 | ret->cipher = ssl_get_cipher_by_char(s, &(buf[2])); | 569 | ret->cipher = ssl_get_cipher_by_char(s, &(buf[2])); |
| 527 | else | 570 | else |
| 528 | ret->cipher = ssl_get_cipher_by_char(s, &(buf[1])); | 571 | ret->cipher = ssl_get_cipher_by_char(s, &(buf[1])); |
| 572 | |||
| 529 | if (ret->cipher == NULL) | 573 | if (ret->cipher == NULL) |
| 530 | goto err; | 574 | goto err; |
| 531 | } | 575 | } |
| 532 | 576 | ||
| 533 | if (ret->timeout < (time(NULL) - ret->time)) /* timeout */ | 577 | if (ret->timeout < (time(NULL) - ret->time)) { |
| 534 | { | 578 | /* timeout */ |
| 535 | s->session_ctx->stats.sess_timeout++; | 579 | s->session_ctx->stats.sess_timeout++; |
| 536 | if (try_session_cache) { | 580 | if (try_session_cache) { |
| 537 | /* session was from the cache, so remove it */ | 581 | /* session was from the cache, so remove it */ |
| @@ -548,12 +592,14 @@ ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | |||
| 548 | s->verify_result = s->session->verify_result; | 592 | s->verify_result = s->session->verify_result; |
| 549 | return 1; | 593 | return 1; |
| 550 | 594 | ||
| 551 | err: | 595 | err: |
| 552 | if (ret != NULL) { | 596 | if (ret != NULL) { |
| 553 | SSL_SESSION_free(ret); | 597 | SSL_SESSION_free(ret); |
| 554 | if (!try_session_cache) { | 598 | if (!try_session_cache) { |
| 555 | /* The session was from a ticket, so we should | 599 | /* |
| 556 | * issue a ticket for the new session */ | 600 | * The session was from a ticket, so we should |
| 601 | * issue a ticket for the new session. | ||
| 602 | */ | ||
| 557 | s->tlsext_ticket_expected = 1; | 603 | s->tlsext_ticket_expected = 1; |
| 558 | } | 604 | } |
| 559 | } | 605 | } |
| @@ -569,27 +615,36 @@ SSL_CTX_add_session(SSL_CTX *ctx, SSL_SESSION *c) | |||
| 569 | int ret = 0; | 615 | int ret = 0; |
| 570 | SSL_SESSION *s; | 616 | SSL_SESSION *s; |
| 571 | 617 | ||
| 572 | /* add just 1 reference count for the SSL_CTX's session cache | 618 | /* |
| 619 | * Add just 1 reference count for the SSL_CTX's session cache | ||
| 573 | * even though it has two ways of access: each session is in a | 620 | * even though it has two ways of access: each session is in a |
| 574 | * doubly linked list and an lhash */ | 621 | * doubly linked list and an lhash. |
| 622 | */ | ||
| 575 | CRYPTO_add(&c->references, 1, CRYPTO_LOCK_SSL_SESSION); | 623 | CRYPTO_add(&c->references, 1, CRYPTO_LOCK_SSL_SESSION); |
| 576 | /* if session c is in already in cache, we take back the increment later */ | ||
| 577 | 624 | ||
| 625 | /* | ||
| 626 | * If session c is in already in cache, we take back the increment | ||
| 627 | * later. | ||
| 628 | */ | ||
| 578 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_CTX); | 629 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_CTX); |
| 579 | s = lh_SSL_SESSION_insert(ctx->sessions, c); | 630 | s = lh_SSL_SESSION_insert(ctx->sessions, c); |
| 580 | 631 | ||
| 581 | /* s != NULL iff we already had a session with the given PID. | 632 | /* |
| 633 | * s != NULL iff we already had a session with the given PID. | ||
| 582 | * In this case, s == c should hold (then we did not really modify | 634 | * In this case, s == c should hold (then we did not really modify |
| 583 | * ctx->sessions), or we're in trouble. */ | 635 | * ctx->sessions), or we're in trouble. |
| 636 | */ | ||
| 584 | if (s != NULL && s != c) { | 637 | if (s != NULL && s != c) { |
| 585 | /* We *are* in trouble ... */ | 638 | /* We *are* in trouble ... */ |
| 586 | SSL_SESSION_list_remove(ctx, s); | 639 | SSL_SESSION_list_remove(ctx, s); |
| 587 | SSL_SESSION_free(s); | 640 | SSL_SESSION_free(s); |
| 588 | /* ... so pretend the other session did not exist in cache | 641 | /* |
| 642 | * ... so pretend the other session did not exist in cache | ||
| 589 | * (we cannot handle two SSL_SESSION structures with identical | 643 | * (we cannot handle two SSL_SESSION structures with identical |
| 590 | * session ID in the same cache, which could happen e.g. when | 644 | * session ID in the same cache, which could happen e.g. when |
| 591 | * two threads concurrently obtain the same session from an external | 645 | * two threads concurrently obtain the same session from an |
| 592 | * cache) */ | 646 | * external cache). |
| 647 | */ | ||
| 593 | s = NULL; | 648 | s = NULL; |
| 594 | } | 649 | } |
| 595 | 650 | ||
| @@ -598,22 +653,27 @@ SSL_CTX_add_session(SSL_CTX *ctx, SSL_SESSION *c) | |||
| 598 | SSL_SESSION_list_add(ctx, c); | 653 | SSL_SESSION_list_add(ctx, c); |
| 599 | 654 | ||
| 600 | if (s != NULL) { | 655 | if (s != NULL) { |
| 601 | /* existing cache entry -- decrement previously incremented reference | 656 | /* |
| 602 | * count because it already takes into account the cache */ | 657 | * existing cache entry -- decrement previously incremented |
| 603 | 658 | * reference count because it already takes into account the | |
| 659 | * cache. | ||
| 660 | */ | ||
| 604 | SSL_SESSION_free(s); /* s == c */ | 661 | SSL_SESSION_free(s); /* s == c */ |
| 605 | ret = 0; | 662 | ret = 0; |
| 606 | } else { | 663 | } else { |
| 607 | /* new cache entry -- remove old ones if cache has become too large */ | 664 | /* |
| 665 | * New cache entry -- remove old ones if cache has become | ||
| 666 | * too large. | ||
| 667 | */ | ||
| 608 | 668 | ||
| 609 | ret = 1; | 669 | ret = 1; |
| 610 | 670 | ||
| 611 | if (SSL_CTX_sess_get_cache_size(ctx) > 0) { | 671 | if (SSL_CTX_sess_get_cache_size(ctx) > 0) { |
| 612 | while (SSL_CTX_sess_number(ctx) > | 672 | while (SSL_CTX_sess_number(ctx) > |
| 613 | SSL_CTX_sess_get_cache_size(ctx)) { | 673 | SSL_CTX_sess_get_cache_size(ctx)) { |
| 614 | if (!remove_session_lock(ctx, | 674 | if (!remove_session_lock(ctx, |
| 615 | ctx->session_cache_tail, 0)) | 675 | ctx->session_cache_tail, 0)) |
| 616 | break; | 676 | break; |
| 617 | else | 677 | else |
| 618 | ctx->stats.sess_cache_full++; | 678 | ctx->stats.sess_cache_full++; |
| 619 | } | 679 | } |
| @@ -638,12 +698,11 @@ remove_session_lock(SSL_CTX *ctx, SSL_SESSION *c, int lck) | |||
| 638 | if ((c != NULL) && (c->session_id_length != 0)) { | 698 | if ((c != NULL) && (c->session_id_length != 0)) { |
| 639 | if (lck) | 699 | if (lck) |
| 640 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_CTX); | 700 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_CTX); |
| 641 | if ((r = lh_SSL_SESSION_retrieve(ctx->sessions, c)) == c) { | 701 | if ((r = lh_SSL_SESSION_retrieve(ctx->sessions, c)) == c) { |
| 642 | ret = 1; | 702 | ret = 1; |
| 643 | r = lh_SSL_SESSION_delete(ctx->sessions, c); | 703 | r = lh_SSL_SESSION_delete(ctx->sessions, c); |
| 644 | SSL_SESSION_list_remove(ctx, c); | 704 | SSL_SESSION_list_remove(ctx, c); |
| 645 | } | 705 | } |
| 646 | |||
| 647 | if (lck) | 706 | if (lck) |
| 648 | CRYPTO_w_unlock(CRYPTO_LOCK_SSL_CTX); | 707 | CRYPTO_w_unlock(CRYPTO_LOCK_SSL_CTX); |
| 649 | 708 | ||
| @@ -701,7 +760,8 @@ SSL_set_session(SSL *s, SSL_SESSION *session) | |||
| 701 | if (meth == NULL) | 760 | if (meth == NULL) |
| 702 | meth = s->method->get_ssl_method(session->ssl_version); | 761 | meth = s->method->get_ssl_method(session->ssl_version); |
| 703 | if (meth == NULL) { | 762 | if (meth == NULL) { |
| 704 | SSLerr(SSL_F_SSL_SET_SESSION, SSL_R_UNABLE_TO_FIND_SSL_METHOD); | 763 | SSLerr(SSL_F_SSL_SET_SESSION, |
| 764 | SSL_R_UNABLE_TO_FIND_SSL_METHOD); | ||
| 705 | return (0); | 765 | return (0); |
| 706 | } | 766 | } |
| 707 | 767 | ||
| @@ -782,7 +842,8 @@ SSL_SESSION_set1_id_context(SSL_SESSION *s, const unsigned char *sid_ctx, | |||
| 782 | unsigned int sid_ctx_len) | 842 | unsigned int sid_ctx_len) |
| 783 | { | 843 | { |
| 784 | if (sid_ctx_len > SSL_MAX_SID_CTX_LENGTH) { | 844 | if (sid_ctx_len > SSL_MAX_SID_CTX_LENGTH) { |
| 785 | SSLerr(SSL_F_SSL_SESSION_SET1_ID_CONTEXT, SSL_R_SSL_SESSION_ID_CONTEXT_TOO_LONG); | 845 | SSLerr(SSL_F_SSL_SESSION_SET1_ID_CONTEXT, |
| 846 | SSL_R_SSL_SESSION_ID_CONTEXT_TOO_LONG); | ||
| 786 | return 0; | 847 | return 0; |
| 787 | } | 848 | } |
| 788 | s->sid_ctx_length = sid_ctx_len; | 849 | s->sid_ctx_length = sid_ctx_len; |
| @@ -795,10 +856,12 @@ long | |||
| 795 | SSL_CTX_set_timeout(SSL_CTX *s, long t) | 856 | SSL_CTX_set_timeout(SSL_CTX *s, long t) |
| 796 | { | 857 | { |
| 797 | long l; | 858 | long l; |
| 859 | |||
| 798 | if (s == NULL) | 860 | if (s == NULL) |
| 799 | return (0); | 861 | return (0); |
| 800 | l = s->session_timeout; | 862 | l = s->session_timeout; |
| 801 | s->session_timeout = t; | 863 | s->session_timeout = t; |
| 864 | |||
| 802 | return (l); | 865 | return (l); |
| 803 | } | 866 | } |
| 804 | 867 | ||
| @@ -811,8 +874,9 @@ SSL_CTX_get_timeout(const SSL_CTX *s) | |||
| 811 | } | 874 | } |
| 812 | 875 | ||
| 813 | int | 876 | int |
| 814 | SSL_set_session_secret_cb(SSL *s, int (*tls_session_secret_cb)(SSL *s, void *secret, int *secret_len, | 877 | SSL_set_session_secret_cb(SSL *s, int (*tls_session_secret_cb)(SSL *s, |
| 815 | STACK_OF(SSL_CIPHER) *peer_ciphers, SSL_CIPHER **cipher, void *arg), void *arg) | 878 | void *secret, int *secret_len, STACK_OF(SSL_CIPHER) *peer_ciphers, |
| 879 | SSL_CIPHER **cipher, void *arg), void *arg) | ||
| 816 | { | 880 | { |
| 817 | if (s == NULL) | 881 | if (s == NULL) |
| 818 | return (0); | 882 | return (0); |
| @@ -837,16 +901,20 @@ SSL_set_session_ticket_ext(SSL *s, void *ext_data, int ext_len) | |||
| 837 | { | 901 | { |
| 838 | if (s->version >= TLS1_VERSION) { | 902 | if (s->version >= TLS1_VERSION) { |
| 839 | free(s->tlsext_session_ticket); | 903 | free(s->tlsext_session_ticket); |
| 840 | s->tlsext_session_ticket = malloc(sizeof(TLS_SESSION_TICKET_EXT) + ext_len); | 904 | s->tlsext_session_ticket = |
| 905 | malloc(sizeof(TLS_SESSION_TICKET_EXT) + ext_len); | ||
| 841 | if (!s->tlsext_session_ticket) { | 906 | if (!s->tlsext_session_ticket) { |
| 842 | SSLerr(SSL_F_SSL_SET_SESSION_TICKET_EXT, ERR_R_MALLOC_FAILURE); | 907 | SSLerr(SSL_F_SSL_SET_SESSION_TICKET_EXT, |
| 908 | ERR_R_MALLOC_FAILURE); | ||
| 843 | return 0; | 909 | return 0; |
| 844 | } | 910 | } |
| 845 | 911 | ||
| 846 | if (ext_data) { | 912 | if (ext_data) { |
| 847 | s->tlsext_session_ticket->length = ext_len; | 913 | s->tlsext_session_ticket->length = ext_len; |
| 848 | s->tlsext_session_ticket->data = s->tlsext_session_ticket + 1; | 914 | s->tlsext_session_ticket->data = |
| 849 | memcpy(s->tlsext_session_ticket->data, ext_data, ext_len); | 915 | s->tlsext_session_ticket + 1; |
| 916 | memcpy(s->tlsext_session_ticket->data, | ||
| 917 | ext_data, ext_len); | ||
| 850 | } else { | 918 | } else { |
| 851 | s->tlsext_session_ticket->length = 0; | 919 | s->tlsext_session_ticket->length = 0; |
| 852 | s->tlsext_session_ticket->data = NULL; | 920 | s->tlsext_session_ticket->data = NULL; |
| @@ -867,8 +935,8 @@ typedef struct timeout_param_st { | |||
| 867 | static void | 935 | static void |
| 868 | timeout_doall_arg(SSL_SESSION *s, TIMEOUT_PARAM *p) | 936 | timeout_doall_arg(SSL_SESSION *s, TIMEOUT_PARAM *p) |
| 869 | { | 937 | { |
| 870 | if ((p->time == 0) || (p->time > (s->time + s->timeout))) /* timeout */ | 938 | if ((p->time == 0) || (p->time > (s->time + s->timeout))) { |
| 871 | { | 939 | /* timeout */ |
| 872 | /* The reason we don't call SSL_CTX_remove_session() is to | 940 | /* The reason we don't call SSL_CTX_remove_session() is to |
| 873 | * save on locking overhead */ | 941 | * save on locking overhead */ |
| 874 | (void)lh_SSL_SESSION_delete(p->cache, s); | 942 | (void)lh_SSL_SESSION_delete(p->cache, s); |
| @@ -907,9 +975,8 @@ SSL_CTX_flush_sessions(SSL_CTX *s, long t) | |||
| 907 | int | 975 | int |
| 908 | ssl_clear_bad_session(SSL *s) | 976 | ssl_clear_bad_session(SSL *s) |
| 909 | { | 977 | { |
| 910 | if ((s->session != NULL) && | 978 | if ((s->session != NULL) && !(s->shutdown & SSL_SENT_SHUTDOWN) && |
| 911 | !(s->shutdown & SSL_SENT_SHUTDOWN) && | 979 | !(SSL_in_init(s) || SSL_in_before(s))) { |
| 912 | !(SSL_in_init(s) || SSL_in_before(s))) { | ||
| 913 | SSL_CTX_remove_session(s->ctx, s->session); | 980 | SSL_CTX_remove_session(s->ctx, s->session); |
| 914 | return (1); | 981 | return (1); |
| 915 | } else | 982 | } else |
| @@ -920,26 +987,28 @@ ssl_clear_bad_session(SSL *s) | |||
| 920 | static void | 987 | static void |
| 921 | SSL_SESSION_list_remove(SSL_CTX *ctx, SSL_SESSION *s) | 988 | SSL_SESSION_list_remove(SSL_CTX *ctx, SSL_SESSION *s) |
| 922 | { | 989 | { |
| 923 | if ((s->next == NULL) | 990 | if ((s->next == NULL) || (s->prev == NULL)) |
| 924 | || (s->prev == NULL)) return; | 991 | return; |
| 925 | 992 | ||
| 926 | if (s->next == (SSL_SESSION *)&(ctx->session_cache_tail)) | 993 | if (s->next == (SSL_SESSION *)&(ctx->session_cache_tail)) { |
| 927 | { /* last element in list */ | 994 | /* last element in list */ |
| 928 | if (s->prev == (SSL_SESSION *)&(ctx->session_cache_head)) | 995 | if (s->prev == (SSL_SESSION *)&(ctx->session_cache_head)) { |
| 929 | { /* only one element in list */ | 996 | /* only one element in list */ |
| 930 | ctx->session_cache_head = NULL; | 997 | ctx->session_cache_head = NULL; |
| 931 | ctx->session_cache_tail = NULL; | 998 | ctx->session_cache_tail = NULL; |
| 932 | } else { | 999 | } else { |
| 933 | ctx->session_cache_tail = s->prev; | 1000 | ctx->session_cache_tail = s->prev; |
| 934 | s->prev->next = (SSL_SESSION *)&(ctx->session_cache_tail); | 1001 | s->prev->next = |
| 1002 | (SSL_SESSION *)&(ctx->session_cache_tail); | ||
| 935 | } | 1003 | } |
| 936 | } else { | 1004 | } else { |
| 937 | if (s->prev == (SSL_SESSION *)&(ctx->session_cache_head)) | 1005 | if (s->prev == (SSL_SESSION *)&(ctx->session_cache_head)) { |
| 938 | { /* first element in list */ | 1006 | /* first element in list */ |
| 939 | ctx->session_cache_head = s->next; | 1007 | ctx->session_cache_head = s->next; |
| 940 | s->next->prev = (SSL_SESSION *)&(ctx->session_cache_head); | 1008 | s->next->prev = |
| 941 | } else | 1009 | (SSL_SESSION *)&(ctx->session_cache_head); |
| 942 | { /* middle of list */ | 1010 | } else { |
| 1011 | /* middle of list */ | ||
| 943 | s->next->prev = s->prev; | 1012 | s->next->prev = s->prev; |
| 944 | s->prev->next = s->next; | 1013 | s->prev->next = s->next; |
| 945 | } | 1014 | } |
| @@ -972,7 +1041,8 @@ SSL_CTX_sess_set_new_cb(SSL_CTX *ctx, | |||
| 972 | ctx->new_session_cb = cb; | 1041 | ctx->new_session_cb = cb; |
| 973 | } | 1042 | } |
| 974 | 1043 | ||
| 975 | int (*SSL_CTX_sess_get_new_cb(SSL_CTX *ctx))(SSL *ssl, SSL_SESSION *sess) | 1044 | int |
| 1045 | (*SSL_CTX_sess_get_new_cb(SSL_CTX *ctx))(SSL *ssl, SSL_SESSION *sess) | ||
| 976 | { | 1046 | { |
| 977 | return ctx->new_session_cb; | 1047 | return ctx->new_session_cb; |
| 978 | } | 1048 | } |
| @@ -984,21 +1054,22 @@ SSL_CTX_sess_set_remove_cb(SSL_CTX *ctx, | |||
| 984 | ctx->remove_session_cb = cb; | 1054 | ctx->remove_session_cb = cb; |
| 985 | } | 1055 | } |
| 986 | 1056 | ||
| 987 | void (*SSL_CTX_sess_get_remove_cb(SSL_CTX *ctx))(SSL_CTX * ctx, SSL_SESSION *sess) | 1057 | void |
| 1058 | (*SSL_CTX_sess_get_remove_cb(SSL_CTX *ctx))(SSL_CTX * ctx, SSL_SESSION *sess) | ||
| 988 | { | 1059 | { |
| 989 | return ctx->remove_session_cb; | 1060 | return ctx->remove_session_cb; |
| 990 | } | 1061 | } |
| 991 | 1062 | ||
| 992 | void | 1063 | void |
| 993 | SSL_CTX_sess_set_get_cb(SSL_CTX *ctx, | 1064 | SSL_CTX_sess_set_get_cb(SSL_CTX *ctx, SSL_SESSION *(*cb)(struct ssl_st *ssl, |
| 994 | SSL_SESSION *(*cb)(struct ssl_st *ssl, | 1065 | unsigned char *data, int len, int *copy)) |
| 995 | unsigned char *data, int len, int *copy)) | ||
| 996 | { | 1066 | { |
| 997 | ctx->get_session_cb = cb; | 1067 | ctx->get_session_cb = cb; |
| 998 | } | 1068 | } |
| 999 | 1069 | ||
| 1000 | SSL_SESSION * (*SSL_CTX_sess_get_get_cb(SSL_CTX *ctx))(SSL *ssl, | 1070 | SSL_SESSION * |
| 1001 | unsigned char *data, int len, int *copy) | 1071 | (*SSL_CTX_sess_get_get_cb(SSL_CTX *ctx))(SSL *ssl, unsigned char *data, |
| 1072 | int len, int *copy) | ||
| 1002 | { | 1073 | { |
| 1003 | return ctx->get_session_cb; | 1074 | return ctx->get_session_cb; |
| 1004 | } | 1075 | } |
| @@ -1010,7 +1081,8 @@ SSL_CTX_set_info_callback(SSL_CTX *ctx, | |||
| 1010 | ctx->info_callback = cb; | 1081 | ctx->info_callback = cb; |
| 1011 | } | 1082 | } |
| 1012 | 1083 | ||
| 1013 | void (*SSL_CTX_get_info_callback(SSL_CTX *ctx))(const SSL *ssl, int type, int val) | 1084 | void |
| 1085 | (*SSL_CTX_get_info_callback(SSL_CTX *ctx))(const SSL *ssl, int type, int val) | ||
| 1014 | { | 1086 | { |
| 1015 | return ctx->info_callback; | 1087 | return ctx->info_callback; |
| 1016 | } | 1088 | } |
| @@ -1022,7 +1094,9 @@ SSL_CTX_set_client_cert_cb(SSL_CTX *ctx, | |||
| 1022 | ctx->client_cert_cb = cb; | 1094 | ctx->client_cert_cb = cb; |
| 1023 | } | 1095 | } |
| 1024 | 1096 | ||
| 1025 | int (*SSL_CTX_get_client_cert_cb(SSL_CTX *ctx))(SSL * ssl, X509 ** x509 , EVP_PKEY **pkey) | 1097 | int |
| 1098 | (*SSL_CTX_get_client_cert_cb(SSL_CTX *ctx))(SSL * ssl, X509 ** x509, | ||
| 1099 | EVP_PKEY **pkey) | ||
| 1026 | { | 1100 | { |
| 1027 | return ctx->client_cert_cb; | 1101 | return ctx->client_cert_cb; |
| 1028 | } | 1102 | } |
| @@ -1032,11 +1106,13 @@ int | |||
| 1032 | SSL_CTX_set_client_cert_engine(SSL_CTX *ctx, ENGINE *e) | 1106 | SSL_CTX_set_client_cert_engine(SSL_CTX *ctx, ENGINE *e) |
| 1033 | { | 1107 | { |
| 1034 | if (!ENGINE_init(e)) { | 1108 | if (!ENGINE_init(e)) { |
| 1035 | SSLerr(SSL_F_SSL_CTX_SET_CLIENT_CERT_ENGINE, ERR_R_ENGINE_LIB); | 1109 | SSLerr(SSL_F_SSL_CTX_SET_CLIENT_CERT_ENGINE, |
| 1110 | ERR_R_ENGINE_LIB); | ||
| 1036 | return 0; | 1111 | return 0; |
| 1037 | } | 1112 | } |
| 1038 | if (!ENGINE_get_ssl_client_cert_function(e)) { | 1113 | if (!ENGINE_get_ssl_client_cert_function(e)) { |
| 1039 | SSLerr(SSL_F_SSL_CTX_SET_CLIENT_CERT_ENGINE, SSL_R_NO_CLIENT_CERT_METHOD); | 1114 | SSLerr(SSL_F_SSL_CTX_SET_CLIENT_CERT_ENGINE, |
| 1115 | SSL_R_NO_CLIENT_CERT_METHOD); | ||
| 1040 | ENGINE_finish(e); | 1116 | ENGINE_finish(e); |
| 1041 | return 0; | 1117 | return 0; |
| 1042 | } | 1118 | } |
diff --git a/src/lib/libssl/ssl_sess.c b/src/lib/libssl/ssl_sess.c index af29cfc7ff..101da82b56 100644 --- a/src/lib/libssl/ssl_sess.c +++ b/src/lib/libssl/ssl_sess.c | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: ssl_sess.c,v 1.36 2014/07/11 09:24:44 beck Exp $ */ | 1 | /* $OpenBSD: ssl_sess.c,v 1.37 2014/07/12 23:59:11 jsing Exp $ */ |
| 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) | 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
| 3 | * All rights reserved. | 3 | * All rights reserved. |
| 4 | * | 4 | * |
| @@ -135,12 +135,13 @@ | |||
| 135 | * OTHERWISE. | 135 | * OTHERWISE. |
| 136 | */ | 136 | */ |
| 137 | 137 | ||
| 138 | #include <stdio.h> | ||
| 139 | #include <openssl/lhash.h> | 138 | #include <openssl/lhash.h> |
| 140 | #include <openssl/rand.h> | 139 | #include <openssl/rand.h> |
| 140 | |||
| 141 | #ifndef OPENSSL_NO_ENGINE | 141 | #ifndef OPENSSL_NO_ENGINE |
| 142 | #include <openssl/engine.h> | 142 | #include <openssl/engine.h> |
| 143 | #endif | 143 | #endif |
| 144 | |||
| 144 | #include "ssl_locl.h" | 145 | #include "ssl_locl.h" |
| 145 | 146 | ||
| 146 | static void SSL_SESSION_list_remove(SSL_CTX *ctx, SSL_SESSION *s); | 147 | static void SSL_SESSION_list_remove(SSL_CTX *ctx, SSL_SESSION *s); |
| @@ -159,14 +160,18 @@ SSL_SESSION * | |||
| 159 | SSL_get1_session(SSL *ssl) | 160 | SSL_get1_session(SSL *ssl) |
| 160 | { | 161 | { |
| 161 | SSL_SESSION *sess; | 162 | SSL_SESSION *sess; |
| 162 | /* Need to lock this all up rather than just use CRYPTO_add so that | 163 | |
| 164 | /* | ||
| 165 | * Need to lock this all up rather than just use CRYPTO_add so that | ||
| 163 | * somebody doesn't free ssl->session between when we check it's | 166 | * somebody doesn't free ssl->session between when we check it's |
| 164 | * non-null and when we up the reference count. */ | 167 | * non-null and when we up the reference count. |
| 168 | */ | ||
| 165 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_SESSION); | 169 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_SESSION); |
| 166 | sess = ssl->session; | 170 | sess = ssl->session; |
| 167 | if (sess) | 171 | if (sess) |
| 168 | sess->references++; | 172 | sess->references++; |
| 169 | CRYPTO_w_unlock(CRYPTO_LOCK_SSL_SESSION); | 173 | CRYPTO_w_unlock(CRYPTO_LOCK_SSL_SESSION); |
| 174 | |||
| 170 | return (sess); | 175 | return (sess); |
| 171 | } | 176 | } |
| 172 | 177 | ||
| @@ -174,8 +179,8 @@ int | |||
| 174 | SSL_SESSION_get_ex_new_index(long argl, void *argp, CRYPTO_EX_new *new_func, | 179 | SSL_SESSION_get_ex_new_index(long argl, void *argp, CRYPTO_EX_new *new_func, |
| 175 | CRYPTO_EX_dup *dup_func, CRYPTO_EX_free *free_func) | 180 | CRYPTO_EX_dup *dup_func, CRYPTO_EX_free *free_func) |
| 176 | { | 181 | { |
| 177 | return CRYPTO_get_ex_new_index(CRYPTO_EX_INDEX_SSL_SESSION, argl, argp, | 182 | return CRYPTO_get_ex_new_index(CRYPTO_EX_INDEX_SSL_SESSION, |
| 178 | new_func, dup_func, free_func); | 183 | argl, argp, new_func, dup_func, free_func); |
| 179 | } | 184 | } |
| 180 | 185 | ||
| 181 | int | 186 | int |
| @@ -213,7 +218,9 @@ SSL_SESSION_new(void) | |||
| 213 | ss->tlsext_ecpointformatlist = NULL; | 218 | ss->tlsext_ecpointformatlist = NULL; |
| 214 | ss->tlsext_ellipticcurvelist_length = 0; | 219 | ss->tlsext_ellipticcurvelist_length = 0; |
| 215 | ss->tlsext_ellipticcurvelist = NULL; | 220 | ss->tlsext_ellipticcurvelist = NULL; |
| 221 | |||
| 216 | CRYPTO_new_ex_data(CRYPTO_EX_INDEX_SSL_SESSION, ss, &ss->ex_data); | 222 | CRYPTO_new_ex_data(CRYPTO_EX_INDEX_SSL_SESSION, ss, &ss->ex_data); |
| 223 | |||
| 217 | return (ss); | 224 | return (ss); |
| 218 | } | 225 | } |
| 219 | 226 | ||
| @@ -231,28 +238,34 @@ SSL_SESSION_get_compress_id(const SSL_SESSION *s) | |||
| 231 | return 0; | 238 | return 0; |
| 232 | } | 239 | } |
| 233 | 240 | ||
| 234 | /* Even with SSLv2, we have 16 bytes (128 bits) of session ID space. SSLv3/TLSv1 | 241 | /* |
| 235 | * has 32 bytes (256 bits). As such, filling the ID with random gunk repeatedly | 242 | * Even with SSLv2, we have 16 bytes (128 bits) of session ID space. |
| 236 | * until we have no conflict is going to complete in one iteration pretty much | 243 | * SSLv3/TLSv1 has 32 bytes (256 bits). As such, filling the ID with random |
| 237 | * "most" of the time (btw: understatement). So, if it takes us 10 iterations | 244 | * gunk repeatedly until we have no conflict is going to complete in one |
| 238 | * and we still can't avoid a conflict - well that's a reasonable point to call | 245 | * iteration pretty much "most" of the time (btw: understatement). So, if it |
| 239 | * it quits. Either the RAND code is broken or someone is trying to open roughly | 246 | * takes us 10 iterations and we still can't avoid a conflict - well that's a |
| 240 | * very close to 2^128 (or 2^256) SSL sessions to our server. How you might | 247 | * reasonable point to call it quits. Either the RAND code is broken or someone |
| 241 | * store that many sessions is perhaps a more interesting question ... */ | 248 | * is trying to open roughly very close to 2^128 (or 2^256) SSL sessions to our |
| 249 | * server. How you might store that many sessions is perhaps a more interesting | ||
| 250 | * question... | ||
| 251 | */ | ||
| 242 | 252 | ||
| 243 | #define MAX_SESS_ID_ATTEMPTS 10 | 253 | #define MAX_SESS_ID_ATTEMPTS 10 |
| 254 | |||
| 244 | static int | 255 | static int |
| 245 | def_generate_session_id(const SSL *ssl, unsigned char *id, | 256 | def_generate_session_id(const SSL *ssl, unsigned char *id, unsigned int *id_len) |
| 246 | unsigned int *id_len) | ||
| 247 | { | 257 | { |
| 248 | unsigned int retry = 0; | 258 | unsigned int retry = 0; |
| 249 | do | 259 | |
| 250 | if (RAND_pseudo_bytes(id, *id_len) <= 0) | 260 | do { |
| 251 | return 0; | 261 | if (RAND_pseudo_bytes(id, *id_len) <= 0) |
| 252 | while (SSL_has_matching_session_id(ssl, id, *id_len) && | 262 | return 0; |
| 253 | (++retry < MAX_SESS_ID_ATTEMPTS)); | 263 | } while (SSL_has_matching_session_id(ssl, id, *id_len) && |
| 264 | (++retry < MAX_SESS_ID_ATTEMPTS)); | ||
| 265 | |||
| 254 | if (retry < MAX_SESS_ID_ATTEMPTS) | 266 | if (retry < MAX_SESS_ID_ATTEMPTS) |
| 255 | return 1; | 267 | return 1; |
| 268 | |||
| 256 | /* else - woops a session_id match */ | 269 | /* else - woops a session_id match */ |
| 257 | /* XXX We should also check the external cache -- | 270 | /* XXX We should also check the external cache -- |
| 258 | * but the probability of a collision is negligible, and | 271 | * but the probability of a collision is negligible, and |
| @@ -268,13 +281,14 @@ def_generate_session_id(const SSL *ssl, unsigned char *id, | |||
| 268 | int | 281 | int |
| 269 | ssl_get_new_session(SSL *s, int session) | 282 | ssl_get_new_session(SSL *s, int session) |
| 270 | { | 283 | { |
| 271 | /* This gets used by clients and servers. */ | ||
| 272 | |||
| 273 | unsigned int tmp; | 284 | unsigned int tmp; |
| 274 | SSL_SESSION *ss = NULL; | 285 | SSL_SESSION *ss = NULL; |
| 275 | GEN_SESSION_CB cb = def_generate_session_id; | 286 | GEN_SESSION_CB cb = def_generate_session_id; |
| 276 | 287 | ||
| 277 | if ((ss = SSL_SESSION_new()) == NULL) return (0); | 288 | /* This gets used by clients and servers. */ |
| 289 | |||
| 290 | if ((ss = SSL_SESSION_new()) == NULL) | ||
| 291 | return (0); | ||
| 278 | 292 | ||
| 279 | /* If the context has a default timeout, use it */ | 293 | /* If the context has a default timeout, use it */ |
| 280 | if (s->session_ctx->session_timeout == 0) | 294 | if (s->session_ctx->session_timeout == 0) |
| @@ -304,19 +318,22 @@ ssl_get_new_session(SSL *s, int session) | |||
| 304 | SSL_SESSION_free(ss); | 318 | SSL_SESSION_free(ss); |
| 305 | return (0); | 319 | return (0); |
| 306 | } | 320 | } |
| 307 | /* If RFC4507 ticket use empty session ID */ | 321 | |
| 322 | /* If RFC4507 ticket use empty session ID. */ | ||
| 308 | if (s->tlsext_ticket_expected) { | 323 | if (s->tlsext_ticket_expected) { |
| 309 | ss->session_id_length = 0; | 324 | ss->session_id_length = 0; |
| 310 | goto sess_id_done; | 325 | goto sess_id_done; |
| 311 | } | 326 | } |
| 312 | /* Choose which callback will set the session ID */ | 327 | |
| 328 | /* Choose which callback will set the session ID. */ | ||
| 313 | CRYPTO_r_lock(CRYPTO_LOCK_SSL_CTX); | 329 | CRYPTO_r_lock(CRYPTO_LOCK_SSL_CTX); |
| 314 | if (s->generate_session_id) | 330 | if (s->generate_session_id) |
| 315 | cb = s->generate_session_id; | 331 | cb = s->generate_session_id; |
| 316 | else if (s->session_ctx->generate_session_id) | 332 | else if (s->session_ctx->generate_session_id) |
| 317 | cb = s->session_ctx->generate_session_id; | 333 | cb = s->session_ctx->generate_session_id; |
| 318 | CRYPTO_r_unlock(CRYPTO_LOCK_SSL_CTX); | 334 | CRYPTO_r_unlock(CRYPTO_LOCK_SSL_CTX); |
| 319 | /* Choose a session ID */ | 335 | |
| 336 | /* Choose a session ID. */ | ||
| 320 | tmp = ss->session_id_length; | 337 | tmp = ss->session_id_length; |
| 321 | if (!cb(s, ss->session_id, &tmp)) { | 338 | if (!cb(s, ss->session_id, &tmp)) { |
| 322 | /* The callback failed */ | 339 | /* The callback failed */ |
| @@ -325,8 +342,11 @@ ssl_get_new_session(SSL *s, int session) | |||
| 325 | SSL_SESSION_free(ss); | 342 | SSL_SESSION_free(ss); |
| 326 | return (0); | 343 | return (0); |
| 327 | } | 344 | } |
| 328 | /* Don't allow the callback to set the session length to zero. | 345 | |
| 329 | * nor set it higher than it was. */ | 346 | /* |
| 347 | * Don't allow the callback to set the session length to zero. | ||
| 348 | * nor set it higher than it was. | ||
| 349 | */ | ||
| 330 | if (!tmp || (tmp > ss->session_id_length)) { | 350 | if (!tmp || (tmp > ss->session_id_length)) { |
| 331 | /* The callback set an illegal length */ | 351 | /* The callback set an illegal length */ |
| 332 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, | 352 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, |
| @@ -335,7 +355,8 @@ ssl_get_new_session(SSL *s, int session) | |||
| 335 | return (0); | 355 | return (0); |
| 336 | } | 356 | } |
| 337 | ss->session_id_length = tmp; | 357 | ss->session_id_length = tmp; |
| 338 | /* Finally, check for a conflict */ | 358 | |
| 359 | /* Finally, check for a conflict. */ | ||
| 339 | if (SSL_has_matching_session_id(s, ss->session_id, | 360 | if (SSL_has_matching_session_id(s, ss->session_id, |
| 340 | ss->session_id_length)) { | 361 | ss->session_id_length)) { |
| 341 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, | 362 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, |
| @@ -343,11 +364,13 @@ ssl_get_new_session(SSL *s, int session) | |||
| 343 | SSL_SESSION_free(ss); | 364 | SSL_SESSION_free(ss); |
| 344 | return (0); | 365 | return (0); |
| 345 | } | 366 | } |
| 346 | sess_id_done: | 367 | |
| 368 | sess_id_done: | ||
| 347 | if (s->tlsext_hostname) { | 369 | if (s->tlsext_hostname) { |
| 348 | ss->tlsext_hostname = BUF_strdup(s->tlsext_hostname); | 370 | ss->tlsext_hostname = BUF_strdup(s->tlsext_hostname); |
| 349 | if (ss->tlsext_hostname == NULL) { | 371 | if (ss->tlsext_hostname == NULL) { |
| 350 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, ERR_R_INTERNAL_ERROR); | 372 | SSLerr(SSL_F_SSL_GET_NEW_SESSION, |
| 373 | ERR_R_INTERNAL_ERROR); | ||
| 351 | SSL_SESSION_free(ss); | 374 | SSL_SESSION_free(ss); |
| 352 | return 0; | 375 | return 0; |
| 353 | } | 376 | } |
| @@ -381,6 +404,7 @@ ssl_get_new_session(SSL *s, int session) | |||
| 381 | SSL_SESSION_free(ss); | 404 | SSL_SESSION_free(ss); |
| 382 | return 0; | 405 | return 0; |
| 383 | } | 406 | } |
| 407 | |||
| 384 | memcpy(ss->sid_ctx, s->sid_ctx, s->sid_ctx_length); | 408 | memcpy(ss->sid_ctx, s->sid_ctx, s->sid_ctx_length); |
| 385 | ss->sid_ctx_length = s->sid_ctx_length; | 409 | ss->sid_ctx_length = s->sid_ctx_length; |
| 386 | s->session = ss; | 410 | s->session = ss; |
| @@ -390,7 +414,8 @@ ssl_get_new_session(SSL *s, int session) | |||
| 390 | return (1); | 414 | return (1); |
| 391 | } | 415 | } |
| 392 | 416 | ||
| 393 | /* ssl_get_prev attempts to find an SSL_SESSION to be used to resume this | 417 | /* |
| 418 | * ssl_get_prev attempts to find an SSL_SESSION to be used to resume this | ||
| 394 | * connection. It is only called by servers. | 419 | * connection. It is only called by servers. |
| 395 | * | 420 | * |
| 396 | * session_id: points at the session ID in the ClientHello. This code will | 421 | * session_id: points at the session ID in the ClientHello. This code will |
| @@ -404,29 +429,31 @@ ssl_get_new_session(SSL *s, int session) | |||
| 404 | * 0: a session may have been found. | 429 | * 0: a session may have been found. |
| 405 | * | 430 | * |
| 406 | * Side effects: | 431 | * Side effects: |
| 407 | * - If a session is found then s->session is pointed at it (after freeing an | 432 | * - If a session is found then s->session is pointed at it (after freeing |
| 408 | * existing session if need be) and s->verify_result is set from the session. | 433 | * an existing session if need be) and s->verify_result is set from the |
| 409 | * - Both for new and resumed sessions, s->tlsext_ticket_expected is set to 1 | 434 | * session. |
| 410 | * if the server should issue a new session ticket (to 0 otherwise). | 435 | * - Both for new and resumed sessions, s->tlsext_ticket_expected is set |
| 436 | * to 1 if the server should issue a new session ticket (to 0 otherwise). | ||
| 411 | */ | 437 | */ |
| 412 | int | 438 | int |
| 413 | ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | 439 | ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, |
| 414 | const unsigned char *limit) | 440 | const unsigned char *limit) |
| 415 | { | 441 | { |
| 416 | /* This is used only by servers. */ | ||
| 417 | |||
| 418 | SSL_SESSION *ret = NULL; | 442 | SSL_SESSION *ret = NULL; |
| 419 | int fatal = 0; | 443 | int fatal = 0; |
| 420 | int try_session_cache = 1; | 444 | int try_session_cache = 1; |
| 421 | int r; | 445 | int r; |
| 422 | 446 | ||
| 447 | /* This is used only by servers. */ | ||
| 448 | |||
| 423 | if (len > SSL_MAX_SSL_SESSION_ID_LENGTH) | 449 | if (len > SSL_MAX_SSL_SESSION_ID_LENGTH) |
| 424 | goto err; | 450 | goto err; |
| 425 | 451 | ||
| 426 | if (len == 0) | 452 | if (len == 0) |
| 427 | try_session_cache = 0; | 453 | try_session_cache = 0; |
| 428 | 454 | ||
| 429 | r = tls1_process_ticket(s, session_id, len, limit, &ret); /* sets s->tlsext_ticket_expected */ | 455 | /* Sets s->tlsext_ticket_expected. */ |
| 456 | r = tls1_process_ticket(s, session_id, len, limit, &ret); | ||
| 430 | switch (r) { | 457 | switch (r) { |
| 431 | case -1: /* Error during processing */ | 458 | case -1: /* Error during processing */ |
| 432 | fatal = 1; | 459 | fatal = 1; |
| @@ -442,48 +469,60 @@ ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | |||
| 442 | abort(); | 469 | abort(); |
| 443 | } | 470 | } |
| 444 | 471 | ||
| 445 | if (try_session_cache && | 472 | if (try_session_cache && ret == NULL && |
| 446 | ret == NULL && | 473 | !(s->session_ctx->session_cache_mode & |
| 447 | !(s->session_ctx->session_cache_mode & SSL_SESS_CACHE_NO_INTERNAL_LOOKUP)) { | 474 | SSL_SESS_CACHE_NO_INTERNAL_LOOKUP)) { |
| 448 | SSL_SESSION data; | 475 | SSL_SESSION data; |
| 449 | data.ssl_version = s->version; | 476 | data.ssl_version = s->version; |
| 450 | data.session_id_length = len; | 477 | data.session_id_length = len; |
| 451 | if (len == 0) | 478 | if (len == 0) |
| 452 | return 0; | 479 | return 0; |
| 453 | memcpy(data.session_id, session_id, len); | 480 | memcpy(data.session_id, session_id, len); |
| 481 | |||
| 454 | CRYPTO_r_lock(CRYPTO_LOCK_SSL_CTX); | 482 | CRYPTO_r_lock(CRYPTO_LOCK_SSL_CTX); |
| 455 | ret = lh_SSL_SESSION_retrieve(s->session_ctx->sessions, &data); | 483 | ret = lh_SSL_SESSION_retrieve(s->session_ctx->sessions, &data); |
| 456 | if (ret != NULL) { | 484 | if (ret != NULL) { |
| 457 | /* don't allow other threads to steal it: */ | 485 | /* Don't allow other threads to steal it. */ |
| 458 | CRYPTO_add(&ret->references, 1, CRYPTO_LOCK_SSL_SESSION); | 486 | CRYPTO_add(&ret->references, 1, |
| 487 | CRYPTO_LOCK_SSL_SESSION); | ||
| 459 | } | 488 | } |
| 460 | CRYPTO_r_unlock(CRYPTO_LOCK_SSL_CTX); | 489 | CRYPTO_r_unlock(CRYPTO_LOCK_SSL_CTX); |
| 490 | |||
| 461 | if (ret == NULL) | 491 | if (ret == NULL) |
| 462 | s->session_ctx->stats.sess_miss++; | 492 | s->session_ctx->stats.sess_miss++; |
| 463 | } | 493 | } |
| 464 | 494 | ||
| 465 | if (try_session_cache && | 495 | if (try_session_cache && ret == NULL && |
| 466 | ret == NULL && | 496 | s->session_ctx->get_session_cb != NULL) { |
| 467 | s->session_ctx->get_session_cb != NULL) { | ||
| 468 | int copy = 1; | 497 | int copy = 1; |
| 469 | 498 | ||
| 470 | if ((ret = s->session_ctx->get_session_cb(s, session_id, len, ©))) { | 499 | if ((ret = s->session_ctx->get_session_cb(s, session_id, |
| 500 | len, ©))) { | ||
| 471 | s->session_ctx->stats.sess_cb_hit++; | 501 | s->session_ctx->stats.sess_cb_hit++; |
| 472 | 502 | ||
| 473 | /* Increment reference count now if the session callback | 503 | /* |
| 474 | * asks us to do so (note that if the session structures | 504 | * Increment reference count now if the session |
| 475 | * returned by the callback are shared between threads, | 505 | * callback asks us to do so (note that if the session |
| 476 | * it must handle the reference count itself [i.e. copy == 0], | 506 | * structures returned by the callback are shared |
| 477 | * or things won't be thread-safe). */ | 507 | * between threads, it must handle the reference count |
| 508 | * itself [i.e. copy == 0], or things won't be | ||
| 509 | * thread-safe). | ||
| 510 | */ | ||
| 478 | if (copy) | 511 | if (copy) |
| 479 | CRYPTO_add(&ret->references, 1, CRYPTO_LOCK_SSL_SESSION); | 512 | CRYPTO_add(&ret->references, 1, |
| 480 | 513 | CRYPTO_LOCK_SSL_SESSION); | |
| 481 | /* Add the externally cached session to the internal | 514 | |
| 482 | * cache as well if and only if we are supposed to. */ | 515 | /* |
| 483 | if (!(s->session_ctx->session_cache_mode & SSL_SESS_CACHE_NO_INTERNAL_STORE)) | 516 | * Add the externally cached session to the internal |
| 484 | /* The following should not return 1, otherwise, | 517 | * cache as well if and only if we are supposed to. |
| 485 | * things are very strange */ | 518 | */ |
| 486 | SSL_CTX_add_session(s->session_ctx, ret); | 519 | if (!(s->session_ctx->session_cache_mode & |
| 520 | SSL_SESS_CACHE_NO_INTERNAL_STORE)) | ||
| 521 | /* | ||
| 522 | * The following should not return 1, | ||
| 523 | * otherwise, things are very strange. | ||
| 524 | */ | ||
| 525 | SSL_CTX_add_session(s->session_ctx, ret); | ||
| 487 | } | 526 | } |
| 488 | } | 527 | } |
| 489 | 528 | ||
| @@ -492,25 +531,28 @@ ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | |||
| 492 | 531 | ||
| 493 | /* Now ret is non-NULL and we own one of its reference counts. */ | 532 | /* Now ret is non-NULL and we own one of its reference counts. */ |
| 494 | 533 | ||
| 495 | if (ret->sid_ctx_length != s->sid_ctx_length | 534 | if (ret->sid_ctx_length != s->sid_ctx_length || |
| 496 | || timingsafe_memcmp(ret->sid_ctx, s->sid_ctx, ret->sid_ctx_length) != 0) { | 535 | timingsafe_memcmp(ret->sid_ctx, |
| 536 | s->sid_ctx, ret->sid_ctx_length) != 0) { | ||
| 497 | /* We have the session requested by the client, but we don't | 537 | /* We have the session requested by the client, but we don't |
| 498 | * want to use it in this context. */ | 538 | * want to use it in this context. */ |
| 499 | goto err; /* treat like cache miss */ | 539 | goto err; /* treat like cache miss */ |
| 500 | } | 540 | } |
| 501 | 541 | ||
| 502 | if ((s->verify_mode & SSL_VERIFY_PEER) && s->sid_ctx_length == 0) { | 542 | if ((s->verify_mode & SSL_VERIFY_PEER) && s->sid_ctx_length == 0) { |
| 503 | /* We can't be sure if this session is being used out of | 543 | /* |
| 544 | * We can't be sure if this session is being used out of | ||
| 504 | * context, which is especially important for SSL_VERIFY_PEER. | 545 | * context, which is especially important for SSL_VERIFY_PEER. |
| 505 | * The application should have used SSL[_CTX]_set_session_id_context. | 546 | * The application should have used |
| 547 | * SSL[_CTX]_set_session_id_context. | ||
| 506 | * | 548 | * |
| 507 | * For this error case, we generate an error instead of treating | 549 | * For this error case, we generate an error instead of treating |
| 508 | * the event like a cache miss (otherwise it would be easy for | 550 | * the event like a cache miss (otherwise it would be easy for |
| 509 | * applications to effectively disable the session cache by | 551 | * applications to effectively disable the session cache by |
| 510 | * accident without anyone noticing). | 552 | * accident without anyone noticing). |
| 511 | */ | 553 | */ |
| 512 | 554 | SSLerr(SSL_F_SSL_GET_PREV_SESSION, | |
| 513 | SSLerr(SSL_F_SSL_GET_PREV_SESSION, SSL_R_SESSION_ID_CONTEXT_UNINITIALIZED); | 555 | SSL_R_SESSION_ID_CONTEXT_UNINITIALIZED); |
| 514 | fatal = 1; | 556 | fatal = 1; |
| 515 | goto err; | 557 | goto err; |
| 516 | } | 558 | } |
| @@ -522,16 +564,18 @@ ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | |||
| 522 | p = buf; | 564 | p = buf; |
| 523 | l = ret->cipher_id; | 565 | l = ret->cipher_id; |
| 524 | l2n(l, p); | 566 | l2n(l, p); |
| 567 | |||
| 525 | if ((ret->ssl_version >> 8) >= SSL3_VERSION_MAJOR) | 568 | if ((ret->ssl_version >> 8) >= SSL3_VERSION_MAJOR) |
| 526 | ret->cipher = ssl_get_cipher_by_char(s, &(buf[2])); | 569 | ret->cipher = ssl_get_cipher_by_char(s, &(buf[2])); |
| 527 | else | 570 | else |
| 528 | ret->cipher = ssl_get_cipher_by_char(s, &(buf[1])); | 571 | ret->cipher = ssl_get_cipher_by_char(s, &(buf[1])); |
| 572 | |||
| 529 | if (ret->cipher == NULL) | 573 | if (ret->cipher == NULL) |
| 530 | goto err; | 574 | goto err; |
| 531 | } | 575 | } |
| 532 | 576 | ||
| 533 | if (ret->timeout < (time(NULL) - ret->time)) /* timeout */ | 577 | if (ret->timeout < (time(NULL) - ret->time)) { |
| 534 | { | 578 | /* timeout */ |
| 535 | s->session_ctx->stats.sess_timeout++; | 579 | s->session_ctx->stats.sess_timeout++; |
| 536 | if (try_session_cache) { | 580 | if (try_session_cache) { |
| 537 | /* session was from the cache, so remove it */ | 581 | /* session was from the cache, so remove it */ |
| @@ -548,12 +592,14 @@ ssl_get_prev_session(SSL *s, unsigned char *session_id, int len, | |||
| 548 | s->verify_result = s->session->verify_result; | 592 | s->verify_result = s->session->verify_result; |
| 549 | return 1; | 593 | return 1; |
| 550 | 594 | ||
| 551 | err: | 595 | err: |
| 552 | if (ret != NULL) { | 596 | if (ret != NULL) { |
| 553 | SSL_SESSION_free(ret); | 597 | SSL_SESSION_free(ret); |
| 554 | if (!try_session_cache) { | 598 | if (!try_session_cache) { |
| 555 | /* The session was from a ticket, so we should | 599 | /* |
| 556 | * issue a ticket for the new session */ | 600 | * The session was from a ticket, so we should |
| 601 | * issue a ticket for the new session. | ||
| 602 | */ | ||
| 557 | s->tlsext_ticket_expected = 1; | 603 | s->tlsext_ticket_expected = 1; |
| 558 | } | 604 | } |
| 559 | } | 605 | } |
| @@ -569,27 +615,36 @@ SSL_CTX_add_session(SSL_CTX *ctx, SSL_SESSION *c) | |||
| 569 | int ret = 0; | 615 | int ret = 0; |
| 570 | SSL_SESSION *s; | 616 | SSL_SESSION *s; |
| 571 | 617 | ||
| 572 | /* add just 1 reference count for the SSL_CTX's session cache | 618 | /* |
| 619 | * Add just 1 reference count for the SSL_CTX's session cache | ||
| 573 | * even though it has two ways of access: each session is in a | 620 | * even though it has two ways of access: each session is in a |
| 574 | * doubly linked list and an lhash */ | 621 | * doubly linked list and an lhash. |
| 622 | */ | ||
| 575 | CRYPTO_add(&c->references, 1, CRYPTO_LOCK_SSL_SESSION); | 623 | CRYPTO_add(&c->references, 1, CRYPTO_LOCK_SSL_SESSION); |
| 576 | /* if session c is in already in cache, we take back the increment later */ | ||
| 577 | 624 | ||
| 625 | /* | ||
| 626 | * If session c is in already in cache, we take back the increment | ||
| 627 | * later. | ||
| 628 | */ | ||
| 578 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_CTX); | 629 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_CTX); |
| 579 | s = lh_SSL_SESSION_insert(ctx->sessions, c); | 630 | s = lh_SSL_SESSION_insert(ctx->sessions, c); |
| 580 | 631 | ||
| 581 | /* s != NULL iff we already had a session with the given PID. | 632 | /* |
| 633 | * s != NULL iff we already had a session with the given PID. | ||
| 582 | * In this case, s == c should hold (then we did not really modify | 634 | * In this case, s == c should hold (then we did not really modify |
| 583 | * ctx->sessions), or we're in trouble. */ | 635 | * ctx->sessions), or we're in trouble. |
| 636 | */ | ||
| 584 | if (s != NULL && s != c) { | 637 | if (s != NULL && s != c) { |
| 585 | /* We *are* in trouble ... */ | 638 | /* We *are* in trouble ... */ |
| 586 | SSL_SESSION_list_remove(ctx, s); | 639 | SSL_SESSION_list_remove(ctx, s); |
| 587 | SSL_SESSION_free(s); | 640 | SSL_SESSION_free(s); |
| 588 | /* ... so pretend the other session did not exist in cache | 641 | /* |
| 642 | * ... so pretend the other session did not exist in cache | ||
| 589 | * (we cannot handle two SSL_SESSION structures with identical | 643 | * (we cannot handle two SSL_SESSION structures with identical |
| 590 | * session ID in the same cache, which could happen e.g. when | 644 | * session ID in the same cache, which could happen e.g. when |
| 591 | * two threads concurrently obtain the same session from an external | 645 | * two threads concurrently obtain the same session from an |
| 592 | * cache) */ | 646 | * external cache). |
| 647 | */ | ||
| 593 | s = NULL; | 648 | s = NULL; |
| 594 | } | 649 | } |
| 595 | 650 | ||
| @@ -598,22 +653,27 @@ SSL_CTX_add_session(SSL_CTX *ctx, SSL_SESSION *c) | |||
| 598 | SSL_SESSION_list_add(ctx, c); | 653 | SSL_SESSION_list_add(ctx, c); |
| 599 | 654 | ||
| 600 | if (s != NULL) { | 655 | if (s != NULL) { |
| 601 | /* existing cache entry -- decrement previously incremented reference | 656 | /* |
| 602 | * count because it already takes into account the cache */ | 657 | * existing cache entry -- decrement previously incremented |
| 603 | 658 | * reference count because it already takes into account the | |
| 659 | * cache. | ||
| 660 | */ | ||
| 604 | SSL_SESSION_free(s); /* s == c */ | 661 | SSL_SESSION_free(s); /* s == c */ |
| 605 | ret = 0; | 662 | ret = 0; |
| 606 | } else { | 663 | } else { |
| 607 | /* new cache entry -- remove old ones if cache has become too large */ | 664 | /* |
| 665 | * New cache entry -- remove old ones if cache has become | ||
| 666 | * too large. | ||
| 667 | */ | ||
| 608 | 668 | ||
| 609 | ret = 1; | 669 | ret = 1; |
| 610 | 670 | ||
| 611 | if (SSL_CTX_sess_get_cache_size(ctx) > 0) { | 671 | if (SSL_CTX_sess_get_cache_size(ctx) > 0) { |
| 612 | while (SSL_CTX_sess_number(ctx) > | 672 | while (SSL_CTX_sess_number(ctx) > |
| 613 | SSL_CTX_sess_get_cache_size(ctx)) { | 673 | SSL_CTX_sess_get_cache_size(ctx)) { |
| 614 | if (!remove_session_lock(ctx, | 674 | if (!remove_session_lock(ctx, |
| 615 | ctx->session_cache_tail, 0)) | 675 | ctx->session_cache_tail, 0)) |
| 616 | break; | 676 | break; |
| 617 | else | 677 | else |
| 618 | ctx->stats.sess_cache_full++; | 678 | ctx->stats.sess_cache_full++; |
| 619 | } | 679 | } |
| @@ -638,12 +698,11 @@ remove_session_lock(SSL_CTX *ctx, SSL_SESSION *c, int lck) | |||
| 638 | if ((c != NULL) && (c->session_id_length != 0)) { | 698 | if ((c != NULL) && (c->session_id_length != 0)) { |
| 639 | if (lck) | 699 | if (lck) |
| 640 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_CTX); | 700 | CRYPTO_w_lock(CRYPTO_LOCK_SSL_CTX); |
| 641 | if ((r = lh_SSL_SESSION_retrieve(ctx->sessions, c)) == c) { | 701 | if ((r = lh_SSL_SESSION_retrieve(ctx->sessions, c)) == c) { |
| 642 | ret = 1; | 702 | ret = 1; |
| 643 | r = lh_SSL_SESSION_delete(ctx->sessions, c); | 703 | r = lh_SSL_SESSION_delete(ctx->sessions, c); |
| 644 | SSL_SESSION_list_remove(ctx, c); | 704 | SSL_SESSION_list_remove(ctx, c); |
| 645 | } | 705 | } |
| 646 | |||
| 647 | if (lck) | 706 | if (lck) |
| 648 | CRYPTO_w_unlock(CRYPTO_LOCK_SSL_CTX); | 707 | CRYPTO_w_unlock(CRYPTO_LOCK_SSL_CTX); |
| 649 | 708 | ||
| @@ -701,7 +760,8 @@ SSL_set_session(SSL *s, SSL_SESSION *session) | |||
| 701 | if (meth == NULL) | 760 | if (meth == NULL) |
| 702 | meth = s->method->get_ssl_method(session->ssl_version); | 761 | meth = s->method->get_ssl_method(session->ssl_version); |
| 703 | if (meth == NULL) { | 762 | if (meth == NULL) { |
| 704 | SSLerr(SSL_F_SSL_SET_SESSION, SSL_R_UNABLE_TO_FIND_SSL_METHOD); | 763 | SSLerr(SSL_F_SSL_SET_SESSION, |
| 764 | SSL_R_UNABLE_TO_FIND_SSL_METHOD); | ||
| 705 | return (0); | 765 | return (0); |
| 706 | } | 766 | } |
| 707 | 767 | ||
| @@ -782,7 +842,8 @@ SSL_SESSION_set1_id_context(SSL_SESSION *s, const unsigned char *sid_ctx, | |||
| 782 | unsigned int sid_ctx_len) | 842 | unsigned int sid_ctx_len) |
| 783 | { | 843 | { |
| 784 | if (sid_ctx_len > SSL_MAX_SID_CTX_LENGTH) { | 844 | if (sid_ctx_len > SSL_MAX_SID_CTX_LENGTH) { |
| 785 | SSLerr(SSL_F_SSL_SESSION_SET1_ID_CONTEXT, SSL_R_SSL_SESSION_ID_CONTEXT_TOO_LONG); | 845 | SSLerr(SSL_F_SSL_SESSION_SET1_ID_CONTEXT, |
| 846 | SSL_R_SSL_SESSION_ID_CONTEXT_TOO_LONG); | ||
| 786 | return 0; | 847 | return 0; |
| 787 | } | 848 | } |
| 788 | s->sid_ctx_length = sid_ctx_len; | 849 | s->sid_ctx_length = sid_ctx_len; |
| @@ -795,10 +856,12 @@ long | |||
| 795 | SSL_CTX_set_timeout(SSL_CTX *s, long t) | 856 | SSL_CTX_set_timeout(SSL_CTX *s, long t) |
| 796 | { | 857 | { |
| 797 | long l; | 858 | long l; |
| 859 | |||
| 798 | if (s == NULL) | 860 | if (s == NULL) |
| 799 | return (0); | 861 | return (0); |
| 800 | l = s->session_timeout; | 862 | l = s->session_timeout; |
| 801 | s->session_timeout = t; | 863 | s->session_timeout = t; |
| 864 | |||
| 802 | return (l); | 865 | return (l); |
| 803 | } | 866 | } |
| 804 | 867 | ||
| @@ -811,8 +874,9 @@ SSL_CTX_get_timeout(const SSL_CTX *s) | |||
| 811 | } | 874 | } |
| 812 | 875 | ||
| 813 | int | 876 | int |
| 814 | SSL_set_session_secret_cb(SSL *s, int (*tls_session_secret_cb)(SSL *s, void *secret, int *secret_len, | 877 | SSL_set_session_secret_cb(SSL *s, int (*tls_session_secret_cb)(SSL *s, |
| 815 | STACK_OF(SSL_CIPHER) *peer_ciphers, SSL_CIPHER **cipher, void *arg), void *arg) | 878 | void *secret, int *secret_len, STACK_OF(SSL_CIPHER) *peer_ciphers, |
| 879 | SSL_CIPHER **cipher, void *arg), void *arg) | ||
| 816 | { | 880 | { |
| 817 | if (s == NULL) | 881 | if (s == NULL) |
| 818 | return (0); | 882 | return (0); |
| @@ -837,16 +901,20 @@ SSL_set_session_ticket_ext(SSL *s, void *ext_data, int ext_len) | |||
| 837 | { | 901 | { |
| 838 | if (s->version >= TLS1_VERSION) { | 902 | if (s->version >= TLS1_VERSION) { |
| 839 | free(s->tlsext_session_ticket); | 903 | free(s->tlsext_session_ticket); |
| 840 | s->tlsext_session_ticket = malloc(sizeof(TLS_SESSION_TICKET_EXT) + ext_len); | 904 | s->tlsext_session_ticket = |
| 905 | malloc(sizeof(TLS_SESSION_TICKET_EXT) + ext_len); | ||
| 841 | if (!s->tlsext_session_ticket) { | 906 | if (!s->tlsext_session_ticket) { |
| 842 | SSLerr(SSL_F_SSL_SET_SESSION_TICKET_EXT, ERR_R_MALLOC_FAILURE); | 907 | SSLerr(SSL_F_SSL_SET_SESSION_TICKET_EXT, |
| 908 | ERR_R_MALLOC_FAILURE); | ||
| 843 | return 0; | 909 | return 0; |
| 844 | } | 910 | } |
| 845 | 911 | ||
| 846 | if (ext_data) { | 912 | if (ext_data) { |
| 847 | s->tlsext_session_ticket->length = ext_len; | 913 | s->tlsext_session_ticket->length = ext_len; |
| 848 | s->tlsext_session_ticket->data = s->tlsext_session_ticket + 1; | 914 | s->tlsext_session_ticket->data = |
| 849 | memcpy(s->tlsext_session_ticket->data, ext_data, ext_len); | 915 | s->tlsext_session_ticket + 1; |
| 916 | memcpy(s->tlsext_session_ticket->data, | ||
| 917 | ext_data, ext_len); | ||
| 850 | } else { | 918 | } else { |
| 851 | s->tlsext_session_ticket->length = 0; | 919 | s->tlsext_session_ticket->length = 0; |
| 852 | s->tlsext_session_ticket->data = NULL; | 920 | s->tlsext_session_ticket->data = NULL; |
| @@ -867,8 +935,8 @@ typedef struct timeout_param_st { | |||
| 867 | static void | 935 | static void |
| 868 | timeout_doall_arg(SSL_SESSION *s, TIMEOUT_PARAM *p) | 936 | timeout_doall_arg(SSL_SESSION *s, TIMEOUT_PARAM *p) |
| 869 | { | 937 | { |
| 870 | if ((p->time == 0) || (p->time > (s->time + s->timeout))) /* timeout */ | 938 | if ((p->time == 0) || (p->time > (s->time + s->timeout))) { |
| 871 | { | 939 | /* timeout */ |
| 872 | /* The reason we don't call SSL_CTX_remove_session() is to | 940 | /* The reason we don't call SSL_CTX_remove_session() is to |
| 873 | * save on locking overhead */ | 941 | * save on locking overhead */ |
| 874 | (void)lh_SSL_SESSION_delete(p->cache, s); | 942 | (void)lh_SSL_SESSION_delete(p->cache, s); |
| @@ -907,9 +975,8 @@ SSL_CTX_flush_sessions(SSL_CTX *s, long t) | |||
| 907 | int | 975 | int |
| 908 | ssl_clear_bad_session(SSL *s) | 976 | ssl_clear_bad_session(SSL *s) |
| 909 | { | 977 | { |
| 910 | if ((s->session != NULL) && | 978 | if ((s->session != NULL) && !(s->shutdown & SSL_SENT_SHUTDOWN) && |
| 911 | !(s->shutdown & SSL_SENT_SHUTDOWN) && | 979 | !(SSL_in_init(s) || SSL_in_before(s))) { |
| 912 | !(SSL_in_init(s) || SSL_in_before(s))) { | ||
| 913 | SSL_CTX_remove_session(s->ctx, s->session); | 980 | SSL_CTX_remove_session(s->ctx, s->session); |
| 914 | return (1); | 981 | return (1); |
| 915 | } else | 982 | } else |
| @@ -920,26 +987,28 @@ ssl_clear_bad_session(SSL *s) | |||
| 920 | static void | 987 | static void |
| 921 | SSL_SESSION_list_remove(SSL_CTX *ctx, SSL_SESSION *s) | 988 | SSL_SESSION_list_remove(SSL_CTX *ctx, SSL_SESSION *s) |
| 922 | { | 989 | { |
| 923 | if ((s->next == NULL) | 990 | if ((s->next == NULL) || (s->prev == NULL)) |
| 924 | || (s->prev == NULL)) return; | 991 | return; |
| 925 | 992 | ||
| 926 | if (s->next == (SSL_SESSION *)&(ctx->session_cache_tail)) | 993 | if (s->next == (SSL_SESSION *)&(ctx->session_cache_tail)) { |
| 927 | { /* last element in list */ | 994 | /* last element in list */ |
| 928 | if (s->prev == (SSL_SESSION *)&(ctx->session_cache_head)) | 995 | if (s->prev == (SSL_SESSION *)&(ctx->session_cache_head)) { |
| 929 | { /* only one element in list */ | 996 | /* only one element in list */ |
| 930 | ctx->session_cache_head = NULL; | 997 | ctx->session_cache_head = NULL; |
| 931 | ctx->session_cache_tail = NULL; | 998 | ctx->session_cache_tail = NULL; |
| 932 | } else { | 999 | } else { |
| 933 | ctx->session_cache_tail = s->prev; | 1000 | ctx->session_cache_tail = s->prev; |
| 934 | s->prev->next = (SSL_SESSION *)&(ctx->session_cache_tail); | 1001 | s->prev->next = |
| 1002 | (SSL_SESSION *)&(ctx->session_cache_tail); | ||
| 935 | } | 1003 | } |
| 936 | } else { | 1004 | } else { |
| 937 | if (s->prev == (SSL_SESSION *)&(ctx->session_cache_head)) | 1005 | if (s->prev == (SSL_SESSION *)&(ctx->session_cache_head)) { |
| 938 | { /* first element in list */ | 1006 | /* first element in list */ |
| 939 | ctx->session_cache_head = s->next; | 1007 | ctx->session_cache_head = s->next; |
| 940 | s->next->prev = (SSL_SESSION *)&(ctx->session_cache_head); | 1008 | s->next->prev = |
| 941 | } else | 1009 | (SSL_SESSION *)&(ctx->session_cache_head); |
| 942 | { /* middle of list */ | 1010 | } else { |
| 1011 | /* middle of list */ | ||
| 943 | s->next->prev = s->prev; | 1012 | s->next->prev = s->prev; |
| 944 | s->prev->next = s->next; | 1013 | s->prev->next = s->next; |
| 945 | } | 1014 | } |
| @@ -972,7 +1041,8 @@ SSL_CTX_sess_set_new_cb(SSL_CTX *ctx, | |||
| 972 | ctx->new_session_cb = cb; | 1041 | ctx->new_session_cb = cb; |
| 973 | } | 1042 | } |
| 974 | 1043 | ||
| 975 | int (*SSL_CTX_sess_get_new_cb(SSL_CTX *ctx))(SSL *ssl, SSL_SESSION *sess) | 1044 | int |
| 1045 | (*SSL_CTX_sess_get_new_cb(SSL_CTX *ctx))(SSL *ssl, SSL_SESSION *sess) | ||
| 976 | { | 1046 | { |
| 977 | return ctx->new_session_cb; | 1047 | return ctx->new_session_cb; |
| 978 | } | 1048 | } |
| @@ -984,21 +1054,22 @@ SSL_CTX_sess_set_remove_cb(SSL_CTX *ctx, | |||
| 984 | ctx->remove_session_cb = cb; | 1054 | ctx->remove_session_cb = cb; |
| 985 | } | 1055 | } |
| 986 | 1056 | ||
| 987 | void (*SSL_CTX_sess_get_remove_cb(SSL_CTX *ctx))(SSL_CTX * ctx, SSL_SESSION *sess) | 1057 | void |
| 1058 | (*SSL_CTX_sess_get_remove_cb(SSL_CTX *ctx))(SSL_CTX * ctx, SSL_SESSION *sess) | ||
| 988 | { | 1059 | { |
| 989 | return ctx->remove_session_cb; | 1060 | return ctx->remove_session_cb; |
| 990 | } | 1061 | } |
| 991 | 1062 | ||
| 992 | void | 1063 | void |
| 993 | SSL_CTX_sess_set_get_cb(SSL_CTX *ctx, | 1064 | SSL_CTX_sess_set_get_cb(SSL_CTX *ctx, SSL_SESSION *(*cb)(struct ssl_st *ssl, |
| 994 | SSL_SESSION *(*cb)(struct ssl_st *ssl, | 1065 | unsigned char *data, int len, int *copy)) |
| 995 | unsigned char *data, int len, int *copy)) | ||
| 996 | { | 1066 | { |
| 997 | ctx->get_session_cb = cb; | 1067 | ctx->get_session_cb = cb; |
| 998 | } | 1068 | } |
| 999 | 1069 | ||
| 1000 | SSL_SESSION * (*SSL_CTX_sess_get_get_cb(SSL_CTX *ctx))(SSL *ssl, | 1070 | SSL_SESSION * |
| 1001 | unsigned char *data, int len, int *copy) | 1071 | (*SSL_CTX_sess_get_get_cb(SSL_CTX *ctx))(SSL *ssl, unsigned char *data, |
| 1072 | int len, int *copy) | ||
| 1002 | { | 1073 | { |
| 1003 | return ctx->get_session_cb; | 1074 | return ctx->get_session_cb; |
| 1004 | } | 1075 | } |
| @@ -1010,7 +1081,8 @@ SSL_CTX_set_info_callback(SSL_CTX *ctx, | |||
| 1010 | ctx->info_callback = cb; | 1081 | ctx->info_callback = cb; |
| 1011 | } | 1082 | } |
| 1012 | 1083 | ||
| 1013 | void (*SSL_CTX_get_info_callback(SSL_CTX *ctx))(const SSL *ssl, int type, int val) | 1084 | void |
| 1085 | (*SSL_CTX_get_info_callback(SSL_CTX *ctx))(const SSL *ssl, int type, int val) | ||
| 1014 | { | 1086 | { |
| 1015 | return ctx->info_callback; | 1087 | return ctx->info_callback; |
| 1016 | } | 1088 | } |
| @@ -1022,7 +1094,9 @@ SSL_CTX_set_client_cert_cb(SSL_CTX *ctx, | |||
| 1022 | ctx->client_cert_cb = cb; | 1094 | ctx->client_cert_cb = cb; |
| 1023 | } | 1095 | } |
| 1024 | 1096 | ||
| 1025 | int (*SSL_CTX_get_client_cert_cb(SSL_CTX *ctx))(SSL * ssl, X509 ** x509 , EVP_PKEY **pkey) | 1097 | int |
| 1098 | (*SSL_CTX_get_client_cert_cb(SSL_CTX *ctx))(SSL * ssl, X509 ** x509, | ||
| 1099 | EVP_PKEY **pkey) | ||
| 1026 | { | 1100 | { |
| 1027 | return ctx->client_cert_cb; | 1101 | return ctx->client_cert_cb; |
| 1028 | } | 1102 | } |
| @@ -1032,11 +1106,13 @@ int | |||
| 1032 | SSL_CTX_set_client_cert_engine(SSL_CTX *ctx, ENGINE *e) | 1106 | SSL_CTX_set_client_cert_engine(SSL_CTX *ctx, ENGINE *e) |
| 1033 | { | 1107 | { |
| 1034 | if (!ENGINE_init(e)) { | 1108 | if (!ENGINE_init(e)) { |
| 1035 | SSLerr(SSL_F_SSL_CTX_SET_CLIENT_CERT_ENGINE, ERR_R_ENGINE_LIB); | 1109 | SSLerr(SSL_F_SSL_CTX_SET_CLIENT_CERT_ENGINE, |
| 1110 | ERR_R_ENGINE_LIB); | ||
| 1036 | return 0; | 1111 | return 0; |
| 1037 | } | 1112 | } |
| 1038 | if (!ENGINE_get_ssl_client_cert_function(e)) { | 1113 | if (!ENGINE_get_ssl_client_cert_function(e)) { |
| 1039 | SSLerr(SSL_F_SSL_CTX_SET_CLIENT_CERT_ENGINE, SSL_R_NO_CLIENT_CERT_METHOD); | 1114 | SSLerr(SSL_F_SSL_CTX_SET_CLIENT_CERT_ENGINE, |
| 1115 | SSL_R_NO_CLIENT_CERT_METHOD); | ||
| 1040 | ENGINE_finish(e); | 1116 | ENGINE_finish(e); |
| 1041 | return 0; | 1117 | return 0; |
| 1042 | } | 1118 | } |
