OpenCores
URL https://opencores.org/ocsvn/scarts/scarts/trunk

Subversion Repositories scarts

[/] [scarts/] [trunk/] [toolchain/] [scarts-gcc/] [gcc-4.1.1/] [gcc/] [gthr-solaris.h] - Blame information for rev 20

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 12 jlechner
/* Threads compatibility routines for libgcc2 and libobjc.  */
2
/* Compile this one with gcc.  */
3
/* Copyright (C) 1997, 1999, 2000, 2004, 2005
4
   Free Software Foundation, Inc.
5
 
6
This file is part of GCC.
7
 
8
GCC is free software; you can redistribute it and/or modify it under
9
the terms of the GNU General Public License as published by the Free
10
Software Foundation; either version 2, or (at your option) any later
11
version.
12
 
13
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
14
WARRANTY; without even the implied warranty of MERCHANTABILITY or
15
FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
16
for more details.
17
 
18
You should have received a copy of the GNU General Public License
19
along with GCC; see the file COPYING.  If not, write to the Free
20
Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
21
02110-1301, USA.  */
22
 
23
/* As a special exception, if you link this library with other files,
24
   some of which are compiled with GCC, to produce an executable,
25
   this library does not by itself cause the resulting executable
26
   to be covered by the GNU General Public License.
27
   This exception does not however invalidate any other reasons why
28
   the executable file might be covered by the GNU General Public License.  */
29
 
30
#ifndef GCC_GTHR_SOLARIS_H
31
#define GCC_GTHR_SOLARIS_H
32
 
33
/* Solaris threads as found in Solaris 2.[456].
34
   Actually these are Unix International (UI) threads, but I don't
35
   know if anyone else implements these.  */
36
 
37
#define __GTHREADS 1
38
 
39
#include <thread.h>
40
#include <errno.h>
41
 
42
typedef thread_key_t __gthread_key_t;
43
typedef struct {
44
  mutex_t mutex;
45
  int once;
46
} __gthread_once_t;
47
typedef mutex_t __gthread_mutex_t;
48
 
49
typedef struct {
50
  long depth;
51
  thread_t owner;
52
  mutex_t actual;
53
} __gthread_recursive_mutex_t;
54
 
55
#define __GTHREAD_ONCE_INIT { DEFAULTMUTEX, 0 }
56
#define __GTHREAD_MUTEX_INIT DEFAULTMUTEX
57
#define __GTHREAD_RECURSIVE_MUTEX_INIT_FUNCTION __gthread_recursive_mutex_init_function
58
 
59
#if SUPPORTS_WEAK && GTHREAD_USE_WEAK
60
# define __gthrw(name) \
61
  extern __typeof(name) __gthrw_ ## name __attribute__ ((__weakref__(#name)));
62
# define __gthrw_(name) __gthrw_ ## name
63
#else
64
# define __gthrw(name)
65
# define __gthrw_(name) name
66
#endif
67
 
68
__gthrw(thr_keycreate)
69
__gthrw(thr_getspecific)
70
__gthrw(thr_setspecific)
71
__gthrw(thr_create)
72
 
73
__gthrw(mutex_lock)
74
__gthrw(mutex_trylock)
75
__gthrw(mutex_unlock)
76
 
77
#ifdef _LIBOBJC
78
__gthrw(thr_exit)
79
__gthrw(thr_keycreate)
80
__gthrw(thr_getprio)
81
__gthrw(thr_self)
82
__gthrw(thr_setprio)
83
__gthrw(thr_yield)
84
 
85
__gthrw(cond_init)
86
__gthrw(cond_destroy)
87
__gthrw(cond_wait)
88
__gthrw(cond_broadcast)
89
__gthrw(cond_signal)
90
 
91
__gthrw(mutex_init)
92
__gthrw(mutex_destroy)
93
#endif
94
 
95
#if SUPPORTS_WEAK && GTHREAD_USE_WEAK
96
 
97
/* This will not actually work in Solaris 2.5, since libc contains
98
   dummy symbols of all thr_* routines.  */
99
 
100
static inline int
101
__gthread_active_p (void)
102
{
103
  static void *const __gthread_active_ptr = (void *) &__gthrw_(thr_create);
104
  return __gthread_active_ptr != 0;
105
}
106
 
107
#else /* not SUPPORTS_WEAK */
108
 
109
static inline int
110
__gthread_active_p (void)
111
{
112
  return 1;
113
}
114
 
115
#endif /* SUPPORTS_WEAK */
116
 
