1PTHREAD_MUTEXATTR_DESTROY(3PP)OSIX Programmer's ManuPaTlHREAD_MUTEXATTR_DESTROY(3P)
2
3
4
6 This manual page is part of the POSIX Programmer's Manual. The Linux
7 implementation of this interface may differ (consult the corresponding
8 Linux manual page for details of Linux behavior), or the interface may
9 not be implemented on Linux.
10
12 pthread_mutexattr_destroy, pthread_mutexattr_init — destroy and ini‐
13 tialize the mutex attributes object
14
16 #include <pthread.h>
17
18 int pthread_mutexattr_destroy(pthread_mutexattr_t *attr);
19 int pthread_mutexattr_init(pthread_mutexattr_t *attr);
20
22 The pthread_mutexattr_destroy() function shall destroy a mutex
23 attributes object; the object becomes, in effect, uninitialized. An
24 implementation may cause pthread_mutexattr_destroy() to set the object
25 referenced by attr to an invalid value.
26
27 A destroyed attr attributes object can be reinitialized using
28 pthread_mutexattr_init(); the results of otherwise referencing the
29 object after it has been destroyed are undefined.
30
31 The pthread_mutexattr_init() function shall initialize a mutex
32 attributes object attr with the default value for all of the attributes
33 defined by the implementation.
34
35 Results are undefined if pthread_mutexattr_init() is called specifying
36 an already initialized attr attributes object.
37
38 After a mutex attributes object has been used to initialize one or more
39 mutexes, any function affecting the attributes object (including
40 destruction) shall not affect any previously initialized mutexes.
41
42 The behavior is undefined if the value specified by the attr argument
43 to pthread_mutexattr_destroy() does not refer to an initialized mutex
44 attributes object.
45
47 Upon successful completion, pthread_mutexattr_destroy() and
48 pthread_mutexattr_init() shall return zero; otherwise, an error number
49 shall be returned to indicate the error.
50
52 The pthread_mutexattr_init() function shall fail if:
53
54 ENOMEM Insufficient memory exists to initialize the mutex attributes
55 object.
56
57 These functions shall not return an error code of [EINTR].
58
59 The following sections are informative.
60
62 None.
63
65 None.
66
68 If an implementation detects that the value specified by the attr argu‐
69 ment to pthread_mutexattr_destroy() does not refer to an initialized
70 mutex attributes object, it is recommended that the function should
71 fail and report an [EINVAL] error.
72
73 See pthread_attr_destroy() for a general explanation of attributes.
74 Attributes objects allow implementations to experiment with useful
75 extensions and permit extension of this volume of POSIX.1‐2017 without
76 changing the existing functions. Thus, they provide for future extensi‐
77 bility of this volume of POSIX.1‐2017 and reduce the temptation to
78 standardize prematurely on semantics that are not yet widely imple‐
79 mented or understood.
80
81 Examples of possible additional mutex attributes that have been dis‐
82 cussed are spin_only, limited_spin, no_spin, recursive, and metered.
83 (To explain what the latter attributes might mean: recursive mutexes
84 would allow for multiple re-locking by the current owner; metered
85 mutexes would transparently keep records of queue length, wait time,
86 and so on.) Since there is not yet wide agreement on the usefulness of
87 these resulting from shared implementation and usage experience, they
88 are not yet specified in this volume of POSIX.1‐2017. Mutex attributes
89 objects, however, make it possible to test out these concepts for pos‐
90 sible standardization at a later time.
91
92 Mutex Attributes and Performance
93 Care has been taken to ensure that the default values of the mutex
94 attributes have been defined such that mutexes initialized with the
95 defaults have simple enough semantics so that the locking and unlocking
96 can be done with the equivalent of a test-and-set instruction (plus
97 possibly a few other basic instructions).
98
99 There is at least one implementation method that can be used to reduce
100 the cost of testing at lock-time if a mutex has non-default attributes.
101 One such method that an implementation can employ (and this can be made
102 fully transparent to fully conforming POSIX applications) is to
103 secretly pre-lock any mutexes that are initialized to non-default
104 attributes. Any later attempt to lock such a mutex causes the implemen‐
105 tation to branch to the ``slow path'' as if the mutex were unavailable;
106 then, on the slow path, the implementation can do the ``real work'' to
107 lock a non-default mutex. The underlying unlock operation is more com‐
108 plicated since the implementation never really wants to release the
109 pre-lock on this kind of mutex. This illustrates that, depending on the
110 hardware, there may be certain optimizations that can be used so that
111 whatever mutex attributes are considered ``most frequently used'' can
112 be processed most efficiently.
113
114 Process Shared Memory and Synchronization
115 The existence of memory mapping functions in this volume of
116 POSIX.1‐2017 leads to the possibility that an application may allocate
117 the synchronization objects from this section in memory that is
118 accessed by multiple processes (and therefore, by threads of multiple
119 processes).
120
121 In order to permit such usage, while at the same time keeping the usual
122 case (that is, usage within a single process) efficient, a process-
123 shared option has been defined.
124
125 If an implementation supports the _POSIX_THREAD_PROCESS_SHARED option,
126 then the process-shared attribute can be used to indicate that mutexes
127 or condition variables may be accessed by threads of multiple pro‐
128 cesses.
129
130 The default setting of PTHREAD_PROCESS_PRIVATE has been chosen for the
131 process-shared attribute so that the most efficient forms of these syn‐
132 chronization objects are created by default.
133
134 Synchronization variables that are initialized with the
135 PTHREAD_PROCESS_PRIVATE process-shared attribute may only be operated
136 on by threads in the process that initialized them. Synchronization
137 variables that are initialized with the PTHREAD_PROCESS_SHARED process-
138 shared attribute may be operated on by any thread in any process that
139 has access to it. In particular, these processes may exist beyond the
140 lifetime of the initializing process. For example, the following code
141 implements a simple counting semaphore in a mapped file that may be
142 used by many processes.
143
144
145 /* sem.h */
146 struct semaphore {
147 pthread_mutex_t lock;
148 pthread_cond_t nonzero;
149 unsigned count;
150 };
151 typedef struct semaphore semaphore_t;
152
153 semaphore_t *semaphore_create(char *semaphore_name);
154 semaphore_t *semaphore_open(char *semaphore_name);
155 void semaphore_post(semaphore_t *semap);
156 void semaphore_wait(semaphore_t *semap);
157 void semaphore_close(semaphore_t *semap);
158
159 /* sem.c */
160 #include <sys/types.h>
161 #include <sys/stat.h>
162 #include <sys/mman.h>
163 #include <fcntl.h>
164 #include <pthread.h>
165 #include "sem.h"
166
167 semaphore_t *
168 semaphore_create(char *semaphore_name)
169 {
170 int fd;
171 semaphore_t *semap;
172 pthread_mutexattr_t psharedm;
173 pthread_condattr_t psharedc;
174
175 fd = open(semaphore_name, O_RDWR | O_CREAT | O_EXCL, 0666);
176 if (fd < 0)
177 return (NULL);
178 (void) ftruncate(fd, sizeof(semaphore_t));
179 (void) pthread_mutexattr_init(&psharedm);
180 (void) pthread_mutexattr_setpshared(&psharedm,
181 PTHREAD_PROCESS_SHARED);
182 (void) pthread_condattr_init(&psharedc);
183 (void) pthread_condattr_setpshared(&psharedc,
184 PTHREAD_PROCESS_SHARED);
185 semap = (semaphore_t *) mmap(NULL, sizeof(semaphore_t),
186 PROT_READ | PROT_WRITE, MAP_SHARED,
187 fd, 0);
188 close (fd);
189 (void) pthread_mutex_init(&semap->lock, &psharedm);
190 (void) pthread_cond_init(&semap->nonzero, &psharedc);
191 semap->count = 0;
192 return (semap);
193 }
194
195 semaphore_t *
196 semaphore_open(char *semaphore_name)
197 {
198 int fd;
199 semaphore_t *semap;
200
201 fd = open(semaphore_name, O_RDWR, 0666);
202 if (fd < 0)
203 return (NULL);
204 semap = (semaphore_t *) mmap(NULL, sizeof(semaphore_t),
205 PROT_READ | PROT_WRITE, MAP_SHARED,
206 fd, 0);
207 close (fd);
208 return (semap);
209 }
210
211 void
212 semaphore_post(semaphore_t *semap)
213 {
214 pthread_mutex_lock(&semap->lock);
215 if (semap->count == 0)
216 pthread_cond_signal(&semapx->nonzero);
217 semap->count++;
218 pthread_mutex_unlock(&semap->lock);
219 }
220
221 void
222 semaphore_wait(semaphore_t *semap)
223 {
224 pthread_mutex_lock(&semap->lock);
225 while (semap->count == 0)
226 pthread_cond_wait(&semap->nonzero, &semap->lock);
227 semap->count--;
228 pthread_mutex_unlock(&semap->lock);
229 }
230
231 void
232 semaphore_close(semaphore_t *semap)
233 {
234 munmap((void *) semap, sizeof(semaphore_t));
235 }
236
237 The following code is for three separate processes that create, post,
238 and wait on a semaphore in the file /tmp/semaphore. Once the file is
239 created, the post and wait programs increment and decrement the count‐
240 ing semaphore (waiting and waking as required) even though they did not
241 initialize the semaphore.
242
243
244 /* create.c */
245 #include "pthread.h"
246 #include "sem.h"
247
248 int
249 main()
250 {
251 semaphore_t *semap;
252
253 semap = semaphore_create("/tmp/semaphore");
254 if (semap == NULL)
255 exit(1);
256 semaphore_close(semap);
257 return (0);
258 }
259
260 /* post */
261 #include "pthread.h"
262 #include "sem.h"
263
264 int
265 main()
266 {
267 semaphore_t *semap;
268
269 semap = semaphore_open("/tmp/semaphore");
270 if (semap == NULL)
271 exit(1);
272 semaphore_post(semap);
273 semaphore_close(semap);
274 return (0);
275 }
276
277 /* wait */
278 #include "pthread.h"
279 #include "sem.h"
280
281 int
282 main()
283 {
284 semaphore_t *semap;
285
286 semap = semaphore_open("/tmp/semaphore");
287 if (semap == NULL)
288 exit(1);
289 semaphore_wait(semap);
290 semaphore_close(semap);
291 return (0);
292 }
293
295 None.
296
298 pthread_cond_destroy(), pthread_create(), pthread_mutex_destroy()
299
300 The Base Definitions volume of POSIX.1‐2017, <pthread.h>
301
303 Portions of this text are reprinted and reproduced in electronic form
304 from IEEE Std 1003.1-2017, Standard for Information Technology -- Por‐
305 table Operating System Interface (POSIX), The Open Group Base Specifi‐
306 cations Issue 7, 2018 Edition, Copyright (C) 2018 by the Institute of
307 Electrical and Electronics Engineers, Inc and The Open Group. In the
308 event of any discrepancy between this version and the original IEEE and
309 The Open Group Standard, the original IEEE and The Open Group Standard
310 is the referee document. The original Standard can be obtained online
311 at http://www.opengroup.org/unix/online.html .
312
313 Any typographical or formatting errors that appear in this page are
314 most likely to have been introduced during the conversion of the source
315 files to man page format. To report such errors, see https://www.ker‐
316 nel.org/doc/man-pages/reporting_bugs.html .
317
318
319
320IEEE/The Open Group 2017 PTHREAD_MUTEXATTR_DESTROY(3P)