Mercurial > hg > CbC > CbC_gcc
comparison libgcc/config/gthr-vxworks.c @ 145:1830386684a0
gcc-9.2.0
author | anatofuz |
---|---|
date | Thu, 13 Feb 2020 11:34:05 +0900 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
131:84e7813d76e9 | 145:1830386684a0 |
---|---|
1 /* Copyright (C) 2002-2020 Free Software Foundation, Inc. | |
2 Contributed by Zack Weinberg <zack@codesourcery.com> | |
3 | |
4 This file is part of GCC. | |
5 | |
6 GCC is free software; you can redistribute it and/or modify it under | |
7 the terms of the GNU General Public License as published by the Free | |
8 Software Foundation; either version 3, or (at your option) any later | |
9 version. | |
10 | |
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY | |
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
14 for more details. | |
15 | |
16 Under Section 7 of GPL version 3, you are granted additional | |
17 permissions described in the GCC Runtime Library Exception, version | |
18 3.1, as published by the Free Software Foundation. | |
19 | |
20 You should have received a copy of the GNU General Public License and | |
21 a copy of the GCC Runtime Library Exception along with this program; | |
22 see the files COPYING3 and COPYING.RUNTIME respectively. If not, see | |
23 <http://www.gnu.org/licenses/>. */ | |
24 | |
25 /* Threads compatibility routines for libgcc2 for VxWorks. | |
26 | |
27 This file implements the init-once service exposed by gthr-vxworks.h. */ | |
28 | |
29 #include "tconfig.h" | |
30 #include "tsystem.h" | |
31 #include "gthr.h" | |
32 | |
33 #if defined(__GTHREADS) | |
34 | |
35 #include <vxWorks.h> | |
36 | |
37 #ifndef __RTP__ | |
38 # include <vxLib.h> | |
39 # include <taskHookLib.h> | |
40 #else /* __RTP__ */ | |
41 # include <errno.h> | |
42 #endif /* __RTP__ */ | |
43 | |
44 /* ----------------------------- Init-once ------------------------------- */ | |
45 | |
46 static void | |
47 __release (__gthread_once_t ** __guard) | |
48 { | |
49 (*__guard)->busy = 0; | |
50 } | |
51 | |
52 int | |
53 __gthread_once (__gthread_once_t * __guard, void (*__func) (void)) | |
54 { | |
55 if (__guard->done) | |
56 return 0; | |
57 | |
58 /* Busy-wait until we have exclusive access to the state. Check if | |
59 another thread managed to perform the init call in the interim. */ | |
60 | |
61 while (!__TAS(&__guard->busy)) | |
62 { | |
63 if (__guard->done) | |
64 return 0; | |
65 taskDelay (1); | |
66 } | |
67 | |
68 if (!__guard->done) | |
69 { | |
70 #ifndef __USING_SJLJ_EXCEPTIONS__ | |
71 /* Setup a cleanup to release the guard when __func() throws an | |
72 exception. We cannot use this with SJLJ exceptions as | |
73 Unwind_Register calls __gthread_once, leading to an infinite | |
74 recursion. */ | |
75 __attribute__ ((cleanup (__release))) | |
76 __gthread_once_t *__temp = __guard; | |
77 #endif | |
78 | |
79 __func (); | |
80 __guard->done = 1; | |
81 } | |
82 | |
83 __release(&__guard); | |
84 return 0; | |
85 } | |
86 | |
87 #endif /* __GTHREADS */ |