annotate libgomp/oacc-init.c @ 158:494b0b89df80 default tip

...
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Mon, 25 May 2020 18:13:55 +0900
parents 1830386684a0
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
111
kono
parents:
diff changeset
1 /* OpenACC Runtime initialization routines
kono
parents:
diff changeset
2
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
3 Copyright (C) 2013-2020 Free Software Foundation, Inc.
111
kono
parents:
diff changeset
4
kono
parents:
diff changeset
5 Contributed by Mentor Embedded.
kono
parents:
diff changeset
6
kono
parents:
diff changeset
7 This file is part of the GNU Offloading and Multi Processing Library
kono
parents:
diff changeset
8 (libgomp).
kono
parents:
diff changeset
9
kono
parents:
diff changeset
10 Libgomp is free software; you can redistribute it and/or modify it
kono
parents:
diff changeset
11 under the terms of the GNU General Public License as published by
kono
parents:
diff changeset
12 the Free Software Foundation; either version 3, or (at your option)
kono
parents:
diff changeset
13 any later version.
kono
parents:
diff changeset
14
kono
parents:
diff changeset
15 Libgomp is distributed in the hope that it will be useful, but WITHOUT ANY
kono
parents:
diff changeset
16 WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
kono
parents:
diff changeset
17 FOR A PARTICULAR PURPOSE. See the GNU General Public License for
kono
parents:
diff changeset
18 more details.
kono
parents:
diff changeset
19
kono
parents:
diff changeset
20 Under Section 7 of GPL version 3, you are granted additional
kono
parents:
diff changeset
21 permissions described in the GCC Runtime Library Exception, version
kono
parents:
diff changeset
22 3.1, as published by the Free Software Foundation.
kono
parents:
diff changeset
23
kono
parents:
diff changeset
24 You should have received a copy of the GNU General Public License and
kono
parents:
diff changeset
25 a copy of the GCC Runtime Library Exception along with this program;
kono
parents:
diff changeset
26 see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
kono
parents:
diff changeset
27 <http://www.gnu.org/licenses/>. */
kono
parents:
diff changeset
28
kono
parents:
diff changeset
29 #include "libgomp.h"
kono
parents:
diff changeset
30 #include "oacc-int.h"
kono
parents:
diff changeset
31 #include "openacc.h"
kono
parents:
diff changeset
32 #include <assert.h>
kono
parents:
diff changeset
33 #include <stdlib.h>
kono
parents:
diff changeset
34 #include <strings.h>
kono
parents:
diff changeset
35 #include <stdbool.h>
kono
parents:
diff changeset
36 #include <string.h>
kono
parents:
diff changeset
37
kono
parents:
diff changeset
38 /* This lock is used to protect access to cached_base_dev, dispatchers and
kono
parents:
diff changeset
39 the (abstract) initialisation state of attached offloading devices. */
kono
parents:
diff changeset
40
kono
parents:
diff changeset
41 static gomp_mutex_t acc_device_lock;
kono
parents:
diff changeset
42
kono
parents:
diff changeset
43 /* A cached version of the dispatcher for the global "current" accelerator type,
kono
parents:
diff changeset
44 e.g. used as the default when creating new host threads. This is the
kono
parents:
diff changeset
45 device-type equivalent of goacc_device_num (which specifies which device to
kono
parents:
diff changeset
46 use out of potentially several of the same type). If there are several
kono
parents:
diff changeset
47 devices of a given type, this points at the first one. */
kono
parents:
diff changeset
48
kono
parents:
diff changeset
49 static struct gomp_device_descr *cached_base_dev = NULL;
kono
parents:
diff changeset
50
kono
parents:
diff changeset
51 #if defined HAVE_TLS || defined USE_EMUTLS
kono
parents:
diff changeset
52 __thread struct goacc_thread *goacc_tls_data;
kono
parents:
diff changeset
53 #else
kono
parents:
diff changeset
54 pthread_key_t goacc_tls_key;
kono
parents:
diff changeset
55 #endif
kono
parents:
diff changeset
56 static pthread_key_t goacc_cleanup_key;
kono
parents:
diff changeset
57
kono
parents:
diff changeset
58 static struct goacc_thread *goacc_threads;
kono
parents:
diff changeset
59 static gomp_mutex_t goacc_thread_lock;
kono
parents:
diff changeset
60
kono
parents:
diff changeset
61 /* An array of dispatchers for device types, indexed by the type. This array
kono
parents:
diff changeset
62 only references "base" devices, and other instances of the same type are
kono
parents:
diff changeset
63 found by simply indexing from each such device (which are stored linearly,
kono
parents:
diff changeset
64 grouped by device in target.c:devices). */
kono
parents:
diff changeset
65 static struct gomp_device_descr *dispatchers[_ACC_device_hwm] = { 0 };
kono
parents:
diff changeset
66
kono
parents:
diff changeset
67 attribute_hidden void
kono
parents:
diff changeset
68 goacc_register (struct gomp_device_descr *disp)
kono
parents:
diff changeset
69 {
kono
parents:
diff changeset
70 /* Only register the 0th device here. */
kono
parents:
diff changeset
71 if (disp->target_id != 0)
kono
parents:
diff changeset
72 return;
kono
parents:
diff changeset
73
kono
parents:
diff changeset
74 gomp_mutex_lock (&acc_device_lock);
kono
parents:
diff changeset
75
kono
parents:
diff changeset
76 assert (acc_device_type (disp->type) != acc_device_none
kono
parents:
diff changeset
77 && acc_device_type (disp->type) != acc_device_default
kono
parents:
diff changeset
78 && acc_device_type (disp->type) != acc_device_not_host);
kono
parents:
diff changeset
79 assert (!dispatchers[disp->type]);
kono
parents:
diff changeset
80 dispatchers[disp->type] = disp;
kono
parents:
diff changeset
81
kono
parents:
diff changeset
82 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
83 }
kono
parents:
diff changeset
84
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
85 static bool
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
86 known_device_type_p (acc_device_t d)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
87 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
88 return d >= 0 && d < _ACC_device_hwm;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
89 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
90
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
91 static void
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
92 unknown_device_type_error (acc_device_t invalid_type)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
93 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
94 gomp_fatal ("unknown device type %u", invalid_type);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
95 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
96
111
kono
parents:
diff changeset
97 /* OpenACC names some things a little differently. */
kono
parents:
diff changeset
98
kono
parents:
diff changeset
99 static const char *
kono
parents:
diff changeset
100 get_openacc_name (const char *name)
kono
parents:
diff changeset
101 {
kono
parents:
diff changeset
102 if (strcmp (name, "nvptx") == 0)
kono
parents:
diff changeset
103 return "nvidia";
kono
parents:
diff changeset
104 else
kono
parents:
diff changeset
105 return name;
kono
parents:
diff changeset
106 }
kono
parents:
diff changeset
107
kono
parents:
diff changeset
108 static const char *
kono
parents:
diff changeset
109 name_of_acc_device_t (enum acc_device_t type)
kono
parents:
diff changeset
110 {
kono
parents:
diff changeset
111 switch (type)
kono
parents:
diff changeset
112 {
kono
parents:
diff changeset
113 case acc_device_none: return "none";
kono
parents:
diff changeset
114 case acc_device_default: return "default";
kono
parents:
diff changeset
115 case acc_device_host: return "host";
kono
parents:
diff changeset
116 case acc_device_not_host: return "not_host";
kono
parents:
diff changeset
117 case acc_device_nvidia: return "nvidia";
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
118 case acc_device_radeon: return "radeon";
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
119 default: unknown_device_type_error (type);
111
kono
parents:
diff changeset
120 }
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
121 __builtin_unreachable ();
111
kono
parents:
diff changeset
122 }
kono
parents:
diff changeset
123
kono
parents:
diff changeset
124 /* ACC_DEVICE_LOCK must be held before calling this function. If FAIL_IS_ERROR
kono
parents:
diff changeset
125 is true, this function raises an error if there are no devices of type D,
kono
parents:
diff changeset
126 otherwise it returns NULL in that case. */
kono
parents:
diff changeset
127
kono
parents:
diff changeset
128 static struct gomp_device_descr *
kono
parents:
diff changeset
129 resolve_device (acc_device_t d, bool fail_is_error)
kono
parents:
diff changeset
130 {
kono
parents:
diff changeset
131 acc_device_t d_arg = d;
kono
parents:
diff changeset
132
kono
parents:
diff changeset
133 switch (d)
kono
parents:
diff changeset
134 {
kono
parents:
diff changeset
135 case acc_device_default:
kono
parents:
diff changeset
136 {
kono
parents:
diff changeset
137 if (goacc_device_type)
kono
parents:
diff changeset
138 {
kono
parents:
diff changeset
139 /* Lookup the named device. */
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
140 while (known_device_type_p (++d))
111
kono
parents:
diff changeset
141 if (dispatchers[d]
kono
parents:
diff changeset
142 && !strcasecmp (goacc_device_type,
kono
parents:
diff changeset
143 get_openacc_name (dispatchers[d]->name))
kono
parents:
diff changeset
144 && dispatchers[d]->get_num_devices_func () > 0)
kono
parents:
diff changeset
145 goto found;
kono
parents:
diff changeset
146
kono
parents:
diff changeset
147 if (fail_is_error)
kono
parents:
diff changeset
148 {
kono
parents:
diff changeset
149 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
150 gomp_fatal ("device type %s not supported", goacc_device_type);
kono
parents:
diff changeset
151 }
kono
parents:
diff changeset
152 else
kono
parents:
diff changeset
153 return NULL;
kono
parents:
diff changeset
154 }
kono
parents:
diff changeset
155
kono
parents:
diff changeset
156 /* No default device specified, so start scanning for any non-host
kono
parents:
diff changeset
157 device that is available. */
kono
parents:
diff changeset
158 d = acc_device_not_host;
kono
parents:
diff changeset
159 }
kono
parents:
diff changeset
160 /* FALLTHROUGH */
kono
parents:
diff changeset
161
kono
parents:
diff changeset
162 case acc_device_not_host:
kono
parents:
diff changeset
163 /* Find the first available device after acc_device_not_host. */
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
164 while (known_device_type_p (++d))
111
kono
parents:
diff changeset
165 if (dispatchers[d] && dispatchers[d]->get_num_devices_func () > 0)
kono
parents:
diff changeset
166 goto found;
kono
parents:
diff changeset
167 if (d_arg == acc_device_default)
kono
parents:
diff changeset
168 {
kono
parents:
diff changeset
169 d = acc_device_host;
kono
parents:
diff changeset
170 goto found;
kono
parents:
diff changeset
171 }
kono
parents:
diff changeset
172 if (fail_is_error)
kono
parents:
diff changeset
173 {
kono
parents:
diff changeset
174 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
175 gomp_fatal ("no device found");
kono
parents:
diff changeset
176 }
kono
parents:
diff changeset
177 else
kono
parents:
diff changeset
178 return NULL;
kono
parents:
diff changeset
179 break;
kono
parents:
diff changeset
180
kono
parents:
diff changeset
181 case acc_device_host:
kono
parents:
diff changeset
182 break;
kono
parents:
diff changeset
183
kono
parents:
diff changeset
184 default:
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
185 if (!known_device_type_p (d))
111
kono
parents:
diff changeset
186 {
kono
parents:
diff changeset
187 if (fail_is_error)
kono
parents:
diff changeset
188 goto unsupported_device;
kono
parents:
diff changeset
189 else
kono
parents:
diff changeset
190 return NULL;
kono
parents:
diff changeset
191 }
kono
parents:
diff changeset
192 break;
kono
parents:
diff changeset
193 }
kono
parents:
diff changeset
194 found:
kono
parents:
diff changeset
195
kono
parents:
diff changeset
196 assert (d != acc_device_none
kono
parents:
diff changeset
197 && d != acc_device_default
kono
parents:
diff changeset
198 && d != acc_device_not_host);
kono
parents:
diff changeset
199
kono
parents:
diff changeset
200 if (dispatchers[d] == NULL && fail_is_error)
kono
parents:
diff changeset
201 {
kono
parents:
diff changeset
202 unsupported_device:
kono
parents:
diff changeset
203 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
204 gomp_fatal ("device type %s not supported", name_of_acc_device_t (d));
kono
parents:
diff changeset
205 }
kono
parents:
diff changeset
206
kono
parents:
diff changeset
207 return dispatchers[d];
kono
parents:
diff changeset
208 }
kono
parents:
diff changeset
209
kono
parents:
diff changeset
210 /* Emit a suitable error if no device of a particular type is available, or
kono
parents:
diff changeset
211 the given device number is out-of-range. */
kono
parents:
diff changeset
212 static void
kono
parents:
diff changeset
213 acc_dev_num_out_of_range (acc_device_t d, int ord, int ndevs)
kono
parents:
diff changeset
214 {
kono
parents:
diff changeset
215 if (ndevs == 0)
kono
parents:
diff changeset
216 gomp_fatal ("no devices of type %s available", name_of_acc_device_t (d));
kono
parents:
diff changeset
217 else
kono
parents:
diff changeset
218 gomp_fatal ("device %u out of range", ord);
kono
parents:
diff changeset
219 }
kono
parents:
diff changeset
220
kono
parents:
diff changeset
221 /* This is called when plugins have been initialized, and serves to call
kono
parents:
diff changeset
222 (indirectly) the target's device_init hook. Calling multiple times without
kono
parents:
diff changeset
223 an intervening acc_shutdown_1 call is an error. ACC_DEVICE_LOCK must be
kono
parents:
diff changeset
224 held before calling this function. */
kono
parents:
diff changeset
225
kono
parents:
diff changeset
226 static struct gomp_device_descr *
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
227 acc_init_1 (acc_device_t d, acc_construct_t parent_construct, int implicit)
111
kono
parents:
diff changeset
228 {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
229 bool check_not_nested_p;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
230 if (implicit)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
231 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
232 /* In the implicit case, there should (TODO: must?) already be something
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
233 have been set up for an outer construct. */
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
234 check_not_nested_p = false;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
235 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
236 else
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
237 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
238 check_not_nested_p = true;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
239 /* TODO: should we set 'thr->prof_info' etc. in this case ('acc_init')?
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
240 The problem is, that we don't have 'thr' yet? (So,
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
241 'check_not_nested_p = true' also is pointless actually.) */
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
242 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
243 bool profiling_p = GOACC_PROFILING_DISPATCH_P (check_not_nested_p);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
244
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
245 acc_prof_info prof_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
246 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
247 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
248 prof_info.event_type = acc_ev_device_init_start;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
249 prof_info.valid_bytes = _ACC_PROF_INFO_VALID_BYTES;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
250 prof_info.version = _ACC_PROF_INFO_VERSION;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
251 prof_info.device_type = d;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
252 prof_info.device_number = goacc_device_num;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
253 prof_info.thread_id = -1;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
254 prof_info.async = acc_async_sync;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
255 prof_info.async_queue = prof_info.async;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
256 prof_info.src_file = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
257 prof_info.func_name = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
258 prof_info.line_no = -1;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
259 prof_info.end_line_no = -1;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
260 prof_info.func_line_no = -1;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
261 prof_info.func_end_line_no = -1;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
262 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
263 acc_event_info device_init_event_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
264 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
265 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
266 device_init_event_info.other_event.event_type = prof_info.event_type;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
267 device_init_event_info.other_event.valid_bytes
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
268 = _ACC_OTHER_EVENT_INFO_VALID_BYTES;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
269 device_init_event_info.other_event.parent_construct = parent_construct;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
270 device_init_event_info.other_event.implicit = implicit;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
271 device_init_event_info.other_event.tool_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
272 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
273 acc_api_info api_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
274 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
275 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
276 api_info.device_api = acc_device_api_none;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
277 api_info.valid_bytes = _ACC_API_INFO_VALID_BYTES;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
278 api_info.device_type = prof_info.device_type;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
279 api_info.vendor = -1;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
280 api_info.device_handle = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
281 api_info.context_handle = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
282 api_info.async_handle = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
283 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
284
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
285 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
286 goacc_profiling_dispatch (&prof_info, &device_init_event_info, &api_info);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
287
111
kono
parents:
diff changeset
288 struct gomp_device_descr *base_dev, *acc_dev;
kono
parents:
diff changeset
289 int ndevs;
kono
parents:
diff changeset
290
kono
parents:
diff changeset
291 base_dev = resolve_device (d, true);
kono
parents:
diff changeset
292
kono
parents:
diff changeset
293 ndevs = base_dev->get_num_devices_func ();
kono
parents:
diff changeset
294
kono
parents:
diff changeset
295 if (ndevs <= 0 || goacc_device_num >= ndevs)
kono
parents:
diff changeset
296 acc_dev_num_out_of_range (d, goacc_device_num, ndevs);
kono
parents:
diff changeset
297
kono
parents:
diff changeset
298 acc_dev = &base_dev[goacc_device_num];
kono
parents:
diff changeset
299
kono
parents:
diff changeset
300 gomp_mutex_lock (&acc_dev->lock);
kono
parents:
diff changeset
301 if (acc_dev->state == GOMP_DEVICE_INITIALIZED)
kono
parents:
diff changeset
302 {
kono
parents:
diff changeset
303 gomp_mutex_unlock (&acc_dev->lock);
kono
parents:
diff changeset
304 gomp_fatal ("device already active");
kono
parents:
diff changeset
305 }
kono
parents:
diff changeset
306
kono
parents:
diff changeset
307 gomp_init_device (acc_dev);
kono
parents:
diff changeset
308 gomp_mutex_unlock (&acc_dev->lock);
kono
parents:
diff changeset
309
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
310 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
311 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
312 prof_info.event_type = acc_ev_device_init_end;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
313 device_init_event_info.other_event.event_type = prof_info.event_type;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
314 goacc_profiling_dispatch (&prof_info, &device_init_event_info,
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
315 &api_info);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
316 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
317
111
kono
parents:
diff changeset
318 return base_dev;
kono
parents:
diff changeset
319 }
kono
parents:
diff changeset
320
kono
parents:
diff changeset
321 /* ACC_DEVICE_LOCK must be held before calling this function. */
kono
parents:
diff changeset
322
kono
parents:
diff changeset
323 static void
kono
parents:
diff changeset
324 acc_shutdown_1 (acc_device_t d)
kono
parents:
diff changeset
325 {
kono
parents:
diff changeset
326 struct gomp_device_descr *base_dev;
kono
parents:
diff changeset
327 struct goacc_thread *walk;
kono
parents:
diff changeset
328 int ndevs, i;
kono
parents:
diff changeset
329 bool devices_active = false;
kono
parents:
diff changeset
330
kono
parents:
diff changeset
331 /* Get the base device for this device type. */
kono
parents:
diff changeset
332 base_dev = resolve_device (d, true);
kono
parents:
diff changeset
333
kono
parents:
diff changeset
334 ndevs = base_dev->get_num_devices_func ();
kono
parents:
diff changeset
335
kono
parents:
diff changeset
336 /* Unload all the devices of this type that have been opened. */
kono
parents:
diff changeset
337 for (i = 0; i < ndevs; i++)
kono
parents:
diff changeset
338 {
kono
parents:
diff changeset
339 struct gomp_device_descr *acc_dev = &base_dev[i];
kono
parents:
diff changeset
340
kono
parents:
diff changeset
341 gomp_mutex_lock (&acc_dev->lock);
kono
parents:
diff changeset
342 gomp_unload_device (acc_dev);
kono
parents:
diff changeset
343 gomp_mutex_unlock (&acc_dev->lock);
kono
parents:
diff changeset
344 }
kono
parents:
diff changeset
345
kono
parents:
diff changeset
346 gomp_mutex_lock (&goacc_thread_lock);
kono
parents:
diff changeset
347
kono
parents:
diff changeset
348 /* Free target-specific TLS data and close all devices. */
kono
parents:
diff changeset
349 for (walk = goacc_threads; walk != NULL; walk = walk->next)
kono
parents:
diff changeset
350 {
kono
parents:
diff changeset
351 if (walk->target_tls)
kono
parents:
diff changeset
352 base_dev->openacc.destroy_thread_data_func (walk->target_tls);
kono
parents:
diff changeset
353
kono
parents:
diff changeset
354 walk->target_tls = NULL;
kono
parents:
diff changeset
355
kono
parents:
diff changeset
356 /* This would mean the user is shutting down OpenACC in the middle of an
kono
parents:
diff changeset
357 "acc data" pragma. Likely not intentional. */
kono
parents:
diff changeset
358 if (walk->mapped_data)
kono
parents:
diff changeset
359 {
kono
parents:
diff changeset
360 gomp_mutex_unlock (&goacc_thread_lock);
kono
parents:
diff changeset
361 gomp_fatal ("shutdown in 'acc data' region");
kono
parents:
diff changeset
362 }
kono
parents:
diff changeset
363
kono
parents:
diff changeset
364 /* Similarly, if this happens then user code has done something weird. */
kono
parents:
diff changeset
365 if (walk->saved_bound_dev)
kono
parents:
diff changeset
366 {
kono
parents:
diff changeset
367 gomp_mutex_unlock (&goacc_thread_lock);
kono
parents:
diff changeset
368 gomp_fatal ("shutdown during host fallback");
kono
parents:
diff changeset
369 }
kono
parents:
diff changeset
370
kono
parents:
diff changeset
371 if (walk->dev)
kono
parents:
diff changeset
372 {
kono
parents:
diff changeset
373 gomp_mutex_lock (&walk->dev->lock);
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
374
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
375 while (walk->dev->mem_map.root)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
376 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
377 splay_tree_key k = &walk->dev->mem_map.root->key;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
378 if (k->aux)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
379 k->aux->link_key = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
380 gomp_remove_var (walk->dev, k);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
381 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
382
111
kono
parents:
diff changeset
383 gomp_mutex_unlock (&walk->dev->lock);
kono
parents:
diff changeset
384
kono
parents:
diff changeset
385 walk->dev = NULL;
kono
parents:
diff changeset
386 walk->base_dev = NULL;
kono
parents:
diff changeset
387 }
kono
parents:
diff changeset
388 }
kono
parents:
diff changeset
389
kono
parents:
diff changeset
390 gomp_mutex_unlock (&goacc_thread_lock);
kono
parents:
diff changeset
391
kono
parents:
diff changeset
392 /* Close all the devices of this type that have been opened. */
kono
parents:
diff changeset
393 bool ret = true;
kono
parents:
diff changeset
394 for (i = 0; i < ndevs; i++)
kono
parents:
diff changeset
395 {
kono
parents:
diff changeset
396 struct gomp_device_descr *acc_dev = &base_dev[i];
kono
parents:
diff changeset
397 gomp_mutex_lock (&acc_dev->lock);
kono
parents:
diff changeset
398 if (acc_dev->state == GOMP_DEVICE_INITIALIZED)
kono
parents:
diff changeset
399 {
kono
parents:
diff changeset
400 devices_active = true;
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
401 ret &= gomp_fini_device (acc_dev);
111
kono
parents:
diff changeset
402 acc_dev->state = GOMP_DEVICE_UNINITIALIZED;
kono
parents:
diff changeset
403 }
kono
parents:
diff changeset
404 gomp_mutex_unlock (&acc_dev->lock);
kono
parents:
diff changeset
405 }
kono
parents:
diff changeset
406
kono
parents:
diff changeset
407 if (!ret)
kono
parents:
diff changeset
408 gomp_fatal ("device finalization failed");
kono
parents:
diff changeset
409
kono
parents:
diff changeset
410 if (!devices_active)
kono
parents:
diff changeset
411 gomp_fatal ("no device initialized");
kono
parents:
diff changeset
412 }
kono
parents:
diff changeset
413
kono
parents:
diff changeset
414 static struct goacc_thread *
kono
parents:
diff changeset
415 goacc_new_thread (void)
kono
parents:
diff changeset
416 {
kono
parents:
diff changeset
417 struct goacc_thread *thr = gomp_malloc (sizeof (struct goacc_thread));
kono
parents:
diff changeset
418
kono
parents:
diff changeset
419 #if defined HAVE_TLS || defined USE_EMUTLS
kono
parents:
diff changeset
420 goacc_tls_data = thr;
kono
parents:
diff changeset
421 #else
kono
parents:
diff changeset
422 pthread_setspecific (goacc_tls_key, thr);
kono
parents:
diff changeset
423 #endif
kono
parents:
diff changeset
424
kono
parents:
diff changeset
425 pthread_setspecific (goacc_cleanup_key, thr);
kono
parents:
diff changeset
426
kono
parents:
diff changeset
427 gomp_mutex_lock (&goacc_thread_lock);
kono
parents:
diff changeset
428 thr->next = goacc_threads;
kono
parents:
diff changeset
429 goacc_threads = thr;
kono
parents:
diff changeset
430 gomp_mutex_unlock (&goacc_thread_lock);
kono
parents:
diff changeset
431
kono
parents:
diff changeset
432 return thr;
kono
parents:
diff changeset
433 }
kono
parents:
diff changeset
434
kono
parents:
diff changeset
435 static void
kono
parents:
diff changeset
436 goacc_destroy_thread (void *data)
kono
parents:
diff changeset
437 {
kono
parents:
diff changeset
438 struct goacc_thread *thr = data, *walk, *prev;
kono
parents:
diff changeset
439
kono
parents:
diff changeset
440 gomp_mutex_lock (&goacc_thread_lock);
kono
parents:
diff changeset
441
kono
parents:
diff changeset
442 if (thr)
kono
parents:
diff changeset
443 {
kono
parents:
diff changeset
444 struct gomp_device_descr *acc_dev = thr->dev;
kono
parents:
diff changeset
445
kono
parents:
diff changeset
446 if (acc_dev && thr->target_tls)
kono
parents:
diff changeset
447 {
kono
parents:
diff changeset
448 acc_dev->openacc.destroy_thread_data_func (thr->target_tls);
kono
parents:
diff changeset
449 thr->target_tls = NULL;
kono
parents:
diff changeset
450 }
kono
parents:
diff changeset
451
kono
parents:
diff changeset
452 assert (!thr->mapped_data);
kono
parents:
diff changeset
453
kono
parents:
diff changeset
454 /* Remove from thread list. */
kono
parents:
diff changeset
455 for (prev = NULL, walk = goacc_threads; walk;
kono
parents:
diff changeset
456 prev = walk, walk = walk->next)
kono
parents:
diff changeset
457 if (walk == thr)
kono
parents:
diff changeset
458 {
kono
parents:
diff changeset
459 if (prev == NULL)
kono
parents:
diff changeset
460 goacc_threads = walk->next;
kono
parents:
diff changeset
461 else
kono
parents:
diff changeset
462 prev->next = walk->next;
kono
parents:
diff changeset
463
kono
parents:
diff changeset
464 free (thr);
kono
parents:
diff changeset
465
kono
parents:
diff changeset
466 break;
kono
parents:
diff changeset
467 }
kono
parents:
diff changeset
468
kono
parents:
diff changeset
469 assert (walk);
kono
parents:
diff changeset
470 }
kono
parents:
diff changeset
471
kono
parents:
diff changeset
472 gomp_mutex_unlock (&goacc_thread_lock);
kono
parents:
diff changeset
473 }
kono
parents:
diff changeset
474
kono
parents:
diff changeset
475 /* Use the ORD'th device instance for the current host thread (or -1 for the
kono
parents:
diff changeset
476 current global default). The device (and the runtime) must be initialised
kono
parents:
diff changeset
477 before calling this function. */
kono
parents:
diff changeset
478
kono
parents:
diff changeset
479 void
kono
parents:
diff changeset
480 goacc_attach_host_thread_to_device (int ord)
kono
parents:
diff changeset
481 {
kono
parents:
diff changeset
482 struct goacc_thread *thr = goacc_thread ();
kono
parents:
diff changeset
483 struct gomp_device_descr *acc_dev = NULL, *base_dev = NULL;
kono
parents:
diff changeset
484 int num_devices;
kono
parents:
diff changeset
485
kono
parents:
diff changeset
486 if (thr && thr->dev && (thr->dev->target_id == ord || ord < 0))
kono
parents:
diff changeset
487 return;
kono
parents:
diff changeset
488
kono
parents:
diff changeset
489 if (ord < 0)
kono
parents:
diff changeset
490 ord = goacc_device_num;
kono
parents:
diff changeset
491
kono
parents:
diff changeset
492 /* Decide which type of device to use. If the current thread has a device
kono
parents:
diff changeset
493 type already (e.g. set by acc_set_device_type), use that, else use the
kono
parents:
diff changeset
494 global default. */
kono
parents:
diff changeset
495 if (thr && thr->base_dev)
kono
parents:
diff changeset
496 base_dev = thr->base_dev;
kono
parents:
diff changeset
497 else
kono
parents:
diff changeset
498 {
kono
parents:
diff changeset
499 assert (cached_base_dev);
kono
parents:
diff changeset
500 base_dev = cached_base_dev;
kono
parents:
diff changeset
501 }
kono
parents:
diff changeset
502
kono
parents:
diff changeset
503 num_devices = base_dev->get_num_devices_func ();
kono
parents:
diff changeset
504 if (num_devices <= 0 || ord >= num_devices)
kono
parents:
diff changeset
505 acc_dev_num_out_of_range (acc_device_type (base_dev->type), ord,
kono
parents:
diff changeset
506 num_devices);
kono
parents:
diff changeset
507
kono
parents:
diff changeset
508 if (!thr)
kono
parents:
diff changeset
509 thr = goacc_new_thread ();
kono
parents:
diff changeset
510
kono
parents:
diff changeset
511 thr->base_dev = base_dev;
kono
parents:
diff changeset
512 thr->dev = acc_dev = &base_dev[ord];
kono
parents:
diff changeset
513 thr->saved_bound_dev = NULL;
kono
parents:
diff changeset
514 thr->mapped_data = NULL;
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
515 thr->prof_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
516 thr->api_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
517 /* Initially, all callbacks for all events are enabled. */
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
518 thr->prof_callbacks_enabled = true;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
519
111
kono
parents:
diff changeset
520 thr->target_tls
kono
parents:
diff changeset
521 = acc_dev->openacc.create_thread_data_func (ord);
kono
parents:
diff changeset
522 }
kono
parents:
diff changeset
523
kono
parents:
diff changeset
524 /* OpenACC 2.0a (3.2.12, 3.2.13) doesn't specify whether the serialization of
kono
parents:
diff changeset
525 init/shutdown is per-process or per-thread. We choose per-process. */
kono
parents:
diff changeset
526
kono
parents:
diff changeset
527 void
kono
parents:
diff changeset
528 acc_init (acc_device_t d)
kono
parents:
diff changeset
529 {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
530 if (!known_device_type_p (d))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
531 unknown_device_type_error (d);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
532
111
kono
parents:
diff changeset
533 gomp_init_targets_once ();
kono
parents:
diff changeset
534
kono
parents:
diff changeset
535 gomp_mutex_lock (&acc_device_lock);
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
536 cached_base_dev = acc_init_1 (d, acc_construct_runtime_api, 0);
111
kono
parents:
diff changeset
537 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
538
kono
parents:
diff changeset
539 goacc_attach_host_thread_to_device (-1);
kono
parents:
diff changeset
540 }
kono
parents:
diff changeset
541
kono
parents:
diff changeset
542 ialias (acc_init)
kono
parents:
diff changeset
543
kono
parents:
diff changeset
544 void
kono
parents:
diff changeset
545 acc_shutdown (acc_device_t d)
kono
parents:
diff changeset
546 {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
547 if (!known_device_type_p (d))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
548 unknown_device_type_error (d);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
549
111
kono
parents:
diff changeset
550 gomp_init_targets_once ();
kono
parents:
diff changeset
551
kono
parents:
diff changeset
552 gomp_mutex_lock (&acc_device_lock);
kono
parents:
diff changeset
553
kono
parents:
diff changeset
554 acc_shutdown_1 (d);
kono
parents:
diff changeset
555
kono
parents:
diff changeset
556 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
557 }
kono
parents:
diff changeset
558
kono
parents:
diff changeset
559 ialias (acc_shutdown)
kono
parents:
diff changeset
560
kono
parents:
diff changeset
561 int
kono
parents:
diff changeset
562 acc_get_num_devices (acc_device_t d)
kono
parents:
diff changeset
563 {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
564 if (!known_device_type_p (d))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
565 unknown_device_type_error (d);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
566
111
kono
parents:
diff changeset
567 int n = 0;
kono
parents:
diff changeset
568 struct gomp_device_descr *acc_dev;
kono
parents:
diff changeset
569
kono
parents:
diff changeset
570 if (d == acc_device_none)
kono
parents:
diff changeset
571 return 0;
kono
parents:
diff changeset
572
kono
parents:
diff changeset
573 gomp_init_targets_once ();
kono
parents:
diff changeset
574
kono
parents:
diff changeset
575 gomp_mutex_lock (&acc_device_lock);
kono
parents:
diff changeset
576 acc_dev = resolve_device (d, false);
kono
parents:
diff changeset
577 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
578
kono
parents:
diff changeset
579 if (!acc_dev)
kono
parents:
diff changeset
580 return 0;
kono
parents:
diff changeset
581
kono
parents:
diff changeset
582 n = acc_dev->get_num_devices_func ();
kono
parents:
diff changeset
583 if (n < 0)
kono
parents:
diff changeset
584 n = 0;
kono
parents:
diff changeset
585
kono
parents:
diff changeset
586 return n;
kono
parents:
diff changeset
587 }
kono
parents:
diff changeset
588
kono
parents:
diff changeset
589 ialias (acc_get_num_devices)
kono
parents:
diff changeset
590
kono
parents:
diff changeset
591 /* Set the device type for the current thread only (using the current global
kono
parents:
diff changeset
592 default device number), initialising that device if necessary. Also set the
kono
parents:
diff changeset
593 default device type for new threads to D. */
kono
parents:
diff changeset
594
kono
parents:
diff changeset
595 void
kono
parents:
diff changeset
596 acc_set_device_type (acc_device_t d)
kono
parents:
diff changeset
597 {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
598 if (!known_device_type_p (d))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
599 unknown_device_type_error (d);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
600
111
kono
parents:
diff changeset
601 struct gomp_device_descr *base_dev, *acc_dev;
kono
parents:
diff changeset
602 struct goacc_thread *thr = goacc_thread ();
kono
parents:
diff changeset
603
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
604 acc_prof_info prof_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
605 acc_api_info api_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
606 bool profiling_p = GOACC_PROFILING_SETUP_P (thr, &prof_info, &api_info);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
607 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
608 prof_info.device_type = d;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
609
111
kono
parents:
diff changeset
610 gomp_init_targets_once ();
kono
parents:
diff changeset
611
kono
parents:
diff changeset
612 gomp_mutex_lock (&acc_device_lock);
kono
parents:
diff changeset
613
kono
parents:
diff changeset
614 cached_base_dev = base_dev = resolve_device (d, true);
kono
parents:
diff changeset
615 acc_dev = &base_dev[goacc_device_num];
kono
parents:
diff changeset
616
kono
parents:
diff changeset
617 gomp_mutex_lock (&acc_dev->lock);
kono
parents:
diff changeset
618 if (acc_dev->state == GOMP_DEVICE_UNINITIALIZED)
kono
parents:
diff changeset
619 gomp_init_device (acc_dev);
kono
parents:
diff changeset
620 gomp_mutex_unlock (&acc_dev->lock);
kono
parents:
diff changeset
621
kono
parents:
diff changeset
622 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
623
kono
parents:
diff changeset
624 /* We're changing device type: invalidate the current thread's dev and
kono
parents:
diff changeset
625 base_dev pointers. */
kono
parents:
diff changeset
626 if (thr && thr->base_dev != base_dev)
kono
parents:
diff changeset
627 {
kono
parents:
diff changeset
628 thr->base_dev = thr->dev = NULL;
kono
parents:
diff changeset
629 if (thr->mapped_data)
kono
parents:
diff changeset
630 gomp_fatal ("acc_set_device_type in 'acc data' region");
kono
parents:
diff changeset
631 }
kono
parents:
diff changeset
632
kono
parents:
diff changeset
633 goacc_attach_host_thread_to_device (-1);
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
634
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
635 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
636 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
637 thr->prof_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
638 thr->api_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
639 }
111
kono
parents:
diff changeset
640 }
kono
parents:
diff changeset
641
kono
parents:
diff changeset
642 ialias (acc_set_device_type)
kono
parents:
diff changeset
643
kono
parents:
diff changeset
644 acc_device_t
kono
parents:
diff changeset
645 acc_get_device_type (void)
kono
parents:
diff changeset
646 {
kono
parents:
diff changeset
647 acc_device_t res = acc_device_none;
kono
parents:
diff changeset
648 struct gomp_device_descr *dev;
kono
parents:
diff changeset
649 struct goacc_thread *thr = goacc_thread ();
kono
parents:
diff changeset
650
kono
parents:
diff changeset
651 if (thr && thr->base_dev)
kono
parents:
diff changeset
652 res = acc_device_type (thr->base_dev->type);
kono
parents:
diff changeset
653 else
kono
parents:
diff changeset
654 {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
655 acc_prof_info prof_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
656 acc_api_info api_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
657 bool profiling_p = GOACC_PROFILING_SETUP_P (thr, &prof_info, &api_info);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
658
111
kono
parents:
diff changeset
659 gomp_init_targets_once ();
kono
parents:
diff changeset
660
kono
parents:
diff changeset
661 gomp_mutex_lock (&acc_device_lock);
kono
parents:
diff changeset
662 dev = resolve_device (acc_device_default, true);
kono
parents:
diff changeset
663 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
664 res = acc_device_type (dev->type);
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
665
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
666 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
667 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
668 thr->prof_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
669 thr->api_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
670 }
111
kono
parents:
diff changeset
671 }
kono
parents:
diff changeset
672
kono
parents:
diff changeset
673 assert (res != acc_device_default
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
674 && res != acc_device_not_host
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
675 && res != acc_device_current);
111
kono
parents:
diff changeset
676
kono
parents:
diff changeset
677 return res;
kono
parents:
diff changeset
678 }
kono
parents:
diff changeset
679
kono
parents:
diff changeset
680 ialias (acc_get_device_type)
kono
parents:
diff changeset
681
kono
parents:
diff changeset
682 int
kono
parents:
diff changeset
683 acc_get_device_num (acc_device_t d)
kono
parents:
diff changeset
684 {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
685 if (!known_device_type_p (d))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
686 unknown_device_type_error (d);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
687
111
kono
parents:
diff changeset
688 const struct gomp_device_descr *dev;
kono
parents:
diff changeset
689 struct goacc_thread *thr = goacc_thread ();
kono
parents:
diff changeset
690
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
691 acc_prof_info prof_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
692 acc_api_info api_info;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
693 bool profiling_p = GOACC_PROFILING_SETUP_P (thr, &prof_info, &api_info);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
694 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
695 prof_info.device_type = d;
111
kono
parents:
diff changeset
696
kono
parents:
diff changeset
697 gomp_init_targets_once ();
kono
parents:
diff changeset
698
kono
parents:
diff changeset
699 gomp_mutex_lock (&acc_device_lock);
kono
parents:
diff changeset
700 dev = resolve_device (d, true);
kono
parents:
diff changeset
701 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
702
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
703 if (profiling_p)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
704 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
705 thr->prof_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
706 thr->api_info = NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
707 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
708
111
kono
parents:
diff changeset
709 if (thr && thr->base_dev == dev && thr->dev)
kono
parents:
diff changeset
710 return thr->dev->target_id;
kono
parents:
diff changeset
711
kono
parents:
diff changeset
712 return goacc_device_num;
kono
parents:
diff changeset
713 }
kono
parents:
diff changeset
714
kono
parents:
diff changeset
715 ialias (acc_get_device_num)
kono
parents:
diff changeset
716
kono
parents:
diff changeset
717 void
kono
parents:
diff changeset
718 acc_set_device_num (int ord, acc_device_t d)
kono
parents:
diff changeset
719 {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
720 if (!known_device_type_p (d))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
721 unknown_device_type_error (d);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
722
111
kono
parents:
diff changeset
723 struct gomp_device_descr *base_dev, *acc_dev;
kono
parents:
diff changeset
724 int num_devices;
kono
parents:
diff changeset
725
kono
parents:
diff changeset
726 gomp_init_targets_once ();
kono
parents:
diff changeset
727
kono
parents:
diff changeset
728 if (ord < 0)
kono
parents:
diff changeset
729 ord = goacc_device_num;
kono
parents:
diff changeset
730
kono
parents:
diff changeset
731 if ((int) d == 0)
kono
parents:
diff changeset
732 /* Set whatever device is being used by the current host thread to use
kono
parents:
diff changeset
733 device instance ORD. It's unclear if this is supposed to affect other
kono
parents:
diff changeset
734 host threads too (OpenACC 2.0 (3.2.4) acc_set_device_num). */
kono
parents:
diff changeset
735 goacc_attach_host_thread_to_device (ord);
kono
parents:
diff changeset
736 else
kono
parents:
diff changeset
737 {
kono
parents:
diff changeset
738 gomp_mutex_lock (&acc_device_lock);
kono
parents:
diff changeset
739
kono
parents:
diff changeset
740 cached_base_dev = base_dev = resolve_device (d, true);
kono
parents:
diff changeset
741
kono
parents:
diff changeset
742 num_devices = base_dev->get_num_devices_func ();
kono
parents:
diff changeset
743
kono
parents:
diff changeset
744 if (num_devices <= 0 || ord >= num_devices)
kono
parents:
diff changeset
745 acc_dev_num_out_of_range (d, ord, num_devices);
kono
parents:
diff changeset
746
kono
parents:
diff changeset
747 acc_dev = &base_dev[ord];
kono
parents:
diff changeset
748
kono
parents:
diff changeset
749 gomp_mutex_lock (&acc_dev->lock);
kono
parents:
diff changeset
750 if (acc_dev->state == GOMP_DEVICE_UNINITIALIZED)
kono
parents:
diff changeset
751 gomp_init_device (acc_dev);
kono
parents:
diff changeset
752 gomp_mutex_unlock (&acc_dev->lock);
kono
parents:
diff changeset
753
kono
parents:
diff changeset
754 gomp_mutex_unlock (&acc_device_lock);
kono
parents:
diff changeset
755
kono
parents:
diff changeset
756 goacc_attach_host_thread_to_device (ord);
kono
parents:
diff changeset
757 }
kono
parents:
diff changeset
758
kono
parents:
diff changeset
759 goacc_device_num = ord;
kono
parents:
diff changeset
760 }
kono
parents:
diff changeset
761
kono
parents:
diff changeset
762 ialias (acc_set_device_num)
kono
parents:
diff changeset
763
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
764 static union goacc_property_value
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
765 get_property_any (int ord, acc_device_t d, acc_device_property_t prop)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
766 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
767 goacc_lazy_initialize ();
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
768 struct goacc_thread *thr = goacc_thread ();
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
769
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
770 if (d == acc_device_current && thr && thr->dev)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
771 return thr->dev->openacc.get_property_func (thr->dev->target_id, prop);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
772
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
773 gomp_mutex_lock (&acc_device_lock);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
774
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
775 struct gomp_device_descr *dev = resolve_device (d, true);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
776
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
777 int num_devices = dev->get_num_devices_func ();
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
778
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
779 if (num_devices <= 0 || ord >= num_devices)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
780 acc_dev_num_out_of_range (d, ord, num_devices);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
781
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
782 dev += ord;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
783
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
784 gomp_mutex_lock (&dev->lock);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
785 if (dev->state == GOMP_DEVICE_UNINITIALIZED)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
786 gomp_init_device (dev);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
787 gomp_mutex_unlock (&dev->lock);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
788
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
789 gomp_mutex_unlock (&acc_device_lock);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
790
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
791 assert (dev);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
792
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
793 return dev->openacc.get_property_func (dev->target_id, prop);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
794 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
795
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
796 size_t
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
797 acc_get_property (int ord, acc_device_t d, acc_device_property_t prop)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
798 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
799 if (!known_device_type_p (d))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
800 unknown_device_type_error(d);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
801
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
802 if (prop & GOACC_PROPERTY_STRING_MASK)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
803 return 0;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
804 else
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
805 return get_property_any (ord, d, prop).val;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
806 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
807
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
808 ialias (acc_get_property)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
809
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
810 const char *
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
811 acc_get_property_string (int ord, acc_device_t d, acc_device_property_t prop)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
812 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
813 if (!known_device_type_p (d))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
814 unknown_device_type_error(d);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
815
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
816 if (prop & GOACC_PROPERTY_STRING_MASK)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
817 return get_property_any (ord, d, prop).ptr;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
818 else
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
819 return NULL;
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
820 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
821
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
822 ialias (acc_get_property_string)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
823
111
kono
parents:
diff changeset
824 /* For -O and higher, the compiler always attempts to expand acc_on_device, but
kono
parents:
diff changeset
825 if the user disables the builtin, or calls it via a pointer, we'll need this
kono
parents:
diff changeset
826 version.
kono
parents:
diff changeset
827
kono
parents:
diff changeset
828 Compile this with optimization, so that the compiler expands
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
829 this, rather than generating infinitely recursive code.
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
830
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
831 The function just forwards its argument to __builtin_acc_on_device. It does
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
832 not verify that the argument is a valid acc_device_t enumeration value. */
111
kono
parents:
diff changeset
833
kono
parents:
diff changeset
834 int __attribute__ ((__optimize__ ("O2")))
kono
parents:
diff changeset
835 acc_on_device (acc_device_t dev)
kono
parents:
diff changeset
836 {
kono
parents:
diff changeset
837 return __builtin_acc_on_device (dev);
kono
parents:
diff changeset
838 }
kono
parents:
diff changeset
839
kono
parents:
diff changeset
840 ialias (acc_on_device)
kono
parents:
diff changeset
841
kono
parents:
diff changeset
842 attribute_hidden void
kono
parents:
diff changeset
843 goacc_runtime_initialize (void)
kono
parents:
diff changeset
844 {
kono
parents:
diff changeset
845 gomp_mutex_init (&acc_device_lock);
kono
parents:
diff changeset
846
kono
parents:
diff changeset
847 #if !(defined HAVE_TLS || defined USE_EMUTLS)
kono
parents:
diff changeset
848 pthread_key_create (&goacc_tls_key, NULL);
kono
parents:
diff changeset
849 #endif
kono
parents:
diff changeset
850
kono
parents:
diff changeset
851 pthread_key_create (&goacc_cleanup_key, goacc_destroy_thread);
kono
parents:
diff changeset
852
kono
parents:
diff changeset
853 cached_base_dev = NULL;
kono
parents:
diff changeset
854
kono
parents:
diff changeset
855 goacc_threads = NULL;
kono
parents:
diff changeset
856 gomp_mutex_init (&goacc_thread_lock);
kono
parents:
diff changeset
857
kono
parents:
diff changeset
858 /* Initialize and register the 'host' device type. */
kono
parents:
diff changeset
859 goacc_host_init ();
kono
parents:
diff changeset
860 }
kono
parents:
diff changeset
861
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
862 static void __attribute__((destructor))
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
863 goacc_runtime_deinitialize (void)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
864 {
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
865 #if !(defined HAVE_TLS || defined USE_EMUTLS)
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
866 pthread_key_delete (goacc_tls_key);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
867 #endif
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
868 pthread_key_delete (goacc_cleanup_key);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
869 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
870
111
kono
parents:
diff changeset
871 /* Compiler helper functions */
kono
parents:
diff changeset
872
kono
parents:
diff changeset
873 attribute_hidden void
kono
parents:
diff changeset
874 goacc_save_and_set_bind (acc_device_t d)
kono
parents:
diff changeset
875 {
kono
parents:
diff changeset
876 struct goacc_thread *thr = goacc_thread ();
kono
parents:
diff changeset
877
kono
parents:
diff changeset
878 assert (!thr->saved_bound_dev);
kono
parents:
diff changeset
879
kono
parents:
diff changeset
880 thr->saved_bound_dev = thr->dev;
kono
parents:
diff changeset
881 thr->dev = dispatchers[d];
kono
parents:
diff changeset
882 }
kono
parents:
diff changeset
883
kono
parents:
diff changeset
884 attribute_hidden void
kono
parents:
diff changeset
885 goacc_restore_bind (void)
kono
parents:
diff changeset
886 {
kono
parents:
diff changeset
887 struct goacc_thread *thr = goacc_thread ();
kono
parents:
diff changeset
888
kono
parents:
diff changeset
889 thr->dev = thr->saved_bound_dev;
kono
parents:
diff changeset
890 thr->saved_bound_dev = NULL;
kono
parents:
diff changeset
891 }
kono
parents:
diff changeset
892
kono
parents:
diff changeset
893 /* This is called from any OpenACC support function that may need to implicitly
kono
parents:
diff changeset
894 initialize the libgomp runtime, either globally or from a new host thread.
kono
parents:
diff changeset
895 On exit "goacc_thread" will return a valid & populated thread block. */
kono
parents:
diff changeset
896
kono
parents:
diff changeset
897 attribute_hidden void
kono
parents:
diff changeset
898 goacc_lazy_initialize (void)
kono
parents:
diff changeset
899 {
kono
parents:
diff changeset
900 struct goacc_thread *thr = goacc_thread ();
kono
parents:
diff changeset
901
kono
parents:
diff changeset
902 if (thr && thr->dev)
kono
parents:
diff changeset
903 return;
kono
parents:
diff changeset
904
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
905 gomp_init_targets_once ();
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
906
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
907 gomp_mutex_lock (&acc_device_lock);
111
kono
parents:
diff changeset
908 if (!cached_base_dev)
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
909 cached_base_dev = acc_init_1 (acc_device_default,
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
910 acc_construct_parallel, 1);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
911 gomp_mutex_unlock (&acc_device_lock);
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
912
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
913 goacc_attach_host_thread_to_device (-1);
111
kono
parents:
diff changeset
914 }