]> rtime.felk.cvut.cz Git - orte.git/blob - orte/liborte/rtl/pthread_rwlock_destroy.c
Added prerelease of ORTE-0.2 (Real Time Publisher Subscriber communication protocol...
[orte.git] / orte / liborte / rtl / pthread_rwlock_destroy.c
1 /*
2  * pthread_rwlock_destroy.c
3  *
4  * Description:
5  * This translation unit implements read/write lock primitives.
6  *
7  * --------------------------------------------------------------------------
8  *
9  *      Pthreads-win32 - POSIX Threads Library for Win32
10  *      Copyright(C) 1998 John E. Bossom
11  *      Copyright(C) 1999,2002 Pthreads-win32 contributors
12  * 
13  *      Contact Email: rpj@ise.canberra.edu.au
14  * 
15  *      The current list of contributors is contained
16  *      in the file CONTRIBUTORS included with the source
17  *      code distribution. The list can also be seen at the
18  *      following World Wide Web location:
19  *      http://sources.redhat.com/pthreads-win32/contributors.html
20  * 
21  *      This library is free software; you can redistribute it and/or
22  *      modify it under the terms of the GNU Lesser General Public
23  *      License as published by the Free Software Foundation; either
24  *      version 2 of the License, or (at your option) any later version.
25  * 
26  *      This library is distributed in the hope that it will be useful,
27  *      but WITHOUT ANY WARRANTY; without even the implied warranty of
28  *      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
29  *      Lesser General Public License for more details.
30  * 
31  *      You should have received a copy of the GNU Lesser General Public
32  *      License along with this library in the file COPYING.LIB;
33  *      if not, write to the Free Software Foundation, Inc.,
34  *      59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
35  */
36
37 //#include <errno.h>
38 //#include <limits.h>
39
40 //#include "pthread.h"
41 //#include "implement.h"
42
43 #include "orte.h"
44
45 int
46 pthread_rwlock_destroy(pthread_rwlock_t *rwlock)
47 {
48     pthread_rwlock_t rwl;
49     int result = 0, result1 = 0, result2 = 0;
50
51     if (rwlock == NULL || *rwlock == NULL)
52       {
53         return EINVAL;
54       }
55
56     if (*rwlock != PTHREAD_RWLOCK_INITIALIZER)
57       {
58         rwl = *rwlock;
59
60         if (rwl->nMagic != PTW32_RWLOCK_MAGIC)
61           {
62             return EINVAL;
63           }
64
65         if ((result = pthread_mutex_lock(&(rwl->mtxExclusiveAccess))) != 0)
66           {
67             return result;
68           }
69
70         if ((result = pthread_mutex_lock(&(rwl->mtxSharedAccessCompleted))) != 0)
71           {
72             (void) pthread_mutex_unlock(&(rwl->mtxExclusiveAccess));
73             return result;
74           }
75
76         /*
77          * Check whether any threads own/wait for the lock (wait for ex.access);
78          * report "BUSY" if so.
79          */
80         if (rwl->nExclusiveAccessCount > 0
81             || rwl->nSharedAccessCount > rwl->nCompletedSharedAccessCount)
82           {
83             result = pthread_mutex_unlock(&(rwl->mtxSharedAccessCompleted));
84             result1 = pthread_mutex_unlock(&(rwl->mtxExclusiveAccess));
85             result2 = EBUSY;
86           }
87         else 
88           {
89             rwl->nMagic = 0;
90
91             if ((result = pthread_mutex_unlock(&(rwl->mtxSharedAccessCompleted))) != 0)
92               {
93                 pthread_mutex_unlock(&rwl->mtxExclusiveAccess);
94                 return result;
95               }
96
97             if ((result = pthread_mutex_unlock(&(rwl->mtxExclusiveAccess))) != 0)
98               {
99                 return result;
100               }
101
102             *rwlock = NULL; /* Invalidate rwlock before anything else */
103             result = pthread_cond_destroy(&(rwl->cndSharedAccessCompleted));
104             result1 = pthread_mutex_destroy(&(rwl->mtxSharedAccessCompleted));
105             result2 = pthread_mutex_destroy(&(rwl->mtxExclusiveAccess));
106             (void) free(rwl);
107           }
108       }
109     else
110       {
111         /*
112          * See notes in ptw32_rwlock_check_need_init() above also.
113          */
114 //      EnterCriticalSection(&ptw32_rwlock_test_init_lock);
115
116         /*
117          * Check again.
118          */
119         if (*rwlock == PTHREAD_RWLOCK_INITIALIZER)
120           {
121             /*
122              * This is all we need to do to destroy a statically
123              * initialised rwlock that has not yet been used (initialised).
124              * If we get to here, another thread
125              * waiting to initialise this rwlock will get an EINVAL.
126              */
127             *rwlock = NULL;
128           }
129         else
130           {
131             /*
132              * The rwlock has been initialised while we were waiting
133              * so assume it's in use.
134              */
135             result = EBUSY;
136           }
137
138 //      LeaveCriticalSection(&ptw32_rwlock_test_init_lock);
139       }
140
141     return ((result != 0) ? result : ((result1 != 0) ? result1 : result2));
142 }