/******************************************************************************* * SSL.C * libramesys ssl handling functions ******************************************************************************** * COPYRIGHT (C) 2003 Andy Hobbs ******************************************************************************** * These library provides ssl functionality ******************************************************************************** * $Author: andy $ * $Revision: 1.1.8.1 $ * $Log: ssl.c,v $ * Revision 1.1.8.1 2004/10/14 09:45:12 andy * * Revision 1.1 2004/04/01 14:37:39 andy * First cut of code * *******************************************************************************/ #include /* NOTE Change this tou your own includes!! */ /*********< PROTOTYPES >*******************************************************/ extern flag sslGlobalInit (void); extern flag sslThreadInit (void); extern flag sslThreadCleanUp (void); static void sslThreadsLockingCallback (int mode, int type, char * file, int line); static unsigned long sslThreadsThreadId (void); /*********< GLOBALS >**********************************************************/ static pthread_mutex_t *ssl_lock_cs; static long *ssl_lock_count; static int initSSL = NO; // Global flag to indicate if the library has been initialised /******************************************************************************* * SSLGLOBALINIT() : Perform global ssl initialisation *******************************************************************************/ extern flag sslGlobalInit(void) { flag retval = SUCCESS; /************************** * Running on linux we don't * need to initialise the * random seed as we have a * /dev/urandom ***************************/ if (initSSL == NO) { initSSL = YES; #ifdef HAVE_ENGINE_LOAD_BUILTIN_ENGINES ENGINE_load_builtin_engines(); #endif SSL_load_error_strings(); // Use nice error strings SSLeay_add_ssl_algorithms(); // Other ssl set up stuff } return retval; } /******************************************************************************* * SSLGLOBALCLEANUP() : Perform global ssl clean up *******************************************************************************/ extern flag sslGlobalCleanUp(void) { flag retval = SUCCESS; if(initSSL == YES) { ERR_free_strings(); // Free the SSL error strings EVP_cleanup(); // EVP_cleanup() removes all ciphers and digests from the table #ifdef HAVE_ENGINE_cleanup ENGINE_cleanup(); #endif CRYPTO_cleanup_all_ex_data(); initSSL = NO; } return retval; } /******************************************************************************* * SSLTHREADINIT() : Perform thread ssl initialisation required for multi-threading * * Returns: * Currently always returns SUCCESS *******************************************************************************/ extern flag sslThreadInit(void) { flag retval = SUCCESS; int i; sslGlobalInit(); // Create the number of mutexes required ssl_lock_cs = OPENSSL_malloc(CRYPTO_num_locks() * sizeof(pthread_mutex_t)); ssl_lock_count = OPENSSL_malloc(CRYPTO_num_locks() * sizeof(long)); // Initialise each mutex for (i = 0; i < CRYPTO_num_locks(); i++) { ssl_lock_count[i] = 0; pthread_mutex_init(&(ssl_lock_cs[i]), NULL); } // Register the call backs with the OpenSSL library CRYPTO_set_id_callback((unsigned long (*)()) sslThreadsThreadId); CRYPTO_set_locking_callback((void (*)()) sslThreadsLockingCallback); return retval; } /******************************************************************************* * SSLTHREADCLEANUP() : Perform global ssl clean up required for multi-threading * * Returns: * Currently always returns SUCCESS *******************************************************************************/ extern flag sslThreadCleanUp(void) { flag retval = SUCCESS; int i; // Clear the locking callback CRYPTO_set_locking_callback(NULL); // Destroy all the mutexes for (i = 0; i < CRYPTO_num_locks(); i++) { pthread_mutex_destroy(&(ssl_lock_cs[i])); } // Free up the mutexes OPENSSL_free(ssl_lock_cs); OPENSSL_free(ssl_lock_count); sslGlobalCleanUp(); return retval; } /******************************************************************************* * SSLTHREADSLOCKINGCALLBACK() : callback for openssl library to mutex lock * * Params: * mode - the locking mode - CRYPTO_LOCK for lock other for UNLOCK * type - index into array of mutex for which mutex to lock * file - not used - filename of calling source * line - not used - line number of calling source *******************************************************************************/ static void sslThreadsLockingCallback(int mode, int type, char * file, int line) { // Are we locking or unlocking? if (mode & CRYPTO_LOCK) { // Lock the appropriate mutex pthread_mutex_lock(&(ssl_lock_cs[type])); ssl_lock_count[type]++; } else { pthread_mutex_unlock(&(ssl_lock_cs[type])); } } /******************************************************************************* * SSLTHREADSTHREADID() : callback for openssl library to return thread ID * * Returns: ID of calling thread *******************************************************************************/ static unsigned long sslThreadsThreadId(void) { unsigned long retval; retval = (unsigned long) pthread_self(); return retval; }