ssl_server * ssl_setup_server(int fd){ ssl_ensure_initialized(); SSL_CTX * ctx = SSL_CTX_new(DTLSv1_server_method()); { // setup server SSL CTX SSL_CTX_set_cipher_list(ctx, "HIGH:!aNULL:!MD5:!RC4"); SSL_CTX_set_session_cache_mode(ctx, SSL_SESS_CACHE_OFF); if (!SSL_CTX_use_certificate_file(ctx, "certs/server-cert.pem", SSL_FILETYPE_PEM)) printf("\nERROR: no certificate found!"); if (!SSL_CTX_use_PrivateKey_file(ctx, "certs/server-key.pem", SSL_FILETYPE_PEM)) printf("\nERROR: no private key found!"); if (!SSL_CTX_check_private_key (ctx)) printf("\nERROR: invalid private key!"); /* Client has to authenticate */ SSL_CTX_set_verify(ctx, SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE, dtls_verify_callback); SSL_CTX_set_read_ahead(ctx, 1); SSL_CTX_set_cookie_generate_cb(ctx, generate_cookie); SSL_CTX_set_cookie_verify_cb(ctx, verify_cookie); } ssl_server * srv = alloc0(sizeof(ssl_server)); srv->ctx = ctx; srv->fd = fd; return srv; }
static int init_server(dtls_listener_relay_server_type* server, const char* ifname, const char *local_address, int port, int verbose, ioa_engine_handle e, turn_turnserver *ts) { if(!server) return -1; server->dtls_ctx = e->dtls_ctx; server->ts = ts; server->children_ss = ur_addr_map_create(65535); if(ifname) STRCPY(server->ifname,ifname); if(make_ioa_addr((const u08bits*)local_address, port, &server->addr)<0) { TURN_LOG_FUNC(TURN_LOG_LEVEL_ERROR,"Cannot create a UDP/DTLS listener for address: %s\n",local_address); return -1; } server->slen0 = get_ioa_addr_len(&(server->addr)); server->verbose=verbose; server->e = e; TURN_LOG_FUNC(TURN_LOG_LEVEL_INFO,"IO method: %s\n",event_base_get_method(server->e->event_base)); if(server->dtls_ctx) { #if defined(REQUEST_CLIENT_CERT) /* If client has to authenticate, then */ SSL_CTX_set_verify(server->dtls_ctx, SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE, dtls_verify_callback); #endif SSL_CTX_set_read_ahead(server->dtls_ctx, 1); #if !defined(TURN_NO_DTLS) SSL_CTX_set_cookie_generate_cb(server->dtls_ctx, generate_cookie); SSL_CTX_set_cookie_verify_cb(server->dtls_ctx, verify_cookie); #endif } return create_server_socket(server); }
static int init_server(dtls_listener_relay_server_type* server, const char* ifname, const char *local_address, int port, int verbose, ioa_engine_handle e, turn_turnserver *ts, int report_creation, ioa_engine_new_connection_event_handler send_socket) { if(!server) return -1; #if DTLS_SUPPORTED server->dtls_ctx = e->dtls_ctx; #if DTLSv1_2_SUPPORTED server->dtls_ctx_v1_2 = e->dtls_ctx_v1_2; #endif #endif server->ts = ts; server->connect_cb = send_socket; if(ifname) STRCPY(server->ifname,ifname); if(make_ioa_addr((const u08bits*)local_address, port, &server->addr)<0) { TURN_LOG_FUNC(TURN_LOG_LEVEL_ERROR,"Cannot create a DTLS/UDP listener for address: %s\n",local_address); return -1; } server->slen0 = get_ioa_addr_len(&(server->addr)); server->verbose=verbose; server->e = e; #if DTLS_SUPPORTED if(server->dtls_ctx) { #if defined(REQUEST_CLIENT_CERT) /* If client has to authenticate, then */ SSL_CTX_set_verify(server->dtls_ctx, SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE, dtls_verify_callback); #endif SSL_CTX_set_read_ahead(server->dtls_ctx, 1); SSL_CTX_set_cookie_generate_cb(server->dtls_ctx, generate_cookie); SSL_CTX_set_cookie_verify_cb(server->dtls_ctx, verify_cookie); } #if DTLSv1_2_SUPPORTED if(server->dtls_ctx_v1_2) { #if defined(REQUEST_CLIENT_CERT) /* If client has to authenticate, then */ SSL_CTX_set_verify(server->dtls_ctx_v1_2, SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE, dtls_verify_callback); #endif SSL_CTX_set_read_ahead(server->dtls_ctx_v1_2, 1); SSL_CTX_set_cookie_generate_cb(server->dtls_ctx_v1_2, generate_cookie); SSL_CTX_set_cookie_verify_cb(server->dtls_ctx_v1_2, verify_cookie); } #endif #endif return create_server_socket(server, report_creation); }
int main(void) { SSL_CTX *ctx = NULL; SSL *ssl = NULL; BIO *outbio = NULL; BIO *inbio = NULL; BIO_ADDR *peer = BIO_ADDR_new(); char *data; long datalen; int ret, success = 0; size_t i; ctx = SSL_CTX_new(DTLS_server_method()); if (ctx == NULL || peer == NULL) goto err; SSL_CTX_set_cookie_generate_cb(ctx, cookie_gen); SSL_CTX_set_cookie_verify_cb(ctx, cookie_verify); /* Create an SSL object for the connection */ ssl = SSL_new(ctx); if (ssl == NULL) goto err; outbio = BIO_new(BIO_s_mem()); if (outbio == NULL) goto err; SSL_set_wbio(ssl, outbio); success = 1; for (i = 0; i < OSSL_NELEM(testpackets) && success; i++) { inbio = BIO_new_mem_buf((char *)testpackets[i].in, testpackets[i].inlen); if (inbio == NULL) { success = 0; goto err; } /* Set Non-blocking IO behaviour */ BIO_set_mem_eof_return(inbio, -1); SSL_set_rbio(ssl, inbio); /* Process the incoming packet */ ret = DTLSv1_listen(ssl, peer); if (ret < 0) { success = 0; goto err; } datalen = BIO_get_mem_data(outbio, &data); if (testpackets[i].outtype == VERIFY) { if (ret == 0) { if (datalen != sizeof(verify) || (memcmp(data, verify, sizeof(verify)) != 0)) { printf("Test %ld failure: incorrect HelloVerifyRequest\n", i); success = 0; } else { printf("Test %ld success\n", i); } } else { printf ("Test %ld failure: should not have succeeded\n", i); success = 0; } } else if (datalen == 0) { if ((ret == 0 && testpackets[i].outtype == DROP) || (ret == 1 && testpackets[i].outtype == GOOD)) { printf("Test %ld success\n", i); } else { printf("Test %ld failure: wrong return value\n", i); success = 0; } } else { printf("Test %ld failure: Unexpected data output\n", i); success = 0; } (void)BIO_reset(outbio); inbio = NULL; /* Frees up inbio */ SSL_set_rbio(ssl, NULL); } err: if (!success) ERR_print_errors_fp(stderr); /* Also frees up outbio */ SSL_free(ssl); SSL_CTX_free(ctx); BIO_free(inbio); OPENSSL_free(peer); #ifndef OPENSSL_NO_CRYPTO_MDEBUG CRYPTO_mem_leaks_fp(stderr); #endif return success ? 0 : 1; }
/* * \brief Initialize OpenSSl of Verse server */ static int vs_init_ssl(VS_CTX *vs_ctx) { /* Set up the library */ SSL_library_init(); ERR_load_BIO_strings(); SSL_load_error_strings(); OpenSSL_add_all_algorithms(); /* Set up SSL context for TLS */ if( (vs_ctx->tls_ctx = SSL_CTX_new(TLSv1_server_method())) == NULL ) { v_print_log(VRS_PRINT_ERROR, "Setting up SSL_CTX failed.\n"); ERR_print_errors_fp(v_log_file()); return -1; } /* Load certificate chain file from CA */ if(vs_ctx->ca_cert_file != NULL) { if(SSL_CTX_use_certificate_chain_file(vs_ctx->tls_ctx, vs_ctx->ca_cert_file) != 1) { v_print_log(VRS_PRINT_ERROR, "TLS: Loading certificate chain file: %s failed.\n", vs_ctx->ca_cert_file); ERR_print_errors_fp(v_log_file()); return -1; } } /* Load certificate with public key for TLS */ if(SSL_CTX_use_certificate_file(vs_ctx->tls_ctx, vs_ctx->public_cert_file, SSL_FILETYPE_PEM) != 1) { v_print_log(VRS_PRINT_ERROR, "TLS: Loading certificate file: %s failed.\n", vs_ctx->public_cert_file); ERR_print_errors_fp(v_log_file()); return -1; } /* Load private key for TLS */ if(SSL_CTX_use_PrivateKey_file(vs_ctx->tls_ctx, vs_ctx->private_cert_file, SSL_FILETYPE_PEM) != 1) { v_print_log(VRS_PRINT_ERROR, "TLS: Loading private key file: %s failed.\n", vs_ctx->private_cert_file); ERR_print_errors_fp(v_log_file()); return -1; } /* Check the consistency of a private key with the corresponding * certificate loaded into ssl_ctx */ if(SSL_CTX_check_private_key(vs_ctx->tls_ctx) != 1) { v_print_log(VRS_PRINT_ERROR, "TLS: Private key does not match the certificate public key\n"); ERR_print_errors_fp(v_log_file()); return -1; } /* When CA certificate file was set, then try to load it */ if(vs_ctx->ca_cert_file != NULL) { if(SSL_CTX_load_verify_locations(vs_ctx->tls_ctx, vs_ctx->ca_cert_file, NULL) != 1) { v_print_log(VRS_PRINT_ERROR, "TLS: Loading CA certificate file: %s failed.\n", vs_ctx->ca_cert_file); ERR_print_errors_fp(v_log_file()); return -1; } } #if OPENSSL_VERSION_NUMBER>=0x10000000 /* Set up SSL context for DTLS */ if( (vs_ctx->dtls_ctx = SSL_CTX_new(DTLSv1_server_method())) == NULL ) { v_print_log(VRS_PRINT_ERROR, "Setting up SSL_CTX failed.\n"); ERR_print_errors_fp(v_log_file()); return -1; } /* Load certificate chain file from CA */ if(vs_ctx->ca_cert_file != NULL) { if(SSL_CTX_use_certificate_chain_file(vs_ctx->dtls_ctx, vs_ctx->ca_cert_file) != 1) { v_print_log(VRS_PRINT_ERROR, "DTLS: Loading certificate chain file: %s failed.\n", vs_ctx->ca_cert_file); ERR_print_errors_fp(v_log_file()); return -1; } } /* Load certificate with public key for DTLS */ if (SSL_CTX_use_certificate_file(vs_ctx->dtls_ctx, vs_ctx->public_cert_file, SSL_FILETYPE_PEM) != 1) { v_print_log(VRS_PRINT_ERROR, "DTLS: Loading certificate file: %s failed.\n", vs_ctx->public_cert_file); ERR_print_errors_fp(v_log_file()); return -1; } /* Load private key for DTLS */ if(SSL_CTX_use_PrivateKey_file(vs_ctx->dtls_ctx, vs_ctx->private_cert_file, SSL_FILETYPE_PEM) != 1) { v_print_log(VRS_PRINT_ERROR, "DTLS: Loading private key file: %s failed.\n", vs_ctx->private_cert_file); ERR_print_errors_fp(v_log_file()); return -1; } /* Check the consistency of a private key with the corresponding * certificate loaded into ssl_ctx */ if(SSL_CTX_check_private_key(vs_ctx->dtls_ctx) != 1) { v_print_log(VRS_PRINT_ERROR, "DTLS: Private key does not match the certificate public key\n"); ERR_print_errors_fp(v_log_file()); return -1; } /* When CA certificate file was set, then try to load it */ if(vs_ctx->ca_cert_file != NULL) { if(SSL_CTX_load_verify_locations(vs_ctx->dtls_ctx, vs_ctx->ca_cert_file, NULL) != 1) { v_print_log(VRS_PRINT_ERROR, "DTLS: Loading CA certificate file: %s failed.\n", vs_ctx->ca_cert_file); ERR_print_errors_fp(v_log_file()); return -1; } } /* Set up callback functions for DTLS cookie */ SSL_CTX_set_cookie_generate_cb(vs_ctx->dtls_ctx, vs_dtls_generate_cookie); SSL_CTX_set_cookie_verify_cb(vs_ctx->dtls_ctx, vs_dtls_verify_cookie); /* Accept all cipher including NULL cipher (testing) */ if( SSL_CTX_set_cipher_list(vs_ctx->dtls_ctx, "ALL:NULL:eNULL:aNULL") == 0) { v_print_log(VRS_PRINT_ERROR, "Setting ciphers for DTLS failed.\n"); ERR_print_errors_fp(v_log_file()); return 0; } /* DTLS require this */ SSL_CTX_set_read_ahead(vs_ctx->dtls_ctx, 1); #else vs_ctx->dtls_ctx = NULL; #endif return 1; }
int main(int argc, char **argv) { int sockfd = 0; int on = 1; struct sockaddr_in6 listen_addr = { AF_INET6, htons(20220), 0, IN6ADDR_ANY_INIT, 0 }; size_t addr_size = sizeof(struct sockaddr_in6); fd_set fds[2]; int result, flags; int idx, res = 0; struct timeval timeout; struct sigaction act, oact; #ifdef WITH_DTLS SSL_CTX *ctx; memset(ssl_peer_storage, 0, sizeof(ssl_peer_storage)); SSL_load_error_strings(); SSL_library_init(); ctx = SSL_CTX_new(DTLSv1_server_method()); SSL_CTX_set_cipher_list(ctx, "ALL"); SSL_CTX_set_session_cache_mode(ctx, SSL_SESS_CACHE_OFF); res = SSL_CTX_use_certificate_file(ctx, SERVER_CERT_PEM, SSL_FILETYPE_PEM); if (res != 1) { fprintf(stderr, "cannot read server certificate from file '%s' (%s)\n", SERVER_CERT_PEM, ERR_error_string(res,NULL)); goto end; } res = SSL_CTX_use_PrivateKey_file(ctx, SERVER_KEY_PEM, SSL_FILETYPE_PEM); if (res != 1) { fprintf(stderr, "cannot read server key from file '%s' (%s)\n", SERVER_KEY_PEM, ERR_error_string(res,NULL)); goto end; } res = SSL_CTX_check_private_key (ctx); if (res != 1) { fprintf(stderr, "invalid private key\n"); goto end; } res = SSL_CTX_load_verify_locations(ctx, CA_CERT_PEM, NULL); if (res != 1) { fprintf(stderr, "cannot read ca file '%s'\n", CA_CERT_PEM); goto end; } /* Client has to authenticate */ /* Client has to authenticate */ SSL_CTX_set_verify(ctx, SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE, NULL); SSL_CTX_set_read_ahead(ctx, 1); /* disable read-ahead */ SSL_CTX_set_cookie_generate_cb(ctx, generate_cookie); SSL_CTX_set_cookie_verify_cb(ctx, verify_cookie); SSL_CTX_use_psk_identity_hint(ctx, "Enter password for CoAP-Gateway"); SSL_CTX_set_psk_server_callback(ctx, psk_server_callback); SSL_CTX_set_info_callback(ctx, info_callback); #endif sockfd = socket(listen_addr.sin6_family, SOCK_DGRAM, 0); if ( sockfd < 0 ) { perror("socket"); return -1; } if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on) ) < 0) perror("setsockopt SO_REUSEADDR"); flags = fcntl(sockfd, F_GETFL, 0); if (flags < 0 || fcntl(sockfd, F_SETFL, flags | O_NONBLOCK) < 0) { perror("fcntl"); return -1; } on = 1; if (setsockopt(sockfd, IPPROTO_IPV6, IPV6_RECVPKTINFO, &on, sizeof(on) ) < 0) { perror("setsockopt IPV6_PKTINFO"); } if (bind (sockfd, (const struct sockaddr *)&listen_addr, addr_size) < 0) { perror("bind"); res = -2; goto end; } act.sa_handler = handle_sigint; sigemptyset(&act.sa_mask); act.sa_flags = 0; sigaction(SIGINT, &act, &oact); while (!quit) { FD_ZERO(&fds[READ]); FD_ZERO(&fds[WRITE]); FD_SET(sockfd, &fds[READ]); timeout.tv_sec = 1; timeout.tv_usec = 0; result = select( FD_SETSIZE, &fds[READ], &fds[WRITE], 0, &timeout); if (result < 0) { /* error */ if (errno != EINTR) perror("select"); } else if (result > 0) { /* read from socket */ if ( FD_ISSET( sockfd, &fds[READ]) ) { _read(ctx, sockfd); /* read received data */ } else if ( FD_ISSET( sockfd, &fds[WRITE]) ) { /* write to socket */ _write(ctx, sockfd); /* write data */ } } else { /* timeout */ check_timeout(); } remove_closed(); } end: #ifdef WITH_DTLS for (idx = 0; idx < MAX_SSL_PEERS; idx++) { if (ssl_peer_storage[idx] && ssl_peer_storage[idx]->ssl) { if (ssl_peer_storage[idx]->state == PEER_ST_ESTABLISHED) SSL_shutdown(ssl_peer_storage[idx]->ssl); SSL_free(ssl_peer_storage[idx]->ssl); } } SSL_CTX_free(ctx); #endif close(sockfd); /* don't care if we close stdin at this point */ return res; }
void DataPlaneServer::start() { server_addr.s6.sin6_family = AF_INET6; // we listen on public IP, which is the one stored in the DB. struct in6_addr servIp; inet_pton(AF_INET6, qSql->getLocalIP().toUtf8().data(), &servIp); server_addr.s6.sin6_addr = servIp; //in6addr_any; server_addr.s6.sin6_port = htons(DATAPLANEPORT); const int on = 1, off = 0; OpenSSL_add_ssl_algorithms(); SSL_load_error_strings(); ctx = SSL_CTX_new(DTLSv1_server_method()); SSL_CTX_set_cipher_list(ctx, DTLS_ENCRYPT); SSL_CTX_set_session_cache_mode(ctx, SSL_SESS_CACHE_OFF); // get certificate and key from SQL & use them ConnectionInitiator* i = ConnectionInitiator::getInstance(); QSslCertificate cert = i->getLocalCertificate(); QByteArray certBytesPEM = cert.toPem(); char* x509buffer = certBytesPEM.data(); BIO *bi; bi = BIO_new_mem_buf(x509buffer, certBytesPEM.length()); X509 *x; x = PEM_read_bio_X509(bi, NULL, NULL, NULL); if (!SSL_CTX_use_certificate(ctx,x)) { qWarning() << "ERROR: no certificate found!"; UnixSignalHandler::termSignalHandler(0); } if (x != NULL) X509_free(x); if (bi != NULL) BIO_free(bi); QSslKey key = i->getPrivateKey(); QByteArray keyBytesPEM = key.toPem(); char* keyBuffer = keyBytesPEM.data(); bi = BIO_new_mem_buf(keyBuffer, keyBytesPEM.length()); EVP_PKEY *pkey; pkey = PEM_read_bio_PrivateKey(bi, NULL, NULL, NULL); if (!SSL_CTX_use_PrivateKey(ctx, pkey)) { qWarning() << "ERROR: no private key found!"; UnixSignalHandler::termSignalHandler(0); } if (pkey != NULL) EVP_PKEY_free(pkey); if (bi != NULL) BIO_free(bi); if (!SSL_CTX_check_private_key (ctx)) { qWarning() << "ERROR: invalid private key!"; UnixSignalHandler::termSignalHandler(0); } /* Client has to authenticate */ SSL_CTX_set_verify(ctx, SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE, dtls_verify_callback); SSL_CTX_set_read_ahead(ctx, 1); SSL_CTX_set_cookie_generate_cb(ctx, generate_cookie); SSL_CTX_set_cookie_verify_cb(ctx, verify_cookie); fd = socket(server_addr.ss.ss_family, SOCK_DGRAM, 0); if (fd < 0) { qWarning() << "Could not open SOCK_DGRAM"; UnixSignalHandler::termSignalHandler(0); } #ifdef WIN32 setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (const char*) &on, (socklen_t) sizeof(on)); #else setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (const void*) &on, (socklen_t) sizeof(on)); #ifdef SO_REUSEPORT setsockopt(fd, SOL_SOCKET, SO_REUSEPORT, (const void*) &on, (socklen_t) sizeof(on)); #endif #endif setsockopt(fd, IPPROTO_IPV6, IPV6_V6ONLY, (char *)&off, sizeof(off)); bind(fd, (const struct sockaddr *) &server_addr, sizeof(struct sockaddr_in6)); notif = new QSocketNotifier(fd, QSocketNotifier::Read); connect(notif, SIGNAL(activated(int)), this, SLOT(readyRead(int))); }