Home | History | Annotate | Download | only in tests
      1 
      2 #include <pthread.h>
      3 #include <stdio.h>
      4 #include <stdlib.h>
      5 #include <assert.h>
      6 
      7 /* Test that locks, having entered the lock acquisition tracking
      8    machinery, are forgotten by it when the client does
      9    pthread_{mutex,rwlock}_destroy.  2008-Nov-10: see comments below. */
     10 
     11 int main ( void )
     12 {
     13    int r;
     14    pthread_mutex_t *mx1, *mx2;
     15    assert (sizeof(pthread_mutex_t) <= 120);
     16    mx1 = malloc(120 + sizeof(pthread_mutex_t) - sizeof(pthread_mutex_t));
     17    mx2 = malloc(120 + sizeof(pthread_mutex_t) - sizeof(pthread_mutex_t));
     18 
     19    assert(mx1);
     20    assert(mx2);
     21 
     22    r = pthread_mutex_init( mx1, NULL ); assert(r==0);
     23    r = pthread_mutex_init( mx2, NULL ); assert(r==0);
     24 
     25    /* Establish order 1 -> 2 */
     26    fprintf(stderr, "Establish order 1 -> 2\n");
     27    r = pthread_mutex_lock( mx1 ); assert(r==0);
     28    r = pthread_mutex_lock( mx2 ); assert(r==0);
     29 
     30    r = pthread_mutex_unlock( mx1 ); assert(r==0);
     31    r = pthread_mutex_unlock( mx2 ); assert(r==0);
     32 
     33    /* Try order 2 -> 1.  This gives an error. */
     34    fprintf(stderr, "Try order 2 -> 1.  This gives an error.\n");
     35    r = pthread_mutex_lock( mx2 ); assert(r==0); /* error */
     36    r = pthread_mutex_lock( mx1 ); assert(r==0);
     37 
     38    r = pthread_mutex_unlock( mx1 ); assert(r==0);
     39    r = pthread_mutex_unlock( mx2 ); assert(r==0);
     40 
     41    /* De-initialise 2 and re-initialise it.  This gives it a new
     42       identity, so a second locking sequence 2 -> 1 should now be OK. */
     43    fprintf(stderr,
     44            "Free 2 and re-allocate it.  This gives it a new identity,\n");
     45    fprintf(stderr, "so a second locking sequence 2 -> 1 should now be OK.\n");
     46    pthread_mutex_destroy( mx2 );
     47 
     48 
     49 
     50    r = pthread_mutex_init( mx2, NULL ); assert(r==0);
     51 
     52    r = pthread_mutex_lock( mx2 ); assert(r==0);
     53    r = pthread_mutex_lock( mx1 ); assert(r==0); /* no error */
     54 
     55    r = pthread_mutex_unlock( mx1 ); assert(r==0);
     56    r = pthread_mutex_unlock( mx2 ); assert(r==0);
     57 
     58    /* done */
     59 
     60    fprintf(stderr, "done\n");
     61    r = pthread_mutex_destroy( mx1 );
     62    r = pthread_mutex_destroy( mx2 );
     63 
     64    free( mx1 );
     65    free( mx2 );
     66 
     67    return 0;
     68 }
     69 
     70 /* 2008-Nov-10: I believe this test is flawed and requires further
     71    investigation.  I don't think it really tests what it claims to
     72    test.  In particular, it still gives the right results if
     73    "pthread_mutex_destroy( mx2 );" at line 46 is commented out.  In
     74    other words, laog somehow forgets about mx2 so that 2->1 lock
     75    sequence at lines 52/3 does not produce a complaint, EVEN WHEN the
     76    preceding "pthread_mutex_destroy( mx2 );" is not observed.  I don't
     77    know why this is, but it seems highly suspicious to me. */
     78