117
#ifdef _LIBOBJC
118
 
119
/* Key structure for maintaining thread specific storage */
120
static thread_key_t _objc_thread_storage;
121
 
122
/* Thread local storage for a single thread */
123
static void *thread_local_storage = NULL;
124
 
125
/* Backend initialization functions */
126
 
127
/* Initialize the threads subsystem.  */
128
static inline int
129
__gthread_objc_init_thread_system (void)
130
{
131
  /* Initialize the thread storage key.  */
132
  if (__gthread_active_p ()
133
      && __gthrw_(thr_keycreate) (&_objc_thread_storage, NULL) == 0)
134
    return 0;
135
 
136
  return -1;
137
}
138
 
139
/* Close the threads subsystem.  */
140
static inline int
141
__gthread_objc_close_thread_system (void)
142
{
143
  if (__gthread_active_p ())
144
    return 0;
145
  else
146
    return -1;
147
}
148
 
149
/* Backend thread functions */
150
 
151
/* Create a new thread of execution.  */
152
static inline objc_thread_t
153
__gthread_objc_thread_detach (void (*func)(void *), void *arg)
154
{
155
  objc_thread_t thread_id;
156
  thread_t new_thread_id = 0;
157
 
158
  if (!__gthread_active_p ())
159
    return NULL;
160
 
161
  if (__gthrw_(thr_create) (NULL, 0, (void *) func, arg,
162
                  THR_DETACHED | THR_NEW_LWP,
163
                  &new_thread_id) == 0)
164
    thread_id = *(objc_thread_t *) &new_thread_id;
165
  else
166
    thread_id = NULL;
167
 
168
  return thread_id;
169
}
170
 
171
/* Set the current thread's priority.  */
172
static inline int
173
__gthread_objc_thread_set_priority (int priority)
174
{
175
  int sys_priority = 0;
176
 
177
  if (!__gthread_active_p ())
178
    return -1;
179
 
180
  switch (priority)
181
    {
182
    case OBJC_THREAD_INTERACTIVE_PRIORITY:
183
      sys_priority = 300;
184
      break;
185
    default:
186
    case OBJC_THREAD_BACKGROUND_PRIORITY:
187
      sys_priority = 200;
188
      break;
189
    case OBJC_THREAD_LOW_PRIORITY:
190
      sys_priority = 1000;
191
      break;
192
    }
193
 
194
  /* Change priority */
195
  if (__gthrw_(thr_setprio) (__gthrw_(thr_self) (), sys_priority) == 0)
196
    return 0;
197
  else
198
    return -1;
199
}
200
 
201
/* Return the current thread's priority.  */
202
static inline int
203
__gthread_objc_thread_get_priority (void)
204
{
205
  int sys_priority;
206
 
207
  if (!__gthread_active_p ())
208
    return OBJC_THREAD_INTERACTIVE_PRIORITY;
209
 
210
  if (__gthrw_(thr_getprio) (__gthrw_(thr_self) (), &sys_priority) == 0)
211
    {
212
      if (sys_priority >= 250)
213
        return OBJC_THREAD_INTERACTIVE_PRIORITY;
214
      else if (sys_priority >= 150)
215
        return OBJC_THREAD_BACKGROUND_PRIORITY;
216
      return OBJC_THREAD_LOW_PRIORITY;
217
    }
218
 
219
  /* Couldn't get priority.  */
220
  return -1;
221
}
222
 
223
/* Yield our process time to another thread.  */
224
static inline void
225
__gthread_objc_thread_yield (void)
226
{
227
  if (__gthread_active_p ())
228
    __gthrw_(thr_yield) ();
229
}
230
 
231
/* Terminate the current thread.  */
232
static inline int
233
__gthread_objc_thread_exit (void)
234
{
235
  if (__gthread_active_p ())
236
    /* exit the thread */
237
    __gthrw_(thr_exit) (&__objc_thread_exit_status);
238
 
239
  /* Failed if we reached here */
240
  return -1;
241
}
242
 
243
/* Returns an integer value which uniquely describes a thread.  */
244
static inline objc_thread_t
245
__gthread_objc_thread_id (void)
246
{
247
  if (__gthread_active_p ())
248
    return (objc_thread_t) __gthrw_(thr_self) ();
249
  else
250
    return (objc_thread_t) 1;
251
}
252
 
