We have been using stunnel on Windows as a SSL proxy to connect to HTTPS server but stunnel kept crashing randomly under load.
After some investigation, we found the following: according to OpenSSL document (http://www.openssl.org/docs/crypto/threads.html),
"OpenSSL can safely be used in multi-threaded applications provided that at least two callback functions are set.
locking_function(int mode, int n, const char *file, int line) is needed to perform locking on shared data structures. (Note that OpenSSL uses a number of global data structures that will be implicitly shared whenever multiple threads use OpenSSL.) Multi-threaded applications will crash at random if it is not set. "
The original stunnel package only implements a POSIX Pthread version of locking callback functions, but doesn't provide any implementation for Windows. This has caused random crashes during our testing because the way we use stunnel requires frequent creation/destruction of threads and stunnel is not thread-safe without the locking callbacks.
The attached fix attempts to address the problem by implementing the Windows version of locking callbacks using Windows native CRITICAL_SECTION object.
=============================================================================================================================== *** sthreads.c Fri Dec 31 02:55:40 2004 --- sthreads_w32.c Thu Apr 14 08:29:07 2005 *************** *** 121,126 **** --- 121,127 ---- #ifdef USE_WIN32
CRITICAL_SECTION stunnel_cs[CRIT_SECTIONS]; + static CRITICAL_SECTION lock_cs[CRYPTO_NUM_LOCKS];
void enter_critical_section(SECTION_CODE i) { EnterCriticalSection(stunnel_cs+i); *************** *** 130,141 **** --- 131,161 ---- LeaveCriticalSection(stunnel_cs+i); }
+ static void locking_callback(int mode, int type, + #ifdef HAVE_OPENSSL + const /* Callback definition has been changed in openssl 0.9.3 */ + #endif + char *file, int line) { + if(mode&CRYPTO_LOCK) + EnterCriticalSection(lock_cs+type); + else + LeaveCriticalSection(lock_cs+type); + } + + void sthreads_init(void) { int i;
/* Initialize stunnel critical sections */ for(i=0; i<CRIT_SECTIONS; i++) InitializeCriticalSection(stunnel_cs+i); + + /* Initialize OpenSSL locking callback */ + for(i=0; i<CRYPTO_NUM_LOCKS; i++) + InitializeCriticalSection(lock_cs+i); + CRYPTO_set_locking_callback(locking_callback); + + }
unsigned long stunnel_process_id(void) {
(See attached file: sthread_diff)
Yi Lin Convergys Corporation yi.lin@convergys.com (703)885-5767 -- "NOTICE: The information contained in this electronic mail transmission is intended by Convergys Corporation for the use of the named individual or entity to which it is directed and may contain information that is privileged or otherwise confidential. If you have received this electronic mail transmission in error, please delete it from your system without copying or forwarding it, and notify the sender of the error by reply email or by telephone (collect), so that the sender's address records can be corrected."