// // SSLConnection.cc // // SSLConnection: This class forms a easy to use interface to the // socket interface using SSL connection encryption. // // Part of the ht://Dig package // Copyright (c) 1999-2004 The ht://Dig Group // For copyright details, see the file COPYING in your distribution // or the GNU Library General Public License (LGPL) version 2 or later // // // $Id: SSLConnection.cc,v 1.6 2004/05/28 13:15:23 lha Exp $ // #ifdef HAVE_CONFIG_H #include "htconfig.h" #endif /* HAVE_CONFIG_H */ #ifdef HAVE_SSL_H #include "SSLConnection.h" #ifdef HAVE_STD #include #ifdef HAVE_NAMESPACES using namespace std; #endif #else #include #endif /* HAVE_STD */ // Global needed only once in HtDig // SSL_CTX *SSLConnection::ctx = NULL; SSLConnection::SSLConnection() { InitSSL(); } SSLConnection::SSLConnection(int socket) { InitSSL(); } void SSLConnection::InitSSL() { if( ctx == NULL ) { // Add in the OpenSSL algorithms ?? // OpenSSL_add_ssl_algorithms(); // Load the error strings ... openssl says so // SSL_load_error_strings(); // New CTX, either v3 but can default to v2 // ctx = SSL_CTX_new (SSLv23_client_method()); if( ctx == NULL ) { cout << "ctx NULL" << endl; exit(1); } } } SSLConnection::~SSLConnection() { if( ctx != NULL ) SSL_CTX_free (ctx); ctx = NULL; } int SSLConnection::Connect() { // Run the standard connect // int ret = Connection::Connect(); if( ret != OK ) return ret; // Now start SSL negotiation // ssl = SSL_new (ctx); // Attach ssl to socket // SSL_set_fd (ssl, sock); int err = SSL_connect (ssl); if( err == -1) { // cout << "SSL_connect failed!" << endl; // Close the socket // Connection::Close(); return NOTOK; } return OK; } int SSLConnection::Close() { // First kill the SSL stuff // SSL_shutdown (ssl); /* send SSL/TLS close_notify */ /* Clean up. */ // Now call the Connection Close // int ret = Connection::Close(); if( ret == OK ) { SSL_free (ssl); } return ret; } int SSLConnection::Read_Partial(char *buffer, int maxlength) { int count; need_io_stop = 0; do { errno = 0; if (timeout_value > 0) { FD_SET_T fds; FD_ZERO(&fds); FD_SET(sock, &fds); timeval tv; tv.tv_sec = timeout_value; tv.tv_usec = 0; int selected = select(sock+1, &fds, 0, 0, &tv); if (selected <= 0) need_io_stop++; } if (!need_io_stop) count = SSL_read(ssl, buffer, maxlength); else count = -1; // Input timed out } while (count <= 0 && errno == EINTR && !need_io_stop); need_io_stop = 0; return count; } //************************************************************************* // int Connection::Write_Partial(char *buffer, int maxlength) // int SSLConnection::Write_Partial(char *buffer, int maxlength) { int count; do { count = SSL_write(ssl, buffer, maxlength); } while (count < 0 && errno == EINTR && !need_io_stop); need_io_stop = 0; return count; } #endif