253
/* Sets the thread's local storage pointer.  */
254
static inline int
255
__gthread_objc_thread_set_data (void *value)
256
{
257
  if (__gthread_active_p ())
258
    {
259
      if (__gthrw_(thr_setspecific) (_objc_thread_storage, value) == 0)
260
        return 0;
261
      else
262
        return -1;
263
    }
264
  else
265
    {
266
      thread_local_storage = value;
267
      return 0;
268
    }
269
}
270
 
271
/* Returns the thread's local storage pointer.  */
272
static inline void *
273
__gthread_objc_thread_get_data (void)
274
{
275
  void *value = NULL;
276
 
277
  if (__gthread_active_p ())
278
    {
279
      if (__gthrw_(thr_getspecific) (_objc_thread_storage, &value) == 0)
280
        return value;
281
      else
282
        return NULL;
283
    }
284
  else
285
    return thread_local_storage;
286
}
287
 
288
/* Backend mutex functions */
289
 
290
/* Allocate a mutex.  */
291
static inline int
292
__gthread_objc_mutex_allocate (objc_mutex_t mutex)
293
{
294
  if (__gthread_active_p ()
295
      && __gthrw_(mutex_init) ((mutex_t *) (&(mutex->backend)), USYNC_THREAD, 0))
296
    return -1;
297
 
298
  return 0;
299
}
300
 
301
/* Deallocate a mutex.  */
302
static inline int
303
__gthread_objc_mutex_deallocate (objc_mutex_t mutex)
304
{
305
  if (__gthread_active_p ())
306
    __gthrw_(mutex_destroy) ((mutex_t *) (&(mutex->backend)));
307
 
308
  return 0;
309
}
310
 
311
/* Grab a lock on a mutex.  */
312
static inline int
313
__gthread_objc_mutex_lock (objc_mutex_t mutex)
314
{
315
  if (__gthread_active_p ()
316
      && __gthrw_(mutex_lock) ((mutex_t *) (&(mutex->backend))) != 0)
317
    return -1;
318
 
319
  return 0;
320
}
321
 
322
/* Try to grab a lock on a mutex.  */
323
static inline int
324
__gthread_objc_mutex_trylock (objc_mutex_t mutex)
325
{
326
  if (__gthread_active_p ()
327
      && __gthrw_(mutex_trylock) ((mutex_t *) (&(mutex->backend))) != 0)
328
    return -1;
329
 
330
  return 0;
331
}
332
 
333
/* Unlock the mutex */
334
static inline int
335
__gthread_objc_mutex_unlock (objc_mutex_t mutex)
336
{
337
  if (__gthread_active_p ()
338
      && __gthrw_(mutex_unlock) ((mutex_t *) (&(mutex->backend))) != 0)
339
    return -1;
340
 
341
  return 0;
342
}
343
 
344
/* Backend condition mutex functions */
345
 
346
/* Allocate a condition.  */
347
static inline int
348
__gthread_objc_condition_allocate (objc_condition_t condition)
349
{
350
  if (__gthread_active_p ())
351
    return __gthrw_(cond_init) ((cond_t *) (&(condition->backend)), USYNC_THREAD,
352
                      NULL);
353
  else
354
    return 0;
355
}
356
 
357
/* Deallocate a condition.  */
358
static inline int
359
__gthread_objc_condition_deallocate (objc_condition_t condition)
360
{
361
  if (__gthread_active_p ())
362
    return __gthrw_(cond_destroy) ((cond_t *) (&(condition->backend)));
363
  else
364
    return 0;
365
}
366
 
367
/* Wait on the condition */
368
static inline int
369
__gthread_objc_condition_wait (objc_condition_t condition, objc_mutex_t mutex)
370
{
371
  if (__gthread_active_p ())
372
    return __gthrw_(cond_wait) ((cond_t *) (&(condition->backend)),
373
                      (mutex_t *) (&(mutex->backend)));
374
  else
375
    return 0;
376
}
377
 
378
/* Wake up all threads waiting on this condition.  */
379
static inline int
380
__gthread_objc_condition_broadcast (objc_condition_t condition)
381
{
382
  if (__gthread_active_p ())
383
    return __gthrw_(cond_broadcast) ((cond_t *) (&(condition->backend)));
384
  else
385
    return 0;
386
}
387
 
388
/* Wake up one thread waiting on this condition.  */
389
static inline int
390
__gthread_objc_condition_signal (objc_condition_t condition)
391
{
392
  if (__gthread_active_p ())
393
    return __gthrw_(cond_signal) ((cond_t *) (&(condition->backend)));
394
  else
395
    return 0;
396
}
397
 
398
#else /* _LIBOBJC */
399
 
