int SSLContext::getSession(State & state, SSLContextData * ssl_context_data) { Stack * stack = state.stack; SSLSession * interfaceSSLSession = OBJECT_IFACE(SSLSession); mbedtls_ssl_session * session = new mbedtls_ssl_session; if (mbedtls_ssl_get_session(ssl_context_data->context, session) == 0) { interfaceSSLSession->push(session, true); return 1; } else { delete session; return 0; } }
static CURLcode mbed_connect_step3(struct connectdata *conn, int sockindex) { CURLcode retcode = CURLE_OK; struct ssl_connect_data *connssl = &conn->ssl[sockindex]; struct Curl_easy *data = conn->data; DEBUGASSERT(ssl_connect_3 == connssl->connecting_state); if(SSL_SET_OPTION(primary.sessionid)) { int ret; mbedtls_ssl_session *our_ssl_sessionid; void *old_ssl_sessionid = NULL; our_ssl_sessionid = malloc(sizeof(mbedtls_ssl_session)); if(!our_ssl_sessionid) return CURLE_OUT_OF_MEMORY; mbedtls_ssl_session_init(our_ssl_sessionid); ret = mbedtls_ssl_get_session(&BACKEND->ssl, our_ssl_sessionid); if(ret) { free(our_ssl_sessionid); failf(data, "mbedtls_ssl_get_session returned -0x%x", -ret); return CURLE_SSL_CONNECT_ERROR; } /* If there's already a matching session in the cache, delete it */ Curl_ssl_sessionid_lock(conn); if(!Curl_ssl_getsessionid(conn, &old_ssl_sessionid, NULL, sockindex)) Curl_ssl_delsessionid(conn, old_ssl_sessionid); retcode = Curl_ssl_addsessionid(conn, our_ssl_sessionid, 0, sockindex); Curl_ssl_sessionid_unlock(conn); if(retcode) { free(our_ssl_sessionid); failf(data, "failed to store ssl session"); return retcode; } } connssl->connecting_state = ssl_connect_done; return CURLE_OK; }
int conn_link_open(struct conn_link_s *link, int *sock, bool use_ssl, uint32_t recv_timeout_ms, uint32_t send_timeout_ms) { DEBUGASSERT(link->sock < 0); #ifdef CONFIG_THINGSEE_HTTPS_PROTOCOL DEBUGASSERT(link->ssl == NULL); #ifdef CONFIG_MBEDTLS DEBUGASSERT(link->net.fd < 0); #endif #endif link->send_timeout_ms = send_timeout_ms; link->recv_timeout_ms = recv_timeout_ms; if (!use_ssl) { link->sock = *sock; *sock = -1; return OK; } else { #ifdef CONFIG_THINGSEE_HTTPS_PROTOCOL #ifdef CONFIG_MBEDTLS int ret; struct timeval tv; if (!g_https_data.initialized) { con_dbg_save_pos(); if (conn_link_mbedtls_initialize() < 0) return ERROR; } mbedtls_ssl_conf_read_timeout(&g_https_data.mbedtls->conf, link->recv_timeout_ms); /* Set up a send timeout */ tv.tv_sec = link->send_timeout_ms / 1000; tv.tv_usec = (link->send_timeout_ms % 1000) * 1000; ret = setsockopt(*sock, SOL_SOCKET, SO_SNDTIMEO, &tv, sizeof(struct timeval)); if (ret < 0) { con_dbg("Setting SO_SNDTIMEO failed, errno: %d\n", errno); /* Return here. Socket is more than likely broken */ return ERROR; } else { http_con_dbg("SO_SNDTIMEO := %d msecs\n", link->send_timeout_ms); } /* Set up a receive timeout */ tv.tv_sec = link->recv_timeout_ms / 1000; tv.tv_usec = (link->recv_timeout_ms % 1000) * 1000; ret = setsockopt(*sock, SOL_SOCKET, SO_RCVTIMEO, &tv, sizeof(struct timeval)); if (ret < 0) { con_dbg("Setting SO_RCVTIMEO failed, errno: %d\n", errno); /* Return if ERROR occurred */ return ERROR; } else { http_con_dbg("SO_RCVTIMEO := %d msecs\n", link->recv_timeout_ms); } con_dbg_save_pos(); link->ssl = malloc(sizeof(*link->ssl)); if (!link->ssl) return -1; mbedtls_ssl_init(link->ssl); ret = mbedtls_ssl_setup(link->ssl, &g_https_data.mbedtls->conf); if (ret != 0) { con_dbg("mbedtls_ssl_setup error: -0x%x\n", -ret); goto err_close_tls; } link->net.fd = *sock; link->sock = link->net.fd; *sock = -1; ret = mbedtls_ssl_set_session(link->ssl, &g_https_data.mbedtls->saved_session); if (ret != 0) { con_dbg( "mbedtls_ssl_set_session error: -0x%x\n\n", -ret); } mbedtls_ssl_set_bio(link->ssl, &link->net, mbedtls_net_send, mbedtls_net_recv, mbedtls_net_recv_timeout); ret = mbedtls_ssl_handshake(link->ssl); if (ret != 0) { int lowlevel_err = -(-ret & 0x007F); int highlevel_err = -(-ret & 0x7F80); con_dbg("mbedtls_ssl_handshake error: -0x%x\n", -ret); /* Check out-of-memory cases. If we have run out memory or memory * has become too fragmented, device will be stuck in bad state. * In this case, it will be better to reset. * TODO: Should we add controlled reset? */ DEBUGASSERT(lowlevel_err != MBEDTLS_ERR_MPI_ALLOC_FAILED); DEBUGASSERT(lowlevel_err != MBEDTLS_ERR_ASN1_ALLOC_FAILED); DEBUGASSERT(highlevel_err != MBEDTLS_ERR_X509_ALLOC_FAILED); DEBUGASSERT(highlevel_err != MBEDTLS_ERR_DHM_ALLOC_FAILED); DEBUGASSERT(highlevel_err != MBEDTLS_ERR_PK_ALLOC_FAILED); DEBUGASSERT(highlevel_err != MBEDTLS_ERR_ECP_ALLOC_FAILED); DEBUGASSERT(highlevel_err != MBEDTLS_ERR_CIPHER_ALLOC_FAILED); DEBUGASSERT(highlevel_err != MBEDTLS_ERR_SSL_ALLOC_FAILED); goto err_close_tls; } con_dbg("%c[38;5;%d48;5;%dm" "HTTPS: TLS version is '%s'." "%c[0m\n", 0x1B, 0, 1, mbedtls_ssl_get_version(link->ssl), 0x1B); con_dbg("%c[38;5;%d48;5;%dm" "HTTPS: TLS cipher suite is '%s'." "%c[0m\n", 0x1B, 0, 1, mbedtls_ssl_get_ciphersuite(link->ssl), 0x1B); ret = mbedtls_ssl_get_session(link->ssl, &g_https_data.mbedtls->saved_session); if (ret != 0) { con_dbg( "mbedtls_ssl_get_session error: -0x%x\n\n", -ret); } return OK; err_close_tls: con_dbg_save_pos(); mbedtls_ssl_free(link->ssl); free(link->ssl); link->ssl = NULL; return ERROR; #endif #endif return ERROR; } }
int ssl_init_info(int *server_fd,ssl_info *sslinfo) { int ret; const char *pers = "ssl"; mbedtls_x509_crt_init(&sslinfo->cacert ); mbedtls_ctr_drbg_init(&sslinfo->ctr_drbg); mbedtls_entropy_init(&sslinfo->entropy ); if( mbedtls_ctr_drbg_seed( &sslinfo->ctr_drbg, mbedtls_entropy_func, &sslinfo->entropy, (const unsigned char *) pers, strlen( pers ) ) != 0 ) { return -1; } mbedtls_ssl_init( &sslinfo->ssl ); mbedtls_ssl_config_init( &sslinfo->conf ); if( ( ret = mbedtls_ssl_config_defaults( &sslinfo->conf, MBEDTLS_SSL_IS_CLIENT, MBEDTLS_SSL_TRANSPORT_STREAM, MBEDTLS_SSL_PRESET_DEFAULT ) ) != 0 ) { echo( " failed\n ! mbedtls_ssl_config_defaults returned %d\n\n", ret ); return -1; } mbedtls_ssl_conf_endpoint( &sslinfo->conf, MBEDTLS_SSL_IS_CLIENT ); mbedtls_ssl_conf_authmode( &sslinfo->conf, MBEDTLS_SSL_VERIFY_OPTIONAL ); mbedtls_ssl_conf_ca_chain( &sslinfo->conf, &sslinfo->cacert,NULL); mbedtls_ssl_conf_rng( &sslinfo->conf, mbedtls_ctr_drbg_random, &sslinfo->ctr_drbg ); if( ( ret = mbedtls_ssl_setup( &sslinfo->ssl, &sslinfo->conf ) ) != 0 ) { echo( " failed\n ! mbedtls_ssl_setup returned %d\n\n", ret ); return -1; } mbedtls_ssl_set_bio( &sslinfo->ssl, server_fd,mbedtls_net_send, mbedtls_net_recv,NULL ); mbedtls_ssl_set_session(&sslinfo->ssl, &ssn); while((ret = mbedtls_ssl_handshake(&sslinfo->ssl))!=0) { if( ret != MBEDTLS_ERR_SSL_WANT_READ && ret != MBEDTLS_ERR_SSL_WANT_WRITE ) { echo( " failed\n ! ssl_handshake returned -0x%x\n\n", -ret ); return -1; } //CPU sleep sleeps(1); } if((ret = mbedtls_ssl_get_verify_result( &sslinfo->ssl ) ) != 0 ) { // echo( "Verifying peer X.509 certificate...failed \r\n" ); } else { echo( " ok\n" ); } //保存session if( ( ret = mbedtls_ssl_get_session( &sslinfo->ssl, &ssn ) ) != 0 ) { //失败初始化 memset(&ssn, 0, sizeof(mbedtls_ssl_session)); } return 0; }