• R/O
  • HTTP
  • SSH
  • HTTPS

提交

標籤
無標籤

Frequently used words (click to add to your profile)

javac++androidlinuxc#windowsobjective-ccocoa誰得qtpythonphprubygameguibathyscaphec計画中(planning stage)翻訳omegatframeworktwitterdomtestvb.netdirectxゲームエンジンbtronarduinopreviewer

Commit MetaInfo

修訂d0bc0d2bc8e5898bed6dfa6f253d164e9fc149f4 (tree)
時間2019-11-08 11:03:43
作者Waldemar Brodkorb <wbx@open...>
CommiterWaldemar Brodkorb

Log Message

riscv64: implement NPTL/TLS

basically from or1k port of uClibc-ng, with fixes for structures in
pthreadtypes.h from 64 bit architectures.

18 testsuite failures counted.

Change Summary

差異

--- a/extra/Configs/Config.in
+++ b/extra/Configs/Config.in
@@ -529,6 +529,7 @@ config UCLIBC_HAS_LINUXTHREADS
529529 # linuxthreads need nanosleep()
530530 select UCLIBC_HAS_REALTIME
531531 depends on !TARGET_aarch64 && \
532+ !TARGET_riscv64 && \
532533 !TARGET_metag
533534 help
534535 If you want to compile uClibc with Linuxthreads support, then answer Y.
--- a/ldso/ldso/riscv64/elfinterp.c
+++ b/ldso/ldso/riscv64/elfinterp.c
@@ -33,11 +33,6 @@
3333
3434 #include "ldso.h"
3535
36-#if defined(USE_TLS) && USE_TLS
37-#include "dl-tls.h"
38-#include "tlsdeschtab.h"
39-#endif
40-
4136 extern int _dl_linux_resolve(void);
4237
4338 unsigned long _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
@@ -212,6 +207,18 @@ _dl_do_reloc (struct elf_resolve *tpnt, struct r_scope_elem *scope,
212207 _dl_memcpy((void *) reloc_addr,
213208 (void *) symbol_addr, sym_ref.sym->st_size);
214209 break;
210+#if defined USE_TLS && USE_TLS
211+ case R_RISCV_TLS_DTPMOD64:
212+ *reloc_addr = tls_tpnt->l_tls_modid;
213+ break;
214+ case R_RISCV_TLS_DTPREL64:
215+ *reloc_addr = symbol_addr;
216+ break;
217+ case R_RISCV_TLS_TPREL64:
218+ CHECK_STATIC_TLS ((struct link_map *) tls_tpnt);
219+ *reloc_addr = tls_tpnt->l_tls_offset + symbol_addr + rpnt->r_addend;
220+ break;
221+#endif
215222 default:
216223 return -1; /*call _dl_exit(1) */
217224 }
--- a/libc/sysdeps/linux/riscv64/sys/ucontext.h
+++ b/libc/sysdeps/linux/riscv64/sys/ucontext.h
@@ -21,6 +21,8 @@
2121 #define _SYS_UCONTEXT_H 1
2222
2323 #include <features.h>
24+#include <signal.h>
25+#include <bits/sigcontext.h>
2426
2527 typedef unsigned long int __riscv_mc_gp_state[32];
2628
--- a/libc/sysdeps/linux/riscv64/sysdep.h
+++ b/libc/sysdeps/linux/riscv64/sysdep.h
@@ -20,6 +20,7 @@
2020 #define _LINUX_RISCV_SYSDEP_H 1
2121
2222 #include <common/sysdep.h>
23+#include <sys/syscall.h>
2324
2425 #ifdef __ASSEMBLER__
2526
--- /dev/null
+++ b/libpthread/nptl/sysdeps/riscv64/Makefile.arch
@@ -0,0 +1,4 @@
1+# Makefile for uClibc-ng NPTL
2+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
3+
4+libc_arch_a_CSRC = libc-tls.c
--- /dev/null
+++ b/libpthread/nptl/sysdeps/riscv64/dl-tls.h
@@ -0,0 +1,24 @@
1+/* Copyright (C) 2005-2016 Free Software Foundation, Inc.
2+
3+ The GNU C Library is free software; you can redistribute it and/or
4+ modify it under the terms of the GNU Lesser General Public License as
5+ published by the Free Software Foundation; either version 2.1 of the
6+ License, or (at your option) any later version.
7+
8+ The GNU C Library is distributed in the hope that it will be useful,
9+ but WITHOUT ANY WARRANTY; without even the implied warranty of
10+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11+ Lesser General Public License for more details.
12+
13+ You should have received a copy of the GNU Lesser General Public
14+ License along with the GNU C Library; if not, see
15+ <http://www.gnu.org/licenses/>. */
16+
17+/* Type used for the representation of TLS information in the GOT. */
18+typedef struct
19+{
20+ unsigned long int ti_module;
21+ unsigned long int ti_offset;
22+} tls_index;
23+
24+extern void *__tls_get_addr (tls_index *ti);
--- /dev/null
+++ b/libpthread/nptl/sysdeps/riscv64/libc-tls.c
@@ -0,0 +1,34 @@
1+/* Copyright (C) 2005-2016 Free Software Foundation, Inc.
2+
3+ The GNU C Library is free software; you can redistribute it and/or
4+ modify it under the terms of the GNU Lesser General Public License as
5+ published by the Free Software Foundation; either version 2.1 of the
6+ License, or (at your option) any later version.
7+
8+ The GNU C Library is distributed in the hope that it will be useful,
9+ but WITHOUT ANY WARRANTY; without even the implied warranty of
10+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11+ Lesser General Public License for more details.
12+
13+ You should have received a copy of the GNU Lesser General Public
14+ License along with the GNU C Library; if not, see
15+ <http://www.gnu.org/licenses/>. */
16+
17+#include <sysdeps/generic/libc-tls.c>
18+#include <dl-tls.h>
19+
20+/* On OpenRISC, linker optimizations are not required, so __tls_get_addr
21+ can be called even in statically linked binaries. In this case module
22+ must be always 1 and PT_TLS segment exist in the binary, otherwise it
23+ would not link. */
24+
25+#if defined(USE_TLS) && USE_TLS
26+
27+void *
28+__tls_get_addr (tls_index *ti)
29+{
30+ dtv_t *dtv = THREAD_DTV ();
31+ return (char *) dtv[1].pointer.val + ti->ti_offset;
32+}
33+
34+#endif
--- /dev/null
+++ b/libpthread/nptl/sysdeps/riscv64/pthread_spin_lock.c
@@ -0,0 +1,65 @@
1+/* pthread_spin_lock -- lock a spin lock. Generic version.
2+ Copyright (C) 2012-2016 Free Software Foundation, Inc.
3+
4+ The GNU C Library is free software; you can redistribute it and/or
5+ modify it under the terms of the GNU Lesser General Public
6+ License as published by the Free Software Foundation; either
7+ version 2.1 of the License, or (at your option) any later version.
8+
9+ The GNU C Library is distributed in the hope that it will be useful,
10+ but WITHOUT ANY WARRANTY; without even the implied warranty of
11+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12+ Lesser General Public License for more details.
13+
14+ You should have received a copy of the GNU Lesser General Public
15+ License along with the GNU C Library; if not, see
16+ <http://www.gnu.org/licenses/>. */
17+
18+#include <atomic.h>
19+#include "pthreadP.h"
20+
21+/* A machine-specific version can define SPIN_LOCK_READS_BETWEEN_CMPXCHG
22+ to the number of plain reads that it's optimal to spin on between uses
23+ of atomic_compare_and_exchange_val_acq. If spinning forever is optimal
24+ then use -1. If no plain reads here would ever be optimal, use 0. */
25+#define SPIN_LOCK_READS_BETWEEN_CMPXCHG 1000
26+
27+int
28+pthread_spin_lock (pthread_spinlock_t *lock)
29+{
30+ /* atomic_exchange usually takes less instructions than
31+ atomic_compare_and_exchange. On the other hand,
32+ atomic_compare_and_exchange potentially generates less bus traffic
33+ when the lock is locked.
34+ We assume that the first try mostly will be successful, and we use
35+ atomic_exchange. For the subsequent tries we use
36+ atomic_compare_and_exchange. */
37+ if (atomic_exchange_acq (lock, 1) == 0)
38+ return 0;
39+
40+ do
41+ {
42+ /* The lock is contended and we need to wait. Going straight back
43+ to cmpxchg is not a good idea on many targets as that will force
44+ expensive memory synchronizations among processors and penalize other
45+ running threads.
46+ On the other hand, we do want to update memory state on the local core
47+ once in a while to avoid spinning indefinitely until some event that
48+ will happen to update local memory as a side-effect. */
49+ if (SPIN_LOCK_READS_BETWEEN_CMPXCHG >= 0)
50+ {
51+ int wait = SPIN_LOCK_READS_BETWEEN_CMPXCHG;
52+
53+ while (*lock != 0 && wait > 0)
54+ --wait;
55+ }
56+ else
57+ {
58+ while (*lock != 0)
59+ ;
60+ }
61+ }
62+ while (atomic_compare_and_exchange_val_acq (lock, 1, 0) != 0);
63+
64+ return 0;
65+}
--- /dev/null
+++ b/libpthread/nptl/sysdeps/riscv64/pthread_spin_trylock.c
@@ -0,0 +1,26 @@
1+/* pthread_spin_trylock -- trylock a spin lock. Generic version.
2+ Copyright (C) 2012-2016 Free Software Foundation, Inc.
3+
4+ The GNU C Library is free software; you can redistribute it and/or
5+ modify it under the terms of the GNU Lesser General Public
6+ License as published by the Free Software Foundation; either
7+ version 2.1 of the License, or (at your option) any later version.
8+
9+ The GNU C Library is distributed in the hope that it will be useful,
10+ but WITHOUT ANY WARRANTY; without even the implied warranty of
11+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12+ Lesser General Public License for more details.
13+
14+ You should have received a copy of the GNU Lesser General Public
15+ License along with the GNU C Library; if not, see
16+ <http://www.gnu.org/licenses/>. */
17+
18+#include <errno.h>
19+#include <atomic.h>
20+#include "pthreadP.h"
21+
22+int
23+pthread_spin_trylock (pthread_spinlock_t *lock)
24+{
25+ return atomic_exchange_acq (lock, 1) ? EBUSY : 0;
26+}
--- /dev/null
+++ b/libpthread/nptl/sysdeps/riscv64/pthreaddef.h
@@ -0,0 +1,36 @@
1+/* Copyright (C) 2002-2012 Free Software Foundation, Inc.
2+
3+ The GNU C Library is free software; you can redistribute it and/or
4+ modify it under the terms of the GNU Lesser General Public License as
5+ published by the Free Software Foundation; either version 2.1 of the
6+ License, or (at your option) any later version.
7+
8+ The GNU C Library is distributed in the hope that it will be useful,
9+ but WITHOUT ANY WARRANTY; without even the implied warranty of
10+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11+ Lesser General Public License for more details.
12+
13+ You should have received a copy of the GNU Lesser General Public
14+ License along with the GNU C Library; if not, see
15+ <http://www.gnu.org/licenses/>. */
16+
17+/* Default stack size. */
18+#define ARCH_STACK_DEFAULT_SIZE (2 * 1024 * 1024)
19+
20+/* Required stack pointer alignment at beginning. */
21+#define STACK_ALIGN 16
22+
23+/* Minimal stack size after allocating thread descriptor and guard size. */
24+#define MINIMAL_REST_STACK 2048
25+
26+/* Alignment requirement for TCB. */
27+#define TCB_ALIGNMENT 16
28+
29+/* Location of current stack frame. */
30+#define CURRENT_STACK_FRAME __builtin_frame_address (0)
31+
32+
33+/* XXX Until we have a better place keep the definitions here. */
34+#define __exit_thread_inline(val) \
35+ INLINE_SYSCALL (exit, 1, (val))
36+
--- /dev/null
+++ b/libpthread/nptl/sysdeps/riscv64/tcb-offsets.sym
@@ -0,0 +1,6 @@
1+#include <sysdep.h>
2+#include <tls.h>
3+
4+MULTIPLE_THREADS_OFFSET offsetof (struct pthread, header.multiple_threads)
5+TID_OFFSET offsetof (struct pthread, tid)
6+TP_TO_PTHREAD_OFFSET -(sizeof (struct pthread) + sizeof (tcbhead_t))
--- /dev/null
+++ b/libpthread/nptl/sysdeps/riscv64/tls.h
@@ -0,0 +1,201 @@
1+/* Definition for thread-local data handling. NPTL/OR1K version.
2+ Copyright (C) 2005, 2007, 2011 Free Software Foundation, Inc.
3+ This file is part of the GNU C Library.
4+
5+ The GNU C Library is free software; you can redistribute it and/or
6+ modify it under the terms of the GNU Lesser General Public
7+ License as published by the Free Software Foundation; either
8+ version 2.1 of the License, or (at your option) any later version.
9+
10+ The GNU C Library is distributed in the hope that it will be useful,
11+ but WITHOUT ANY WARRANTY; without even the implied warranty of
12+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13+ Lesser General Public License for more details.
14+
15+ You should have received a copy of the GNU Lesser General Public
16+ License along with the GNU C Library. If not, see
17+ <http://www.gnu.org/licenses/>. */
18+
19+#ifndef _TLS_H
20+#define _TLS_H 1
21+
22+#ifndef __ASSEMBLER__
23+# include <stdbool.h>
24+# include <stddef.h>
25+# include <stdint.h>
26+
27+/* Type for the dtv. */
28+typedef union dtv
29+{
30+ size_t counter;
31+ struct
32+ {
33+ void *val;
34+ bool is_static;
35+ } pointer;
36+} dtv_t;
37+
38+typedef struct
39+{
40+ dtv_t *dtv;
41+} tcbhead_t;
42+
43+register tcbhead_t *__thread_self __asm__("tp");
44+
45+# define TLS_MULTIPLE_THREADS_IN_TCB 1
46+
47+#else /* __ASSEMBLER__ */
48+# include <tcb-offsets.h>
49+#endif /* __ASSEMBLER__ */
50+
51+/* We require TLS support in the tools. */
52+#define HAVE_TLS_SUPPORT 1
53+#define HAVE_TLS_MODEL_ATTRIBUTE 1
54+#define HAVE___THREAD 1
55+
56+/* Signal that TLS support is available. */
57+#define USE_TLS 1
58+
59+#ifndef __ASSEMBLER__
60+
61+/* Get system call information. */
62+# include <sysdep.h>
63+
64+/* The TP points to the start of the TLS block.
65+ * As I understand it, this isn't strictly that "TP points to DTV" - it's
66+ * more where to place the TCB in the TLS block. This will place it in
67+ * the beginning.
68+ *
69+ * Layout:
70+ * ------------------------------------
71+ * | PRE | TCB | TLS MEMORY .. |
72+ * ------------------------------------
73+ * ^ r10 / TP
74+ *
75+ * PRE is the struct pthread described below
76+ * TCB is tcbhead_t
77+ * TLS memory is where the TLS program sections are loaded
78+ *
79+ * See _dl_allocate_tls_storage and __libc_setup_tls for more information.
80+ */
81+# define TLS_DTV_AT_TP 1
82+
83+/* Get the thread descriptor definition. */
84+# include <../../descr.h>
85+
86+/* Requirements for the TCB. */
87+# define TLS_INIT_TCB_SIZE sizeof (tcbhead_t)
88+# define TLS_INIT_TCB_ALIGN __alignof__ (tcbhead_t)
89+
90+# define TLS_TCB_SIZE sizeof (tcbhead_t)
91+# define TLS_TCB_ALIGN __alignof__ (tcbhead_t)
92+
93+/* This is the size of the TCB. */
94+
95+/* This is the size we need before TCB.
96+ * To support THREAD_GETMEM with friends we want to have a
97+ * struct pthread available.
98+ * Yank it in infront of everything, I'm sure nobody will mind.
99+ *
100+ * This memory is really allocated PRE the TLS block, so it's possible
101+ * to do ((char*)tlsblock) - TLS_PRE_TCB_SIZE to access it.
102+ * This is done for THREAD_SELF. */
103+# define TLS_PRE_TCB_SIZE sizeof (struct pthread)
104+
105+
106+/* Install the dtv pointer.
107+ * When called, dtvp is a pointer not the DTV per say (which should start
108+ * with the generation counter) but to the length of the DTV.
109+ * We can always index with -1, so we store dtvp[1]
110+ */
111+# define INSTALL_DTV(tcbp, dtvp) \
112+ (((tcbhead_t *) (tcbp))->dtv = (dtvp) + 1)
113+
114+/* Install new dtv for current thread
115+ * In a logicial world dtv here would also point to the length of the DTV.
116+ * However it does not, this time it points to the generation counter,
117+ * so just store it.
118+ *
119+ * Note: -1 is still valid and contains the length. */
120+# define INSTALL_NEW_DTV(dtv) \
121+ (THREAD_DTV() = (dtv))
122+
123+/* Return dtv of given thread descriptor. */
124+# define GET_DTV(tcbp) \
125+ (((tcbhead_t *) (tcbp))->dtv)
126+
127+/* Code to initially initialize the thread pointer.
128+ *
129+ * Set TP to the address _after_ tcbhead_t. This will allow us
130+ * to change the size of tcbhead_t without having to re-link everything.
131+ *
132+ * secondcall has something to do with USE__THREAD,
133+ * seems to always be 0 so we don't care about it.
134+ *
135+ * This has to return NULL on success (or a string with the failure text).
136+ * It's hard to fail this, so return NULL always.
137+ */
138+# define TLS_INIT_TP(tcbp, secondcall) \
139+ ({__thread_self = ((tcbhead_t *)tcbp + 1); NULL;})
140+
141+/* Return the address of the dtv for the current thread.
142+ *
143+ * Dereference TP, offset to dtv - really straightforward.
144+ * Remember that we made TP point to after tcb, so we need to reverse that.
145+ */
146+# define THREAD_DTV() \
147+ ((((tcbhead_t *)__thread_self)-1)->dtv)
148+
149+/* Return the thread descriptor for the current thread.
150+ *
151+ * Return a pointer to the TLS_PRE area where we allocated space for
152+ * a struct pthread. Again, TP points to after tcbhead_t, compensate with
153+ * TLS_INIT_TCB_SIZE.
154+ *
155+ * I regard this is a seperate system from the "normal" TLS.
156+ */
157+# define THREAD_SELF \
158+ ((struct pthread *) ((char *) __thread_self - TLS_INIT_TCB_SIZE \
159+ - TLS_PRE_TCB_SIZE))
160+
161+/* Magic for libthread_db to know how to do THREAD_SELF. */
162+# define DB_THREAD_SELF \
163+ CONST_THREAD_AREA (32, sizeof (struct pthread))
164+
165+/* Access to data in the thread descriptor is easy. */
166+#define THREAD_GETMEM(descr, member) \
167+ descr->member
168+#define THREAD_GETMEM_NC(descr, member, idx) \
169+ descr->member[idx]
170+#define THREAD_SETMEM(descr, member, value) \
171+ descr->member = (value)
172+#define THREAD_SETMEM_NC(descr, member, idx, value) \
173+ descr->member[idx] = (value)
174+
175+/* Get and set the global scope generation counter in struct pthread. */
176+#define THREAD_GSCOPE_FLAG_UNUSED 0
177+#define THREAD_GSCOPE_FLAG_USED 1
178+#define THREAD_GSCOPE_FLAG_WAIT 2
179+#define THREAD_GSCOPE_RESET_FLAG() \
180+ do \
181+ { int __res \
182+ = atomic_exchange_rel (&THREAD_SELF->header.gscope_flag, \
183+ THREAD_GSCOPE_FLAG_UNUSED); \
184+ if (__res == THREAD_GSCOPE_FLAG_WAIT) \
185+ lll_futex_wake (&THREAD_SELF->header.gscope_flag, 1, LLL_PRIVATE); \
186+ } \
187+ while (0)
188+#define THREAD_GSCOPE_SET_FLAG() \
189+ do \
190+ { \
191+ THREAD_SELF->header.gscope_flag = THREAD_GSCOPE_FLAG_USED; \
192+ atomic_write_barrier (); \
193+ } \
194+ while (0)
195+#define THREAD_GSCOPE_WAIT() \
196+ GL(dl_wait_lookup_done) ()
197+
198+#endif /* __ASSEMBLER__ */
199+
200+#endif /* tls.h */
201+
--- a/libpthread/nptl/sysdeps/unix/sysv/linux/aarch64/bits/pthreadtypes.h
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/aarch64/bits/pthreadtypes.h
@@ -36,7 +36,6 @@
3636 exposed on purpose. */
3737 typedef unsigned long int pthread_t;
3838
39-
4039 union pthread_attr_t
4140 {
4241 char __size[__SIZEOF_PTHREAD_ATTR_T];
@@ -44,7 +43,7 @@ union pthread_attr_t
4443 };
4544 #ifndef __have_pthread_attr_t
4645 typedef union pthread_attr_t pthread_attr_t;
47-# define __have_pthread_attr_t1
46+# define __have_pthread_attr_t 1
4847 #endif
4948
5049 typedef struct __pthread_internal_list
@@ -75,9 +74,6 @@ typedef union
7574 long int __align;
7675 } pthread_mutex_t;
7776
78-/* Mutex __spins initializer used by PTHREAD_MUTEX_INITIALIZER. */
79-#define __PTHREAD_SPINS 0
80-
8177 typedef union
8278 {
8379 char __size[__SIZEOF_PTHREAD_MUTEXATTR_T];
@@ -141,8 +137,6 @@ typedef union
141137 long int __align;
142138 } pthread_rwlock_t;
143139
144-#define __PTHREAD_RWLOCK_ELISION_EXTRA 0
145-
146140 typedef union
147141 {
148142 char __size[__SIZEOF_PTHREAD_RWLOCKATTR_T];
--- /dev/null
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/riscv64/Makefile
@@ -0,0 +1,9 @@
1+# Makefile for uClibc-ng NPTL
2+# Licensed under the LGPL v2.1 or later, see the file COPYING.LIB in this tarball.
3+
4+top_srcdir=../../../../../../../
5+top_builddir=../../../../../../../
6+all: objs
7+include $(top_builddir)Rules.mak
8+include Makefile.arch
9+include $(top_srcdir)Makerules
--- /dev/null
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/riscv64/Makefile.arch
@@ -0,0 +1,9 @@
1+# Makefile for uClibc-ng NPTL
2+# Licensed under the LGPL v2.1 or later, see the file COPYING.LIB in this tarball.
3+
4+libpthread_linux_arch_SSRC =
5+libpthread_linux_arch_CSRC = pthread_once.c
6+
7+libc_linux_arch_CSRC = fork.c
8+
9+CFLAGS += $(SSP_ALL_CFLAGS)
--- /dev/null
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/riscv64/bits/pthreadtypes.h
@@ -0,0 +1,167 @@
1+/* Copyright (C) 2002,2003,2004,2005,2006,2007 Free Software Foundation, Inc.
2+
3+ The GNU C Library is free software; you can redistribute it and/or
4+ modify it under the terms of the GNU Lesser General Public
5+ License as published by the Free Software Foundation; either
6+ version 2.1 of the License, or (at your option) any later version.
7+
8+ The GNU C Library is distributed in the hope that it will be useful,
9+ but WITHOUT ANY WARRANTY; without even the implied warranty of
10+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11+ Lesser General Public License for more details.
12+
13+ You should have received a copy of the GNU Lesser General Public
14+ License along with the GNU C Library; if not, write to the Free
15+ Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
16+ 02111-1307 USA. */
17+
18+#ifndef _BITS_PTHREADTYPES_H
19+#define _BITS_PTHREADTYPES_H 1
20+
21+#define __SIZEOF_PTHREAD_ATTR_T 56
22+#define __SIZEOF_PTHREAD_MUTEX_T 40
23+#define __SIZEOF_PTHREAD_MUTEXATTR_T 4
24+#define __SIZEOF_PTHREAD_COND_T 48
25+#define __SIZEOF_PTHREAD_COND_COMPAT_T 12
26+#define __SIZEOF_PTHREAD_CONDATTR_T 4
27+#define __SIZEOF_PTHREAD_RWLOCK_T 56
28+#define __SIZEOF_PTHREAD_RWLOCKATTR_T 8
29+#define __SIZEOF_PTHREAD_BARRIER_T 32
30+#define __SIZEOF_PTHREAD_BARRIERATTR_T 4
31+
32+
33+/* Thread identifiers. The structure of the attribute type is not
34+ exposed on purpose. */
35+typedef unsigned long int pthread_t;
36+
37+union pthread_attr_t
38+{
39+ char __size[__SIZEOF_PTHREAD_ATTR_T];
40+ long int __align;
41+};
42+#ifndef __have_pthread_attr_t
43+typedef union pthread_attr_t pthread_attr_t;
44+# define __have_pthread_attr_t 1
45+#endif
46+
47+typedef struct __pthread_internal_list
48+{
49+ struct __pthread_internal_list *__prev;
50+ struct __pthread_internal_list *__next;
51+} __pthread_list_t;
52+
53+
54+/* Data structures for mutex handling. The structure of the attribute
55+ type is not exposed on purpose. */
56+typedef union
57+{
58+ struct __pthread_mutex_s
59+ {
60+ int __lock;
61+ unsigned int __count;
62+ int __owner;
63+ unsigned int __nusers;
64+ /* KIND must stay at this position in the structure to maintain
65+ binary compatibility with static initializers. */
66+ int __kind;
67+ int __spins;
68+ __pthread_list_t __list;
69+#define __PTHREAD_MUTEX_HAVE_PREV 1
70+ } __data;
71+ char __size[__SIZEOF_PTHREAD_MUTEX_T];
72+ long int __align;
73+} pthread_mutex_t;
74+
75+typedef union
76+{
77+ char __size[__SIZEOF_PTHREAD_MUTEXATTR_T];
78+ long int __align;
79+} pthread_mutexattr_t;
80+
81+
82+/* Data structure for conditional variable handling. The structure of
83+ the attribute type is not exposed on purpose. */
84+typedef union
85+{
86+ struct
87+ {
88+ int __lock;
89+ unsigned int __futex;
90+ __extension__ unsigned long long int __total_seq;
91+ __extension__ unsigned long long int __wakeup_seq;
92+ __extension__ unsigned long long int __woken_seq;
93+ void *__mutex;
94+ unsigned int __nwaiters;
95+ unsigned int __broadcast_seq;
96+ } __data;
97+ char __size[__SIZEOF_PTHREAD_COND_T];
98+ __extension__ long long int __align;
99+} pthread_cond_t;
100+
101+typedef union
102+{
103+ char __size[__SIZEOF_PTHREAD_CONDATTR_T];
104+ long int __align;
105+} pthread_condattr_t;
106+
107+
108+/* Keys for thread-specific data */
109+typedef unsigned int pthread_key_t;
110+
111+
112+/* Once-only execution */
113+typedef int pthread_once_t;
114+
115+
116+#if defined __USE_UNIX98 || defined __USE_XOPEN2K
117+/* Data structure for read-write lock variable handling. The
118+ structure of the attribute type is not exposed on purpose. */
119+typedef union
120+{
121+ struct
122+ {
123+ int __lock;
124+ unsigned int __nr_readers;
125+ unsigned int __readers_wakeup;
126+ unsigned int __writer_wakeup;
127+ unsigned int __nr_readers_queued;
128+ unsigned int __nr_writers_queued;
129+ int __writer;
130+ int __shared;
131+ unsigned long int __pad1;
132+ unsigned long int __pad2;
133+ unsigned int __flags;
134+ } __data;
135+ char __size[__SIZEOF_PTHREAD_RWLOCK_T];
136+ long int __align;
137+} pthread_rwlock_t;
138+
139+typedef union
140+{
141+ char __size[__SIZEOF_PTHREAD_RWLOCKATTR_T];
142+ long int __align;
143+} pthread_rwlockattr_t;
144+#endif
145+
146+
147+#ifdef __USE_XOPEN2K
148+/* POSIX spinlock data type. */
149+typedef volatile int pthread_spinlock_t;
150+
151+
152+/* POSIX barriers data type. The structure of the type is
153+ deliberately not exposed. */
154+typedef union
155+{
156+ char __size[__SIZEOF_PTHREAD_BARRIER_T];
157+ long int __align;
158+} pthread_barrier_t;
159+
160+typedef union
161+{
162+ char __size[__SIZEOF_PTHREAD_BARRIERATTR_T];
163+ int __align;
164+} pthread_barrierattr_t;
165+#endif
166+
167+#endif /* bits/pthreadtypes.h */
--- /dev/null
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/riscv64/bits/semaphore.h
@@ -0,0 +1,33 @@
1+/* Copyright (C) 2002, 2005, 2007 Free Software Foundation, Inc.
2+
3+ The GNU C Library is free software; you can redistribute it and/or
4+ modify it under the terms of the GNU Lesser General Public
5+ License as published by the Free Software Foundation; either
6+ version 2.1 of the License, or (at your option) any later version.
7+
8+ The GNU C Library is distributed in the hope that it will be useful,
9+ but WITHOUT ANY WARRANTY; without even the implied warranty of
10+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11+ Lesser General Public License for more details.
12+
13+ You should have received a copy of the GNU Lesser General Public
14+ License along with the GNU C Library. If not, see
15+ <http://www.gnu.org/licenses/>. */
16+
17+#ifndef _SEMAPHORE_H
18+# error "Never use <bits/semaphore.h> directly; include <semaphore.h> instead."
19+#endif
20+
21+
22+#define __SIZEOF_SEM_T (4 * __SIZEOF_POINTER__)
23+
24+
25+/* Value returned if `sem_open' failed. */
26+#define SEM_FAILED ((sem_t *) 0)
27+
28+
29+typedef union
30+{
31+ char __size[__SIZEOF_SEM_T];
32+ long int __align;
33+} sem_t;
--- /dev/null
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/riscv64/createthread.c
@@ -0,0 +1,22 @@
1+/* Copyright (C) 2012 Free Software Foundation, Inc.
2+
3+ The GNU C Library is free software; you can redistribute it and/or
4+ modify it under the terms of the GNU Lesser General Public
5+ License as published by the Free Software Foundation; either
6+ version 2.1 of the License, or (at your option) any later version.
7+
8+ The GNU C Library is distributed in the hope that it will be useful,
9+ but WITHOUT ANY WARRANTY; without even the implied warranty of
10+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11+ Lesser General Public License for more details.
12+
13+ You should have received a copy of the GNU Lesser General Public
14+ License along with the GNU C Library; see the file COPYING.LIB. If
15+ not, see <http://www.gnu.org/licenses/>.  */
16+
17+/* Value passed to 'clone' for initialization of the thread register. */
18+#define TLS_VALUE ((void *) (pd) \
19+ + TLS_PRE_TCB_SIZE + TLS_INIT_TCB_SIZE)
20+
21+/* Get the real implementation. */
22+#include <sysdeps/pthread/createthread.c>
--- /dev/null
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/riscv64/fork.c
@@ -0,0 +1,27 @@
1+/* Copyright (C) 2005 Free Software Foundation, Inc.
2+ Contributed by Phil Blundell <pb@nexus.co.uk>, 2005
3+
4+ The GNU C Library is free software; you can redistribute it and/or
5+ modify it under the terms of the GNU Lesser General Public
6+ License as published by the Free Software Foundation; either
7+ version 2.1 of the License, or (at your option) any later version.
8+
9+ The GNU C Library is distributed in the hope that it will be useful,
10+ but WITHOUT ANY WARRANTY; without even the implied warranty of
11+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12+ Lesser General Public License for more details.
13+
14+ You should have received a copy of the GNU Lesser General Public
15+ License along with the GNU C Library; if not, see
16+ <http://www.gnu.org/licenses/>. */
17+#include <sched.h>
18+#include <signal.h>
19+#include <sysdep.h>
20+#include <tls.h>
21+
22+#define ARCH_FORK() \
23+ INLINE_SYSCALL (clone, 5, \
24+ CLONE_CHILD_SETTID | CLONE_CHILD_CLEARTID | SIGCHLD, 0, \
25+ NULL, &THREAD_SELF->tid, NULL)
26+
27+#include "../fork.c"
--- /dev/null
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/riscv64/pthread_once.c
@@ -0,0 +1,92 @@
1+/* Copyright (C) 2003-2013 Free Software Foundation, Inc.
2+ Contributed by Jakub Jelinek <jakub@redhat.com>, 2003.
3+
4+ The GNU C Library is free software; you can redistribute it and/or
5+ modify it under the terms of the GNU Lesser General Public
6+ License as published by the Free Software Foundation; either
7+ version 2.1 of the License, or (at your option) any later version.
8+
9+ The GNU C Library is distributed in the hope that it will be useful,
10+ but WITHOUT ANY WARRANTY; without even the implied warranty of
11+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12+ Lesser General Public License for more details.
13+
14+ You should have received a copy of the GNU Lesser General Public
15+ License along with the GNU C Library; if not, see
16+ <http://www.gnu.org/licenses/>. */
17+
18+#include "pthreadP.h"
19+#include <lowlevellock.h>
20+
21+
22+unsigned long int __fork_generation attribute_hidden;
23+
24+
25+static void
26+clear_once_control (void *arg)
27+{
28+ pthread_once_t *once_control = (pthread_once_t *) arg;
29+
30+ *once_control = 0;
31+ lll_futex_wake (once_control, INT_MAX, LLL_PRIVATE);
32+}
33+
34+
35+int
36+__pthread_once (once_control, init_routine)
37+ pthread_once_t *once_control;
38+ void (*init_routine) (void);
39+{
40+ while (1)
41+ {
42+ int oldval, val, newval;
43+
44+ val = *once_control;
45+ do
46+ {
47+ /* Check if the initialized has already been done. */
48+ if ((val & 2) != 0)
49+ return 0;
50+
51+ oldval = val;
52+ newval = (oldval & 3) | __fork_generation | 1;
53+ val = atomic_compare_and_exchange_val_acq (once_control, newval,
54+ oldval);
55+ }
56+ while (__builtin_expect (val != oldval, 0));
57+
58+ /* Check if another thread already runs the initializer. */
59+ if ((oldval & 1) != 0)
60+ {
61+ /* Check whether the initializer execution was interrupted
62+ by a fork. */
63+ if (((oldval ^ newval) & -4) == 0)
64+ {
65+ /* Same generation, some other thread was faster. Wait. */
66+ lll_futex_wait (once_control, newval, LLL_PRIVATE);
67+ continue;
68+ }
69+ }
70+
71+ /* This thread is the first here. Do the initialization.
72+ Register a cleanup handler so that in case the thread gets
73+ interrupted the initialization can be restarted. */
74+ pthread_cleanup_push (clear_once_control, once_control);
75+
76+ init_routine ();
77+
78+ pthread_cleanup_pop (0);
79+
80+
81+ /* Add one to *once_control. */
82+ atomic_increment (once_control);
83+
84+ /* Wake up all other threads. */
85+ lll_futex_wake (once_control, INT_MAX, LLL_PRIVATE);
86+ break;
87+ }
88+
89+ return 0;
90+}
91+weak_alias (__pthread_once, pthread_once)
92+strong_alias (__pthread_once, __pthread_once_internal)
--- /dev/null
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/riscv64/sysdep-cancel.h
@@ -0,0 +1,38 @@
1+/* Copyright (C) 2014 Free Software Foundation, Inc.
2+
3+ The GNU C Library is free software; you can redistribute it and/or
4+ modify it under the terms of the GNU Lesser General Public
5+ License as published by the Free Software Foundation; either
6+ version 2.1 of the License, or (at your option) any later version.
7+
8+ The GNU C Library is distributed in the hope that it will be useful,
9+ but WITHOUT ANY WARRANTY; without even the implied warranty of
10+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11+ Lesser General Public License for more details.
12+
13+ You should have received a copy of the GNU Lesser General Public
14+ License along with the GNU C Library. If not, see
15+ <http://www.gnu.org/licenses/>. */
16+
17+#include <sysdep.h>
18+#include <tls.h>
19+#ifndef __ASSEMBLER__
20+# include <pthreadP.h>
21+#endif
22+
23+#if !defined NOT_IN_libc || defined IS_IN_libpthread || defined IS_IN_librt
24+
25+# define SINGLE_THREAD_P \
26+ __builtin_expect (THREAD_GETMEM (THREAD_SELF, \
27+ header.multiple_threads) == 0, 1)
28+
29+#else
30+
31+# define SINGLE_THREAD_P 1
32+# define NO_CANCELLATION 1
33+
34+#endif
35+
36+#define RTLD_SINGLE_THREAD_P \
37+ __builtin_expect (THREAD_GETMEM (THREAD_SELF, \
38+ header.multiple_threads) == 0, 1)