400
static inline int
401
__gthread_once (__gthread_once_t *once, void (*func) (void))
402
{
403
  if (! __gthread_active_p ())
404
    return -1;
405
 
406
  if (once == 0 || func == 0)
407
    return EINVAL;
408
 
409
  if (once->once == 0)
410
    {
411
      int status = __gthrw_(mutex_lock) (&once->mutex);
412
      if (status != 0)
413
        return status;
414
      if (once->once == 0)
415
        {
416
          (*func) ();
417
          once->once++;
418
        }
419
      __gthrw_(mutex_unlock) (&once->mutex);
420
    }
421
  return 0;
422
}
423
 
424
static inline int
425
__gthread_key_create (__gthread_key_t *key, void (*dtor) (void *))
426
{
427
  /* Solaris 2.5 contains thr_* routines no-op in libc, so test if we actually
428
     got a reasonable key value, and if not, fail.  */
429
  *key = (__gthread_key_t)-1;
430
  if (__gthrw_(thr_keycreate) (key, dtor) != 0 || *key == (__gthread_key_t)-1)
431
    return -1;
432
  else
433
    return 0;
434
}
435
 
436
static inline int
437
__gthread_key_delete (__gthread_key_t key)
438
{
439
  /* Not possible.  */
440
  return -1;
441
}
442
 
443
static inline void *
444
__gthread_getspecific (__gthread_key_t key)
445
{
446
  void *ptr;
447
  if (__gthrw_(thr_getspecific) (key, &ptr) == 0)
448
    return ptr;
449
  else
450
    return 0;
451
}
452
 
453
static inline int
454
__gthread_setspecific (__gthread_key_t key, const void *ptr)
455
{
456
  return __gthrw_(thr_setspecific) (key, (void *) ptr);
457
}
458
 
459
static inline int
460
__gthread_mutex_lock (__gthread_mutex_t *mutex)
461
{
462
  if (__gthread_active_p ())
463
    return __gthrw_(mutex_lock) (mutex);
464
  else
465
    return 0;
466
}
467
 
468
static inline int
469
__gthread_mutex_trylock (__gthread_mutex_t *mutex)
470
{
471
  if (__gthread_active_p ())
472
    return __gthrw_(mutex_trylock) (mutex);
473
  else
474
    return 0;
475
}
476
 
477
static inline int
478
__gthread_mutex_unlock (__gthread_mutex_t *mutex)
479
{
480
  if (__gthread_active_p ())
481
    return __gthrw_(mutex_unlock) (mutex);
482
  else
483
    return 0;
484
}
485
 
486
static inline int
487
__gthread_recursive_mutex_init_function (__gthread_recursive_mutex_t *mutex)
488
{
489
  mutex->depth = 0;
490
  mutex->owner = (thread_t) 0;
491
  return __gthrw_(mutex_init) (&mutex->actual, USYNC_THREAD, 0);
492
}
493
 
494
static inline int
495
__gthread_recursive_mutex_lock (__gthread_recursive_mutex_t *mutex)
496
{
497
  if (__gthread_active_p ())
498
    {
499
      thread_t me = __gthrw_(thr_self) ();
500
 
501
      if (mutex->owner != me)
502
        {
503
          __gthrw_(mutex_lock) (&mutex->actual);
504
          mutex->owner = me;
505
        }
506
 
507
      mutex->depth++;
508
    }
509
  return 0;
510
}
511
 
512
static inline int
513
__gthread_recursive_mutex_trylock (__gthread_recursive_mutex_t *mutex)
514
{
515
  if (__gthread_active_p ())
516
    {
517
      thread_t me = __gthrw_(thr_self) ();
518
 
519
      if (mutex->owner != me)
520
        {
521
          if (__gthrw_(mutex_trylock) (&mutex->actual))
522
            return 1;
523
          mutex->owner = me;
524
        }
525
 
526
      mutex->depth++;
527
    }
528
  return 0;
529
}
530
 
531
static inline int
532
__gthread_recursive_mutex_unlock (__gthread_recursive_mutex_t *mutex)
533
{
534
  if (__gthread_active_p ())
535
    {
536
      if (--mutex->depth == 0)
537
        {
538
           mutex->owner = (thread_t) 0;
539
           __gthrw_(mutex_unlock) (&mutex->actual);
540
        }
541
    }
542
  return 0;
543
}
544
 
545
#endif /* _LIBOBJC */
546
 
547
#endif /* ! GCC_GTHR_SOLARIS_H */

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.