Annotation of src/lib/libc/thread-stub/thread-stub.c, Revision 1.8
1.8 ! matt 1: /* $NetBSD: thread-stub.c,v 1.7 2003/01/20 01:58:54 thorpej Exp $ */
1.2 thorpej 2:
3: /*-
4: * Copyright (c) 2003 The NetBSD Foundation, Inc.
5: * All rights reserved.
6: *
7: * This code is derived from software contributed to The NetBSD Foundation
8: * by Jason R. Thorpe.
9: *
10: * Redistribution and use in source and binary forms, with or without
11: * modification, are permitted provided that the following conditions
12: * are met:
13: * 1. Redistributions of source code must retain the above copyright
14: * notice, this list of conditions and the following disclaimer.
15: * 2. Redistributions in binary form must reproduce the above copyright
16: * notice, this list of conditions and the following disclaimer in the
17: * documentation and/or other materials provided with the distribution.
18: * 3. All advertising materials mentioning features or use of this software
19: * must display the following acknowledgement:
20: * This product includes software developed by the NetBSD
21: * Foundation, Inc. and its contributors.
22: * 4. Neither the name of The NetBSD Foundation nor the names of its
23: * contributors may be used to endorse or promote products derived
24: * from this software without specific prior written permission.
25: *
26: * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
27: * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
28: * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
29: * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
30: * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
31: * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
32: * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
33: * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
34: * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
35: * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
36: * POSSIBILITY OF SUCH DAMAGE.
37: */
38:
39: /*
40: * Stubs for thread operations, for use when threads are not used by
41: * the application. See "reentrant.h" for details.
42: */
43:
44: #ifdef _REENTRANT
45:
46: #define __LIBC_THREAD_STUBS
47:
48: #include "namespace.h"
49: #include "reentrant.h"
50:
1.5 thorpej 51: #include <errno.h>
1.2 thorpej 52: #include <signal.h>
1.8 ! matt 53: #include <stdlib.h>
1.2 thorpej 54: #include <unistd.h>
55:
56: extern int __isthreaded;
57:
58: #define DIE() (void)kill(getpid(), SIGABRT)
59:
60: #define CHECK_NOT_THREADED_ALWAYS() \
61: do { \
62: if (__isthreaded) \
63: DIE(); \
64: } while (/*CONSTCOND*/0)
65:
66: #if 1
67: #define CHECK_NOT_THREADED() CHECK_NOT_THREADED_ALWAYS()
68: #else
69: #define CHECK_NOT_THREADED() /* nothing */
70: #endif
71:
72: /* mutexes */
73:
74: int __libc_mutex_init_stub(mutex_t *, const mutexattr_t *);
75: int __libc_mutex_catchall_stub(mutex_t *);
76:
77: __weak_alias(__libc_mutex_init,__libc_mutex_init_stub)
78: __weak_alias(__libc_mutex_lock,__libc_mutex_catchall_stub)
79: __weak_alias(__libc_mutex_trylock,__libc_mutex_catchall_stub)
80: __weak_alias(__libc_mutex_unlock,__libc_mutex_catchall_stub)
81: __weak_alias(__libc_mutex_destroy,__libc_mutex_catchall_stub)
82:
1.4 thorpej 83: int __libc_mutexattr_catchall_stub(mutexattr_t *);
84: int __libc_mutexattr_settype_stub(mutexattr_t *, int);
85:
86: __weak_alias(__libc_mutexattr_init,__libc_mutexattr_catchall_stub)
87: __weak_alias(__libc_mutexattr_destroy,__libc_mutexattr_catchall_stub)
88: __weak_alias(__libc_mutexattr_settype,__libc_mutexattr_settype_stub)
89:
1.2 thorpej 90: int
91: __libc_mutex_init_stub(mutex_t *m, const mutexattr_t *a)
92: {
93: /* LINTED deliberate lack of effect */
94: (void)m;
95: /* LINTED deliberate lack of effect */
96: (void)a;
97:
98: CHECK_NOT_THREADED();
99:
100: return (0);
101: }
102:
103: int
104: __libc_mutex_catchall_stub(mutex_t *m)
105: {
106: /* LINTED deliberate lack of effect */
107: (void)m;
108:
109: CHECK_NOT_THREADED();
110:
111: return (0);
112: }
113:
1.4 thorpej 114: int
115: __libc_mutexattr_settype_stub(mutexattr_t *ma, int type)
116: {
117: /* LINTED deliberate lack of effect */
118: (void)ma;
119: /* LINTED deliberate lack of effect */
120: (void)type;
121:
122: return (0);
123: }
124:
125: int
126: __libc_mutexattr_catchall_stub(mutexattr_t *ma)
127: {
128: /* LINTED deliberate lack of effect */
129: (void)ma;
130:
131: CHECK_NOT_THREADED();
132:
133: return (0);
134: }
1.2 thorpej 135:
136: /* condition variables */
137:
138: int __libc_cond_init_stub(cond_t *, const condattr_t *);
139: int __libc_cond_wait_stub(cond_t *, mutex_t *);
140: int __libc_cond_timedwait_stub(cond_t *, mutex_t *,
141: const struct timespec *);
142: int __libc_cond_catchall_stub(cond_t *);
143:
144: __weak_alias(__libc_cond_init,__libc_cond_init_stub)
145: __weak_alias(__libc_cond_signal,__libc_cond_catchall_stub)
146: __weak_alias(__libc_cond_broadcast,__libc_cond_catchall_stub)
147: __weak_alias(__libc_cond_wait,__libc_cond_wait_stub)
148: __weak_alias(__libc_cond_timedwait,__libc_cond_timedwait_stub)
149: __weak_alias(__libc_cond_destroy,__libc_cond_catchall_stub)
150:
151: int
152: __libc_cond_init_stub(cond_t *c, const condattr_t *a)
153: {
154: /* LINTED deliberate lack of effect */
155: (void)c;
156: /* LINTED deliberate lack of effect */
157: (void)a;
158:
159: CHECK_NOT_THREADED();
160:
161: return (0);
162: }
163:
164: int
165: __libc_cond_wait_stub(cond_t *c, mutex_t *m)
166: {
167: /* LINTED deliberate lack of effect */
168: (void)c;
169: /* LINTED deliberate lack of effect */
170: (void)m;
171:
172: CHECK_NOT_THREADED();
173:
174: return (0);
175: }
176:
177: int
178: __libc_cond_timedwait_stub(cond_t *c, mutex_t *m, const struct timespec *t)
179: {
180: /* LINTED deliberate lack of effect */
181: (void)c;
182: /* LINTED deliberate lack of effect */
183: (void)m;
184: /* LINTED deliberate lack of effect */
185: (void)t;
186:
187: CHECK_NOT_THREADED();
188:
189: return (0);
190: }
191:
192: int
193: __libc_cond_catchall_stub(cond_t *c)
194: {
195: /* LINTED deliberate lack of effect */
196: (void)c;
197:
198: CHECK_NOT_THREADED();
199:
200: return (0);
201: }
202:
203:
204: /* read-write locks */
205:
206: int __libc_rwlock_init_stub(rwlock_t *, rwlockattr_t *);
207: int __libc_rwlock_catchall_stub(rwlock_t *);
208:
209: __weak_alias(__libc_rwlock_init,__libc_rwlock_init_stub)
210: __weak_alias(__libc_rwlock_rdlock,__libc_rwlock_catchall_stub)
211: __weak_alias(__libc_rwlock_wrlock,__libc_rwlock_catchall_stub)
212: __weak_alias(__libc_rwlock_tryrdlock,__libc_rwlock_catchall_stub)
213: __weak_alias(__libc_rwlock_trywrlock,__libc_rwlock_catchall_stub)
214: __weak_alias(__libc_rwlock_unlock,__libc_rwlock_catchall_stub)
215: __weak_alias(__libc_rwlock_destroy,__libc_rwlock_catchall_stub)
216:
217: int
218: __libc_rwlock_init_stub(rwlock_t *l, rwlockattr_t *a)
219: {
220: /* LINTED deliberate lack of effect */
221: (void)l;
222: /* LINTED deliberate lack of effect */
223: (void)a;
224:
225: CHECK_NOT_THREADED();
226:
227: return (0);
228: }
229:
230: int
231: __libc_rwlock_catchall_stub(rwlock_t *l)
232: {
233: /* LINTED deliberate lack of effect */
234: (void)l;
235:
236: CHECK_NOT_THREADED();
237:
238: return (0);
239: }
240:
241:
1.7 thorpej 242: /*
243: * thread-specific data; we need to actually provide a simple TSD
244: * implementation, since some thread-safe libraries want to use it.
245: */
246:
247: #define TSD_KEYS_MAX 64
248:
249: static struct {
250: void *tsd_val;
251: void (*tsd_dtor)(void *);
252: int tsd_inuse;
253: } __libc_tsd[TSD_KEYS_MAX];
254: static int __libc_tsd_nextkey;
1.2 thorpej 255:
256: int __libc_thr_keycreate_stub(thread_key_t *, void (*)(void *));
257: int __libc_thr_setspecific_stub(thread_key_t, const void *);
258: void *__libc_thr_getspecific_stub(thread_key_t);
259: int __libc_thr_keydelete_stub(thread_key_t);
260:
261: __weak_alias(__libc_thr_keycreate,__libc_thr_keycreate_stub)
262: __weak_alias(__libc_thr_setspecific,__libc_thr_setspecific_stub)
263: __weak_alias(__libc_thr_getspecific,__libc_thr_getspecific_stub)
264: __weak_alias(__libc_thr_keydelete,__libc_thr_keydelete_stub)
265:
266: int
267: __libc_thr_keycreate_stub(thread_key_t *k, void (*d)(void *))
268: {
1.7 thorpej 269: int i;
1.2 thorpej 270:
1.7 thorpej 271: for (i = __libc_tsd_nextkey; i < TSD_KEYS_MAX; i++) {
272: if (__libc_tsd[i].tsd_inuse == 0)
273: goto out;
274: }
275:
276: for (i = 0; i < __libc_tsd_nextkey; i++) {
277: if (__libc_tsd[i].tsd_inuse == 0)
278: goto out;
279: }
280:
281: return (EAGAIN);
282:
283: out:
284: /*
285: * XXX We don't actually do anything with the destructor. We
286: * XXX probably should.
287: */
288: __libc_tsd[i].tsd_inuse = 1;
289: __libc_tsd_nextkey = (i + i) % TSD_KEYS_MAX;
290: __libc_tsd[i].tsd_dtor = d;
291: *k = i;
1.2 thorpej 292:
293: return (0);
294: }
295:
296: int
297: __libc_thr_setspecific_stub(thread_key_t k, const void *v)
298: {
299:
1.7 thorpej 300: /* LINTED cast away const */
301: __libc_tsd[k].tsd_val = (void *) v;
1.2 thorpej 302:
303: return (0);
304: }
305:
306: void *
307: __libc_thr_getspecific_stub(thread_key_t k)
308: {
309:
1.7 thorpej 310: return (__libc_tsd[k].tsd_val);
1.2 thorpej 311: }
312:
313: int
314: __libc_thr_keydelete_stub(thread_key_t k)
315: {
316:
1.7 thorpej 317: /*
318: * XXX Do not recycle key; see big comment in libpthread.
319: */
320:
321: __libc_tsd[k].tsd_dtor = NULL;
1.2 thorpej 322:
323: return (0);
324: }
325:
326:
327: /* misc. */
328:
329: int __libc_thr_once_stub(once_t *, void (*)(void));
330: int __libc_thr_sigsetmask_stub(int, const sigset_t *, sigset_t *);
331: thr_t __libc_thr_self_stub(void);
1.5 thorpej 332: void __libc_thr_yield_stub(void);
333: int __libc_thr_create_stub(thr_t *, const thrattr_t *,
334: void *(*)(void *), void *);
335: void __libc_thr_exit_stub(void *);
1.2 thorpej 336: int *__libc_thr_errno_stub(void);
337:
338: __weak_alias(__libc_thr_once,__libc_thr_once_stub)
339: __weak_alias(__libc_thr_sigsetmask,__libc_thr_sigsetmask_stub)
340: __weak_alias(__libc_thr_self,__libc_thr_self_stub)
1.5 thorpej 341: __weak_alias(__libc_thr_yield,__libc_thr_yield_stub)
342: __weak_alias(__libc_thr_create,__libc_thr_create_stub)
343: __weak_alias(__libc_thr_exit,__libc_thr_exit_stub)
1.2 thorpej 344: __weak_alias(__libc_thr_errno,__libc_thr_errno_stub)
345:
1.5 thorpej 346:
1.2 thorpej 347: int
348: __libc_thr_once_stub(once_t *o, void (*r)(void))
349: {
350:
1.3 thorpej 351: /* XXX Knowledge of libpthread types. */
352:
353: if (o->pto_done == 0) {
354: (*r)();
355: o->pto_done = 1;
356: }
1.2 thorpej 357:
358: return (0);
359: }
360:
361: int
362: __libc_thr_sigsetmask_stub(int h, const sigset_t *s, sigset_t *o)
363: {
364: /* LINTED deliberate lack of effect */
365: (void)h;
366: /* LINTED deliberate lack of effect */
367: (void)s;
368: /* LINTED deliberate lack of effect */
369: (void)o;
370:
371: CHECK_NOT_THREADED();
372:
373: /* XXX just use sigmask(2)? abort? */
374:
375: return (0);
376: }
377:
378: thr_t
379: __libc_thr_self_stub(void)
380: {
381:
1.6 thorpej 382: return ((thr_t) -1);
1.5 thorpej 383: }
384:
385: void
386: __libc_thr_yield_stub(void)
387: {
388:
389: /* Nothing to do. */
390: }
391:
392: int
393: __libc_thr_create_stub(thr_t *tp, const thrattr_t *ta,
394: void *(*f)(void *), void *a)
395: {
396: /* LINTED deliberate lack of effect */
397: (void)tp;
398: /* LINTED deliberate lack of effect */
399: (void)ta;
400: /* LINTED deliberate lack of effect */
401: (void)f;
402: /* LINTED deliberate lack of effect */
403: (void)a;
404:
1.2 thorpej 405: DIE();
406:
1.5 thorpej 407: return (EOPNOTSUPP);
408: }
409:
410: void
411: __libc_thr_exit_stub(void *v)
412: {
413: /* LINTED deliberate lack of effect */
414: (void)v;
415:
416: exit(0);
1.2 thorpej 417: }
418:
419: int *
420: __libc_thr_errno_stub(void)
421: {
422:
423: DIE();
424:
425: return (NULL);
426: }
427:
428: #endif /* _REENTRANT */
CVSweb <webmaster@jp.NetBSD.org>