Warning: This file is not a C or C++ file. It does not have highlighting.

1/* Definition for thread-local data handling. NPTL/s390 version.
2 Copyright (C) 2003-2022 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 <https://www.gnu.org/licenses/>. */
18
19#ifndef _TLS_H
20#define _TLS_H 1
21
22#include <dl-sysdep.h>
23#ifndef __ASSEMBLER__
24# include <stdbool.h>
25# include <stddef.h>
26# include <stdint.h>
27# include <stdlib.h>
28# include <list.h>
29# include <kernel-features.h>
30# include <dl-dtv.h>
31
32typedef struct
33{
34 void *tcb; /* Pointer to the TCB. Not necessary the
35 thread descriptor used by libpthread. */
36 dtv_t *dtv;
37 void *self; /* Pointer to the thread descriptor. */
38 int multiple_threads;
39 uintptr_t sysinfo;
40 uintptr_t stack_guard;
41 int gscope_flag;
42 int __glibc_reserved1;
43 /* GCC split stack support. */
44 void *__private_ss;
45} tcbhead_t;
46
47# ifndef __s390x__
48# define TLS_MULTIPLE_THREADS_IN_TCB 1
49# endif
50
51#else /* __ASSEMBLER__ */
52# include <tcb-offsets.h>
53#endif
54
55
56/* Alignment requirement for the stack. For IA-32 this is governed by
57 the SSE memory functions. */
58#define STACK_ALIGN 16
59
60#ifndef __ASSEMBLER__
61/* Get system call information. */
62# include <sysdep.h>
63
64/* This is the size of the initial TCB. Can't be just sizeof (tcbhead_t),
65 because NPTL getpid, __libc_alloca_cutoff etc. need (almost) the whole
66 struct pthread even when not linked with -lpthread. */
67# define TLS_INIT_TCB_SIZE sizeof (struct pthread)
68
69/* This is the size of the TCB. */
70# define TLS_TCB_SIZE sizeof (struct pthread)
71
72/* The TCB can have any size and the memory following the address the
73 thread pointer points to is unspecified. Allocate the TCB there. */
74# define TLS_TCB_AT_TP 1
75# define TLS_DTV_AT_TP 0
76
77/* Get the thread descriptor definition. */
78# include <nptl/descr.h>
79
80
81/* Install the dtv pointer. The pointer passed is to the element with
82 index -1 which contain the length. */
83# define INSTALL_DTV(descr, dtvp) \
84 ((tcbhead_t *) (descr))->dtv = (dtvp) + 1
85
86/* Install new dtv for current thread. */
87# define INSTALL_NEW_DTV(dtv) \
88 (((tcbhead_t *) __builtin_thread_pointer ())->dtv = (dtv))
89
90/* Return dtv of given thread descriptor. */
91# define GET_DTV(descr) \
92 (((tcbhead_t *) (descr))->dtv)
93
94#if defined NEED_DL_SYSINFO && defined SHARED
95# define INIT_SYSINFO \
96 _head->sysinfo = GLRO(dl_sysinfo)
97#else
98# define INIT_SYSINFO
99#endif
100
101/* Code to initially initialize the thread pointer. This might need
102 special attention since 'errno' is not yet available and if the
103 operation can cause a failure 'errno' must not be touched. */
104# define TLS_INIT_TP(thrdescr) \
105 ({ void *_thrdescr = (thrdescr); \
106 tcbhead_t *_head = _thrdescr; \
107 \
108 _head->tcb = _thrdescr; \
109 /* For now the thread descriptor is at the same address. */ \
110 _head->self = _thrdescr; \
111 /* New syscall handling support. */ \
112 INIT_SYSINFO; \
113 \
114 __builtin_set_thread_pointer (_thrdescr); \
115 NULL; \
116 })
117
118/* Value passed to 'clone' for initialization of the thread register. */
119# define TLS_DEFINE_INIT_TP(tp, pd) void *tp = (pd)
120
121/* Return the address of the dtv for the current thread. */
122# define THREAD_DTV() \
123 (((tcbhead_t *) __builtin_thread_pointer ())->dtv)
124
125/* Return the thread descriptor for the current thread. */
126# define THREAD_SELF ((struct pthread *) __builtin_thread_pointer ())
127
128/* Magic for libthread_db to know how to do THREAD_SELF. */
129# define DB_THREAD_SELF REGISTER (32, 32, 18 * 4, 0) \
130 REGISTER (64, __WORDSIZE, 18 * 8, 0)
131
132# include <tcb-access.h>
133
134/* Set the stack guard field in TCB head. */
135#define THREAD_SET_STACK_GUARD(value) \
136 do \
137 { \
138 __asm__ __volatile__ ("" : : : "a0", "a1"); \
139 THREAD_SETMEM (THREAD_SELF, header.stack_guard, value); \
140 } \
141 while (0)
142#define THREAD_COPY_STACK_GUARD(descr) \
143 ((descr)->header.stack_guard \
144 = THREAD_GETMEM (THREAD_SELF, header.stack_guard))
145
146/* s390 doesn't have HP_TIMING_*, so for the time being
147 use stack_guard as pointer_guard. */
148#define THREAD_GET_POINTER_GUARD() \
149 THREAD_GETMEM (THREAD_SELF, header.stack_guard)
150#define THREAD_SET_POINTER_GUARD(value) ((void) (value))
151#define THREAD_COPY_POINTER_GUARD(descr)
152
153/* Get and set the global scope generation counter in struct pthread. */
154#define THREAD_GSCOPE_FLAG_UNUSED 0
155#define THREAD_GSCOPE_FLAG_USED 1
156#define THREAD_GSCOPE_FLAG_WAIT 2
157#define THREAD_GSCOPE_RESET_FLAG() \
158 do \
159 { int __res \
160 = atomic_exchange_rel (&THREAD_SELF->header.gscope_flag, \
161 THREAD_GSCOPE_FLAG_UNUSED); \
162 if (__res == THREAD_GSCOPE_FLAG_WAIT) \
163 lll_futex_wake (&THREAD_SELF->header.gscope_flag, 1, LLL_PRIVATE); \
164 } \
165 while (0)
166#define THREAD_GSCOPE_SET_FLAG() \
167 do \
168 { \
169 THREAD_SELF->header.gscope_flag = THREAD_GSCOPE_FLAG_USED; \
170 atomic_write_barrier (); \
171 } \
172 while (0)
173
174#endif /* __ASSEMBLER__ */
175
176#endif /* tls.h */
177

Warning: This file is not a C or C++ file. It does not have highlighting.

source code of glibc/sysdeps/s390/nptl/tls.h