diff --git a/platform/src/ssl_stream.cpp b/platform/src/ssl_stream.cpp index 79e0e77..7426c46 100644 --- a/platform/src/ssl_stream.cpp +++ b/platform/src/ssl_stream.cpp @@ -67,6 +67,9 @@ enum ssl_stream_stat { SSL_UP_NEW, SSL_UP_ERR, + SSL_UP_ERR_NO_CIPHER, + SSL_UP_ERR_UNSUPPORT_PROTO, + SSL_UP_CLOSING, SSL_UP_CLOSED, SSL_UP_DIRTY_CLOSED, @@ -76,6 +79,9 @@ enum ssl_stream_stat SSL_DOWN_NEW, SSL_DOWN_ERR, + SSL_DOWN_ERR_NO_CERT, + SSL_DOWN_ERR_INAPPROPRIATE_FALLBACK, + SSL_DOWN_CLOSING, SSL_DOWN_CLOSED, SSL_DOWN_DIRTY_CLOSED, @@ -93,9 +99,10 @@ enum ssl_stream_stat KEY_KEEPER_CACHE_SIZE, KEY_KEEPER_ASK, KEY_KEEPER_HIT, + + SSL_STAT_MAX }; - struct session_ticket_key { size_t size; @@ -265,7 +272,10 @@ void ssl_stat_init(struct ssl_mgr * mgr) int i=0; const char* spec[SSL_STAT_MAX]={0}; spec[SSL_UP_NEW]="ussl_new"; - spec[SSL_UP_ERR]="ussl_err"; + spec[SSL_UP_ERR]="ussl_err"; + spec[SSL_UP_ERR_NO_CIPHER]="ussl_e_ciph"; + spec[SSL_UP_ERR_UNSUPPORT_PROTO]="ussl_e_proto"; + spec[SSL_UP_CLOSING]="ussl_clsing"; spec[SSL_UP_CLOSED]="ussl_clsed"; spec[SSL_UP_DIRTY_CLOSED]="ussl_dirty_cls"; @@ -275,6 +285,8 @@ void ssl_stat_init(struct ssl_mgr * mgr) spec[SSL_DOWN_NEW]="dssl_new"; spec[SSL_DOWN_ERR]="dssl_err"; + spec[SSL_DOWN_ERR_NO_CERT]="no_cert"; + spec[SSL_DOWN_ERR_INAPPROPRIATE_FALLBACK]="dssl_e_fb"; spec[SSL_DOWN_CLOSING]="dssl_clsing"; spec[SSL_DOWN_CLOSED]="dssl_clsed"; spec[SSL_DOWN_DIRTY_CLOSED]="dssl_dirty_cls"; @@ -862,16 +874,37 @@ struct bufferevent * ssl_upstream_create_result_release_bev(future_result_t * re ctx->bev = NULL; //giveup ownership return ret; } -void ssl_stream_log_error(struct bufferevent * bev, enum tfe_conn_dir dir, void* logger) +void ssl_stream_log_error(struct bufferevent * bev, enum tfe_conn_dir dir, struct ssl_mgr* mgr) { unsigned long sslerr=0; int fd=bufferevent_getfd(bev); char* addr_string=tfe_string_addr_create_by_fd(fd, dir); + void* logger=mgr->logger; + int fs_id=-1; /* Can happen for socket errs, ssl errs; * may happen for unclean ssl socket shutdowns. */ sslerr = bufferevent_get_openssl_error(bev); - + switch(sslerr) + { + case SSL_R_INAPPROPRIATE_FALLBACK: + if(dir==CONN_DIR_DOWNSTREAM) fs_id=SSL_DOWN_ERR_INAPPROPRIATE_FALLBACK; + break; + case SSL_R_SSLV3_ALERT_CERTIFICATE_UNKNOWN: + if(dir==CONN_DIR_DOWNSTREAM) fs_id=SSL_DOWN_ERR_NO_CERT; + break; + case SSL_R_UNSUPPORTED_PROTOCOL: + if(dir==CONN_DIR_UPSTREAM) fs_id=SSL_UP_ERR_UNSUPPORT_PROTO; + case SSL_R_NO_CIPHERS_AVAILABLE: + if(dir==CONN_DIR_UPSTREAM) fs_id=SSL_UP_ERR_NO_CIPHER; + break; + default: + fs_id=-1; + } + if(fs_id>=0) + { + FS_operate(mgr->fs_handle, mgr->fs_id[fs_id], 0, FS_OP_ADD, 1); + } if (!errno && !sslerr) { /* We have disabled notification for unclean shutdowns @@ -968,7 +1001,7 @@ static void ssl_server_connected_eventcb(struct bufferevent * bev, short events, if (events & BEV_EVENT_ERROR) { ATOMIC_INC(&(ctx->mgr->stat_val[SSL_UP_ERR])); - ssl_stream_log_error(bev, CONN_DIR_UPSTREAM, ctx->mgr->logger); + ssl_stream_log_error(bev, CONN_DIR_UPSTREAM, ctx->mgr); snprintf(error_str, sizeof(error_str), "connect to original server failed : sni=%s", sni); promise_failed(p, FUTURE_ERROR_EXCEPTION, error_str); } @@ -1472,7 +1505,7 @@ static void ssl_client_connected_eventcb(struct bufferevent * bev, short events, if (events & BEV_EVENT_ERROR) { ATOMIC_INC(&(mgr->stat_val[SSL_DOWN_ERR])); - ssl_stream_log_error(bev, CONN_DIR_DOWNSTREAM, mgr->logger); + ssl_stream_log_error(bev, CONN_DIR_DOWNSTREAM, mgr); snprintf(error_str, sizeof(error_str), "connect to client failed : sni=%s", sni); promise_failed(p, FUTURE_ERROR_EXCEPTION, error_str); }