Mailing-List: contact cygwin-help AT sourceware DOT cygnus DOT com; run by ezmlm List-Subscribe: List-Archive: List-Post: List-Help: , Sender: cygwin-owner AT sources DOT redhat DOT com Delivered-To: mailing list cygwin AT sources DOT redhat DOT com From: David Lum MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Message-ID: <15230.62731.676056.47490@wallaroo.lum.org> Date: Sat, 18 Aug 2001 18:06:51 -0500 To: cygwin AT cygwin DOT com Subject: bug in pthread_mutex_init (cygwin-src-20010813) X-Mailer: VM 6.89 under 21.1 (patch 14) "Cuyahoga Valley" XEmacs Lucid Hi. I think there's a problem with pthread_mutex_init in Cygwin-- I looked at the source code (from 8/13/01) and it verified my suspicions. The implementation of pthread_mutex_init in "winsup/cygwin/thread.cc" does this: > int > __pthread_mutex_init (pthread_mutex_t *mutex, > const pthread_mutexattr_t *attr) > { > if ((((pshared_mutex *)(mutex))->flags & SYS_BASE == SYS_BASE)) > // a pshared mutex > return EBUSY; > ... > } This is bogus! The pthread specification permits the passed-in mutex pointer to refer to completely uninitialized memory. However, the first line of code here accesses a flag from that region of random memory. If the bit happens to be zero, all is well. But if it happens to be 1 then the call fails with EBUSY. Below I've attached (inline) a simple test program to demonstrate this bug. All it does is make a bunch of calls to pthread_mutex_init, simulating the effect of starting with random, uninitialized memory. Typical output for me looks like this: GIRAFFE:/f/lum/cygwin> ./mutex.exe Mutex contains: 0x58 0x0 0x0 0x0 --> OK. Mutex contains: 0xaf 0x80 0x96 0x8d --> Failed to initialize a mutex: 16 = Device or resource busy It fails on the second call with the expected EBUSY return code. I don't really have any suggestions on how to fix this, since it was probably caused by the introduction of "pshared" mutexes (which I do not understand). But I'll bet someone on the list does. -Dave -- David Lum 713-868-6950 (Houston) dlum AT alum DOT mit DOT edu 703-318-1266 (Dulles) /*------------------------------------------------------------------------------ * * Sample program to demonstrate a mutex bug in Cygwin 8/13/01 * *----------------------------------------------------------------------------*/ #include #include #include #include static void randomizeMutexBits( pthread_mutex_t*); static void showMutexBits( pthread_mutex_t*); int main( char** argv, char argc) { pthread_mutex_t mut; int retval; while( 1) { /* * If the following line is uncommented, all goes well. * However, that's not part of the pthread contract! You're * supposed to be able to pass in uninitialized memory to * the pthread_mutex_init function. */ /* memset( &mut, 0, sizeof( pthread_mutex_t)); */ /* * Print out the contents of the mutex for debugging. */ showMutexBits( &mut); /* * Try to initialize the mutex. */ if( (retval = pthread_mutex_init( &mut, NULL)) != 0) { printf( " --> Failed to initialize a mutex: %d = %s\n", retval, strerror( retval)); exit( -1); } else { printf( " --> OK.\n\n"); pthread_mutex_destroy( &mut); } /* * For the next time through the loop, simulate the random bits * found in uninitialized memory. */ randomizeMutexBits( &mut); } exit( 0); } static void randomizeMutexBits( pthread_mutex_t* mutex) { unsigned char* uc; int i; uc = (unsigned char*) mutex; for( i=0; i