Line data Source code
1 : /* Perform the semantic phase of parsing, i.e., the process of
2 : building tree structure, checking semantic consistency, and
3 : building RTL. These routines are used both during actual parsing
4 : and during the instantiation of template functions.
5 :
6 : Copyright (C) 1998-2026 Free Software Foundation, Inc.
7 : Written by Mark Mitchell (mmitchell@usa.net) based on code found
8 : formerly in parse.y and pt.cc.
9 :
10 : This file is part of GCC.
11 :
12 : GCC is free software; you can redistribute it and/or modify it
13 : under the terms of the GNU General Public License as published by
14 : the Free Software Foundation; either version 3, or (at your option)
15 : any later version.
16 :
17 : GCC is distributed in the hope that it will be useful, but
18 : WITHOUT ANY WARRANTY; without even the implied warranty of
19 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
20 : General Public License for more details.
21 :
22 : You should have received a copy of the GNU General Public License
23 : along with GCC; see the file COPYING3. If not see
24 : <http://www.gnu.org/licenses/>. */
25 :
26 : #include "config.h"
27 : #include "system.h"
28 : #include "coretypes.h"
29 : #include "target.h"
30 : #include "bitmap.h"
31 : #include "cp-tree.h"
32 : #include "stringpool.h"
33 : #include "cgraph.h"
34 : #include "stmt.h"
35 : #include "varasm.h"
36 : #include "stor-layout.h"
37 : #include "c-family/c-objc.h"
38 : #include "tree-inline.h"
39 : #include "intl.h"
40 : #include "tree-iterator.h"
41 : #include "omp-general.h"
42 : #include "convert.h"
43 : #include "attribs.h"
44 : #include "gomp-constants.h"
45 : #include "predict.h"
46 : #include "memmodel.h"
47 : #include "gimplify.h"
48 : #include "contracts.h"
49 : #include "c-family/c-pragma.h"
50 :
51 : /* There routines provide a modular interface to perform many parsing
52 : operations. They may therefore be used during actual parsing, or
53 : during template instantiation, which may be regarded as a
54 : degenerate form of parsing. */
55 :
56 : static tree finalize_nrv_r (tree *, int *, void *);
57 :
58 : /* Used for OpenMP non-static data member privatization. */
59 :
60 : static hash_map<tree, tree> *omp_private_member_map;
61 : static vec<tree> omp_private_member_vec;
62 : static bool omp_private_member_ignore_next;
63 :
64 :
65 : /* Deferred Access Checking Overview
66 : ---------------------------------
67 :
68 : Most C++ expressions and declarations require access checking
69 : to be performed during parsing. However, in several cases,
70 : this has to be treated differently.
71 :
72 : For member declarations, access checking has to be deferred
73 : until more information about the declaration is known. For
74 : example:
75 :
76 : class A {
77 : typedef int X;
78 : public:
79 : X f();
80 : };
81 :
82 : A::X A::f();
83 : A::X g();
84 :
85 : When we are parsing the function return type `A::X', we don't
86 : really know if this is allowed until we parse the function name.
87 :
88 : Furthermore, some contexts require that access checking is
89 : never performed at all. These include class heads, and template
90 : instantiations.
91 :
92 : Typical use of access checking functions is described here:
93 :
94 : 1. When we enter a context that requires certain access checking
95 : mode, the function `push_deferring_access_checks' is called with
96 : DEFERRING argument specifying the desired mode. Access checking
97 : may be performed immediately (dk_no_deferred), deferred
98 : (dk_deferred), or not performed (dk_no_check).
99 :
100 : 2. When a declaration such as a type, or a variable, is encountered,
101 : the function `perform_or_defer_access_check' is called. It
102 : maintains a vector of all deferred checks.
103 :
104 : 3. The global `current_class_type' or `current_function_decl' is then
105 : setup by the parser. `enforce_access' relies on these information
106 : to check access.
107 :
108 : 4. Upon exiting the context mentioned in step 1,
109 : `perform_deferred_access_checks' is called to check all declaration
110 : stored in the vector. `pop_deferring_access_checks' is then
111 : called to restore the previous access checking mode.
112 :
113 : In case of parsing error, we simply call `pop_deferring_access_checks'
114 : without `perform_deferred_access_checks'. */
115 :
116 : struct GTY(()) deferred_access {
117 : /* A vector representing name-lookups for which we have deferred
118 : checking access controls. We cannot check the accessibility of
119 : names used in a decl-specifier-seq until we know what is being
120 : declared because code like:
121 :
122 : class A {
123 : class B {};
124 : B* f();
125 : }
126 :
127 : A::B* A::f() { return 0; }
128 :
129 : is valid, even though `A::B' is not generally accessible. */
130 : vec<deferred_access_check, va_gc> *deferred_access_checks;
131 :
132 : /* The current mode of access checks. */
133 : enum deferring_kind deferring_access_checks_kind;
134 : };
135 :
136 : /* Data for deferred access checking. */
137 : static GTY(()) vec<deferred_access, va_gc> *deferred_access_stack;
138 : static GTY(()) unsigned deferred_access_no_check;
139 :
140 : /* Save the current deferred access states and start deferred
141 : access checking iff DEFER_P is true. */
142 :
143 : void
144 24633284817 : push_deferring_access_checks (deferring_kind deferring)
145 : {
146 : /* For context like template instantiation, access checking
147 : disabling applies to all nested context. */
148 24633284817 : if (deferred_access_no_check || deferring == dk_no_check)
149 317608306 : deferred_access_no_check++;
150 : else
151 : {
152 24315676511 : deferred_access e = {NULL, deferring};
153 24315676511 : vec_safe_push (deferred_access_stack, e);
154 : }
155 24633284817 : }
156 :
157 : /* Save the current deferred access states and start deferred access
158 : checking, continuing the set of deferred checks in CHECKS. */
159 :
160 : void
161 395804173 : reopen_deferring_access_checks (vec<deferred_access_check, va_gc> * checks)
162 : {
163 395804173 : push_deferring_access_checks (dk_deferred);
164 395804173 : if (!deferred_access_no_check)
165 387903558 : deferred_access_stack->last().deferred_access_checks = checks;
166 395804173 : }
167 :
168 : /* Resume deferring access checks again after we stopped doing
169 : this previously. */
170 :
171 : void
172 187870800 : resume_deferring_access_checks (void)
173 : {
174 187870800 : if (!deferred_access_no_check)
175 187844073 : deferred_access_stack->last().deferring_access_checks_kind = dk_deferred;
176 187870800 : }
177 :
178 : /* Stop deferring access checks. */
179 :
180 : void
181 526841321 : stop_deferring_access_checks (void)
182 : {
183 526841321 : if (!deferred_access_no_check)
184 526763701 : deferred_access_stack->last().deferring_access_checks_kind = dk_no_deferred;
185 526841321 : }
186 :
187 : /* Discard the current deferred access checks and restore the
188 : previous states. */
189 :
190 : void
191 15273756871 : pop_deferring_access_checks (void)
192 : {
193 15273756871 : if (deferred_access_no_check)
194 243342500 : deferred_access_no_check--;
195 : else
196 15030414371 : deferred_access_stack->pop ();
197 15273756871 : }
198 :
199 : /* Returns a TREE_LIST representing the deferred checks.
200 : The TREE_PURPOSE of each node is the type through which the
201 : access occurred; the TREE_VALUE is the declaration named.
202 : */
203 :
204 : vec<deferred_access_check, va_gc> *
205 1318310010 : get_deferred_access_checks (void)
206 : {
207 1318310010 : if (deferred_access_no_check)
208 : return NULL;
209 : else
210 1302028441 : return (deferred_access_stack->last().deferred_access_checks);
211 : }
212 :
213 : /* Take current deferred checks and combine with the
214 : previous states if we also defer checks previously.
215 : Otherwise perform checks now. */
216 :
217 : void
218 9359389849 : pop_to_parent_deferring_access_checks (void)
219 : {
220 9359389849 : if (deferred_access_no_check)
221 74265798 : deferred_access_no_check--;
222 : else
223 : {
224 9285124051 : vec<deferred_access_check, va_gc> *checks;
225 9285124051 : deferred_access *ptr;
226 :
227 9285124051 : checks = (deferred_access_stack->last ().deferred_access_checks);
228 :
229 9285124051 : deferred_access_stack->pop ();
230 9285124051 : ptr = &deferred_access_stack->last ();
231 9285124051 : if (ptr->deferring_access_checks_kind == dk_no_deferred)
232 : {
233 : /* Check access. */
234 585598214 : perform_access_checks (checks, tf_warning_or_error);
235 : }
236 : else
237 : {
238 : /* Merge with parent. */
239 : int i, j;
240 : deferred_access_check *chk, *probe;
241 :
242 8907282695 : FOR_EACH_VEC_SAFE_ELT (checks, i, chk)
243 : {
244 112896455 : FOR_EACH_VEC_SAFE_ELT (ptr->deferred_access_checks, j, probe)
245 : {
246 10021007 : if (probe->binfo == chk->binfo &&
247 7921530 : probe->decl == chk->decl &&
248 1003921 : probe->diag_decl == chk->diag_decl)
249 1002981 : goto found;
250 : }
251 : /* Insert into parent's checks. */
252 102875448 : vec_safe_push (ptr->deferred_access_checks, *chk);
253 103878429 : found:;
254 : }
255 : }
256 : }
257 9359389849 : }
258 :
259 : /* Called from enforce_access. A class has attempted (but failed) to access
260 : DECL. It is already established that a baseclass of that class,
261 : PARENT_BINFO, has private access to DECL. Examine certain special cases
262 : to find a decl that accurately describes the source of the problem. If
263 : none of the special cases apply, simply return DECL as the source of the
264 : problem. */
265 :
266 : static tree
267 182 : get_class_access_diagnostic_decl (tree parent_binfo, tree decl)
268 : {
269 : /* When a class is denied access to a decl in a baseclass, most of the
270 : time it is because the decl itself was declared as private at the point
271 : of declaration.
272 :
273 : However, in C++, there are (at least) two situations in which a decl
274 : can be private even though it was not originally defined as such.
275 : These two situations only apply if a baseclass had private access to
276 : DECL (this function is only called if that is the case). */
277 :
278 : /* We should first check whether the reason the parent had private access
279 : to DECL was simply because DECL was created and declared as private in
280 : the parent. If it was, then DECL is definitively the source of the
281 : problem. */
282 182 : if (SAME_BINFO_TYPE_P (context_for_name_lookup (decl),
283 : BINFO_TYPE (parent_binfo)))
284 : return decl;
285 :
286 : /* 1. If the "using" keyword is used to inherit DECL within the parent,
287 : this may cause DECL to be private, so we should return the using
288 : statement as the source of the problem.
289 :
290 : Scan the fields of PARENT_BINFO and see if there are any using decls. If
291 : there are, see if they inherit DECL. If they do, that's where DECL must
292 : have been declared private. */
293 :
294 66 : for (tree parent_field = TYPE_FIELDS (BINFO_TYPE (parent_binfo));
295 326 : parent_field;
296 260 : parent_field = DECL_CHAIN (parent_field))
297 : /* Not necessary, but also check TREE_PRIVATE for the sake of
298 : eliminating obviously non-relevant using decls. */
299 278 : if (TREE_CODE (parent_field) == USING_DECL
300 81 : && TREE_PRIVATE (parent_field))
301 : {
302 78 : tree decl_stripped = strip_using_decl (parent_field);
303 :
304 : /* The using statement might be overloaded. If so, we need to
305 : check all of the overloads. */
306 180 : for (ovl_iterator iter (decl_stripped); iter; ++iter)
307 : /* If equal, the using statement inherits DECL, and so is the
308 : source of the access failure, so return it. */
309 99 : if (*iter == decl)
310 18 : return parent_field;
311 : }
312 :
313 : /* 2. If DECL was privately inherited by the parent class, then DECL will
314 : be inaccessible, even though it may originally have been accessible to
315 : deriving classes. In that case, the fault lies with the parent, since it
316 : used a private inheritance, so we return the parent as the source of the
317 : problem.
318 :
319 : Since this is the last check, we just assume it's true. At worst, it
320 : will simply point to the class that failed to give access, which is
321 : technically true. */
322 48 : return TYPE_NAME (BINFO_TYPE (parent_binfo));
323 : }
324 :
325 : /* If the current scope isn't allowed to access DECL along
326 : BASETYPE_PATH, give an error, or if we're parsing a function or class
327 : template, defer the access check to be performed at instantiation time.
328 : The most derived class in BASETYPE_PATH is the one used to qualify DECL.
329 : DIAG_DECL is the declaration to use in the error diagnostic. */
330 :
331 : static bool
332 428294097 : enforce_access (tree basetype_path, tree decl, tree diag_decl,
333 : tsubst_flags_t complain, access_failure_info *afi = NULL)
334 : {
335 428294097 : gcc_assert (TREE_CODE (basetype_path) == TREE_BINFO);
336 :
337 428294097 : if (flag_new_inheriting_ctors
338 541215470 : && DECL_INHERITED_CTOR (decl))
339 : {
340 : /* 7.3.3/18: The additional constructors are accessible if they would be
341 : accessible when used to construct an object of the corresponding base
342 : class. */
343 63420 : decl = strip_inheriting_ctors (decl);
344 63420 : basetype_path = lookup_base (basetype_path, DECL_CONTEXT (decl),
345 : ba_any, NULL, complain);
346 : }
347 :
348 428294097 : tree cs = current_scope ();
349 428294097 : if (in_template_context
350 428294097 : && (CLASS_TYPE_P (cs) || TREE_CODE (cs) == FUNCTION_DECL))
351 42700534 : if (tree template_info = get_template_info (cs))
352 : {
353 : /* When parsing a function or class template, we in general need to
354 : defer access checks until template instantiation time, since a friend
355 : declaration may grant access only to a particular specialization of
356 : the template. */
357 :
358 42451933 : if (accessible_p (basetype_path, decl, /*consider_local_p=*/true))
359 : /* But if the member is deemed accessible at parse time, then we can
360 : assume it'll be accessible at instantiation time. */
361 : return true;
362 :
363 : /* Access of a dependent decl should be rechecked after tsubst'ing
364 : into the user of the decl, rather than explicitly deferring the
365 : check here. */
366 135 : gcc_assert (!uses_template_parms (decl));
367 135 : if (TREE_CODE (decl) == FIELD_DECL)
368 6 : gcc_assert (!uses_template_parms (DECL_CONTEXT (decl)));
369 :
370 : /* Defer this access check until instantiation time. */
371 135 : deferred_access_check access_check;
372 135 : access_check.binfo = basetype_path;
373 135 : access_check.decl = decl;
374 135 : access_check.diag_decl = diag_decl;
375 135 : access_check.loc = input_location;
376 135 : vec_safe_push (TI_DEFERRED_ACCESS_CHECKS (template_info), access_check);
377 135 : return true;
378 : }
379 :
380 385842164 : if (!accessible_p (basetype_path, decl, /*consider_local_p=*/true))
381 : {
382 22515 : if (flag_new_inheriting_ctors)
383 22485 : diag_decl = strip_inheriting_ctors (diag_decl);
384 22515 : if (complain & tf_error)
385 : {
386 1159 : access_kind access_failure_reason = ak_none;
387 :
388 : /* By default, using the decl as the source of the problem will
389 : usually give correct results. */
390 1159 : tree diag_location = diag_decl;
391 :
392 : /* However, if a parent of BASETYPE_PATH had private access to decl,
393 : then it actually might be the case that the source of the problem
394 : is not DECL. */
395 1159 : tree parent_binfo = get_parent_with_private_access (decl,
396 : basetype_path);
397 :
398 : /* So if a parent did have private access, then we need to do
399 : special checks to obtain the best diagnostic location decl. */
400 1159 : if (parent_binfo != NULL_TREE)
401 : {
402 182 : diag_location = get_class_access_diagnostic_decl (parent_binfo,
403 : diag_decl);
404 :
405 : /* We also at this point know that the reason access failed was
406 : because decl was private. */
407 182 : access_failure_reason = ak_private;
408 : }
409 :
410 : /* Finally, generate an error message. */
411 1159 : complain_about_access (decl, diag_decl, diag_location, true,
412 : access_failure_reason);
413 : }
414 22515 : if (afi)
415 412 : afi->record_access_failure (basetype_path, decl, diag_decl);
416 : return false;
417 : }
418 :
419 : return true;
420 : }
421 :
422 : /* Perform the access checks in CHECKS. The TREE_PURPOSE of each node
423 : is the BINFO indicating the qualifying scope used to access the
424 : DECL node stored in the TREE_VALUE of the node. If CHECKS is empty
425 : or we aren't in SFINAE context or all the checks succeed return TRUE,
426 : otherwise FALSE. */
427 :
428 : bool
429 1122316243 : perform_access_checks (vec<deferred_access_check, va_gc> *checks,
430 : tsubst_flags_t complain)
431 : {
432 1122316243 : int i;
433 1122316243 : deferred_access_check *chk;
434 1122316243 : location_t loc = input_location;
435 1122316243 : bool ok = true;
436 :
437 1122316243 : if (!checks)
438 : return true;
439 :
440 130326620 : FOR_EACH_VEC_SAFE_ELT (checks, i, chk)
441 : {
442 72541630 : input_location = chk->loc;
443 72541630 : ok &= enforce_access (chk->binfo, chk->decl, chk->diag_decl, complain);
444 : }
445 :
446 57784990 : input_location = loc;
447 57784990 : return (complain & tf_error) ? true : ok;
448 : }
449 :
450 : /* Perform the deferred access checks.
451 :
452 : After performing the checks, we still have to keep the list
453 : `deferred_access_stack->deferred_access_checks' since we may want
454 : to check access for them again later in a different context.
455 : For example:
456 :
457 : class A {
458 : typedef int X;
459 : static X a;
460 : };
461 : A::X A::a, x; // No error for `A::a', error for `x'
462 :
463 : We have to perform deferred access of `A::X', first with `A::a',
464 : next with `x'. Return value like perform_access_checks above. */
465 :
466 : bool
467 293216407 : perform_deferred_access_checks (tsubst_flags_t complain)
468 : {
469 293216407 : return perform_access_checks (get_deferred_access_checks (), complain);
470 : }
471 :
472 : /* Defer checking the accessibility of DECL, when looked up in
473 : BINFO. DIAG_DECL is the declaration to use to print diagnostics.
474 : Return value like perform_access_checks above.
475 : If non-NULL, report failures to AFI. */
476 :
477 : bool
478 643398192 : perform_or_defer_access_check (tree binfo, tree decl, tree diag_decl,
479 : tsubst_flags_t complain,
480 : access_failure_info *afi)
481 : {
482 643398192 : int i;
483 643398192 : deferred_access *ptr;
484 643398192 : deferred_access_check *chk;
485 :
486 : /* Exit if we are in a context that no access checking is performed. */
487 643398192 : if (deferred_access_no_check)
488 : return true;
489 :
490 612376539 : gcc_assert (TREE_CODE (binfo) == TREE_BINFO);
491 :
492 612376539 : ptr = &deferred_access_stack->last ();
493 :
494 : /* If we are not supposed to defer access checks, just check now. */
495 612376539 : if (ptr->deferring_access_checks_kind == dk_no_deferred)
496 : {
497 355752467 : bool ok = enforce_access (binfo, decl, diag_decl, complain, afi);
498 355752467 : return (complain & tf_error) ? true : ok;
499 : }
500 :
501 : /* See if we are already going to perform this check. */
502 312161043 : FOR_EACH_VEC_SAFE_ELT (ptr->deferred_access_checks, i, chk)
503 : {
504 72906664 : if (chk->decl == decl && chk->binfo == binfo &&
505 17370774 : chk->diag_decl == diag_decl)
506 : {
507 : return true;
508 : }
509 : }
510 : /* If not, record the check. */
511 239254379 : deferred_access_check new_access = {binfo, decl, diag_decl, input_location};
512 239254379 : vec_safe_push (ptr->deferred_access_checks, new_access);
513 :
514 239254379 : return true;
515 : }
516 :
517 : /* Returns nonzero if the current statement is a full expression,
518 : i.e. temporaries created during that statement should be destroyed
519 : at the end of the statement. */
520 :
521 : int
522 1432901296 : stmts_are_full_exprs_p (void)
523 : {
524 1432901296 : return current_stmt_tree ()->stmts_are_full_exprs_p;
525 : }
526 :
527 : /* T is a statement. Add it to the statement-tree. This is the C++
528 : version. The C/ObjC frontends have a slightly different version of
529 : this function. */
530 :
531 : tree
532 1333065888 : add_stmt (tree t)
533 : {
534 1333065888 : enum tree_code code = TREE_CODE (t);
535 :
536 1333065888 : if (EXPR_P (t) && code != LABEL_EXPR)
537 : {
538 1281862399 : if (!EXPR_HAS_LOCATION (t))
539 205047001 : SET_EXPR_LOCATION (t, input_location);
540 :
541 : /* When we expand a statement-tree, we must know whether or not the
542 : statements are full-expressions. We record that fact here. */
543 1281862399 : if (STATEMENT_CODE_P (TREE_CODE (t)))
544 333663255 : STMT_IS_FULL_EXPR_P (t) = stmts_are_full_exprs_p ();
545 : }
546 :
547 1333065888 : if (code == LABEL_EXPR || code == CASE_LABEL_EXPR)
548 6061041 : STATEMENT_LIST_HAS_LABEL (cur_stmt_list) = 1;
549 :
550 : /* Add T to the statement-tree. Non-side-effect statements need to be
551 : recorded during statement expressions. */
552 1333065888 : gcc_checking_assert (!stmt_list_stack->is_empty ());
553 1333065888 : append_to_statement_list_force (t, &cur_stmt_list);
554 :
555 1333065888 : return t;
556 : }
557 :
558 : /* Returns the stmt_tree to which statements are currently being added. */
559 :
560 : stmt_tree
561 7784470744 : current_stmt_tree (void)
562 : {
563 7784470744 : return (cfun
564 7760391347 : ? &cfun->language->base.x_stmt_tree
565 7784470744 : : &scope_chain->x_stmt_tree);
566 : }
567 :
568 : /* If statements are full expressions, wrap STMT in a CLEANUP_POINT_EXPR. */
569 :
570 : static tree
571 332328 : maybe_cleanup_point_expr (tree expr)
572 : {
573 332328 : if (!processing_template_decl && stmts_are_full_exprs_p ())
574 318913 : expr = fold_build_cleanup_point_expr (TREE_TYPE (expr), expr);
575 332328 : return expr;
576 : }
577 :
578 : /* Like maybe_cleanup_point_expr except have the type of the new expression be
579 : void so we don't need to create a temporary variable to hold the inner
580 : expression. The reason why we do this is because the original type might be
581 : an aggregate and we cannot create a temporary variable for that type. */
582 :
583 : tree
584 330395070 : maybe_cleanup_point_expr_void (tree expr)
585 : {
586 330395070 : if (!processing_template_decl && stmts_are_full_exprs_p ())
587 110625618 : expr = fold_build_cleanup_point_expr (void_type_node, expr);
588 330395070 : return expr;
589 : }
590 :
591 :
592 :
593 : /* Create a declaration statement for the declaration given by the DECL. */
594 :
595 : void
596 111615925 : add_decl_expr (tree decl)
597 : {
598 111615925 : tree r = build_stmt (DECL_SOURCE_LOCATION (decl), DECL_EXPR, decl);
599 111615925 : if (DECL_INITIAL (decl)
600 111615925 : || (DECL_SIZE (decl) && TREE_SIDE_EFFECTS (DECL_SIZE (decl))))
601 19816487 : r = maybe_cleanup_point_expr_void (r);
602 111615925 : add_stmt (r);
603 111615925 : }
604 :
605 : /* Set EXPR_LOCATION on one cleanup T to LOC. */
606 :
607 : static void
608 5944840 : set_one_cleanup_loc (tree t, location_t loc)
609 : {
610 5944840 : if (!t)
611 : return;
612 :
613 5944840 : if (TREE_CODE (t) != POSTCONDITION_STMT)
614 5944840 : protected_set_expr_location (t, loc);
615 :
616 : /* Avoid locus differences for C++ cdtor calls depending on whether
617 : cdtor_returns_this: a conversion to void is added to discard the return
618 : value, and this conversion ends up carrying the location, and when it
619 : gets discarded, the location is lost. So hold it in the call as well. */
620 5944840 : if (TREE_CODE (t) == NOP_EXPR
621 0 : && TREE_TYPE (t) == void_type_node
622 5944840 : && TREE_CODE (TREE_OPERAND (t, 0)) == CALL_EXPR)
623 0 : protected_set_expr_location (TREE_OPERAND (t, 0), loc);
624 : }
625 :
626 : /* Set EXPR_LOCATION of the cleanups of any CLEANUP_STMT in STMTS to LOC. */
627 :
628 : static void
629 1258410602 : set_cleanup_locs (tree stmts, location_t loc)
630 : {
631 1264355442 : if (TREE_CODE (stmts) == CLEANUP_STMT)
632 : {
633 5944840 : set_one_cleanup_loc (CLEANUP_EXPR (stmts), loc);
634 5944840 : set_cleanup_locs (CLEANUP_BODY (stmts), loc);
635 : }
636 1258410602 : else if (TREE_CODE (stmts) == STATEMENT_LIST)
637 1118823898 : for (tree stmt : tsi_range (stmts))
638 866507668 : set_cleanup_locs (stmt, loc);
639 1258410602 : }
640 :
641 : /* True iff the innermost block scope is a try block. */
642 :
643 : static bool
644 391902934 : at_try_scope ()
645 : {
646 391902934 : cp_binding_level *b = current_binding_level;
647 391903383 : while (b && b->kind == sk_cleanup)
648 449 : b = b->level_chain;
649 391902934 : return b && b->kind == sk_try;
650 : }
651 :
652 : /* Finish a scope. */
653 :
654 : tree
655 391902934 : do_poplevel (tree stmt_list)
656 : {
657 391902934 : tree block = NULL;
658 :
659 391902934 : bool was_try = at_try_scope ();
660 :
661 391902934 : if (stmts_are_full_exprs_p ())
662 391839918 : block = poplevel (kept_level_p (), 1, 0);
663 :
664 : /* This needs to come after poplevel merges sk_cleanup statement_lists. */
665 391902934 : maybe_splice_retval_cleanup (stmt_list, was_try);
666 :
667 391902934 : stmt_list = pop_stmt_list (stmt_list);
668 :
669 : /* input_location is the last token of the scope, usually a }. */
670 391902934 : set_cleanup_locs (stmt_list, input_location);
671 :
672 391902934 : if (!processing_template_decl)
673 : {
674 120148587 : stmt_list = c_build_bind_expr (input_location, block, stmt_list);
675 : /* ??? See c_end_compound_stmt re statement expressions. */
676 : }
677 :
678 391902934 : return stmt_list;
679 : }
680 :
681 : /* Begin a new scope. */
682 :
683 : tree
684 391864958 : do_pushlevel (scope_kind sk)
685 : {
686 391864958 : tree ret = push_stmt_list ();
687 391864958 : if (stmts_are_full_exprs_p ())
688 391839972 : begin_scope (sk, NULL);
689 391864958 : return ret;
690 : }
691 :
692 : /* Queue a cleanup. CLEANUP is an expression/statement to be executed
693 : when the current scope is exited. EH_ONLY is true when this is not
694 : meant to apply to normal control flow transfer. DECL is the VAR_DECL
695 : being cleaned up, if any, or null for temporaries or subobjects. */
696 :
697 : void
698 5944769 : push_cleanup (tree decl, tree cleanup, bool eh_only)
699 : {
700 5944769 : tree stmt = build_stmt (input_location, CLEANUP_STMT, NULL, cleanup, decl);
701 5944769 : CLEANUP_EH_ONLY (stmt) = eh_only;
702 5944769 : add_stmt (stmt);
703 5944769 : CLEANUP_BODY (stmt) = push_stmt_list ();
704 5944769 : }
705 :
706 : /* Simple infinite loop tracking for -Wreturn-type. We keep a stack of all
707 : the current loops, represented by 'NULL_TREE' if we've seen a possible
708 : exit, and 'error_mark_node' if not. This is currently used only to
709 : suppress the warning about a function with no return statements, and
710 : therefore we don't bother noting returns as possible exits. We also
711 : don't bother with gotos. */
712 :
713 : static void
714 18749789 : begin_maybe_infinite_loop (tree cond)
715 : {
716 : /* Only track this while parsing a function, not during instantiation. */
717 18749789 : if (!cfun || (DECL_TEMPLATE_INSTANTIATION (current_function_decl)
718 2741526 : && !processing_template_decl))
719 : return;
720 16007765 : bool maybe_infinite = true;
721 16007765 : if (cond)
722 : {
723 15694283 : cond = fold_non_dependent_expr (cond);
724 15694283 : maybe_infinite = integer_nonzerop (cond);
725 : }
726 31702048 : vec_safe_push (cp_function_chain->infinite_loops,
727 16007765 : maybe_infinite ? error_mark_node : NULL_TREE);
728 :
729 : }
730 :
731 : /* A break is a possible exit for the current loop. */
732 :
733 : void
734 1576154 : break_maybe_infinite_loop (void)
735 : {
736 1576154 : if (!cfun)
737 : return;
738 1576154 : cp_function_chain->infinite_loops->last() = NULL_TREE;
739 : }
740 :
741 : /* If we reach the end of the loop without seeing a possible exit, we have
742 : an infinite loop. */
743 :
744 : static void
745 18749789 : end_maybe_infinite_loop (tree cond)
746 : {
747 18749789 : if (!cfun || (DECL_TEMPLATE_INSTANTIATION (current_function_decl)
748 2741526 : && !processing_template_decl))
749 : return;
750 16007765 : tree current = cp_function_chain->infinite_loops->pop();
751 16007765 : if (current != NULL_TREE)
752 : {
753 5190094 : cond = fold_non_dependent_expr (cond);
754 5190094 : if (integer_nonzerop (cond))
755 337254 : current_function_infinite_loop = 1;
756 : }
757 : }
758 :
759 : /* Begin a conditional that might contain a declaration. When generating
760 : normal code, we want the declaration to appear before the statement
761 : containing the conditional. When generating template code, we want the
762 : conditional to be rendered as the raw DECL_EXPR. */
763 :
764 : static void
765 90636443 : begin_cond (tree *cond_p)
766 : {
767 90636443 : if (processing_template_decl)
768 64358536 : *cond_p = push_stmt_list ();
769 90636443 : }
770 :
771 : /* Finish such a conditional. */
772 :
773 : static void
774 90636443 : finish_cond (tree *cond_p, tree expr)
775 : {
776 90636443 : if (processing_template_decl)
777 : {
778 64358536 : tree cond = pop_stmt_list (*cond_p);
779 :
780 64358536 : if (expr == NULL_TREE)
781 : /* Empty condition in 'for'. */
782 292613 : gcc_assert (empty_expr_stmt_p (cond));
783 64065923 : else if (check_for_bare_parameter_packs (expr))
784 0 : expr = error_mark_node;
785 64065923 : else if (!empty_expr_stmt_p (cond))
786 992228 : expr = build2 (COMPOUND_EXPR, TREE_TYPE (expr), cond, expr);
787 : }
788 90636443 : *cond_p = expr;
789 90636443 : }
790 :
791 : /* If loop condition specifies a conditional with a declaration,
792 : such as
793 : while (A x = 42) { }
794 : for (; A x = 42;) { }
795 : move the *BODY_P statements as a BIND_EXPR into {FOR,WHILE}_COND_PREP
796 : and if there are any CLEANUP_STMT at the end, remember their count in
797 : {FOR,WHILE}_COND_CLEANUP.
798 : genericize_c_loop will then handle it appropriately. In particular,
799 : the {FOR,WHILE}_COND, {FOR,WHILE}_BODY, if used continue label and
800 : FOR_EXPR will be appended into the {FOR,WHILE}_COND_PREP BIND_EXPR,
801 : but it can't be done too early because only the actual body should
802 : bind BREAK_STMT and CONTINUE_STMT to the inner loop.
803 : The statement list for *BODY will be empty if the conditional did
804 : not declare anything. */
805 :
806 : static void
807 12630714 : adjust_loop_decl_cond (tree *body_p, tree *prep_p, tree *cleanup_p)
808 : {
809 12630714 : if (!TREE_SIDE_EFFECTS (*body_p))
810 12620911 : return;
811 :
812 9803 : gcc_assert (!processing_template_decl);
813 9803 : *prep_p = *body_p;
814 9803 : if (*prep_p != cur_stmt_list)
815 : {
816 : /* There can be just one CLEANUP_STMT, or there could be multiple
817 : nested CLEANUP_STMTs, e.g. for structured bindings used as
818 : condition. */
819 97 : gcc_assert (stmt_list_stack->length () > 1);
820 97 : for (unsigned i = stmt_list_stack->length () - 2; ; --i)
821 : {
822 109 : tree t = (*stmt_list_stack)[i];
823 109 : tree_stmt_iterator last = tsi_last (t);
824 218 : gcc_assert (tsi_one_before_end_p (last)
825 : && TREE_CODE (tsi_stmt (last)) == CLEANUP_STMT
826 : && (CLEANUP_BODY (tsi_stmt (last))
827 : == (*stmt_list_stack)[i + 1])
828 : && !CLEANUP_EH_ONLY (tsi_stmt (last)));
829 109 : if (t == *prep_p)
830 : {
831 97 : *cleanup_p = build_int_cst (long_unsigned_type_node,
832 97 : stmt_list_stack->length () - 1 - i);
833 97 : break;
834 : }
835 12 : gcc_assert (i >= 1);
836 12 : }
837 : }
838 9803 : current_binding_level->keep = true;
839 9803 : tree_stmt_iterator iter = tsi_last (cur_stmt_list);
840 : /* Temporarily store in {FOR,WHILE}_BODY the last statement of
841 : the innnermost statement list or NULL if it has no statement.
842 : This is used in finish_loop_cond_prep to find out the splitting
843 : point and then {FOR,WHILE}_BODY will be changed to the actual
844 : body. */
845 9803 : if (tsi_end_p (iter))
846 : *body_p = NULL_TREE;
847 : else
848 9712 : *body_p = tsi_stmt (iter);
849 : }
850 :
851 : /* Finalize {FOR,WHILE}_{BODY,COND_PREP} after the loop body.
852 : The above function initialized *BODY_P to the last statement
853 : in *PREP_P at that point.
854 : Call do_poplevel on *PREP_P and move everything after that
855 : former last statement into *BODY_P. genericize_c_loop
856 : will later put those parts back together.
857 : CLEANUP is {FOR,WHILE}_COND_CLEANUP. */
858 :
859 : static void
860 9803 : finish_loop_cond_prep (tree *body_p, tree *prep_p, tree cleanup)
861 : {
862 9803 : *prep_p = do_poplevel (*prep_p);
863 9803 : gcc_assert (TREE_CODE (*prep_p) == BIND_EXPR);
864 9803 : if (BIND_EXPR_BODY (*prep_p) == *body_p)
865 : {
866 18 : gcc_assert (cleanup == NULL_TREE);
867 18 : *body_p = build_empty_stmt (input_location);
868 109 : return;
869 : }
870 9785 : tree stmt_list = BIND_EXPR_BODY (*prep_p);
871 9785 : gcc_assert (TREE_CODE (stmt_list) == STATEMENT_LIST);
872 9785 : if (cleanup)
873 : {
874 97 : tree_stmt_iterator iter = tsi_last (stmt_list);
875 97 : gcc_assert (TREE_CODE (tsi_stmt (iter)) == CLEANUP_STMT);
876 109 : for (unsigned depth = tree_to_uhwi (cleanup); depth > 1; --depth)
877 : {
878 12 : gcc_assert (TREE_CODE (CLEANUP_BODY (tsi_stmt (iter)))
879 : == STATEMENT_LIST);
880 12 : iter = tsi_last (CLEANUP_BODY (tsi_stmt (iter)));
881 12 : gcc_assert (TREE_CODE (tsi_stmt (iter)) == CLEANUP_STMT);
882 : }
883 97 : if (*body_p == NULL_TREE)
884 : {
885 91 : *body_p = CLEANUP_BODY (tsi_stmt (iter));
886 91 : CLEANUP_BODY (tsi_stmt (iter)) = build_empty_stmt (input_location);
887 91 : return;
888 : }
889 6 : stmt_list = CLEANUP_BODY (tsi_stmt (iter));
890 : }
891 9694 : tree_stmt_iterator iter = tsi_start (stmt_list);
892 9926 : while (tsi_stmt (iter) != *body_p)
893 232 : tsi_next (&iter);
894 9694 : *body_p = tsi_split_stmt_list (input_location, iter);
895 : }
896 :
897 : /* Finish a goto-statement. */
898 :
899 : tree
900 2764 : finish_goto_stmt (tree destination)
901 : {
902 2764 : if (identifier_p (destination))
903 2618 : destination = lookup_label (destination);
904 :
905 : /* We warn about unused labels with -Wunused. That means we have to
906 : mark the used labels as used. */
907 2764 : if (TREE_CODE (destination) == LABEL_DECL)
908 2618 : TREE_USED (destination) = 1;
909 : else
910 : {
911 146 : destination = mark_rvalue_use (destination);
912 146 : if (!processing_template_decl)
913 : {
914 126 : destination = cp_convert (ptr_type_node, destination,
915 : tf_warning_or_error);
916 126 : if (error_operand_p (destination))
917 : return NULL_TREE;
918 117 : destination
919 117 : = fold_build_cleanup_point_expr (TREE_TYPE (destination),
920 : destination);
921 : }
922 : }
923 :
924 2755 : add_stmt (build_predict_expr (PRED_GOTO, NOT_TAKEN));
925 :
926 2755 : tree stmt = build_stmt (input_location, GOTO_EXPR, destination);
927 2755 : check_goto (&TREE_OPERAND (stmt, 0));
928 :
929 2755 : return add_stmt (stmt);
930 : }
931 :
932 : /* Returns true if T corresponds to an assignment operator expression. */
933 :
934 : static bool
935 882148 : is_assignment_op_expr_p (tree t)
936 : {
937 882148 : if (t == NULL_TREE)
938 : return false;
939 :
940 882148 : if (TREE_CODE (t) == MODIFY_EXPR
941 882148 : || (TREE_CODE (t) == MODOP_EXPR
942 336 : && TREE_CODE (TREE_OPERAND (t, 1)) == NOP_EXPR))
943 : return true;
944 :
945 881461 : tree call = extract_call_expr (t);
946 881461 : if (call == NULL_TREE
947 129916 : || call == error_mark_node
948 1011377 : || !CALL_EXPR_OPERATOR_SYNTAX (call))
949 : return false;
950 :
951 4678 : tree fndecl = cp_get_callee_fndecl_nofold (call);
952 4678 : return fndecl != NULL_TREE
953 4580 : && DECL_ASSIGNMENT_OPERATOR_P (fndecl)
954 4729 : && DECL_OVERLOADED_OPERATOR_IS (fndecl, NOP_EXPR);
955 : }
956 :
957 : /* Return true if TYPE is a class type that is convertible to
958 : and assignable from bool. */
959 :
960 : static GTY((deletable)) hash_map<tree, bool> *boolish_class_type_p_cache;
961 :
962 : static bool
963 60 : boolish_class_type_p (tree type)
964 : {
965 60 : type = TYPE_MAIN_VARIANT (type);
966 60 : if (!CLASS_TYPE_P (type) || !COMPLETE_TYPE_P (type))
967 : return false;
968 :
969 77 : if (bool *r = hash_map_safe_get (boolish_class_type_p_cache, type))
970 26 : return *r;
971 :
972 19 : tree ops;
973 19 : bool has_bool_assignment = false;
974 19 : bool has_bool_conversion = false;
975 :
976 19 : ops = lookup_fnfields (type, assign_op_identifier, /*protect=*/0, tf_none);
977 58 : for (tree op : ovl_range (BASELINK_FUNCTIONS (ops)))
978 : {
979 31 : op = STRIP_TEMPLATE (op);
980 31 : if (TREE_CODE (op) != FUNCTION_DECL)
981 0 : continue;
982 31 : tree parm = DECL_CHAIN (DECL_ARGUMENTS (op));
983 31 : tree parm_type = non_reference (TREE_TYPE (parm));
984 31 : if (TREE_CODE (parm_type) == BOOLEAN_TYPE)
985 : {
986 : has_bool_assignment = true;
987 : break;
988 : }
989 : }
990 :
991 19 : if (has_bool_assignment)
992 : {
993 4 : ops = lookup_conversions (type);
994 8 : for (; ops; ops = TREE_CHAIN (ops))
995 : {
996 4 : tree op = TREE_VALUE (ops);
997 4 : if (!DECL_NONCONVERTING_P (op)
998 4 : && TREE_CODE (DECL_CONV_FN_TYPE (op)) == BOOLEAN_TYPE)
999 : {
1000 : has_bool_conversion = true;
1001 : break;
1002 : }
1003 : }
1004 : }
1005 :
1006 19 : bool boolish = has_bool_assignment && has_bool_conversion;
1007 19 : hash_map_safe_put<true> (boolish_class_type_p_cache, type, boolish);
1008 19 : return boolish;
1009 : }
1010 :
1011 :
1012 : /* Maybe warn about an unparenthesized 'a = b' (appearing in a
1013 : boolean context where 'a == b' might have been intended).
1014 : NESTED_P is true if T is the RHS of another assignment. */
1015 :
1016 : void
1017 93588438 : maybe_warn_unparenthesized_assignment (tree t, bool nested_p,
1018 : tsubst_flags_t complain)
1019 : {
1020 93588438 : tree type = TREE_TYPE (t);
1021 93588438 : t = STRIP_REFERENCE_REF (t);
1022 :
1023 93588438 : if ((complain & tf_warning)
1024 93526557 : && warn_parentheses
1025 882148 : && is_assignment_op_expr_p (t)
1026 : /* A parenthesized expression would've had this warning
1027 : suppressed by finish_parenthesized_expr. */
1028 738 : && !warning_suppressed_p (t, OPT_Wparentheses)
1029 : /* In c = a = b, don't warn if a has type bool or bool-like class. */
1030 93588785 : && (!nested_p
1031 176 : || (TREE_CODE (type) != BOOLEAN_TYPE
1032 60 : && !boolish_class_type_p (type))))
1033 : {
1034 219 : warning_at (cp_expr_loc_or_input_loc (t), OPT_Wparentheses,
1035 : "suggest parentheses around assignment used as truth value");
1036 219 : suppress_warning (t, OPT_Wparentheses);
1037 : }
1038 93588438 : }
1039 :
1040 : /* Helper class for saving/restoring ANNOTATE_EXPRs. For a tree node t, users
1041 : can construct one of these like so:
1042 :
1043 : annotate_saver s (&t);
1044 :
1045 : and t will be updated to have any annotations removed. The user can then
1046 : transform t, and later restore the ANNOTATE_EXPRs with:
1047 :
1048 : t = s.restore (t).
1049 :
1050 : The intent is to ensure that any ANNOTATE_EXPRs remain the outermost
1051 : expressions following any operations on t. */
1052 :
1053 : class annotate_saver {
1054 : /* The chain of saved annotations, if there were any. Otherwise null. */
1055 : tree m_annotations;
1056 :
1057 : /* If M_ANNOTATIONS is non-null, then M_INNER points to TREE_OPERAND (A, 0)
1058 : for the innermost annotation A. */
1059 : tree *m_inner;
1060 :
1061 : public:
1062 : annotate_saver (tree *);
1063 : tree restore (tree);
1064 : };
1065 :
1066 : /* If *COND is an ANNOTATE_EXPR, walk through the chain of annotations, and set
1067 : *COND equal to the first non-ANNOTATE_EXPR (saving a pointer to the
1068 : original chain of annotations for later use in restore). */
1069 :
1070 55264019 : annotate_saver::annotate_saver (tree *cond) : m_annotations (nullptr)
1071 : {
1072 55264019 : tree *t = cond;
1073 55274451 : while (TREE_CODE (*t) == ANNOTATE_EXPR)
1074 10432 : t = &TREE_OPERAND (*t, 0);
1075 :
1076 55264019 : if (t != cond)
1077 : {
1078 10429 : m_annotations = *cond;
1079 10429 : *cond = *t;
1080 10429 : m_inner = t;
1081 : }
1082 55264019 : }
1083 :
1084 : /* If we didn't strip any annotations on construction, return NEW_INNER
1085 : unmodified. Otherwise, wrap the saved annotations around NEW_INNER (updating
1086 : the types and flags of the annotations if needed) and return the resulting
1087 : expression. */
1088 :
1089 : tree
1090 55264019 : annotate_saver::restore (tree new_inner)
1091 : {
1092 55264019 : if (!m_annotations)
1093 : return new_inner;
1094 :
1095 : /* If the type of the inner expression changed, we need to update the types
1096 : of all the ANNOTATE_EXPRs. We may need to update the flags too, but we
1097 : assume they only change if the type of the inner expression changes.
1098 : The flag update logic assumes that the other operands to the
1099 : ANNOTATE_EXPRs are always INTEGER_CSTs. */
1100 10429 : if (TREE_TYPE (new_inner) != TREE_TYPE (*m_inner))
1101 : {
1102 6 : const bool new_readonly
1103 6 : = TREE_READONLY (new_inner) || CONSTANT_CLASS_P (new_inner);
1104 :
1105 12 : for (tree c = m_annotations; c != *m_inner; c = TREE_OPERAND (c, 0))
1106 : {
1107 6 : gcc_checking_assert (TREE_CODE (c) == ANNOTATE_EXPR
1108 : && TREE_CODE (TREE_OPERAND (c, 1)) == INTEGER_CST
1109 : && TREE_CODE (TREE_OPERAND (c, 2)) == INTEGER_CST);
1110 6 : TREE_TYPE (c) = TREE_TYPE (new_inner);
1111 6 : TREE_SIDE_EFFECTS (c) = TREE_SIDE_EFFECTS (new_inner);
1112 6 : TREE_READONLY (c) = new_readonly;
1113 : }
1114 : }
1115 :
1116 10429 : *m_inner = new_inner;
1117 10429 : return m_annotations;
1118 : }
1119 :
1120 : /* COND is the condition-expression for an if, while, etc.,
1121 : statement. Convert it to a boolean value, if appropriate.
1122 : In addition, verify sequence points if -Wsequence-point is enabled. */
1123 :
1124 : tree
1125 95735931 : maybe_convert_cond (tree cond)
1126 : {
1127 : /* Empty conditions remain empty. */
1128 95735931 : if (!cond)
1129 : return NULL_TREE;
1130 :
1131 : /* Wait until we instantiate templates before doing conversion. */
1132 95362121 : if (type_dependent_expression_p (cond))
1133 40098102 : return cond;
1134 :
1135 : /* Strip any ANNOTATE_EXPRs from COND. */
1136 55264019 : annotate_saver annotations (&cond);
1137 :
1138 : /* For structured binding used in condition, the conversion needs to be
1139 : evaluated before the individual variables are initialized in the
1140 : std::tuple_{size,element} case. cp_finish_decomp saved the conversion
1141 : result in a NON_LVALUE_EXPR, pick it up from there. */
1142 386993 : if (DECL_DECOMPOSITION_P (cond)
1143 228 : && DECL_DECOMP_IS_BASE (cond)
1144 228 : && DECL_DECOMP_BASE (cond)
1145 55264244 : && TREE_CODE (DECL_DECOMP_BASE (cond)) == NON_LVALUE_EXPR)
1146 59 : cond = TREE_OPERAND (DECL_DECOMP_BASE (cond), 0);
1147 :
1148 55264019 : if (warn_sequence_point && !processing_template_decl)
1149 328179 : verify_sequence_points (cond);
1150 :
1151 55264019 : maybe_warn_unparenthesized_assignment (cond, /*nested_p=*/false,
1152 : tf_warning_or_error);
1153 :
1154 : /* Do the conversion. */
1155 55264019 : cond = convert_from_reference (cond);
1156 55264019 : cond = condition_conversion (cond);
1157 :
1158 : /* Restore any ANNOTATE_EXPRs around COND. */
1159 55264019 : return annotations.restore (cond);
1160 : }
1161 :
1162 : /* Finish an expression-statement, whose EXPRESSION is as indicated. */
1163 :
1164 : tree
1165 169565635 : finish_expr_stmt (tree expr)
1166 : {
1167 169565635 : tree r = NULL_TREE;
1168 169565635 : location_t loc = EXPR_LOCATION (expr);
1169 :
1170 169376159 : if (expr != NULL_TREE)
1171 : {
1172 : /* If we ran into a problem, make sure we complained. */
1173 169565474 : gcc_assert (expr != error_mark_node || seen_error ());
1174 :
1175 169565474 : if (!processing_template_decl)
1176 : {
1177 61745316 : if (warn_sequence_point)
1178 819409 : verify_sequence_points (expr);
1179 61745316 : expr = convert_to_void (expr, ICV_STATEMENT, tf_warning_or_error);
1180 : }
1181 107820158 : else if (!type_dependent_expression_p (expr))
1182 23487966 : convert_to_void (expr, ICV_STATEMENT, tf_warning_or_error);
1183 :
1184 169565471 : if (check_for_bare_parameter_packs (expr))
1185 24 : expr = error_mark_node;
1186 :
1187 : /* Simplification of inner statement expressions, compound exprs,
1188 : etc can result in us already having an EXPR_STMT or other statement
1189 : tree. Don't wrap them in EXPR_STMT. */
1190 169565471 : if (TREE_CODE (expr) != CLEANUP_POINT_EXPR)
1191 : {
1192 169565292 : if (TREE_CODE (expr) != EXPR_STMT
1193 167027363 : && !STATEMENT_CLASS_P (expr)
1194 167023212 : && TREE_CODE (expr) != STATEMENT_LIST)
1195 166865487 : expr = build_stmt (loc, EXPR_STMT, expr);
1196 169565292 : expr = maybe_cleanup_point_expr_void (expr);
1197 : }
1198 :
1199 169565471 : r = add_stmt (expr);
1200 : }
1201 :
1202 169565632 : return r;
1203 : }
1204 :
1205 :
1206 : /* Begin an if-statement. Returns a newly created IF_STMT if
1207 : appropriate. */
1208 :
1209 : tree
1210 77263182 : begin_if_stmt (void)
1211 : {
1212 77263182 : tree r, scope;
1213 77263182 : scope = do_pushlevel (sk_cond);
1214 77263182 : r = build_stmt (input_location, IF_STMT, NULL_TREE,
1215 : NULL_TREE, NULL_TREE, scope);
1216 77263182 : current_binding_level->this_entity = r;
1217 77263182 : begin_cond (&IF_COND (r));
1218 77263182 : return r;
1219 : }
1220 :
1221 : /* Returns true if FN, a CALL_EXPR, is a call to
1222 : std::is_constant_evaluated or __builtin_is_constant_evaluated. */
1223 :
1224 : static bool
1225 254711 : is_std_constant_evaluated_p (tree fn)
1226 : {
1227 : /* std::is_constant_evaluated takes no arguments. */
1228 254711 : if (call_expr_nargs (fn) != 0)
1229 : return false;
1230 :
1231 91145 : tree fndecl = cp_get_callee_fndecl_nofold (fn);
1232 91145 : if (fndecl == NULL_TREE)
1233 : return false;
1234 :
1235 28360 : if (fndecl_built_in_p (fndecl, CP_BUILT_IN_IS_CONSTANT_EVALUATED,
1236 : BUILT_IN_FRONTEND))
1237 : return true;
1238 :
1239 28331 : if (!decl_in_std_namespace_p (fndecl))
1240 : return false;
1241 :
1242 12992 : tree name = DECL_NAME (fndecl);
1243 12992 : return name && id_equal (name, "is_constant_evaluated");
1244 : }
1245 :
1246 : /* Callback function for maybe_warn_for_constant_evaluated that looks
1247 : for calls to std::is_constant_evaluated in TP. */
1248 :
1249 : static tree
1250 4721366 : find_std_constant_evaluated_r (tree *tp, int *walk_subtrees, void *)
1251 : {
1252 4721366 : tree t = *tp;
1253 :
1254 4721366 : if (TYPE_P (t) || TREE_CONSTANT (t))
1255 : {
1256 836686 : *walk_subtrees = false;
1257 836686 : return NULL_TREE;
1258 : }
1259 :
1260 3884680 : switch (TREE_CODE (t))
1261 : {
1262 254711 : case CALL_EXPR:
1263 254711 : if (is_std_constant_evaluated_p (t))
1264 2396 : return t;
1265 : break;
1266 6 : case EXPR_STMT:
1267 : /* Don't warn in statement expressions. */
1268 6 : *walk_subtrees = false;
1269 6 : return NULL_TREE;
1270 : default:
1271 : break;
1272 : }
1273 :
1274 : return NULL_TREE;
1275 : }
1276 :
1277 : /* In certain contexts, std::is_constant_evaluated() is always true (for
1278 : instance, in a consteval function or in a constexpr if), or always false
1279 : (e.g., in a non-constexpr non-consteval function) so give the user a clue. */
1280 :
1281 : static void
1282 77349084 : maybe_warn_for_constant_evaluated (tree cond, bool constexpr_if,
1283 : bool trivial_infinite)
1284 : {
1285 77349084 : if (!warn_tautological_compare)
1286 : return;
1287 :
1288 : /* Suppress warning for std::is_constant_evaluated if the conditional
1289 : comes from a macro. */
1290 1439674 : if (from_macro_expansion_at (EXPR_LOCATION (cond)))
1291 : return;
1292 :
1293 608023 : cond = cp_walk_tree_without_duplicates (&cond, find_std_constant_evaluated_r,
1294 : NULL);
1295 608023 : if (cond)
1296 : {
1297 2396 : if (constexpr_if)
1298 34 : warning_at (EXPR_LOCATION (cond), OPT_Wtautological_compare,
1299 : "%<std::is_constant_evaluated%> always evaluates to "
1300 : "true in %<if constexpr%>");
1301 2362 : else if (trivial_infinite)
1302 : {
1303 8 : auto_diagnostic_group d;
1304 8 : if (warning_at (EXPR_LOCATION (cond), OPT_Wtautological_compare,
1305 : "%<std::is_constant_evaluated%> evaluates to "
1306 : "true when checking if trivially empty iteration "
1307 : "statement is trivial infinite loop")
1308 8 : && !maybe_constexpr_fn (current_function_decl))
1309 8 : inform (EXPR_LOCATION (cond),
1310 : "and evaluates to false when actually evaluating "
1311 : "the condition in non-%<constexpr%> function");
1312 8 : }
1313 2354 : else if (!maybe_constexpr_fn (current_function_decl))
1314 38 : warning_at (EXPR_LOCATION (cond), OPT_Wtautological_compare,
1315 : "%<std::is_constant_evaluated%> always evaluates to "
1316 : "false in a non-%<constexpr%> function");
1317 4632 : else if (DECL_IMMEDIATE_FUNCTION_P (current_function_decl))
1318 3 : warning_at (EXPR_LOCATION (cond), OPT_Wtautological_compare,
1319 : "%<std::is_constant_evaluated%> always evaluates to "
1320 : "true in a %<consteval%> function");
1321 : }
1322 : }
1323 :
1324 : /* Process the COND of an if-statement, which may be given by
1325 : IF_STMT. */
1326 :
1327 : tree
1328 77263182 : finish_if_stmt_cond (tree orig_cond, tree if_stmt)
1329 : {
1330 77263182 : tree cond = maybe_convert_cond (orig_cond);
1331 77263182 : maybe_warn_for_constant_evaluated (cond, IF_STMT_CONSTEXPR_P (if_stmt),
1332 : /*trivial_infinite=*/false);
1333 77263182 : if (IF_STMT_CONSTEXPR_P (if_stmt)
1334 16299405 : && !type_dependent_expression_p (cond)
1335 11176737 : && require_constant_expression (cond)
1336 11176706 : && !instantiation_dependent_expression_p (cond)
1337 : /* Wait until instantiation time, since only then COND has been
1338 : converted to bool. */
1339 83278348 : && TYPE_MAIN_VARIANT (TREE_TYPE (cond)) == boolean_type_node)
1340 : {
1341 6015166 : cond = instantiate_non_dependent_expr (cond);
1342 6015166 : cond = cxx_constant_value (cond);
1343 : }
1344 71248016 : else if (processing_template_decl)
1345 53482544 : cond = orig_cond;
1346 77263182 : finish_cond (&IF_COND (if_stmt), cond);
1347 77263182 : add_stmt (if_stmt);
1348 77263182 : THEN_CLAUSE (if_stmt) = push_stmt_list ();
1349 77263182 : return cond;
1350 : }
1351 :
1352 : /* Finish the then-clause of an if-statement, which may be given by
1353 : IF_STMT. */
1354 :
1355 : tree
1356 77255353 : finish_then_clause (tree if_stmt)
1357 : {
1358 77255353 : THEN_CLAUSE (if_stmt) = pop_stmt_list (THEN_CLAUSE (if_stmt));
1359 77255353 : return if_stmt;
1360 : }
1361 :
1362 : /* Begin the else-clause of an if-statement. */
1363 :
1364 : void
1365 28771441 : begin_else_clause (tree if_stmt)
1366 : {
1367 28771441 : ELSE_CLAUSE (if_stmt) = push_stmt_list ();
1368 28771441 : }
1369 :
1370 : /* Finish the else-clause of an if-statement, which may be given by
1371 : IF_STMT. */
1372 :
1373 : void
1374 28771403 : finish_else_clause (tree if_stmt)
1375 : {
1376 28771403 : ELSE_CLAUSE (if_stmt) = pop_stmt_list (ELSE_CLAUSE (if_stmt));
1377 28771403 : }
1378 :
1379 : /* Callback for cp_walk_tree to mark all {VAR,PARM}_DECLs in a tree as
1380 : read. */
1381 :
1382 : static tree
1383 887284075 : maybe_mark_exp_read_r (tree *tp, int *, void *)
1384 : {
1385 887284075 : tree t = *tp;
1386 887284075 : if (VAR_P (t) || TREE_CODE (t) == PARM_DECL)
1387 51963965 : mark_exp_read (t);
1388 887284075 : return NULL_TREE;
1389 : }
1390 :
1391 : /* Finish an if-statement. */
1392 :
1393 : void
1394 77255353 : finish_if_stmt (tree if_stmt)
1395 : {
1396 77255353 : tree scope = IF_SCOPE (if_stmt);
1397 77255353 : IF_SCOPE (if_stmt) = NULL;
1398 77255353 : if (IF_STMT_CONSTEXPR_P (if_stmt))
1399 : {
1400 : /* Prevent various -Wunused warnings. We might not instantiate
1401 : either of these branches, so we would not mark the variables
1402 : used in that branch as read. */
1403 16291576 : cp_walk_tree_without_duplicates (&THEN_CLAUSE (if_stmt),
1404 : maybe_mark_exp_read_r, NULL);
1405 16291576 : cp_walk_tree_without_duplicates (&ELSE_CLAUSE (if_stmt),
1406 : maybe_mark_exp_read_r, NULL);
1407 : }
1408 77255353 : add_stmt (do_poplevel (scope));
1409 77255353 : }
1410 :
1411 : /* Determine if iteration statement with *CONDP condition and
1412 : loop BODY is trivially empty iteration statement or even
1413 : trivial infinite loop. In the latter case for -ffinite-loops
1414 : add ANNOTATE_EXPR to mark the loop as maybe validly infinite.
1415 : Also, emit -Wtautological-compare warning for std::is_constant_evaluated ()
1416 : calls in the condition when needed. */
1417 :
1418 : static void
1419 18095648 : finish_loop_cond (tree *condp, tree body)
1420 : {
1421 18095648 : if (TREE_CODE (*condp) == INTEGER_CST)
1422 : return;
1423 12968961 : bool trivially_empty = expr_first (body) == NULL_TREE;
1424 12968961 : bool trivial_infinite = false;
1425 12968961 : if (trivially_empty)
1426 : {
1427 100214 : tree c = fold_non_dependent_expr (*condp, tf_none,
1428 : /*manifestly_const_eval=*/true);
1429 100214 : trivial_infinite = c && integer_nonzerop (c);
1430 : }
1431 12968961 : if (warn_tautological_compare)
1432 : {
1433 86104 : tree cond = *condp;
1434 86471 : while (TREE_CODE (cond) == ANNOTATE_EXPR)
1435 367 : cond = TREE_OPERAND (cond, 0);
1436 86104 : if (trivial_infinite
1437 86168 : && !DECL_IMMEDIATE_FUNCTION_P (current_function_decl))
1438 64 : maybe_warn_for_constant_evaluated (cond, /*constexpr_if=*/false,
1439 : /*trivial_infinite=*/true);
1440 86040 : else if (!trivially_empty
1441 375 : || !processing_template_decl
1442 86444 : || DECL_IMMEDIATE_FUNCTION_P (current_function_decl))
1443 85838 : maybe_warn_for_constant_evaluated (cond, /*constexpr_if=*/false,
1444 : /*trivial_infinite=*/false);
1445 : }
1446 12968961 : if (trivial_infinite && flag_finite_loops && !processing_template_decl)
1447 64 : *condp = build3 (ANNOTATE_EXPR, TREE_TYPE (*condp), *condp,
1448 : build_int_cst (integer_type_node,
1449 : annot_expr_maybe_infinite_kind),
1450 : integer_zero_node);
1451 : }
1452 :
1453 : /* Begin a while-statement. Returns a newly created WHILE_STMT if
1454 : appropriate. */
1455 :
1456 : tree
1457 4946309 : begin_while_stmt (void)
1458 : {
1459 4946309 : tree r;
1460 4946309 : r = build_stmt (input_location, WHILE_STMT, NULL_TREE, NULL_TREE, NULL_TREE,
1461 : NULL_TREE, NULL_TREE);
1462 4946309 : add_stmt (r);
1463 4946309 : WHILE_BODY (r) = do_pushlevel (sk_block);
1464 4946309 : begin_cond (&WHILE_COND (r));
1465 4946309 : return r;
1466 : }
1467 :
1468 : /* Process the COND of a while-statement, which may be given by
1469 : WHILE_STMT. */
1470 :
1471 : void
1472 4946309 : finish_while_stmt_cond (tree cond, tree while_stmt, bool ivdep,
1473 : tree unroll, bool novector)
1474 : {
1475 4946309 : cond = maybe_convert_cond (cond);
1476 4946309 : finish_cond (&WHILE_COND (while_stmt), cond);
1477 4946309 : begin_maybe_infinite_loop (cond);
1478 4946309 : if (ivdep && cond != error_mark_node)
1479 24 : WHILE_COND (while_stmt) = build3 (ANNOTATE_EXPR,
1480 12 : TREE_TYPE (WHILE_COND (while_stmt)),
1481 12 : WHILE_COND (while_stmt),
1482 : build_int_cst (integer_type_node,
1483 : annot_expr_ivdep_kind),
1484 : integer_zero_node);
1485 4946309 : if (unroll && cond != error_mark_node)
1486 28074 : WHILE_COND (while_stmt) = build3 (ANNOTATE_EXPR,
1487 14037 : TREE_TYPE (WHILE_COND (while_stmt)),
1488 14037 : WHILE_COND (while_stmt),
1489 : build_int_cst (integer_type_node,
1490 : annot_expr_unroll_kind),
1491 : unroll);
1492 4946309 : if (novector && cond != error_mark_node)
1493 42 : WHILE_COND (while_stmt) = build3 (ANNOTATE_EXPR,
1494 21 : TREE_TYPE (WHILE_COND (while_stmt)),
1495 21 : WHILE_COND (while_stmt),
1496 : build_int_cst (integer_type_node,
1497 : annot_expr_no_vector_kind),
1498 : integer_zero_node);
1499 4946309 : adjust_loop_decl_cond (&WHILE_BODY (while_stmt),
1500 : &WHILE_COND_PREP (while_stmt),
1501 : &WHILE_COND_CLEANUP (while_stmt));
1502 4946309 : }
1503 :
1504 : /* Finish a while-statement, which may be given by WHILE_STMT. */
1505 :
1506 : void
1507 4946309 : finish_while_stmt (tree while_stmt)
1508 : {
1509 4946309 : end_maybe_infinite_loop (boolean_true_node);
1510 4946309 : if (WHILE_COND_PREP (while_stmt))
1511 9629 : finish_loop_cond_prep (&WHILE_BODY (while_stmt),
1512 : &WHILE_COND_PREP (while_stmt),
1513 9629 : WHILE_COND_CLEANUP (while_stmt));
1514 : else
1515 4936680 : WHILE_BODY (while_stmt) = do_poplevel (WHILE_BODY (while_stmt));
1516 4946309 : finish_loop_cond (&WHILE_COND (while_stmt), WHILE_BODY (while_stmt));
1517 4946309 : }
1518 :
1519 : /* Begin a do-statement. Returns a newly created DO_STMT if
1520 : appropriate. */
1521 :
1522 : tree
1523 5838744 : begin_do_stmt (void)
1524 : {
1525 5838744 : tree r = build_stmt (input_location, DO_STMT, NULL_TREE, NULL_TREE,
1526 : NULL_TREE);
1527 5838744 : begin_maybe_infinite_loop (boolean_true_node);
1528 5838744 : add_stmt (r);
1529 5838744 : DO_BODY (r) = push_stmt_list ();
1530 5838744 : return r;
1531 : }
1532 :
1533 : /* Finish the body of a do-statement, which may be given by DO_STMT. */
1534 :
1535 : void
1536 5838744 : finish_do_body (tree do_stmt)
1537 : {
1538 5838744 : tree body = DO_BODY (do_stmt) = pop_stmt_list (DO_BODY (do_stmt));
1539 :
1540 5838744 : if (TREE_CODE (body) == STATEMENT_LIST && STATEMENT_LIST_TAIL (body))
1541 546788 : body = STATEMENT_LIST_TAIL (body)->stmt;
1542 :
1543 5838744 : if (IS_EMPTY_STMT (body))
1544 30 : warning (OPT_Wempty_body,
1545 : "suggest explicit braces around empty body in %<do%> statement");
1546 5838744 : }
1547 :
1548 : /* Finish a do-statement, which may be given by DO_STMT, and whose
1549 : COND is as indicated. */
1550 :
1551 : void
1552 5838744 : finish_do_stmt (tree cond, tree do_stmt, bool ivdep, tree unroll,
1553 : bool novector)
1554 : {
1555 5838744 : cond = maybe_convert_cond (cond);
1556 5838744 : end_maybe_infinite_loop (cond);
1557 : /* Unlike other iteration statements, the condition may not contain
1558 : a declaration, so we don't call finish_cond which checks for
1559 : unexpanded parameter packs. */
1560 5838744 : if (check_for_bare_parameter_packs (cond))
1561 3 : cond = error_mark_node;
1562 5838744 : if (ivdep && cond != error_mark_node)
1563 3 : cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
1564 : build_int_cst (integer_type_node, annot_expr_ivdep_kind),
1565 : integer_zero_node);
1566 5838744 : if (unroll && cond != error_mark_node)
1567 9 : cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
1568 : build_int_cst (integer_type_node, annot_expr_unroll_kind),
1569 : unroll);
1570 5838744 : if (novector && cond != error_mark_node)
1571 0 : cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
1572 : build_int_cst (integer_type_node, annot_expr_no_vector_kind),
1573 : integer_zero_node);
1574 5838744 : DO_COND (do_stmt) = cond;
1575 5838744 : tree do_body = DO_BODY (do_stmt);
1576 5838714 : if (CONVERT_EXPR_P (do_body)
1577 30 : && integer_zerop (TREE_OPERAND (do_body, 0))
1578 5838774 : && VOID_TYPE_P (TREE_TYPE (do_body)))
1579 : do_body = NULL_TREE;
1580 5838744 : finish_loop_cond (&DO_COND (do_stmt), do_body);
1581 5838744 : }
1582 :
1583 : /* Finish a return-statement. The EXPRESSION returned, if any, is as
1584 : indicated. */
1585 :
1586 : tree
1587 133735436 : finish_return_stmt (tree expr)
1588 : {
1589 133735436 : tree r;
1590 133735436 : bool no_warning;
1591 133735436 : bool dangling;
1592 :
1593 133735436 : expr = check_return_expr (expr, &no_warning, &dangling);
1594 :
1595 133735436 : if (error_operand_p (expr)
1596 133735436 : || (flag_openmp && !check_omp_return ()))
1597 : {
1598 : /* Suppress -Wreturn-type for this function. */
1599 1358 : if (warn_return_type)
1600 1352 : suppress_warning (current_function_decl, OPT_Wreturn_type);
1601 1358 : return error_mark_node;
1602 : }
1603 :
1604 133734078 : if (!processing_template_decl)
1605 : {
1606 46646471 : if (warn_sequence_point)
1607 1039499 : verify_sequence_points (expr);
1608 : }
1609 :
1610 133734078 : r = build_stmt (input_location, RETURN_EXPR, expr);
1611 133734078 : RETURN_EXPR_LOCAL_ADDR_P (r) = dangling;
1612 133734078 : if (no_warning)
1613 33 : suppress_warning (r, OPT_Wreturn_type);
1614 133734078 : r = maybe_cleanup_point_expr_void (r);
1615 133734078 : r = add_stmt (r);
1616 :
1617 133734078 : return r;
1618 : }
1619 :
1620 : /* Begin the scope of a for-statement or a range-for-statement.
1621 : Both the returned trees are to be used in a call to
1622 : begin_for_stmt or begin_range_for_stmt. */
1623 :
1624 : tree
1625 7964736 : begin_for_scope (tree *init)
1626 : {
1627 7964736 : tree scope = do_pushlevel (sk_for);
1628 :
1629 7964736 : if (processing_template_decl)
1630 6328948 : *init = push_stmt_list ();
1631 : else
1632 1635788 : *init = NULL_TREE;
1633 :
1634 7964736 : return scope;
1635 : }
1636 :
1637 : /* Begin a for-statement. Returns a new FOR_STMT.
1638 : SCOPE and INIT should be the return of begin_for_scope,
1639 : or both NULL_TREE */
1640 :
1641 : tree
1642 7684405 : begin_for_stmt (tree scope, tree init)
1643 : {
1644 7684405 : tree r;
1645 :
1646 7684405 : r = build_stmt (input_location, FOR_STMT, NULL_TREE, NULL_TREE,
1647 : NULL_TREE, NULL_TREE, NULL_TREE, NULL_TREE,
1648 : NULL_TREE, NULL_TREE);
1649 :
1650 7684405 : if (scope == NULL_TREE)
1651 : {
1652 1385257 : gcc_assert (!init);
1653 1385257 : scope = begin_for_scope (&init);
1654 : }
1655 :
1656 7684405 : FOR_INIT_STMT (r) = init;
1657 7684405 : FOR_SCOPE (r) = scope;
1658 :
1659 7684405 : return r;
1660 : }
1661 :
1662 : /* Finish the init-statement of a for-statement, which may be
1663 : given by FOR_STMT. */
1664 :
1665 : void
1666 7684405 : finish_init_stmt (tree for_stmt)
1667 : {
1668 7684405 : if (processing_template_decl)
1669 6048617 : FOR_INIT_STMT (for_stmt) = pop_stmt_list (FOR_INIT_STMT (for_stmt));
1670 7684405 : add_stmt (for_stmt);
1671 7684405 : FOR_BODY (for_stmt) = do_pushlevel (sk_block);
1672 7684405 : begin_cond (&FOR_COND (for_stmt));
1673 7684405 : }
1674 :
1675 : /* Finish the COND of a for-statement, which may be given by
1676 : FOR_STMT. */
1677 :
1678 : void
1679 7684405 : finish_for_cond (tree cond, tree for_stmt, bool ivdep, tree unroll,
1680 : bool novector)
1681 : {
1682 7684405 : cond = maybe_convert_cond (cond);
1683 7684405 : finish_cond (&FOR_COND (for_stmt), cond);
1684 7684405 : begin_maybe_infinite_loop (cond);
1685 7684405 : if (ivdep && cond != error_mark_node)
1686 68 : FOR_COND (for_stmt) = build3 (ANNOTATE_EXPR,
1687 34 : TREE_TYPE (FOR_COND (for_stmt)),
1688 34 : FOR_COND (for_stmt),
1689 : build_int_cst (integer_type_node,
1690 : annot_expr_ivdep_kind),
1691 : integer_zero_node);
1692 7684405 : if (unroll && cond != error_mark_node)
1693 408 : FOR_COND (for_stmt) = build3 (ANNOTATE_EXPR,
1694 204 : TREE_TYPE (FOR_COND (for_stmt)),
1695 204 : FOR_COND (for_stmt),
1696 : build_int_cst (integer_type_node,
1697 : annot_expr_unroll_kind),
1698 : unroll);
1699 7684405 : if (novector && cond && cond != error_mark_node)
1700 268 : FOR_COND (for_stmt) = build3 (ANNOTATE_EXPR,
1701 134 : TREE_TYPE (FOR_COND (for_stmt)),
1702 134 : FOR_COND (for_stmt),
1703 : build_int_cst (integer_type_node,
1704 : annot_expr_no_vector_kind),
1705 : integer_zero_node);
1706 7684405 : adjust_loop_decl_cond (&FOR_BODY (for_stmt), &FOR_COND_PREP (for_stmt),
1707 : &FOR_COND_CLEANUP (for_stmt));
1708 7684405 : }
1709 :
1710 : /* Finish the increment-EXPRESSION in a for-statement, which may be
1711 : given by FOR_STMT. */
1712 :
1713 : void
1714 7671966 : finish_for_expr (tree expr, tree for_stmt)
1715 : {
1716 7671966 : if (!expr)
1717 : return;
1718 : /* If EXPR is an overloaded function, issue an error; there is no
1719 : context available to use to perform overload resolution. */
1720 7207342 : if (type_unknown_p (expr))
1721 : {
1722 6 : cxx_incomplete_type_error (expr, TREE_TYPE (expr));
1723 6 : expr = error_mark_node;
1724 : }
1725 7207342 : if (!processing_template_decl)
1726 : {
1727 1561088 : if (warn_sequence_point)
1728 15015 : verify_sequence_points (expr);
1729 1561088 : expr = convert_to_void (expr, ICV_THIRD_IN_FOR,
1730 : tf_warning_or_error);
1731 : }
1732 5646254 : else if (!type_dependent_expression_p (expr))
1733 2039743 : convert_to_void (expr, ICV_THIRD_IN_FOR, tf_warning_or_error);
1734 7207342 : expr = maybe_cleanup_point_expr_void (expr);
1735 7207342 : if (check_for_bare_parameter_packs (expr))
1736 0 : expr = error_mark_node;
1737 7207342 : FOR_EXPR (for_stmt) = expr;
1738 : }
1739 :
1740 : /* During parsing of the body, range for uses "__for_{range,begin,end} "
1741 : decl names to make those unaccessible by code in the body.
1742 : Find those decls and store into RANGE_FOR_DECL array, so that they
1743 : can be changed later to ones with underscore instead of space, so that
1744 : it can be inspected in the debugger. */
1745 :
1746 : void
1747 7964849 : find_range_for_decls (tree range_for_decl[3])
1748 : {
1749 7964849 : gcc_assert (CPTI_FOR_BEGIN__IDENTIFIER == CPTI_FOR_RANGE__IDENTIFIER + 1
1750 : && CPTI_FOR_END__IDENTIFIER == CPTI_FOR_RANGE__IDENTIFIER + 2
1751 : && CPTI_FOR_RANGE_IDENTIFIER == CPTI_FOR_RANGE__IDENTIFIER + 3
1752 : && CPTI_FOR_BEGIN_IDENTIFIER == CPTI_FOR_BEGIN__IDENTIFIER + 3
1753 : && CPTI_FOR_END_IDENTIFIER == CPTI_FOR_END__IDENTIFIER + 3);
1754 31859396 : for (int i = 0; i < 3; i++)
1755 : {
1756 23894547 : tree id = cp_global_trees[CPTI_FOR_RANGE__IDENTIFIER + i];
1757 23894547 : if (IDENTIFIER_BINDING (id)
1758 23894547 : && IDENTIFIER_BINDING (id)->scope == current_binding_level)
1759 : {
1760 278152 : range_for_decl[i] = IDENTIFIER_BINDING (id)->value;
1761 278152 : gcc_assert (VAR_P (range_for_decl[i])
1762 : && DECL_ARTIFICIAL (range_for_decl[i]));
1763 : }
1764 : }
1765 7964849 : }
1766 :
1767 : /* Finish the body of a for-statement, which may be given by
1768 : FOR_STMT. The increment-EXPR for the loop must be
1769 : provided.
1770 : It can also finish RANGE_FOR_STMT. */
1771 :
1772 : void
1773 7964736 : finish_for_stmt (tree for_stmt)
1774 : {
1775 7964736 : end_maybe_infinite_loop (boolean_true_node);
1776 :
1777 7964736 : if (TREE_CODE (for_stmt) == RANGE_FOR_STMT)
1778 280331 : RANGE_FOR_BODY (for_stmt) = do_poplevel (RANGE_FOR_BODY (for_stmt));
1779 : else
1780 : {
1781 7684405 : if (FOR_COND_PREP (for_stmt))
1782 174 : finish_loop_cond_prep (&FOR_BODY (for_stmt),
1783 : &FOR_COND_PREP (for_stmt),
1784 174 : FOR_COND_CLEANUP (for_stmt));
1785 : else
1786 7684231 : FOR_BODY (for_stmt) = do_poplevel (FOR_BODY (for_stmt));
1787 7684405 : if (FOR_COND (for_stmt))
1788 7310595 : finish_loop_cond (&FOR_COND (for_stmt),
1789 7310595 : FOR_EXPR (for_stmt) ? integer_one_node
1790 144372 : : FOR_BODY (for_stmt));
1791 : }
1792 :
1793 : /* Pop the scope for the body of the loop. */
1794 7964736 : tree *scope_ptr = (TREE_CODE (for_stmt) == RANGE_FOR_STMT
1795 7964736 : ? &RANGE_FOR_SCOPE (for_stmt)
1796 7684405 : : &FOR_SCOPE (for_stmt));
1797 7964736 : tree scope = *scope_ptr;
1798 7964736 : *scope_ptr = NULL;
1799 :
1800 : /* During parsing of the body, range for uses "__for_{range,begin,end} "
1801 : decl names to make those unaccessible by code in the body.
1802 : Change it to ones with underscore instead of space, so that it can
1803 : be inspected in the debugger. */
1804 7964736 : tree range_for_decl[3] = { NULL_TREE, NULL_TREE, NULL_TREE };
1805 7964736 : find_range_for_decls (range_for_decl);
1806 :
1807 7964736 : add_stmt (do_poplevel (scope));
1808 :
1809 : /* If we're being called from build_vec_init, don't mess with the names of
1810 : the variables for an enclosing range-for. */
1811 7964736 : if (!stmts_are_full_exprs_p ())
1812 12439 : return;
1813 :
1814 31809188 : for (int i = 0; i < 3; i++)
1815 23856891 : if (range_for_decl[i])
1816 278036 : DECL_NAME (range_for_decl[i])
1817 278036 : = cp_global_trees[CPTI_FOR_RANGE_IDENTIFIER + i];
1818 : }
1819 :
1820 : /* Begin a range-for-statement. Returns a new RANGE_FOR_STMT.
1821 : SCOPE and INIT should be the return of begin_for_scope,
1822 : or both NULL_TREE .
1823 : To finish it call finish_for_stmt(). */
1824 :
1825 : tree
1826 280331 : begin_range_for_stmt (tree scope, tree init)
1827 : {
1828 280331 : begin_maybe_infinite_loop (boolean_false_node);
1829 :
1830 280331 : tree r = build_stmt (input_location, RANGE_FOR_STMT, NULL_TREE, NULL_TREE,
1831 : NULL_TREE, NULL_TREE, NULL_TREE, NULL_TREE);
1832 :
1833 280331 : if (scope == NULL_TREE)
1834 : {
1835 506 : gcc_assert (!init);
1836 506 : scope = begin_for_scope (&init);
1837 : }
1838 :
1839 : /* Since C++20, RANGE_FOR_STMTs can use the init tree, so save it. */
1840 280331 : RANGE_FOR_INIT_STMT (r) = init;
1841 280331 : RANGE_FOR_SCOPE (r) = scope;
1842 :
1843 280331 : return r;
1844 : }
1845 :
1846 : /* Finish the head of a range-based for statement, which may
1847 : be given by RANGE_FOR_STMT. DECL must be the declaration
1848 : and EXPR must be the loop expression. */
1849 :
1850 : void
1851 280331 : finish_range_for_decl (tree range_for_stmt, tree decl, tree expr)
1852 : {
1853 280331 : if (processing_template_decl)
1854 560662 : RANGE_FOR_INIT_STMT (range_for_stmt)
1855 560662 : = pop_stmt_list (RANGE_FOR_INIT_STMT (range_for_stmt));
1856 280331 : RANGE_FOR_DECL (range_for_stmt) = decl;
1857 280331 : RANGE_FOR_EXPR (range_for_stmt) = expr;
1858 280331 : add_stmt (range_for_stmt);
1859 280331 : RANGE_FOR_BODY (range_for_stmt) = do_pushlevel (sk_block);
1860 280331 : }
1861 :
1862 : /* Begin the scope of an expansion-statement. */
1863 :
1864 : tree
1865 2324 : begin_template_for_scope (tree *init)
1866 : {
1867 2324 : tree scope = do_pushlevel (sk_template_for);
1868 :
1869 2324 : if (processing_template_decl)
1870 547 : *init = push_stmt_list ();
1871 : else
1872 1777 : *init = NULL_TREE;
1873 :
1874 2324 : return scope;
1875 : }
1876 :
1877 : /* Finish a break-statement. */
1878 :
1879 : tree
1880 4958946 : finish_break_stmt (void)
1881 : {
1882 : /* In switch statements break is sometimes stylistically used after
1883 : a return statement. This can lead to spurious warnings about
1884 : control reaching the end of a non-void function when it is
1885 : inlined. Note that we are calling block_may_fallthru with
1886 : language specific tree nodes; this works because
1887 : block_may_fallthru returns true when given something it does not
1888 : understand. */
1889 4958946 : if (!block_may_fallthru (cur_stmt_list))
1890 921 : return void_node;
1891 4958025 : note_break_stmt ();
1892 4958025 : return add_stmt (build_stmt (input_location, BREAK_STMT, NULL_TREE));
1893 : }
1894 :
1895 : /* Finish a continue-statement. */
1896 :
1897 : tree
1898 254257 : finish_continue_stmt (void)
1899 : {
1900 254257 : return add_stmt (build_stmt (input_location, CONTINUE_STMT, NULL_TREE));
1901 : }
1902 :
1903 : /* Begin a switch-statement. Returns a new SWITCH_STMT if
1904 : appropriate. */
1905 :
1906 : tree
1907 742547 : begin_switch_stmt (void)
1908 : {
1909 742547 : tree r, scope;
1910 :
1911 742547 : scope = do_pushlevel (sk_cond);
1912 742547 : r = build_stmt (input_location, SWITCH_STMT, NULL_TREE, NULL_TREE, NULL_TREE,
1913 : scope, NULL_TREE);
1914 :
1915 742547 : begin_cond (&SWITCH_STMT_COND (r));
1916 :
1917 742547 : return r;
1918 : }
1919 :
1920 : /* Finish the cond of a switch-statement. */
1921 :
1922 : void
1923 742547 : finish_switch_cond (tree cond, tree switch_stmt)
1924 : {
1925 742547 : tree orig_type = NULL;
1926 :
1927 742547 : if (!processing_template_decl)
1928 : {
1929 : /* Convert the condition to an integer or enumeration type. */
1930 303480 : tree orig_cond = cond;
1931 : /* For structured binding used in condition, the conversion needs to be
1932 : evaluated before the individual variables are initialized in the
1933 : std::tuple_{size,element} case. cp_finish_decomp saved the
1934 : conversion result in a NON_LVALUE_EXPR, pick it up from there. */
1935 122 : if (DECL_DECOMPOSITION_P (cond)
1936 57 : && DECL_DECOMP_IS_BASE (cond)
1937 57 : && DECL_DECOMP_BASE (cond)
1938 303534 : && TREE_CODE (DECL_DECOMP_BASE (cond)) == NON_LVALUE_EXPR)
1939 18 : cond = TREE_OPERAND (DECL_DECOMP_BASE (cond), 0);
1940 303480 : cond = build_expr_type_conversion (WANT_INT | WANT_ENUM, cond, true);
1941 303480 : if (cond == NULL_TREE)
1942 : {
1943 42 : error_at (cp_expr_loc_or_input_loc (orig_cond),
1944 : "switch quantity not an integer");
1945 27 : cond = error_mark_node;
1946 : }
1947 : /* We want unlowered type here to handle enum bit-fields. */
1948 303480 : orig_type = unlowered_expr_type (cond);
1949 303480 : if (TREE_CODE (orig_type) != ENUMERAL_TYPE)
1950 208709 : orig_type = TREE_TYPE (cond);
1951 303480 : if (cond != error_mark_node)
1952 : {
1953 : /* [stmt.switch]
1954 :
1955 : Integral promotions are performed. */
1956 303444 : cond = perform_integral_promotions (cond);
1957 303444 : cond = maybe_cleanup_point_expr (cond);
1958 : }
1959 : }
1960 742547 : if (check_for_bare_parameter_packs (cond))
1961 0 : cond = error_mark_node;
1962 742547 : else if (!processing_template_decl && warn_sequence_point)
1963 2853 : verify_sequence_points (cond);
1964 :
1965 742547 : finish_cond (&SWITCH_STMT_COND (switch_stmt), cond);
1966 742547 : SWITCH_STMT_TYPE (switch_stmt) = orig_type;
1967 742547 : add_stmt (switch_stmt);
1968 742547 : push_switch (switch_stmt);
1969 742547 : SWITCH_STMT_BODY (switch_stmt) = push_stmt_list ();
1970 742547 : }
1971 :
1972 : /* Finish the body of a switch-statement, which may be given by
1973 : SWITCH_STMT. The COND to switch on is indicated. */
1974 :
1975 : void
1976 742547 : finish_switch_stmt (tree switch_stmt)
1977 : {
1978 742547 : tree scope;
1979 :
1980 1485094 : SWITCH_STMT_BODY (switch_stmt) =
1981 742547 : pop_stmt_list (SWITCH_STMT_BODY (switch_stmt));
1982 742547 : pop_switch ();
1983 :
1984 742547 : scope = SWITCH_STMT_SCOPE (switch_stmt);
1985 742547 : SWITCH_STMT_SCOPE (switch_stmt) = NULL;
1986 742547 : add_stmt (do_poplevel (scope));
1987 742547 : }
1988 :
1989 : /* Begin a try-block. Returns a newly-created TRY_BLOCK if
1990 : appropriate. */
1991 :
1992 : tree
1993 1216900 : begin_try_block (void)
1994 : {
1995 1216900 : tree r = build_stmt (input_location, TRY_BLOCK, NULL_TREE, NULL_TREE);
1996 1216900 : add_stmt (r);
1997 1216900 : TRY_STMTS (r) = push_stmt_list ();
1998 1216900 : return r;
1999 : }
2000 :
2001 : /* Likewise, for a function-try-block. The block returned in
2002 : *COMPOUND_STMT is an artificial outer scope, containing the
2003 : function-try-block. */
2004 :
2005 : tree
2006 2241 : begin_function_try_block (tree *compound_stmt)
2007 : {
2008 2241 : tree r;
2009 : /* This outer scope does not exist in the C++ standard, but we need
2010 : a place to put __FUNCTION__ and similar variables. */
2011 2241 : *compound_stmt = begin_compound_stmt (0);
2012 2241 : current_binding_level->artificial = 1;
2013 2241 : r = begin_try_block ();
2014 2241 : FN_TRY_BLOCK_P (r) = 1;
2015 2241 : return r;
2016 : }
2017 :
2018 : /* Finish a try-block, which may be given by TRY_BLOCK. */
2019 :
2020 : void
2021 1216900 : finish_try_block (tree try_block)
2022 : {
2023 1216900 : TRY_STMTS (try_block) = pop_stmt_list (TRY_STMTS (try_block));
2024 1216900 : TRY_HANDLERS (try_block) = push_stmt_list ();
2025 1216900 : }
2026 :
2027 : /* Finish the body of a cleanup try-block, which may be given by
2028 : TRY_BLOCK. */
2029 :
2030 : void
2031 0 : finish_cleanup_try_block (tree try_block)
2032 : {
2033 0 : TRY_STMTS (try_block) = pop_stmt_list (TRY_STMTS (try_block));
2034 0 : }
2035 :
2036 : /* Finish an implicitly generated try-block, with a cleanup is given
2037 : by CLEANUP. */
2038 :
2039 : void
2040 0 : finish_cleanup (tree cleanup, tree try_block)
2041 : {
2042 0 : TRY_HANDLERS (try_block) = cleanup;
2043 0 : CLEANUP_P (try_block) = 1;
2044 0 : }
2045 :
2046 : /* Likewise, for a function-try-block. */
2047 :
2048 : void
2049 2241 : finish_function_try_block (tree try_block)
2050 : {
2051 2241 : finish_try_block (try_block);
2052 : /* FIXME : something queer about CTOR_INITIALIZER somehow following
2053 : the try block, but moving it inside. */
2054 2241 : in_function_try_handler = 1;
2055 2241 : }
2056 :
2057 : /* Finish a handler-sequence for a try-block, which may be given by
2058 : TRY_BLOCK. */
2059 :
2060 : void
2061 1216900 : finish_handler_sequence (tree try_block)
2062 : {
2063 1216900 : TRY_HANDLERS (try_block) = pop_stmt_list (TRY_HANDLERS (try_block));
2064 1216900 : check_handlers (TRY_HANDLERS (try_block));
2065 1216900 : }
2066 :
2067 : /* Finish the handler-seq for a function-try-block, given by
2068 : TRY_BLOCK. COMPOUND_STMT is the outer block created by
2069 : begin_function_try_block. */
2070 :
2071 : void
2072 2241 : finish_function_handler_sequence (tree try_block, tree compound_stmt)
2073 : {
2074 2241 : in_function_try_handler = 0;
2075 2241 : finish_handler_sequence (try_block);
2076 2241 : finish_compound_stmt (compound_stmt);
2077 2241 : }
2078 :
2079 : /* Begin a handler. Returns a HANDLER if appropriate. */
2080 :
2081 : tree
2082 1697321 : begin_handler (void)
2083 : {
2084 1697321 : tree r;
2085 :
2086 1697321 : r = build_stmt (input_location, HANDLER, NULL_TREE, NULL_TREE);
2087 1697321 : add_stmt (r);
2088 :
2089 : /* Create a binding level for the eh_info and the exception object
2090 : cleanup. */
2091 1697321 : HANDLER_BODY (r) = do_pushlevel (sk_catch);
2092 :
2093 1697321 : return r;
2094 : }
2095 :
2096 : /* Finish the handler-parameters for a handler, which may be given by
2097 : HANDLER. DECL is the declaration for the catch parameter, or NULL
2098 : if this is a `catch (...)' clause. */
2099 :
2100 : void
2101 1697321 : finish_handler_parms (tree decl, tree handler)
2102 : {
2103 1697321 : tree type = NULL_TREE;
2104 1697321 : if (processing_template_decl)
2105 : {
2106 1550052 : if (decl)
2107 : {
2108 504179 : decl = pushdecl (decl);
2109 504179 : decl = push_template_decl (decl);
2110 504179 : HANDLER_PARMS (handler) = decl;
2111 504179 : type = TREE_TYPE (decl);
2112 : }
2113 : }
2114 : else
2115 : {
2116 147269 : type = expand_start_catch_block (decl);
2117 147269 : if (warn_catch_value
2118 2116 : && type != NULL_TREE
2119 711 : && type != error_mark_node
2120 147980 : && !TYPE_REF_P (TREE_TYPE (decl)))
2121 : {
2122 210 : tree orig_type = TREE_TYPE (decl);
2123 210 : if (CLASS_TYPE_P (orig_type))
2124 : {
2125 96 : if (TYPE_POLYMORPHIC_P (orig_type))
2126 48 : warning_at (DECL_SOURCE_LOCATION (decl),
2127 48 : OPT_Wcatch_value_,
2128 : "catching polymorphic type %q#T by value",
2129 : orig_type);
2130 48 : else if (warn_catch_value > 1)
2131 36 : warning_at (DECL_SOURCE_LOCATION (decl),
2132 36 : OPT_Wcatch_value_,
2133 : "catching type %q#T by value", orig_type);
2134 : }
2135 114 : else if (warn_catch_value > 2)
2136 54 : warning_at (DECL_SOURCE_LOCATION (decl),
2137 54 : OPT_Wcatch_value_,
2138 : "catching non-reference type %q#T", orig_type);
2139 : }
2140 : }
2141 1697321 : HANDLER_TYPE (handler) = type;
2142 1697321 : }
2143 :
2144 : /* Finish a handler, which may be given by HANDLER. The BLOCKs are
2145 : the return value from the matching call to finish_handler_parms. */
2146 :
2147 : void
2148 1697321 : finish_handler (tree handler)
2149 : {
2150 1697321 : if (!processing_template_decl)
2151 147269 : expand_end_catch_block ();
2152 1697321 : HANDLER_BODY (handler) = do_poplevel (HANDLER_BODY (handler));
2153 1697321 : }
2154 :
2155 : /* Begin a compound statement. FLAGS contains some bits that control the
2156 : behavior and context. If BCS_NO_SCOPE is set, the compound statement
2157 : does not define a scope. If BCS_FN_BODY is set, this is the outermost
2158 : block of a function. If BCS_TRY_BLOCK is set, this is the block
2159 : created on behalf of a TRY statement. Returns a token to be passed to
2160 : finish_compound_stmt. */
2161 :
2162 : tree
2163 296886937 : begin_compound_stmt (unsigned int flags)
2164 : {
2165 296886937 : tree r;
2166 :
2167 296886937 : if (flags & BCS_NO_SCOPE)
2168 : {
2169 5672316 : r = push_stmt_list ();
2170 5672316 : STATEMENT_LIST_NO_SCOPE (r) = 1;
2171 :
2172 : /* Normally, we try hard to keep the BLOCK for a statement-expression.
2173 : But, if it's a statement-expression with a scopeless block, there's
2174 : nothing to keep, and we don't want to accidentally keep a block
2175 : *inside* the scopeless block. */
2176 5672316 : keep_next_level (false);
2177 : }
2178 : else
2179 : {
2180 291214621 : scope_kind sk = sk_block;
2181 291214621 : if (flags & BCS_TRY_BLOCK)
2182 : sk = sk_try;
2183 289997973 : else if (flags & BCS_TRANSACTION)
2184 : sk = sk_transaction;
2185 289997738 : else if (flags & BCS_STMT_EXPR)
2186 29154 : sk = sk_stmt_expr;
2187 291214621 : r = do_pushlevel (sk);
2188 : }
2189 :
2190 : /* When processing a template, we need to remember where the braces were,
2191 : so that we can set up identical scopes when instantiating the template
2192 : later. BIND_EXPR is a handy candidate for this.
2193 : Note that do_poplevel won't create a BIND_EXPR itself here (and thus
2194 : result in nested BIND_EXPRs), since we don't build BLOCK nodes when
2195 : processing templates. */
2196 296886937 : if (processing_template_decl)
2197 : {
2198 199230374 : r = build3 (BIND_EXPR, NULL, NULL, r, NULL);
2199 199230374 : BIND_EXPR_TRY_BLOCK (r) = (flags & BCS_TRY_BLOCK) != 0;
2200 199230374 : BIND_EXPR_BODY_BLOCK (r) = (flags & BCS_FN_BODY) != 0;
2201 199230374 : TREE_SIDE_EFFECTS (r) = 1;
2202 : }
2203 :
2204 296886937 : return r;
2205 : }
2206 :
2207 : /* Finish a compound-statement, which is given by STMT. */
2208 :
2209 : void
2210 296886898 : finish_compound_stmt (tree stmt)
2211 : {
2212 296886898 : if (TREE_CODE (stmt) == BIND_EXPR)
2213 : {
2214 199230374 : tree body = do_poplevel (BIND_EXPR_BODY (stmt));
2215 : /* If the STATEMENT_LIST is empty and this BIND_EXPR isn't special,
2216 : discard the BIND_EXPR so it can be merged with the containing
2217 : STATEMENT_LIST. */
2218 199230374 : if (TREE_CODE (body) == STATEMENT_LIST
2219 181186413 : && STATEMENT_LIST_HEAD (body) == NULL
2220 12034718 : && !BIND_EXPR_BODY_BLOCK (stmt)
2221 210739569 : && !BIND_EXPR_TRY_BLOCK (stmt))
2222 : stmt = body;
2223 : else
2224 187721276 : BIND_EXPR_BODY (stmt) = body;
2225 : }
2226 97656524 : else if (STATEMENT_LIST_NO_SCOPE (stmt))
2227 5634286 : stmt = pop_stmt_list (stmt);
2228 : else
2229 : {
2230 : /* Destroy any ObjC "super" receivers that may have been
2231 : created. */
2232 92022238 : objc_clear_super_receiver ();
2233 :
2234 92022238 : stmt = do_poplevel (stmt);
2235 : }
2236 :
2237 : /* ??? See c_end_compound_stmt wrt statement expressions. */
2238 296886898 : add_stmt (stmt);
2239 296886898 : }
2240 :
2241 : /* Finish an asm string literal, which can be a string literal
2242 : or parenthesized constant expression. Extract the string literal
2243 : from the latter. */
2244 :
2245 : tree
2246 54987 : finish_asm_string_expression (location_t loc, tree string)
2247 : {
2248 54987 : if (string == error_mark_node
2249 54974 : || TREE_CODE (string) == STRING_CST
2250 883 : || processing_template_decl)
2251 : return string;
2252 576 : string = cxx_constant_value (string, tf_error);
2253 576 : if (TREE_CODE (string) == STRING_CST)
2254 10 : string = build1_loc (loc, PAREN_EXPR, TREE_TYPE (string),
2255 : string);
2256 576 : cexpr_str cstr (string);
2257 576 : if (!cstr.type_check (loc))
2258 171 : return error_mark_node;
2259 405 : if (!cstr.extract (loc, string))
2260 62 : string = error_mark_node;
2261 405 : return string;
2262 576 : }
2263 :
2264 : /* Finish an asm-statement, whose components are a STRING, some
2265 : OUTPUT_OPERANDS, some INPUT_OPERANDS, some CLOBBERS and some
2266 : LABELS. Also note whether the asm-statement should be
2267 : considered volatile, and whether it is asm inline. TOPLEV_P
2268 : is true if finishing namespace scope extended asm. */
2269 :
2270 : tree
2271 32730 : finish_asm_stmt (location_t loc, int volatile_p, tree string,
2272 : tree output_operands, tree input_operands, tree clobbers,
2273 : tree labels, bool inline_p, bool toplev_p)
2274 : {
2275 32730 : tree r;
2276 32730 : tree t;
2277 32730 : int ninputs = list_length (input_operands);
2278 32730 : int noutputs = list_length (output_operands);
2279 :
2280 32730 : if (!processing_template_decl)
2281 : {
2282 12752 : const char *constraint;
2283 12752 : const char **oconstraints;
2284 12752 : bool allows_mem, allows_reg, is_inout;
2285 12752 : tree operand;
2286 12752 : int i;
2287 :
2288 12752 : oconstraints = XALLOCAVEC (const char *, noutputs);
2289 :
2290 25402 : string = finish_asm_string_expression (cp_expr_loc_or_loc (string, loc),
2291 : string);
2292 12752 : if (string == error_mark_node)
2293 109 : return error_mark_node;
2294 37974 : for (int i = 0; i < 2; ++i)
2295 61519 : for (t = i ? input_operands : output_operands; t; t = TREE_CHAIN (t))
2296 : {
2297 36218 : tree s = TREE_VALUE (TREE_PURPOSE (t));
2298 72418 : s = finish_asm_string_expression (cp_expr_loc_or_loc (s, loc), s);
2299 36218 : if (s == error_mark_node)
2300 : return error_mark_node;
2301 36188 : TREE_VALUE (TREE_PURPOSE (t)) = s;
2302 : }
2303 18060 : for (t = clobbers; t; t = TREE_CHAIN (t))
2304 : {
2305 5417 : tree s = TREE_VALUE (t);
2306 10828 : s = finish_asm_string_expression (cp_expr_loc_or_loc (s, loc), s);
2307 5417 : TREE_VALUE (t) = s;
2308 : }
2309 :
2310 12643 : string = resolve_asm_operand_names (string, output_operands,
2311 : input_operands, labels);
2312 :
2313 44198 : for (i = 0, t = output_operands; t; t = TREE_CHAIN (t), ++i)
2314 : {
2315 18912 : operand = TREE_VALUE (t);
2316 :
2317 : /* ??? Really, this should not be here. Users should be using a
2318 : proper lvalue, dammit. But there's a long history of using
2319 : casts in the output operands. In cases like longlong.h, this
2320 : becomes a primitive form of typechecking -- if the cast can be
2321 : removed, then the output operand had a type of the proper width;
2322 : otherwise we'll get an error. Gross, but ... */
2323 18912 : STRIP_NOPS (operand);
2324 :
2325 18912 : operand = mark_lvalue_use (operand);
2326 :
2327 18912 : if (!lvalue_or_else (operand, lv_asm, tf_warning_or_error))
2328 9 : operand = error_mark_node;
2329 :
2330 18912 : if (operand != error_mark_node
2331 18912 : && (TREE_READONLY (operand)
2332 18897 : || CP_TYPE_CONST_P (TREE_TYPE (operand))
2333 : /* Functions are not modifiable, even though they are
2334 : lvalues. */
2335 18897 : || FUNC_OR_METHOD_TYPE_P (TREE_TYPE (operand))
2336 : /* If it's an aggregate and any field is const, then it is
2337 : effectively const. */
2338 18897 : || (CLASS_TYPE_P (TREE_TYPE (operand))
2339 426 : && C_TYPE_FIELDS_READONLY (TREE_TYPE (operand)))))
2340 6 : cxx_readonly_error (loc, operand, lv_asm);
2341 :
2342 18912 : tree *op = &operand;
2343 18919 : while (TREE_CODE (*op) == COMPOUND_EXPR)
2344 7 : op = &TREE_OPERAND (*op, 1);
2345 18912 : switch (TREE_CODE (*op))
2346 : {
2347 30 : case PREINCREMENT_EXPR:
2348 30 : case PREDECREMENT_EXPR:
2349 30 : case MODIFY_EXPR:
2350 30 : *op = genericize_compound_lvalue (*op);
2351 30 : op = &TREE_OPERAND (*op, 1);
2352 30 : break;
2353 : default:
2354 : break;
2355 : }
2356 :
2357 18912 : constraint = TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (t)));
2358 18912 : oconstraints[i] = constraint;
2359 :
2360 18912 : if (parse_output_constraint (&constraint, i, ninputs, noutputs,
2361 : &allows_mem, &allows_reg, &is_inout,
2362 : nullptr))
2363 : {
2364 : /* If the operand is going to end up in memory,
2365 : mark it addressable. */
2366 18903 : if (!allows_reg && !cxx_mark_addressable (*op))
2367 0 : operand = error_mark_node;
2368 18903 : if (allows_reg && toplev_p)
2369 : {
2370 3 : error_at (loc, "constraint allows registers outside of "
2371 : "a function");
2372 3 : operand = error_mark_node;
2373 : }
2374 : }
2375 : else
2376 9 : operand = error_mark_node;
2377 :
2378 715 : if (toplev_p && operand != error_mark_node)
2379 : {
2380 21 : if (TREE_SIDE_EFFECTS (operand))
2381 : {
2382 0 : error_at (loc, "side-effects in output operand outside "
2383 : "of a function");
2384 0 : operand = error_mark_node;
2385 : }
2386 : else
2387 : {
2388 21 : tree addr
2389 21 : = cp_build_addr_expr (operand, tf_warning_or_error);
2390 21 : if (addr == error_mark_node)
2391 0 : operand = error_mark_node;
2392 : else
2393 : {
2394 21 : addr = maybe_constant_value (addr);
2395 21 : if (!initializer_constant_valid_p (addr,
2396 21 : TREE_TYPE (addr)))
2397 : {
2398 3 : error_at (loc, "output operand outside of a "
2399 : "function is not constant");
2400 3 : operand = error_mark_node;
2401 : }
2402 : else
2403 18 : operand = build_fold_indirect_ref (addr);
2404 : }
2405 : }
2406 : }
2407 18891 : else if (operand != error_mark_node && strstr (constraint, "-"))
2408 : {
2409 3 : error_at (loc, "%<-%> modifier used inside of a function");
2410 3 : operand = error_mark_node;
2411 : }
2412 :
2413 18912 : TREE_VALUE (t) = operand;
2414 : }
2415 :
2416 29914 : for (i = 0, t = input_operands; t; ++i, t = TREE_CHAIN (t))
2417 : {
2418 17271 : constraint = TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (t)));
2419 17271 : bool constraint_parsed
2420 17271 : = parse_input_constraint (&constraint, i, ninputs, noutputs, 0,
2421 : oconstraints, &allows_mem, &allows_reg,
2422 : nullptr);
2423 : /* If the operand is going to end up in memory, don't call
2424 : decay_conversion. */
2425 17271 : if (constraint_parsed && !allows_reg && allows_mem)
2426 574 : operand = mark_lvalue_use (TREE_VALUE (t));
2427 : else
2428 16697 : operand = decay_conversion (TREE_VALUE (t), tf_warning_or_error);
2429 :
2430 : /* If the type of the operand hasn't been determined (e.g.,
2431 : because it involves an overloaded function), then issue
2432 : an error message. There's no context available to
2433 : resolve the overloading. */
2434 17271 : if (TREE_TYPE (operand) == unknown_type_node)
2435 : {
2436 3 : error_at (loc,
2437 : "type of %<asm%> operand %qE could not be determined",
2438 3 : TREE_VALUE (t));
2439 3 : operand = error_mark_node;
2440 : }
2441 :
2442 17271 : if (constraint_parsed)
2443 : {
2444 : /* If the operand is going to end up in memory,
2445 : mark it addressable. */
2446 17250 : if (!allows_reg && allows_mem)
2447 : {
2448 : /* Strip the nops as we allow this case. FIXME, this really
2449 : should be rejected or made deprecated. */
2450 574 : STRIP_NOPS (operand);
2451 :
2452 574 : tree *op = &operand;
2453 581 : while (TREE_CODE (*op) == COMPOUND_EXPR)
2454 7 : op = &TREE_OPERAND (*op, 1);
2455 574 : switch (TREE_CODE (*op))
2456 : {
2457 27 : case PREINCREMENT_EXPR:
2458 27 : case PREDECREMENT_EXPR:
2459 27 : case MODIFY_EXPR:
2460 27 : *op = genericize_compound_lvalue (*op);
2461 27 : op = &TREE_OPERAND (*op, 1);
2462 27 : break;
2463 : default:
2464 : break;
2465 : }
2466 :
2467 574 : if (!cxx_mark_addressable (*op))
2468 0 : operand = error_mark_node;
2469 : }
2470 16676 : else if (!allows_reg && !allows_mem)
2471 : {
2472 : /* If constraint allows neither register nor memory,
2473 : try harder to get a constant. */
2474 465 : tree constop = maybe_constant_value (operand);
2475 465 : if (TREE_CONSTANT (constop))
2476 438 : operand = constop;
2477 : }
2478 17250 : if (allows_reg && toplev_p)
2479 : {
2480 3 : error_at (loc, "constraint allows registers outside of "
2481 : "a function");
2482 3 : operand = error_mark_node;
2483 : }
2484 17250 : if (constraint[0] == ':' && operand != error_mark_node)
2485 : {
2486 48 : tree t = operand;
2487 48 : STRIP_NOPS (t);
2488 48 : if (TREE_CODE (t) != ADDR_EXPR
2489 48 : || !(TREE_CODE (TREE_OPERAND (t, 0)) == FUNCTION_DECL
2490 30 : || (VAR_P (TREE_OPERAND (t, 0))
2491 24 : && is_global_var (TREE_OPERAND (t, 0)))))
2492 : {
2493 15 : error_at (loc, "%<:%> constraint operand is not address "
2494 : "of a function or non-automatic variable");
2495 15 : operand = error_mark_node;
2496 : }
2497 33 : else if (TREE_CODE (TREE_OPERAND (t, 0)) == FUNCTION_DECL)
2498 12 : suppress_warning (TREE_OPERAND (t, 0), OPT_Wunused);
2499 : }
2500 : }
2501 : else
2502 21 : operand = error_mark_node;
2503 :
2504 17271 : if (toplev_p && operand != error_mark_node)
2505 : {
2506 117 : if (TREE_SIDE_EFFECTS (operand))
2507 : {
2508 6 : error_at (loc, "side-effects in input operand outside "
2509 : "of a function");
2510 6 : operand = error_mark_node;
2511 : }
2512 111 : else if (allows_mem && lvalue_or_else (operand, lv_asm, tf_none))
2513 : {
2514 21 : tree addr = cp_build_addr_expr (operand, tf_warning_or_error);
2515 21 : if (addr == error_mark_node)
2516 0 : operand = error_mark_node;
2517 : else
2518 : {
2519 21 : addr = maybe_constant_value (addr);
2520 21 : if (!initializer_constant_valid_p (addr,
2521 21 : TREE_TYPE (addr)))
2522 : {
2523 3 : error_at (loc, "input operand outside of a "
2524 : "function is not constant");
2525 3 : operand = error_mark_node;
2526 : }
2527 : else
2528 18 : operand = build_fold_indirect_ref (addr);
2529 : }
2530 : }
2531 : else
2532 : {
2533 90 : operand = maybe_constant_value (operand);
2534 90 : if (!initializer_constant_valid_p (operand,
2535 90 : TREE_TYPE (operand)))
2536 : {
2537 3 : error_at (loc, "input operand outside of a "
2538 : "function is not constant");
2539 3 : operand = error_mark_node;
2540 : }
2541 : }
2542 : }
2543 17154 : else if (operand != error_mark_node && strstr (constraint, "-"))
2544 : {
2545 9 : error_at (loc, "%<-%> modifier used inside of a function");
2546 9 : operand = error_mark_node;
2547 : }
2548 :
2549 17271 : TREE_VALUE (t) = operand;
2550 : }
2551 : }
2552 :
2553 32621 : r = build_stmt (loc, ASM_EXPR, string,
2554 : output_operands, input_operands,
2555 : clobbers, labels);
2556 32621 : ASM_VOLATILE_P (r) = volatile_p || noutputs == 0;
2557 32621 : ASM_INLINE_P (r) = inline_p;
2558 32621 : if (toplev_p)
2559 : {
2560 99 : symtab->finalize_toplevel_asm (r);
2561 99 : return r;
2562 : }
2563 32522 : r = maybe_cleanup_point_expr_void (r);
2564 32522 : return add_stmt (r);
2565 : }
2566 :
2567 : /* Finish a label with the indicated NAME. Returns the new label. */
2568 :
2569 : tree
2570 2539 : finish_label_stmt (tree name)
2571 : {
2572 2539 : tree decl = define_label (input_location, name);
2573 :
2574 2539 : if (decl == error_mark_node)
2575 : return error_mark_node;
2576 :
2577 2533 : add_stmt (build_stmt (input_location, LABEL_EXPR, decl));
2578 :
2579 2533 : return decl;
2580 : }
2581 :
2582 : /* Finish a series of declarations for local labels. G++ allows users
2583 : to declare "local" labels, i.e., labels with scope. This extension
2584 : is useful when writing code involving statement-expressions. */
2585 :
2586 : void
2587 219 : finish_label_decl (tree name)
2588 : {
2589 219 : if (!at_function_scope_p ())
2590 : {
2591 0 : error ("%<__label__%> declarations are only allowed in function scopes");
2592 0 : return;
2593 : }
2594 :
2595 219 : add_decl_expr (declare_local_label (name));
2596 : }
2597 :
2598 : /* When DECL goes out of scope, make sure that CLEANUP is executed. */
2599 :
2600 : void
2601 3641301 : finish_decl_cleanup (tree decl, tree cleanup)
2602 : {
2603 3641301 : push_cleanup (decl, cleanup, false);
2604 3641301 : }
2605 :
2606 : /* If the current scope exits with an exception, run CLEANUP. */
2607 :
2608 : void
2609 2293586 : finish_eh_cleanup (tree cleanup)
2610 : {
2611 2293586 : push_cleanup (NULL, cleanup, true);
2612 2293586 : }
2613 :
2614 : /* The MEM_INITS is a list of mem-initializers, in reverse of the
2615 : order they were written by the user. Each node is as for
2616 : emit_mem_initializers. */
2617 :
2618 : void
2619 21134319 : finish_mem_initializers (tree mem_inits)
2620 : {
2621 : /* Reorder the MEM_INITS so that they are in the order they appeared
2622 : in the source program. */
2623 21134319 : mem_inits = nreverse (mem_inits);
2624 :
2625 21134319 : if (processing_template_decl)
2626 : {
2627 : tree mem;
2628 :
2629 35743266 : for (mem = mem_inits; mem; mem = TREE_CHAIN (mem))
2630 : {
2631 : /* If the TREE_PURPOSE is a TYPE_PACK_EXPANSION, skip the
2632 : check for bare parameter packs in the TREE_VALUE, because
2633 : any parameter packs in the TREE_VALUE have already been
2634 : bound as part of the TREE_PURPOSE. See
2635 : make_pack_expansion for more information. */
2636 21148920 : if (TREE_CODE (TREE_PURPOSE (mem)) != TYPE_PACK_EXPANSION
2637 21148920 : && check_for_bare_parameter_packs (TREE_VALUE (mem)))
2638 3 : TREE_VALUE (mem) = error_mark_node;
2639 : }
2640 :
2641 14594346 : add_stmt (build_min_nt_loc (UNKNOWN_LOCATION,
2642 : CTOR_INITIALIZER, mem_inits));
2643 : }
2644 : else
2645 6539973 : emit_mem_initializers (mem_inits);
2646 21134319 : }
2647 :
2648 : /* Obfuscate EXPR if it looks like an id-expression or member access so
2649 : that the call to finish_decltype in do_auto_deduction will give the
2650 : right result. If EVEN_UNEVAL, do this even in unevaluated context. */
2651 :
2652 : tree
2653 46712852 : force_paren_expr (tree expr, bool even_uneval /* = false */)
2654 : {
2655 : /* This is only needed for decltype(auto) in C++14. */
2656 46712852 : if (cxx_dialect < cxx14)
2657 : return expr;
2658 :
2659 : /* If we're in unevaluated context, we can't be deducing a
2660 : return/initializer type, so we don't need to mess with this. */
2661 46065557 : if (cp_unevaluated_operand && !even_uneval)
2662 : return expr;
2663 :
2664 38292461 : if (TREE_CODE (expr) == COMPONENT_REF
2665 38230128 : || TREE_CODE (expr) == SCOPE_REF
2666 76515646 : || REFERENCE_REF_P (expr))
2667 628996 : REF_PARENTHESIZED_P (expr) = true;
2668 37663465 : else if (DECL_P (tree_strip_any_location_wrapper (expr)))
2669 : {
2670 1802381 : location_t loc = cp_expr_location (expr);
2671 1802381 : const tree_code code = processing_template_decl ? PAREN_EXPR
2672 : : VIEW_CONVERT_EXPR;
2673 1802381 : expr = build1_loc (loc, code, TREE_TYPE (expr), expr);
2674 1802381 : REF_PARENTHESIZED_P (expr) = true;
2675 : }
2676 : return expr;
2677 : }
2678 :
2679 : /* If T is an id-expression obfuscated by force_paren_expr, undo the
2680 : obfuscation and return the underlying id-expression. Otherwise
2681 : return T. */
2682 :
2683 : tree
2684 1030726782 : maybe_undo_parenthesized_ref (tree t)
2685 : {
2686 1030726782 : if (cxx_dialect < cxx14)
2687 : return t;
2688 :
2689 1020525378 : if ((TREE_CODE (t) == PAREN_EXPR || TREE_CODE (t) == VIEW_CONVERT_EXPR)
2690 1131599289 : && REF_PARENTHESIZED_P (t))
2691 206401 : t = TREE_OPERAND (t, 0);
2692 :
2693 : return t;
2694 : }
2695 :
2696 : /* Finish a parenthesized expression EXPR. */
2697 :
2698 : cp_expr
2699 34766408 : finish_parenthesized_expr (cp_expr expr)
2700 : {
2701 34766408 : if (EXPR_P (expr))
2702 : {
2703 : /* This inhibits warnings in maybe_warn_unparenthesized_assignment
2704 : and c_common_truthvalue_conversion. */
2705 69118062 : suppress_warning (STRIP_REFERENCE_REF (*expr), OPT_Wparentheses);
2706 : /* And maybe_warn_sizeof_array_div. */
2707 69118062 : suppress_warning (STRIP_REFERENCE_REF (*expr), OPT_Wsizeof_array_div);
2708 : }
2709 :
2710 34766408 : if (TREE_CODE (expr) == OFFSET_REF
2711 34766408 : || TREE_CODE (expr) == SCOPE_REF)
2712 : /* [expr.unary.op]/3 The qualified id of a pointer-to-member must not be
2713 : enclosed in parentheses. */
2714 31997 : PTRMEM_OK_P (expr) = 0;
2715 :
2716 34766408 : tree stripped_expr = tree_strip_any_location_wrapper (expr);
2717 34766408 : if (TREE_CODE (stripped_expr) == STRING_CST)
2718 904615 : PAREN_STRING_LITERAL_P (stripped_expr) = 1;
2719 33861793 : else if (TREE_CODE (stripped_expr) == PACK_INDEX_EXPR)
2720 1484 : PACK_INDEX_PARENTHESIZED_P (stripped_expr) = true;
2721 :
2722 34766408 : expr = cp_expr (force_paren_expr (expr), expr.get_location ());
2723 :
2724 34766408 : return expr;
2725 : }
2726 :
2727 : /* Finish a reference to a non-static data member (DECL) that is not
2728 : preceded by `.' or `->'. */
2729 :
2730 : tree
2731 80168611 : finish_non_static_data_member (tree decl, tree object, tree qualifying_scope,
2732 : tsubst_flags_t complain /* = tf_warning_or_error */)
2733 : {
2734 80168611 : gcc_assert (TREE_CODE (decl) == FIELD_DECL);
2735 80168611 : bool try_omp_private = !object && omp_private_member_map;
2736 69635445 : tree ret;
2737 :
2738 69635445 : if (!object)
2739 : {
2740 69635445 : tree scope = qualifying_scope;
2741 69635445 : if (scope == NULL_TREE)
2742 : {
2743 69623206 : scope = context_for_name_lookup (decl);
2744 69623206 : if (!TYPE_P (scope))
2745 : {
2746 : /* Can happen during error recovery (c++/85014). */
2747 3 : gcc_assert (seen_error ());
2748 3 : return error_mark_node;
2749 : }
2750 : }
2751 69635442 : object = maybe_dummy_object (scope, NULL);
2752 : }
2753 :
2754 80168608 : object = maybe_resolve_dummy (object, true);
2755 80168608 : if (object == error_mark_node)
2756 : return error_mark_node;
2757 :
2758 : /* DR 613/850: Can use non-static data members without an associated
2759 : object in sizeof/decltype/alignof. */
2760 80168605 : if (is_dummy_object (object)
2761 36362 : && !cp_unevaluated_operand
2762 80168711 : && (!processing_template_decl || !current_class_ref))
2763 : {
2764 91 : if (complain & tf_error)
2765 : {
2766 74 : auto_diagnostic_group d;
2767 74 : if (current_function_decl
2768 74 : && DECL_STATIC_FUNCTION_P (current_function_decl))
2769 3 : error ("invalid use of member %qD in static member function", decl);
2770 71 : else if (current_function_decl
2771 63 : && processing_contract_condition
2772 71 : && DECL_CONSTRUCTOR_P (current_function_decl))
2773 0 : error ("invalid use of member %qD in constructor %<pre%> contract", decl);
2774 71 : else if (current_function_decl
2775 63 : && processing_contract_condition
2776 71 : && DECL_DESTRUCTOR_P (current_function_decl))
2777 0 : error ("invalid use of member %qD in destructor %<post%> contract", decl);
2778 : else
2779 71 : error ("invalid use of non-static data member %qD", decl);
2780 74 : inform (DECL_SOURCE_LOCATION (decl), "declared here");
2781 74 : }
2782 :
2783 91 : return error_mark_node;
2784 : }
2785 :
2786 80168514 : if (current_class_ptr)
2787 79835606 : TREE_USED (current_class_ptr) = 1;
2788 80168514 : if (processing_template_decl)
2789 : {
2790 63784687 : tree type = TREE_TYPE (decl);
2791 :
2792 63784687 : if (TYPE_REF_P (type))
2793 : /* Quals on the object don't matter. */;
2794 61348983 : else if (PACK_EXPANSION_P (type))
2795 : /* Don't bother trying to represent this. */
2796 : type = NULL_TREE;
2797 61345949 : else if (!TREE_TYPE (object) || WILDCARD_TYPE_P (TREE_TYPE (object)))
2798 : /* We don't know what the eventual quals will be, so punt until
2799 : instantiation time.
2800 :
2801 : This can happen when called from build_capture_proxy for an explicit
2802 : object lambda. It's a bit marginal to call this function in that
2803 : case, since this function is for references to members of 'this',
2804 : but the deduced type is required to be derived from the closure
2805 : type, so it works. */
2806 : type = NULL_TREE;
2807 : else
2808 : {
2809 : /* Set the cv qualifiers. */
2810 61341371 : int quals = cp_type_quals (TREE_TYPE (object));
2811 :
2812 61341371 : if (DECL_MUTABLE_P (decl))
2813 245442 : quals &= ~TYPE_QUAL_CONST;
2814 :
2815 61341371 : quals |= cp_type_quals (TREE_TYPE (decl));
2816 61341371 : type = cp_build_qualified_type (type, quals);
2817 : }
2818 :
2819 63784687 : if (qualifying_scope)
2820 : /* Wrap this in a SCOPE_REF for now. */
2821 9561 : ret = build_qualified_name (type, qualifying_scope, decl,
2822 : /*template_p=*/false);
2823 : else
2824 63775126 : ret = (convert_from_reference
2825 63775126 : (build_min (COMPONENT_REF, type, object, decl, NULL_TREE)));
2826 : }
2827 : /* If PROCESSING_TEMPLATE_DECL is nonzero here, then
2828 : QUALIFYING_SCOPE is also non-null. */
2829 : else
2830 : {
2831 16383827 : tree access_type = TREE_TYPE (object);
2832 :
2833 16383827 : if (!perform_or_defer_access_check (TYPE_BINFO (access_type), decl,
2834 : decl, complain))
2835 0 : return error_mark_node;
2836 :
2837 : /* If the data member was named `C::M', convert `*this' to `C'
2838 : first. */
2839 16383827 : if (qualifying_scope)
2840 : {
2841 2631 : tree binfo = NULL_TREE;
2842 2631 : object = build_scoped_ref (object, qualifying_scope,
2843 : &binfo);
2844 : }
2845 :
2846 16383827 : ret = build_class_member_access_expr (object, decl,
2847 : /*access_path=*/NULL_TREE,
2848 : /*preserve_reference=*/false,
2849 : complain);
2850 : }
2851 80168514 : if (try_omp_private)
2852 : {
2853 1671 : tree *v = omp_private_member_map->get (decl);
2854 1671 : if (v)
2855 1243 : ret = convert_from_reference (*v);
2856 : }
2857 : return ret;
2858 : }
2859 :
2860 : /* DECL was the declaration to which a qualified-id resolved. Issue
2861 : an error message if it is not accessible. If OBJECT_TYPE is
2862 : non-NULL, we have just seen `x->' or `x.' and OBJECT_TYPE is the
2863 : type of `*x', or `x', respectively. If the DECL was named as
2864 : `A::B' then NESTED_NAME_SPECIFIER is `A'. Return value is like
2865 : perform_access_checks above. */
2866 :
2867 : bool
2868 5029530093 : check_accessibility_of_qualified_id (tree decl,
2869 : tree object_type,
2870 : tree nested_name_specifier,
2871 : tsubst_flags_t complain)
2872 : {
2873 : /* If we're not checking, return immediately. */
2874 5029530093 : if (deferred_access_no_check)
2875 : return true;
2876 :
2877 : /* Determine the SCOPE of DECL. */
2878 5018094645 : tree scope = context_for_name_lookup (decl);
2879 : /* If the SCOPE is not a type, then DECL is not a member. */
2880 5018094645 : if (!TYPE_P (scope)
2881 : /* If SCOPE is dependent then we can't perform this access check now,
2882 : and since we'll perform this access check again after substitution
2883 : there's no need to explicitly defer it. */
2884 5018094645 : || dependent_type_p (scope))
2885 : return true;
2886 :
2887 480308824 : tree qualifying_type = NULL_TREE;
2888 : /* Compute the scope through which DECL is being accessed. */
2889 480308824 : if (object_type
2890 : /* OBJECT_TYPE might not be a class type; consider:
2891 :
2892 : class A { typedef int I; };
2893 : I *p;
2894 : p->A::I::~I();
2895 :
2896 : In this case, we will have "A::I" as the DECL, but "I" as the
2897 : OBJECT_TYPE. */
2898 102108 : && CLASS_TYPE_P (object_type)
2899 480410915 : && DERIVED_FROM_P (scope, object_type))
2900 : {
2901 : /* If we are processing a `->' or `.' expression, use the type of the
2902 : left-hand side. */
2903 102082 : if (tree open = currently_open_class (object_type))
2904 : qualifying_type = open;
2905 : else
2906 : qualifying_type = object_type;
2907 : }
2908 480206742 : else if (nested_name_specifier)
2909 : {
2910 : /* If the reference is to a non-static member of the
2911 : current class, treat it as if it were referenced through
2912 : `this'. */
2913 639961463 : if (DECL_NONSTATIC_MEMBER_P (decl)
2914 320033754 : && current_class_ptr)
2915 42147 : if (tree current = current_nonlambda_class_type ())
2916 : {
2917 42102 : if (dependent_type_p (current))
2918 : /* In general we can't know whether this access goes through
2919 : `this' until instantiation time. Punt now, or else we might
2920 : create a deferred access check that's not relative to `this'
2921 : when it ought to be. We'll check this access again after
2922 : substitution, e.g. from tsubst_qualified_id. */
2923 : return true;
2924 :
2925 4199 : if (DERIVED_FROM_P (scope, current))
2926 : qualifying_type = current;
2927 : }
2928 : /* Otherwise, use the type indicated by the
2929 : nested-name-specifier. */
2930 : if (!qualifying_type)
2931 : qualifying_type = nested_name_specifier;
2932 : }
2933 : else
2934 : /* Otherwise, the name must be from the current class or one of
2935 : its bases. */
2936 160226009 : qualifying_type = currently_open_derived_class (scope);
2937 :
2938 480206835 : if (qualifying_type
2939 : /* It is possible for qualifying type to be a TEMPLATE_TYPE_PARM
2940 : or similar in a default argument value. */
2941 480270921 : && CLASS_TYPE_P (qualifying_type))
2942 451858334 : return perform_or_defer_access_check (TYPE_BINFO (qualifying_type), decl,
2943 451858334 : decl, complain);
2944 :
2945 : return true;
2946 : }
2947 :
2948 : /* EXPR is the result of a qualified-id. The QUALIFYING_CLASS was the
2949 : class named to the left of the "::" operator. DONE is true if this
2950 : expression is a complete postfix-expression; it is false if this
2951 : expression is followed by '->', '[', '(', etc. ADDRESS_P is true
2952 : iff this expression is the operand of '&'. TEMPLATE_P is true iff
2953 : the qualified-id was of the form "A::template B". TEMPLATE_ARG_P
2954 : is true iff this qualified name appears as a template argument. */
2955 :
2956 : tree
2957 86648095 : finish_qualified_id_expr (tree qualifying_class,
2958 : tree expr,
2959 : bool done,
2960 : bool address_p,
2961 : bool template_p,
2962 : bool template_arg_p,
2963 : tsubst_flags_t complain)
2964 : {
2965 86648095 : gcc_assert (TYPE_P (qualifying_class));
2966 :
2967 86648095 : if (error_operand_p (expr))
2968 21 : return error_mark_node;
2969 :
2970 86648074 : if (DECL_P (expr)
2971 : /* Functions are marked after overload resolution; avoid redundant
2972 : warnings. */
2973 79325174 : && TREE_CODE (expr) != FUNCTION_DECL
2974 165973224 : && !mark_used (expr, complain))
2975 0 : return error_mark_node;
2976 :
2977 86648074 : if (template_p)
2978 : {
2979 264469 : if (TREE_CODE (expr) == UNBOUND_CLASS_TEMPLATE)
2980 : {
2981 : /* cp_parser_lookup_name thought we were looking for a type,
2982 : but we're actually looking for a declaration. */
2983 9 : qualifying_class = TYPE_CONTEXT (expr);
2984 9 : expr = TYPE_IDENTIFIER (expr);
2985 : }
2986 : else
2987 264460 : check_template_keyword (expr);
2988 : }
2989 :
2990 : /* If EXPR occurs as the operand of '&', use special handling that
2991 : permits a pointer-to-member. */
2992 86648074 : if (address_p && done
2993 164301 : && TREE_CODE (qualifying_class) != ENUMERAL_TYPE)
2994 : {
2995 164299 : if (TREE_CODE (expr) == SCOPE_REF)
2996 0 : expr = TREE_OPERAND (expr, 1);
2997 164299 : expr = build_offset_ref (qualifying_class, expr,
2998 : /*address_p=*/true, complain);
2999 164299 : return expr;
3000 : }
3001 :
3002 : /* No need to check access within an enum. */
3003 86483775 : if (TREE_CODE (qualifying_class) == ENUMERAL_TYPE
3004 3822890 : && TREE_CODE (expr) != IDENTIFIER_NODE)
3005 : return expr;
3006 :
3007 : /* Within the scope of a class, turn references to non-static
3008 : members into expression of the form "this->...". */
3009 82660888 : if (template_arg_p)
3010 : /* But, within a template argument, we do not want make the
3011 : transformation, as there is no "this" pointer. */
3012 : ;
3013 82658216 : else if (TREE_CODE (expr) == FIELD_DECL)
3014 : {
3015 12239 : push_deferring_access_checks (dk_no_check);
3016 12239 : expr = finish_non_static_data_member (expr, NULL_TREE,
3017 : qualifying_class, complain);
3018 12239 : pop_deferring_access_checks ();
3019 : }
3020 82645977 : else if (BASELINK_P (expr))
3021 : {
3022 : /* See if any of the functions are non-static members. */
3023 : /* If so, the expression may be relative to 'this'. */
3024 6832516 : if (!shared_member_p (expr)
3025 456266 : && current_class_ptr
3026 7288095 : && DERIVED_FROM_P (qualifying_class,
3027 : current_nonlambda_class_type ()))
3028 455265 : expr = (build_class_member_access_expr
3029 455265 : (maybe_dummy_object (qualifying_class, NULL),
3030 : expr,
3031 455265 : BASELINK_ACCESS_BINFO (expr),
3032 : /*preserve_reference=*/false,
3033 : complain));
3034 6377251 : else if (done)
3035 : /* The expression is a qualified name whose address is not
3036 : being taken. */
3037 3606 : expr = build_offset_ref (qualifying_class, expr, /*address_p=*/false,
3038 : complain);
3039 : }
3040 75813461 : else if (!template_p
3041 75599094 : && TREE_CODE (expr) == TEMPLATE_DECL
3042 75813545 : && !DECL_FUNCTION_TEMPLATE_P (expr))
3043 : {
3044 84 : if (complain & tf_error)
3045 5 : error ("%qE missing template arguments", expr);
3046 84 : return error_mark_node;
3047 : }
3048 : else
3049 : {
3050 : /* In a template, return a SCOPE_REF for most qualified-ids
3051 : so that we can check access at instantiation time. But if
3052 : we're looking at a member of the current instantiation, we
3053 : know we have access and building up the SCOPE_REF confuses
3054 : non-type template argument handling. */
3055 75813377 : if (processing_template_decl
3056 75813377 : && (!currently_open_class (qualifying_class)
3057 10690 : || TREE_CODE (expr) == IDENTIFIER_NODE
3058 10690 : || TREE_CODE (expr) == TEMPLATE_ID_EXPR
3059 82 : || TREE_CODE (expr) == BIT_NOT_EXPR))
3060 11175041 : expr = build_qualified_name (TREE_TYPE (expr),
3061 : qualifying_class, expr,
3062 : template_p);
3063 64638336 : else if (tree wrap = maybe_get_tls_wrapper_call (expr))
3064 9 : expr = wrap;
3065 :
3066 75813377 : expr = convert_from_reference (expr);
3067 : }
3068 :
3069 : return expr;
3070 : }
3071 :
3072 : /* Begin a statement-expression. The value returned must be passed to
3073 : finish_stmt_expr. */
3074 :
3075 : tree
3076 5693732 : begin_stmt_expr (void)
3077 : {
3078 5693732 : return push_stmt_list ();
3079 : }
3080 :
3081 : /* Process the final expression of a statement expression. EXPR can be
3082 : NULL, if the final expression is empty. Return a STATEMENT_LIST
3083 : containing all the statements in the statement-expression, or
3084 : ERROR_MARK_NODE if there was an error. */
3085 :
3086 : tree
3087 29117 : finish_stmt_expr_expr (tree expr, tree stmt_expr)
3088 : {
3089 29117 : if (error_operand_p (expr))
3090 : {
3091 : /* The type of the statement-expression is the type of the last
3092 : expression. */
3093 3 : TREE_TYPE (stmt_expr) = error_mark_node;
3094 3 : return error_mark_node;
3095 : }
3096 :
3097 : /* If the last statement does not have "void" type, then the value
3098 : of the last statement is the value of the entire expression. */
3099 29114 : if (expr)
3100 : {
3101 29099 : tree type = TREE_TYPE (expr);
3102 :
3103 29099 : if (type && type_unknown_p (type))
3104 : {
3105 15 : error ("a statement expression is an insufficient context"
3106 : " for overload resolution");
3107 15 : TREE_TYPE (stmt_expr) = error_mark_node;
3108 15 : return error_mark_node;
3109 : }
3110 29084 : else if (processing_template_decl)
3111 : {
3112 : /* Not finish_expr_stmt because we don't want convert_to_void. */
3113 169 : expr = build_stmt (input_location, EXPR_STMT, expr);
3114 169 : expr = add_stmt (expr);
3115 : /* Mark the last statement so that we can recognize it as such at
3116 : template-instantiation time. */
3117 169 : EXPR_STMT_STMT_EXPR_RESULT (expr) = 1;
3118 : }
3119 28915 : else if (VOID_TYPE_P (type))
3120 : {
3121 : /* Just treat this like an ordinary statement. */
3122 31 : expr = finish_expr_stmt (expr);
3123 : }
3124 : else
3125 : {
3126 : /* It actually has a value we need to deal with. First, force it
3127 : to be an rvalue so that we won't need to build up a copy
3128 : constructor call later when we try to assign it to something. */
3129 28884 : expr = force_rvalue (expr, tf_warning_or_error);
3130 28884 : if (error_operand_p (expr))
3131 0 : return error_mark_node;
3132 :
3133 : /* Update for array-to-pointer decay. */
3134 28884 : type = TREE_TYPE (expr);
3135 :
3136 : /* This TARGET_EXPR will initialize the outer one added by
3137 : finish_stmt_expr. */
3138 28884 : set_target_expr_eliding (expr);
3139 :
3140 : /* Wrap it in a CLEANUP_POINT_EXPR and add it to the list like a
3141 : normal statement, but don't convert to void or actually add
3142 : the EXPR_STMT. */
3143 28884 : if (TREE_CODE (expr) != CLEANUP_POINT_EXPR)
3144 28884 : expr = maybe_cleanup_point_expr (expr);
3145 28884 : add_stmt (expr);
3146 : }
3147 :
3148 : /* The type of the statement-expression is the type of the last
3149 : expression. */
3150 29084 : TREE_TYPE (stmt_expr) = type;
3151 : }
3152 :
3153 : return stmt_expr;
3154 : }
3155 :
3156 : /* Finish a statement-expression. EXPR should be the value returned
3157 : by the previous begin_stmt_expr. Returns an expression
3158 : representing the statement-expression. */
3159 :
3160 : tree
3161 5693732 : finish_stmt_expr (tree stmt_expr, bool has_no_scope)
3162 : {
3163 5693732 : tree type;
3164 5693732 : tree result;
3165 :
3166 5693732 : if (error_operand_p (stmt_expr))
3167 : {
3168 18 : pop_stmt_list (stmt_expr);
3169 18 : return error_mark_node;
3170 : }
3171 :
3172 5693714 : gcc_assert (TREE_CODE (stmt_expr) == STATEMENT_LIST);
3173 :
3174 5693714 : type = TREE_TYPE (stmt_expr);
3175 5693714 : result = pop_stmt_list (stmt_expr);
3176 5693714 : TREE_TYPE (result) = type;
3177 :
3178 5693714 : if (processing_template_decl)
3179 : {
3180 38223 : result = build_min (STMT_EXPR, type, result);
3181 38223 : TREE_SIDE_EFFECTS (result) = 1;
3182 38223 : STMT_EXPR_NO_SCOPE (result) = has_no_scope;
3183 : }
3184 5655491 : else if (CLASS_TYPE_P (type))
3185 : {
3186 : /* Wrap the statement-expression in a TARGET_EXPR so that the
3187 : temporary object created by the final expression is destroyed at
3188 : the end of the full-expression containing the
3189 : statement-expression. */
3190 118 : result = force_target_expr (type, result, tf_warning_or_error);
3191 : }
3192 :
3193 : return result;
3194 : }
3195 :
3196 : /* Returns the expression which provides the value of STMT_EXPR. */
3197 :
3198 : tree
3199 191 : stmt_expr_value_expr (tree stmt_expr)
3200 : {
3201 191 : tree t = STMT_EXPR_STMT (stmt_expr);
3202 :
3203 191 : if (TREE_CODE (t) == BIND_EXPR)
3204 191 : t = BIND_EXPR_BODY (t);
3205 :
3206 191 : if (TREE_CODE (t) == STATEMENT_LIST && STATEMENT_LIST_TAIL (t))
3207 158 : t = STATEMENT_LIST_TAIL (t)->stmt;
3208 :
3209 191 : if (TREE_CODE (t) == EXPR_STMT)
3210 173 : t = EXPR_STMT_EXPR (t);
3211 :
3212 191 : return t;
3213 : }
3214 :
3215 : /* Return TRUE iff EXPR_STMT is an empty list of
3216 : expression statements. */
3217 :
3218 : bool
3219 64358708 : empty_expr_stmt_p (tree expr_stmt)
3220 : {
3221 64358713 : tree body = NULL_TREE;
3222 :
3223 64358713 : if (expr_stmt == void_node)
3224 : return true;
3225 :
3226 64358710 : if (expr_stmt)
3227 : {
3228 64358710 : if (TREE_CODE (expr_stmt) == EXPR_STMT)
3229 5 : body = EXPR_STMT_EXPR (expr_stmt);
3230 64358705 : else if (TREE_CODE (expr_stmt) == STATEMENT_LIST)
3231 : body = expr_stmt;
3232 : }
3233 :
3234 5 : if (body)
3235 : {
3236 63366346 : if (TREE_CODE (body) == STATEMENT_LIST)
3237 63366341 : return tsi_end_p (tsi_start (body));
3238 : else
3239 : return empty_expr_stmt_p (body);
3240 : }
3241 : return false;
3242 : }
3243 :
3244 : /* Perform Koenig lookup. FN_EXPR is the postfix-expression representing
3245 : the function (or functions) to call; ARGS are the arguments to the
3246 : call. Returns the functions to be considered by overload resolution. */
3247 :
3248 : cp_expr
3249 19407498 : perform_koenig_lookup (cp_expr fn_expr, vec<tree, va_gc> *args,
3250 : tsubst_flags_t complain)
3251 : {
3252 19407498 : tree identifier = NULL_TREE;
3253 19407498 : tree functions = NULL_TREE;
3254 19407498 : tree tmpl_args = NULL_TREE;
3255 19407498 : bool template_id = false;
3256 19407498 : location_t loc = fn_expr.get_location ();
3257 19407498 : tree fn = fn_expr.get_value ();
3258 :
3259 19407498 : STRIP_ANY_LOCATION_WRAPPER (fn);
3260 :
3261 19407498 : if (TREE_CODE (fn) == TEMPLATE_ID_EXPR)
3262 : {
3263 : /* Use a separate flag to handle null args. */
3264 3733240 : template_id = true;
3265 3733240 : tmpl_args = TREE_OPERAND (fn, 1);
3266 3733240 : fn = TREE_OPERAND (fn, 0);
3267 : }
3268 :
3269 : /* Find the name of the overloaded function. */
3270 19407498 : if (identifier_p (fn))
3271 : identifier = fn;
3272 : else
3273 : {
3274 27425678 : functions = fn;
3275 19206643 : identifier = OVL_NAME (functions);
3276 : }
3277 :
3278 : /* A call to a namespace-scope function using an unqualified name.
3279 :
3280 : Do Koenig lookup -- unless any of the arguments are
3281 : type-dependent. */
3282 19407498 : if (!any_type_dependent_arguments_p (args)
3283 19407498 : && !any_dependent_template_arguments_p (tmpl_args))
3284 : {
3285 18528625 : fn = lookup_arg_dependent (identifier, functions, args);
3286 18528625 : if (!fn)
3287 : {
3288 : /* The unqualified name could not be resolved. */
3289 59595 : if (complain & tf_error)
3290 393 : fn = unqualified_fn_lookup_error (cp_expr (identifier, loc));
3291 : else
3292 : fn = identifier;
3293 : }
3294 : }
3295 :
3296 19407498 : if (fn && template_id && fn != error_mark_node)
3297 3733227 : fn = build2 (TEMPLATE_ID_EXPR, unknown_type_node, fn, tmpl_args);
3298 :
3299 19407498 : return cp_expr (fn, loc);
3300 : }
3301 :
3302 : /* Analyze call to a front-end builtin FN with arguments *ARGS. Return true
3303 : if the call is correct, false if erroneous. */
3304 :
3305 : static bool
3306 129356 : check_frontend_builtin (tree fn, vec<tree, va_gc> **args,
3307 : tsubst_flags_t complain)
3308 : {
3309 129356 : tree arg, ptype, type;
3310 129356 : switch (DECL_UNCHECKED_FUNCTION_CODE (fn))
3311 : {
3312 860 : case CP_BUILT_IN_IS_WITHIN_LIFETIME:
3313 860 : case CP_BUILT_IN_START_LIFETIME:
3314 : /* Unless users call the builtin directly, the following 2 checks
3315 : should be ensured from std::is_within_lifetime or
3316 : std::start_lifetime template. */
3317 860 : if (vec_safe_length (*args) != 1)
3318 : {
3319 14 : if (complain & tf_error)
3320 14 : error ("%qE needs a single argument", DECL_NAME (fn));
3321 : return false;
3322 : }
3323 846 : arg = (**args)[0];
3324 846 : if (error_operand_p (arg))
3325 : return false;
3326 846 : ptype = TREE_TYPE (arg);
3327 846 : if (!POINTER_TYPE_P (ptype))
3328 : {
3329 13 : if (complain & tf_error)
3330 13 : error ("%qE argument type %qT is not pointer type",
3331 13 : DECL_NAME (fn), ptype);
3332 : return false;
3333 : }
3334 833 : if (DECL_UNCHECKED_FUNCTION_CODE (fn) == CP_BUILT_IN_IS_WITHIN_LIFETIME)
3335 : return true;
3336 343 : type = TREE_TYPE (ptype);
3337 343 : if (!complete_type_or_maybe_complain (type, NULL_TREE, complain))
3338 : return false;
3339 343 : if (!CP_AGGREGATE_TYPE_P (type))
3340 : {
3341 10 : if (complain & tf_error)
3342 10 : error ("%qE argument type %qT is not a pointer to aggregate type",
3343 10 : DECL_NAME (fn), ptype);
3344 : return false;
3345 : }
3346 333 : if (!implicit_lifetime_type_p (type))
3347 : {
3348 4 : if (complain & tf_error)
3349 4 : error ("%qE argument type %qT is not a pointer to "
3350 4 : "implicit-lifetime type", DECL_NAME (fn), ptype);
3351 : return false;
3352 : }
3353 : return true;
3354 : default:
3355 : return true;
3356 : }
3357 : }
3358 :
3359 : /* Generate an expression for `FN (ARGS)'. This may change the
3360 : contents of ARGS.
3361 :
3362 : If DISALLOW_VIRTUAL is true, the call to FN will be not generated
3363 : as a virtual call, even if FN is virtual. (This flag is set when
3364 : encountering an expression where the function name is explicitly
3365 : qualified. For example a call to `X::f' never generates a virtual
3366 : call.)
3367 :
3368 : Returns code for the call. */
3369 :
3370 : tree
3371 377779906 : finish_call_expr (tree fn, vec<tree, va_gc> **args, bool disallow_virtual,
3372 : bool koenig_p, tsubst_flags_t complain)
3373 : {
3374 377779906 : tree result;
3375 377779906 : tree orig_fn;
3376 377779906 : vec<tree, va_gc> *orig_args = *args;
3377 377779906 : tsubst_flags_t orig_complain = complain;
3378 :
3379 377779906 : if (fn == error_mark_node)
3380 : return error_mark_node;
3381 :
3382 377778836 : complain &= ~tf_any_viable;
3383 377778836 : gcc_assert (!TYPE_P (fn));
3384 :
3385 : /* If FN may be a FUNCTION_DECL obfuscated by force_paren_expr, undo
3386 : it so that we can tell this is a call to a known function. */
3387 377778836 : fn = maybe_undo_parenthesized_ref (fn);
3388 :
3389 377778836 : STRIP_ANY_LOCATION_WRAPPER (fn);
3390 :
3391 377778836 : orig_fn = fn;
3392 :
3393 377778836 : if (concept_check_p (fn))
3394 : {
3395 6 : error_at (EXPR_LOC_OR_LOC (fn, input_location),
3396 : "cannot call a concept as a function");
3397 6 : return error_mark_node;
3398 : }
3399 :
3400 377778830 : if (processing_template_decl)
3401 : {
3402 : /* If FN is a local extern declaration (or set thereof) in a template,
3403 : look it up again at instantiation time. */
3404 243677032 : if (is_overloaded_fn (fn))
3405 : {
3406 149403109 : tree ifn = get_first_fn (fn);
3407 149403109 : if (TREE_CODE (ifn) == FUNCTION_DECL
3408 149403109 : && dependent_local_decl_p (ifn))
3409 41258 : orig_fn = DECL_NAME (ifn);
3410 : }
3411 :
3412 : /* If the call expression is dependent, build a CALL_EXPR node
3413 : with no type; type_dependent_expression_p recognizes
3414 : expressions with no type as being dependent. */
3415 243677032 : if (type_dependent_expression_p (fn)
3416 243677032 : || any_type_dependent_arguments_p (*args))
3417 : {
3418 221566457 : if (koenig_p
3419 10807865 : && TREE_CODE (orig_fn) == FUNCTION_DECL
3420 224962227 : && !fndecl_built_in_p (orig_fn))
3421 : /* For an ADL-enabled call where unqualified lookup found a
3422 : single non-template function, wrap it in an OVERLOAD so that
3423 : later substitution doesn't overeagerly mark the function as
3424 : used. */
3425 882270 : orig_fn = ovl_make (orig_fn, NULL_TREE);
3426 221566457 : result = build_min_nt_call_vec (orig_fn, *args);
3427 301168940 : SET_EXPR_LOCATION (result, cp_expr_loc_or_input_loc (fn));
3428 221566457 : KOENIG_LOOKUP_P (result) = koenig_p;
3429 : /* Disable the std::move warnings since this call was dependent
3430 : (c++/89780, c++/107363). This also suppresses the
3431 : -Wredundant-move warning. */
3432 221566457 : suppress_warning (result, OPT_Wpessimizing_move);
3433 :
3434 221566457 : if (cfun && cp_function_chain && !cp_unevaluated_operand)
3435 : {
3436 192965582 : bool abnormal = true;
3437 193252512 : for (lkp_iterator iter (maybe_get_fns (fn)); iter; ++iter)
3438 : {
3439 107152934 : tree fndecl = STRIP_TEMPLATE (*iter);
3440 107152934 : if (TREE_CODE (fndecl) != FUNCTION_DECL
3441 107152856 : || !TREE_THIS_VOLATILE (fndecl))
3442 : {
3443 : abnormal = false;
3444 : break;
3445 : }
3446 : }
3447 : /* FIXME: Stop warning about falling off end of non-void
3448 : function. But this is wrong. Even if we only see
3449 : no-return fns at this point, we could select a
3450 : future-defined return fn during instantiation. Or
3451 : vice-versa. */
3452 192965582 : if (abnormal)
3453 86099578 : current_function_returns_abnormally = 1;
3454 : }
3455 221566457 : if (TREE_CODE (fn) == COMPONENT_REF)
3456 102528050 : maybe_generic_this_capture (TREE_OPERAND (fn, 0),
3457 102528050 : TREE_OPERAND (fn, 1));
3458 : return result;
3459 : }
3460 22110575 : orig_args = make_tree_vector_copy (*args);
3461 : }
3462 :
3463 156212373 : if (TREE_CODE (fn) == COMPONENT_REF)
3464 : {
3465 29849723 : tree member = TREE_OPERAND (fn, 1);
3466 29849723 : if (BASELINK_P (member))
3467 : {
3468 29658922 : tree object = TREE_OPERAND (fn, 0);
3469 58901416 : return build_new_method_call (object, member,
3470 : args, NULL_TREE,
3471 : (disallow_virtual
3472 : ? LOOKUP_NORMAL | LOOKUP_NONVIRTUAL
3473 : : LOOKUP_NORMAL),
3474 : /*fn_p=*/NULL,
3475 29658922 : complain);
3476 : }
3477 : }
3478 :
3479 : /* Per 13.3.1.1, '(&f)(...)' is the same as '(f)(...)'. */
3480 126553451 : if (TREE_CODE (fn) == ADDR_EXPR
3481 126553451 : && TREE_CODE (TREE_OPERAND (fn, 0)) == OVERLOAD)
3482 9 : fn = TREE_OPERAND (fn, 0);
3483 :
3484 126553451 : if (is_overloaded_fn (fn))
3485 117593595 : fn = baselink_for_fns (fn);
3486 :
3487 126553451 : result = NULL_TREE;
3488 126553451 : if (BASELINK_P (fn))
3489 : {
3490 14369820 : tree object;
3491 :
3492 : /* A call to a member function. From [over.call.func]:
3493 :
3494 : If the keyword this is in scope and refers to the class of
3495 : that member function, or a derived class thereof, then the
3496 : function call is transformed into a qualified function call
3497 : using (*this) as the postfix-expression to the left of the
3498 : . operator.... [Otherwise] a contrived object of type T
3499 : becomes the implied object argument.
3500 :
3501 : In this situation:
3502 :
3503 : struct A { void f(); };
3504 : struct B : public A {};
3505 : struct C : public A { void g() { B::f(); }};
3506 :
3507 : "the class of that member function" refers to `A'. But 11.2
3508 : [class.access.base] says that we need to convert 'this' to B* as
3509 : part of the access, so we pass 'B' to maybe_dummy_object. */
3510 :
3511 14369820 : if (DECL_MAYBE_IN_CHARGE_CONSTRUCTOR_P (get_first_fn (fn)))
3512 : {
3513 : /* A constructor call always uses a dummy object. (This constructor
3514 : call which has the form A::A () is actually invalid and we are
3515 : going to reject it later in build_new_method_call.) */
3516 39 : object = build_dummy_object (BINFO_TYPE (BASELINK_ACCESS_BINFO (fn)));
3517 : }
3518 : else
3519 14369781 : object = maybe_dummy_object (BINFO_TYPE (BASELINK_ACCESS_BINFO (fn)),
3520 : NULL);
3521 :
3522 16405081 : result = build_new_method_call (object, fn, args, NULL_TREE,
3523 : (disallow_virtual
3524 : ? LOOKUP_NORMAL|LOOKUP_NONVIRTUAL
3525 : : LOOKUP_NORMAL),
3526 : /*fn_p=*/NULL,
3527 : complain);
3528 : }
3529 112183631 : else if (is_overloaded_fn (fn))
3530 : {
3531 : /* If the function is an overloaded builtin, resolve it. */
3532 103223775 : if (TREE_CODE (fn) == FUNCTION_DECL
3533 103223775 : && (DECL_BUILT_IN_CLASS (fn) == BUILT_IN_NORMAL
3534 19237900 : || DECL_BUILT_IN_CLASS (fn) == BUILT_IN_MD))
3535 9714398 : result = resolve_overloaded_builtin (input_location, fn, *args,
3536 : complain & tf_error);
3537 :
3538 9714398 : if (!result)
3539 : {
3540 102875735 : tree alloc_size_attr = NULL_TREE;
3541 102875735 : if (warn_calloc_transposed_args
3542 715404 : && TREE_CODE (fn) == FUNCTION_DECL
3543 102875735 : && (alloc_size_attr
3544 432781 : = lookup_attribute ("alloc_size",
3545 432781 : TYPE_ATTRIBUTES (TREE_TYPE (fn)))))
3546 3399 : if (TREE_VALUE (alloc_size_attr) == NULL_TREE
3547 3399 : || TREE_CHAIN (TREE_VALUE (alloc_size_attr)) == NULL_TREE)
3548 : alloc_size_attr = NULL_TREE;
3549 101133299 : if ((warn_sizeof_pointer_memaccess || alloc_size_attr)
3550 1742496 : && (complain & tf_warning)
3551 1521731 : && !vec_safe_is_empty (*args)
3552 104043449 : && !processing_template_decl)
3553 : {
3554 : location_t sizeof_arg_loc[6];
3555 : tree sizeof_arg[6];
3556 : unsigned int i;
3557 8390988 : for (i = 0; i < (alloc_size_attr ? 6 : 3); i++)
3558 : {
3559 3146823 : tree t;
3560 :
3561 3146823 : sizeof_arg_loc[i] = UNKNOWN_LOCATION;
3562 3146823 : sizeof_arg[i] = NULL_TREE;
3563 3146823 : if (i >= (*args)->length ())
3564 657495 : continue;
3565 2489328 : t = (**args)[i];
3566 2489328 : if (TREE_CODE (t) != SIZEOF_EXPR)
3567 2482653 : continue;
3568 6675 : if (SIZEOF_EXPR_TYPE_P (t))
3569 2663 : sizeof_arg[i] = TREE_TYPE (TREE_OPERAND (t, 0));
3570 : else
3571 4012 : sizeof_arg[i] = TREE_OPERAND (t, 0);
3572 6675 : sizeof_arg_loc[i] = EXPR_LOCATION (t);
3573 : }
3574 1048881 : if (warn_sizeof_pointer_memaccess)
3575 : {
3576 1048821 : auto same_p = same_type_ignoring_top_level_qualifiers_p;
3577 1048821 : sizeof_pointer_memaccess_warning (sizeof_arg_loc, fn, *args,
3578 : sizeof_arg, same_p);
3579 : }
3580 1048881 : if (alloc_size_attr)
3581 60 : warn_for_calloc (sizeof_arg_loc, fn, *args, sizeof_arg,
3582 : alloc_size_attr);
3583 : }
3584 :
3585 102875735 : if ((complain & tf_warning)
3586 56832323 : && TREE_CODE (fn) == FUNCTION_DECL
3587 27199795 : && fndecl_built_in_p (fn, BUILT_IN_MEMSET)
3588 148049 : && vec_safe_length (*args) == 3
3589 103023784 : && !any_type_dependent_arguments_p (*args))
3590 : {
3591 148049 : tree arg0 = (*orig_args)[0];
3592 148049 : tree arg1 = (*orig_args)[1];
3593 148049 : tree arg2 = (*orig_args)[2];
3594 148049 : int literal_mask = ((literal_integer_zerop (arg1) << 1)
3595 148049 : | (literal_integer_zerop (arg2) << 2));
3596 148049 : warn_for_memset (input_location, arg0, arg2, literal_mask);
3597 : }
3598 :
3599 102875735 : if (TREE_CODE (fn) == FUNCTION_DECL
3600 27327170 : && fndecl_built_in_p (fn, BUILT_IN_FRONTEND)
3601 103005091 : && !check_frontend_builtin (fn, args, complain))
3602 41 : return error_mark_node;
3603 :
3604 : /* A call to a namespace-scope function. */
3605 102875694 : result = build_new_function_call (fn, args, orig_complain);
3606 : }
3607 : }
3608 8959856 : else if (TREE_CODE (fn) == PSEUDO_DTOR_EXPR)
3609 : {
3610 162486 : if (!vec_safe_is_empty (*args))
3611 0 : error ("arguments to destructor are not allowed");
3612 : /* C++20/DR: If the postfix-expression names a pseudo-destructor (in
3613 : which case the postfix-expression is a possibly-parenthesized class
3614 : member access), the function call destroys the object of scalar type
3615 : denoted by the object expression of the class member access. */
3616 162486 : tree ob = TREE_OPERAND (fn, 0);
3617 162486 : if (obvalue_p (ob))
3618 162468 : result = build_trivial_dtor_call (ob, true);
3619 : else
3620 : /* No location to clobber. */
3621 18 : result = convert_to_void (ob, ICV_STATEMENT, complain);
3622 : }
3623 8797370 : else if (CLASS_TYPE_P (TREE_TYPE (fn)))
3624 : /* If the "function" is really an object of class type, it might
3625 : have an overloaded `operator ()'. */
3626 2650889 : result = build_op_call (fn, args, complain);
3627 :
3628 120045371 : if (!result)
3629 : /* A call where the function is unknown. */
3630 6146481 : result = cp_build_function_call_vec (fn, args, complain);
3631 :
3632 126539892 : if (processing_template_decl && result != error_mark_node)
3633 : {
3634 16933878 : if (INDIRECT_REF_P (result))
3635 1151197 : result = TREE_OPERAND (result, 0);
3636 :
3637 : /* Prune all but the selected function from the original overload
3638 : set so that we can avoid some duplicate work at instantiation time. */
3639 16933878 : if (TREE_CODE (result) == CALL_EXPR
3640 16924077 : && really_overloaded_fn (orig_fn))
3641 : {
3642 6245474 : tree sel_fn = CALL_EXPR_FN (result);
3643 6245474 : if (TREE_CODE (sel_fn) == COMPONENT_REF)
3644 : {
3645 : /* The non-dependent result of build_new_method_call. */
3646 263085 : sel_fn = TREE_OPERAND (sel_fn, 1);
3647 263085 : gcc_assert (BASELINK_P (sel_fn));
3648 : }
3649 5982389 : else if (TREE_CODE (sel_fn) == ADDR_EXPR)
3650 : /* Our original callee wasn't wrapped in an ADDR_EXPR,
3651 : so strip this ADDR_EXPR added by build_over_call. */
3652 5982389 : sel_fn = TREE_OPERAND (sel_fn, 0);
3653 : orig_fn = sel_fn;
3654 : }
3655 :
3656 16933878 : tree r = build_call_vec (TREE_TYPE (result), orig_fn, orig_args);
3657 16933878 : SET_EXPR_LOCATION (r, input_location);
3658 16933878 : KOENIG_LOOKUP_P (r) = koenig_p;
3659 16933878 : TREE_NO_WARNING (r) = TREE_NO_WARNING (result);
3660 16933878 : release_tree_vector (orig_args);
3661 16933878 : result = convert_from_reference (r);
3662 : }
3663 :
3664 : return result;
3665 : }
3666 :
3667 : /* Finish a call to a postfix increment or decrement or EXPR. (Which
3668 : is indicated by CODE, which should be POSTINCREMENT_EXPR or
3669 : POSTDECREMENT_EXPR.) */
3670 :
3671 : cp_expr
3672 2712096 : finish_increment_expr (cp_expr expr, enum tree_code code)
3673 : {
3674 : /* input_location holds the location of the trailing operator token.
3675 : Build a location of the form:
3676 : expr++
3677 : ~~~~^~
3678 : with the caret at the operator token, ranging from the start
3679 : of EXPR to the end of the operator token. */
3680 2712096 : location_t combined_loc = make_location (input_location,
3681 : expr.get_start (),
3682 : get_finish (input_location));
3683 2712096 : cp_expr result = build_x_unary_op (combined_loc, code, expr,
3684 2712096 : NULL_TREE, tf_warning_or_error);
3685 : /* TODO: build_x_unary_op doesn't honor the location, so set it here. */
3686 2712096 : result.set_location (combined_loc);
3687 2712096 : return result;
3688 : }
3689 :
3690 : /* Finish a use of `this'. Returns an expression for `this'. */
3691 :
3692 : tree
3693 37461379 : finish_this_expr (void)
3694 : {
3695 37461379 : tree result = NULL_TREE;
3696 :
3697 74922634 : if (current_class_ref && !LAMBDA_TYPE_P (TREE_TYPE (current_class_ref)))
3698 37159020 : result = current_class_ptr;
3699 604702 : else if (current_class_type && LAMBDA_TYPE_P (current_class_type))
3700 302283 : result = (lambda_expr_this_capture
3701 302283 : (CLASSTYPE_LAMBDA_EXPR (current_class_type), /*add*/true));
3702 : else
3703 76 : gcc_checking_assert (!current_class_ptr);
3704 :
3705 37461303 : if (result)
3706 : /* The keyword 'this' is a prvalue expression. */
3707 37461300 : return rvalue (result);
3708 :
3709 79 : tree fn = current_nonlambda_function ();
3710 79 : if (fn && DECL_XOBJ_MEMBER_FUNCTION_P (fn))
3711 : {
3712 6 : auto_diagnostic_group d;
3713 6 : error ("%<this%> is unavailable for explicit object member "
3714 : "functions");
3715 6 : tree xobj_parm = DECL_ARGUMENTS (fn);
3716 6 : gcc_assert (xobj_parm);
3717 6 : tree parm_name = DECL_NAME (xobj_parm);
3718 :
3719 6 : static tree remembered_fn = NULL_TREE;
3720 : /* Only output this diagnostic once per function. */
3721 6 : if (remembered_fn == fn)
3722 : /* Early escape. */;
3723 6 : else if (parm_name)
3724 6 : inform (DECL_SOURCE_LOCATION (xobj_parm),
3725 : "use explicit object parameter %qs instead",
3726 3 : IDENTIFIER_POINTER (parm_name));
3727 : else
3728 3 : inform (DECL_SOURCE_LOCATION (xobj_parm),
3729 : "name the explicit object parameter");
3730 :
3731 6 : remembered_fn = fn;
3732 6 : }
3733 73 : else if (fn && DECL_STATIC_FUNCTION_P (fn))
3734 3 : error ("%<this%> is unavailable for static member functions");
3735 70 : else if (fn && processing_contract_condition && DECL_CONSTRUCTOR_P (fn))
3736 0 : error ("invalid use of %<this%> in a constructor %<pre%> condition");
3737 70 : else if (fn && processing_contract_condition && DECL_DESTRUCTOR_P (fn))
3738 0 : error ("invalid use of %<this%> in a destructor %<post%> condition");
3739 70 : else if (fn)
3740 22 : error ("invalid use of %<this%> in non-member function");
3741 : else
3742 48 : error ("invalid use of %<this%> at top level");
3743 79 : return error_mark_node;
3744 : }
3745 :
3746 : /* Finish a pseudo-destructor expression. If SCOPE is NULL, the
3747 : expression was of the form `OBJECT.~DESTRUCTOR' where DESTRUCTOR is
3748 : the TYPE for the type given. If SCOPE is non-NULL, the expression
3749 : was of the form `OBJECT.SCOPE::~DESTRUCTOR'. */
3750 :
3751 : tree
3752 162537 : finish_pseudo_destructor_expr (tree object, tree scope, tree destructor,
3753 : location_t loc, tsubst_flags_t complain)
3754 : {
3755 162537 : if (object == error_mark_node || destructor == error_mark_node)
3756 : return error_mark_node;
3757 :
3758 162528 : gcc_assert (TYPE_P (destructor));
3759 :
3760 162528 : if (!processing_template_decl)
3761 : {
3762 162507 : if (scope == error_mark_node)
3763 : {
3764 0 : if (complain & tf_error)
3765 0 : error_at (loc, "invalid qualifying scope in pseudo-destructor name");
3766 0 : return error_mark_node;
3767 : }
3768 162507 : if (is_auto (destructor))
3769 3 : destructor = TREE_TYPE (object);
3770 162507 : if (scope && TYPE_P (scope) && !check_dtor_name (scope, destructor))
3771 : {
3772 3 : if (complain & tf_error)
3773 3 : error_at (loc,
3774 : "qualified type %qT does not match destructor name ~%qT",
3775 : scope, destructor);
3776 3 : return error_mark_node;
3777 : }
3778 :
3779 :
3780 : /* [expr.pseudo] says both:
3781 :
3782 : The type designated by the pseudo-destructor-name shall be
3783 : the same as the object type.
3784 :
3785 : and:
3786 :
3787 : The cv-unqualified versions of the object type and of the
3788 : type designated by the pseudo-destructor-name shall be the
3789 : same type.
3790 :
3791 : We implement the more generous second sentence, since that is
3792 : what most other compilers do. */
3793 162504 : if (!same_type_ignoring_top_level_qualifiers_p (TREE_TYPE (object),
3794 : destructor))
3795 : {
3796 12 : if (complain & tf_error)
3797 9 : error_at (loc, "%qE is not of type %qT", object, destructor);
3798 12 : return error_mark_node;
3799 : }
3800 : }
3801 :
3802 162513 : tree type = (type_dependent_expression_p (object)
3803 162513 : ? NULL_TREE : void_type_node);
3804 :
3805 162513 : return build3_loc (loc, PSEUDO_DTOR_EXPR, type, object,
3806 162513 : scope, destructor);
3807 : }
3808 :
3809 : /* Finish an expression of the form CODE EXPR. */
3810 :
3811 : cp_expr
3812 39786490 : finish_unary_op_expr (location_t op_loc, enum tree_code code, cp_expr expr,
3813 : tsubst_flags_t complain)
3814 : {
3815 : /* Build a location of the form:
3816 : ++expr
3817 : ^~~~~~
3818 : with the caret at the operator token, ranging from the start
3819 : of the operator token to the end of EXPR. */
3820 39786490 : location_t combined_loc = make_location (op_loc,
3821 : op_loc, expr.get_finish ());
3822 39786490 : cp_expr result = build_x_unary_op (combined_loc, code, expr,
3823 39786490 : NULL_TREE, complain);
3824 : /* TODO: build_x_unary_op doesn't always honor the location. */
3825 39786490 : result.set_location (combined_loc);
3826 :
3827 39786490 : if (result == error_mark_node)
3828 : return result;
3829 :
3830 39785987 : if (!(complain & tf_warning))
3831 : return result;
3832 :
3833 : /* These will never fold into a constant, so no need to check for
3834 : overflow for them. */
3835 39785987 : if (code == PREINCREMENT_EXPR || code == PREDECREMENT_EXPR)
3836 : return result;
3837 :
3838 21520441 : tree result_ovl = result;
3839 21520441 : tree expr_ovl = expr;
3840 :
3841 21520441 : if (!processing_template_decl)
3842 1876285 : expr_ovl = cp_fully_fold (expr_ovl);
3843 :
3844 21520441 : if (!CONSTANT_CLASS_P (expr_ovl)
3845 21520441 : || TREE_OVERFLOW_P (expr_ovl))
3846 : return result;
3847 :
3848 262246 : if (!processing_template_decl)
3849 252546 : result_ovl = cp_fully_fold (result_ovl);
3850 :
3851 262246 : if (CONSTANT_CLASS_P (result_ovl) && TREE_OVERFLOW_P (result_ovl))
3852 9 : overflow_warning (combined_loc, result_ovl);
3853 :
3854 : return result;
3855 : }
3856 :
3857 : /* Return true if CONSTRUCTOR EXPR after pack expansion could have no
3858 : elements. */
3859 :
3860 : static bool
3861 12 : maybe_zero_constructor_nelts (tree expr)
3862 : {
3863 12 : if (CONSTRUCTOR_NELTS (expr) == 0)
3864 : return true;
3865 12 : if (!processing_template_decl)
3866 : return false;
3867 30 : for (constructor_elt &elt : CONSTRUCTOR_ELTS (expr))
3868 21 : if (!PACK_EXPANSION_P (elt.value))
3869 : return false;
3870 : return true;
3871 : }
3872 :
3873 : /* Finish a compound-literal expression or C++11 functional cast with aggregate
3874 : initializer. TYPE is the type to which the CONSTRUCTOR in COMPOUND_LITERAL
3875 : is being cast. */
3876 :
3877 : tree
3878 10104874 : finish_compound_literal (tree type, tree compound_literal,
3879 : tsubst_flags_t complain,
3880 : fcl_t fcl_context)
3881 : {
3882 10104874 : if (type == error_mark_node)
3883 : return error_mark_node;
3884 :
3885 10104822 : if (TYPE_REF_P (type))
3886 : {
3887 12 : compound_literal
3888 12 : = finish_compound_literal (TREE_TYPE (type), compound_literal,
3889 : complain, fcl_context);
3890 : /* The prvalue is then used to direct-initialize the reference. */
3891 12 : tree r = (perform_implicit_conversion_flags
3892 12 : (type, compound_literal, complain, LOOKUP_NORMAL));
3893 12 : return convert_from_reference (r);
3894 : }
3895 :
3896 10104810 : if (!TYPE_OBJ_P (type))
3897 : {
3898 : /* DR2351 */
3899 60 : if (VOID_TYPE_P (type) && CONSTRUCTOR_NELTS (compound_literal) == 0)
3900 : {
3901 12 : if (!processing_template_decl)
3902 9 : return void_node;
3903 3 : TREE_TYPE (compound_literal) = type;
3904 3 : TREE_HAS_CONSTRUCTOR (compound_literal) = 1;
3905 3 : CONSTRUCTOR_IS_DEPENDENT (compound_literal) = 0;
3906 3 : return compound_literal;
3907 : }
3908 21 : else if (VOID_TYPE_P (type)
3909 15 : && processing_template_decl
3910 33 : && maybe_zero_constructor_nelts (compound_literal))
3911 : /* If there are only packs in compound_literal, it could
3912 : be void{} after pack expansion. */;
3913 : else
3914 : {
3915 12 : if (complain & tf_error)
3916 9 : error ("compound literal of non-object type %qT", type);
3917 12 : return error_mark_node;
3918 : }
3919 : }
3920 :
3921 10104786 : if (template_placeholder_p (type))
3922 : {
3923 195399 : type = do_auto_deduction (type, compound_literal, type, complain,
3924 : adc_variable_type);
3925 195399 : if (type == error_mark_node)
3926 : return error_mark_node;
3927 : }
3928 : /* C++23 auto{x}. */
3929 9909387 : else if (is_auto (type)
3930 162 : && !AUTO_IS_DECLTYPE (type)
3931 9909546 : && CONSTRUCTOR_NELTS (compound_literal) == 1)
3932 : {
3933 150 : if (is_constrained_auto (type))
3934 : {
3935 3 : if (complain & tf_error)
3936 3 : error ("%<auto{x}%> cannot be constrained");
3937 3 : return error_mark_node;
3938 : }
3939 147 : else if (cxx_dialect < cxx23)
3940 : {
3941 1 : if ((complain & tf_warning_or_error) == 0)
3942 0 : return error_mark_node;
3943 1 : pedwarn (input_location, OPT_Wc__23_extensions,
3944 : "%<auto{x}%> only available with "
3945 : "%<-std=c++23%> or %<-std=gnu++23%>");
3946 : }
3947 147 : type = do_auto_deduction (type, compound_literal, type, complain,
3948 : adc_variable_type);
3949 147 : if (type == error_mark_node)
3950 : return error_mark_node;
3951 : }
3952 :
3953 : /* Used to hold a copy of the compound literal in a template. */
3954 10104639 : tree orig_cl = NULL_TREE;
3955 :
3956 10104639 : if (processing_template_decl)
3957 : {
3958 5287126 : const bool dependent_p
3959 5287126 : = (instantiation_dependent_expression_p (compound_literal)
3960 5287126 : || dependent_type_p (type));
3961 1747892 : if (dependent_p)
3962 : /* We're about to return, no need to copy. */
3963 : orig_cl = compound_literal;
3964 : else
3965 : /* We're going to need a copy. */
3966 1747892 : orig_cl = unshare_constructor (compound_literal);
3967 5287126 : TREE_TYPE (orig_cl) = type;
3968 : /* Mark the expression as a compound literal. */
3969 5287126 : TREE_HAS_CONSTRUCTOR (orig_cl) = 1;
3970 : /* And as instantiation-dependent. */
3971 5287126 : CONSTRUCTOR_IS_DEPENDENT (orig_cl) = dependent_p;
3972 5287126 : if (fcl_context == fcl_c99)
3973 130 : CONSTRUCTOR_C99_COMPOUND_LITERAL (orig_cl) = 1;
3974 : /* If the compound literal is dependent, we're done for now. */
3975 5287126 : if (dependent_p)
3976 : return orig_cl;
3977 : /* Otherwise, do go on to e.g. check narrowing. */
3978 : }
3979 :
3980 6565405 : type = complete_type (type);
3981 :
3982 6565405 : if (TYPE_NON_AGGREGATE_CLASS (type))
3983 : {
3984 : /* Trying to deal with a CONSTRUCTOR instead of a TREE_LIST
3985 : everywhere that deals with function arguments would be a pain, so
3986 : just wrap it in a TREE_LIST. The parser set a flag so we know
3987 : that it came from T{} rather than T({}). */
3988 1090053 : CONSTRUCTOR_IS_DIRECT_INIT (compound_literal) = 1;
3989 1090053 : compound_literal = build_tree_list (NULL_TREE, compound_literal);
3990 1090053 : return build_functional_cast (input_location, type,
3991 1090053 : compound_literal, complain);
3992 : }
3993 :
3994 5475352 : if (TREE_CODE (type) == ARRAY_TYPE
3995 5475352 : && check_array_initializer (NULL_TREE, type, compound_literal))
3996 9 : return error_mark_node;
3997 5475343 : compound_literal = reshape_init (type, compound_literal, complain);
3998 5475343 : if (SCALAR_TYPE_P (type)
3999 757750 : && !BRACE_ENCLOSED_INITIALIZER_P (compound_literal)
4000 218890 : && !check_narrowing (type, compound_literal, complain))
4001 131 : return error_mark_node;
4002 5475212 : if (TREE_CODE (type) == ARRAY_TYPE
4003 5475212 : && TYPE_DOMAIN (type) == NULL_TREE)
4004 : {
4005 1253 : cp_complete_array_type_or_error (&type, compound_literal,
4006 : false, complain);
4007 1253 : if (type == error_mark_node)
4008 : return error_mark_node;
4009 : }
4010 5475209 : if (abstract_virtuals_error (ACU_UNKNOWN, type, complain))
4011 7 : return error_mark_node;
4012 5475202 : compound_literal = digest_init_flags (type, compound_literal,
4013 : LOOKUP_NORMAL | LOOKUP_NO_NARROWING,
4014 : complain);
4015 5475202 : if (compound_literal == error_mark_node)
4016 : return error_mark_node;
4017 :
4018 : /* If we're in a template, return the original compound literal. */
4019 5474523 : if (orig_cl)
4020 : return orig_cl;
4021 :
4022 3815671 : if (TREE_CODE (compound_literal) == CONSTRUCTOR)
4023 : {
4024 3114945 : TREE_HAS_CONSTRUCTOR (compound_literal) = true;
4025 3114945 : if (fcl_context == fcl_c99)
4026 37967 : CONSTRUCTOR_C99_COMPOUND_LITERAL (compound_literal) = 1;
4027 : }
4028 :
4029 : /* Put static/constant array temporaries in static variables. */
4030 : /* FIXME all C99 compound literals should be variables rather than C++
4031 : temporaries, unless they are used as an aggregate initializer. */
4032 5029538 : if ((!at_function_scope_p () || CP_TYPE_CONST_P (type))
4033 2610620 : && fcl_context == fcl_c99
4034 83 : && TREE_CODE (type) == ARRAY_TYPE
4035 31 : && !TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type)
4036 3815702 : && initializer_constant_valid_p (compound_literal, type))
4037 : {
4038 31 : tree decl = create_temporary_var (type);
4039 31 : DECL_CONTEXT (decl) = NULL_TREE;
4040 31 : DECL_INITIAL (decl) = compound_literal;
4041 31 : TREE_STATIC (decl) = 1;
4042 31 : if (literal_type_p (type) && CP_TYPE_CONST_NON_VOLATILE_P (type))
4043 : {
4044 : /* 5.19 says that a constant expression can include an
4045 : lvalue-rvalue conversion applied to "a glvalue of literal type
4046 : that refers to a non-volatile temporary object initialized
4047 : with a constant expression". Rather than try to communicate
4048 : that this VAR_DECL is a temporary, just mark it constexpr. */
4049 24 : DECL_DECLARED_CONSTEXPR_P (decl) = true;
4050 24 : DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P (decl) = true;
4051 24 : TREE_CONSTANT (decl) = true;
4052 : }
4053 31 : cp_apply_type_quals_to_decl (cp_type_quals (type), decl);
4054 31 : decl = pushdecl_top_level (decl);
4055 31 : DECL_NAME (decl) = make_anon_name ();
4056 31 : SET_DECL_ASSEMBLER_NAME (decl, DECL_NAME (decl));
4057 : /* Make sure the destructor is callable. */
4058 31 : tree clean = cxx_maybe_build_cleanup (decl, complain);
4059 31 : if (clean == error_mark_node)
4060 : return error_mark_node;
4061 31 : return decl;
4062 : }
4063 :
4064 : /* Represent other compound literals with TARGET_EXPR so we produce
4065 : a prvalue, and can elide copies. */
4066 3815640 : if (!VECTOR_TYPE_P (type)
4067 3775067 : && (TREE_CODE (compound_literal) == CONSTRUCTOR
4068 700720 : || TREE_CODE (compound_literal) == VEC_INIT_EXPR))
4069 : {
4070 : /* The CONSTRUCTOR is now an initializer, not a compound literal. */
4071 3074347 : if (TREE_CODE (compound_literal) == CONSTRUCTOR)
4072 3074347 : TREE_HAS_CONSTRUCTOR (compound_literal) = false;
4073 3074347 : compound_literal = get_target_expr (compound_literal, complain);
4074 : }
4075 : else
4076 : /* For e.g. int{42} just make sure it's a prvalue. */
4077 741293 : compound_literal = rvalue (compound_literal);
4078 :
4079 : return compound_literal;
4080 : }
4081 :
4082 : /* Return the declaration for the function-name variable indicated by
4083 : ID. */
4084 :
4085 : tree
4086 307461 : finish_fname (tree id)
4087 : {
4088 307461 : tree decl = fname_decl (input_location, C_RID_CODE (id), id);
4089 : /* [expr.prim.lambda.closure]/16 "Unless the compound-statement is that
4090 : of a consteval-block-declaration, a variable __func__ is implicitly
4091 : defined...". We could be in a consteval block in a function, though,
4092 : and then we shouldn't warn. */
4093 307461 : if (current_function_decl
4094 307461 : && !current_nonlambda_function (/*only_skip_consteval_block_p=*/true))
4095 8 : pedwarn (input_location, 0, "%qD is not defined outside of function scope",
4096 : decl);
4097 307461 : if (processing_template_decl && current_function_decl
4098 228699 : && decl != error_mark_node)
4099 228699 : decl = DECL_NAME (decl);
4100 307461 : return decl;
4101 : }
4102 :
4103 : /* Finish a translation unit. */
4104 :
4105 : void
4106 99891 : finish_translation_unit (void)
4107 : {
4108 : /* In case there were missing closebraces,
4109 : get us back to the global binding level. */
4110 99891 : pop_everything ();
4111 199782 : while (current_namespace != global_namespace)
4112 0 : pop_namespace ();
4113 :
4114 : /* Do file scope __FUNCTION__ et al. */
4115 99891 : finish_fname_decls ();
4116 :
4117 99891 : if (vec_safe_length (scope_chain->omp_declare_target_attribute))
4118 : {
4119 12 : cp_omp_declare_target_attr
4120 12 : a = scope_chain->omp_declare_target_attribute->pop ();
4121 12 : if (!errorcount)
4122 9 : error ("%qs without corresponding %qs",
4123 : a.device_type >= 0 ? "#pragma omp begin declare target"
4124 : : "#pragma omp declare target",
4125 : "#pragma omp end declare target");
4126 24 : vec_safe_truncate (scope_chain->omp_declare_target_attribute, 0);
4127 : }
4128 99891 : if (vec_safe_length (scope_chain->omp_declare_variant_attribute))
4129 : {
4130 0 : if (!errorcount)
4131 0 : error ("%<omp begin declare variant%> without corresponding "
4132 : "%<omp end declare variant%>");
4133 0 : vec_safe_truncate (scope_chain->omp_declare_variant_attribute, 0);
4134 : }
4135 99891 : if (vec_safe_length (scope_chain->omp_begin_assumes))
4136 : {
4137 3 : if (!errorcount)
4138 3 : error ("%qs without corresponding %qs",
4139 : "#pragma omp begin assumes", "#pragma omp end assumes");
4140 3 : vec_safe_truncate (scope_chain->omp_begin_assumes, 0);
4141 : }
4142 99891 : }
4143 :
4144 : /* Finish a template type parameter, specified as AGGR IDENTIFIER.
4145 : Returns the parameter. */
4146 :
4147 : tree
4148 166327530 : finish_template_type_parm (tree aggr, tree identifier)
4149 : {
4150 166327530 : if (aggr != class_type_node)
4151 : {
4152 0 : permerror (input_location, "template type parameters must use the keyword %<class%> or %<typename%>");
4153 0 : aggr = class_type_node;
4154 : }
4155 :
4156 166327530 : return build_tree_list (aggr, identifier);
4157 : }
4158 :
4159 : /* Finish a template template parameter, specified as AGGR IDENTIFIER.
4160 : Returns the parameter. */
4161 :
4162 : tree
4163 422841 : finish_template_template_parm (tree aggr, tree identifier)
4164 : {
4165 422841 : tree decl = build_decl (input_location,
4166 : TYPE_DECL, identifier, NULL_TREE);
4167 :
4168 422841 : tree tmpl = build_lang_decl (TEMPLATE_DECL, identifier, NULL_TREE);
4169 422841 : DECL_TEMPLATE_PARMS (tmpl) = current_template_parms;
4170 422841 : DECL_TEMPLATE_RESULT (tmpl) = decl;
4171 422841 : DECL_ARTIFICIAL (decl) = 1;
4172 :
4173 : /* Associate the constraints with the underlying declaration,
4174 : not the template. */
4175 422841 : tree constr = current_template_constraints ();
4176 422841 : set_constraints (decl, constr);
4177 :
4178 422841 : end_template_decl ();
4179 :
4180 422841 : gcc_assert (DECL_TEMPLATE_PARMS (tmpl));
4181 :
4182 422841 : check_default_tmpl_args (decl, DECL_TEMPLATE_PARMS (tmpl),
4183 : /*is_primary=*/true, /*is_partial=*/false,
4184 : /*is_friend=*/0);
4185 :
4186 422841 : return finish_template_type_parm (aggr, tmpl);
4187 : }
4188 :
4189 : /* ARGUMENT is the default-argument value for a template template
4190 : parameter. If ARGUMENT is invalid, issue error messages and return
4191 : the ERROR_MARK_NODE. Otherwise, ARGUMENT itself is returned. */
4192 :
4193 : tree
4194 984 : check_template_template_default_arg (tree argument)
4195 : {
4196 984 : if (TREE_CODE (argument) != TEMPLATE_DECL
4197 : && TREE_CODE (argument) != TEMPLATE_TEMPLATE_PARM
4198 : && TREE_CODE (argument) != UNBOUND_CLASS_TEMPLATE)
4199 : {
4200 : if (TREE_CODE (argument) == TYPE_DECL)
4201 : {
4202 18 : if (tree t = maybe_get_template_decl_from_type_decl (argument))
4203 18 : if (TREE_CODE (t) == TEMPLATE_DECL)
4204 : return t;
4205 15 : error ("invalid use of type %qT as a default value for a template "
4206 15 : "template-parameter", TREE_TYPE (argument));
4207 : }
4208 : else
4209 0 : error ("invalid default argument for a template template parameter");
4210 15 : return error_mark_node;
4211 : }
4212 :
4213 : return argument;
4214 : }
4215 :
4216 : /* Begin a class definition, as indicated by T. */
4217 :
4218 : tree
4219 31987625 : begin_class_definition (tree t)
4220 : {
4221 31987625 : if (error_operand_p (t) || error_operand_p (TYPE_MAIN_DECL (t)))
4222 33 : return error_mark_node;
4223 :
4224 31987742 : if (processing_template_parmlist && !LAMBDA_TYPE_P (t))
4225 : {
4226 24 : error ("definition of %q#T inside template parameter list", t);
4227 24 : return error_mark_node;
4228 : }
4229 :
4230 : /* According to the C++ ABI, decimal classes defined in ISO/IEC TR 24733
4231 : are passed the same as decimal scalar types. */
4232 31987568 : if (TREE_CODE (t) == RECORD_TYPE
4233 31454278 : && !processing_template_decl)
4234 : {
4235 11281321 : tree ns = TYPE_CONTEXT (t);
4236 11281318 : if (ns && TREE_CODE (ns) == NAMESPACE_DECL
4237 9264969 : && DECL_CONTEXT (ns) == std_node
4238 2244099 : && DECL_NAME (ns)
4239 13525400 : && id_equal (DECL_NAME (ns), "decimal"))
4240 : {
4241 150 : const char *n = TYPE_NAME_STRING (t);
4242 150 : if ((strcmp (n, "decimal32") == 0)
4243 101 : || (strcmp (n, "decimal64") == 0)
4244 46 : || (strcmp (n, "decimal128") == 0))
4245 147 : TYPE_TRANSPARENT_AGGR (t) = 1;
4246 : }
4247 : }
4248 :
4249 : /* A non-implicit typename comes from code like:
4250 :
4251 : template <typename T> struct A {
4252 : template <typename U> struct A<T>::B ...
4253 :
4254 : This is erroneous. */
4255 20706247 : else if (TREE_CODE (t) == TYPENAME_TYPE)
4256 : {
4257 0 : error ("invalid definition of qualified type %qT", t);
4258 0 : t = error_mark_node;
4259 : }
4260 :
4261 31987568 : if (t == error_mark_node || ! MAYBE_CLASS_TYPE_P (t))
4262 : {
4263 0 : t = make_class_type (RECORD_TYPE);
4264 0 : pushtag (make_anon_name (), t);
4265 : }
4266 :
4267 31987568 : if (TYPE_BEING_DEFINED (t))
4268 : {
4269 0 : t = make_class_type (TREE_CODE (t));
4270 0 : pushtag (TYPE_IDENTIFIER (t), t);
4271 : }
4272 :
4273 31987568 : maybe_process_partial_specialization (t);
4274 31987568 : pushclass (t);
4275 31987568 : TYPE_BEING_DEFINED (t) = 1;
4276 31987568 : class_binding_level->defining_class_p = 1;
4277 :
4278 31987568 : if (flag_pack_struct)
4279 : {
4280 99 : tree v;
4281 99 : TYPE_PACKED (t) = 1;
4282 : /* Even though the type is being defined for the first time
4283 : here, there might have been a forward declaration, so there
4284 : might be cv-qualified variants of T. */
4285 99 : for (v = TYPE_NEXT_VARIANT (t); v; v = TYPE_NEXT_VARIANT (v))
4286 0 : TYPE_PACKED (v) = 1;
4287 : }
4288 : /* Reset the interface data, at the earliest possible
4289 : moment, as it might have been set via a class foo;
4290 : before. */
4291 66426325 : if (! TYPE_UNNAMED_P (t))
4292 : {
4293 31221080 : struct c_fileinfo *finfo = \
4294 31221080 : get_fileinfo (LOCATION_FILE (input_location));
4295 31221080 : CLASSTYPE_INTERFACE_ONLY (t) = finfo->interface_only;
4296 31221080 : SET_CLASSTYPE_INTERFACE_UNKNOWN_X
4297 : (t, finfo->interface_unknown);
4298 : }
4299 31987568 : reset_specialization ();
4300 :
4301 : /* Make a declaration for this class in its own scope. */
4302 31987568 : build_self_reference ();
4303 :
4304 31987568 : return t;
4305 : }
4306 :
4307 : /* Finish the member declaration given by DECL. */
4308 :
4309 : void
4310 431511655 : finish_member_declaration (tree decl)
4311 : {
4312 431511655 : if (decl == error_mark_node || decl == NULL_TREE)
4313 : return;
4314 :
4315 431510606 : if (decl == void_type_node)
4316 : /* The COMPONENT was a friend, not a member, and so there's
4317 : nothing for us to do. */
4318 : return;
4319 :
4320 : /* We should see only one DECL at a time. */
4321 431510606 : gcc_assert (DECL_CHAIN (decl) == NULL_TREE);
4322 :
4323 : /* Don't add decls after definition. */
4324 431510627 : gcc_assert (TYPE_BEING_DEFINED (current_class_type)
4325 : /* We can add lambda types when late parsing default
4326 : arguments. */
4327 : || LAMBDA_TYPE_P (TREE_TYPE (decl)));
4328 :
4329 : /* Set up access control for DECL. */
4330 431510606 : TREE_PRIVATE (decl)
4331 431510606 : = (current_access_specifier == access_private_node);
4332 431510606 : TREE_PROTECTED (decl)
4333 431510606 : = (current_access_specifier == access_protected_node);
4334 431510606 : if (TREE_CODE (decl) == TEMPLATE_DECL)
4335 : {
4336 49393859 : TREE_PRIVATE (DECL_TEMPLATE_RESULT (decl)) = TREE_PRIVATE (decl);
4337 49393859 : TREE_PROTECTED (DECL_TEMPLATE_RESULT (decl)) = TREE_PROTECTED (decl);
4338 : }
4339 :
4340 : /* Mark the DECL as a member of the current class, unless it's
4341 : a member of an enumeration. */
4342 431510606 : if (TREE_CODE (decl) != CONST_DECL)
4343 429077436 : DECL_CONTEXT (decl) = current_class_type;
4344 :
4345 431510606 : if (TREE_TYPE (decl)
4346 427900038 : && ANON_AGGR_TYPE_P (TREE_TYPE (decl))
4347 431908130 : && TREE_CODE (decl) != TYPE_DECL)
4348 : {
4349 : /* Remember the single FIELD_DECL an anonymous aggregate type is used
4350 : for. */
4351 289474 : if (TREE_CODE (decl) == FIELD_DECL && DECL_NAME (decl) == NULL_TREE)
4352 : {
4353 289458 : tree type = TYPE_MAIN_VARIANT (TREE_TYPE (decl));
4354 289458 : gcc_assert (!ANON_AGGR_TYPE_FIELD (type));
4355 289458 : SET_ANON_AGGR_TYPE_FIELD (type, decl);
4356 : }
4357 : /* [class.union.anon]/1: Each object of such an unnamed type shall
4358 : be such an unnamed object. */
4359 16 : else if (ANON_UNION_TYPE_P (TREE_TYPE (decl)))
4360 : {
4361 10 : tree adecl = TYPE_MAIN_DECL (TYPE_MAIN_VARIANT (TREE_TYPE (decl)));
4362 10 : auto_diagnostic_group d;
4363 10 : error_at (location_of (decl),
4364 : "declaration of member %qD with anonymous union type %qT",
4365 10 : decl, TREE_TYPE (decl));
4366 10 : inform (DECL_SOURCE_LOCATION (adecl),
4367 : "anonymous union declared here");
4368 10 : }
4369 : else
4370 : {
4371 6 : tree adecl = TYPE_MAIN_DECL (TYPE_MAIN_VARIANT (TREE_TYPE (decl)));
4372 6 : auto_diagnostic_group d;
4373 6 : error_at (location_of (decl),
4374 : "declaration of member %qD with anonymous struct type %qT",
4375 6 : decl, TREE_TYPE (decl));
4376 6 : inform (DECL_SOURCE_LOCATION (adecl),
4377 : "anonymous struct declared here");
4378 6 : }
4379 : }
4380 431221132 : else if (TREE_TYPE (decl)
4381 427610564 : && TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE
4382 432830929 : && TREE_CODE (decl) != TYPE_DECL)
4383 : {
4384 1544763 : tree type = strip_array_types (TREE_TYPE (decl));
4385 1544763 : if (ANON_AGGR_TYPE_P (type))
4386 : {
4387 : /* [class.union.anon]/1: Each object of such an unnamed type shall
4388 : be such an unnamed object. */
4389 12 : tree adecl = TYPE_MAIN_DECL (TYPE_MAIN_VARIANT (type));
4390 12 : auto_diagnostic_group d;
4391 12 : if (ANON_UNION_TYPE_P (type))
4392 : {
4393 8 : error_at (location_of (decl),
4394 : "declaration of member %qD with array of anonymous "
4395 8 : "union type %qT", decl, TREE_TYPE (decl));
4396 8 : inform (DECL_SOURCE_LOCATION (adecl),
4397 : "anonymous union declared here");
4398 : }
4399 : else
4400 : {
4401 4 : error_at (location_of (decl),
4402 : "declaration of member %qD with array of anonymous "
4403 4 : "struct type %qT", decl, TREE_TYPE (decl));
4404 4 : inform (DECL_SOURCE_LOCATION (adecl),
4405 : "anonymous struct declared here");
4406 : }
4407 12 : }
4408 : }
4409 :
4410 431510606 : if (TREE_CODE (decl) == USING_DECL)
4411 : /* Avoid debug info for class-scope USING_DECLS for now, we'll
4412 : call cp_emit_debug_info_for_using later. */
4413 3517345 : DECL_IGNORED_P (decl) = 1;
4414 :
4415 : /* Check for bare parameter packs in the non-static data member
4416 : declaration. */
4417 431510606 : if (TREE_CODE (decl) == FIELD_DECL)
4418 : {
4419 31675489 : if (check_for_bare_parameter_packs (TREE_TYPE (decl)))
4420 9 : TREE_TYPE (decl) = error_mark_node;
4421 31675489 : if (check_for_bare_parameter_packs (DECL_ATTRIBUTES (decl)))
4422 0 : DECL_ATTRIBUTES (decl) = NULL_TREE;
4423 : }
4424 :
4425 : /* [dcl.link]
4426 :
4427 : A C language linkage is ignored for the names of class members
4428 : and the member function type of class member functions. */
4429 431510606 : if (DECL_LANG_SPECIFIC (decl))
4430 393807726 : SET_DECL_LANGUAGE (decl, lang_cplusplus);
4431 :
4432 431510606 : bool add = false;
4433 :
4434 : /* Functions and non-functions are added differently. */
4435 431510606 : if (DECL_DECLARES_FUNCTION_P (decl))
4436 222901540 : add = add_method (current_class_type, decl, false);
4437 : /* Enter the DECL into the scope of the class, if the class
4438 : isn't a closure (whose fields are supposed to be unnamed). */
4439 208609066 : else if (CLASSTYPE_LAMBDA_EXPR (current_class_type)
4440 204665170 : || maybe_push_used_methods (decl)
4441 411335840 : || pushdecl_class_level (decl))
4442 : add = true;
4443 :
4444 222901540 : if (add)
4445 : {
4446 : /* All TYPE_DECLs go at the end of TYPE_FIELDS. Ordinary fields
4447 : go at the beginning. The reason is that
4448 : legacy_nonfn_member_lookup searches the list in order, and we
4449 : want a field name to override a type name so that the "struct
4450 : stat hack" will work. In particular:
4451 :
4452 : struct S { enum E { }; static const int E = 5; int ary[S::E]; } s;
4453 :
4454 : is valid. */
4455 :
4456 431497181 : if (TREE_CODE (decl) == TYPE_DECL)
4457 147949497 : TYPE_FIELDS (current_class_type)
4458 295898994 : = chainon (TYPE_FIELDS (current_class_type), decl);
4459 : else
4460 : {
4461 283547684 : DECL_CHAIN (decl) = TYPE_FIELDS (current_class_type);
4462 283547684 : TYPE_FIELDS (current_class_type) = decl;
4463 : }
4464 :
4465 431497181 : maybe_add_class_template_decl_list (current_class_type, decl,
4466 : /*friend_p=*/0);
4467 : }
4468 : }
4469 :
4470 : /* Finish processing a complete template declaration. The PARMS are
4471 : the template parameters. */
4472 :
4473 : void
4474 95412119 : finish_template_decl (tree parms)
4475 : {
4476 95412119 : if (parms)
4477 95412110 : end_template_decl ();
4478 : else
4479 9 : end_specialization ();
4480 95412119 : }
4481 :
4482 : // Returns the template type of the class scope being entered. If we're
4483 : // entering a constrained class scope. TYPE is the class template
4484 : // scope being entered and we may need to match the intended type with
4485 : // a constrained specialization. For example:
4486 : //
4487 : // template<Object T>
4488 : // struct S { void f(); }; #1
4489 : //
4490 : // template<Object T>
4491 : // void S<T>::f() { } #2
4492 : //
4493 : // We check, in #2, that S<T> refers precisely to the type declared by
4494 : // #1 (i.e., that the constraints match). Note that the following should
4495 : // be an error since there is no specialization of S<T> that is
4496 : // unconstrained, but this is not diagnosed here.
4497 : //
4498 : // template<typename T>
4499 : // void S<T>::f() { }
4500 : //
4501 : // We cannot diagnose this problem here since this function also matches
4502 : // qualified template names that are not part of a definition. For example:
4503 : //
4504 : // template<Integral T, Floating_point U>
4505 : // typename pair<T, U>::first_type void f(T, U);
4506 : //
4507 : // Here, it is unlikely that there is a partial specialization of
4508 : // pair constrained for Integral and Floating_point arguments.
4509 : //
4510 : // The general rule is: if a constrained specialization with matching
4511 : // constraints is found return that type. Also note that if TYPE is not a
4512 : // class-type (e.g. a typename type), then no fixup is needed.
4513 :
4514 : static tree
4515 18737666 : fixup_template_type (tree type)
4516 : {
4517 : // Find the template parameter list at the a depth appropriate to
4518 : // the scope we're trying to enter.
4519 18737666 : tree parms = current_template_parms;
4520 18737666 : int depth = template_class_depth (type);
4521 23098119 : for (int n = current_template_depth; n > depth && parms; --n)
4522 4360453 : parms = TREE_CHAIN (parms);
4523 18737666 : if (!parms)
4524 : return type;
4525 18737656 : tree cur_reqs = TEMPLATE_PARMS_CONSTRAINTS (parms);
4526 18737656 : tree cur_constr = build_constraints (cur_reqs, NULL_TREE);
4527 :
4528 : // Search for a specialization whose type and constraints match.
4529 18737656 : tree tmpl = CLASSTYPE_TI_TEMPLATE (type);
4530 18737656 : tree specs = DECL_TEMPLATE_SPECIALIZATIONS (tmpl);
4531 36230588 : while (specs)
4532 : {
4533 17941680 : tree spec_constr = get_constraints (TREE_VALUE (specs));
4534 :
4535 : // If the type and constraints match a specialization, then we
4536 : // are entering that type.
4537 17941680 : if (same_type_p (type, TREE_TYPE (specs))
4538 17941680 : && equivalent_constraints (cur_constr, spec_constr))
4539 448748 : return TREE_TYPE (specs);
4540 17492932 : specs = TREE_CHAIN (specs);
4541 : }
4542 :
4543 : // If no specialization matches, then must return the type
4544 : // previously found.
4545 : return type;
4546 : }
4547 :
4548 : /* Finish processing a template-id (which names a type) of the form
4549 : NAME < ARGS >. Return the TYPE_DECL for the type named by the
4550 : template-id. If ENTERING_SCOPE is nonzero we are about to enter
4551 : the scope of template-id indicated. */
4552 :
4553 : tree
4554 193327540 : finish_template_type (tree name, tree args, int entering_scope)
4555 : {
4556 193327540 : tree type;
4557 :
4558 193327540 : type = lookup_template_class (name, args,
4559 : NULL_TREE, NULL_TREE,
4560 : tf_warning_or_error | tf_user);
4561 193327537 : if (entering_scope)
4562 19797278 : type = adjust_type_for_entering_scope (type);
4563 :
4564 : /* If we might be entering the scope of a partial specialization,
4565 : find the one with the right constraints. */
4566 193327537 : if (flag_concepts
4567 190561796 : && entering_scope
4568 19423204 : && CLASS_TYPE_P (type)
4569 19250244 : && CLASSTYPE_TEMPLATE_INFO (type)
4570 19250235 : && dependent_type_p (type)
4571 212065203 : && PRIMARY_TEMPLATE_P (CLASSTYPE_TI_TEMPLATE (type)))
4572 18737666 : type = fixup_template_type (type);
4573 :
4574 193327537 : if (type == error_mark_node)
4575 : return type;
4576 193325247 : else if (CLASS_TYPE_P (type) && !alias_type_or_template_p (type))
4577 151756075 : return TYPE_STUB_DECL (type);
4578 : else
4579 41569172 : return TYPE_NAME (type);
4580 : }
4581 :
4582 : /* Finish processing a BASE_CLASS with the indicated ACCESS_SPECIFIER
4583 : and ANNOTATIONS.
4584 : Return a TREE_LIST containing the ACCESS_SPECIFIER (or if there are
4585 : ANNOTATIONS, TREE_LIST containing the ACCESS_SPECIFIER and ANNOTATIONS)
4586 : and the BASE_CLASS, or NULL_TREE if an error occurred. The
4587 : ACCESS_SPECIFIER is one of
4588 : access_{default,public,protected,private}_node. For a virtual base
4589 : we set TREE_TYPE. */
4590 :
4591 : tree
4592 11777216 : finish_base_specifier (tree base, tree access, bool virtual_p,
4593 : tree annotations)
4594 : {
4595 11777216 : tree result;
4596 :
4597 11777216 : if (base == error_mark_node)
4598 : {
4599 0 : error ("invalid base-class specification");
4600 0 : result = NULL_TREE;
4601 : }
4602 11777216 : else if (! MAYBE_CLASS_TYPE_P (base))
4603 : {
4604 3 : error ("%qT is not a class type", base);
4605 3 : result = NULL_TREE;
4606 : }
4607 : else
4608 : {
4609 11777213 : if (cp_type_quals (base) != 0)
4610 : {
4611 : /* DR 484: Can a base-specifier name a cv-qualified
4612 : class type? */
4613 12 : base = TYPE_MAIN_VARIANT (base);
4614 : }
4615 11777213 : if (annotations)
4616 18 : access = build_tree_list (access, nreverse (annotations));
4617 11777213 : result = build_tree_list (access, base);
4618 11777213 : if (virtual_p)
4619 26827 : TREE_TYPE (result) = integer_type_node;
4620 : }
4621 :
4622 11777216 : return result;
4623 : }
4624 :
4625 : /* If FNS is a member function, a set of member functions, or a
4626 : template-id referring to one or more member functions, return a
4627 : BASELINK for FNS, incorporating the current access context.
4628 : Otherwise, return FNS unchanged. If IGNORE_CURRENT_CLASS_P is
4629 : true, we do not consider the currently open derived class. */
4630 :
4631 : tree
4632 189131528 : baselink_for_fns (tree fns, bool ignore_current_class_p/*=false*/)
4633 : {
4634 189131528 : if (BASELINK_P (fns) || error_operand_p (fns))
4635 : return fns;
4636 :
4637 174883047 : tree scope = ovl_scope (fns);
4638 174883047 : if (!CLASS_TYPE_P (scope))
4639 : return fns;
4640 :
4641 9173345 : tree cl = (ignore_current_class_p
4642 9173345 : ? NULL_TREE
4643 9171605 : : currently_open_derived_class (scope));
4644 9171605 : if (!cl)
4645 : cl = scope;
4646 9173345 : tree access_path = TYPE_BINFO (cl);
4647 9173345 : tree conv_path = (cl == scope ? access_path
4648 732646 : : lookup_base (cl, scope, ba_any, NULL, tf_none));
4649 9173345 : return build_baselink (conv_path, access_path, fns, /*optype=*/NULL_TREE);
4650 : }
4651 :
4652 : /* Returns true iff we are currently parsing a lambda-declarator. */
4653 :
4654 : bool
4655 2034946477 : parsing_lambda_declarator ()
4656 : {
4657 2034946477 : cp_binding_level *b = current_binding_level;
4658 2037027228 : while (b->kind == sk_template_parms || b->kind == sk_function_parms)
4659 2080751 : b = b->level_chain;
4660 2034946477 : return b->kind == sk_lambda;
4661 : }
4662 :
4663 : /* Returns true iff DECL is a variable from a function outside
4664 : the current one. */
4665 :
4666 : static bool
4667 2717898769 : outer_var_p (tree decl)
4668 : {
4669 : /* These should have been stripped or otherwise handled by the caller. */
4670 2717898769 : gcc_checking_assert (!REFERENCE_REF_P (decl));
4671 :
4672 1785561750 : return ((VAR_P (decl) || TREE_CODE (decl) == PARM_DECL)
4673 2496041970 : && DECL_FUNCTION_SCOPE_P (decl)
4674 : /* Don't get confused by temporaries. */
4675 2067783622 : && DECL_NAME (decl)
4676 4761202549 : && (DECL_CONTEXT (decl) != current_function_decl
4677 2032719994 : || parsing_nsdmi ()
4678 : /* Also consider captures as outer vars if we are in
4679 : decltype in a lambda declarator as in:
4680 : auto l = [j=0]() -> decltype((j)) { ... }
4681 : for the sake of finish_decltype_type.
4682 :
4683 : (Similar issue also affects non-lambdas, but vexing parse
4684 : makes it more difficult to handle than lambdas.) */
4685 2032718617 : || parsing_lambda_declarator ()));
4686 : }
4687 :
4688 : /* As above, but also checks that DECL is automatic. */
4689 :
4690 : bool
4691 2717898769 : outer_automatic_var_p (tree decl)
4692 : {
4693 2717898769 : return (outer_var_p (decl)
4694 2717898769 : && !TREE_STATIC (decl));
4695 : }
4696 :
4697 : /* Note whether capture proxy D is only used in a contract condition. */
4698 :
4699 : static void
4700 180938 : set_contract_capture_flag (tree d, bool val)
4701 : {
4702 180938 : gcc_checking_assert (DECL_HAS_VALUE_EXPR_P (d));
4703 180938 : tree proxy = DECL_VALUE_EXPR (d);
4704 180938 : gcc_checking_assert (TREE_CODE (proxy) == COMPONENT_REF
4705 : && TREE_CODE (TREE_OPERAND (proxy, 1)) == FIELD_DECL);
4706 180938 : DECL_CONTRACT_CAPTURE_P (TREE_OPERAND (proxy, 1)) = val;
4707 180938 : }
4708 :
4709 : /* DECL satisfies outer_automatic_var_p. Possibly complain about it or
4710 : rewrite it for lambda capture.
4711 :
4712 : If ODR_USE is true, we're being called from mark_use, and we complain about
4713 : use of constant variables. If ODR_USE is false, we're being called for the
4714 : id-expression, and we do lambda capture. */
4715 :
4716 : tree
4717 5445383 : process_outer_var_ref (tree decl, tsubst_flags_t complain,
4718 : bool odr_use/*=false*/)
4719 : {
4720 5451872 : bool in_typeid_probe = false;
4721 5451872 : if (cp_unevaluated_operand)
4722 : {
4723 3223828 : tree type = TREE_TYPE (decl);
4724 3223828 : if (!dependent_type_p (type)
4725 3223828 : && variably_modified_type_p (type, NULL_TREE))
4726 : /* VLAs are used even in unevaluated context. */;
4727 3223822 : else if (cp_unevaluated_operand > cp_unevaluated_typeid_cutoff)
4728 : /* It's not a use (3.2) if we're in an unevaluated context. */
4729 : return decl;
4730 : else
4731 : /* Inside a typeid operand's own probe: capture is still
4732 : attempted below ([expr.prim.lambda.capture]/7), but a missing
4733 : capture-default must not be diagnosed yet - see below. */
4734 : in_typeid_probe = true;
4735 : }
4736 2228113 : if (decl == error_mark_node)
4737 : return decl;
4738 :
4739 2228107 : tree context = DECL_CONTEXT (decl);
4740 2228107 : tree containing_function = current_function_decl;
4741 2228107 : tree lambda_stack = NULL_TREE;
4742 2228107 : tree lambda_expr = NULL_TREE;
4743 2228107 : tree initializer = convert_from_reference (decl);
4744 2228107 : tree var = strip_normal_capture_proxy (decl);
4745 :
4746 : /* Mark it as used now even if the use is ill-formed. */
4747 2228107 : if (!mark_used (decl, complain))
4748 3 : return error_mark_node;
4749 :
4750 2228104 : if (parsing_nsdmi () || parsing_lambda_declarator ())
4751 : containing_function = NULL_TREE;
4752 :
4753 4455301 : if (containing_function && LAMBDA_FUNCTION_P (containing_function))
4754 : {
4755 : /* Check whether we've already built a proxy. */
4756 2227546 : tree d = retrieve_local_specialization (var);
4757 :
4758 2227546 : if (d && d != decl && is_capture_proxy (d))
4759 : {
4760 1142840 : if (flag_contracts && !processing_contract_condition)
4761 : /* We might have created a capture for a contract_assert ref. to
4762 : some var, if that is now captured 'normally' then this is OK.
4763 : Otherwise we leave the capture marked as incorrect. */
4764 180932 : set_contract_capture_flag (d, false);
4765 1142840 : if (DECL_CONTEXT (d) == containing_function)
4766 : /* We already have an inner proxy. */
4767 : return d;
4768 : else
4769 : /* We need to capture an outer proxy. */
4770 : return process_outer_var_ref (d, complain, odr_use);
4771 : }
4772 : }
4773 :
4774 : /* If we are in a lambda function, we can move out until we hit
4775 : 1. the context,
4776 : 2. a non-lambda function, or
4777 : 3. a non-default capturing lambda function. */
4778 2176808 : while (context != containing_function
4779 : /* containing_function can be null with invalid generic lambdas. */
4780 2176808 : && containing_function
4781 3269770 : && LAMBDA_FUNCTION_P (containing_function))
4782 : {
4783 1092962 : tree closure = DECL_CONTEXT (containing_function);
4784 1092962 : lambda_expr = CLASSTYPE_LAMBDA_EXPR (closure);
4785 :
4786 1092962 : if (TYPE_CLASS_SCOPE_P (closure))
4787 : /* A lambda in an NSDMI (c++/64496). */
4788 : break;
4789 :
4790 1092959 : if (LAMBDA_EXPR_DEFAULT_CAPTURE_MODE (lambda_expr) == CPLD_NONE)
4791 : break;
4792 :
4793 1091544 : lambda_stack = tree_cons (NULL_TREE, lambda_expr, lambda_stack);
4794 :
4795 1091544 : containing_function = decl_function_context (containing_function);
4796 : }
4797 :
4798 : /* In a lambda within a template, wait until instantiation time to implicitly
4799 : capture a parameter pack. We want to wait because we don't know if we're
4800 : capturing the whole pack or a single element, and it's OK to wait because
4801 : find_parameter_packs_r walks into the lambda body. */
4802 1085264 : if (context == containing_function
4803 1085264 : && DECL_PACK_P (decl))
4804 : return decl;
4805 :
4806 1040603 : if (lambda_expr && VAR_P (decl) && DECL_ANON_UNION_VAR_P (decl))
4807 : {
4808 6 : if (complain & tf_error)
4809 6 : error ("cannot capture member %qD of anonymous union", decl);
4810 6 : return error_mark_node;
4811 : }
4812 : /* Do lambda capture when processing the id-expression, not when
4813 : odr-using a variable, but uses in a contract must not cause a capture. */
4814 1040597 : if (!odr_use && context == containing_function)
4815 : {
4816 1038621 : decl = add_default_capture (lambda_stack,
4817 1038621 : /*id=*/DECL_NAME (decl), initializer);
4818 1038621 : if (flag_contracts && processing_contract_condition)
4819 6 : set_contract_capture_flag (decl, true);
4820 : }
4821 : /* Capture was attempted above; whether it's really needed depends on
4822 : an evaluated-ness we don't know yet. Defer instead of diagnosing:
4823 : a later, non-probe pass will complain if the operand turns out
4824 : evaluated, and there's nothing to complain about if it doesn't. */
4825 1976 : else if (in_typeid_probe)
4826 : return var;
4827 : /* Only an odr-use of an outer automatic variable causes an
4828 : error, and a constant variable can decay to a prvalue
4829 : constant without odr-use. So don't complain yet. */
4830 1967 : else if (!odr_use && decl_constant_var_p (var))
4831 : return var;
4832 : /* Don't complain when DECL is dependent, because it can turn out to
4833 : be constant (and therefore needing no capture) when instantiating. */
4834 438 : else if (VAR_P (var) && instantiation_dependent_expression_p (var))
4835 : return var;
4836 420 : else if (lambda_expr)
4837 : {
4838 60 : if (complain & tf_error)
4839 : {
4840 56 : auto_diagnostic_group d;
4841 56 : error ("%qD is not captured", decl);
4842 56 : tree closure = LAMBDA_EXPR_CLOSURE (lambda_expr);
4843 56 : if (LAMBDA_EXPR_DEFAULT_CAPTURE_MODE (lambda_expr) == CPLD_NONE)
4844 53 : inform (location_of (closure),
4845 : "the lambda has no capture-default");
4846 3 : else if (TYPE_CLASS_SCOPE_P (closure))
4847 3 : inform (UNKNOWN_LOCATION, "lambda in local class %q+T cannot "
4848 : "capture variables from the enclosing context",
4849 3 : TYPE_CONTEXT (closure));
4850 56 : inform (DECL_SOURCE_LOCATION (decl), "%q#D declared here", decl);
4851 56 : }
4852 60 : return error_mark_node;
4853 : }
4854 360 : else if (processing_contract_condition && TREE_CODE (decl) == PARM_DECL)
4855 : /* Use of a parameter in a contract condition is fine. */
4856 : return decl;
4857 : else
4858 : {
4859 53 : if (complain & tf_error)
4860 : {
4861 39 : auto_diagnostic_group d;
4862 57 : error (VAR_P (decl)
4863 : ? G_("use of local variable with automatic storage from "
4864 : "containing function")
4865 : : G_("use of parameter from containing function"));
4866 39 : inform (DECL_SOURCE_LOCATION (decl), "%q#D declared here", decl);
4867 39 : }
4868 53 : return error_mark_node;
4869 : }
4870 : return decl;
4871 : }
4872 :
4873 : /* ID_EXPRESSION is a representation of parsed, but unprocessed,
4874 : id-expression. (See cp_parser_id_expression for details.) SCOPE,
4875 : if non-NULL, is the type or namespace used to explicitly qualify
4876 : ID_EXPRESSION. DECL is the entity to which that name has been
4877 : resolved.
4878 :
4879 : *CONSTANT_EXPRESSION_P is true if we are presently parsing a
4880 : constant-expression. In that case, *NON_CONSTANT_EXPRESSION_P will
4881 : be set to true if this expression isn't permitted in a
4882 : constant-expression, but it is otherwise not set by this function.
4883 : *ALLOW_NON_CONSTANT_EXPRESSION_P is true if we are parsing a
4884 : constant-expression, but a non-constant expression is also
4885 : permissible.
4886 :
4887 : DONE is true if this expression is a complete postfix-expression;
4888 : it is false if this expression is followed by '->', '[', '(', etc.
4889 : ADDRESS_P is true iff this expression is the operand of '&'.
4890 : TEMPLATE_P is true iff the qualified-id was of the form
4891 : "A::template B". TEMPLATE_ARG_P is true iff this qualified name
4892 : appears as a template argument.
4893 :
4894 : If an error occurs, and it is the kind of error that might cause
4895 : the parser to abort a tentative parse, *ERROR_MSG is filled in. It
4896 : is the caller's responsibility to issue the message. *ERROR_MSG
4897 : will be a string with static storage duration, so the caller need
4898 : not "free" it.
4899 :
4900 : Return an expression for the entity, after issuing appropriate
4901 : diagnostics. This function is also responsible for transforming a
4902 : reference to a non-static member into a COMPONENT_REF that makes
4903 : the use of "this" explicit.
4904 :
4905 : Upon return, *IDK will be filled in appropriately. */
4906 : static cp_expr
4907 807553851 : finish_id_expression_1 (tree id_expression,
4908 : tree decl,
4909 : tree scope,
4910 : cp_id_kind *idk,
4911 : bool integral_constant_expression_p,
4912 : bool allow_non_integral_constant_expression_p,
4913 : bool *non_integral_constant_expression_p,
4914 : bool template_p,
4915 : bool done,
4916 : bool address_p,
4917 : bool template_arg_p,
4918 : const char **error_msg,
4919 : location_t location)
4920 : {
4921 807553851 : decl = strip_using_decl (decl);
4922 :
4923 : /* Initialize the output parameters. */
4924 807553851 : *idk = CP_ID_KIND_NONE;
4925 807553851 : *error_msg = NULL;
4926 :
4927 807553851 : if (id_expression == error_mark_node)
4928 12 : return error_mark_node;
4929 : /* If we have a template-id, then no further lookup is
4930 : required. If the template-id was for a template-class, we
4931 : will sometimes have a TYPE_DECL at this point. */
4932 807553839 : else if (TREE_CODE (decl) == TEMPLATE_ID_EXPR
4933 751284378 : || TREE_CODE (decl) == TYPE_DECL)
4934 : ;
4935 : /* Look up the name. */
4936 : else
4937 : {
4938 751283453 : if (decl == error_mark_node)
4939 : {
4940 : /* Name lookup failed. */
4941 133424 : if (scope
4942 374 : && !dependent_namespace_p (scope)
4943 133798 : && (!TYPE_P (scope)
4944 119 : || (!dependentish_scope_p (scope)
4945 115 : && !(identifier_p (id_expression)
4946 100 : && IDENTIFIER_CONV_OP_P (id_expression)
4947 3 : && dependent_type_p (TREE_TYPE (id_expression))))))
4948 : {
4949 : /* If the qualifying type is non-dependent (and the name
4950 : does not name a conversion operator to a dependent
4951 : type), issue an error. */
4952 364 : qualified_name_lookup_error (scope, id_expression, decl, location);
4953 364 : return error_mark_node;
4954 : }
4955 133060 : else if (!scope)
4956 : {
4957 : /* It may be resolved via Koenig lookup. */
4958 133050 : *idk = CP_ID_KIND_UNQUALIFIED;
4959 133050 : return id_expression;
4960 : }
4961 : else
4962 : decl = id_expression;
4963 : }
4964 :
4965 : /* Remember that the name was used in the definition of
4966 : the current class so that we can check later to see if
4967 : the meaning would have been different after the class
4968 : was entirely defined. */
4969 751150029 : if (!scope && decl != error_mark_node && identifier_p (id_expression))
4970 671623679 : maybe_note_name_used_in_class (id_expression, decl);
4971 :
4972 : /* A use in unevaluated operand might not be instantiated appropriately
4973 : if tsubst_copy builds a dummy parm, or if we never instantiate a
4974 : generic lambda, so mark it now. */
4975 751150039 : if (processing_template_decl
4976 751150039 : && (cp_unevaluated_operand
4977 650027359 : || generic_lambda_fn_p (current_function_decl)))
4978 21000413 : mark_type_use (decl);
4979 :
4980 : /* Disallow uses of local variables from containing functions, except
4981 : within lambda-expressions. */
4982 751150039 : if (outer_automatic_var_p (decl))
4983 : {
4984 3888069 : decl = process_outer_var_ref (decl, tf_warning_or_error);
4985 3888069 : if (decl == error_mark_node)
4986 92 : return error_mark_node;
4987 : }
4988 :
4989 : /* Also disallow uses of function parameters outside the function
4990 : body, except inside an unevaluated context (i.e. decltype). */
4991 751149947 : if (TREE_CODE (decl) == PARM_DECL
4992 313132005 : && DECL_CONTEXT (decl) == NULL_TREE
4993 8483070 : && !CONSTRAINT_VAR_P (decl)
4994 4550769 : && !cp_unevaluated_operand
4995 595 : && !processing_contract_condition
4996 751150003 : && !processing_omp_trait_property_expr)
4997 : {
4998 38 : *error_msg = G_("use of parameter outside function body");
4999 38 : return error_mark_node;
5000 : }
5001 : }
5002 :
5003 : /* If we didn't find anything, or what we found was a type,
5004 : then this wasn't really an id-expression. */
5005 807420295 : if (TREE_CODE (decl) == TEMPLATE_DECL
5006 807420295 : && !DECL_FUNCTION_TEMPLATE_P (decl))
5007 : {
5008 51 : *error_msg = G_("missing template arguments");
5009 51 : return error_mark_node;
5010 : }
5011 807420244 : else if (TREE_CODE (decl) == TYPE_DECL
5012 807419319 : || TREE_CODE (decl) == NAMESPACE_DECL)
5013 : {
5014 940 : *error_msg = G_("expected primary-expression");
5015 940 : return error_mark_node;
5016 : }
5017 :
5018 : /* If the name resolved to a template parameter, there is no
5019 : need to look it up again later. */
5020 34491915 : if ((TREE_CODE (decl) == CONST_DECL && DECL_TEMPLATE_PARM_P (decl))
5021 821761106 : || TREE_CODE (decl) == TEMPLATE_PARM_INDEX)
5022 : {
5023 20150113 : tree r;
5024 :
5025 20150113 : *idk = CP_ID_KIND_NONE;
5026 20150113 : if (TREE_CODE (decl) == TEMPLATE_PARM_INDEX)
5027 0 : decl = TEMPLATE_PARM_DECL (decl);
5028 20150113 : r = DECL_INITIAL (decl);
5029 20150113 : if (CLASS_TYPE_P (TREE_TYPE (r)) && !CP_TYPE_CONST_P (TREE_TYPE (r)))
5030 : {
5031 : /* If the entity is a template parameter object for a template
5032 : parameter of type T, the type of the expression is const T. */
5033 2969 : tree ctype = TREE_TYPE (r);
5034 2969 : ctype = cp_build_qualified_type (ctype, (cp_type_quals (ctype)
5035 : | TYPE_QUAL_CONST));
5036 2969 : r = build1 (VIEW_CONVERT_EXPR, ctype, r);
5037 : }
5038 20150113 : r = convert_from_reference (r);
5039 20150113 : if (integral_constant_expression_p
5040 3500993 : && !dependent_type_p (TREE_TYPE (decl))
5041 23144095 : && !(INTEGRAL_OR_ENUMERATION_TYPE_P (TREE_TYPE (r))))
5042 : {
5043 1039 : if (!allow_non_integral_constant_expression_p)
5044 6 : error ("template parameter %qD of type %qT is not allowed in "
5045 : "an integral constant expression because it is not of "
5046 6 : "integral or enumeration type", decl, TREE_TYPE (decl));
5047 1039 : *non_integral_constant_expression_p = true;
5048 : }
5049 :
5050 20150113 : if (flag_contracts && processing_contract_condition)
5051 27 : r = constify_contract_access (r);
5052 :
5053 20150113 : return r;
5054 : }
5055 787269191 : else if (TREE_CODE (decl) == UNBOUND_CLASS_TEMPLATE)
5056 : {
5057 9 : gcc_checking_assert (scope);
5058 9 : *idk = CP_ID_KIND_QUALIFIED;
5059 9 : cp_warn_deprecated_use_scopes (scope);
5060 9 : decl = finish_qualified_id_expr (scope, decl, done, address_p,
5061 : template_p, template_arg_p,
5062 : tf_warning_or_error);
5063 : }
5064 : else
5065 : {
5066 787269182 : if (TREE_CODE (decl) == TEMPLATE_ID_EXPR
5067 56269461 : && variable_template_p (TREE_OPERAND (decl, 0))
5068 800004181 : && !concept_check_p (decl))
5069 : /* Try resolving this variable TEMPLATE_ID_EXPR (which is always
5070 : considered type-dependent) now, so that the dependence test that
5071 : follows gives us the right answer: if it represents a non-dependent
5072 : variable template-id then finish_template_variable will yield the
5073 : corresponding non-dependent VAR_DECL. */
5074 12734999 : decl = finish_template_variable (decl);
5075 :
5076 787269182 : bool dependent_p = type_dependent_expression_p (decl);
5077 :
5078 : /* If the declaration was explicitly qualified indicate
5079 : that. The semantics of `A::f(3)' are different than
5080 : `f(3)' if `f' is virtual. */
5081 1574538364 : *idk = (scope
5082 787269182 : ? CP_ID_KIND_QUALIFIED
5083 684810156 : : (TREE_CODE (decl) == TEMPLATE_ID_EXPR
5084 684810156 : ? CP_ID_KIND_TEMPLATE_ID
5085 : : (dependent_p
5086 651768442 : ? CP_ID_KIND_UNQUALIFIED_DEPENDENT
5087 : : CP_ID_KIND_UNQUALIFIED)));
5088 :
5089 787269182 : if (dependent_p
5090 787269182 : && !scope
5091 451536290 : && DECL_P (decl)
5092 1206872418 : && any_dependent_type_attributes_p (DECL_ATTRIBUTES (decl)))
5093 : /* Dependent type attributes on the decl mean that the TREE_TYPE is
5094 : wrong, so just return the identifier. */
5095 39 : return id_expression;
5096 :
5097 787269143 : if (DECL_CLASS_TEMPLATE_P (decl))
5098 : {
5099 0 : error ("use of class template %qT as expression", decl);
5100 0 : return error_mark_node;
5101 : }
5102 :
5103 787269143 : if (TREE_CODE (decl) == TREE_LIST)
5104 : {
5105 : /* Ambiguous reference to base members. */
5106 0 : auto_diagnostic_group d;
5107 0 : error ("request for member %qD is ambiguous in "
5108 : "multiple inheritance lattice", id_expression);
5109 0 : print_candidates (input_location, decl);
5110 0 : return error_mark_node;
5111 0 : }
5112 :
5113 : /* Mark variable-like entities as used. Functions are similarly
5114 : marked either below or after overload resolution. */
5115 787269143 : if ((VAR_P (decl)
5116 570722703 : || TREE_CODE (decl) == PARM_DECL
5117 257590742 : || TREE_CODE (decl) == CONST_DECL
5118 243248940 : || TREE_CODE (decl) == RESULT_DECL)
5119 1114742906 : && !mark_used (decl))
5120 12 : return error_mark_node;
5121 :
5122 : /* Only certain kinds of names are allowed in constant
5123 : expression. Template parameters have already
5124 : been handled above. */
5125 787269128 : if (! error_operand_p (decl)
5126 787268800 : && !dependent_p
5127 787268800 : && integral_constant_expression_p
5128 79332652 : && !decl_constant_var_p (decl)
5129 64507852 : && TREE_CODE (decl) != CONST_DECL
5130 55671222 : && !builtin_valid_in_constant_expr_p (decl)
5131 842889994 : && !concept_check_p (decl))
5132 : {
5133 55041826 : if (!allow_non_integral_constant_expression_p)
5134 : {
5135 31 : error ("%qD cannot appear in a constant-expression", decl);
5136 31 : return error_mark_node;
5137 : }
5138 55041795 : *non_integral_constant_expression_p = true;
5139 : }
5140 :
5141 787269097 : if (tree wrap = maybe_get_tls_wrapper_call (decl))
5142 : /* Replace an evaluated use of the thread_local variable with
5143 : a call to its wrapper. */
5144 : decl = wrap;
5145 787268585 : else if (concept_check_p (decl))
5146 : {
5147 : /* Nothing more to do. All of the analysis for concept checks
5148 : is done by build_conept_id, called from the parser. */
5149 : }
5150 769926268 : else if (scope)
5151 : {
5152 100465395 : if (TREE_CODE (decl) == SCOPE_REF)
5153 : {
5154 91659 : gcc_assert (same_type_p (scope, TREE_OPERAND (decl, 0)));
5155 91659 : decl = TREE_OPERAND (decl, 1);
5156 : }
5157 :
5158 100465395 : decl = (adjust_result_of_qualified_name_lookup
5159 100465395 : (decl, scope, current_nonlambda_class_type()));
5160 :
5161 100465395 : cp_warn_deprecated_use_scopes (scope);
5162 :
5163 100465395 : if (TYPE_P (scope))
5164 14367395 : decl = finish_qualified_id_expr (scope,
5165 : decl,
5166 : done,
5167 : address_p,
5168 : template_p,
5169 : template_arg_p,
5170 : tf_warning_or_error);
5171 : else
5172 86098000 : decl = convert_from_reference (decl);
5173 : }
5174 669460873 : else if (TREE_CODE (decl) == FIELD_DECL)
5175 : {
5176 69622315 : if (flag_contracts && processing_contract_condition
5177 37 : && contract_class_ptr == current_class_ptr)
5178 : {
5179 6 : error ("%qD 'this' required when accessing a member within a "
5180 : "constructor precondition or destructor postcondition "
5181 : "contract check", decl);
5182 6 : return error_mark_node;
5183 : }
5184 : /* Since SCOPE is NULL here, this is an unqualified name.
5185 : Access checking has been performed during name lookup
5186 : already. Turn off checking to avoid duplicate errors. */
5187 69622309 : push_deferring_access_checks (dk_no_check);
5188 69622309 : decl = finish_non_static_data_member (decl, NULL_TREE,
5189 : /*qualifying_scope=*/NULL_TREE);
5190 69622309 : pop_deferring_access_checks ();
5191 : }
5192 599838558 : else if (is_overloaded_fn (decl))
5193 : {
5194 : /* We only need to look at the first function,
5195 : because all the fns share the attribute we're
5196 : concerned with (all member fns or all non-members). */
5197 64413182 : tree first_fn = get_first_fn (decl);
5198 64413182 : first_fn = STRIP_TEMPLATE (first_fn);
5199 :
5200 64413182 : if (!template_arg_p
5201 64413182 : && (TREE_CODE (first_fn) == USING_DECL
5202 64411292 : || (TREE_CODE (first_fn) == FUNCTION_DECL
5203 64411292 : && DECL_FUNCTION_MEMBER_P (first_fn)
5204 39457086 : && !shared_member_p (decl))))
5205 : {
5206 : /* A set of member functions. */
5207 30408529 : if (flag_contracts && processing_contract_condition
5208 24 : && contract_class_ptr == current_class_ptr)
5209 : {
5210 3 : error ("%qD 'this' required when accessing a member within a "
5211 : "constructor precondition or destructor postcondition "
5212 : "contract check", decl);
5213 3 : return error_mark_node;
5214 : }
5215 30408526 : decl = maybe_dummy_object (DECL_CONTEXT (first_fn), 0);
5216 30408526 : return finish_class_member_access_expr (decl, id_expression,
5217 : /*template_p=*/false,
5218 30408526 : tf_warning_or_error);
5219 : }
5220 :
5221 34004653 : decl = baselink_for_fns (decl);
5222 : }
5223 : else
5224 : {
5225 523658520 : if (DECL_P (decl) && DECL_NONLOCAL (decl)
5226 536962889 : && DECL_CLASS_SCOPE_P (decl))
5227 : {
5228 1537513 : tree context = context_for_name_lookup (decl);
5229 1537513 : if (context != current_class_type)
5230 : {
5231 804316 : tree path = currently_open_derived_class (context);
5232 804316 : if (!path)
5233 : /* PATH can be null for using an enum of an unrelated
5234 : class; we checked its access in lookup_using_decl.
5235 :
5236 : ??? Should this case make a clone instead, like
5237 : handle_using_decl? */
5238 43 : gcc_assert (TREE_CODE (decl) == CONST_DECL
5239 : /* This is for:
5240 : constexpr auto r = ^^S::i;
5241 : auto a = [:r:]; */
5242 : || flag_reflection);
5243 : else
5244 804273 : perform_or_defer_access_check (TYPE_BINFO (path),
5245 : decl, decl,
5246 : tf_warning_or_error);
5247 : }
5248 : }
5249 :
5250 535425376 : decl = convert_from_reference (decl);
5251 : }
5252 : }
5253 :
5254 756860571 : check_param_in_postcondition (decl, location);
5255 756860571 : if (flag_contracts && processing_contract_condition)
5256 2184 : decl = constify_contract_access (decl);
5257 :
5258 756860571 : return cp_expr (decl, location);
5259 : }
5260 :
5261 : /* As per finish_id_expression_1, but adding a wrapper node
5262 : around the result if needed to express LOCATION. */
5263 :
5264 : cp_expr
5265 807553851 : finish_id_expression (tree id_expression,
5266 : tree decl,
5267 : tree scope,
5268 : cp_id_kind *idk,
5269 : bool integral_constant_expression_p,
5270 : bool allow_non_integral_constant_expression_p,
5271 : bool *non_integral_constant_expression_p,
5272 : bool template_p,
5273 : bool done,
5274 : bool address_p,
5275 : bool template_arg_p,
5276 : const char **error_msg,
5277 : location_t location)
5278 : {
5279 807553851 : cp_expr result
5280 807553851 : = finish_id_expression_1 (id_expression, decl, scope, idk,
5281 : integral_constant_expression_p,
5282 : allow_non_integral_constant_expression_p,
5283 : non_integral_constant_expression_p,
5284 : template_p, done, address_p, template_arg_p,
5285 : error_msg, location);
5286 807553848 : return result.maybe_add_location_wrapper ();
5287 : }
5288 :
5289 : /* Implement the __typeof keyword: Return the type of EXPR, suitable for
5290 : use as a type-specifier. */
5291 :
5292 : tree
5293 22433982 : finish_typeof (tree expr)
5294 : {
5295 22433982 : tree type;
5296 :
5297 22433982 : if (type_dependent_expression_p (expr))
5298 : {
5299 22340719 : type = cxx_make_type (TYPEOF_TYPE);
5300 22340719 : TYPEOF_TYPE_EXPR (type) = expr;
5301 22340719 : SET_TYPE_STRUCTURAL_EQUALITY (type);
5302 :
5303 22340719 : return type;
5304 : }
5305 :
5306 93263 : expr = mark_type_use (expr);
5307 :
5308 93263 : type = unlowered_expr_type (expr);
5309 :
5310 93263 : if (!type || type == unknown_type_node)
5311 : {
5312 3 : error ("type of %qE is unknown", expr);
5313 3 : return error_mark_node;
5314 : }
5315 :
5316 : return type;
5317 : }
5318 :
5319 : /* Implement the __underlying_type keyword: Return the underlying
5320 : type of TYPE, suitable for use as a type-specifier. */
5321 :
5322 : tree
5323 49045 : finish_underlying_type (tree type)
5324 : {
5325 49045 : if (!complete_type_or_else (type, NULL_TREE))
5326 3 : return error_mark_node;
5327 :
5328 49042 : if (TREE_CODE (type) != ENUMERAL_TYPE)
5329 : {
5330 24 : error ("%qT is not an enumeration type", type);
5331 24 : return error_mark_node;
5332 : }
5333 :
5334 49018 : tree underlying_type = ENUM_UNDERLYING_TYPE (type);
5335 :
5336 : /* Fixup necessary in this case because ENUM_UNDERLYING_TYPE
5337 : includes TYPE_MIN_VALUE and TYPE_MAX_VALUE information.
5338 : See finish_enum_value_list for details. */
5339 49018 : if (!ENUM_FIXED_UNDERLYING_TYPE_P (type))
5340 56 : underlying_type
5341 56 : = c_common_type_for_mode (TYPE_MODE (underlying_type),
5342 56 : TYPE_UNSIGNED (underlying_type));
5343 :
5344 : return underlying_type;
5345 : }
5346 :
5347 : /* Implement the __type_pack_element keyword: Return the type
5348 : at index IDX within TYPES. */
5349 :
5350 : static tree
5351 136054 : finish_type_pack_element (tree idx, tree types, tsubst_flags_t complain)
5352 : {
5353 136054 : idx = maybe_constant_value (idx, NULL_TREE, mce_true);
5354 136054 : if (!INTEGRAL_TYPE_P (TREE_TYPE (idx)))
5355 : {
5356 6 : if (complain & tf_error)
5357 3 : error ("pack index has non-integral type %qT", TREE_TYPE (idx));
5358 6 : return error_mark_node;
5359 : }
5360 136048 : if (TREE_CODE (idx) != INTEGER_CST)
5361 : {
5362 2 : if (complain & tf_error)
5363 : {
5364 2 : error ("pack index is not an integral constant");
5365 2 : cxx_constant_value (idx);
5366 : }
5367 2 : return error_mark_node;
5368 : }
5369 136046 : if (tree_int_cst_sgn (idx) < 0)
5370 : {
5371 3 : if (complain & tf_error)
5372 3 : error ("pack index %qE is negative", idx);
5373 3 : return error_mark_node;
5374 : }
5375 136043 : if (wi::to_widest (idx) >= TREE_VEC_LENGTH (types))
5376 : {
5377 35 : if (complain & tf_error)
5378 29 : error ("pack index %qE is out of range for pack of length %qd",
5379 29 : idx, TREE_VEC_LENGTH (types));
5380 35 : return error_mark_node;
5381 : }
5382 136008 : return TREE_VEC_ELT (types, tree_to_shwi (idx));
5383 : }
5384 :
5385 : /* In a pack-index T...[N], return the element at index IDX within TYPES.
5386 : PARENTHESIZED_P is true iff the pack index was wrapped in (). */
5387 :
5388 : tree
5389 22552 : pack_index_element (tree idx, tree types, bool parenthesized_p,
5390 : tsubst_flags_t complain)
5391 : {
5392 22552 : tree r = finish_type_pack_element (idx, types, complain);
5393 22552 : if (parenthesized_p)
5394 : /* For the benefit of decltype(auto). */
5395 35 : r = force_paren_expr (r);
5396 22552 : return r;
5397 : }
5398 :
5399 : /* Implement the __direct_bases keyword: Return the direct base classes
5400 : of type. */
5401 :
5402 : tree
5403 15 : calculate_direct_bases (tree type, tsubst_flags_t complain)
5404 : {
5405 15 : if (!complete_type_or_maybe_complain (type, NULL_TREE, complain)
5406 15 : || !NON_UNION_CLASS_TYPE_P (type))
5407 8 : return make_tree_vec (0);
5408 :
5409 7 : releasing_vec vector;
5410 7 : vec<tree, va_gc> *base_binfos = BINFO_BASE_BINFOS (TYPE_BINFO (type));
5411 7 : tree binfo;
5412 7 : unsigned i;
5413 :
5414 : /* Virtual bases are initialized first */
5415 20 : for (i = 0; base_binfos->iterate (i, &binfo); i++)
5416 13 : if (BINFO_VIRTUAL_P (binfo))
5417 2 : vec_safe_push (vector, binfo);
5418 :
5419 : /* Now non-virtuals */
5420 20 : for (i = 0; base_binfos->iterate (i, &binfo); i++)
5421 13 : if (!BINFO_VIRTUAL_P (binfo))
5422 11 : vec_safe_push (vector, binfo);
5423 :
5424 7 : tree bases_vec = make_tree_vec (vector->length ());
5425 :
5426 27 : for (i = 0; i < vector->length (); ++i)
5427 13 : TREE_VEC_ELT (bases_vec, i) = BINFO_TYPE ((*vector)[i]);
5428 :
5429 7 : return bases_vec;
5430 7 : }
5431 :
5432 : /* Implement the __bases keyword: Return the base classes
5433 : of type */
5434 :
5435 : /* Find morally non-virtual base classes by walking binfo hierarchy */
5436 : /* Virtual base classes are handled separately in finish_bases */
5437 :
5438 : static tree
5439 73 : dfs_calculate_bases_pre (tree binfo, void * /*data_*/)
5440 : {
5441 : /* Don't walk bases of virtual bases */
5442 73 : return BINFO_VIRTUAL_P (binfo) ? dfs_skip_bases : NULL_TREE;
5443 : }
5444 :
5445 : static tree
5446 73 : dfs_calculate_bases_post (tree binfo, void *data_)
5447 : {
5448 73 : vec<tree, va_gc> **data = ((vec<tree, va_gc> **) data_);
5449 73 : if (!BINFO_VIRTUAL_P (binfo))
5450 48 : vec_safe_push (*data, BINFO_TYPE (binfo));
5451 73 : return NULL_TREE;
5452 : }
5453 :
5454 : /* Calculates the morally non-virtual base classes of a class */
5455 : static vec<tree, va_gc> *
5456 16 : calculate_bases_helper (tree type)
5457 : {
5458 16 : vec<tree, va_gc> *vector = make_tree_vector ();
5459 :
5460 : /* Now add non-virtual base classes in order of construction */
5461 16 : if (TYPE_BINFO (type))
5462 16 : dfs_walk_all (TYPE_BINFO (type),
5463 : dfs_calculate_bases_pre, dfs_calculate_bases_post, &vector);
5464 16 : return vector;
5465 : }
5466 :
5467 : tree
5468 12 : calculate_bases (tree type, tsubst_flags_t complain)
5469 : {
5470 12 : if (!complete_type_or_maybe_complain (type, NULL_TREE, complain)
5471 12 : || !NON_UNION_CLASS_TYPE_P (type))
5472 5 : return make_tree_vec (0);
5473 :
5474 7 : releasing_vec vector;
5475 7 : tree bases_vec = NULL_TREE;
5476 7 : unsigned i;
5477 7 : vec<tree, va_gc> *vbases;
5478 7 : tree binfo;
5479 :
5480 : /* First go through virtual base classes */
5481 7 : for (vbases = CLASSTYPE_VBASECLASSES (type), i = 0;
5482 16 : vec_safe_iterate (vbases, i, &binfo); i++)
5483 : {
5484 9 : releasing_vec vbase_bases
5485 9 : = calculate_bases_helper (BINFO_TYPE (binfo));
5486 9 : vec_safe_splice (vector, vbase_bases);
5487 9 : }
5488 :
5489 : /* Now for the non-virtual bases */
5490 7 : releasing_vec nonvbases = calculate_bases_helper (type);
5491 7 : vec_safe_splice (vector, nonvbases);
5492 :
5493 : /* Note that during error recovery vector->length can even be zero. */
5494 7 : if (vector->length () > 1)
5495 : {
5496 : /* Last element is entire class, so don't copy */
5497 6 : bases_vec = make_tree_vec (vector->length () - 1);
5498 :
5499 53 : for (i = 0; i < vector->length () - 1; ++i)
5500 41 : TREE_VEC_ELT (bases_vec, i) = (*vector)[i];
5501 : }
5502 : else
5503 1 : bases_vec = make_tree_vec (0);
5504 :
5505 7 : return bases_vec;
5506 7 : }
5507 :
5508 : tree
5509 28 : finish_bases (tree type, bool direct)
5510 : {
5511 28 : tree bases = NULL_TREE;
5512 :
5513 28 : if (!processing_template_decl)
5514 : {
5515 : /* Parameter packs can only be used in templates */
5516 0 : error ("parameter pack %<__bases%> only valid in template declaration");
5517 0 : return error_mark_node;
5518 : }
5519 :
5520 28 : bases = cxx_make_type (BASES);
5521 28 : BASES_TYPE (bases) = type;
5522 28 : BASES_DIRECT (bases) = direct;
5523 28 : SET_TYPE_STRUCTURAL_EQUALITY (bases);
5524 :
5525 28 : return bases;
5526 : }
5527 :
5528 : /* Perform C++-specific checks for __builtin_offsetof before calling
5529 : fold_offsetof. */
5530 :
5531 : tree
5532 2497 : finish_offsetof (tree object_ptr, tree expr, location_t loc)
5533 : {
5534 : /* If we're processing a template, we can't finish the semantics yet.
5535 : Otherwise we can fold the entire expression now. */
5536 2497 : if (processing_template_decl)
5537 : {
5538 60 : expr = build2 (OFFSETOF_EXPR, size_type_node, expr, object_ptr);
5539 60 : SET_EXPR_LOCATION (expr, loc);
5540 60 : return expr;
5541 : }
5542 :
5543 2437 : if (expr == error_mark_node)
5544 : return error_mark_node;
5545 :
5546 2420 : if (TREE_CODE (expr) == PSEUDO_DTOR_EXPR)
5547 : {
5548 6 : error ("cannot apply %<offsetof%> to destructor %<~%T%>",
5549 6 : TREE_OPERAND (expr, 2));
5550 6 : return error_mark_node;
5551 : }
5552 4813 : if (FUNC_OR_METHOD_TYPE_P (TREE_TYPE (expr))
5553 4813 : || TREE_TYPE (expr) == unknown_type_node)
5554 : {
5555 30 : while (TREE_CODE (expr) == COMPONENT_REF
5556 30 : || TREE_CODE (expr) == COMPOUND_EXPR)
5557 12 : expr = TREE_OPERAND (expr, 1);
5558 :
5559 18 : if (DECL_P (expr))
5560 : {
5561 0 : auto_diagnostic_group d;
5562 0 : error ("cannot apply %<offsetof%> to member function %qD", expr);
5563 0 : inform (DECL_SOURCE_LOCATION (expr), "declared here");
5564 0 : }
5565 : else
5566 18 : error ("cannot apply %<offsetof%> to member function");
5567 18 : return error_mark_node;
5568 : }
5569 2396 : if (TREE_CODE (expr) == CONST_DECL)
5570 : {
5571 3 : error ("cannot apply %<offsetof%> to an enumerator %qD", expr);
5572 3 : return error_mark_node;
5573 : }
5574 2393 : if (REFERENCE_REF_P (expr))
5575 9 : expr = TREE_OPERAND (expr, 0);
5576 2393 : if (!complete_type_or_else (TREE_TYPE (TREE_TYPE (object_ptr)), object_ptr))
5577 3 : return error_mark_node;
5578 2390 : if (warn_invalid_offsetof
5579 2390 : && CLASS_TYPE_P (TREE_TYPE (TREE_TYPE (object_ptr)))
5580 2390 : && CLASSTYPE_NON_STD_LAYOUT (TREE_TYPE (TREE_TYPE (object_ptr)))
5581 2435 : && cp_unevaluated_operand == 0)
5582 45 : warning_at (loc, OPT_Winvalid_offsetof, "%<offsetof%> within "
5583 : "non-standard-layout type %qT is conditionally-supported",
5584 45 : TREE_TYPE (TREE_TYPE (object_ptr)));
5585 2390 : return fold_offsetof (expr);
5586 : }
5587 :
5588 : /* Replace the AGGR_INIT_EXPR at *TP with an equivalent CALL_EXPR. This
5589 : function is broken out from the above for the benefit of the tree-ssa
5590 : project. */
5591 :
5592 : void
5593 376884 : simplify_aggr_init_expr (tree *tp)
5594 : {
5595 376884 : tree aggr_init_expr = *tp;
5596 :
5597 : /* Form an appropriate CALL_EXPR. */
5598 376884 : tree fn = AGGR_INIT_EXPR_FN (aggr_init_expr);
5599 376884 : tree slot = AGGR_INIT_EXPR_SLOT (aggr_init_expr);
5600 376884 : tree type = TREE_TYPE (slot);
5601 :
5602 376884 : tree call_expr;
5603 376884 : enum style_t { ctor, arg, pcc } style;
5604 :
5605 376884 : if (AGGR_INIT_VIA_CTOR_P (aggr_init_expr))
5606 : style = ctor;
5607 : #ifdef PCC_STATIC_STRUCT_RETURN
5608 : else if (1)
5609 : style = pcc;
5610 : #endif
5611 : else
5612 : {
5613 101143 : gcc_assert (TREE_ADDRESSABLE (type));
5614 : style = arg;
5615 : }
5616 :
5617 376884 : call_expr = build_call_array_loc (input_location,
5618 376884 : TREE_TYPE (TREE_TYPE (TREE_TYPE (fn))),
5619 : fn,
5620 376884 : aggr_init_expr_nargs (aggr_init_expr),
5621 376884 : AGGR_INIT_EXPR_ARGP (aggr_init_expr));
5622 376884 : TREE_NOTHROW (call_expr) = TREE_NOTHROW (aggr_init_expr);
5623 376884 : CALL_FROM_THUNK_P (call_expr) = AGGR_INIT_FROM_THUNK_P (aggr_init_expr);
5624 376884 : CALL_EXPR_OPERATOR_SYNTAX (call_expr)
5625 376884 : = CALL_EXPR_OPERATOR_SYNTAX (aggr_init_expr);
5626 376884 : CALL_EXPR_ORDERED_ARGS (call_expr) = CALL_EXPR_ORDERED_ARGS (aggr_init_expr);
5627 376884 : CALL_EXPR_REVERSE_ARGS (call_expr) = CALL_EXPR_REVERSE_ARGS (aggr_init_expr);
5628 376884 : CALL_EXPR_MUST_TAIL_CALL (call_expr) = AGGR_INIT_EXPR_MUST_TAIL (aggr_init_expr);
5629 :
5630 376884 : if (style == ctor)
5631 : {
5632 : /* Replace the first argument to the ctor with the address of the
5633 : slot. */
5634 275741 : cxx_mark_addressable (slot);
5635 275741 : CALL_EXPR_ARG (call_expr, 0) =
5636 275741 : build1 (ADDR_EXPR, build_pointer_type (type), slot);
5637 : }
5638 101143 : else if (style == arg)
5639 : {
5640 : /* Just mark it addressable here, and leave the rest to
5641 : expand_call{,_inline}. */
5642 101143 : cxx_mark_addressable (slot);
5643 101143 : CALL_EXPR_RETURN_SLOT_OPT (call_expr) = true;
5644 101143 : call_expr = cp_build_init_expr (slot, call_expr);
5645 : }
5646 : else if (style == pcc)
5647 : {
5648 : /* If we're using the non-reentrant PCC calling convention, then we
5649 : need to copy the returned value out of the static buffer into the
5650 : SLOT. */
5651 : push_deferring_access_checks (dk_no_check);
5652 : call_expr = build_aggr_init (slot, call_expr,
5653 : DIRECT_BIND | LOOKUP_ONLYCONVERTING,
5654 : tf_warning_or_error);
5655 : pop_deferring_access_checks ();
5656 : call_expr = build2 (COMPOUND_EXPR, TREE_TYPE (slot), call_expr, slot);
5657 : }
5658 :
5659 376884 : if (AGGR_INIT_ZERO_FIRST (aggr_init_expr))
5660 : {
5661 4198 : tree init = build_zero_init (type, NULL_TREE,
5662 : /*static_storage_p=*/false);
5663 4198 : init = cp_build_init_expr (slot, init);
5664 4198 : call_expr = build2 (COMPOUND_EXPR, TREE_TYPE (call_expr),
5665 : init, call_expr);
5666 : }
5667 :
5668 376884 : *tp = call_expr;
5669 376884 : }
5670 :
5671 : /* Emit all thunks to FN that should be emitted when FN is emitted. */
5672 :
5673 : void
5674 61810988 : emit_associated_thunks (tree fn)
5675 : {
5676 : /* When we use vcall offsets, we emit thunks with the virtual
5677 : functions to which they thunk. The whole point of vcall offsets
5678 : is so that you can know statically the entire set of thunks that
5679 : will ever be needed for a given virtual function, thereby
5680 : enabling you to output all the thunks with the function itself. */
5681 61810988 : if (DECL_VIRTUAL_P (fn)
5682 : /* Do not emit thunks for extern template instantiations. */
5683 1176719 : && ! DECL_REALLY_EXTERN (fn)
5684 : /* Do not emit thunks for tentative decls, those will be processed
5685 : again at_eof if really needed. */
5686 62869525 : && (DECL_INTERFACE_KNOWN (fn) || !DECL_DEFER_OUTPUT (fn)))
5687 : {
5688 1057366 : tree thunk;
5689 :
5690 1061836 : for (thunk = DECL_THUNKS (fn); thunk; thunk = DECL_CHAIN (thunk))
5691 : {
5692 4470 : if (!THUNK_ALIAS (thunk))
5693 : {
5694 4470 : use_thunk (thunk, /*emit_p=*/1);
5695 4470 : if (DECL_RESULT_THUNK_P (thunk))
5696 : {
5697 181 : tree probe;
5698 :
5699 181 : for (probe = DECL_THUNKS (thunk);
5700 333 : probe; probe = DECL_CHAIN (probe))
5701 152 : use_thunk (probe, /*emit_p=*/1);
5702 : }
5703 : }
5704 : else
5705 0 : gcc_assert (!DECL_THUNKS (thunk));
5706 : }
5707 : }
5708 61810988 : }
5709 :
5710 : /* Generate RTL for FN. */
5711 :
5712 : bool
5713 168322043 : expand_or_defer_fn_1 (tree fn)
5714 : {
5715 : /* When the parser calls us after finishing the body of a template
5716 : function, we don't really want to expand the body. */
5717 168322043 : if (processing_template_decl)
5718 : {
5719 : /* Normally, collection only occurs in rest_of_compilation. So,
5720 : if we don't collect here, we never collect junk generated
5721 : during the processing of templates until we hit a
5722 : non-template function. It's not safe to do this inside a
5723 : nested class, though, as the parser may have local state that
5724 : is not a GC root. */
5725 98241396 : if (!function_depth)
5726 97785170 : ggc_collect ();
5727 : return false;
5728 : }
5729 :
5730 70080647 : gcc_assert (DECL_SAVED_TREE (fn));
5731 :
5732 : /* We make a decision about linkage for these functions at the end
5733 : of the compilation. Until that point, we do not want the back
5734 : end to output them -- but we do want it to see the bodies of
5735 : these functions so that it can inline them as appropriate. */
5736 70080647 : if (DECL_DECLARED_INLINE_P (fn)
5737 1968614 : || DECL_IMPLICIT_INSTANTIATION (fn)
5738 70345203 : || DECL_FRIEND_PSEUDO_TEMPLATE_INSTANTIATION (fn))
5739 : {
5740 69816118 : if (DECL_INTERFACE_KNOWN (fn))
5741 : /* We've already made a decision as to how this function will
5742 : be handled. */;
5743 49376390 : else if (!at_eof
5744 17789498 : || DECL_IMMEDIATE_FUNCTION_P (fn)
5745 66728606 : || DECL_OMP_DECLARE_REDUCTION_P (fn))
5746 32024174 : tentative_decl_linkage (fn);
5747 : else
5748 17352216 : import_export_decl (fn);
5749 :
5750 : /* If the user wants us to keep all inline functions, then mark
5751 : this function as needed so that finish_file will make sure to
5752 : output it later. Similarly, all dllexport'd functions must
5753 : be emitted; there may be callers in other DLLs. */
5754 69816118 : if (DECL_DECLARED_INLINE_P (fn)
5755 68112033 : && !DECL_REALLY_EXTERN (fn)
5756 64348287 : && !DECL_IMMEDIATE_FUNCTION_P (fn)
5757 63293775 : && !DECL_OMP_DECLARE_REDUCTION_P (fn)
5758 133109893 : && (flag_keep_inline_functions
5759 63290982 : || (flag_keep_inline_dllexport
5760 63290982 : && lookup_attribute ("dllexport", DECL_ATTRIBUTES (fn)))))
5761 : {
5762 2793 : mark_needed (fn);
5763 2793 : DECL_EXTERNAL (fn) = 0;
5764 : }
5765 : }
5766 :
5767 : /* If this is a constructor or destructor body, we have to clone
5768 : it. */
5769 70080647 : if (maybe_clone_body (fn))
5770 : {
5771 : /* We don't want to process FN again, so pretend we've written
5772 : it out, even though we haven't. */
5773 8241453 : TREE_ASM_WRITTEN (fn) = 1;
5774 : /* If this is a constexpr function we still need the body to be
5775 : able to evaluate it. Similarly, with modules we only stream
5776 : the maybe-in-charge cdtor and regenerate the clones from it on
5777 : demand, so we also need to keep the body. Otherwise we don't
5778 : need it anymore. */
5779 8241453 : if (!maybe_constexpr_fn (fn)
5780 8241453 : && !(module_maybe_has_cmi_p () && vague_linkage_p (fn)))
5781 3849960 : DECL_SAVED_TREE (fn) = void_node;
5782 : return false;
5783 : }
5784 :
5785 : /* There's no reason to do any of the work here if we're only doing
5786 : semantic analysis; this code just generates RTL. */
5787 61839194 : if (flag_syntax_only)
5788 : {
5789 : /* Pretend that this function has been written out so that we don't try
5790 : to expand it again. */
5791 28190 : TREE_ASM_WRITTEN (fn) = 1;
5792 28190 : return false;
5793 : }
5794 :
5795 61811004 : if (DECL_OMP_DECLARE_REDUCTION_P (fn))
5796 16 : return false;
5797 :
5798 : return true;
5799 : }
5800 :
5801 : void
5802 160098895 : expand_or_defer_fn (tree fn)
5803 : {
5804 160098895 : if (expand_or_defer_fn_1 (fn))
5805 : {
5806 53590331 : function_depth++;
5807 :
5808 : /* Expand or defer, at the whim of the compilation unit manager. */
5809 53590331 : cgraph_node::finalize_function (fn, function_depth > 1);
5810 53590331 : emit_associated_thunks (fn);
5811 :
5812 53590331 : function_depth--;
5813 :
5814 107180662 : if (DECL_IMMEDIATE_FUNCTION_P (fn))
5815 : {
5816 1009928 : if (cgraph_node *node = cgraph_node::get (fn))
5817 : {
5818 1009928 : node->body_removed = true;
5819 1009928 : node->analyzed = false;
5820 1009928 : node->definition = false;
5821 1009928 : node->force_output = false;
5822 : }
5823 : }
5824 : }
5825 160098895 : }
5826 :
5827 469654 : class nrv_data
5828 : {
5829 : public:
5830 234827 : nrv_data () : visited (37) {}
5831 :
5832 : tree var;
5833 : tree result;
5834 : hash_set<tree> visited;
5835 : bool simple;
5836 : bool in_nrv_cleanup;
5837 : };
5838 :
5839 : /* Helper function for walk_tree, used by finalize_nrv below. */
5840 :
5841 : static tree
5842 21274151 : finalize_nrv_r (tree* tp, int* walk_subtrees, void* data)
5843 : {
5844 21274151 : class nrv_data *dp = (class nrv_data *)data;
5845 :
5846 : /* No need to walk into types. There wouldn't be any need to walk into
5847 : non-statements, except that we have to consider STMT_EXPRs. */
5848 21274151 : if (TYPE_P (*tp))
5849 193862 : *walk_subtrees = 0;
5850 :
5851 : /* Replace all uses of the NRV with the RESULT_DECL. */
5852 21080289 : else if (*tp == dp->var)
5853 510236 : *tp = dp->result;
5854 :
5855 : /* Avoid walking into the same tree more than once. Unfortunately, we
5856 : can't just use walk_tree_without duplicates because it would only call
5857 : us for the first occurrence of dp->var in the function body. */
5858 20570053 : else if (dp->visited.add (*tp))
5859 4498008 : *walk_subtrees = 0;
5860 :
5861 : /* If there's a label, we might need to destroy the NRV on goto (92407). */
5862 16072045 : else if (TREE_CODE (*tp) == LABEL_EXPR && !dp->in_nrv_cleanup)
5863 3 : dp->simple = false;
5864 : /* Change NRV returns to just refer to the RESULT_DECL; this is a nop,
5865 : but differs from using NULL_TREE in that it indicates that we care
5866 : about the value of the RESULT_DECL. But preserve anything appended
5867 : by check_return_expr. */
5868 16072042 : else if (TREE_CODE (*tp) == RETURN_EXPR)
5869 : {
5870 241053 : tree *p = &TREE_OPERAND (*tp, 0);
5871 618107 : while (TREE_CODE (*p) == COMPOUND_EXPR)
5872 136001 : p = &TREE_OPERAND (*p, 0);
5873 241053 : if (TREE_CODE (*p) == INIT_EXPR
5874 241053 : && INIT_EXPR_NRV_P (*p))
5875 240643 : *p = dp->result;
5876 : }
5877 : /* Change all cleanups for the NRV to only run when not returning. */
5878 15830989 : else if (TREE_CODE (*tp) == CLEANUP_STMT
5879 15830989 : && CLEANUP_DECL (*tp) == dp->var)
5880 : {
5881 130839 : dp->in_nrv_cleanup = true;
5882 130839 : cp_walk_tree (&CLEANUP_BODY (*tp), finalize_nrv_r, data, 0);
5883 130839 : dp->in_nrv_cleanup = false;
5884 130839 : cp_walk_tree (&CLEANUP_EXPR (*tp), finalize_nrv_r, data, 0);
5885 130839 : *walk_subtrees = 0;
5886 :
5887 130839 : if (dp->simple)
5888 : /* For a simple NRV, just run it on the EH path. */
5889 130178 : CLEANUP_EH_ONLY (*tp) = true;
5890 : else
5891 : {
5892 : /* Not simple, we need to check current_retval_sentinel to decide
5893 : whether to run it. If it's set, we're returning normally and
5894 : don't want to destroy the NRV. If the sentinel is not set, we're
5895 : leaving scope some other way, either by flowing off the end of its
5896 : scope or throwing an exception. */
5897 1983 : tree cond = build3 (COND_EXPR, void_type_node,
5898 661 : current_retval_sentinel,
5899 661 : void_node, CLEANUP_EXPR (*tp));
5900 661 : CLEANUP_EXPR (*tp) = cond;
5901 : }
5902 :
5903 : /* If a cleanup might throw, we need to clear current_retval_sentinel on
5904 : the exception path, both so the check above succeeds and so an outer
5905 : cleanup added by maybe_splice_retval_cleanup doesn't run. */
5906 130839 : if (cp_function_chain->throwing_cleanup)
5907 : {
5908 220 : tree clear = build2 (MODIFY_EXPR, boolean_type_node,
5909 : current_retval_sentinel,
5910 : boolean_false_node);
5911 220 : if (dp->simple)
5912 : {
5913 : /* We're already only on the EH path, just prepend it. */
5914 210 : tree &exp = CLEANUP_EXPR (*tp);
5915 210 : exp = build2 (COMPOUND_EXPR, void_type_node, clear, exp);
5916 : }
5917 : else
5918 : {
5919 : /* The cleanup runs on both normal and EH paths, we need another
5920 : CLEANUP_STMT to clear the flag only on the EH path. */
5921 10 : tree &bod = CLEANUP_BODY (*tp);
5922 10 : bod = build_stmt (EXPR_LOCATION (*tp), CLEANUP_STMT,
5923 10 : bod, clear, current_retval_sentinel);
5924 10 : CLEANUP_EH_ONLY (bod) = true;
5925 : }
5926 : }
5927 : }
5928 : /* Disable maybe_splice_retval_cleanup within the NRV cleanup scope, we don't
5929 : want to destroy the retval before the variable goes out of scope. */
5930 15700150 : else if (TREE_CODE (*tp) == CLEANUP_STMT
5931 5192 : && dp->in_nrv_cleanup
5932 15703897 : && CLEANUP_DECL (*tp) == dp->result)
5933 6 : CLEANUP_EXPR (*tp) = void_node;
5934 : /* Replace the DECL_EXPR for the NRV with an initialization of the
5935 : RESULT_DECL, if needed. */
5936 15700144 : else if (TREE_CODE (*tp) == DECL_EXPR
5937 15700144 : && DECL_EXPR_DECL (*tp) == dp->var)
5938 : {
5939 234829 : tree init;
5940 234829 : if (DECL_INITIAL (dp->var)
5941 234829 : && DECL_INITIAL (dp->var) != error_mark_node)
5942 96141 : init = cp_build_init_expr (dp->result,
5943 96141 : DECL_INITIAL (dp->var));
5944 : else
5945 138688 : init = build_empty_stmt (EXPR_LOCATION (*tp));
5946 234829 : DECL_INITIAL (dp->var) = NULL_TREE;
5947 234829 : SET_EXPR_LOCATION (init, EXPR_LOCATION (*tp));
5948 234829 : *tp = init;
5949 : }
5950 :
5951 : /* Keep iterating. */
5952 21274151 : return NULL_TREE;
5953 : }
5954 :
5955 : /* Called from finish_function to implement the named return value
5956 : optimization by overriding all the RETURN_EXPRs and pertinent
5957 : CLEANUP_STMTs and replacing all occurrences of VAR with RESULT, the
5958 : RESULT_DECL for the function. */
5959 :
5960 : void
5961 234827 : finalize_nrv (tree fndecl, tree var)
5962 : {
5963 234827 : class nrv_data data;
5964 234827 : tree result = DECL_RESULT (fndecl);
5965 :
5966 : /* Copy name from VAR to RESULT. */
5967 234827 : DECL_NAME (result) = DECL_NAME (var);
5968 : /* Don't forget that we take its address. */
5969 234827 : TREE_ADDRESSABLE (result) = TREE_ADDRESSABLE (var);
5970 : /* Finally set DECL_VALUE_EXPR to avoid assigning
5971 : a stack slot at -O0 for the original var and debug info
5972 : uses RESULT location for VAR. */
5973 234827 : SET_DECL_VALUE_EXPR (var, result);
5974 234827 : DECL_HAS_VALUE_EXPR_P (var) = 1;
5975 :
5976 234827 : data.var = var;
5977 234827 : data.result = result;
5978 234827 : data.in_nrv_cleanup = false;
5979 :
5980 : /* This is simpler for variables declared in the outer scope of
5981 : the function so we know that their lifetime always ends with a
5982 : return; see g++.dg/opt/nrv6.C. */
5983 234827 : tree outer = outer_curly_brace_block (fndecl);
5984 234827 : data.simple = chain_member (var, BLOCK_VARS (outer));
5985 :
5986 234827 : cp_walk_tree (&DECL_SAVED_TREE (fndecl), finalize_nrv_r, &data, 0);
5987 234827 : }
5988 :
5989 : /* Create CP_OMP_CLAUSE_INFO for clause C. Returns true if it is invalid. */
5990 :
5991 : bool
5992 2249 : cxx_omp_create_clause_info (tree c, tree type, bool need_default_ctor,
5993 : bool need_copy_ctor, bool need_copy_assignment,
5994 : bool need_dtor)
5995 : {
5996 2249 : int save_errorcount = errorcount;
5997 2249 : tree info, t;
5998 :
5999 : /* Always allocate 3 elements for simplicity. These are the
6000 : function decls for the ctor, dtor, and assignment op.
6001 : This layout is known to the three lang hooks,
6002 : cxx_omp_clause_default_init, cxx_omp_clause_copy_init,
6003 : and cxx_omp_clause_assign_op. */
6004 2249 : info = make_tree_vec (3);
6005 2249 : CP_OMP_CLAUSE_INFO (c) = info;
6006 :
6007 2249 : if (need_default_ctor || need_copy_ctor)
6008 : {
6009 1654 : if (need_default_ctor)
6010 1255 : t = get_default_ctor (type);
6011 : else
6012 399 : t = get_copy_ctor (type, tf_warning_or_error);
6013 :
6014 1654 : if (t && !trivial_fn_p (t))
6015 1400 : TREE_VEC_ELT (info, 0) = t;
6016 : }
6017 :
6018 2249 : if (need_dtor && TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type))
6019 1632 : TREE_VEC_ELT (info, 1) = get_dtor (type, tf_warning_or_error);
6020 :
6021 2249 : if (need_copy_assignment)
6022 : {
6023 397 : t = get_copy_assign (type);
6024 :
6025 397 : if (t && !trivial_fn_p (t))
6026 344 : TREE_VEC_ELT (info, 2) = t;
6027 : }
6028 :
6029 2249 : return errorcount != save_errorcount;
6030 : }
6031 :
6032 : /* If DECL is DECL_OMP_PRIVATIZED_MEMBER, return corresponding
6033 : FIELD_DECL, otherwise return DECL itself. */
6034 :
6035 : static tree
6036 26714 : omp_clause_decl_field (tree decl)
6037 : {
6038 26714 : if (VAR_P (decl)
6039 18651 : && DECL_HAS_VALUE_EXPR_P (decl)
6040 359 : && DECL_ARTIFICIAL (decl)
6041 359 : && DECL_LANG_SPECIFIC (decl)
6042 27049 : && DECL_OMP_PRIVATIZED_MEMBER (decl))
6043 : {
6044 328 : tree f = DECL_VALUE_EXPR (decl);
6045 328 : if (INDIRECT_REF_P (f))
6046 0 : f = TREE_OPERAND (f, 0);
6047 328 : if (TREE_CODE (f) == COMPONENT_REF)
6048 : {
6049 328 : f = TREE_OPERAND (f, 1);
6050 328 : gcc_assert (TREE_CODE (f) == FIELD_DECL);
6051 : return f;
6052 : }
6053 : }
6054 : return NULL_TREE;
6055 : }
6056 :
6057 : /* Adjust DECL if needed for printing using %qE. */
6058 :
6059 : static tree
6060 187 : omp_clause_printable_decl (tree decl)
6061 : {
6062 0 : tree t = omp_clause_decl_field (decl);
6063 187 : if (t)
6064 45 : return t;
6065 : return decl;
6066 : }
6067 :
6068 : /* For a FIELD_DECL F and corresponding DECL_OMP_PRIVATIZED_MEMBER
6069 : VAR_DECL T that doesn't need a DECL_EXPR added, record it for
6070 : privatization. */
6071 :
6072 : static void
6073 219 : omp_note_field_privatization (tree f, tree t)
6074 : {
6075 219 : if (!omp_private_member_map)
6076 71 : omp_private_member_map = new hash_map<tree, tree>;
6077 219 : tree &v = omp_private_member_map->get_or_insert (f);
6078 219 : if (v == NULL_TREE)
6079 : {
6080 146 : v = t;
6081 146 : omp_private_member_vec.safe_push (f);
6082 : /* Signal that we don't want to create DECL_EXPR for this dummy var. */
6083 146 : omp_private_member_vec.safe_push (integer_zero_node);
6084 : }
6085 219 : }
6086 :
6087 : /* Privatize FIELD_DECL T, return corresponding DECL_OMP_PRIVATIZED_MEMBER
6088 : dummy VAR_DECL. */
6089 :
6090 : tree
6091 861 : omp_privatize_field (tree t, bool shared)
6092 : {
6093 861 : tree m = finish_non_static_data_member (t, NULL_TREE, NULL_TREE);
6094 861 : if (m == error_mark_node)
6095 : return error_mark_node;
6096 861 : if (!omp_private_member_map && !shared)
6097 365 : omp_private_member_map = new hash_map<tree, tree>;
6098 861 : if (TYPE_REF_P (TREE_TYPE (t)))
6099 : {
6100 123 : gcc_assert (INDIRECT_REF_P (m));
6101 123 : m = TREE_OPERAND (m, 0);
6102 : }
6103 861 : tree vb = NULL_TREE;
6104 861 : tree &v = shared ? vb : omp_private_member_map->get_or_insert (t);
6105 861 : if (v == NULL_TREE)
6106 : {
6107 770 : v = create_temporary_var (TREE_TYPE (m));
6108 770 : retrofit_lang_decl (v);
6109 770 : DECL_OMP_PRIVATIZED_MEMBER (v) = 1;
6110 770 : SET_DECL_VALUE_EXPR (v, m);
6111 770 : DECL_HAS_VALUE_EXPR_P (v) = 1;
6112 770 : if (!shared)
6113 690 : omp_private_member_vec.safe_push (t);
6114 : }
6115 861 : return v;
6116 : }
6117 :
6118 : /* C++ specialisation of the c_omp_address_inspector class. */
6119 :
6120 : class cp_omp_address_inspector : public c_omp_address_inspector
6121 : {
6122 : public:
6123 31570 : cp_omp_address_inspector (location_t loc, tree t)
6124 31570 : : c_omp_address_inspector (loc, t)
6125 : {
6126 : }
6127 :
6128 31570 : ~cp_omp_address_inspector ()
6129 : {
6130 23123 : }
6131 :
6132 134809 : bool processing_template_decl_p ()
6133 : {
6134 134809 : return processing_template_decl;
6135 : }
6136 :
6137 0 : void emit_unmappable_type_notes (tree t)
6138 : {
6139 0 : if (TREE_TYPE (t) != error_mark_node
6140 0 : && !COMPLETE_TYPE_P (TREE_TYPE (t)))
6141 0 : cxx_incomplete_type_inform (TREE_TYPE (t));
6142 0 : }
6143 :
6144 1062 : tree convert_from_reference (tree x)
6145 : {
6146 1062 : return ::convert_from_reference (x);
6147 : }
6148 :
6149 147 : tree build_array_ref (location_t loc, tree arr, tree idx)
6150 : {
6151 147 : return ::build_array_ref (loc, arr, idx);
6152 : }
6153 :
6154 23065 : bool check_clause (tree clause)
6155 : {
6156 23065 : if (TREE_CODE (orig) == COMPONENT_REF
6157 23065 : && invalid_nonstatic_memfn_p (EXPR_LOCATION (orig), orig,
6158 : tf_warning_or_error))
6159 : return false;
6160 23062 : if (!c_omp_address_inspector::check_clause (clause))
6161 : return false;
6162 : return true;
6163 : }
6164 : };
6165 :
6166 : /* Helper function for handle_omp_array_sections. Called recursively
6167 : to handle multiple array-section-subscripts. C is the clause,
6168 : T current expression (initially OMP_CLAUSE_DECL), which is either
6169 : a TREE_LIST for array-section-subscript (TREE_PURPOSE is low-bound
6170 : expression if specified, TREE_VALUE length expression if specified,
6171 : TREE_CHAIN is what it has been specified after, or some decl.
6172 : TYPES vector is populated with array section types, MAYBE_ZERO_LEN
6173 : set to true if any of the array-section-subscript could have length
6174 : of zero (explicit or implicit), FIRST_NON_ONE is the index of the
6175 : first array-section-subscript which is known not to have length
6176 : of one. Given say:
6177 : map(a[:b][2:1][:c][:2][:d][e:f][2:5])
6178 : FIRST_NON_ONE will be 3, array-section-subscript [:b], [2:1] and [:c]
6179 : all are or may have length of 1, array-section-subscript [:2] is the
6180 : first one known not to have length 1. For array-section-subscript
6181 : <= FIRST_NON_ONE we diagnose non-contiguous arrays if low bound isn't
6182 : 0 or length isn't the array domain max + 1, for > FIRST_NON_ONE we
6183 : can if MAYBE_ZERO_LEN is false. MAYBE_ZERO_LEN will be true in the above
6184 : case though, as some lengths could be zero. */
6185 :
6186 : static tree
6187 21514 : handle_omp_array_sections_1 (tree c, tree t, vec<tree> &types,
6188 : bool &maybe_zero_len, unsigned int &first_non_one,
6189 : enum c_omp_region_type ort)
6190 : {
6191 21514 : tree ret, low_bound, length, type;
6192 21514 : bool openacc = (ort & C_ORT_ACC) != 0;
6193 21514 : if (TREE_CODE (t) != OMP_ARRAY_SECTION)
6194 : {
6195 9718 : if (error_operand_p (t))
6196 6 : return error_mark_node;
6197 :
6198 9712 : cp_omp_address_inspector ai (OMP_CLAUSE_LOCATION (c), t);
6199 9712 : tree t_refto = ai.maybe_unconvert_ref (t);
6200 :
6201 9712 : if (!ai.check_clause (c))
6202 0 : return error_mark_node;
6203 9712 : else if (ai.component_access_p ()
6204 11100 : && (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
6205 64 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TO
6206 40 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_FROM))
6207 1388 : t = ai.get_root_term (true);
6208 : else
6209 8324 : t = ai.unconverted_ref_origin ();
6210 9712 : if (t == error_mark_node)
6211 : return error_mark_node;
6212 9712 : ret = t_refto;
6213 9712 : if (TREE_CODE (t) == FIELD_DECL)
6214 33 : ret = finish_non_static_data_member (t, NULL_TREE, NULL_TREE);
6215 9679 : else if (!VAR_P (t)
6216 2871 : && (openacc || !EXPR_P (t))
6217 2676 : && TREE_CODE (t) != PARM_DECL)
6218 : {
6219 51 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
6220 : return NULL_TREE;
6221 33 : if (DECL_P (t))
6222 33 : error_at (OMP_CLAUSE_LOCATION (c),
6223 : "%qD is not a variable in %qs clause", t,
6224 33 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6225 : else
6226 0 : error_at (OMP_CLAUSE_LOCATION (c),
6227 : "%qE is not a variable in %qs clause", t,
6228 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6229 33 : return error_mark_node;
6230 : }
6231 9628 : else if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY
6232 9237 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND
6233 17936 : && VAR_P (t) && CP_DECL_THREAD_LOCAL_P (t))
6234 : {
6235 18 : error_at (OMP_CLAUSE_LOCATION (c),
6236 : "%qD is threadprivate variable in %qs clause", t,
6237 18 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6238 18 : return error_mark_node;
6239 : }
6240 9643 : if (type_dependent_expression_p (ret))
6241 : return NULL_TREE;
6242 8932 : ret = convert_from_reference (ret);
6243 8932 : return ret;
6244 9712 : }
6245 :
6246 11796 : if ((ort & C_ORT_OMP_DECLARE_SIMD) == C_ORT_OMP
6247 7869 : && (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
6248 6567 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
6249 5283 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION)
6250 14510 : && TREE_CODE (TREE_OPERAND (t, 0)) == FIELD_DECL)
6251 43 : TREE_OPERAND (t, 0) = omp_privatize_field (TREE_OPERAND (t, 0), false);
6252 11796 : ret = handle_omp_array_sections_1 (c, TREE_OPERAND (t, 0), types,
6253 : maybe_zero_len, first_non_one, ort);
6254 11796 : if (ret == error_mark_node || ret == NULL_TREE)
6255 : return ret;
6256 :
6257 10726 : type = TREE_TYPE (ret);
6258 10726 : low_bound = TREE_OPERAND (t, 1);
6259 10726 : length = TREE_OPERAND (t, 2);
6260 8607 : if ((low_bound && type_dependent_expression_p (low_bound))
6261 19250 : || (length && type_dependent_expression_p (length)))
6262 : return NULL_TREE;
6263 :
6264 10638 : if (low_bound == error_mark_node || length == error_mark_node)
6265 : return error_mark_node;
6266 :
6267 10626 : if (low_bound && !INTEGRAL_TYPE_P (TREE_TYPE (low_bound)))
6268 : {
6269 75 : error_at (OMP_CLAUSE_LOCATION (c),
6270 : "low bound %qE of array section does not have integral type",
6271 : low_bound);
6272 75 : return error_mark_node;
6273 : }
6274 10551 : if (length && !INTEGRAL_TYPE_P (TREE_TYPE (length)))
6275 : {
6276 75 : error_at (OMP_CLAUSE_LOCATION (c),
6277 : "length %qE of array section does not have integral type",
6278 : length);
6279 75 : return error_mark_node;
6280 : }
6281 10476 : if (low_bound)
6282 8423 : low_bound = mark_rvalue_use (low_bound);
6283 10476 : if (length)
6284 9413 : length = mark_rvalue_use (length);
6285 : /* We need to reduce to real constant-values for checks below. */
6286 9413 : if (length)
6287 9413 : length = fold_simple (length);
6288 10476 : if (low_bound)
6289 8423 : low_bound = fold_simple (low_bound);
6290 8423 : if (low_bound
6291 8423 : && TREE_CODE (low_bound) == INTEGER_CST
6292 15909 : && TYPE_PRECISION (TREE_TYPE (low_bound))
6293 7486 : > TYPE_PRECISION (sizetype))
6294 0 : low_bound = fold_convert (sizetype, low_bound);
6295 10476 : if (length
6296 9413 : && TREE_CODE (length) == INTEGER_CST
6297 17866 : && TYPE_PRECISION (TREE_TYPE (length))
6298 7390 : > TYPE_PRECISION (sizetype))
6299 0 : length = fold_convert (sizetype, length);
6300 10476 : if (low_bound == NULL_TREE)
6301 2053 : low_bound = integer_zero_node;
6302 :
6303 10476 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
6304 10476 : && (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH
6305 5168 : || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_DETACH))
6306 : {
6307 60 : if (length != integer_one_node)
6308 : {
6309 36 : error_at (OMP_CLAUSE_LOCATION (c),
6310 : "expected single pointer in %qs clause",
6311 : user_omp_clause_code_name (c, openacc));
6312 36 : return error_mark_node;
6313 : }
6314 : }
6315 10440 : if (length != NULL_TREE)
6316 : {
6317 9401 : if (!integer_nonzerop (length))
6318 : {
6319 2078 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY
6320 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
6321 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
6322 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
6323 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION)
6324 : {
6325 479 : if (integer_zerop (length))
6326 : {
6327 36 : error_at (OMP_CLAUSE_LOCATION (c),
6328 : "zero length array section in %qs clause",
6329 36 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6330 36 : return error_mark_node;
6331 : }
6332 : }
6333 : else
6334 1599 : maybe_zero_len = true;
6335 : }
6336 9365 : if (first_non_one == types.length ()
6337 9365 : && (TREE_CODE (length) != INTEGER_CST || integer_onep (length)))
6338 3999 : first_non_one++;
6339 : }
6340 10404 : if (TREE_CODE (type) == ARRAY_TYPE)
6341 : {
6342 5796 : if (length == NULL_TREE
6343 5796 : && (TYPE_DOMAIN (type) == NULL_TREE
6344 955 : || TYPE_MAX_VALUE (TYPE_DOMAIN (type)) == NULL_TREE))
6345 : {
6346 33 : error_at (OMP_CLAUSE_LOCATION (c),
6347 : "for unknown bound array type length expression must "
6348 : "be specified");
6349 33 : return error_mark_node;
6350 : }
6351 5763 : if (TREE_CODE (low_bound) == INTEGER_CST
6352 5763 : && tree_int_cst_sgn (low_bound) == -1)
6353 : {
6354 177 : error_at (OMP_CLAUSE_LOCATION (c),
6355 : "negative low bound in array section in %qs clause",
6356 177 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6357 177 : return error_mark_node;
6358 : }
6359 5586 : if (length != NULL_TREE
6360 4688 : && TREE_CODE (length) == INTEGER_CST
6361 9348 : && tree_int_cst_sgn (length) == -1)
6362 : {
6363 177 : error_at (OMP_CLAUSE_LOCATION (c),
6364 : "negative length in array section in %qs clause",
6365 177 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6366 177 : return error_mark_node;
6367 : }
6368 5409 : if (TYPE_DOMAIN (type)
6369 5310 : && TYPE_MAX_VALUE (TYPE_DOMAIN (type))
6370 10719 : && TREE_CODE (TYPE_MAX_VALUE (TYPE_DOMAIN (type)))
6371 : == INTEGER_CST)
6372 : {
6373 4914 : tree size
6374 4914 : = fold_convert (sizetype, TYPE_MAX_VALUE (TYPE_DOMAIN (type)));
6375 4914 : size = size_binop (PLUS_EXPR, size, size_one_node);
6376 4914 : if (TREE_CODE (low_bound) == INTEGER_CST)
6377 : {
6378 4137 : if (tree_int_cst_lt (size, low_bound))
6379 : {
6380 63 : error_at (OMP_CLAUSE_LOCATION (c),
6381 : "low bound %qE above array section size "
6382 : "in %qs clause", low_bound,
6383 63 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6384 63 : return error_mark_node;
6385 : }
6386 4074 : if (tree_int_cst_equal (size, low_bound))
6387 : {
6388 21 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY
6389 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
6390 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
6391 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
6392 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION)
6393 : {
6394 21 : error_at (OMP_CLAUSE_LOCATION (c),
6395 : "zero length array section in %qs clause",
6396 21 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6397 21 : return error_mark_node;
6398 : }
6399 0 : maybe_zero_len = true;
6400 : }
6401 4053 : else if (length == NULL_TREE
6402 1578 : && first_non_one == types.length ()
6403 4406 : && tree_int_cst_equal
6404 353 : (TYPE_MAX_VALUE (TYPE_DOMAIN (type)),
6405 : low_bound))
6406 207 : first_non_one++;
6407 : }
6408 777 : else if (length == NULL_TREE)
6409 : {
6410 24 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY
6411 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND
6412 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_REDUCTION
6413 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_IN_REDUCTION
6414 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_TASK_REDUCTION)
6415 13 : maybe_zero_len = true;
6416 48 : if (first_non_one == types.length ())
6417 21 : first_non_one++;
6418 : }
6419 4830 : if (length && TREE_CODE (length) == INTEGER_CST)
6420 : {
6421 3465 : if (tree_int_cst_lt (size, length))
6422 : {
6423 63 : error_at (OMP_CLAUSE_LOCATION (c),
6424 : "length %qE above array section size "
6425 : "in %qs clause", length,
6426 63 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6427 63 : return error_mark_node;
6428 : }
6429 3402 : if (TREE_CODE (low_bound) == INTEGER_CST)
6430 : {
6431 3064 : tree lbpluslen
6432 3064 : = size_binop (PLUS_EXPR,
6433 : fold_convert (sizetype, low_bound),
6434 : fold_convert (sizetype, length));
6435 3064 : if (TREE_CODE (lbpluslen) == INTEGER_CST
6436 3064 : && tree_int_cst_lt (size, lbpluslen))
6437 : {
6438 60 : error_at (OMP_CLAUSE_LOCATION (c),
6439 : "high bound %qE above array section size "
6440 : "in %qs clause", lbpluslen,
6441 60 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6442 60 : return error_mark_node;
6443 : }
6444 : }
6445 : }
6446 : }
6447 495 : else if (length == NULL_TREE)
6448 : {
6449 1 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY
6450 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND
6451 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_REDUCTION
6452 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_IN_REDUCTION
6453 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_TASK_REDUCTION)
6454 0 : maybe_zero_len = true;
6455 2 : if (first_non_one == types.length ())
6456 1 : first_non_one++;
6457 : }
6458 :
6459 : /* For [lb:] we will need to evaluate lb more than once. */
6460 4157 : if (length == NULL_TREE && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND)
6461 : {
6462 733 : tree lb = cp_save_expr (low_bound);
6463 733 : if (lb != low_bound)
6464 : {
6465 13 : TREE_OPERAND (t, 1) = lb;
6466 13 : low_bound = lb;
6467 : }
6468 : }
6469 : }
6470 4608 : else if (TYPE_PTR_P (type))
6471 : {
6472 4548 : if (length == NULL_TREE)
6473 : {
6474 51 : if (TREE_CODE (ret) == PARM_DECL && DECL_ARRAY_PARAMETER_P (ret))
6475 45 : error_at (OMP_CLAUSE_LOCATION (c),
6476 : "for array function parameter length expression "
6477 : "must be specified");
6478 : else
6479 6 : error_at (OMP_CLAUSE_LOCATION (c),
6480 : "for pointer type length expression must be specified");
6481 51 : return error_mark_node;
6482 : }
6483 4497 : if (length != NULL_TREE
6484 4497 : && TREE_CODE (length) == INTEGER_CST
6485 3400 : && tree_int_cst_sgn (length) == -1)
6486 : {
6487 96 : error_at (OMP_CLAUSE_LOCATION (c),
6488 : "negative length in array section in %qs clause",
6489 96 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6490 96 : return error_mark_node;
6491 : }
6492 : /* If there is a pointer type anywhere but in the very first
6493 : array-section-subscript, the array section could be non-contiguous. */
6494 4401 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_AFFINITY
6495 4299 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND
6496 8215 : && TREE_CODE (TREE_OPERAND (t, 0)) == OMP_ARRAY_SECTION)
6497 : {
6498 : /* If any prior dimension has a non-one length, then deem this
6499 : array section as non-contiguous. */
6500 159 : for (tree d = TREE_OPERAND (t, 0); TREE_CODE (d) == OMP_ARRAY_SECTION;
6501 69 : d = TREE_OPERAND (d, 0))
6502 : {
6503 90 : tree d_length = TREE_OPERAND (d, 2);
6504 90 : if (d_length == NULL_TREE || !integer_onep (d_length))
6505 : {
6506 21 : error_at (OMP_CLAUSE_LOCATION (c),
6507 : "array section is not contiguous in %qs clause",
6508 21 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6509 21 : return error_mark_node;
6510 : }
6511 : }
6512 : }
6513 : }
6514 : else
6515 : {
6516 60 : error_at (OMP_CLAUSE_LOCATION (c),
6517 : "%qE does not have pointer or array type", ret);
6518 60 : return error_mark_node;
6519 : }
6520 9582 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DEPEND)
6521 8677 : types.safe_push (TREE_TYPE (ret));
6522 : /* We will need to evaluate lb more than once. */
6523 9582 : tree lb = cp_save_expr (low_bound);
6524 9582 : if (lb != low_bound)
6525 : {
6526 722 : TREE_OPERAND (t, 1) = lb;
6527 722 : low_bound = lb;
6528 : }
6529 : /* Temporarily disable -fstrong-eval-order for array reductions.
6530 : The SAVE_EXPR and COMPOUND_EXPR added if low_bound has side-effects
6531 : is something the middle-end can't cope with and more importantly,
6532 : it needs to be the actual base variable that is privatized, not some
6533 : temporary assigned previous value of it. That, together with OpenMP
6534 : saying how many times the side-effects are evaluated is unspecified,
6535 : makes int *a, *b; ... reduction(+:a[a = b, 3:10]) really unspecified. */
6536 9582 : warning_sentinel s (flag_strong_eval_order,
6537 9582 : OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
6538 8485 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
6539 16933 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION);
6540 9582 : ret = grok_array_decl (OMP_CLAUSE_LOCATION (c), ret, low_bound, NULL,
6541 : tf_warning_or_error);
6542 9582 : return ret;
6543 9582 : }
6544 :
6545 : /* Handle array sections for clause C. */
6546 :
6547 : static bool
6548 9718 : handle_omp_array_sections (tree &c, enum c_omp_region_type ort)
6549 : {
6550 9718 : bool maybe_zero_len = false;
6551 9718 : unsigned int first_non_one = 0;
6552 9718 : auto_vec<tree, 10> types;
6553 9718 : tree *tp = &OMP_CLAUSE_DECL (c);
6554 9718 : if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
6555 8759 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY)
6556 10127 : && OMP_ITERATOR_DECL_P (*tp))
6557 258 : tp = &TREE_VALUE (*tp);
6558 9718 : tree first = handle_omp_array_sections_1 (c, *tp, types,
6559 : maybe_zero_len, first_non_one,
6560 : ort);
6561 9718 : if (first == error_mark_node)
6562 : return true;
6563 8605 : if (first == NULL_TREE)
6564 : return false;
6565 7788 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
6566 7788 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_AFFINITY)
6567 : {
6568 951 : tree t = *tp;
6569 951 : tree tem = NULL_TREE;
6570 951 : if (processing_template_decl)
6571 : return false;
6572 : /* Need to evaluate side effects in the length expressions
6573 : if any. */
6574 852 : while (TREE_CODE (t) == TREE_LIST)
6575 : {
6576 0 : if (TREE_VALUE (t) && TREE_SIDE_EFFECTS (TREE_VALUE (t)))
6577 : {
6578 0 : if (tem == NULL_TREE)
6579 : tem = TREE_VALUE (t);
6580 : else
6581 0 : tem = build2 (COMPOUND_EXPR, TREE_TYPE (tem),
6582 0 : TREE_VALUE (t), tem);
6583 : }
6584 0 : t = TREE_CHAIN (t);
6585 : }
6586 852 : if (tem)
6587 0 : first = build2 (COMPOUND_EXPR, TREE_TYPE (first), tem, first);
6588 852 : *tp = first;
6589 : }
6590 : else
6591 : {
6592 6837 : unsigned int num = types.length (), i;
6593 6837 : tree t, side_effects = NULL_TREE, size = NULL_TREE;
6594 6837 : tree condition = NULL_TREE;
6595 :
6596 6837 : if (int_size_in_bytes (TREE_TYPE (first)) <= 0)
6597 3 : maybe_zero_len = true;
6598 6837 : if (processing_template_decl && maybe_zero_len)
6599 : return false;
6600 :
6601 14382 : for (i = num, t = OMP_CLAUSE_DECL (c); i > 0;
6602 7623 : t = TREE_OPERAND (t, 0))
6603 : {
6604 7698 : gcc_assert (TREE_CODE (t) == OMP_ARRAY_SECTION);
6605 :
6606 7698 : tree low_bound = TREE_OPERAND (t, 1);
6607 7698 : tree length = TREE_OPERAND (t, 2);
6608 :
6609 7698 : i--;
6610 7698 : if (low_bound
6611 6252 : && TREE_CODE (low_bound) == INTEGER_CST
6612 13339 : && TYPE_PRECISION (TREE_TYPE (low_bound))
6613 5641 : > TYPE_PRECISION (sizetype))
6614 0 : low_bound = fold_convert (sizetype, low_bound);
6615 7698 : if (length
6616 7149 : && TREE_CODE (length) == INTEGER_CST
6617 12955 : && TYPE_PRECISION (TREE_TYPE (length))
6618 5257 : > TYPE_PRECISION (sizetype))
6619 0 : length = fold_convert (sizetype, length);
6620 7698 : if (low_bound == NULL_TREE)
6621 1446 : low_bound = integer_zero_node;
6622 7698 : if (!maybe_zero_len && i > first_non_one)
6623 : {
6624 646 : if (integer_nonzerop (low_bound))
6625 36 : goto do_warn_noncontiguous;
6626 610 : if (length != NULL_TREE
6627 282 : && TREE_CODE (length) == INTEGER_CST
6628 282 : && TYPE_DOMAIN (types[i])
6629 282 : && TYPE_MAX_VALUE (TYPE_DOMAIN (types[i]))
6630 892 : && TREE_CODE (TYPE_MAX_VALUE (TYPE_DOMAIN (types[i])))
6631 : == INTEGER_CST)
6632 : {
6633 282 : tree size;
6634 282 : size = size_binop (PLUS_EXPR,
6635 : TYPE_MAX_VALUE (TYPE_DOMAIN (types[i])),
6636 : size_one_node);
6637 282 : if (!tree_int_cst_equal (length, size))
6638 : {
6639 39 : do_warn_noncontiguous:
6640 150 : error_at (OMP_CLAUSE_LOCATION (c),
6641 : "array section is not contiguous in %qs "
6642 : "clause",
6643 75 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
6644 75 : return true;
6645 : }
6646 : }
6647 571 : if (!processing_template_decl
6648 401 : && length != NULL_TREE
6649 742 : && TREE_SIDE_EFFECTS (length))
6650 : {
6651 0 : if (side_effects == NULL_TREE)
6652 : side_effects = length;
6653 : else
6654 0 : side_effects = build2 (COMPOUND_EXPR,
6655 0 : TREE_TYPE (side_effects),
6656 : length, side_effects);
6657 : }
6658 : }
6659 7052 : else if (processing_template_decl)
6660 726 : continue;
6661 : else
6662 : {
6663 6326 : tree l;
6664 :
6665 6326 : if (i > first_non_one
6666 6326 : && ((length && integer_nonzerop (length))
6667 0 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
6668 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
6669 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION))
6670 0 : continue;
6671 6326 : if (length)
6672 6187 : l = fold_convert (sizetype, length);
6673 : else
6674 : {
6675 139 : l = size_binop (PLUS_EXPR,
6676 : TYPE_MAX_VALUE (TYPE_DOMAIN (types[i])),
6677 : size_one_node);
6678 139 : l = size_binop (MINUS_EXPR, l,
6679 : fold_convert (sizetype, low_bound));
6680 : }
6681 6326 : if (i > first_non_one)
6682 : {
6683 0 : l = fold_build2 (NE_EXPR, boolean_type_node, l,
6684 : size_zero_node);
6685 0 : if (condition == NULL_TREE)
6686 : condition = l;
6687 : else
6688 0 : condition = fold_build2 (BIT_AND_EXPR, boolean_type_node,
6689 : l, condition);
6690 : }
6691 6326 : else if (size == NULL_TREE)
6692 : {
6693 6039 : size = size_in_bytes (TREE_TYPE (types[i]));
6694 6039 : tree eltype = TREE_TYPE (types[num - 1]);
6695 6110 : while (TREE_CODE (eltype) == ARRAY_TYPE)
6696 71 : eltype = TREE_TYPE (eltype);
6697 6039 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
6698 5229 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
6699 10515 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION)
6700 1659 : size = size_binop (EXACT_DIV_EXPR, size,
6701 : size_in_bytes (eltype));
6702 6039 : size = size_binop (MULT_EXPR, size, l);
6703 6039 : if (condition)
6704 0 : size = fold_build3 (COND_EXPR, sizetype, condition,
6705 : size, size_zero_node);
6706 : }
6707 : else
6708 287 : size = size_binop (MULT_EXPR, size, l);
6709 : }
6710 : }
6711 6684 : if (!processing_template_decl)
6712 : {
6713 6039 : if (side_effects)
6714 0 : size = build2 (COMPOUND_EXPR, sizetype, side_effects, size);
6715 6039 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
6716 5229 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
6717 10515 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION)
6718 : {
6719 1659 : size = size_binop (MINUS_EXPR, size, size_one_node);
6720 1659 : size = save_expr (size);
6721 1659 : tree index_type = build_index_type (size);
6722 1659 : tree eltype = TREE_TYPE (first);
6723 1688 : while (TREE_CODE (eltype) == ARRAY_TYPE)
6724 29 : eltype = TREE_TYPE (eltype);
6725 1659 : tree type = build_array_type (eltype, index_type);
6726 1659 : tree ptype = build_pointer_type (eltype);
6727 1659 : if (TYPE_REF_P (TREE_TYPE (t))
6728 1659 : && INDIRECT_TYPE_P (TREE_TYPE (TREE_TYPE (t))))
6729 170 : t = convert_from_reference (t);
6730 1489 : else if (TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE)
6731 641 : t = build_fold_addr_expr (t);
6732 1659 : tree t2 = build_fold_addr_expr (first);
6733 1659 : t2 = fold_convert_loc (OMP_CLAUSE_LOCATION (c),
6734 : ptrdiff_type_node, t2);
6735 1659 : t2 = fold_build2_loc (OMP_CLAUSE_LOCATION (c), MINUS_EXPR,
6736 : ptrdiff_type_node, t2,
6737 1659 : fold_convert_loc (OMP_CLAUSE_LOCATION (c),
6738 : ptrdiff_type_node, t));
6739 1659 : if (tree_fits_shwi_p (t2))
6740 1321 : t = build2 (MEM_REF, type, t,
6741 1321 : build_int_cst (ptype, tree_to_shwi (t2)));
6742 : else
6743 : {
6744 338 : t2 = fold_convert_loc (OMP_CLAUSE_LOCATION (c),
6745 : sizetype, t2);
6746 338 : t = build2_loc (OMP_CLAUSE_LOCATION (c), POINTER_PLUS_EXPR,
6747 338 : TREE_TYPE (t), t, t2);
6748 338 : t = build2 (MEM_REF, type, t, build_int_cst (ptype, 0));
6749 : }
6750 1659 : OMP_CLAUSE_DECL (c) = t;
6751 6039 : return false;
6752 : }
6753 4380 : OMP_CLAUSE_DECL (c) = first;
6754 4380 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_HAS_DEVICE_ADDR)
6755 : return false;
6756 4354 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP
6757 4354 : || (OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ATTACH
6758 3788 : && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_DETACH
6759 3776 : && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_FORCE_DETACH))
6760 4330 : OMP_CLAUSE_SIZE (c) = size;
6761 4354 : if (TREE_CODE (t) == FIELD_DECL)
6762 3 : t = finish_non_static_data_member (t, NULL_TREE, NULL_TREE);
6763 :
6764 4354 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP)
6765 : return false;
6766 :
6767 3800 : if (TREE_CODE (first) == INDIRECT_REF)
6768 : {
6769 : /* Detect and skip adding extra nodes for pointer-to-member
6770 : mappings. These are unsupported for now. */
6771 2414 : tree tmp = TREE_OPERAND (first, 0);
6772 :
6773 2414 : if (TREE_CODE (tmp) == NON_LVALUE_EXPR)
6774 1916 : tmp = TREE_OPERAND (tmp, 0);
6775 :
6776 2414 : if (TREE_CODE (tmp) == INDIRECT_REF)
6777 158 : tmp = TREE_OPERAND (tmp, 0);
6778 :
6779 2414 : if (TREE_CODE (tmp) == POINTER_PLUS_EXPR)
6780 : {
6781 468 : tree offset = TREE_OPERAND (tmp, 1);
6782 468 : STRIP_NOPS (offset);
6783 468 : if (TYPE_PTRMEM_P (TREE_TYPE (offset)))
6784 : {
6785 36 : sorry_at (OMP_CLAUSE_LOCATION (c),
6786 : "pointer-to-member mapping %qE not supported",
6787 18 : OMP_CLAUSE_DECL (c));
6788 18 : return true;
6789 : }
6790 : }
6791 : }
6792 :
6793 : /* FIRST represents the first item of data that we are mapping.
6794 : E.g. if we're mapping an array, FIRST might resemble
6795 : "foo.bar.myarray[0]". */
6796 :
6797 3782 : auto_vec<omp_addr_token *, 10> addr_tokens;
6798 :
6799 3782 : if (!omp_parse_expr (addr_tokens, first))
6800 : return true;
6801 :
6802 3782 : cp_omp_address_inspector ai (OMP_CLAUSE_LOCATION (c), t);
6803 :
6804 3782 : tree nc = ai.expand_map_clause (c, first, addr_tokens, ort);
6805 3782 : if (nc != error_mark_node)
6806 : {
6807 3782 : using namespace omp_addr_tokenizer;
6808 :
6809 3782 : if (ai.maybe_zero_length_array_section (c))
6810 3758 : OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (c) = 1;
6811 :
6812 : /* !!! If we're accessing a base decl via chained access
6813 : methods (e.g. multiple indirections), duplicate clause
6814 : detection won't work properly. Skip it in that case. */
6815 3782 : if ((addr_tokens[0]->type == STRUCTURE_BASE
6816 2765 : || addr_tokens[0]->type == ARRAY_BASE)
6817 3782 : && addr_tokens[0]->u.structure_base_kind == BASE_DECL
6818 3771 : && addr_tokens[1]->type == ACCESS_METHOD
6819 7553 : && omp_access_chain_p (addr_tokens, 1))
6820 218 : c = nc;
6821 :
6822 3782 : return false;
6823 : }
6824 7564 : }
6825 : }
6826 : return false;
6827 9718 : }
6828 :
6829 : /* Return identifier to look up for omp declare reduction. */
6830 :
6831 : tree
6832 7113 : omp_reduction_id (enum tree_code reduction_code, tree reduction_id, tree type)
6833 : {
6834 7113 : const char *p = NULL;
6835 7113 : const char *m = NULL;
6836 7113 : switch (reduction_code)
6837 : {
6838 4200 : case PLUS_EXPR:
6839 4200 : case MULT_EXPR:
6840 4200 : case MINUS_EXPR:
6841 4200 : case BIT_AND_EXPR:
6842 4200 : case BIT_XOR_EXPR:
6843 4200 : case BIT_IOR_EXPR:
6844 4200 : case TRUTH_ANDIF_EXPR:
6845 4200 : case TRUTH_ORIF_EXPR:
6846 4200 : reduction_id = ovl_op_identifier (false, reduction_code);
6847 4200 : break;
6848 : case MIN_EXPR:
6849 : p = "min";
6850 : break;
6851 : case MAX_EXPR:
6852 : p = "max";
6853 : break;
6854 : default:
6855 : break;
6856 : }
6857 :
6858 4200 : if (p == NULL)
6859 : {
6860 6949 : if (TREE_CODE (reduction_id) != IDENTIFIER_NODE)
6861 0 : return error_mark_node;
6862 6949 : p = IDENTIFIER_POINTER (reduction_id);
6863 : }
6864 :
6865 7113 : if (type != NULL_TREE)
6866 2047 : m = mangle_type_string (TYPE_MAIN_VARIANT (type));
6867 :
6868 7113 : const char prefix[] = "omp declare reduction ";
6869 7113 : size_t lenp = sizeof (prefix);
6870 7113 : if (strncmp (p, prefix, lenp - 1) == 0)
6871 2047 : lenp = 1;
6872 7113 : size_t len = strlen (p);
6873 7113 : size_t lenm = m ? strlen (m) + 1 : 0;
6874 7113 : char *name = XALLOCAVEC (char, lenp + len + lenm);
6875 7113 : if (lenp > 1)
6876 5066 : memcpy (name, prefix, lenp - 1);
6877 7113 : memcpy (name + lenp - 1, p, len + 1);
6878 7113 : if (m)
6879 : {
6880 2047 : name[lenp + len - 1] = '~';
6881 2047 : memcpy (name + lenp + len, m, lenm);
6882 : }
6883 7113 : return get_identifier (name);
6884 : }
6885 :
6886 : /* Lookup OpenMP UDR ID for TYPE, return the corresponding artificial
6887 : FUNCTION_DECL or NULL_TREE if not found. */
6888 :
6889 : static tree
6890 1298 : omp_reduction_lookup (location_t loc, tree id, tree type, tree *baselinkp,
6891 : vec<tree> *ambiguousp)
6892 : {
6893 1298 : tree orig_id = id;
6894 1298 : tree baselink = NULL_TREE;
6895 1298 : if (identifier_p (id))
6896 : {
6897 1270 : cp_id_kind idk;
6898 1270 : bool nonint_cst_expression_p;
6899 1270 : const char *error_msg;
6900 1270 : id = omp_reduction_id (ERROR_MARK, id, type);
6901 1270 : tree decl = lookup_name (id);
6902 1270 : if (decl == NULL_TREE)
6903 80 : decl = error_mark_node;
6904 1270 : id = finish_id_expression (id, decl, NULL_TREE, &idk, false, true,
6905 : &nonint_cst_expression_p, false, true, false,
6906 : false, &error_msg, loc);
6907 1270 : if (idk == CP_ID_KIND_UNQUALIFIED
6908 1350 : && identifier_p (id))
6909 : {
6910 80 : vec<tree, va_gc> *args = NULL;
6911 80 : vec_safe_push (args, build_reference_type (type));
6912 80 : id = perform_koenig_lookup (id, args, tf_none);
6913 : }
6914 : }
6915 28 : else if (TREE_CODE (id) == SCOPE_REF)
6916 28 : id = lookup_qualified_name (TREE_OPERAND (id, 0),
6917 : omp_reduction_id (ERROR_MARK,
6918 28 : TREE_OPERAND (id, 1),
6919 : type),
6920 : LOOK_want::NORMAL, false);
6921 1298 : tree fns = id;
6922 1298 : id = NULL_TREE;
6923 1298 : if (fns && is_overloaded_fn (fns))
6924 : {
6925 1224 : for (lkp_iterator iter (get_fns (fns)); iter; ++iter)
6926 : {
6927 1224 : tree fndecl = *iter;
6928 1224 : if (TREE_CODE (fndecl) == FUNCTION_DECL)
6929 : {
6930 1224 : tree argtype = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (fndecl)));
6931 1224 : if (same_type_p (TREE_TYPE (argtype), type))
6932 : {
6933 1224 : id = fndecl;
6934 1224 : break;
6935 : }
6936 : }
6937 : }
6938 :
6939 1224 : if (id && BASELINK_P (fns))
6940 : {
6941 74 : if (baselinkp)
6942 0 : *baselinkp = fns;
6943 : else
6944 74 : baselink = fns;
6945 : }
6946 : }
6947 :
6948 1298 : if (!id && CLASS_TYPE_P (type) && TYPE_BINFO (type))
6949 : {
6950 35 : auto_vec<tree> ambiguous;
6951 35 : tree binfo = TYPE_BINFO (type), base_binfo, ret = NULL_TREE;
6952 35 : unsigned int ix;
6953 35 : if (ambiguousp == NULL)
6954 19 : ambiguousp = &ambiguous;
6955 73 : for (ix = 0; BINFO_BASE_ITERATE (binfo, ix, base_binfo); ix++)
6956 : {
6957 62 : id = omp_reduction_lookup (loc, orig_id, BINFO_TYPE (base_binfo),
6958 : baselinkp ? baselinkp : &baselink,
6959 : ambiguousp);
6960 38 : if (id == NULL_TREE)
6961 14 : continue;
6962 24 : if (!ambiguousp->is_empty ())
6963 3 : ambiguousp->safe_push (id);
6964 21 : else if (ret != NULL_TREE)
6965 : {
6966 6 : ambiguousp->safe_push (ret);
6967 6 : ambiguousp->safe_push (id);
6968 6 : ret = NULL_TREE;
6969 : }
6970 : else
6971 15 : ret = id;
6972 : }
6973 35 : if (ambiguousp != &ambiguous)
6974 16 : return ret;
6975 19 : if (!ambiguous.is_empty ())
6976 : {
6977 6 : auto_diagnostic_group d;
6978 6 : const char *str = _("candidates are:");
6979 6 : unsigned int idx;
6980 6 : tree udr;
6981 6 : error_at (loc, "user defined reduction lookup is ambiguous");
6982 27 : FOR_EACH_VEC_ELT (ambiguous, idx, udr)
6983 : {
6984 15 : inform (DECL_SOURCE_LOCATION (udr), "%s %#qD", str, udr);
6985 15 : if (idx == 0)
6986 6 : str = get_spaces (str);
6987 : }
6988 6 : ret = error_mark_node;
6989 6 : baselink = NULL_TREE;
6990 6 : }
6991 19 : id = ret;
6992 35 : }
6993 1282 : if (id && baselink)
6994 74 : perform_or_defer_access_check (BASELINK_BINFO (baselink),
6995 : id, id, tf_warning_or_error);
6996 : return id;
6997 : }
6998 :
6999 : /* Return identifier to look up for omp declare mapper. */
7000 :
7001 : tree
7002 4119 : omp_mapper_id (tree mapper_id, tree type)
7003 : {
7004 4119 : const char *p = NULL;
7005 4119 : const char *m = NULL;
7006 :
7007 4119 : if (mapper_id == NULL_TREE)
7008 : p = "";
7009 91 : else if (TREE_CODE (mapper_id) == IDENTIFIER_NODE)
7010 91 : p = IDENTIFIER_POINTER (mapper_id);
7011 : else
7012 0 : return error_mark_node;
7013 :
7014 4119 : if (type != NULL_TREE)
7015 4111 : m = mangle_type_string (TYPE_MAIN_VARIANT (type));
7016 :
7017 4119 : const char prefix[] = "omp declare mapper ";
7018 4119 : size_t lenp = sizeof (prefix);
7019 4119 : if (strncmp (p, prefix, lenp - 1) == 0)
7020 8 : lenp = 1;
7021 4119 : size_t len = strlen (p);
7022 4119 : size_t lenm = m ? strlen (m) + 1 : 0;
7023 4119 : char *name = XALLOCAVEC (char, lenp + len + lenm);
7024 4119 : memcpy (name, prefix, lenp - 1);
7025 4119 : memcpy (name + lenp - 1, p, len + 1);
7026 4119 : if (m)
7027 : {
7028 4111 : name[lenp + len - 1] = '~';
7029 4111 : memcpy (name + lenp + len, m, lenm);
7030 : }
7031 4119 : return get_identifier (name);
7032 : }
7033 :
7034 : tree
7035 12120 : cxx_omp_mapper_lookup (tree id, tree type)
7036 : {
7037 12120 : if (!RECORD_OR_UNION_TYPE_P (type))
7038 : return NULL_TREE;
7039 3878 : id = omp_mapper_id (id, type);
7040 3878 : return lookup_name (id);
7041 : }
7042 :
7043 : tree
7044 375 : cxx_omp_extract_mapper_directive (tree vardecl)
7045 : {
7046 375 : gcc_assert (TREE_CODE (vardecl) == VAR_DECL);
7047 :
7048 : /* Instantiate the decl if we haven't already. */
7049 375 : mark_used (vardecl);
7050 375 : tree body = DECL_INITIAL (vardecl);
7051 :
7052 375 : if (TREE_CODE (body) == STATEMENT_LIST)
7053 : {
7054 0 : tree_stmt_iterator tsi = tsi_start (body);
7055 0 : gcc_assert (TREE_CODE (tsi_stmt (tsi)) == DECL_EXPR);
7056 0 : tsi_next (&tsi);
7057 0 : body = tsi_stmt (tsi);
7058 : }
7059 :
7060 375 : gcc_assert (TREE_CODE (body) == OMP_DECLARE_MAPPER);
7061 :
7062 375 : return body;
7063 : }
7064 :
7065 : /* For now we can handle singleton OMP_ARRAY_SECTIONs with custom mappers, but
7066 : nothing more complicated. */
7067 :
7068 : tree
7069 1969 : cxx_omp_map_array_section (location_t loc, tree t)
7070 : {
7071 1969 : tree low = TREE_OPERAND (t, 1);
7072 1969 : tree len = TREE_OPERAND (t, 2);
7073 :
7074 1969 : if (len && integer_onep (len))
7075 : {
7076 327 : t = TREE_OPERAND (t, 0);
7077 :
7078 327 : if (!low)
7079 26 : low = integer_zero_node;
7080 :
7081 327 : if (TREE_CODE (TREE_TYPE (t)) == REFERENCE_TYPE)
7082 6 : t = convert_from_reference (t);
7083 :
7084 327 : if (TYPE_PTR_P (TREE_TYPE (t))
7085 327 : || TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE)
7086 327 : t = build_array_ref (loc, t, low);
7087 : else
7088 : /* handle_omp_array_sections_1 has already diagnosed the error. */
7089 0 : t = error_mark_node;
7090 : }
7091 :
7092 1969 : return t;
7093 : }
7094 :
7095 : /* Helper function for cp_parser_omp_declare_reduction_exprs
7096 : and tsubst_omp_udr.
7097 : Remove CLEANUP_STMT for data (omp_priv variable).
7098 : Also append INIT_EXPR for DECL_INITIAL of omp_priv after its
7099 : DECL_EXPR. */
7100 :
7101 : tree
7102 4449 : cp_remove_omp_priv_cleanup_stmt (tree *tp, int *walk_subtrees, void *data)
7103 : {
7104 4449 : if (TYPE_P (*tp))
7105 230 : *walk_subtrees = 0;
7106 4219 : else if (TREE_CODE (*tp) == CLEANUP_STMT && CLEANUP_DECL (*tp) == (tree) data)
7107 52 : *tp = CLEANUP_BODY (*tp);
7108 4167 : else if (TREE_CODE (*tp) == DECL_EXPR)
7109 : {
7110 310 : tree decl = DECL_EXPR_DECL (*tp);
7111 310 : if (!processing_template_decl
7112 261 : && decl == (tree) data
7113 261 : && DECL_INITIAL (decl)
7114 402 : && DECL_INITIAL (decl) != error_mark_node)
7115 : {
7116 92 : tree list = NULL_TREE;
7117 92 : append_to_statement_list_force (*tp, &list);
7118 92 : tree init_expr = build2 (INIT_EXPR, void_type_node,
7119 92 : decl, DECL_INITIAL (decl));
7120 92 : DECL_INITIAL (decl) = NULL_TREE;
7121 92 : append_to_statement_list_force (init_expr, &list);
7122 92 : *tp = list;
7123 : }
7124 : }
7125 4449 : return NULL_TREE;
7126 : }
7127 :
7128 : /* Data passed from cp_check_omp_declare_reduction to
7129 : cp_check_omp_declare_reduction_r. */
7130 :
7131 : struct cp_check_omp_declare_reduction_data
7132 : {
7133 : location_t loc;
7134 : tree stmts[7];
7135 : bool combiner_p;
7136 : };
7137 :
7138 : /* Helper function for cp_check_omp_declare_reduction, called via
7139 : cp_walk_tree. */
7140 :
7141 : static tree
7142 15042 : cp_check_omp_declare_reduction_r (tree *tp, int *, void *data)
7143 : {
7144 15042 : struct cp_check_omp_declare_reduction_data *udr_data
7145 : = (struct cp_check_omp_declare_reduction_data *) data;
7146 15042 : if (SSA_VAR_P (*tp)
7147 2702 : && !DECL_ARTIFICIAL (*tp)
7148 225 : && *tp != DECL_EXPR_DECL (udr_data->stmts[udr_data->combiner_p ? 0 : 3])
7149 225 : && *tp != DECL_EXPR_DECL (udr_data->stmts[udr_data->combiner_p ? 1 : 4]))
7150 : {
7151 135 : location_t loc = udr_data->loc;
7152 135 : if (udr_data->combiner_p)
7153 45 : error_at (loc, "%<#pragma omp declare reduction%> combiner refers to "
7154 : "variable %qD which is not %<omp_out%> nor %<omp_in%>",
7155 : *tp);
7156 : else
7157 90 : error_at (loc, "%<#pragma omp declare reduction%> initializer refers "
7158 : "to variable %qD which is not %<omp_priv%> nor "
7159 : "%<omp_orig%>",
7160 : *tp);
7161 135 : return *tp;
7162 : }
7163 : return NULL_TREE;
7164 : }
7165 :
7166 : /* Diagnose violation of OpenMP #pragma omp declare reduction restrictions. */
7167 :
7168 : bool
7169 1104 : cp_check_omp_declare_reduction (tree udr)
7170 : {
7171 1104 : tree type = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (udr)));
7172 1104 : gcc_assert (TYPE_REF_P (type));
7173 1104 : type = TREE_TYPE (type);
7174 1104 : int i;
7175 1104 : location_t loc = DECL_SOURCE_LOCATION (udr);
7176 :
7177 1104 : if (type == error_mark_node)
7178 : return false;
7179 1104 : if (ARITHMETIC_TYPE_P (type))
7180 : {
7181 : static enum tree_code predef_codes[]
7182 : = { PLUS_EXPR, MULT_EXPR, MINUS_EXPR, BIT_AND_EXPR, BIT_XOR_EXPR,
7183 : BIT_IOR_EXPR, TRUTH_ANDIF_EXPR, TRUTH_ORIF_EXPR };
7184 3276 : for (i = 0; i < 8; i++)
7185 : {
7186 2918 : tree id = omp_reduction_id (predef_codes[i], NULL_TREE, NULL_TREE);
7187 2918 : const char *n1 = IDENTIFIER_POINTER (DECL_NAME (udr));
7188 2918 : const char *n2 = IDENTIFIER_POINTER (id);
7189 2918 : if (strncmp (n1, n2, IDENTIFIER_LENGTH (id)) == 0
7190 2918 : && (n1[IDENTIFIER_LENGTH (id)] == '~'
7191 0 : || n1[IDENTIFIER_LENGTH (id)] == '\0'))
7192 : break;
7193 : }
7194 :
7195 376 : if (i == 8
7196 358 : && TREE_CODE (type) != COMPLEX_EXPR)
7197 : {
7198 358 : const char prefix_minmax[] = "omp declare reduction m";
7199 358 : size_t prefix_size = sizeof (prefix_minmax) - 1;
7200 358 : const char *n = IDENTIFIER_POINTER (DECL_NAME (udr));
7201 358 : if (strncmp (IDENTIFIER_POINTER (DECL_NAME (udr)),
7202 : prefix_minmax, prefix_size) == 0
7203 10 : && ((n[prefix_size] == 'i' && n[prefix_size + 1] == 'n')
7204 4 : || (n[prefix_size] == 'a' && n[prefix_size + 1] == 'x'))
7205 368 : && (n[prefix_size + 2] == '~' || n[prefix_size + 2] == '\0'))
7206 6 : i = 0;
7207 : }
7208 376 : if (i < 8)
7209 : {
7210 24 : error_at (loc, "predeclared arithmetic type %qT in "
7211 : "%<#pragma omp declare reduction%>", type);
7212 24 : return false;
7213 : }
7214 : }
7215 : else if (FUNC_OR_METHOD_TYPE_P (type)
7216 : || TREE_CODE (type) == ARRAY_TYPE)
7217 : {
7218 24 : error_at (loc, "function or array type %qT in "
7219 : "%<#pragma omp declare reduction%>", type);
7220 24 : return false;
7221 : }
7222 : else if (TYPE_REF_P (type))
7223 : {
7224 0 : error_at (loc, "reference type %qT in %<#pragma omp declare reduction%>",
7225 : type);
7226 0 : return false;
7227 : }
7228 704 : else if (TYPE_QUALS_NO_ADDR_SPACE (type))
7229 : {
7230 24 : error_at (loc, "%<const%>, %<volatile%> or %<__restrict%>-qualified "
7231 : "type %qT in %<#pragma omp declare reduction%>", type);
7232 24 : return false;
7233 : }
7234 :
7235 1032 : tree body = DECL_SAVED_TREE (udr);
7236 1032 : if (body == NULL_TREE || TREE_CODE (body) != STATEMENT_LIST)
7237 : return true;
7238 :
7239 846 : tree_stmt_iterator tsi;
7240 846 : struct cp_check_omp_declare_reduction_data data;
7241 846 : memset (data.stmts, 0, sizeof data.stmts);
7242 846 : for (i = 0, tsi = tsi_start (body);
7243 4707 : i < 7 && !tsi_end_p (tsi);
7244 3861 : i++, tsi_next (&tsi))
7245 3861 : data.stmts[i] = tsi_stmt (tsi);
7246 846 : data.loc = loc;
7247 846 : gcc_assert (tsi_end_p (tsi));
7248 846 : if (i >= 3)
7249 : {
7250 846 : gcc_assert (TREE_CODE (data.stmts[0]) == DECL_EXPR
7251 : && TREE_CODE (data.stmts[1]) == DECL_EXPR);
7252 846 : if (warning_suppressed_p (DECL_EXPR_DECL (data.stmts[0]) /* What warning? */))
7253 : return true;
7254 801 : data.combiner_p = true;
7255 801 : if (cp_walk_tree (&data.stmts[2], cp_check_omp_declare_reduction_r,
7256 : &data, NULL))
7257 45 : suppress_warning (DECL_EXPR_DECL (data.stmts[0]) /* What warning? */);
7258 : }
7259 801 : if (i >= 6)
7260 : {
7261 339 : gcc_assert (TREE_CODE (data.stmts[3]) == DECL_EXPR
7262 : && TREE_CODE (data.stmts[4]) == DECL_EXPR);
7263 339 : data.combiner_p = false;
7264 339 : if (cp_walk_tree (&data.stmts[5], cp_check_omp_declare_reduction_r,
7265 : &data, NULL)
7266 339 : || cp_walk_tree (&DECL_INITIAL (DECL_EXPR_DECL (data.stmts[3])),
7267 : cp_check_omp_declare_reduction_r, &data, NULL))
7268 90 : suppress_warning (DECL_EXPR_DECL (data.stmts[0]) /* Wat warning? */);
7269 339 : if (i == 7)
7270 201 : gcc_assert (TREE_CODE (data.stmts[6]) == DECL_EXPR);
7271 : }
7272 : return true;
7273 : }
7274 :
7275 : /* Helper function of finish_omp_clauses. Clone STMT as if we were making
7276 : an inline call. But, remap
7277 : the OMP_DECL1 VAR_DECL (omp_out resp. omp_orig) to PLACEHOLDER
7278 : and OMP_DECL2 VAR_DECL (omp_in resp. omp_priv) to DECL. */
7279 :
7280 : static tree
7281 2217 : clone_omp_udr (tree stmt, tree omp_decl1, tree omp_decl2,
7282 : tree decl, tree placeholder)
7283 : {
7284 2217 : copy_body_data id;
7285 2217 : hash_map<tree, tree> decl_map;
7286 :
7287 2217 : decl_map.put (omp_decl1, placeholder);
7288 2217 : decl_map.put (omp_decl2, decl);
7289 2217 : memset (&id, 0, sizeof (id));
7290 2217 : id.src_fn = DECL_CONTEXT (omp_decl1);
7291 2217 : id.dst_fn = current_function_decl;
7292 2217 : id.src_cfun = DECL_STRUCT_FUNCTION (id.src_fn);
7293 2217 : id.decl_map = &decl_map;
7294 :
7295 2217 : id.copy_decl = copy_decl_no_change;
7296 2217 : id.transform_call_graph_edges = CB_CGE_DUPLICATE;
7297 2217 : id.transform_new_cfg = true;
7298 2217 : id.transform_return_to_modify = false;
7299 2217 : id.eh_lp_nr = 0;
7300 2217 : walk_tree (&stmt, copy_tree_body_r, &id, NULL);
7301 2217 : return stmt;
7302 2217 : }
7303 :
7304 : /* Helper function of finish_omp_clauses, called via cp_walk_tree.
7305 : Find OMP_CLAUSE_PLACEHOLDER (passed in DATA) in *TP. */
7306 :
7307 : static tree
7308 15573 : find_omp_placeholder_r (tree *tp, int *, void *data)
7309 : {
7310 15573 : if (*tp == (tree) data)
7311 274 : return *tp;
7312 : return NULL_TREE;
7313 : }
7314 :
7315 : /* Helper function of finish_omp_clauses. Handle OMP_CLAUSE_REDUCTION C.
7316 : Return true if there is some error and the clause should be removed. */
7317 :
7318 : static bool
7319 9018 : finish_omp_reduction_clause (tree c, bool *need_default_ctor, bool *need_dtor)
7320 : {
7321 9018 : tree t = OMP_CLAUSE_DECL (c);
7322 9018 : bool predefined = false;
7323 9018 : if (TREE_CODE (t) == TREE_LIST)
7324 : {
7325 0 : gcc_assert (processing_template_decl);
7326 : return false;
7327 : }
7328 9018 : tree type = TREE_TYPE (t);
7329 9018 : if (TREE_CODE (t) == MEM_REF)
7330 1656 : type = TREE_TYPE (type);
7331 9018 : if (TYPE_REF_P (type))
7332 557 : type = TREE_TYPE (type);
7333 9018 : if (TREE_CODE (type) == ARRAY_TYPE)
7334 : {
7335 377 : tree oatype = type;
7336 377 : gcc_assert (TREE_CODE (t) != MEM_REF);
7337 757 : while (TREE_CODE (type) == ARRAY_TYPE)
7338 380 : type = TREE_TYPE (type);
7339 377 : if (!processing_template_decl)
7340 : {
7341 270 : t = require_complete_type (t);
7342 270 : if (t == error_mark_node
7343 270 : || !complete_type_or_else (oatype, NULL_TREE))
7344 : return true;
7345 261 : tree size = size_binop (EXACT_DIV_EXPR, TYPE_SIZE_UNIT (oatype),
7346 : TYPE_SIZE_UNIT (type));
7347 261 : if (integer_zerop (size))
7348 : {
7349 6 : error_at (OMP_CLAUSE_LOCATION (c),
7350 : "%qE in %<reduction%> clause is a zero size array",
7351 : omp_clause_printable_decl (t));
7352 3 : return true;
7353 : }
7354 258 : size = size_binop (MINUS_EXPR, size, size_one_node);
7355 258 : size = save_expr (size);
7356 258 : tree index_type = build_index_type (size);
7357 258 : tree atype = build_array_type (type, index_type);
7358 258 : tree ptype = build_pointer_type (type);
7359 258 : if (TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE)
7360 152 : t = build_fold_addr_expr (t);
7361 258 : t = build2 (MEM_REF, atype, t, build_int_cst (ptype, 0));
7362 258 : OMP_CLAUSE_DECL (c) = t;
7363 : }
7364 : }
7365 9006 : if (type == error_mark_node)
7366 : return true;
7367 9003 : else if (ARITHMETIC_TYPE_P (type))
7368 7734 : switch (OMP_CLAUSE_REDUCTION_CODE (c))
7369 : {
7370 : case PLUS_EXPR:
7371 : case MULT_EXPR:
7372 : case MINUS_EXPR:
7373 : case TRUTH_ANDIF_EXPR:
7374 : case TRUTH_ORIF_EXPR:
7375 : predefined = true;
7376 : break;
7377 246 : case MIN_EXPR:
7378 246 : case MAX_EXPR:
7379 246 : if (TREE_CODE (type) == COMPLEX_TYPE)
7380 : break;
7381 : predefined = true;
7382 : break;
7383 111 : case BIT_AND_EXPR:
7384 111 : case BIT_IOR_EXPR:
7385 111 : case BIT_XOR_EXPR:
7386 111 : if (FLOAT_TYPE_P (type) || TREE_CODE (type) == COMPLEX_TYPE)
7387 : break;
7388 : predefined = true;
7389 : break;
7390 : default:
7391 : break;
7392 : }
7393 1269 : else if (TYPE_READONLY (type))
7394 : {
7395 18 : error_at (OMP_CLAUSE_LOCATION (c),
7396 : "%qE has const type for %<reduction%>",
7397 : omp_clause_printable_decl (t));
7398 9 : return true;
7399 : }
7400 1260 : else if (!processing_template_decl)
7401 : {
7402 1047 : t = require_complete_type (t);
7403 1047 : if (t == error_mark_node)
7404 : return true;
7405 1047 : OMP_CLAUSE_DECL (c) = t;
7406 : }
7407 :
7408 1047 : if (predefined)
7409 : {
7410 7512 : OMP_CLAUSE_REDUCTION_PLACEHOLDER (c) = NULL_TREE;
7411 7512 : return false;
7412 : }
7413 1482 : else if (processing_template_decl)
7414 : {
7415 222 : if (OMP_CLAUSE_REDUCTION_PLACEHOLDER (c) == error_mark_node)
7416 : return true;
7417 219 : return false;
7418 : }
7419 :
7420 1260 : tree id = OMP_CLAUSE_REDUCTION_PLACEHOLDER (c);
7421 :
7422 1260 : type = TYPE_MAIN_VARIANT (type);
7423 1260 : OMP_CLAUSE_REDUCTION_PLACEHOLDER (c) = NULL_TREE;
7424 1260 : if (id == NULL_TREE)
7425 933 : id = omp_reduction_id (OMP_CLAUSE_REDUCTION_CODE (c),
7426 : NULL_TREE, NULL_TREE);
7427 1260 : id = omp_reduction_lookup (OMP_CLAUSE_LOCATION (c), id, type, NULL, NULL);
7428 1260 : if (id)
7429 : {
7430 1215 : if (id == error_mark_node)
7431 : return true;
7432 1209 : mark_used (id);
7433 1209 : tree body = DECL_SAVED_TREE (id);
7434 1209 : if (!body)
7435 : return true;
7436 1206 : if (TREE_CODE (body) == STATEMENT_LIST)
7437 : {
7438 1206 : tree_stmt_iterator tsi;
7439 1206 : tree placeholder = NULL_TREE, decl_placeholder = NULL_TREE;
7440 1206 : int i;
7441 1206 : tree stmts[7];
7442 1206 : tree atype = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (id)));
7443 1206 : atype = TREE_TYPE (atype);
7444 1206 : bool need_static_cast = !same_type_p (type, atype);
7445 1206 : memset (stmts, 0, sizeof stmts);
7446 1206 : for (i = 0, tsi = tsi_start (body);
7447 8594 : i < 7 && !tsi_end_p (tsi);
7448 7388 : i++, tsi_next (&tsi))
7449 7388 : stmts[i] = tsi_stmt (tsi);
7450 1206 : gcc_assert (tsi_end_p (tsi));
7451 :
7452 1206 : if (i >= 3)
7453 : {
7454 1206 : gcc_assert (TREE_CODE (stmts[0]) == DECL_EXPR
7455 : && TREE_CODE (stmts[1]) == DECL_EXPR);
7456 1206 : placeholder = build_lang_decl (VAR_DECL, NULL_TREE, type);
7457 1206 : DECL_ARTIFICIAL (placeholder) = 1;
7458 1206 : DECL_IGNORED_P (placeholder) = 1;
7459 1206 : OMP_CLAUSE_REDUCTION_PLACEHOLDER (c) = placeholder;
7460 1206 : if (TREE_CODE (t) == MEM_REF)
7461 : {
7462 600 : decl_placeholder = build_lang_decl (VAR_DECL, NULL_TREE,
7463 : type);
7464 600 : DECL_ARTIFICIAL (decl_placeholder) = 1;
7465 600 : DECL_IGNORED_P (decl_placeholder) = 1;
7466 600 : OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (c) = decl_placeholder;
7467 : }
7468 1206 : if (TREE_ADDRESSABLE (DECL_EXPR_DECL (stmts[0])))
7469 294 : cxx_mark_addressable (placeholder);
7470 1206 : if (TREE_ADDRESSABLE (DECL_EXPR_DECL (stmts[1]))
7471 1206 : && (decl_placeholder
7472 158 : || !TYPE_REF_P (TREE_TYPE (OMP_CLAUSE_DECL (c)))))
7473 390 : cxx_mark_addressable (decl_placeholder ? decl_placeholder
7474 127 : : OMP_CLAUSE_DECL (c));
7475 1206 : tree omp_out = placeholder;
7476 1206 : tree omp_in = decl_placeholder ? decl_placeholder
7477 606 : : convert_from_reference (OMP_CLAUSE_DECL (c));
7478 1206 : if (need_static_cast)
7479 : {
7480 7 : tree rtype = build_reference_type (atype);
7481 7 : omp_out = build_static_cast (input_location,
7482 : rtype, omp_out,
7483 : tf_warning_or_error);
7484 7 : omp_in = build_static_cast (input_location,
7485 : rtype, omp_in,
7486 : tf_warning_or_error);
7487 7 : if (omp_out == error_mark_node || omp_in == error_mark_node)
7488 3 : return true;
7489 7 : omp_out = convert_from_reference (omp_out);
7490 7 : omp_in = convert_from_reference (omp_in);
7491 : }
7492 1206 : OMP_CLAUSE_REDUCTION_MERGE (c)
7493 1206 : = clone_omp_udr (stmts[2], DECL_EXPR_DECL (stmts[0]),
7494 1206 : DECL_EXPR_DECL (stmts[1]), omp_in, omp_out);
7495 : }
7496 1206 : if (i >= 6)
7497 : {
7498 1014 : gcc_assert (TREE_CODE (stmts[3]) == DECL_EXPR
7499 : && TREE_CODE (stmts[4]) == DECL_EXPR);
7500 1014 : if (TREE_ADDRESSABLE (DECL_EXPR_DECL (stmts[3]))
7501 1014 : && (decl_placeholder
7502 232 : || !TYPE_REF_P (TREE_TYPE (OMP_CLAUSE_DECL (c)))))
7503 844 : cxx_mark_addressable (decl_placeholder ? decl_placeholder
7504 170 : : OMP_CLAUSE_DECL (c));
7505 1014 : if (TREE_ADDRESSABLE (DECL_EXPR_DECL (stmts[4])))
7506 225 : cxx_mark_addressable (placeholder);
7507 1014 : tree omp_priv = decl_placeholder ? decl_placeholder
7508 438 : : convert_from_reference (OMP_CLAUSE_DECL (c));
7509 1014 : tree omp_orig = placeholder;
7510 1014 : if (need_static_cast)
7511 : {
7512 5 : if (i == 7)
7513 : {
7514 3 : error_at (OMP_CLAUSE_LOCATION (c),
7515 : "user defined reduction with constructor "
7516 : "initializer for base class %qT", atype);
7517 3 : return true;
7518 : }
7519 2 : tree rtype = build_reference_type (atype);
7520 2 : omp_priv = build_static_cast (input_location,
7521 : rtype, omp_priv,
7522 : tf_warning_or_error);
7523 2 : omp_orig = build_static_cast (input_location,
7524 : rtype, omp_orig,
7525 : tf_warning_or_error);
7526 2 : if (omp_priv == error_mark_node
7527 2 : || omp_orig == error_mark_node)
7528 : return true;
7529 2 : omp_priv = convert_from_reference (omp_priv);
7530 2 : omp_orig = convert_from_reference (omp_orig);
7531 : }
7532 1011 : if (i == 6)
7533 286 : *need_default_ctor = true;
7534 1011 : OMP_CLAUSE_REDUCTION_INIT (c)
7535 1011 : = clone_omp_udr (stmts[5], DECL_EXPR_DECL (stmts[4]),
7536 1011 : DECL_EXPR_DECL (stmts[3]),
7537 : omp_priv, omp_orig);
7538 1011 : if (cp_walk_tree (&OMP_CLAUSE_REDUCTION_INIT (c),
7539 : find_omp_placeholder_r, placeholder, NULL))
7540 247 : OMP_CLAUSE_REDUCTION_OMP_ORIG_REF (c) = 1;
7541 : }
7542 192 : else if (i >= 3)
7543 : {
7544 192 : if (CLASS_TYPE_P (type) && !pod_type_p (type))
7545 175 : *need_default_ctor = true;
7546 : else
7547 : {
7548 17 : tree init;
7549 17 : tree v = decl_placeholder ? decl_placeholder
7550 17 : : convert_from_reference (t);
7551 17 : if (AGGREGATE_TYPE_P (TREE_TYPE (v)))
7552 8 : init = build_constructor (TREE_TYPE (v), NULL);
7553 : else
7554 9 : init = fold_convert (TREE_TYPE (v), integer_zero_node);
7555 34 : OMP_CLAUSE_REDUCTION_INIT (c)
7556 34 : = cp_build_init_expr (v, init);
7557 : }
7558 : }
7559 : }
7560 : }
7561 1248 : if (OMP_CLAUSE_REDUCTION_PLACEHOLDER (c))
7562 1203 : *need_dtor = true;
7563 : else
7564 : {
7565 90 : error_at (OMP_CLAUSE_LOCATION (c),
7566 : "user defined reduction not found for %qE",
7567 : omp_clause_printable_decl (t));
7568 45 : return true;
7569 : }
7570 1203 : if (TREE_CODE (OMP_CLAUSE_DECL (c)) == MEM_REF)
7571 600 : gcc_assert (TYPE_SIZE_UNIT (type)
7572 : && TREE_CODE (TYPE_SIZE_UNIT (type)) == INTEGER_CST);
7573 : return false;
7574 : }
7575 :
7576 : /* Check an instance of an "omp declare mapper" function. */
7577 :
7578 : bool
7579 208 : cp_check_omp_declare_mapper (tree udm)
7580 : {
7581 208 : tree var = OMP_DECLARE_MAPPER_DECL (udm);
7582 208 : tree type = TREE_TYPE (var);
7583 208 : location_t loc = DECL_SOURCE_LOCATION (var);
7584 :
7585 208 : if (type == error_mark_node)
7586 : return false;
7587 :
7588 208 : if (processing_template_decl)
7589 : return true;
7590 :
7591 197 : if (!RECORD_OR_UNION_TYPE_P (type))
7592 : {
7593 17 : error_at (loc, "%qT is not a struct, union or class type in "
7594 : "%<#pragma omp declare mapper%>", type);
7595 17 : return false;
7596 : }
7597 180 : if (CLASSTYPE_VBASECLASSES (type))
7598 : {
7599 3 : error_at (loc, "%qT must not be a virtual base class in "
7600 : "%<#pragma omp declare mapper%>", type);
7601 3 : return false;
7602 : }
7603 :
7604 177 : tree c = OMP_DECLARE_MAPPER_CLAUSES (udm);
7605 215 : for ( ; c; c = OMP_CLAUSE_CHAIN (c))
7606 : {
7607 187 : tree dvar = OMP_CLAUSE_DECL (c);
7608 400 : while (!DECL_P (dvar) && TREE_OPERAND_LENGTH (dvar))
7609 213 : dvar = TREE_OPERAND (dvar, 0);
7610 187 : if (dvar == var)
7611 : break;
7612 : }
7613 177 : if (!c)
7614 : {
7615 : // After template handling, the var is mangled, demangle it
7616 28 : const char *name = IDENTIFIER_POINTER (DECL_NAME (var));
7617 28 : char *n = NULL;
7618 28 : if (startswith (name, "omp declare mapper "))
7619 : {
7620 3 : name += strlen ("omp declare mapper ");
7621 3 : n = xstrdup (name);
7622 3 : n[strchr (n, '~')-n] = '\0';
7623 3 : name = n;
7624 : }
7625 28 : error_at (loc, "at least one %<map%> clause must map %qs or an "
7626 : "element of it", name);
7627 28 : if (n)
7628 3 : free (n);
7629 : return false;
7630 : }
7631 :
7632 : /* FIXME: The vardecl created for the mapper_id uses DECL_DECLARED_CONSTEXPR_P
7633 : = 1, which is set to false in finalize_literal_type_property for C++ < 11,
7634 : leading to an error in ensure_literal_type_for_constexpr_object.
7635 : Examples (compile with -std=c++98): gcc.dg/gomp/declare-mapper-13.c and
7636 : libgomp.c++/declare-mapper-{5,6,8}.C. */
7637 149 : if (cxx_dialect < cxx11)
7638 : {
7639 0 : sorry_at (loc, "%<#pragma omp declare mapper%> with %<-std=%> set to "
7640 : "before C++11");
7641 0 : return false;
7642 : }
7643 :
7644 : return true;
7645 : }
7646 :
7647 : /* Called from finish_struct_1. linear(this) or linear(this:step)
7648 : clauses might not be finalized yet because the class has been incomplete
7649 : when parsing #pragma omp declare simd methods. Fix those up now. */
7650 :
7651 : void
7652 118670 : finish_omp_declare_simd_methods (tree t)
7653 : {
7654 118670 : if (processing_template_decl)
7655 : return;
7656 :
7657 809929 : for (tree x = TYPE_FIELDS (t); x; x = DECL_CHAIN (x))
7658 : {
7659 1144212 : if (TREE_CODE (x) == USING_DECL
7660 691259 : || !DECL_IOBJ_MEMBER_FUNCTION_P (x))
7661 452953 : continue;
7662 238306 : tree ods = lookup_attribute ("omp declare simd", DECL_ATTRIBUTES (x));
7663 238414 : if (!ods || !TREE_VALUE (ods))
7664 238198 : continue;
7665 366 : for (tree c = TREE_VALUE (TREE_VALUE (ods)); c; c = OMP_CLAUSE_CHAIN (c))
7666 258 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
7667 66 : && integer_zerop (OMP_CLAUSE_DECL (c))
7668 18 : && OMP_CLAUSE_LINEAR_STEP (c)
7669 276 : && TYPE_PTR_P (TREE_TYPE (OMP_CLAUSE_LINEAR_STEP (c))))
7670 : {
7671 18 : tree s = OMP_CLAUSE_LINEAR_STEP (c);
7672 18 : s = fold_convert_loc (OMP_CLAUSE_LOCATION (c), sizetype, s);
7673 18 : s = fold_build2_loc (OMP_CLAUSE_LOCATION (c), MULT_EXPR,
7674 18 : sizetype, s, TYPE_SIZE_UNIT (t));
7675 18 : OMP_CLAUSE_LINEAR_STEP (c) = s;
7676 : }
7677 : }
7678 : }
7679 :
7680 : /* Adjust sink depend/doacross clause to take into account pointer offsets.
7681 :
7682 : Return TRUE if there was a problem processing the offset, and the
7683 : whole clause should be removed. */
7684 :
7685 : static bool
7686 298 : cp_finish_omp_clause_doacross_sink (tree sink_clause)
7687 : {
7688 298 : tree t = OMP_CLAUSE_DECL (sink_clause);
7689 298 : gcc_assert (TREE_CODE (t) == TREE_LIST);
7690 :
7691 : /* Make sure we don't adjust things twice for templates. */
7692 298 : if (processing_template_decl)
7693 : return false;
7694 :
7695 671 : for (; t; t = TREE_CHAIN (t))
7696 : {
7697 391 : tree decl = TREE_VALUE (t);
7698 391 : if (TYPE_PTR_P (TREE_TYPE (decl)))
7699 : {
7700 6 : tree offset = TREE_PURPOSE (t);
7701 6 : bool neg = wi::neg_p (wi::to_wide (offset));
7702 6 : offset = fold_unary (ABS_EXPR, TREE_TYPE (offset), offset);
7703 6 : decl = mark_rvalue_use (decl);
7704 6 : decl = convert_from_reference (decl);
7705 12 : tree t2 = pointer_int_sum (OMP_CLAUSE_LOCATION (sink_clause),
7706 : neg ? MINUS_EXPR : PLUS_EXPR,
7707 : decl, offset);
7708 6 : t2 = fold_build2_loc (OMP_CLAUSE_LOCATION (sink_clause),
7709 : MINUS_EXPR, sizetype,
7710 : fold_convert (sizetype, t2),
7711 : fold_convert (sizetype, decl));
7712 6 : if (t2 == error_mark_node)
7713 : return true;
7714 6 : TREE_PURPOSE (t) = t2;
7715 : }
7716 : }
7717 : return false;
7718 : }
7719 :
7720 : /* Finish OpenMP iterators ITER. Return true if they are erroneous
7721 : and clauses containing them should be removed. */
7722 :
7723 : static bool
7724 624 : cp_omp_finish_iterators (tree iter)
7725 : {
7726 624 : bool ret = false;
7727 1413 : for (tree it = iter; it; it = TREE_CHAIN (it))
7728 : {
7729 789 : tree var = OMP_ITERATOR_VAR (it);
7730 789 : tree begin = OMP_ITERATOR_BEGIN (it);
7731 789 : tree end = OMP_ITERATOR_END (it);
7732 789 : tree step = OMP_ITERATOR_STEP (it);
7733 789 : tree orig_step;
7734 789 : tree type = TREE_TYPE (var);
7735 789 : location_t loc = DECL_SOURCE_LOCATION (var);
7736 789 : if (type == error_mark_node)
7737 : {
7738 0 : ret = true;
7739 218 : continue;
7740 : }
7741 789 : if (type_dependent_expression_p (var))
7742 59 : continue;
7743 730 : if (!INTEGRAL_TYPE_P (type) && !POINTER_TYPE_P (type))
7744 : {
7745 27 : error_at (loc, "iterator %qD has neither integral nor pointer type",
7746 : var);
7747 27 : ret = true;
7748 27 : continue;
7749 : }
7750 703 : else if (TYPE_READONLY (type))
7751 : {
7752 24 : error_at (loc, "iterator %qD has const qualified type", var);
7753 24 : ret = true;
7754 24 : continue;
7755 : }
7756 679 : if (type_dependent_expression_p (begin)
7757 670 : || type_dependent_expression_p (end)
7758 1349 : || type_dependent_expression_p (step))
7759 15 : continue;
7760 664 : else if (error_operand_p (step))
7761 : {
7762 0 : ret = true;
7763 0 : continue;
7764 : }
7765 664 : else if (!INTEGRAL_TYPE_P (TREE_TYPE (step)))
7766 : {
7767 21 : error_at (EXPR_LOC_OR_LOC (step, loc),
7768 : "iterator step with non-integral type");
7769 21 : ret = true;
7770 21 : continue;
7771 : }
7772 :
7773 643 : begin = mark_rvalue_use (begin);
7774 643 : end = mark_rvalue_use (end);
7775 643 : step = mark_rvalue_use (step);
7776 643 : begin = cp_build_c_cast (input_location, type, begin,
7777 : tf_warning_or_error);
7778 643 : end = cp_build_c_cast (input_location, type, end,
7779 : tf_warning_or_error);
7780 643 : orig_step = step;
7781 643 : if (!processing_template_decl)
7782 566 : step = orig_step = save_expr (step);
7783 643 : tree stype = POINTER_TYPE_P (type) ? sizetype : type;
7784 643 : step = cp_build_c_cast (input_location, stype, step,
7785 : tf_warning_or_error);
7786 643 : if (POINTER_TYPE_P (type) && !processing_template_decl)
7787 : {
7788 66 : begin = save_expr (begin);
7789 66 : step = pointer_int_sum (loc, PLUS_EXPR, begin, step);
7790 66 : step = fold_build2_loc (loc, MINUS_EXPR, sizetype,
7791 : fold_convert (sizetype, step),
7792 : fold_convert (sizetype, begin));
7793 66 : step = fold_convert (ssizetype, step);
7794 : }
7795 643 : if (!processing_template_decl)
7796 : {
7797 566 : begin = maybe_constant_value (begin);
7798 566 : end = maybe_constant_value (end);
7799 566 : step = maybe_constant_value (step);
7800 566 : orig_step = maybe_constant_value (orig_step);
7801 : }
7802 643 : if (integer_zerop (step))
7803 : {
7804 27 : error_at (loc, "iterator %qD has zero step", var);
7805 27 : ret = true;
7806 27 : continue;
7807 : }
7808 :
7809 616 : if (begin == error_mark_node
7810 607 : || end == error_mark_node
7811 598 : || step == error_mark_node
7812 598 : || orig_step == error_mark_node)
7813 : {
7814 18 : ret = true;
7815 18 : continue;
7816 : }
7817 :
7818 598 : if (!processing_template_decl)
7819 : {
7820 521 : begin = fold_build_cleanup_point_expr (TREE_TYPE (begin), begin);
7821 521 : end = fold_build_cleanup_point_expr (TREE_TYPE (end), end);
7822 521 : step = fold_build_cleanup_point_expr (TREE_TYPE (step), step);
7823 521 : orig_step = fold_build_cleanup_point_expr (TREE_TYPE (orig_step),
7824 : orig_step);
7825 : }
7826 598 : hash_set<tree> pset;
7827 598 : tree it2;
7828 754 : for (it2 = TREE_CHAIN (it); it2; it2 = TREE_CHAIN (it2))
7829 : {
7830 183 : tree var2 = OMP_ITERATOR_VAR (it2);
7831 183 : tree begin2 = OMP_ITERATOR_BEGIN (it2);
7832 183 : tree end2 = OMP_ITERATOR_END (it2);
7833 183 : tree step2 = OMP_ITERATOR_STEP (it2);
7834 183 : location_t loc2 = DECL_SOURCE_LOCATION (var2);
7835 183 : if (cp_walk_tree (&begin2, find_omp_placeholder_r, var, &pset))
7836 : {
7837 9 : error_at (EXPR_LOC_OR_LOC (begin2, loc2),
7838 : "begin expression refers to outer iterator %qD", var);
7839 36 : break;
7840 : }
7841 174 : else if (cp_walk_tree (&end2, find_omp_placeholder_r, var, &pset))
7842 : {
7843 9 : error_at (EXPR_LOC_OR_LOC (end2, loc2),
7844 : "end expression refers to outer iterator %qD", var);
7845 9 : break;
7846 : }
7847 165 : else if (cp_walk_tree (&step2, find_omp_placeholder_r, var, &pset))
7848 : {
7849 9 : error_at (EXPR_LOC_OR_LOC (step2, loc2),
7850 : "step expression refers to outer iterator %qD", var);
7851 9 : break;
7852 : }
7853 : }
7854 598 : if (it2)
7855 : {
7856 27 : ret = true;
7857 27 : continue;
7858 : }
7859 571 : OMP_ITERATOR_BEGIN (it) = begin;
7860 571 : OMP_ITERATOR_END (it) = end;
7861 571 : if (processing_template_decl)
7862 71 : OMP_ITERATOR_STEP (it) = orig_step;
7863 : else
7864 : {
7865 500 : OMP_ITERATOR_STEP (it) = step;
7866 500 : OMP_ITERATOR_ORIG_STEP (it) = orig_step;
7867 : }
7868 598 : }
7869 624 : return ret;
7870 : }
7871 :
7872 : /* Ensure that pointers are used in OpenACC attach and detach clauses.
7873 : Return true if an error has been detected. */
7874 :
7875 : static bool
7876 18852 : cp_oacc_check_attachments (tree c)
7877 : {
7878 18852 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP)
7879 : return false;
7880 :
7881 : /* OpenACC attach / detach clauses must be pointers. */
7882 14817 : if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH
7883 14817 : || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_DETACH)
7884 : {
7885 196 : tree t = OMP_CLAUSE_DECL (c);
7886 196 : tree type;
7887 :
7888 232 : while (TREE_CODE (t) == OMP_ARRAY_SECTION)
7889 36 : t = TREE_OPERAND (t, 0);
7890 :
7891 196 : type = TREE_TYPE (t);
7892 :
7893 196 : if (TREE_CODE (type) == REFERENCE_TYPE)
7894 36 : type = TREE_TYPE (type);
7895 :
7896 196 : if (TREE_CODE (type) != POINTER_TYPE)
7897 : {
7898 36 : error_at (OMP_CLAUSE_LOCATION (c), "expected pointer in %qs clause",
7899 : user_omp_clause_code_name (c, true));
7900 36 : return true;
7901 : }
7902 : }
7903 :
7904 : return false;
7905 : }
7906 :
7907 : /* Update OMP_CLAUSE_INIT_PREFER_TYPE in case template substitution
7908 : happened. */
7909 :
7910 : tree
7911 813 : cp_finish_omp_init_prefer_type (tree pref_type)
7912 : {
7913 813 : if (processing_template_decl
7914 741 : || pref_type == NULL_TREE
7915 356 : || TREE_CODE (pref_type) != TREE_LIST)
7916 : return pref_type;
7917 :
7918 81 : tree t = TREE_PURPOSE (pref_type);
7919 81 : char *str = const_cast<char *> (TREE_STRING_POINTER (t));
7920 81 : tree fr_list = TREE_VALUE (pref_type);
7921 81 : int len = TREE_VEC_LENGTH (fr_list);
7922 81 : int cnt = 0;
7923 :
7924 270 : while (str[0] == (char) GOMP_INTEROP_IFR_SEPARATOR)
7925 : {
7926 270 : str++;
7927 270 : if (str[0] == (char) GOMP_INTEROP_IFR_UNKNOWN)
7928 : {
7929 : /* Assume a no or a single 'fr'. */
7930 150 : gcc_checking_assert (str[1] == (char) GOMP_INTEROP_IFR_SEPARATOR);
7931 150 : location_t loc = UNKNOWN_LOCATION;
7932 150 : tree value = TREE_VEC_ELT (fr_list, cnt);
7933 150 : if (value != NULL_TREE && value != error_mark_node)
7934 : {
7935 126 : loc = EXPR_LOCATION (value);
7936 126 : if (value && TREE_CODE (value) == NOP_EXPR)
7937 39 : value = TREE_OPERAND (value, 0);
7938 126 : value = cp_fully_fold (value);
7939 : }
7940 126 : if (value != NULL_TREE && value != error_mark_node)
7941 : {
7942 126 : if (TREE_CODE (value) != INTEGER_CST
7943 126 : || !tree_fits_shwi_p (value))
7944 0 : error_at (loc,
7945 : "expected string literal or "
7946 : "constant integer expression instead of %qE", value);
7947 : else
7948 : {
7949 126 : HOST_WIDE_INT n = tree_to_shwi (value);
7950 126 : if (n < 1 || n > GOMP_INTEROP_IFR_LAST)
7951 : {
7952 48 : warning_at (loc, OPT_Wopenmp,
7953 : "unknown foreign runtime identifier %qwd", n);
7954 48 : n = GOMP_INTEROP_IFR_UNKNOWN;
7955 : }
7956 126 : str[0] = (char) n;
7957 : }
7958 : }
7959 150 : str++;
7960 : }
7961 120 : else if (str[0] != (char) GOMP_INTEROP_IFR_SEPARATOR)
7962 : {
7963 : /* Assume a no or a single 'fr'. */
7964 120 : gcc_checking_assert (str[1] == (char) GOMP_INTEROP_IFR_SEPARATOR);
7965 120 : str++;
7966 : }
7967 270 : str++;
7968 294 : while (str[0] != '\0')
7969 24 : str += strlen (str) + 1;
7970 270 : str++;
7971 270 : cnt++;
7972 270 : if (cnt >= len)
7973 : break;
7974 : }
7975 : return t;
7976 : }
7977 :
7978 : /* For all elements of CLAUSES, validate them vs OpenMP constraints.
7979 : Remove any elements from the list that are invalid. */
7980 :
7981 : tree
7982 63634 : finish_omp_clauses (tree clauses, enum c_omp_region_type ort)
7983 : {
7984 63634 : bitmap_head generic_head, firstprivate_head, lastprivate_head;
7985 63634 : bitmap_head aligned_head, map_head, map_field_head, map_firstprivate_head;
7986 63634 : bitmap_head oacc_reduction_head, is_on_device_head;
7987 63634 : tree c, t, *pc;
7988 63634 : tree safelen = NULL_TREE;
7989 63634 : bool openacc = (ort & C_ORT_ACC) != 0;
7990 63634 : bool branch_seen = false;
7991 63634 : bool copyprivate_seen = false;
7992 63634 : bool ordered_seen = false;
7993 63634 : bool order_seen = false;
7994 63634 : bool schedule_seen = false;
7995 63634 : bool oacc_async = false;
7996 63634 : bool indir_component_ref_p = false;
7997 63634 : tree last_iterators = NULL_TREE;
7998 63634 : bool last_iterators_remove = false;
7999 : /* 1 if normal/task reduction has been seen, -1 if inscan reduction
8000 : has been seen, -2 if mixed inscan/normal reduction diagnosed. */
8001 63634 : int reduction_seen = 0;
8002 63634 : bool allocate_seen = false;
8003 63634 : tree detach_seen = NULL_TREE;
8004 63634 : bool mergeable_seen = false;
8005 63634 : bool implicit_moved = false;
8006 63634 : bool target_in_reduction_seen = false;
8007 63634 : bool num_tasks_seen = false;
8008 63634 : bool partial_seen = false;
8009 63634 : bool init_seen = false;
8010 63634 : bool init_use_destroy_seen = false;
8011 63634 : tree init_no_targetsync_clause = NULL_TREE;
8012 63634 : tree depend_clause = NULL_TREE;
8013 :
8014 63634 : if (!openacc)
8015 50813 : clauses = omp_remove_duplicate_maps (clauses, true);
8016 :
8017 63634 : bitmap_obstack_initialize (NULL);
8018 63634 : bitmap_initialize (&generic_head, &bitmap_default_obstack);
8019 63634 : bitmap_initialize (&firstprivate_head, &bitmap_default_obstack);
8020 63634 : bitmap_initialize (&lastprivate_head, &bitmap_default_obstack);
8021 63634 : bitmap_initialize (&aligned_head, &bitmap_default_obstack);
8022 : /* If ort == C_ORT_OMP_DECLARE_SIMD used as uniform_head instead. */
8023 63634 : bitmap_initialize (&map_head, &bitmap_default_obstack);
8024 63634 : bitmap_initialize (&map_field_head, &bitmap_default_obstack);
8025 63634 : bitmap_initialize (&map_firstprivate_head, &bitmap_default_obstack);
8026 : /* If ort == C_ORT_OMP used as nontemporal_head or use_device_xxx_head
8027 : instead and for ort == C_ORT_OMP_TARGET used as in_reduction_head. */
8028 63634 : bitmap_initialize (&oacc_reduction_head, &bitmap_default_obstack);
8029 63634 : bitmap_initialize (&is_on_device_head, &bitmap_default_obstack);
8030 :
8031 63634 : if (openacc)
8032 28440 : for (c = clauses; c; c = OMP_CLAUSE_CHAIN (c))
8033 16007 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_ASYNC)
8034 : {
8035 : oacc_async = true;
8036 : break;
8037 : }
8038 :
8039 63634 : tree *grp_start_p = NULL, grp_sentinel = NULL_TREE;
8040 :
8041 162725 : for (pc = &clauses, c = clauses; c ; c = *pc)
8042 : {
8043 99091 : bool remove = false;
8044 99091 : bool field_ok = false;
8045 :
8046 : /* We've reached the end of a list of expanded nodes. Reset the group
8047 : start pointer. */
8048 99091 : if (c == grp_sentinel)
8049 : {
8050 5713 : if (grp_start_p
8051 5713 : && OMP_CLAUSE_HAS_ITERATORS (*grp_start_p))
8052 96 : for (tree gc = *grp_start_p; gc != grp_sentinel;
8053 66 : gc = OMP_CLAUSE_CHAIN (gc))
8054 66 : OMP_CLAUSE_ITERATORS (gc) = OMP_CLAUSE_ITERATORS (*grp_start_p);
8055 : grp_start_p = NULL;
8056 : }
8057 :
8058 99091 : switch (OMP_CLAUSE_CODE (c))
8059 : {
8060 2100 : case OMP_CLAUSE_SHARED:
8061 2100 : field_ok = ((ort & C_ORT_OMP_DECLARE_SIMD) == C_ORT_OMP);
8062 2100 : goto check_dup_generic;
8063 2584 : case OMP_CLAUSE_PRIVATE:
8064 2584 : field_ok = ((ort & C_ORT_OMP_DECLARE_SIMD) == C_ORT_OMP);
8065 2584 : goto check_dup_generic;
8066 7548 : case OMP_CLAUSE_REDUCTION:
8067 7548 : if (reduction_seen == 0)
8068 6429 : reduction_seen = OMP_CLAUSE_REDUCTION_INSCAN (c) ? -1 : 1;
8069 1119 : else if (reduction_seen != -2
8070 2238 : && reduction_seen != (OMP_CLAUSE_REDUCTION_INSCAN (c)
8071 1119 : ? -1 : 1))
8072 : {
8073 6 : error_at (OMP_CLAUSE_LOCATION (c),
8074 : "%<inscan%> and non-%<inscan%> %<reduction%> clauses "
8075 : "on the same construct");
8076 6 : reduction_seen = -2;
8077 : }
8078 : /* FALLTHRU */
8079 9693 : case OMP_CLAUSE_IN_REDUCTION:
8080 9693 : case OMP_CLAUSE_TASK_REDUCTION:
8081 9693 : field_ok = ((ort & C_ORT_OMP_DECLARE_SIMD) == C_ORT_OMP);
8082 9693 : t = OMP_CLAUSE_DECL (c);
8083 9693 : if (TREE_CODE (t) == OMP_ARRAY_SECTION)
8084 : {
8085 2315 : if (handle_omp_array_sections (c, ort))
8086 : {
8087 : remove = true;
8088 : break;
8089 : }
8090 2273 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
8091 2273 : && OMP_CLAUSE_REDUCTION_INSCAN (c))
8092 : {
8093 3 : error_at (OMP_CLAUSE_LOCATION (c),
8094 : "%<inscan%> %<reduction%> clause with array "
8095 : "section");
8096 3 : remove = true;
8097 3 : break;
8098 : }
8099 2270 : if (TREE_CODE (t) == OMP_ARRAY_SECTION)
8100 : {
8101 4888 : while (TREE_CODE (t) == OMP_ARRAY_SECTION)
8102 2618 : t = TREE_OPERAND (t, 0);
8103 : }
8104 : else
8105 : {
8106 0 : gcc_assert (TREE_CODE (t) == MEM_REF);
8107 0 : t = TREE_OPERAND (t, 0);
8108 0 : if (TREE_CODE (t) == POINTER_PLUS_EXPR)
8109 0 : t = TREE_OPERAND (t, 0);
8110 0 : if (TREE_CODE (t) == ADDR_EXPR
8111 0 : || INDIRECT_REF_P (t))
8112 0 : t = TREE_OPERAND (t, 0);
8113 : }
8114 2270 : tree n = omp_clause_decl_field (t);
8115 2270 : if (n)
8116 59 : t = n;
8117 2270 : goto check_dup_generic_t;
8118 : }
8119 7378 : if (oacc_async)
8120 7 : cxx_mark_addressable (t);
8121 7378 : goto check_dup_generic;
8122 98 : case OMP_CLAUSE_COPYPRIVATE:
8123 98 : copyprivate_seen = true;
8124 98 : field_ok = ((ort & C_ORT_OMP_DECLARE_SIMD) == C_ORT_OMP);
8125 98 : goto check_dup_generic;
8126 280 : case OMP_CLAUSE_COPYIN:
8127 280 : goto check_dup_generic;
8128 1631 : case OMP_CLAUSE_LINEAR:
8129 1631 : field_ok = ((ort & C_ORT_OMP_DECLARE_SIMD) == C_ORT_OMP);
8130 1631 : t = OMP_CLAUSE_DECL (c);
8131 1631 : if (ort != C_ORT_OMP_DECLARE_SIMD
8132 1631 : && OMP_CLAUSE_LINEAR_KIND (c) != OMP_CLAUSE_LINEAR_DEFAULT)
8133 : {
8134 84 : if (OMP_CLAUSE_LINEAR_OLD_LINEAR_MODIFIER (c))
8135 : {
8136 42 : error_at (OMP_CLAUSE_LOCATION (c),
8137 : "modifier should not be specified in %<linear%> "
8138 : "clause on %<simd%> or %<for%> constructs when "
8139 : "not using OpenMP 5.2 modifiers");
8140 42 : OMP_CLAUSE_LINEAR_KIND (c) = OMP_CLAUSE_LINEAR_DEFAULT;
8141 : }
8142 42 : else if (OMP_CLAUSE_LINEAR_KIND (c) != OMP_CLAUSE_LINEAR_VAL)
8143 : {
8144 18 : error_at (OMP_CLAUSE_LOCATION (c),
8145 : "modifier other than %<val%> specified in "
8146 : "%<linear%> clause on %<simd%> or %<for%> "
8147 : "constructs when using OpenMP 5.2 modifiers");
8148 18 : OMP_CLAUSE_LINEAR_KIND (c) = OMP_CLAUSE_LINEAR_DEFAULT;
8149 : }
8150 : }
8151 1011 : if ((VAR_P (t) || TREE_CODE (t) == PARM_DECL)
8152 2571 : && !type_dependent_expression_p (t))
8153 : {
8154 1529 : tree type = TREE_TYPE (t);
8155 1529 : if ((OMP_CLAUSE_LINEAR_KIND (c) == OMP_CLAUSE_LINEAR_REF
8156 1448 : || OMP_CLAUSE_LINEAR_KIND (c) == OMP_CLAUSE_LINEAR_UVAL)
8157 1598 : && !TYPE_REF_P (type))
8158 : {
8159 12 : error_at (OMP_CLAUSE_LOCATION (c),
8160 : "linear clause with %qs modifier applied to "
8161 : "non-reference variable with %qT type",
8162 12 : OMP_CLAUSE_LINEAR_KIND (c) == OMP_CLAUSE_LINEAR_REF
8163 12 : ? "ref" : "uval", TREE_TYPE (t));
8164 12 : remove = true;
8165 12 : break;
8166 : }
8167 1517 : if (TYPE_REF_P (type))
8168 281 : type = TREE_TYPE (type);
8169 1517 : if (OMP_CLAUSE_LINEAR_KIND (c) != OMP_CLAUSE_LINEAR_REF)
8170 : {
8171 1442 : if (!INTEGRAL_TYPE_P (type)
8172 85 : && !TYPE_PTR_P (type))
8173 : {
8174 18 : error_at (OMP_CLAUSE_LOCATION (c),
8175 : "linear clause applied to non-integral "
8176 : "non-pointer variable with %qT type",
8177 18 : TREE_TYPE (t));
8178 18 : remove = true;
8179 18 : break;
8180 : }
8181 : }
8182 : }
8183 1601 : t = OMP_CLAUSE_LINEAR_STEP (c);
8184 1601 : if (t == NULL_TREE)
8185 6 : t = integer_one_node;
8186 1601 : if (t == error_mark_node)
8187 : {
8188 : remove = true;
8189 : break;
8190 : }
8191 1601 : else if (!type_dependent_expression_p (t)
8192 1599 : && !INTEGRAL_TYPE_P (TREE_TYPE (t))
8193 1613 : && (ort != C_ORT_OMP_DECLARE_SIMD
8194 9 : || TREE_CODE (t) != PARM_DECL
8195 6 : || !TYPE_REF_P (TREE_TYPE (t))
8196 6 : || !INTEGRAL_TYPE_P (TREE_TYPE (TREE_TYPE (t)))))
8197 : {
8198 6 : error_at (OMP_CLAUSE_LOCATION (c),
8199 : "linear step expression must be integral");
8200 6 : remove = true;
8201 6 : break;
8202 : }
8203 : else
8204 : {
8205 1595 : t = mark_rvalue_use (t);
8206 1595 : if (ort == C_ORT_OMP_DECLARE_SIMD && TREE_CODE (t) == PARM_DECL)
8207 : {
8208 42 : OMP_CLAUSE_LINEAR_VARIABLE_STRIDE (c) = 1;
8209 42 : goto check_dup_generic;
8210 : }
8211 1553 : if (!processing_template_decl
8212 1553 : && (VAR_P (OMP_CLAUSE_DECL (c))
8213 835 : || TREE_CODE (OMP_CLAUSE_DECL (c)) == PARM_DECL))
8214 : {
8215 1372 : if (ort == C_ORT_OMP_DECLARE_SIMD)
8216 : {
8217 589 : t = maybe_constant_value (t);
8218 589 : if (TREE_CODE (t) != INTEGER_CST)
8219 : {
8220 6 : error_at (OMP_CLAUSE_LOCATION (c),
8221 : "%<linear%> clause step %qE is neither "
8222 : "constant nor a parameter", t);
8223 6 : remove = true;
8224 6 : break;
8225 : }
8226 : }
8227 1366 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8228 1366 : tree type = TREE_TYPE (OMP_CLAUSE_DECL (c));
8229 1366 : if (TYPE_REF_P (type))
8230 257 : type = TREE_TYPE (type);
8231 1366 : if (OMP_CLAUSE_LINEAR_KIND (c) == OMP_CLAUSE_LINEAR_REF)
8232 : {
8233 66 : type = build_pointer_type (type);
8234 66 : tree d = fold_convert (type, OMP_CLAUSE_DECL (c));
8235 66 : t = pointer_int_sum (OMP_CLAUSE_LOCATION (c), PLUS_EXPR,
8236 : d, t);
8237 66 : t = fold_build2_loc (OMP_CLAUSE_LOCATION (c),
8238 : MINUS_EXPR, sizetype,
8239 : fold_convert (sizetype, t),
8240 : fold_convert (sizetype, d));
8241 66 : if (t == error_mark_node)
8242 : {
8243 : remove = true;
8244 : break;
8245 : }
8246 : }
8247 1300 : else if (TYPE_PTR_P (type)
8248 : /* Can't multiply the step yet if *this
8249 : is still incomplete type. */
8250 1300 : && (ort != C_ORT_OMP_DECLARE_SIMD
8251 45 : || TREE_CODE (OMP_CLAUSE_DECL (c)) != PARM_DECL
8252 45 : || !DECL_ARTIFICIAL (OMP_CLAUSE_DECL (c))
8253 30 : || DECL_NAME (OMP_CLAUSE_DECL (c))
8254 30 : != this_identifier
8255 30 : || !TYPE_BEING_DEFINED (TREE_TYPE (type))))
8256 : {
8257 37 : tree d = convert_from_reference (OMP_CLAUSE_DECL (c));
8258 37 : t = pointer_int_sum (OMP_CLAUSE_LOCATION (c), PLUS_EXPR,
8259 : d, t);
8260 37 : t = fold_build2_loc (OMP_CLAUSE_LOCATION (c),
8261 : MINUS_EXPR, sizetype,
8262 : fold_convert (sizetype, t),
8263 : fold_convert (sizetype, d));
8264 37 : if (t == error_mark_node)
8265 : {
8266 : remove = true;
8267 : break;
8268 : }
8269 : }
8270 : else
8271 1263 : t = fold_convert (type, t);
8272 : }
8273 1547 : OMP_CLAUSE_LINEAR_STEP (c) = t;
8274 : }
8275 1547 : goto check_dup_generic;
8276 14995 : check_dup_generic:
8277 14995 : t = omp_clause_decl_field (OMP_CLAUSE_DECL (c));
8278 14995 : if (t)
8279 : {
8280 101 : if (!remove && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_SHARED)
8281 101 : omp_note_field_privatization (t, OMP_CLAUSE_DECL (c));
8282 : }
8283 : else
8284 14894 : t = OMP_CLAUSE_DECL (c);
8285 17532 : check_dup_generic_t:
8286 17532 : if (t == current_class_ptr
8287 17532 : && ((ort != C_ORT_OMP_DECLARE_SIMD && !openacc)
8288 102 : || (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_LINEAR
8289 72 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_UNIFORM)))
8290 : {
8291 24 : error_at (OMP_CLAUSE_LOCATION (c),
8292 : "%<this%> allowed in OpenMP only in %<declare simd%>"
8293 : " clauses");
8294 24 : remove = true;
8295 24 : break;
8296 : }
8297 17508 : if (!VAR_P (t) && TREE_CODE (t) != PARM_DECL
8298 586 : && (!field_ok || TREE_CODE (t) != FIELD_DECL))
8299 : {
8300 59 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
8301 : break;
8302 39 : if (DECL_P (t))
8303 30 : error_at (OMP_CLAUSE_LOCATION (c),
8304 : "%qD is not a variable in clause %qs", t,
8305 15 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
8306 : else
8307 48 : error_at (OMP_CLAUSE_LOCATION (c),
8308 : "%qE is not a variable in clause %qs", t,
8309 24 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
8310 : remove = true;
8311 : }
8312 17449 : else if ((openacc
8313 2707 : && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION)
8314 14980 : || (ort == C_ORT_OMP
8315 12647 : && (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR
8316 12616 : || (OMP_CLAUSE_CODE (c)
8317 : == OMP_CLAUSE_USE_DEVICE_ADDR)))
8318 32322 : || (ort == C_ORT_OMP_TARGET
8319 938 : && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION))
8320 : {
8321 2854 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
8322 2854 : && (bitmap_bit_p (&generic_head, DECL_UID (t))
8323 275 : || bitmap_bit_p (&firstprivate_head, DECL_UID (t))))
8324 : {
8325 6 : error_at (OMP_CLAUSE_LOCATION (c),
8326 : "%qD appears more than once in data-sharing "
8327 : "clauses", t);
8328 6 : remove = true;
8329 6 : break;
8330 : }
8331 2848 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION)
8332 272 : target_in_reduction_seen = true;
8333 2848 : if (bitmap_bit_p (&oacc_reduction_head, DECL_UID (t)))
8334 : {
8335 12 : error_at (OMP_CLAUSE_LOCATION (c),
8336 : openacc
8337 : ? "%qD appears more than once in reduction clauses"
8338 : : "%qD appears more than once in data clauses",
8339 : t);
8340 6 : remove = true;
8341 : }
8342 : else
8343 2842 : bitmap_set_bit (&oacc_reduction_head, DECL_UID (t));
8344 : }
8345 14595 : else if (bitmap_bit_p (&generic_head, DECL_UID (t))
8346 14522 : || bitmap_bit_p (&firstprivate_head, DECL_UID (t))
8347 14519 : || bitmap_bit_p (&lastprivate_head, DECL_UID (t))
8348 29114 : || bitmap_bit_p (&map_firstprivate_head, DECL_UID (t)))
8349 : {
8350 76 : error_at (OMP_CLAUSE_LOCATION (c),
8351 : "%qD appears more than once in data clauses", t);
8352 76 : remove = true;
8353 : }
8354 14519 : else if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_PRIVATE
8355 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_HAS_DEVICE_ADDR
8356 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IS_DEVICE_PTR)
8357 3125 : && bitmap_bit_p (&map_head, DECL_UID (t)))
8358 : {
8359 9 : if (openacc)
8360 0 : error_at (OMP_CLAUSE_LOCATION (c),
8361 : "%qD appears more than once in data clauses", t);
8362 : else
8363 9 : error_at (OMP_CLAUSE_LOCATION (c),
8364 : "%qD appears both in data and map clauses", t);
8365 : remove = true;
8366 : }
8367 : else
8368 14510 : bitmap_set_bit (&generic_head, DECL_UID (t));
8369 17482 : if (!field_ok)
8370 : break;
8371 13071 : handle_field_decl:
8372 21825 : if (!remove
8373 21630 : && TREE_CODE (t) == FIELD_DECL
8374 16940 : && t == OMP_CLAUSE_DECL (c))
8375 : {
8376 795 : OMP_CLAUSE_DECL (c)
8377 795 : = omp_privatize_field (t, (OMP_CLAUSE_CODE (c)
8378 : == OMP_CLAUSE_SHARED));
8379 795 : if (OMP_CLAUSE_DECL (c) == error_mark_node)
8380 98622 : remove = true;
8381 : }
8382 : break;
8383 :
8384 3486 : case OMP_CLAUSE_FIRSTPRIVATE:
8385 3486 : if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c) && !implicit_moved)
8386 : {
8387 414 : move_implicit:
8388 414 : implicit_moved = true;
8389 : /* Move firstprivate and map clauses with
8390 : OMP_CLAUSE_{FIRSTPRIVATE,MAP}_IMPLICIT set to the end of
8391 : clauses chain. */
8392 414 : tree cl1 = NULL_TREE, cl2 = NULL_TREE;
8393 414 : tree *pc1 = pc, *pc2 = &cl1, *pc3 = &cl2;
8394 2704 : while (*pc1)
8395 2290 : if (OMP_CLAUSE_CODE (*pc1) == OMP_CLAUSE_FIRSTPRIVATE
8396 2290 : && OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (*pc1))
8397 : {
8398 275 : *pc3 = *pc1;
8399 275 : pc3 = &OMP_CLAUSE_CHAIN (*pc3);
8400 275 : *pc1 = OMP_CLAUSE_CHAIN (*pc1);
8401 : }
8402 2015 : else if (OMP_CLAUSE_CODE (*pc1) == OMP_CLAUSE_MAP
8403 2015 : && OMP_CLAUSE_MAP_IMPLICIT (*pc1))
8404 : {
8405 370 : *pc2 = *pc1;
8406 370 : pc2 = &OMP_CLAUSE_CHAIN (*pc2);
8407 370 : *pc1 = OMP_CLAUSE_CHAIN (*pc1);
8408 : }
8409 : else
8410 1645 : pc1 = &OMP_CLAUSE_CHAIN (*pc1);
8411 414 : *pc3 = NULL;
8412 414 : *pc2 = cl2;
8413 414 : *pc1 = cl1;
8414 414 : continue;
8415 414 : }
8416 3229 : t = omp_clause_decl_field (OMP_CLAUSE_DECL (c));
8417 3229 : if (t)
8418 69 : omp_note_field_privatization (t, OMP_CLAUSE_DECL (c));
8419 : else
8420 3160 : t = OMP_CLAUSE_DECL (c);
8421 3229 : if (!openacc && t == current_class_ptr)
8422 : {
8423 6 : error_at (OMP_CLAUSE_LOCATION (c),
8424 : "%<this%> allowed in OpenMP only in %<declare simd%>"
8425 : " clauses");
8426 6 : remove = true;
8427 6 : break;
8428 : }
8429 3223 : if (!VAR_P (t) && TREE_CODE (t) != PARM_DECL
8430 333 : && ((ort & C_ORT_OMP_DECLARE_SIMD) != C_ORT_OMP
8431 333 : || TREE_CODE (t) != FIELD_DECL))
8432 : {
8433 41 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
8434 : break;
8435 18 : if (DECL_P (t))
8436 12 : error_at (OMP_CLAUSE_LOCATION (c),
8437 : "%qD is not a variable in clause %<firstprivate%>",
8438 : t);
8439 : else
8440 6 : error_at (OMP_CLAUSE_LOCATION (c),
8441 : "%qE is not a variable in clause %<firstprivate%>",
8442 : t);
8443 : remove = true;
8444 : }
8445 3182 : else if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c)
8446 275 : && !OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET (c)
8447 3436 : && bitmap_bit_p (&map_firstprivate_head, DECL_UID (t)))
8448 : remove = true;
8449 3182 : else if (bitmap_bit_p (&generic_head, DECL_UID (t))
8450 3173 : || bitmap_bit_p (&firstprivate_head, DECL_UID (t))
8451 6352 : || bitmap_bit_p (&map_firstprivate_head, DECL_UID (t)))
8452 : {
8453 15 : error_at (OMP_CLAUSE_LOCATION (c),
8454 : "%qD appears more than once in data clauses", t);
8455 15 : remove = true;
8456 : }
8457 3167 : else if (bitmap_bit_p (&map_head, DECL_UID (t))
8458 3167 : || bitmap_bit_p (&map_field_head, DECL_UID (t)))
8459 : {
8460 21 : if (openacc)
8461 0 : error_at (OMP_CLAUSE_LOCATION (c),
8462 : "%qD appears more than once in data clauses", t);
8463 21 : else if (OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (c)
8464 21 : && !OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT_TARGET (c))
8465 : /* Silently drop the clause. */;
8466 : else
8467 18 : error_at (OMP_CLAUSE_LOCATION (c),
8468 : "%qD appears both in data and map clauses", t);
8469 : remove = true;
8470 : }
8471 : else
8472 3146 : bitmap_set_bit (&firstprivate_head, DECL_UID (t));
8473 3200 : goto handle_field_decl;
8474 :
8475 2793 : case OMP_CLAUSE_LASTPRIVATE:
8476 2793 : t = omp_clause_decl_field (OMP_CLAUSE_DECL (c));
8477 2793 : if (t)
8478 35 : omp_note_field_privatization (t, OMP_CLAUSE_DECL (c));
8479 : else
8480 2758 : t = OMP_CLAUSE_DECL (c);
8481 2793 : if (!openacc && t == current_class_ptr)
8482 : {
8483 6 : error_at (OMP_CLAUSE_LOCATION (c),
8484 : "%<this%> allowed in OpenMP only in %<declare simd%>"
8485 : " clauses");
8486 6 : remove = true;
8487 6 : break;
8488 : }
8489 2787 : if (!VAR_P (t) && TREE_CODE (t) != PARM_DECL
8490 259 : && ((ort & C_ORT_OMP_DECLARE_SIMD) != C_ORT_OMP
8491 259 : || TREE_CODE (t) != FIELD_DECL))
8492 : {
8493 35 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
8494 : break;
8495 9 : if (DECL_P (t))
8496 3 : error_at (OMP_CLAUSE_LOCATION (c),
8497 : "%qD is not a variable in clause %<lastprivate%>",
8498 : t);
8499 : else
8500 6 : error_at (OMP_CLAUSE_LOCATION (c),
8501 : "%qE is not a variable in clause %<lastprivate%>",
8502 : t);
8503 : remove = true;
8504 : }
8505 2752 : else if (bitmap_bit_p (&generic_head, DECL_UID (t))
8506 2752 : || bitmap_bit_p (&lastprivate_head, DECL_UID (t)))
8507 : {
8508 12 : error_at (OMP_CLAUSE_LOCATION (c),
8509 : "%qD appears more than once in data clauses", t);
8510 12 : remove = true;
8511 : }
8512 : else
8513 2740 : bitmap_set_bit (&lastprivate_head, DECL_UID (t));
8514 2761 : goto handle_field_decl;
8515 :
8516 2221 : case OMP_CLAUSE_IF:
8517 2221 : case OMP_CLAUSE_SELF:
8518 2221 : t = OMP_CLAUSE_OPERAND (c, 0);
8519 2221 : t = maybe_convert_cond (t);
8520 2221 : if (t == error_mark_node)
8521 : remove = true;
8522 2206 : else if (!processing_template_decl)
8523 2145 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8524 2221 : OMP_CLAUSE_OPERAND (c, 0) = t;
8525 2221 : break;
8526 :
8527 289 : case OMP_CLAUSE_FINAL:
8528 289 : t = OMP_CLAUSE_FINAL_EXPR (c);
8529 289 : t = maybe_convert_cond (t);
8530 289 : if (t == error_mark_node)
8531 : remove = true;
8532 289 : else if (!processing_template_decl)
8533 283 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8534 289 : OMP_CLAUSE_FINAL_EXPR (c) = t;
8535 289 : break;
8536 :
8537 92 : case OMP_CLAUSE_NOCONTEXT:
8538 92 : t = OMP_CLAUSE_NOCONTEXT_EXPR (c);
8539 92 : t = maybe_convert_cond (t);
8540 92 : if (t == error_mark_node)
8541 : remove = true;
8542 89 : else if (!processing_template_decl)
8543 83 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8544 92 : OMP_CLAUSE_NOCONTEXT_EXPR (c) = t;
8545 92 : break;
8546 :
8547 80 : case OMP_CLAUSE_NOVARIANTS:
8548 80 : t = OMP_CLAUSE_NOVARIANTS_EXPR (c);
8549 80 : t = maybe_convert_cond (t);
8550 80 : if (t == error_mark_node)
8551 : remove = true;
8552 77 : else if (!processing_template_decl)
8553 71 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8554 80 : OMP_CLAUSE_NOVARIANTS_EXPR (c) = t;
8555 80 : break;
8556 :
8557 1249 : case OMP_CLAUSE_GANG:
8558 : /* Operand 1 is the gang static: argument. */
8559 1249 : t = OMP_CLAUSE_OPERAND (c, 1);
8560 1249 : if (t != NULL_TREE)
8561 : {
8562 129 : if (t == error_mark_node)
8563 : remove = true;
8564 129 : else if (!type_dependent_expression_p (t)
8565 129 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8566 : {
8567 6 : error_at (OMP_CLAUSE_LOCATION (c),
8568 : "%<gang%> static expression must be integral");
8569 6 : remove = true;
8570 : }
8571 : else
8572 : {
8573 123 : t = mark_rvalue_use (t);
8574 123 : if (!processing_template_decl)
8575 : {
8576 123 : t = maybe_constant_value (t);
8577 123 : if (TREE_CODE (t) == INTEGER_CST
8578 109 : && tree_int_cst_sgn (t) != 1
8579 176 : && t != integer_minus_one_node)
8580 : {
8581 0 : warning_at (OMP_CLAUSE_LOCATION (c), 0,
8582 : "%<gang%> static value must be "
8583 : "positive");
8584 0 : t = integer_one_node;
8585 : }
8586 123 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8587 : }
8588 : }
8589 129 : OMP_CLAUSE_OPERAND (c, 1) = t;
8590 : }
8591 : /* Check operand 0, the num argument. */
8592 : /* FALLTHRU */
8593 :
8594 3480 : case OMP_CLAUSE_WORKER:
8595 3480 : case OMP_CLAUSE_VECTOR:
8596 3480 : if (OMP_CLAUSE_OPERAND (c, 0) == NULL_TREE)
8597 : break;
8598 : /* FALLTHRU */
8599 :
8600 484 : case OMP_CLAUSE_NUM_TASKS:
8601 484 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_NUM_TASKS)
8602 136 : num_tasks_seen = true;
8603 : /* FALLTHRU */
8604 :
8605 3034 : case OMP_CLAUSE_NUM_TEAMS:
8606 3034 : case OMP_CLAUSE_NUM_THREADS:
8607 3034 : case OMP_CLAUSE_NUM_GANGS:
8608 3034 : case OMP_CLAUSE_NUM_WORKERS:
8609 3034 : case OMP_CLAUSE_DYN_GROUPPRIVATE:
8610 3034 : case OMP_CLAUSE_VECTOR_LENGTH:
8611 3034 : t = OMP_CLAUSE_OPERAND (c, 0);
8612 3034 : if (t == error_mark_node)
8613 : remove = true;
8614 3034 : else if (!type_dependent_expression_p (t)
8615 3034 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8616 : {
8617 99 : switch (OMP_CLAUSE_CODE (c))
8618 : {
8619 12 : case OMP_CLAUSE_GANG:
8620 12 : error_at (OMP_CLAUSE_LOCATION (c),
8621 12 : "%<gang%> num expression must be integral"); break;
8622 12 : case OMP_CLAUSE_VECTOR:
8623 12 : error_at (OMP_CLAUSE_LOCATION (c),
8624 : "%<vector%> length expression must be integral");
8625 12 : break;
8626 12 : case OMP_CLAUSE_WORKER:
8627 12 : error_at (OMP_CLAUSE_LOCATION (c),
8628 : "%<worker%> num expression must be integral");
8629 12 : break;
8630 63 : default:
8631 63 : error_at (OMP_CLAUSE_LOCATION (c),
8632 : "%qs expression must be integral",
8633 63 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
8634 : }
8635 : remove = true;
8636 : }
8637 : else
8638 : {
8639 2935 : t = mark_rvalue_use (t);
8640 2935 : if (!processing_template_decl)
8641 : {
8642 2687 : t = maybe_constant_value (t);
8643 2687 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_DYN_GROUPPRIVATE
8644 2652 : && TREE_CODE (t) == INTEGER_CST
8645 4142 : && tree_int_cst_sgn (t) != 1)
8646 : {
8647 85 : switch (OMP_CLAUSE_CODE (c))
8648 : {
8649 3 : case OMP_CLAUSE_GANG:
8650 3 : warning_at (OMP_CLAUSE_LOCATION (c), 0,
8651 : "%<gang%> num value must be positive");
8652 3 : break;
8653 0 : case OMP_CLAUSE_VECTOR:
8654 0 : warning_at (OMP_CLAUSE_LOCATION (c), 0,
8655 : "%<vector%> length value must be "
8656 : "positive");
8657 0 : break;
8658 0 : case OMP_CLAUSE_WORKER:
8659 0 : warning_at (OMP_CLAUSE_LOCATION (c), 0,
8660 : "%<worker%> num value must be "
8661 : "positive");
8662 0 : break;
8663 82 : default:
8664 82 : warning_at (OMP_CLAUSE_LOCATION (c),
8665 46 : (flag_openmp || flag_openmp_simd)
8666 82 : ? OPT_Wopenmp : 0,
8667 : "%qs value must be positive",
8668 : omp_clause_code_name
8669 82 : [OMP_CLAUSE_CODE (c)]);
8670 : }
8671 85 : t = integer_one_node;
8672 : }
8673 2602 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DYN_GROUPPRIVATE
8674 35 : && TREE_CODE (t) == INTEGER_CST
8675 2625 : && tree_int_cst_sgn (t) < 0)
8676 : {
8677 8 : warning_at (OMP_CLAUSE_LOCATION (c), OPT_Wopenmp,
8678 : "%<dyn_groupprivate%> value must be "
8679 : "non-negative");
8680 8 : t = integer_zero_node;
8681 : }
8682 2687 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8683 : }
8684 2935 : OMP_CLAUSE_OPERAND (c, 0) = t;
8685 : }
8686 3034 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_NUM_TEAMS
8687 752 : && OMP_CLAUSE_NUM_TEAMS_LOWER_EXPR (c)
8688 3313 : && !remove)
8689 : {
8690 279 : t = OMP_CLAUSE_NUM_TEAMS_LOWER_EXPR (c);
8691 279 : if (t == error_mark_node)
8692 : remove = true;
8693 279 : else if (!type_dependent_expression_p (t)
8694 279 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8695 : {
8696 0 : error_at (OMP_CLAUSE_LOCATION (c),
8697 : "%qs expression must be integral",
8698 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
8699 0 : remove = true;
8700 : }
8701 : else
8702 : {
8703 279 : t = mark_rvalue_use (t);
8704 279 : if (!processing_template_decl)
8705 : {
8706 213 : t = maybe_constant_value (t);
8707 213 : if (TREE_CODE (t) == INTEGER_CST
8708 213 : && tree_int_cst_sgn (t) != 1)
8709 : {
8710 18 : warning_at (OMP_CLAUSE_LOCATION (c), OPT_Wopenmp,
8711 : "%qs value must be positive",
8712 : omp_clause_code_name
8713 18 : [OMP_CLAUSE_CODE (c)]);
8714 18 : t = NULL_TREE;
8715 : }
8716 : else
8717 195 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8718 213 : tree upper = OMP_CLAUSE_NUM_TEAMS_UPPER_EXPR (c);
8719 213 : if (t
8720 195 : && TREE_CODE (t) == INTEGER_CST
8721 43 : && TREE_CODE (upper) == INTEGER_CST
8722 250 : && tree_int_cst_lt (upper, t))
8723 : {
8724 18 : warning_at (OMP_CLAUSE_LOCATION (c), OPT_Wopenmp,
8725 : "%<num_teams%> lower bound %qE bigger "
8726 : "than upper bound %qE", t, upper);
8727 18 : t = NULL_TREE;
8728 : }
8729 : }
8730 279 : OMP_CLAUSE_NUM_TEAMS_LOWER_EXPR (c) = t;
8731 : }
8732 : }
8733 : break;
8734 :
8735 3892 : case OMP_CLAUSE_SCHEDULE:
8736 3892 : t = OMP_CLAUSE_SCHEDULE_CHUNK_EXPR (c);
8737 3892 : if (t == NULL)
8738 : ;
8739 2093 : else if (t == error_mark_node)
8740 : remove = true;
8741 2093 : else if (!type_dependent_expression_p (t)
8742 2093 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8743 : {
8744 9 : error_at (OMP_CLAUSE_LOCATION (c),
8745 : "schedule chunk size expression must be integral");
8746 9 : remove = true;
8747 : }
8748 : else
8749 : {
8750 2084 : t = mark_rvalue_use (t);
8751 2084 : if (!processing_template_decl)
8752 : {
8753 2044 : t = maybe_constant_value (t);
8754 2044 : if (TREE_CODE (t) == INTEGER_CST
8755 2044 : && tree_int_cst_sgn (t) != 1)
8756 : {
8757 6 : warning_at (OMP_CLAUSE_LOCATION (c), OPT_Wopenmp,
8758 : "chunk size value must be positive");
8759 6 : t = integer_one_node;
8760 : }
8761 2044 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8762 : }
8763 2084 : OMP_CLAUSE_SCHEDULE_CHUNK_EXPR (c) = t;
8764 : }
8765 2093 : if (!remove)
8766 : schedule_seen = true;
8767 : break;
8768 :
8769 894 : case OMP_CLAUSE_SIMDLEN:
8770 894 : t = OMP_CLAUSE_SIMDLEN_TYPE (c);
8771 894 : if (t == error_mark_node)
8772 : remove = true;
8773 75 : else if (t && !dependent_type_p (t)
8774 942 : && !ARITHMETIC_TYPE_P (t))
8775 : {
8776 3 : error_at (OMP_CLAUSE_LOCATION (c),
8777 : "expected arithmetic type name as argument to the "
8778 : "%<scaled%> modifier");
8779 3 : remove = true;
8780 : }
8781 894 : t = OMP_CLAUSE_SIMDLEN_DIVISOR (c);
8782 894 : if (t == error_mark_node)
8783 : remove = true;
8784 54 : else if (t && !type_dependent_expression_p (t)
8785 947 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8786 : {
8787 0 : error_at (OMP_CLAUSE_LOCATION (c),
8788 : "%qs divisor expression of the %<scaled%> modifier "
8789 : "must be integral",
8790 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
8791 0 : remove = true;
8792 : }
8793 893 : else if (t)
8794 : {
8795 54 : t = mark_rvalue_use (t);
8796 54 : if (!processing_template_decl)
8797 : {
8798 40 : t = maybe_constant_value (t);
8799 40 : if (TREE_CODE (t) != INTEGER_CST
8800 40 : || tree_int_cst_sgn (t) != 1)
8801 : {
8802 16 : error_at (OMP_CLAUSE_LOCATION (c),
8803 : "%qs divisor expression of the %<scaled%> "
8804 : "modifier must be a positive constant integer "
8805 : "expression",
8806 8 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
8807 8 : remove = true;
8808 : }
8809 : }
8810 54 : OMP_CLAUSE_SIMDLEN_DIVISOR (c) = t;
8811 : }
8812 : /* FALLTHRU */
8813 1364 : case OMP_CLAUSE_SAFELEN:
8814 1364 : t = OMP_CLAUSE_OPERAND (c, 0);
8815 1364 : if (t == error_mark_node)
8816 : remove = true;
8817 1358 : else if (!type_dependent_expression_p (t)
8818 1358 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8819 : {
8820 0 : error_at (OMP_CLAUSE_LOCATION (c),
8821 : "%qs length expression must be integral",
8822 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
8823 0 : remove = true;
8824 : }
8825 : else
8826 : {
8827 1358 : t = mark_rvalue_use (t);
8828 1358 : if (!processing_template_decl)
8829 : {
8830 1291 : t = maybe_constant_value (t);
8831 1291 : if (TREE_CODE (t) != INTEGER_CST
8832 1291 : || tree_int_cst_sgn (t) != 1)
8833 : {
8834 0 : error_at (OMP_CLAUSE_LOCATION (c),
8835 : "%qs length expression must be positive "
8836 : "constant integer expression",
8837 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
8838 0 : remove = true;
8839 : }
8840 : }
8841 1358 : OMP_CLAUSE_OPERAND (c, 0) = t;
8842 1358 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SAFELEN)
8843 470 : safelen = c;
8844 : }
8845 : break;
8846 :
8847 388 : case OMP_CLAUSE_ASYNC:
8848 388 : t = OMP_CLAUSE_ASYNC_EXPR (c);
8849 388 : if (t == error_mark_node)
8850 : remove = true;
8851 373 : else if (!type_dependent_expression_p (t)
8852 373 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8853 : {
8854 12 : error_at (OMP_CLAUSE_LOCATION (c),
8855 : "%<async%> expression must be integral");
8856 12 : remove = true;
8857 : }
8858 : else
8859 : {
8860 361 : t = mark_rvalue_use (t);
8861 361 : if (!processing_template_decl)
8862 352 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8863 361 : OMP_CLAUSE_ASYNC_EXPR (c) = t;
8864 : }
8865 : break;
8866 :
8867 204 : case OMP_CLAUSE_WAIT:
8868 204 : t = OMP_CLAUSE_WAIT_EXPR (c);
8869 204 : if (t == error_mark_node)
8870 : remove = true;
8871 204 : else if (!processing_template_decl)
8872 196 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8873 204 : OMP_CLAUSE_WAIT_EXPR (c) = t;
8874 204 : break;
8875 :
8876 637 : case OMP_CLAUSE_THREAD_LIMIT:
8877 637 : t = OMP_CLAUSE_THREAD_LIMIT_EXPR (c);
8878 637 : if (t == error_mark_node)
8879 : remove = true;
8880 637 : else if (!type_dependent_expression_p (t)
8881 637 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8882 : {
8883 0 : error_at (OMP_CLAUSE_LOCATION (c),
8884 : "%<thread_limit%> expression must be integral");
8885 0 : remove = true;
8886 : }
8887 : else
8888 : {
8889 637 : t = mark_rvalue_use (t);
8890 637 : if (!processing_template_decl)
8891 : {
8892 583 : t = maybe_constant_value (t);
8893 583 : if (TREE_CODE (t) == INTEGER_CST
8894 583 : && tree_int_cst_sgn (t) != 1)
8895 : {
8896 0 : warning_at (OMP_CLAUSE_LOCATION (c), OPT_Wopenmp,
8897 : "%<thread_limit%> value must be positive");
8898 0 : t = integer_one_node;
8899 : }
8900 583 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8901 : }
8902 637 : OMP_CLAUSE_THREAD_LIMIT_EXPR (c) = t;
8903 : }
8904 : break;
8905 :
8906 771 : case OMP_CLAUSE_DEVICE:
8907 771 : t = OMP_CLAUSE_DEVICE_ID (c);
8908 771 : if (t == error_mark_node)
8909 : remove = true;
8910 771 : else if (!type_dependent_expression_p (t)
8911 771 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8912 : {
8913 6 : error_at (OMP_CLAUSE_LOCATION (c),
8914 : "%<device%> id must be integral");
8915 6 : remove = true;
8916 : }
8917 765 : else if (OMP_CLAUSE_DEVICE_ANCESTOR (c)
8918 66 : && TREE_CODE (t) == INTEGER_CST
8919 825 : && !integer_onep (t))
8920 : {
8921 3 : error_at (OMP_CLAUSE_LOCATION (c),
8922 : "the %<device%> clause expression must evaluate to "
8923 : "%<1%>");
8924 3 : remove = true;
8925 : }
8926 : else
8927 : {
8928 762 : t = mark_rvalue_use (t);
8929 762 : if (!processing_template_decl)
8930 751 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8931 762 : OMP_CLAUSE_DEVICE_ID (c) = t;
8932 : }
8933 : break;
8934 :
8935 1848 : case OMP_CLAUSE_DIST_SCHEDULE:
8936 1848 : t = OMP_CLAUSE_DIST_SCHEDULE_CHUNK_EXPR (c);
8937 1848 : if (t == NULL)
8938 : ;
8939 1827 : else if (t == error_mark_node)
8940 : remove = true;
8941 1827 : else if (!type_dependent_expression_p (t)
8942 1827 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
8943 : {
8944 0 : error_at (OMP_CLAUSE_LOCATION (c),
8945 : "%<dist_schedule%> chunk size expression must be "
8946 : "integral");
8947 0 : remove = true;
8948 : }
8949 : else
8950 : {
8951 1827 : t = mark_rvalue_use (t);
8952 1827 : if (!processing_template_decl)
8953 1827 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
8954 1827 : OMP_CLAUSE_DIST_SCHEDULE_CHUNK_EXPR (c) = t;
8955 : }
8956 : break;
8957 :
8958 807 : case OMP_CLAUSE_ALIGNED:
8959 807 : t = OMP_CLAUSE_DECL (c);
8960 807 : if (t == current_class_ptr && ort != C_ORT_OMP_DECLARE_SIMD)
8961 : {
8962 0 : error_at (OMP_CLAUSE_LOCATION (c),
8963 : "%<this%> allowed in OpenMP only in %<declare simd%>"
8964 : " clauses");
8965 0 : remove = true;
8966 0 : break;
8967 : }
8968 807 : if (!VAR_P (t) && TREE_CODE (t) != PARM_DECL)
8969 : {
8970 0 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
8971 : break;
8972 0 : if (DECL_P (t))
8973 0 : error_at (OMP_CLAUSE_LOCATION (c),
8974 : "%qD is not a variable in %<aligned%> clause", t);
8975 : else
8976 0 : error_at (OMP_CLAUSE_LOCATION (c),
8977 : "%qE is not a variable in %<aligned%> clause", t);
8978 : remove = true;
8979 : }
8980 807 : else if (!type_dependent_expression_p (t)
8981 789 : && !TYPE_PTR_P (TREE_TYPE (t))
8982 111 : && TREE_CODE (TREE_TYPE (t)) != ARRAY_TYPE
8983 864 : && (!TYPE_REF_P (TREE_TYPE (t))
8984 39 : || (!INDIRECT_TYPE_P (TREE_TYPE (TREE_TYPE (t)))
8985 30 : && (TREE_CODE (TREE_TYPE (TREE_TYPE (t)))
8986 : != ARRAY_TYPE))))
8987 : {
8988 33 : error_at (OMP_CLAUSE_LOCATION (c),
8989 : "%qE in %<aligned%> clause is neither a pointer nor "
8990 : "an array nor a reference to pointer or array", t);
8991 33 : remove = true;
8992 : }
8993 774 : else if (bitmap_bit_p (&aligned_head, DECL_UID (t)))
8994 : {
8995 0 : error_at (OMP_CLAUSE_LOCATION (c),
8996 : "%qD appears more than once in %<aligned%> clauses",
8997 : t);
8998 0 : remove = true;
8999 : }
9000 : else
9001 774 : bitmap_set_bit (&aligned_head, DECL_UID (t));
9002 807 : t = OMP_CLAUSE_ALIGNED_ALIGNMENT (c);
9003 807 : if (t == error_mark_node)
9004 : remove = true;
9005 807 : else if (t == NULL_TREE)
9006 : break;
9007 744 : else if (!type_dependent_expression_p (t)
9008 744 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
9009 : {
9010 0 : error_at (OMP_CLAUSE_LOCATION (c),
9011 : "%<aligned%> clause alignment expression must "
9012 : "be integral");
9013 0 : remove = true;
9014 : }
9015 : else
9016 : {
9017 744 : t = mark_rvalue_use (t);
9018 744 : if (!processing_template_decl)
9019 : {
9020 690 : t = maybe_constant_value (t);
9021 690 : if (TREE_CODE (t) != INTEGER_CST
9022 690 : || tree_int_cst_sgn (t) != 1)
9023 : {
9024 0 : error_at (OMP_CLAUSE_LOCATION (c),
9025 : "%<aligned%> clause alignment expression must "
9026 : "be positive constant integer expression");
9027 0 : remove = true;
9028 : }
9029 : }
9030 744 : OMP_CLAUSE_ALIGNED_ALIGNMENT (c) = t;
9031 : }
9032 : break;
9033 :
9034 369 : case OMP_CLAUSE_NONTEMPORAL:
9035 369 : t = OMP_CLAUSE_DECL (c);
9036 369 : if (!VAR_P (t) && TREE_CODE (t) != PARM_DECL)
9037 : {
9038 0 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
9039 : break;
9040 0 : if (DECL_P (t))
9041 0 : error_at (OMP_CLAUSE_LOCATION (c),
9042 : "%qD is not a variable in %<nontemporal%> clause",
9043 : t);
9044 : else
9045 0 : error_at (OMP_CLAUSE_LOCATION (c),
9046 : "%qE is not a variable in %<nontemporal%> clause",
9047 : t);
9048 : remove = true;
9049 : }
9050 369 : else if (bitmap_bit_p (&oacc_reduction_head, DECL_UID (t)))
9051 : {
9052 6 : error_at (OMP_CLAUSE_LOCATION (c),
9053 : "%qD appears more than once in %<nontemporal%> "
9054 : "clauses", t);
9055 6 : remove = true;
9056 : }
9057 : else
9058 363 : bitmap_set_bit (&oacc_reduction_head, DECL_UID (t));
9059 : break;
9060 :
9061 2809 : case OMP_CLAUSE_ALLOCATE:
9062 2809 : t = omp_clause_decl_field (OMP_CLAUSE_DECL (c));
9063 2809 : if (t)
9064 14 : omp_note_field_privatization (t, OMP_CLAUSE_DECL (c));
9065 : else
9066 2795 : t = OMP_CLAUSE_DECL (c);
9067 2809 : if (t == current_class_ptr)
9068 : {
9069 0 : error_at (OMP_CLAUSE_LOCATION (c),
9070 : "%<this%> not allowed in %<allocate%> clause");
9071 0 : remove = true;
9072 0 : break;
9073 : }
9074 2809 : if (!VAR_P (t)
9075 678 : && TREE_CODE (t) != PARM_DECL
9076 45 : && TREE_CODE (t) != FIELD_DECL)
9077 : {
9078 3 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
9079 : break;
9080 3 : if (DECL_P (t))
9081 3 : error_at (OMP_CLAUSE_LOCATION (c),
9082 : "%qD is not a variable in %<allocate%> clause", t);
9083 : else
9084 0 : error_at (OMP_CLAUSE_LOCATION (c),
9085 : "%qE is not a variable in %<allocate%> clause", t);
9086 : remove = true;
9087 : }
9088 2806 : else if (bitmap_bit_p (&aligned_head, DECL_UID (t)))
9089 : {
9090 12 : warning_at (OMP_CLAUSE_LOCATION (c), OPT_Wopenmp,
9091 : "%qD appears more than once in %<allocate%> clauses",
9092 : t);
9093 12 : remove = true;
9094 : }
9095 : else
9096 : {
9097 2794 : bitmap_set_bit (&aligned_head, DECL_UID (t));
9098 2794 : allocate_seen = true;
9099 : }
9100 2809 : tree allocator, align;
9101 2809 : align = OMP_CLAUSE_ALLOCATE_ALIGN (c);
9102 2809 : if (error_operand_p (align))
9103 : {
9104 : remove = true;
9105 : break;
9106 : }
9107 2809 : if (align)
9108 : {
9109 211 : if (!type_dependent_expression_p (align)
9110 211 : && !INTEGRAL_TYPE_P (TREE_TYPE (align)))
9111 : {
9112 4 : error_at (OMP_CLAUSE_LOCATION (c),
9113 : "%<allocate%> clause %<align%> modifier "
9114 : "argument needs to be positive constant "
9115 : "power of two integer expression");
9116 4 : remove = true;
9117 : }
9118 : else
9119 : {
9120 207 : align = mark_rvalue_use (align);
9121 207 : if (!processing_template_decl)
9122 : {
9123 192 : align = maybe_constant_value (align);
9124 192 : if (TREE_CODE (align) != INTEGER_CST
9125 189 : || !tree_fits_uhwi_p (align)
9126 381 : || !integer_pow2p (align))
9127 : {
9128 10 : error_at (OMP_CLAUSE_LOCATION (c),
9129 : "%<allocate%> clause %<align%> modifier "
9130 : "argument needs to be positive constant "
9131 : "power of two integer expression");
9132 10 : remove = true;
9133 : }
9134 : }
9135 : }
9136 211 : OMP_CLAUSE_ALLOCATE_ALIGN (c) = align;
9137 : }
9138 2809 : allocator = OMP_CLAUSE_ALLOCATE_ALLOCATOR (c);
9139 2809 : if (error_operand_p (allocator))
9140 : {
9141 : remove = true;
9142 : break;
9143 : }
9144 2809 : if (allocator == NULL_TREE)
9145 1751 : goto handle_field_decl;
9146 1058 : tree allocatort;
9147 1058 : allocatort = TYPE_MAIN_VARIANT (TREE_TYPE (allocator));
9148 1058 : if (!type_dependent_expression_p (allocator)
9149 1058 : && (TREE_CODE (allocatort) != ENUMERAL_TYPE
9150 1039 : || TYPE_NAME (allocatort) == NULL_TREE
9151 1039 : || TREE_CODE (TYPE_NAME (allocatort)) != TYPE_DECL
9152 2078 : || (DECL_NAME (TYPE_NAME (allocatort))
9153 1039 : != get_identifier ("omp_allocator_handle_t"))
9154 1039 : || (TYPE_CONTEXT (allocatort)
9155 1039 : != DECL_CONTEXT (global_namespace))))
9156 : {
9157 16 : error_at (OMP_CLAUSE_LOCATION (c),
9158 : "%<allocate%> clause allocator expression has "
9159 : "type %qT rather than %<omp_allocator_handle_t%>",
9160 16 : TREE_TYPE (allocator));
9161 16 : remove = true;
9162 16 : break;
9163 : }
9164 : else
9165 : {
9166 1042 : allocator = mark_rvalue_use (allocator);
9167 1042 : if (!processing_template_decl)
9168 1023 : allocator = maybe_constant_value (allocator);
9169 1042 : OMP_CLAUSE_ALLOCATE_ALLOCATOR (c) = allocator;
9170 : }
9171 1042 : goto handle_field_decl;
9172 :
9173 654 : case OMP_CLAUSE_DOACROSS:
9174 654 : t = OMP_CLAUSE_DECL (c);
9175 654 : if (t == NULL_TREE)
9176 : break;
9177 298 : if (OMP_CLAUSE_DOACROSS_KIND (c) == OMP_CLAUSE_DOACROSS_SINK)
9178 : {
9179 298 : if (cp_finish_omp_clause_doacross_sink (c))
9180 98622 : remove = true;
9181 : break;
9182 : }
9183 0 : gcc_unreachable ();
9184 89 : case OMP_CLAUSE_USES_ALLOCATORS:
9185 89 : t = OMP_CLAUSE_USES_ALLOCATORS_ALLOCATOR (c);
9186 89 : t = convert_from_reference (t);
9187 89 : if (t == error_mark_node)
9188 : {
9189 : remove = true;
9190 : break;
9191 : }
9192 82 : if (DECL_P (t)
9193 82 : && (bitmap_bit_p (&generic_head, DECL_UID (t))
9194 79 : || bitmap_bit_p (&firstprivate_head, DECL_UID (t))
9195 78 : || bitmap_bit_p (&map_firstprivate_head, DECL_UID (t))))
9196 : {
9197 1 : error_at (OMP_CLAUSE_LOCATION (c),
9198 : "%qE appears more than once in data clauses", t);
9199 1 : remove = true;
9200 : }
9201 81 : else if (DECL_P (t))
9202 78 : bitmap_set_bit (&generic_head, DECL_UID (t));
9203 82 : if (type_dependent_expression_p (t))
9204 : break;
9205 77 : if (TREE_CODE (t) == FIELD_DECL)
9206 : {
9207 0 : sorry_at (OMP_CLAUSE_LOCATION (c), "class member %qE not yet "
9208 : "supported in %<uses_allocators%> clause", t);
9209 0 : remove = true;
9210 0 : break;
9211 : }
9212 77 : if (TREE_CODE (TREE_TYPE (t)) != ENUMERAL_TYPE
9213 151 : || strcmp (IDENTIFIER_POINTER (TYPE_IDENTIFIER (TREE_TYPE (t))),
9214 : "omp_allocator_handle_t") != 0)
9215 : {
9216 3 : error_at (OMP_CLAUSE_LOCATION (c),
9217 : "allocator %qE must be of %<omp_allocator_handle_t%> "
9218 : "type", t);
9219 3 : remove = true;
9220 3 : break;
9221 : }
9222 74 : tree init;
9223 74 : if (TREE_CODE (t) == CONST_DECL)
9224 7 : init = DECL_INITIAL(t);
9225 : else
9226 : init = t;
9227 74 : if (!DECL_P (t)
9228 74 : && (init == NULL_TREE
9229 3 : || TREE_CODE (init) != INTEGER_CST
9230 3 : || ((wi::to_widest (init) < 0
9231 3 : || wi::to_widest (init) > GOMP_OMP_PREDEF_ALLOC_MAX)
9232 1 : && (wi::to_widest (init) < GOMP_OMPX_PREDEF_ALLOC_MIN
9233 1 : || (wi::to_widest (init)
9234 2 : > GOMP_OMPX_PREDEF_ALLOC_MAX)))))
9235 : {
9236 1 : remove = true;
9237 1 : error_at (OMP_CLAUSE_LOCATION (c),
9238 : "allocator %qE must be either a variable or a "
9239 : "predefined allocator", t);
9240 1 : break;
9241 : }
9242 73 : else if (TREE_CODE (t) == CONST_DECL)
9243 : {
9244 : /* omp_null_allocator is ignored and for predefined allocators,
9245 : not special handling is required; thus, remove them removed. */
9246 7 : remove = true;
9247 :
9248 7 : if (OMP_CLAUSE_USES_ALLOCATORS_MEMSPACE (c)
9249 7 : || OMP_CLAUSE_USES_ALLOCATORS_TRAITS (c))
9250 : {
9251 0 : error_at (OMP_CLAUSE_LOCATION (c),
9252 : "modifiers cannot be used with predefined "
9253 : "allocators");
9254 0 : break;
9255 : }
9256 : }
9257 73 : t = OMP_CLAUSE_USES_ALLOCATORS_MEMSPACE (c);
9258 73 : if (t == error_mark_node)
9259 : {
9260 : remove = true;
9261 : break;
9262 : }
9263 72 : if (t != NULL_TREE
9264 16 : && !type_dependent_expression_p (t)
9265 88 : && ((TREE_CODE (t) != CONST_DECL && TREE_CODE (t) != INTEGER_CST)
9266 15 : || TREE_CODE (TREE_TYPE (t)) != ENUMERAL_TYPE
9267 28 : || strcmp (IDENTIFIER_POINTER (TYPE_IDENTIFIER (TREE_TYPE (t))),
9268 : "omp_memspace_handle_t") != 0))
9269 : {
9270 2 : error_at (OMP_CLAUSE_LOCATION (c), "memspace modifier %qE must be"
9271 : " constant enum of %<omp_memspace_handle_t%> type", t);
9272 2 : remove = true;
9273 2 : break;
9274 : }
9275 70 : t = OMP_CLAUSE_USES_ALLOCATORS_TRAITS (c);
9276 70 : if (t == error_mark_node)
9277 : {
9278 : remove = true;
9279 : break;
9280 : }
9281 69 : if (type_dependent_expression_p (t))
9282 : break;
9283 69 : if (t != NULL_TREE
9284 41 : && t != error_mark_node
9285 41 : && !type_dependent_expression_p (t)
9286 110 : && (!DECL_P (t)
9287 41 : || DECL_EXTERNAL (t)
9288 39 : || TREE_CODE (t) == PARM_DECL))
9289 : {
9290 4 : error_at (OMP_CLAUSE_LOCATION (c), "traits array %qE must be "
9291 : "defined in same scope as the construct on which the "
9292 : "clause appears", t);
9293 4 : remove = true;
9294 : }
9295 69 : if (t != NULL_TREE)
9296 : {
9297 41 : bool type_err = false;
9298 :
9299 41 : if (TREE_CODE (TREE_TYPE (t)) != ARRAY_TYPE
9300 39 : || DECL_SIZE (t) == NULL_TREE
9301 79 : || !COMPLETE_TYPE_P (TREE_TYPE (t)))
9302 : type_err = true;
9303 : else
9304 : {
9305 38 : tree elem_t = TREE_TYPE (TREE_TYPE (t));
9306 38 : if (TREE_CODE (elem_t) != RECORD_TYPE
9307 76 : || strcmp (IDENTIFIER_POINTER (TYPE_IDENTIFIER (elem_t)),
9308 : "omp_alloctrait_t") != 0
9309 76 : || !TYPE_READONLY (elem_t))
9310 : type_err = true;
9311 : }
9312 37 : if (type_err)
9313 : {
9314 4 : error_at (OMP_CLAUSE_LOCATION (c), "traits array %qE must "
9315 : "be of %<const omp_alloctrait_t []%> type", t);
9316 4 : remove = true;
9317 : }
9318 37 : else if (TREE_CODE (array_type_nelts_top (TREE_TYPE (t)))
9319 : != INTEGER_CST)
9320 : {
9321 1 : error_at (OMP_CLAUSE_LOCATION (c), "variable length traits "
9322 : "arrays are not supported");
9323 1 : remove = true;
9324 : }
9325 : else
9326 : {
9327 36 : tree cst_val = decl_constant_value (t);
9328 36 : if (cst_val == t)
9329 : {
9330 1 : error_at (OMP_CLAUSE_LOCATION (c), "traits array must be "
9331 : "initialized with constants");
9332 1 : remove = true;
9333 : }
9334 : }
9335 : }
9336 69 : if (remove)
9337 : break;
9338 55 : pc = &OMP_CLAUSE_CHAIN (c);
9339 55 : continue;
9340 1807 : case OMP_CLAUSE_DEPEND:
9341 1807 : depend_clause = c;
9342 : /* FALLTHRU */
9343 2416 : case OMP_CLAUSE_AFFINITY:
9344 2416 : t = OMP_CLAUSE_DECL (c);
9345 2416 : if (OMP_ITERATOR_DECL_P (t))
9346 : {
9347 623 : if (TREE_PURPOSE (t) != last_iterators)
9348 525 : last_iterators_remove
9349 525 : = cp_omp_finish_iterators (TREE_PURPOSE (t));
9350 623 : last_iterators = TREE_PURPOSE (t);
9351 623 : t = TREE_VALUE (t);
9352 623 : if (last_iterators_remove)
9353 144 : t = error_mark_node;
9354 : }
9355 : else
9356 : last_iterators = NULL_TREE;
9357 :
9358 2416 : if (TREE_CODE (t) == OMP_ARRAY_SECTION)
9359 : {
9360 1368 : if (handle_omp_array_sections (c, ort))
9361 : remove = true;
9362 1014 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
9363 1014 : && (OMP_CLAUSE_DEPEND_KIND (c)
9364 : == OMP_CLAUSE_DEPEND_DEPOBJ))
9365 : {
9366 6 : error_at (OMP_CLAUSE_LOCATION (c),
9367 : "%<depend%> clause with %<depobj%> dependence "
9368 : "type on array section");
9369 6 : remove = true;
9370 : }
9371 : break;
9372 : }
9373 1048 : if (t == error_mark_node)
9374 : remove = true;
9375 886 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
9376 886 : && t == ridpointers[RID_OMP_ALL_MEMORY])
9377 : {
9378 33 : if (OMP_CLAUSE_DEPEND_KIND (c) != OMP_CLAUSE_DEPEND_OUT
9379 33 : && OMP_CLAUSE_DEPEND_KIND (c) != OMP_CLAUSE_DEPEND_INOUT)
9380 : {
9381 9 : error_at (OMP_CLAUSE_LOCATION (c),
9382 : "%<omp_all_memory%> used with %<depend%> kind "
9383 : "other than %<out%> or %<inout%>");
9384 9 : remove = true;
9385 : }
9386 33 : if (processing_template_decl)
9387 : break;
9388 : }
9389 853 : else if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
9390 : break;
9391 661 : else if (!lvalue_p (t))
9392 : {
9393 21 : if (DECL_P (t))
9394 24 : error_at (OMP_CLAUSE_LOCATION (c),
9395 : "%qD is not lvalue expression nor array section "
9396 : "in %qs clause", t,
9397 12 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
9398 : else
9399 18 : error_at (OMP_CLAUSE_LOCATION (c),
9400 : "%qE is not lvalue expression nor array section "
9401 : "in %qs clause", t,
9402 9 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
9403 : remove = true;
9404 : }
9405 640 : else if (TREE_CODE (t) == COMPONENT_REF
9406 36 : && TREE_CODE (TREE_OPERAND (t, 1)) == FIELD_DECL
9407 676 : && DECL_BIT_FIELD (TREE_OPERAND (t, 1)))
9408 : {
9409 12 : error_at (OMP_CLAUSE_LOCATION (c),
9410 : "bit-field %qE in %qs clause", t,
9411 6 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
9412 6 : remove = true;
9413 : }
9414 634 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
9415 634 : && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_DEPOBJ)
9416 : {
9417 130 : if (!c_omp_depend_t_p (TYPE_REF_P (TREE_TYPE (t))
9418 8 : ? TREE_TYPE (TREE_TYPE (t))
9419 57 : : TREE_TYPE (t)))
9420 : {
9421 12 : error_at (OMP_CLAUSE_LOCATION (c),
9422 : "%qE does not have %<omp_depend_t%> type in "
9423 : "%<depend%> clause with %<depobj%> dependence "
9424 : "type", t);
9425 12 : remove = true;
9426 : }
9427 : }
9428 569 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
9429 1010 : && c_omp_depend_t_p (TYPE_REF_P (TREE_TYPE (t))
9430 4 : ? TREE_TYPE (TREE_TYPE (t))
9431 437 : : TREE_TYPE (t)))
9432 : {
9433 15 : error_at (OMP_CLAUSE_LOCATION (c),
9434 : "%qE should not have %<omp_depend_t%> type in "
9435 : "%<depend%> clause with dependence type other than "
9436 : "%<depobj%>", t);
9437 15 : remove = true;
9438 : }
9439 87 : if (!remove)
9440 : {
9441 631 : if (t == ridpointers[RID_OMP_ALL_MEMORY])
9442 24 : t = null_pointer_node;
9443 : else
9444 : {
9445 607 : tree addr = cp_build_addr_expr (t, tf_warning_or_error);
9446 607 : if (addr == error_mark_node)
9447 : {
9448 : remove = true;
9449 : break;
9450 : }
9451 607 : t = cp_build_indirect_ref (OMP_CLAUSE_LOCATION (c),
9452 : addr, RO_UNARY_STAR,
9453 : tf_warning_or_error);
9454 607 : if (t == error_mark_node)
9455 : {
9456 : remove = true;
9457 : break;
9458 : }
9459 : }
9460 631 : if (TREE_CODE (OMP_CLAUSE_DECL (c)) == TREE_LIST
9461 137 : && TREE_PURPOSE (OMP_CLAUSE_DECL (c))
9462 768 : && (TREE_CODE (TREE_PURPOSE (OMP_CLAUSE_DECL (c)))
9463 : == TREE_VEC))
9464 137 : TREE_VALUE (OMP_CLAUSE_DECL (c)) = t;
9465 : else
9466 494 : OMP_CLAUSE_DECL (c) = t;
9467 : }
9468 : break;
9469 69 : case OMP_CLAUSE_DETACH:
9470 69 : t = OMP_CLAUSE_DECL (c);
9471 69 : if (detach_seen)
9472 : {
9473 3 : error_at (OMP_CLAUSE_LOCATION (c),
9474 : "too many %qs clauses on a task construct",
9475 : "detach");
9476 3 : remove = true;
9477 3 : break;
9478 : }
9479 66 : else if (error_operand_p (t))
9480 : {
9481 : remove = true;
9482 : break;
9483 : }
9484 : else
9485 : {
9486 63 : tree type = TYPE_MAIN_VARIANT (TREE_TYPE (t));
9487 63 : if (!type_dependent_expression_p (t)
9488 63 : && (!INTEGRAL_TYPE_P (type)
9489 : || TREE_CODE (type) != ENUMERAL_TYPE
9490 51 : || TYPE_NAME (type) == NULL_TREE
9491 102 : || (DECL_NAME (TYPE_NAME (type))
9492 51 : != get_identifier ("omp_event_handle_t"))))
9493 : {
9494 6 : error_at (OMP_CLAUSE_LOCATION (c),
9495 : "%<detach%> clause event handle "
9496 : "has type %qT rather than "
9497 : "%<omp_event_handle_t%>",
9498 : type);
9499 6 : remove = true;
9500 : }
9501 63 : detach_seen = c;
9502 63 : cxx_mark_addressable (t);
9503 : }
9504 63 : break;
9505 :
9506 16363 : case OMP_CLAUSE_MAP:
9507 16363 : if (OMP_CLAUSE_MAP_IMPLICIT (c) && !implicit_moved)
9508 157 : goto move_implicit;
9509 16206 : if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_PUSH_MAPPER_NAME
9510 16206 : || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_POP_MAPPER_NAME)
9511 : {
9512 : remove = true;
9513 : break;
9514 : }
9515 : /* FALLTHRU */
9516 19393 : case OMP_CLAUSE_TO:
9517 19393 : case OMP_CLAUSE_FROM:
9518 19393 : if (OMP_CLAUSE_ITERATORS (c)
9519 19393 : && cp_omp_finish_iterators (OMP_CLAUSE_ITERATORS (c)))
9520 : {
9521 98622 : t = error_mark_node;
9522 : break;
9523 : }
9524 : /* FALLTHRU */
9525 20281 : case OMP_CLAUSE__CACHE_:
9526 20281 : {
9527 20281 : using namespace omp_addr_tokenizer;
9528 20281 : auto_vec<omp_addr_token *, 10> addr_tokens;
9529 :
9530 20281 : t = OMP_CLAUSE_DECL (c);
9531 20281 : if (TREE_CODE (t) == OMP_ARRAY_SECTION)
9532 : {
9533 6007 : grp_start_p = pc;
9534 6007 : grp_sentinel = OMP_CLAUSE_CHAIN (c);
9535 :
9536 6007 : if (handle_omp_array_sections (c, ort))
9537 : remove = true;
9538 : else
9539 : {
9540 5197 : t = OMP_CLAUSE_DECL (c);
9541 5197 : if (TREE_CODE (t) != OMP_ARRAY_SECTION
9542 4336 : && !type_dependent_expression_p (t)
9543 9533 : && !omp_mappable_type (TREE_TYPE (t)))
9544 : {
9545 3 : auto_diagnostic_group d;
9546 6 : error_at (OMP_CLAUSE_LOCATION (c),
9547 : "array section does not have mappable type "
9548 : "in %qs clause",
9549 3 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
9550 3 : if (TREE_TYPE (t) != error_mark_node
9551 3 : && !COMPLETE_TYPE_P (TREE_TYPE (t)))
9552 3 : cxx_incomplete_type_inform (TREE_TYPE (t));
9553 3 : remove = true;
9554 3 : }
9555 7122 : while (TREE_CODE (t) == ARRAY_REF)
9556 1925 : t = TREE_OPERAND (t, 0);
9557 :
9558 5197 : if (type_dependent_expression_p (t))
9559 : break;
9560 :
9561 4723 : cp_omp_address_inspector ai (OMP_CLAUSE_LOCATION (c), t);
9562 :
9563 4723 : if (!ai.map_supported_p ()
9564 4723 : || !omp_parse_expr (addr_tokens, t))
9565 : {
9566 18 : sorry_at (OMP_CLAUSE_LOCATION (c),
9567 : "unsupported map expression %qE",
9568 9 : OMP_CLAUSE_DECL (c));
9569 9 : remove = true;
9570 9 : break;
9571 : }
9572 :
9573 : /* This check is to determine if this will be the only map
9574 : node created for this clause. Otherwise, we'll check
9575 : the following FIRSTPRIVATE_POINTER,
9576 : FIRSTPRIVATE_REFERENCE or ATTACH_DETACH node on the next
9577 : iteration(s) of the loop. */
9578 9379 : if (addr_tokens.length () >= 4
9579 1063 : && addr_tokens[0]->type == STRUCTURE_BASE
9580 1057 : && addr_tokens[0]->u.structure_base_kind == BASE_DECL
9581 1057 : && addr_tokens[1]->type == ACCESS_METHOD
9582 1057 : && addr_tokens[2]->type == COMPONENT_SELECTOR
9583 977 : && addr_tokens[3]->type == ACCESS_METHOD
9584 5428 : && (addr_tokens[3]->u.access_kind == ACCESS_DIRECT
9585 551 : || (addr_tokens[3]->u.access_kind
9586 : == ACCESS_INDEXED_ARRAY)))
9587 : {
9588 165 : tree rt = addr_tokens[1]->expr;
9589 :
9590 165 : gcc_assert (DECL_P (rt));
9591 :
9592 165 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9593 154 : && OMP_CLAUSE_MAP_IMPLICIT (c)
9594 165 : && (bitmap_bit_p (&map_head, DECL_UID (rt))
9595 0 : || bitmap_bit_p (&map_field_head, DECL_UID (rt))
9596 0 : || bitmap_bit_p (&map_firstprivate_head,
9597 0 : DECL_UID (rt))))
9598 : {
9599 : remove = true;
9600 : break;
9601 : }
9602 165 : if (bitmap_bit_p (&map_field_head, DECL_UID (rt)))
9603 : break;
9604 116 : if (bitmap_bit_p (&map_head, DECL_UID (rt)))
9605 : {
9606 0 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP)
9607 0 : error_at (OMP_CLAUSE_LOCATION (c),
9608 : "%qD appears more than once in motion"
9609 : " clauses", rt);
9610 0 : else if (openacc)
9611 0 : error_at (OMP_CLAUSE_LOCATION (c),
9612 : "%qD appears more than once in data"
9613 : " clauses", rt);
9614 : else
9615 0 : error_at (OMP_CLAUSE_LOCATION (c),
9616 : "%qD appears more than once in map"
9617 : " clauses", rt);
9618 : remove = true;
9619 : }
9620 : else
9621 : {
9622 116 : bitmap_set_bit (&map_head, DECL_UID (rt));
9623 116 : bitmap_set_bit (&map_field_head, DECL_UID (rt));
9624 : }
9625 : }
9626 4723 : }
9627 5475 : if (cp_oacc_check_attachments (c))
9628 12 : remove = true;
9629 5475 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9630 4485 : && (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH
9631 4421 : || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_DETACH)
9632 5573 : && !OMP_CLAUSE_SIZE (c))
9633 : /* In this case, we have a single array element which is a
9634 : pointer, and we already set OMP_CLAUSE_SIZE in
9635 : handle_omp_array_sections above. For attach/detach
9636 : clauses, reset the OMP_CLAUSE_SIZE (representing a bias)
9637 : to zero here. */
9638 60 : OMP_CLAUSE_SIZE (c) = size_zero_node;
9639 : break;
9640 : }
9641 14274 : else if (type_dependent_expression_p (t))
9642 : break;
9643 13491 : else if (!omp_parse_expr (addr_tokens, t))
9644 : {
9645 0 : sorry_at (OMP_CLAUSE_LOCATION (c),
9646 : "unsupported map expression %qE",
9647 0 : OMP_CLAUSE_DECL (c));
9648 0 : remove = true;
9649 0 : break;
9650 : }
9651 13491 : if (t == error_mark_node)
9652 : {
9653 : remove = true;
9654 : break;
9655 : }
9656 :
9657 13377 : tree attr;
9658 13377 : if (DECL_P (t)
9659 10691 : && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9660 7768 : && (attr = lookup_attribute ("omp declare target",
9661 7768 : DECL_ATTRIBUTES (t)))
9662 13909 : && value_member (get_identifier ("local"),
9663 532 : TREE_VALUE (attr)))
9664 : {
9665 0 : error_at (OMP_CLAUSE_LOCATION (c),
9666 : "device-local variable %qD cannot appear "
9667 : "in map clause", t);
9668 0 : remove = true;
9669 0 : break;
9670 : }
9671 :
9672 : /* OpenACC attach / detach clauses must be pointers. */
9673 13377 : if (cp_oacc_check_attachments (c))
9674 : {
9675 : remove = true;
9676 : break;
9677 : }
9678 13353 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9679 10308 : && (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH
9680 10259 : || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_DETACH)
9681 13427 : && !OMP_CLAUSE_SIZE (c))
9682 : /* For attach/detach clauses, set OMP_CLAUSE_SIZE (representing a
9683 : bias) to zero here, so it is not set erroneously to the
9684 : pointer size later on in gimplify.cc. */
9685 66 : OMP_CLAUSE_SIZE (c) = size_zero_node;
9686 :
9687 13353 : cp_omp_address_inspector ai (OMP_CLAUSE_LOCATION (c), t);
9688 :
9689 13353 : if (!ai.check_clause (c))
9690 : {
9691 : remove = true;
9692 : break;
9693 : }
9694 :
9695 13332 : if (!ai.map_supported_p ())
9696 : {
9697 88 : sorry_at (OMP_CLAUSE_LOCATION (c),
9698 : "unsupported map expression %qE",
9699 44 : OMP_CLAUSE_DECL (c));
9700 44 : remove = true;
9701 44 : break;
9702 : }
9703 :
9704 26576 : gcc_assert ((addr_tokens[0]->type == ARRAY_BASE
9705 : || addr_tokens[0]->type == STRUCTURE_BASE)
9706 : && addr_tokens[1]->type == ACCESS_METHOD);
9707 :
9708 13288 : t = addr_tokens[1]->expr;
9709 :
9710 : /* This is used to prevent cxx_mark_addressable from being called
9711 : on 'this' for expressions like 'this->a', i.e. typical member
9712 : accesses. */
9713 13288 : indir_component_ref_p
9714 26576 : = (addr_tokens[0]->type == STRUCTURE_BASE
9715 13288 : && addr_tokens[1]->u.access_kind != ACCESS_DIRECT);
9716 :
9717 13288 : if (addr_tokens[0]->u.structure_base_kind != BASE_DECL)
9718 1 : goto skip_decl_checks;
9719 :
9720 : /* For OpenMP, we can access a struct "t" and "t.d" on the same
9721 : mapping. OpenACC allows multiple fields of the same structure
9722 : to be written. */
9723 13287 : if (addr_tokens[0]->type == STRUCTURE_BASE
9724 13287 : && (bitmap_bit_p (&map_field_head, DECL_UID (t))
9725 1263 : || (!openacc && bitmap_bit_p (&map_head, DECL_UID (t)))))
9726 1351 : goto skip_decl_checks;
9727 :
9728 11936 : if (!processing_template_decl && TREE_CODE (t) == FIELD_DECL)
9729 : {
9730 0 : OMP_CLAUSE_DECL (c)
9731 0 : = finish_non_static_data_member (t, NULL_TREE, NULL_TREE);
9732 0 : break;
9733 : }
9734 11936 : if (!VAR_P (t) && TREE_CODE (t) != PARM_DECL)
9735 : {
9736 0 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
9737 : break;
9738 0 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9739 0 : && (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_POINTER
9740 0 : || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_POINTER
9741 0 : || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH_DETACH
9742 0 : || (!openacc && EXPR_P (t))))
9743 : break;
9744 0 : if (DECL_P (t))
9745 0 : error_at (OMP_CLAUSE_LOCATION (c),
9746 : "%qD is not a variable in %qs clause", t,
9747 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
9748 : else
9749 0 : error_at (OMP_CLAUSE_LOCATION (c),
9750 : "%qE is not a variable in %qs clause", t,
9751 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
9752 : remove = true;
9753 : }
9754 11936 : else if (VAR_P (t) && CP_DECL_THREAD_LOCAL_P (t))
9755 : {
9756 0 : error_at (OMP_CLAUSE_LOCATION (c),
9757 : "%qD is threadprivate variable in %qs clause", t,
9758 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
9759 0 : remove = true;
9760 : }
9761 11936 : else if (!processing_template_decl
9762 11757 : && !TYPE_REF_P (TREE_TYPE (t))
9763 11080 : && (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP
9764 8145 : || (OMP_CLAUSE_MAP_KIND (c)
9765 : != GOMP_MAP_FIRSTPRIVATE_POINTER))
9766 9096 : && !indir_component_ref_p
9767 8732 : && (t != current_class_ptr
9768 18 : || OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP
9769 6 : || OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ATTACH_DETACH)
9770 20668 : && !cxx_mark_addressable (t))
9771 : remove = true;
9772 11936 : else if (!(OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9773 8983 : && (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_POINTER
9774 8983 : || (OMP_CLAUSE_MAP_KIND (c)
9775 : == GOMP_MAP_FIRSTPRIVATE_POINTER)
9776 6999 : || (OMP_CLAUSE_MAP_KIND (c)
9777 : == GOMP_MAP_ATTACH_DETACH)))
9778 9292 : && t == OMP_CLAUSE_DECL (c)
9779 8594 : && !type_dependent_expression_p (t)
9780 29124 : && !omp_mappable_type (TYPE_REF_P (TREE_TYPE (t))
9781 278 : ? TREE_TYPE (TREE_TYPE (t))
9782 8316 : : TREE_TYPE (t)))
9783 : {
9784 42 : auto_diagnostic_group d;
9785 84 : error_at (OMP_CLAUSE_LOCATION (c),
9786 : "%qD does not have a mappable type in %qs clause", t,
9787 42 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
9788 42 : if (TREE_TYPE (t) != error_mark_node
9789 42 : && !COMPLETE_TYPE_P (TREE_TYPE (t)))
9790 39 : cxx_incomplete_type_inform (TREE_TYPE (t));
9791 42 : remove = true;
9792 42 : }
9793 11894 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9794 8947 : && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FORCE_DEVICEPTR
9795 93 : && !type_dependent_expression_p (t)
9796 11987 : && !INDIRECT_TYPE_P (TREE_TYPE (t)))
9797 : {
9798 6 : error_at (OMP_CLAUSE_LOCATION (c),
9799 : "%qD is not a pointer variable", t);
9800 6 : remove = true;
9801 : }
9802 11888 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9803 8941 : && OMP_CLAUSE_MAP_IMPLICIT (c)
9804 12258 : && (bitmap_bit_p (&map_head, DECL_UID (t))
9805 367 : || bitmap_bit_p (&map_field_head, DECL_UID (t))
9806 367 : || bitmap_bit_p (&map_firstprivate_head,
9807 367 : DECL_UID (t))))
9808 : remove = true;
9809 11882 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9810 11882 : && (OMP_CLAUSE_MAP_KIND (c)
9811 : == GOMP_MAP_FIRSTPRIVATE_POINTER))
9812 : {
9813 1978 : if (bitmap_bit_p (&generic_head, DECL_UID (t))
9814 1978 : || bitmap_bit_p (&firstprivate_head, DECL_UID (t))
9815 3953 : || (openacc
9816 1364 : && bitmap_bit_p (&map_firstprivate_head, DECL_UID (t))))
9817 : {
9818 12 : error_at (OMP_CLAUSE_LOCATION (c),
9819 : "%qD appears more than once in data clauses", t);
9820 12 : remove = true;
9821 : }
9822 1966 : else if (bitmap_bit_p (&map_head, DECL_UID (t))
9823 12 : && !bitmap_bit_p (&map_field_head, DECL_UID (t))
9824 1974 : && openacc)
9825 : {
9826 3 : error_at (OMP_CLAUSE_LOCATION (c),
9827 : "%qD appears more than once in data clauses", t);
9828 3 : remove = true;
9829 : }
9830 : else
9831 1963 : bitmap_set_bit (&map_firstprivate_head, DECL_UID (t));
9832 : }
9833 9904 : else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9834 9904 : && (OMP_CLAUSE_MAP_KIND (c)
9835 : == GOMP_MAP_FIRSTPRIVATE_REFERENCE))
9836 115 : bitmap_set_bit (&map_firstprivate_head, DECL_UID (t));
9837 9789 : else if (bitmap_bit_p (&map_head, DECL_UID (t))
9838 181 : && !bitmap_bit_p (&map_field_head, DECL_UID (t))
9839 38 : && ort != C_ORT_OMP
9840 38 : && ort != C_ORT_OMP_TARGET
9841 9805 : && ort != C_ORT_OMP_EXIT_DATA)
9842 : {
9843 9 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP)
9844 0 : error_at (OMP_CLAUSE_LOCATION (c),
9845 : "%qD appears more than once in motion clauses", t);
9846 9 : else if (openacc)
9847 9 : error_at (OMP_CLAUSE_LOCATION (c),
9848 : "%qD appears more than once in data clauses", t);
9849 : else
9850 0 : error_at (OMP_CLAUSE_LOCATION (c),
9851 : "%qD appears more than once in map clauses", t);
9852 : remove = true;
9853 : }
9854 9780 : else if (openacc && bitmap_bit_p (&generic_head, DECL_UID (t)))
9855 : {
9856 0 : error_at (OMP_CLAUSE_LOCATION (c),
9857 : "%qD appears more than once in data clauses", t);
9858 0 : remove = true;
9859 : }
9860 9780 : else if (bitmap_bit_p (&firstprivate_head, DECL_UID (t))
9861 9780 : || bitmap_bit_p (&is_on_device_head, DECL_UID (t)))
9862 : {
9863 27 : if (openacc)
9864 0 : error_at (OMP_CLAUSE_LOCATION (c),
9865 : "%qD appears more than once in data clauses", t);
9866 : else
9867 27 : error_at (OMP_CLAUSE_LOCATION (c),
9868 : "%qD appears both in data and map clauses", t);
9869 : remove = true;
9870 : }
9871 9753 : else if (!omp_access_chain_p (addr_tokens, 1))
9872 : {
9873 9673 : bitmap_set_bit (&map_head, DECL_UID (t));
9874 :
9875 9673 : tree decl = OMP_CLAUSE_DECL (c);
9876 9673 : if (t != decl
9877 9673 : && (TREE_CODE (decl) == COMPONENT_REF
9878 162 : || (INDIRECT_REF_P (decl)
9879 162 : && (TREE_CODE (TREE_OPERAND (decl, 0))
9880 : == COMPONENT_REF)
9881 150 : && TYPE_REF_P (TREE_TYPE (TREE_OPERAND (decl,
9882 : 0))))))
9883 1165 : bitmap_set_bit (&map_field_head, DECL_UID (t));
9884 : }
9885 :
9886 4694 : skip_decl_checks:
9887 : /* If we call ai.expand_map_clause in handle_omp_array_sections,
9888 : the containing loop (here) iterates through the new nodes
9889 : created by that expansion. Avoid expanding those again (just
9890 : by checking the node type). */
9891 4694 : if (!remove
9892 13183 : && !processing_template_decl
9893 13007 : && ort != C_ORT_DECLARE_SIMD
9894 13007 : && (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP
9895 9980 : || (OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_FIRSTPRIVATE_POINTER
9896 8017 : && (OMP_CLAUSE_MAP_KIND (c)
9897 : != GOMP_MAP_FIRSTPRIVATE_REFERENCE)
9898 7902 : && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ALWAYS_POINTER
9899 7902 : && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ATTACH_DETACH
9900 6903 : && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ATTACH
9901 6854 : && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_DETACH)))
9902 : {
9903 9856 : grp_start_p = pc;
9904 9856 : grp_sentinel = OMP_CLAUSE_CHAIN (c);
9905 9856 : tree nc = ai.expand_map_clause (c, OMP_CLAUSE_DECL (c),
9906 : addr_tokens, ort);
9907 9856 : if (nc != error_mark_node)
9908 9856 : c = nc;
9909 : }
9910 20346 : }
9911 13288 : break;
9912 :
9913 645 : case OMP_CLAUSE_ENTER:
9914 645 : case OMP_CLAUSE_LINK:
9915 645 : case OMP_CLAUSE_LOCAL:
9916 645 : t = OMP_CLAUSE_DECL (c);
9917 645 : const char *cname;
9918 645 : cname = omp_clause_code_name[OMP_CLAUSE_CODE (c)];
9919 645 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_ENTER
9920 645 : && OMP_CLAUSE_ENTER_TO (c))
9921 : cname = "to";
9922 645 : if (TREE_CODE (t) == FUNCTION_DECL
9923 645 : && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_ENTER)
9924 : ;
9925 428 : else if (!VAR_P (t))
9926 : {
9927 12 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_ENTER)
9928 : {
9929 9 : if (TREE_CODE (t) == TEMPLATE_ID_EXPR)
9930 6 : error_at (OMP_CLAUSE_LOCATION (c),
9931 : "template %qE in clause %qs", t, cname);
9932 3 : else if (really_overloaded_fn (t))
9933 3 : error_at (OMP_CLAUSE_LOCATION (c),
9934 : "overloaded function name %qE in clause %qs", t,
9935 : cname);
9936 : else
9937 0 : error_at (OMP_CLAUSE_LOCATION (c),
9938 : "%qE is neither a variable nor a function name "
9939 : "in clause %qs", t, cname);
9940 : }
9941 : else
9942 3 : error_at (OMP_CLAUSE_LOCATION (c),
9943 : "%qE is not a variable in clause %qs", t, cname);
9944 : remove = true;
9945 : }
9946 416 : else if (DECL_THREAD_LOCAL_P (t))
9947 : {
9948 6 : error_at (OMP_CLAUSE_LOCATION (c),
9949 : "%qD is threadprivate variable in %qs clause", t,
9950 : cname);
9951 6 : remove = true;
9952 : }
9953 410 : else if (!omp_mappable_type (TREE_TYPE (t)))
9954 : {
9955 18 : auto_diagnostic_group d;
9956 18 : error_at (OMP_CLAUSE_LOCATION (c),
9957 : "%qD does not have a mappable type in %qs clause", t,
9958 : cname);
9959 18 : if (TREE_TYPE (t) != error_mark_node
9960 18 : && !COMPLETE_TYPE_P (TREE_TYPE (t)))
9961 18 : cxx_incomplete_type_inform (TREE_TYPE (t));
9962 18 : remove = true;
9963 18 : }
9964 36 : if (remove)
9965 : break;
9966 609 : if (bitmap_bit_p (&generic_head, DECL_UID (t)))
9967 : {
9968 30 : error_at (OMP_CLAUSE_LOCATION (c),
9969 : "%qE appears more than once on the same "
9970 : "%<declare target%> directive", t);
9971 30 : remove = true;
9972 : }
9973 : else
9974 579 : bitmap_set_bit (&generic_head, DECL_UID (t));
9975 : break;
9976 :
9977 457 : case OMP_CLAUSE_UNIFORM:
9978 457 : t = OMP_CLAUSE_DECL (c);
9979 457 : if (TREE_CODE (t) != PARM_DECL)
9980 : {
9981 0 : if (processing_template_decl)
9982 : break;
9983 0 : if (DECL_P (t))
9984 0 : error_at (OMP_CLAUSE_LOCATION (c),
9985 : "%qD is not an argument in %<uniform%> clause", t);
9986 : else
9987 0 : error_at (OMP_CLAUSE_LOCATION (c),
9988 : "%qE is not an argument in %<uniform%> clause", t);
9989 : remove = true;
9990 : break;
9991 : }
9992 : /* map_head bitmap is used as uniform_head if declare_simd. */
9993 457 : bitmap_set_bit (&map_head, DECL_UID (t));
9994 457 : goto check_dup_generic;
9995 :
9996 165 : case OMP_CLAUSE_GRAINSIZE:
9997 165 : t = OMP_CLAUSE_GRAINSIZE_EXPR (c);
9998 165 : if (t == error_mark_node)
9999 : remove = true;
10000 165 : else if (!type_dependent_expression_p (t)
10001 165 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
10002 : {
10003 0 : error_at (OMP_CLAUSE_LOCATION (c),
10004 : "%<grainsize%> expression must be integral");
10005 0 : remove = true;
10006 : }
10007 : else
10008 : {
10009 165 : t = mark_rvalue_use (t);
10010 165 : if (!processing_template_decl)
10011 : {
10012 164 : t = maybe_constant_value (t);
10013 164 : if (TREE_CODE (t) == INTEGER_CST
10014 164 : && tree_int_cst_sgn (t) != 1)
10015 : {
10016 0 : warning_at (OMP_CLAUSE_LOCATION (c), OPT_Wopenmp,
10017 : "%<grainsize%> value must be positive");
10018 0 : t = integer_one_node;
10019 : }
10020 164 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
10021 : }
10022 165 : OMP_CLAUSE_GRAINSIZE_EXPR (c) = t;
10023 : }
10024 : break;
10025 :
10026 276 : case OMP_CLAUSE_PRIORITY:
10027 276 : t = OMP_CLAUSE_PRIORITY_EXPR (c);
10028 276 : if (t == error_mark_node)
10029 : remove = true;
10030 276 : else if (!type_dependent_expression_p (t)
10031 276 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
10032 : {
10033 0 : error_at (OMP_CLAUSE_LOCATION (c),
10034 : "%<priority%> expression must be integral");
10035 0 : remove = true;
10036 : }
10037 : else
10038 : {
10039 276 : t = mark_rvalue_use (t);
10040 276 : if (!processing_template_decl)
10041 : {
10042 276 : t = maybe_constant_value (t);
10043 276 : if (TREE_CODE (t) == INTEGER_CST
10044 276 : && tree_int_cst_sgn (t) == -1)
10045 : {
10046 0 : warning_at (OMP_CLAUSE_LOCATION (c), OPT_Wopenmp,
10047 : "%<priority%> value must be non-negative");
10048 0 : t = integer_one_node;
10049 : }
10050 276 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
10051 : }
10052 276 : OMP_CLAUSE_PRIORITY_EXPR (c) = t;
10053 : }
10054 : break;
10055 :
10056 228 : case OMP_CLAUSE_HINT:
10057 228 : t = OMP_CLAUSE_HINT_EXPR (c);
10058 228 : if (t == error_mark_node)
10059 : remove = true;
10060 228 : else if (!type_dependent_expression_p (t)
10061 228 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
10062 : {
10063 9 : error_at (OMP_CLAUSE_LOCATION (c),
10064 : "%<hint%> expression must be integral");
10065 9 : remove = true;
10066 : }
10067 : else
10068 : {
10069 219 : t = mark_rvalue_use (t);
10070 219 : if (!processing_template_decl)
10071 : {
10072 171 : t = maybe_constant_value (t);
10073 171 : if (TREE_CODE (t) != INTEGER_CST)
10074 : {
10075 16 : error_at (OMP_CLAUSE_LOCATION (c),
10076 : "%<hint%> expression must be constant integer "
10077 : "expression");
10078 16 : remove = true;
10079 : }
10080 : }
10081 219 : OMP_CLAUSE_HINT_EXPR (c) = t;
10082 : }
10083 : break;
10084 :
10085 186 : case OMP_CLAUSE_FILTER:
10086 186 : t = OMP_CLAUSE_FILTER_EXPR (c);
10087 186 : if (t == error_mark_node)
10088 : remove = true;
10089 186 : else if (!type_dependent_expression_p (t)
10090 186 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
10091 : {
10092 6 : error_at (OMP_CLAUSE_LOCATION (c),
10093 : "%<filter%> expression must be integral");
10094 6 : remove = true;
10095 : }
10096 : else
10097 : {
10098 180 : t = mark_rvalue_use (t);
10099 180 : if (!processing_template_decl)
10100 : {
10101 177 : t = maybe_constant_value (t);
10102 177 : t = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
10103 : }
10104 180 : OMP_CLAUSE_FILTER_EXPR (c) = t;
10105 : }
10106 : break;
10107 :
10108 433 : case OMP_CLAUSE_IS_DEVICE_PTR:
10109 433 : case OMP_CLAUSE_USE_DEVICE_PTR:
10110 433 : field_ok = (ort & C_ORT_OMP_DECLARE_SIMD) == C_ORT_OMP;
10111 433 : t = OMP_CLAUSE_DECL (c);
10112 433 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IS_DEVICE_PTR)
10113 329 : bitmap_set_bit (&is_on_device_head, DECL_UID (t));
10114 433 : if (!type_dependent_expression_p (t))
10115 : {
10116 431 : tree type = TREE_TYPE (t);
10117 431 : if (!TYPE_PTR_P (type)
10118 431 : && (!TYPE_REF_P (type) || !TYPE_PTR_P (TREE_TYPE (type))))
10119 : {
10120 57 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR
10121 57 : && ort == C_ORT_OMP)
10122 : {
10123 3 : error_at (OMP_CLAUSE_LOCATION (c),
10124 : "%qs variable is neither a pointer "
10125 : "nor reference to pointer",
10126 3 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
10127 3 : remove = true;
10128 : }
10129 54 : else if (TREE_CODE (type) != ARRAY_TYPE
10130 54 : && (!TYPE_REF_P (type)
10131 2 : || TREE_CODE (TREE_TYPE (type)) != ARRAY_TYPE))
10132 : {
10133 12 : error_at (OMP_CLAUSE_LOCATION (c),
10134 : "%qs variable is neither a pointer, nor an "
10135 : "array nor reference to pointer or array",
10136 12 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
10137 12 : remove = true;
10138 : }
10139 : }
10140 : }
10141 433 : goto check_dup_generic;
10142 :
10143 267 : case OMP_CLAUSE_HAS_DEVICE_ADDR:
10144 267 : t = OMP_CLAUSE_DECL (c);
10145 267 : if (TREE_CODE (t) == OMP_ARRAY_SECTION)
10146 : {
10147 28 : if (handle_omp_array_sections (c, ort))
10148 : remove = true;
10149 : else
10150 : {
10151 28 : t = OMP_CLAUSE_DECL (c);
10152 30 : while (TREE_CODE (t) == OMP_ARRAY_SECTION)
10153 2 : t = TREE_OPERAND (t, 0);
10154 64 : while (INDIRECT_REF_P (t)
10155 64 : || TREE_CODE (t) == ARRAY_REF)
10156 36 : t = TREE_OPERAND (t, 0);
10157 : }
10158 : }
10159 267 : if (VAR_P (t) || TREE_CODE (t) == PARM_DECL)
10160 : {
10161 267 : bitmap_set_bit (&is_on_device_head, DECL_UID (t));
10162 267 : if (!processing_template_decl
10163 267 : && !cxx_mark_addressable (t))
10164 : remove = true;
10165 : }
10166 267 : goto check_dup_generic_t;
10167 :
10168 76 : case OMP_CLAUSE_USE_DEVICE_ADDR:
10169 76 : field_ok = true;
10170 76 : t = OMP_CLAUSE_DECL (c);
10171 76 : if (!processing_template_decl
10172 74 : && (VAR_P (t) || TREE_CODE (t) == PARM_DECL)
10173 74 : && !TYPE_REF_P (TREE_TYPE (t))
10174 143 : && !cxx_mark_addressable (t))
10175 : remove = true;
10176 76 : goto check_dup_generic;
10177 :
10178 : case OMP_CLAUSE_NOWAIT:
10179 : case OMP_CLAUSE_DEFAULT:
10180 : case OMP_CLAUSE_UNTIED:
10181 : case OMP_CLAUSE_COLLAPSE:
10182 : case OMP_CLAUSE_PARALLEL:
10183 : case OMP_CLAUSE_FOR:
10184 : case OMP_CLAUSE_SECTIONS:
10185 : case OMP_CLAUSE_TASKGROUP:
10186 : case OMP_CLAUSE_PROC_BIND:
10187 : case OMP_CLAUSE_DEVICE_TYPE:
10188 : case OMP_CLAUSE_NOGROUP:
10189 : case OMP_CLAUSE_THREADS:
10190 : case OMP_CLAUSE_SIMD:
10191 : case OMP_CLAUSE_DEFAULTMAP:
10192 : case OMP_CLAUSE_BIND:
10193 : case OMP_CLAUSE_AUTO:
10194 : case OMP_CLAUSE_INDEPENDENT:
10195 : case OMP_CLAUSE_SEQ:
10196 : case OMP_CLAUSE_IF_PRESENT:
10197 : case OMP_CLAUSE_FINALIZE:
10198 : case OMP_CLAUSE_NOHOST:
10199 : case OMP_CLAUSE_INDIRECT:
10200 : break;
10201 :
10202 231 : case OMP_CLAUSE_MERGEABLE:
10203 231 : mergeable_seen = true;
10204 231 : break;
10205 :
10206 322 : case OMP_CLAUSE_TILE:
10207 754 : for (tree list = OMP_CLAUSE_TILE_LIST (c); !remove && list;
10208 432 : list = TREE_CHAIN (list))
10209 : {
10210 432 : t = TREE_VALUE (list);
10211 :
10212 432 : if (t == error_mark_node)
10213 : remove = true;
10214 403 : else if (!type_dependent_expression_p (t)
10215 403 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
10216 : {
10217 3 : error_at (OMP_CLAUSE_LOCATION (c),
10218 : "%<tile%> argument needs integral type");
10219 3 : remove = true;
10220 : }
10221 : else
10222 : {
10223 400 : t = mark_rvalue_use (t);
10224 400 : if (!processing_template_decl)
10225 : {
10226 : /* Zero is used to indicate '*', we permit you
10227 : to get there via an ICE of value zero. */
10228 385 : t = maybe_constant_value (t);
10229 385 : if (!tree_fits_shwi_p (t)
10230 369 : || tree_to_shwi (t) < 0)
10231 : {
10232 40 : error_at (OMP_CLAUSE_LOCATION (c),
10233 : "%<tile%> argument needs positive "
10234 : "integral constant");
10235 40 : remove = true;
10236 : }
10237 : }
10238 : }
10239 :
10240 : /* Update list item. */
10241 432 : TREE_VALUE (list) = t;
10242 : }
10243 : break;
10244 :
10245 1027 : case OMP_CLAUSE_SIZES:
10246 1027 : for (tree list = OMP_CLAUSE_SIZES_LIST (c);
10247 2688 : !remove && list; list = TREE_CHAIN (list))
10248 : {
10249 1661 : t = TREE_VALUE (list);
10250 :
10251 1661 : if (t == error_mark_node)
10252 0 : t = integer_one_node;
10253 1661 : else if (!type_dependent_expression_p (t)
10254 1661 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
10255 : {
10256 8 : error_at (OMP_CLAUSE_LOCATION (c),
10257 : "%<sizes%> argument needs positive integral "
10258 : "constant");
10259 8 : t = integer_one_node;
10260 : }
10261 : else
10262 : {
10263 1653 : t = mark_rvalue_use (t);
10264 1653 : if (!processing_template_decl)
10265 : {
10266 1636 : t = maybe_constant_value (t);
10267 1636 : HOST_WIDE_INT n;
10268 1636 : if (!tree_fits_shwi_p (t)
10269 1632 : || !INTEGRAL_TYPE_P (TREE_TYPE (t))
10270 1632 : || (n = tree_to_shwi (t)) <= 0
10271 3240 : || (int)n != n)
10272 : {
10273 32 : error_at (OMP_CLAUSE_LOCATION (c),
10274 : "%<sizes%> argument needs positive "
10275 : "integral constant");
10276 32 : t = integer_one_node;
10277 : }
10278 : }
10279 : }
10280 :
10281 : /* Update list item. */
10282 1661 : TREE_VALUE (list) = t;
10283 : }
10284 : break;
10285 :
10286 630 : case OMP_CLAUSE_ORDERED:
10287 630 : ordered_seen = true;
10288 630 : break;
10289 :
10290 1549 : case OMP_CLAUSE_ORDER:
10291 1549 : if (order_seen)
10292 : remove = true;
10293 : else
10294 : order_seen = true;
10295 : break;
10296 :
10297 638 : case OMP_CLAUSE_INBRANCH:
10298 638 : case OMP_CLAUSE_NOTINBRANCH:
10299 638 : if (branch_seen)
10300 : {
10301 3 : error_at (OMP_CLAUSE_LOCATION (c),
10302 : "%<inbranch%> clause is incompatible with "
10303 : "%<notinbranch%>");
10304 3 : remove = true;
10305 : }
10306 : branch_seen = true;
10307 : break;
10308 :
10309 306 : case OMP_CLAUSE_INCLUSIVE:
10310 306 : case OMP_CLAUSE_EXCLUSIVE:
10311 306 : t = omp_clause_decl_field (OMP_CLAUSE_DECL (c));
10312 306 : if (!t)
10313 306 : t = OMP_CLAUSE_DECL (c);
10314 306 : if (t == current_class_ptr)
10315 : {
10316 0 : error_at (OMP_CLAUSE_LOCATION (c),
10317 : "%<this%> allowed in OpenMP only in %<declare simd%>"
10318 : " clauses");
10319 0 : remove = true;
10320 0 : break;
10321 : }
10322 306 : if (!VAR_P (t)
10323 : && TREE_CODE (t) != PARM_DECL
10324 : && TREE_CODE (t) != FIELD_DECL)
10325 : {
10326 0 : if (processing_template_decl && TREE_CODE (t) != OVERLOAD)
10327 : break;
10328 0 : if (DECL_P (t))
10329 0 : error_at (OMP_CLAUSE_LOCATION (c),
10330 : "%qD is not a variable in clause %qs", t,
10331 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
10332 : else
10333 0 : error_at (OMP_CLAUSE_LOCATION (c),
10334 : "%qE is not a variable in clause %qs", t,
10335 0 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
10336 : remove = true;
10337 : }
10338 : break;
10339 :
10340 : case OMP_CLAUSE_FULL:
10341 : break;
10342 :
10343 470 : case OMP_CLAUSE_PARTIAL:
10344 470 : partial_seen = true;
10345 470 : t = OMP_CLAUSE_PARTIAL_EXPR (c);
10346 470 : if (!t)
10347 : break;
10348 :
10349 313 : if (t == error_mark_node)
10350 : t = NULL_TREE;
10351 313 : else if (!type_dependent_expression_p (t)
10352 313 : && !INTEGRAL_TYPE_P (TREE_TYPE (t)))
10353 : {
10354 3 : error_at (OMP_CLAUSE_LOCATION (c),
10355 : "%<partial%> argument needs positive constant "
10356 : "integer expression");
10357 3 : t = NULL_TREE;
10358 : }
10359 : else
10360 : {
10361 310 : t = mark_rvalue_use (t);
10362 310 : if (!processing_template_decl)
10363 : {
10364 292 : t = maybe_constant_value (t);
10365 :
10366 292 : HOST_WIDE_INT n;
10367 584 : if (!INTEGRAL_TYPE_P (TREE_TYPE (t))
10368 292 : || !tree_fits_shwi_p (t)
10369 286 : || (n = tree_to_shwi (t)) <= 0
10370 560 : || (int)n != n)
10371 : {
10372 24 : error_at (OMP_CLAUSE_LOCATION (c),
10373 : "%<partial%> argument needs positive "
10374 : "constant integer expression");
10375 24 : t = NULL_TREE;
10376 : }
10377 : }
10378 : }
10379 :
10380 313 : OMP_CLAUSE_PARTIAL_EXPR (c) = t;
10381 313 : break;
10382 549 : case OMP_CLAUSE_INIT:
10383 549 : init_seen = true;
10384 549 : OMP_CLAUSE_INIT_PREFER_TYPE (c)
10385 549 : = cp_finish_omp_init_prefer_type (OMP_CLAUSE_INIT_PREFER_TYPE (c));
10386 549 : if (!OMP_CLAUSE_INIT_TARGETSYNC (c))
10387 271 : init_no_targetsync_clause = c;
10388 : /* FALLTHRU */
10389 844 : case OMP_CLAUSE_DESTROY:
10390 844 : case OMP_CLAUSE_USE:
10391 844 : init_use_destroy_seen = true;
10392 844 : t = OMP_CLAUSE_DECL (c);
10393 844 : if (bitmap_bit_p (&generic_head, DECL_UID (t)))
10394 : {
10395 9 : error_at (OMP_CLAUSE_LOCATION (c),
10396 : "%qD appears more than once in action clauses", t);
10397 9 : remove = true;
10398 9 : break;
10399 : }
10400 835 : bitmap_set_bit (&generic_head, DECL_UID (t));
10401 : /* FALLTHRU */
10402 1099 : case OMP_CLAUSE_INTEROP:
10403 1099 : if (!processing_template_decl)
10404 : {
10405 1003 : if (/* (ort == C_ORT_OMP_INTEROP [uncomment for depobj init]
10406 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_INTEROP) && */
10407 1003 : !c_omp_interop_t_p (TREE_TYPE (OMP_CLAUSE_DECL (c))))
10408 : {
10409 126 : error_at (OMP_CLAUSE_LOCATION (c),
10410 : "%qD must be of %<omp_interop_t%>",
10411 63 : OMP_CLAUSE_DECL (c));
10412 63 : remove = true;
10413 : }
10414 940 : else if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_INIT
10415 481 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DESTROY)
10416 1058 : && TREE_READONLY (OMP_CLAUSE_DECL (c)))
10417 : {
10418 36 : error_at (OMP_CLAUSE_LOCATION (c),
10419 18 : "%qD shall not be const", OMP_CLAUSE_DECL (c));
10420 18 : remove = true;
10421 : }
10422 : }
10423 1099 : pc = &OMP_CLAUSE_CHAIN (c);
10424 1099 : break;
10425 0 : default:
10426 0 : gcc_unreachable ();
10427 55 : }
10428 :
10429 98622 : if (remove)
10430 : {
10431 2733 : if (grp_start_p)
10432 : {
10433 : /* If we found a clause to remove, we want to remove the whole
10434 : expanded group, otherwise gimplify
10435 : (omp_resolve_clause_dependencies) can get confused. */
10436 861 : *grp_start_p = grp_sentinel;
10437 861 : pc = grp_start_p;
10438 861 : grp_start_p = NULL;
10439 : }
10440 : else
10441 1872 : *pc = OMP_CLAUSE_CHAIN (c);
10442 : }
10443 : else
10444 95889 : pc = &OMP_CLAUSE_CHAIN (c);
10445 : }
10446 :
10447 63634 : if (grp_start_p
10448 63634 : && OMP_CLAUSE_HAS_ITERATORS (*grp_start_p))
10449 158 : for (tree gc = *grp_start_p; gc; gc = OMP_CLAUSE_CHAIN (gc))
10450 95 : OMP_CLAUSE_ITERATORS (gc) = OMP_CLAUSE_ITERATORS (*grp_start_p);
10451 :
10452 63634 : if (reduction_seen < 0 && (ordered_seen || schedule_seen))
10453 63634 : reduction_seen = -2;
10454 :
10455 160490 : for (pc = &clauses, c = clauses; c ; c = *pc)
10456 : {
10457 96856 : enum omp_clause_code c_kind = OMP_CLAUSE_CODE (c);
10458 96856 : bool remove = false;
10459 96856 : bool need_complete_type = false;
10460 96856 : bool need_default_ctor = false;
10461 96856 : bool need_copy_ctor = false;
10462 96856 : bool need_copy_assignment = false;
10463 96856 : bool need_implicitly_determined = false;
10464 96856 : bool need_dtor = false;
10465 96856 : tree type, inner_type;
10466 :
10467 96856 : switch (c_kind)
10468 : {
10469 : case OMP_CLAUSE_SHARED:
10470 : need_implicitly_determined = true;
10471 : break;
10472 2550 : case OMP_CLAUSE_PRIVATE:
10473 2550 : need_complete_type = true;
10474 2550 : need_default_ctor = true;
10475 2550 : need_dtor = true;
10476 2550 : need_implicitly_determined = true;
10477 2550 : break;
10478 3169 : case OMP_CLAUSE_FIRSTPRIVATE:
10479 3169 : need_complete_type = true;
10480 3169 : need_copy_ctor = true;
10481 3169 : need_dtor = true;
10482 3169 : need_implicitly_determined = true;
10483 3169 : break;
10484 2766 : case OMP_CLAUSE_LASTPRIVATE:
10485 2766 : need_complete_type = true;
10486 2766 : need_copy_assignment = true;
10487 2766 : need_implicitly_determined = true;
10488 2766 : break;
10489 7497 : case OMP_CLAUSE_REDUCTION:
10490 7497 : if (reduction_seen == -2)
10491 27 : OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
10492 7497 : if (OMP_CLAUSE_REDUCTION_INSCAN (c))
10493 436 : need_copy_assignment = true;
10494 : need_implicitly_determined = true;
10495 : break;
10496 : case OMP_CLAUSE_IN_REDUCTION:
10497 : case OMP_CLAUSE_TASK_REDUCTION:
10498 : case OMP_CLAUSE_INCLUSIVE:
10499 : case OMP_CLAUSE_EXCLUSIVE:
10500 : need_implicitly_determined = true;
10501 : break;
10502 1550 : case OMP_CLAUSE_LINEAR:
10503 1550 : if (ort != C_ORT_OMP_DECLARE_SIMD)
10504 : need_implicitly_determined = true;
10505 679 : else if (OMP_CLAUSE_LINEAR_VARIABLE_STRIDE (c)
10506 721 : && !bitmap_bit_p (&map_head,
10507 42 : DECL_UID (OMP_CLAUSE_LINEAR_STEP (c))))
10508 : {
10509 6 : error_at (OMP_CLAUSE_LOCATION (c),
10510 : "%<linear%> clause step is a parameter %qD not "
10511 : "specified in %<uniform%> clause",
10512 6 : OMP_CLAUSE_LINEAR_STEP (c));
10513 6 : *pc = OMP_CLAUSE_CHAIN (c);
10514 75123 : continue;
10515 : }
10516 : break;
10517 : case OMP_CLAUSE_COPYPRIVATE:
10518 369 : need_copy_assignment = true;
10519 : break;
10520 : case OMP_CLAUSE_COPYIN:
10521 369 : need_copy_assignment = true;
10522 : break;
10523 873 : case OMP_CLAUSE_SIMDLEN:
10524 873 : if (safelen
10525 345 : && !processing_template_decl
10526 1218 : && tree_int_cst_lt (OMP_CLAUSE_SAFELEN_EXPR (safelen),
10527 345 : OMP_CLAUSE_SIMDLEN_EXPR (c)))
10528 : {
10529 : /* Note: How a scaling factor affects this, is underspecified in
10530 : OpenMP; cf. OpenMP spec issue #5160. Presumably, it means:
10531 : savelen >= simdlen * scale_factor
10532 : with
10533 : scale_factor = MAX (1, FLOOR_DIV_EXPR (VL(type), divisor))
10534 : and OpenMP states that VL(type) might be only known at runtime.
10535 : Hence scale_factor >= 1 and, conservatively, assume == 1 for
10536 : this error check. */
10537 0 : error_at (OMP_CLAUSE_LOCATION (c),
10538 : "%<simdlen%> clause value is bigger than "
10539 : "%<safelen%> clause value");
10540 0 : OMP_CLAUSE_SIMDLEN_EXPR (c)
10541 0 : = OMP_CLAUSE_SAFELEN_EXPR (safelen);
10542 : }
10543 873 : pc = &OMP_CLAUSE_CHAIN (c);
10544 873 : continue;
10545 3883 : case OMP_CLAUSE_SCHEDULE:
10546 3883 : if (ordered_seen
10547 3883 : && (OMP_CLAUSE_SCHEDULE_KIND (c)
10548 : & OMP_CLAUSE_SCHEDULE_NONMONOTONIC))
10549 : {
10550 21 : error_at (OMP_CLAUSE_LOCATION (c),
10551 : "%<nonmonotonic%> schedule modifier specified "
10552 : "together with %<ordered%> clause");
10553 42 : OMP_CLAUSE_SCHEDULE_KIND (c)
10554 21 : = (enum omp_clause_schedule_kind)
10555 21 : (OMP_CLAUSE_SCHEDULE_KIND (c)
10556 : & ~OMP_CLAUSE_SCHEDULE_NONMONOTONIC);
10557 : }
10558 3883 : if (reduction_seen == -2)
10559 9 : error_at (OMP_CLAUSE_LOCATION (c),
10560 : "%qs clause specified together with %<inscan%> "
10561 : "%<reduction%> clause", "schedule");
10562 3883 : pc = &OMP_CLAUSE_CHAIN (c);
10563 3883 : continue;
10564 51 : case OMP_CLAUSE_NOGROUP:
10565 51 : if (reduction_seen)
10566 : {
10567 3 : error_at (OMP_CLAUSE_LOCATION (c),
10568 : "%<nogroup%> clause must not be used together with "
10569 : "%<reduction%> clause");
10570 3 : *pc = OMP_CLAUSE_CHAIN (c);
10571 3 : continue;
10572 : }
10573 48 : pc = &OMP_CLAUSE_CHAIN (c);
10574 48 : continue;
10575 165 : case OMP_CLAUSE_GRAINSIZE:
10576 165 : if (num_tasks_seen)
10577 : {
10578 6 : error_at (OMP_CLAUSE_LOCATION (c),
10579 : "%<grainsize%> clause must not be used together with "
10580 : "%<num_tasks%> clause");
10581 6 : *pc = OMP_CLAUSE_CHAIN (c);
10582 6 : continue;
10583 : }
10584 159 : pc = &OMP_CLAUSE_CHAIN (c);
10585 159 : continue;
10586 630 : case OMP_CLAUSE_ORDERED:
10587 630 : if (reduction_seen == -2)
10588 6 : error_at (OMP_CLAUSE_LOCATION (c),
10589 : "%qs clause specified together with %<inscan%> "
10590 : "%<reduction%> clause", "ordered");
10591 630 : pc = &OMP_CLAUSE_CHAIN (c);
10592 630 : continue;
10593 1525 : case OMP_CLAUSE_ORDER:
10594 1525 : if (ordered_seen)
10595 : {
10596 12 : error_at (OMP_CLAUSE_LOCATION (c),
10597 : "%<order%> clause must not be used together "
10598 : "with %<ordered%> clause");
10599 12 : *pc = OMP_CLAUSE_CHAIN (c);
10600 12 : continue;
10601 : }
10602 1513 : pc = &OMP_CLAUSE_CHAIN (c);
10603 1513 : continue;
10604 57 : case OMP_CLAUSE_DETACH:
10605 57 : if (mergeable_seen)
10606 : {
10607 6 : error_at (OMP_CLAUSE_LOCATION (c),
10608 : "%<detach%> clause must not be used together with "
10609 : "%<mergeable%> clause");
10610 6 : *pc = OMP_CLAUSE_CHAIN (c);
10611 6 : continue;
10612 : }
10613 51 : pc = &OMP_CLAUSE_CHAIN (c);
10614 51 : continue;
10615 16105 : case OMP_CLAUSE_MAP:
10616 16105 : if (target_in_reduction_seen && !processing_template_decl)
10617 : {
10618 684 : t = OMP_CLAUSE_DECL (c);
10619 684 : while (handled_component_p (t)
10620 : || INDIRECT_REF_P (t)
10621 : || TREE_CODE (t) == ADDR_EXPR
10622 : || TREE_CODE (t) == MEM_REF
10623 804 : || TREE_CODE (t) == NON_LVALUE_EXPR)
10624 120 : t = TREE_OPERAND (t, 0);
10625 684 : if (DECL_P (t)
10626 684 : && bitmap_bit_p (&oacc_reduction_head, DECL_UID (t)))
10627 342 : OMP_CLAUSE_MAP_IN_REDUCTION (c) = 1;
10628 : }
10629 16105 : pc = &OMP_CLAUSE_CHAIN (c);
10630 16105 : continue;
10631 225 : case OMP_CLAUSE_FULL:
10632 225 : if (partial_seen)
10633 : {
10634 12 : error_at (OMP_CLAUSE_LOCATION (c),
10635 : "%<full%> clause must not be used together "
10636 : "with %<partial%> clause");
10637 12 : *pc = OMP_CLAUSE_CHAIN (c);
10638 12 : continue;
10639 : }
10640 213 : pc = &OMP_CLAUSE_CHAIN (c);
10641 213 : continue;
10642 6952 : case OMP_CLAUSE_NOWAIT:
10643 6952 : if (copyprivate_seen)
10644 : {
10645 6 : error_at (OMP_CLAUSE_LOCATION (c),
10646 : "%<nowait%> clause must not be used together "
10647 : "with %<copyprivate%> clause");
10648 6 : *pc = OMP_CLAUSE_CHAIN (c);
10649 6 : continue;
10650 : }
10651 : /* FALLTHRU */
10652 50917 : default:
10653 50917 : pc = &OMP_CLAUSE_CHAIN (c);
10654 50917 : continue;
10655 : }
10656 :
10657 22413 : t = OMP_CLAUSE_DECL (c);
10658 22413 : switch (c_kind)
10659 : {
10660 2766 : case OMP_CLAUSE_LASTPRIVATE:
10661 2766 : if (DECL_P (t)
10662 2766 : && !bitmap_bit_p (&firstprivate_head, DECL_UID (t)))
10663 : {
10664 2666 : need_default_ctor = true;
10665 2666 : need_dtor = true;
10666 : }
10667 : break;
10668 :
10669 9636 : case OMP_CLAUSE_REDUCTION:
10670 9636 : case OMP_CLAUSE_IN_REDUCTION:
10671 9636 : case OMP_CLAUSE_TASK_REDUCTION:
10672 9636 : if (allocate_seen)
10673 : {
10674 1711 : if (TREE_CODE (t) == MEM_REF)
10675 : {
10676 222 : t = TREE_OPERAND (t, 0);
10677 222 : if (TREE_CODE (t) == POINTER_PLUS_EXPR)
10678 0 : t = TREE_OPERAND (t, 0);
10679 222 : if (TREE_CODE (t) == ADDR_EXPR
10680 168 : || INDIRECT_REF_P (t))
10681 110 : t = TREE_OPERAND (t, 0);
10682 222 : if (DECL_P (t))
10683 222 : bitmap_clear_bit (&aligned_head, DECL_UID (t));
10684 : }
10685 1489 : else if (TREE_CODE (t) == OMP_ARRAY_SECTION)
10686 : {
10687 288 : while (TREE_CODE (t) == OMP_ARRAY_SECTION)
10688 144 : t = TREE_OPERAND (t, 0);
10689 144 : if (DECL_P (t))
10690 144 : bitmap_clear_bit (&aligned_head, DECL_UID (t));
10691 144 : t = OMP_CLAUSE_DECL (c);
10692 : }
10693 1345 : else if (DECL_P (t))
10694 1345 : bitmap_clear_bit (&aligned_head, DECL_UID (t));
10695 1711 : t = OMP_CLAUSE_DECL (c);
10696 : }
10697 9636 : if (processing_template_decl
10698 929 : && !VAR_P (t) && TREE_CODE (t) != PARM_DECL)
10699 : break;
10700 9018 : if (finish_omp_reduction_clause (c, &need_default_ctor,
10701 : &need_dtor))
10702 : remove = true;
10703 : else
10704 8934 : t = OMP_CLAUSE_DECL (c);
10705 : break;
10706 :
10707 277 : case OMP_CLAUSE_COPYIN:
10708 277 : if (processing_template_decl
10709 0 : && !VAR_P (t) && TREE_CODE (t) != PARM_DECL)
10710 : break;
10711 277 : if (!VAR_P (t) || !CP_DECL_THREAD_LOCAL_P (t))
10712 : {
10713 15 : error_at (OMP_CLAUSE_LOCATION (c),
10714 : "%qE must be %<threadprivate%> for %<copyin%>", t);
10715 15 : remove = true;
10716 : }
10717 : break;
10718 :
10719 : default:
10720 : break;
10721 : }
10722 :
10723 22413 : if (processing_template_decl
10724 1610 : && !VAR_P (t) && TREE_CODE (t) != PARM_DECL)
10725 : {
10726 680 : pc = &OMP_CLAUSE_CHAIN (c);
10727 680 : continue;
10728 : }
10729 :
10730 21733 : if (need_complete_type || need_copy_assignment)
10731 : {
10732 9234 : t = require_complete_type (t);
10733 9234 : if (t == error_mark_node)
10734 : remove = true;
10735 9210 : else if (!processing_template_decl
10736 8827 : && TYPE_REF_P (TREE_TYPE (t))
10737 9766 : && !complete_type_or_else (TREE_TYPE (TREE_TYPE (t)), t))
10738 : remove = true;
10739 : }
10740 21733 : if (need_implicitly_determined)
10741 : {
10742 20692 : const char *share_name = NULL;
10743 :
10744 20692 : if (allocate_seen
10745 5114 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_SHARED
10746 24927 : && DECL_P (t))
10747 3950 : bitmap_clear_bit (&aligned_head, DECL_UID (t));
10748 :
10749 20692 : if (VAR_P (t) && CP_DECL_THREAD_LOCAL_P (t))
10750 : share_name = "threadprivate";
10751 20650 : else switch (cxx_omp_predetermined_sharing_1 (t))
10752 : {
10753 : case OMP_CLAUSE_DEFAULT_UNSPECIFIED:
10754 : break;
10755 47 : case OMP_CLAUSE_DEFAULT_SHARED:
10756 47 : if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED
10757 30 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_FIRSTPRIVATE)
10758 64 : && c_omp_predefined_variable (t))
10759 : /* The __func__ variable and similar function-local predefined
10760 : variables may be listed in a shared or firstprivate
10761 : clause. */
10762 : break;
10763 31 : if (VAR_P (t)
10764 31 : && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_FIRSTPRIVATE
10765 9 : && TREE_STATIC (t)
10766 40 : && cxx_omp_const_qual_no_mutable (t))
10767 : {
10768 6 : tree ctx = CP_DECL_CONTEXT (t);
10769 : /* const qualified static data members without mutable
10770 : member may be specified in firstprivate clause. */
10771 6 : if (TYPE_P (ctx) && MAYBE_CLASS_TYPE_P (ctx))
10772 : break;
10773 : }
10774 : share_name = "shared";
10775 : break;
10776 : case OMP_CLAUSE_DEFAULT_PRIVATE:
10777 : share_name = "private";
10778 : break;
10779 0 : default:
10780 0 : gcc_unreachable ();
10781 : }
10782 : if (share_name)
10783 : {
10784 67 : error_at (OMP_CLAUSE_LOCATION (c),
10785 : "%qE is predetermined %qs for %qs",
10786 : omp_clause_printable_decl (t), share_name,
10787 67 : omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
10788 67 : remove = true;
10789 : }
10790 20625 : else if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_SHARED
10791 18566 : && OMP_CLAUSE_CODE (c) != OMP_CLAUSE_FIRSTPRIVATE
10792 36051 : && cxx_omp_const_qual_no_mutable (t))
10793 : {
10794 126 : error_at (OMP_CLAUSE_LOCATION (c),
10795 : "%<const%> qualified %qE without %<mutable%> member "
10796 : "may appear only in %<shared%> or %<firstprivate%> "
10797 : "clauses", omp_clause_printable_decl (t));
10798 63 : remove = true;
10799 : }
10800 : }
10801 :
10802 21733 : if (detach_seen
10803 16 : && (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED
10804 10 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_PRIVATE
10805 10 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_FIRSTPRIVATE
10806 0 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE)
10807 21749 : && OMP_CLAUSE_DECL (c) == OMP_CLAUSE_DECL (detach_seen))
10808 : {
10809 6 : error_at (OMP_CLAUSE_LOCATION (c),
10810 : "the event handle of a %<detach%> clause "
10811 : "should not be in a data-sharing clause");
10812 6 : remove = true;
10813 : }
10814 :
10815 : /* We're interested in the base element, not arrays. */
10816 21733 : inner_type = type = TREE_TYPE (t);
10817 21733 : if ((need_complete_type
10818 : || need_copy_assignment
10819 12499 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
10820 5717 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
10821 4244 : || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION)
10822 30315 : && TYPE_REF_P (inner_type))
10823 899 : inner_type = TREE_TYPE (inner_type);
10824 24411 : while (TREE_CODE (inner_type) == ARRAY_TYPE)
10825 2678 : inner_type = TREE_TYPE (inner_type);
10826 :
10827 : /* Check for special function availability by building a call to one.
10828 : Save the results, because later we won't be in the right context
10829 : for making these queries. */
10830 2397 : if (CLASS_TYPE_P (inner_type)
10831 2397 : && COMPLETE_TYPE_P (inner_type)
10832 2328 : && (need_default_ctor || need_copy_ctor
10833 1091 : || need_copy_assignment || need_dtor)
10834 2004 : && !type_dependent_expression_p (t)
10835 23737 : && cxx_omp_create_clause_info (c, inner_type, need_default_ctor,
10836 : need_copy_ctor, need_copy_assignment,
10837 : need_dtor))
10838 : remove = true;
10839 :
10840 21733 : if (!remove
10841 21733 : && c_kind == OMP_CLAUSE_SHARED
10842 2056 : && processing_template_decl)
10843 : {
10844 125 : t = omp_clause_decl_field (OMP_CLAUSE_DECL (c));
10845 125 : if (t)
10846 5 : OMP_CLAUSE_DECL (c) = t;
10847 : }
10848 :
10849 21733 : if (remove)
10850 292 : *pc = OMP_CLAUSE_CHAIN (c);
10851 : else
10852 21441 : pc = &OMP_CLAUSE_CHAIN (c);
10853 : }
10854 :
10855 63634 : if (allocate_seen)
10856 17449 : for (pc = &clauses, c = clauses; c ; c = *pc)
10857 : {
10858 14948 : bool remove = false;
10859 14948 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_ALLOCATE
10860 2764 : && !OMP_CLAUSE_ALLOCATE_COMBINED (c)
10861 2312 : && DECL_P (OMP_CLAUSE_DECL (c))
10862 17260 : && bitmap_bit_p (&aligned_head, DECL_UID (OMP_CLAUSE_DECL (c))))
10863 : {
10864 15 : error_at (OMP_CLAUSE_LOCATION (c),
10865 : "%qD specified in %<allocate%> clause but not in "
10866 15 : "an explicit privatization clause", OMP_CLAUSE_DECL (c));
10867 15 : remove = true;
10868 : }
10869 14948 : if (remove)
10870 15 : *pc = OMP_CLAUSE_CHAIN (c);
10871 : else
10872 14933 : pc = &OMP_CLAUSE_CHAIN (c);
10873 : }
10874 :
10875 63634 : if (ort == C_ORT_OMP_INTEROP
10876 63634 : && depend_clause
10877 60 : && (!init_use_destroy_seen
10878 57 : || (init_seen && init_no_targetsync_clause)))
10879 : {
10880 9 : auto_diagnostic_group d;
10881 9 : error_at (OMP_CLAUSE_LOCATION (depend_clause),
10882 : "%<depend%> clause requires action clauses with "
10883 : "%<targetsync%> interop-type");
10884 9 : if (init_no_targetsync_clause)
10885 6 : inform (OMP_CLAUSE_LOCATION (init_no_targetsync_clause),
10886 : "%<init%> clause lacks the %<targetsync%> modifier");
10887 9 : }
10888 :
10889 63634 : bitmap_obstack_release (NULL);
10890 63634 : return clauses;
10891 : }
10892 :
10893 : /* Start processing OpenMP clauses that can include any
10894 : privatization clauses for non-static data members. */
10895 :
10896 : tree
10897 49265 : push_omp_privatization_clauses (bool ignore_next)
10898 : {
10899 49265 : if (omp_private_member_ignore_next)
10900 : {
10901 722 : omp_private_member_ignore_next = ignore_next;
10902 722 : return NULL_TREE;
10903 : }
10904 48543 : omp_private_member_ignore_next = ignore_next;
10905 48543 : if (omp_private_member_map)
10906 24 : omp_private_member_vec.safe_push (error_mark_node);
10907 48543 : return push_stmt_list ();
10908 : }
10909 :
10910 : /* Revert remapping of any non-static data members since
10911 : the last push_omp_privatization_clauses () call. */
10912 :
10913 : void
10914 49259 : pop_omp_privatization_clauses (tree stmt)
10915 : {
10916 49259 : if (stmt == NULL_TREE)
10917 : return;
10918 48537 : stmt = pop_stmt_list (stmt);
10919 48537 : if (omp_private_member_map)
10920 : {
10921 1280 : while (!omp_private_member_vec.is_empty ())
10922 : {
10923 850 : tree t = omp_private_member_vec.pop ();
10924 850 : if (t == error_mark_node)
10925 : {
10926 24 : add_stmt (stmt);
10927 24 : return;
10928 : }
10929 826 : bool no_decl_expr = t == integer_zero_node;
10930 826 : if (no_decl_expr)
10931 136 : t = omp_private_member_vec.pop ();
10932 826 : tree *v = omp_private_member_map->get (t);
10933 826 : gcc_assert (v);
10934 826 : if (!no_decl_expr)
10935 690 : add_decl_expr (*v);
10936 826 : omp_private_member_map->remove (t);
10937 : }
10938 860 : delete omp_private_member_map;
10939 430 : omp_private_member_map = NULL;
10940 : }
10941 48513 : add_stmt (stmt);
10942 : }
10943 :
10944 : /* Remember OpenMP privatization clauses mapping and clear it.
10945 : Used for lambdas. */
10946 :
10947 : void
10948 16509676 : save_omp_privatization_clauses (vec<tree> &save)
10949 : {
10950 16509676 : save = vNULL;
10951 16509676 : if (omp_private_member_ignore_next)
10952 2 : save.safe_push (integer_one_node);
10953 16509676 : omp_private_member_ignore_next = false;
10954 16509676 : if (!omp_private_member_map)
10955 : return;
10956 :
10957 0 : while (!omp_private_member_vec.is_empty ())
10958 : {
10959 0 : tree t = omp_private_member_vec.pop ();
10960 0 : if (t == error_mark_node)
10961 : {
10962 0 : save.safe_push (t);
10963 0 : continue;
10964 : }
10965 0 : tree n = t;
10966 0 : if (t == integer_zero_node)
10967 0 : t = omp_private_member_vec.pop ();
10968 0 : tree *v = omp_private_member_map->get (t);
10969 0 : gcc_assert (v);
10970 0 : save.safe_push (*v);
10971 0 : save.safe_push (t);
10972 0 : if (n != t)
10973 0 : save.safe_push (n);
10974 : }
10975 0 : delete omp_private_member_map;
10976 0 : omp_private_member_map = NULL;
10977 : }
10978 :
10979 : /* Restore OpenMP privatization clauses mapping saved by the
10980 : above function. */
10981 :
10982 : void
10983 16509676 : restore_omp_privatization_clauses (vec<tree> &save)
10984 : {
10985 16509676 : gcc_assert (omp_private_member_vec.is_empty ());
10986 16509676 : omp_private_member_ignore_next = false;
10987 16509676 : if (save.is_empty ())
10988 : return;
10989 4 : if (save.length () == 1 && save[0] == integer_one_node)
10990 : {
10991 2 : omp_private_member_ignore_next = true;
10992 2 : save.release ();
10993 2 : return;
10994 : }
10995 :
10996 0 : omp_private_member_map = new hash_map <tree, tree>;
10997 0 : while (!save.is_empty ())
10998 : {
10999 0 : tree t = save.pop ();
11000 0 : tree n = t;
11001 0 : if (t != error_mark_node)
11002 : {
11003 0 : if (t == integer_one_node)
11004 : {
11005 0 : omp_private_member_ignore_next = true;
11006 0 : gcc_assert (save.is_empty ());
11007 0 : break;
11008 : }
11009 0 : if (t == integer_zero_node)
11010 0 : t = save.pop ();
11011 0 : tree &v = omp_private_member_map->get_or_insert (t);
11012 0 : v = save.pop ();
11013 : }
11014 0 : omp_private_member_vec.safe_push (t);
11015 0 : if (n != t)
11016 0 : omp_private_member_vec.safe_push (n);
11017 : }
11018 0 : save.release ();
11019 : }
11020 :
11021 : /* For all variables in the tree_list VARS, mark them as thread local. */
11022 :
11023 : void
11024 244 : finish_omp_threadprivate (tree vars)
11025 : {
11026 244 : tree t;
11027 :
11028 : /* Mark every variable in VARS to be assigned thread local storage. */
11029 521 : for (t = vars; t; t = TREE_CHAIN (t))
11030 : {
11031 277 : tree v = TREE_PURPOSE (t);
11032 277 : location_t loc = EXPR_LOCATION (TREE_VALUE (t));
11033 :
11034 277 : if (error_operand_p (v))
11035 : ;
11036 277 : else if (!VAR_P (v))
11037 6 : error_at (loc, "%<threadprivate%> %qD is not file, namespace "
11038 : "or block scope variable", v);
11039 : /* If V had already been marked threadprivate, it doesn't matter
11040 : whether it had been used prior to this point. */
11041 271 : else if (TREE_USED (v)
11042 271 : && (DECL_LANG_SPECIFIC (v) == NULL
11043 3 : || !CP_DECL_THREADPRIVATE_P (v)))
11044 6 : error_at (loc, "%qE declared %<threadprivate%> after first use", v);
11045 265 : else if (! TREE_STATIC (v) && ! DECL_EXTERNAL (v))
11046 6 : error_at (loc, "automatic variable %qE cannot be %<threadprivate%>", v);
11047 259 : else if (! COMPLETE_TYPE_P (complete_type (TREE_TYPE (v))))
11048 3 : error_at (loc, "%<threadprivate%> %qE has incomplete type", v);
11049 207 : else if (TREE_STATIC (v) && TYPE_P (CP_DECL_CONTEXT (v))
11050 279 : && CP_DECL_CONTEXT (v) != current_class_type)
11051 6 : error_at (loc, "%<threadprivate%> %qE directive not "
11052 6 : "in %qT definition", v, CP_DECL_CONTEXT (v));
11053 : else
11054 : {
11055 : /* Allocate a LANG_SPECIFIC structure for V, if needed. */
11056 250 : if (DECL_LANG_SPECIFIC (v) == NULL)
11057 206 : retrofit_lang_decl (v);
11058 :
11059 250 : if (! CP_DECL_THREAD_LOCAL_P (v))
11060 : {
11061 250 : CP_DECL_THREAD_LOCAL_P (v) = true;
11062 250 : set_decl_tls_model (v, decl_default_tls_model (v));
11063 : /* If rtl has been already set for this var, call
11064 : make_decl_rtl once again, so that encode_section_info
11065 : has a chance to look at the new decl flags. */
11066 250 : if (DECL_RTL_SET_P (v))
11067 0 : make_decl_rtl (v);
11068 : }
11069 250 : CP_DECL_THREADPRIVATE_P (v) = 1;
11070 : }
11071 : }
11072 244 : }
11073 :
11074 : /* Build an OpenMP structured block. */
11075 :
11076 : tree
11077 64779 : begin_omp_structured_block (void)
11078 : {
11079 64779 : return do_pushlevel (sk_omp);
11080 : }
11081 :
11082 : tree
11083 64764 : finish_omp_structured_block (tree block)
11084 : {
11085 64764 : return do_poplevel (block);
11086 : }
11087 :
11088 : /* Similarly, except force the retention of the BLOCK. */
11089 :
11090 : tree
11091 14970 : begin_omp_parallel (void)
11092 : {
11093 14970 : keep_next_level (true);
11094 14970 : return begin_omp_structured_block ();
11095 : }
11096 :
11097 : /* Generate OACC_DATA, with CLAUSES and BLOCK as its compound
11098 : statement. */
11099 :
11100 : tree
11101 768 : finish_oacc_data (tree clauses, tree block)
11102 : {
11103 768 : tree stmt;
11104 :
11105 768 : block = finish_omp_structured_block (block);
11106 :
11107 768 : stmt = make_node (OACC_DATA);
11108 768 : TREE_TYPE (stmt) = void_type_node;
11109 768 : OACC_DATA_CLAUSES (stmt) = clauses;
11110 768 : OACC_DATA_BODY (stmt) = block;
11111 :
11112 768 : return add_stmt (stmt);
11113 : }
11114 :
11115 : /* Generate OACC_HOST_DATA, with CLAUSES and BLOCK as its compound
11116 : statement. */
11117 :
11118 : tree
11119 55 : finish_oacc_host_data (tree clauses, tree block)
11120 : {
11121 55 : tree stmt;
11122 :
11123 55 : block = finish_omp_structured_block (block);
11124 :
11125 55 : stmt = make_node (OACC_HOST_DATA);
11126 55 : TREE_TYPE (stmt) = void_type_node;
11127 55 : OACC_HOST_DATA_CLAUSES (stmt) = clauses;
11128 55 : OACC_HOST_DATA_BODY (stmt) = block;
11129 :
11130 55 : return add_stmt (stmt);
11131 : }
11132 :
11133 : /* Generate OMP construct CODE, with BODY and CLAUSES as its compound
11134 : statement. */
11135 :
11136 : tree
11137 4689 : finish_omp_construct (enum tree_code code, tree body, tree clauses)
11138 : {
11139 4689 : body = finish_omp_structured_block (body);
11140 :
11141 4689 : tree stmt = make_node (code);
11142 4689 : TREE_TYPE (stmt) = void_type_node;
11143 4689 : OMP_BODY (stmt) = body;
11144 4689 : OMP_CLAUSES (stmt) = clauses;
11145 :
11146 4689 : return add_stmt (stmt);
11147 : }
11148 :
11149 : /* Used to walk OpenMP target directive body. */
11150 :
11151 : struct omp_target_walk_data
11152 : {
11153 : /* Holds the 'this' expression found in current function. */
11154 : tree current_object;
11155 :
11156 : /* True if the 'this' expression was accessed in the target body. */
11157 : bool this_expr_accessed;
11158 :
11159 : /* For non-static functions, record which pointer-typed members were
11160 : accessed, and the whole expression. */
11161 : hash_map<tree, tree> ptr_members_accessed;
11162 :
11163 : /* Record which lambda objects were accessed in target body. */
11164 : hash_set<tree> lambda_objects_accessed;
11165 :
11166 : /* For lambda functions, the __closure object expression of the current
11167 : function, and the set of captured variables accessed in target body. */
11168 : tree current_closure;
11169 : hash_set<tree> closure_vars_accessed;
11170 :
11171 : /* Local variables declared inside a BIND_EXPR, used to filter out such
11172 : variables when recording lambda_objects_accessed. */
11173 : hash_set<tree> local_decls;
11174 :
11175 : omp_mapper_list<tree> *mappers;
11176 : };
11177 :
11178 : /* Helper function of finish_omp_target_clauses, called via
11179 : cp_walk_tree_without_duplicates. Traverse body of OpenMP target
11180 : directive *TP, and fill out omp_target_walk_data passed in *PTR. */
11181 :
11182 : static tree
11183 229266 : finish_omp_target_clauses_r (tree *tp, int *walk_subtrees, void *ptr)
11184 : {
11185 229266 : tree t = *tp;
11186 229266 : struct omp_target_walk_data *data = (struct omp_target_walk_data *) ptr;
11187 229266 : tree current_object = data->current_object;
11188 229266 : tree current_closure = data->current_closure;
11189 229266 : omp_mapper_list<tree> *mlist = data->mappers;
11190 :
11191 : /* References inside of these expression codes shouldn't incur any
11192 : form of mapping, so return early. */
11193 229266 : if (TREE_CODE (t) == SIZEOF_EXPR
11194 229258 : || TREE_CODE (t) == ALIGNOF_EXPR)
11195 : {
11196 8 : *walk_subtrees = 0;
11197 8 : return NULL_TREE;
11198 : }
11199 :
11200 229258 : if (TREE_CODE (t) == OMP_CLAUSE)
11201 : return NULL_TREE;
11202 :
11203 216660 : if (!processing_template_decl)
11204 : {
11205 216660 : tree aggr_type = NULL_TREE;
11206 :
11207 216660 : if (TREE_CODE (t) == COMPONENT_REF
11208 216660 : && RECORD_OR_UNION_TYPE_P (TREE_TYPE (TREE_OPERAND (t, 0))))
11209 2276 : aggr_type = TREE_TYPE (TREE_OPERAND (t, 0));
11210 214384 : else if ((TREE_CODE (t) == VAR_DECL
11211 : || TREE_CODE (t) == PARM_DECL
11212 : || TREE_CODE (t) == RESULT_DECL)
11213 17046 : && RECORD_OR_UNION_TYPE_P (TREE_TYPE (t)))
11214 1249 : aggr_type = TREE_TYPE (t);
11215 :
11216 3525 : if (aggr_type)
11217 : {
11218 3525 : tree mapper_fn = cxx_omp_mapper_lookup (NULL_TREE, aggr_type);
11219 3525 : if (mapper_fn)
11220 199 : mlist->add_mapper (NULL_TREE, aggr_type, mapper_fn);
11221 : }
11222 : }
11223 :
11224 216660 : if (current_object)
11225 : {
11226 2565 : tree this_expr = TREE_OPERAND (current_object, 0);
11227 :
11228 2565 : if (operand_equal_p (t, this_expr))
11229 : {
11230 35 : data->this_expr_accessed = true;
11231 35 : *walk_subtrees = 0;
11232 35 : return NULL_TREE;
11233 : }
11234 :
11235 2530 : if (TREE_CODE (t) == COMPONENT_REF
11236 115 : && POINTER_TYPE_P (TREE_TYPE (t))
11237 36 : && operand_equal_p (TREE_OPERAND (t, 0), current_object)
11238 2564 : && TREE_CODE (TREE_OPERAND (t, 1)) == FIELD_DECL)
11239 : {
11240 34 : data->this_expr_accessed = true;
11241 34 : tree fld = TREE_OPERAND (t, 1);
11242 34 : if (data->ptr_members_accessed.get (fld) == NULL)
11243 : {
11244 14 : if (TREE_CODE (TREE_TYPE (t)) == REFERENCE_TYPE)
11245 4 : t = convert_from_reference (t);
11246 14 : data->ptr_members_accessed.put (fld, t);
11247 : }
11248 34 : *walk_subtrees = 0;
11249 34 : return NULL_TREE;
11250 : }
11251 : }
11252 :
11253 : /* When the current_function_decl is a lambda function, the closure object
11254 : argument's type seems to not yet have fields laid out, so a recording
11255 : of DECL_VALUE_EXPRs during the target body walk seems the only way to
11256 : find them. */
11257 216591 : if (current_closure
11258 301 : && (VAR_P (t)
11259 : || TREE_CODE (t) == PARM_DECL
11260 : || TREE_CODE (t) == RESULT_DECL)
11261 24 : && DECL_HAS_VALUE_EXPR_P (t)
11262 10 : && TREE_CODE (DECL_VALUE_EXPR (t)) == COMPONENT_REF
11263 216601 : && operand_equal_p (current_closure,
11264 10 : TREE_OPERAND (DECL_VALUE_EXPR (t), 0)))
11265 : {
11266 9 : if (!data->closure_vars_accessed.contains (t))
11267 9 : data->closure_vars_accessed.add (t);
11268 9 : *walk_subtrees = 0;
11269 9 : return NULL_TREE;
11270 : }
11271 :
11272 216582 : if (TREE_CODE (t) == BIND_EXPR)
11273 : {
11274 20035 : if (tree block = BIND_EXPR_BLOCK (t))
11275 22495 : for (tree var = BLOCK_VARS (block); var; var = DECL_CHAIN (var))
11276 2464 : if ((VAR_P (var)
11277 : || TREE_CODE (var) == PARM_DECL
11278 : || TREE_CODE (var) == RESULT_DECL)
11279 2424 : && !data->local_decls.contains (var))
11280 2424 : data->local_decls.add (var);
11281 : return NULL_TREE;
11282 : }
11283 :
11284 : /* Note, this really should be done during gimplification using
11285 : a target hook instead, as a magic declare mapper for the lambda
11286 : types. */
11287 196547 : if (tree lt = TREE_TYPE (t))
11288 189910 : if (LAMBDA_TYPE_P (lt))
11289 : {
11290 118 : gcc_assert (CLASS_TYPE_P (lt));
11291 :
11292 118 : if (location_wrapper_p (t))
11293 : /* The wrapped DECL gets handled when walking its operand. */
11294 0 : return NULL_TREE;
11295 :
11296 118 : if (TREE_CODE (t) == TARGET_EXPR
11297 118 : && !data->local_decls.contains (TARGET_EXPR_SLOT (t)))
11298 21 : data->local_decls.add (TARGET_EXPR_SLOT (t));
11299 :
11300 118 : tree b = t;
11301 118 : while (TREE_CODE (b) == COMPONENT_REF
11302 : /* Note, this isn't fully correct. We can handle it
11303 : this way for constant index, or when it is e.g.
11304 : a value of firstprivatized variable, but we can't
11305 : do that if something in the index expression is
11306 : local to the target region. */
11307 143 : || TREE_CODE (b) == ARRAY_REF)
11308 25 : b = TREE_OPERAND (b, 0);
11309 118 : STRIP_ANY_LOCATION_WRAPPER (b);
11310 118 : if ((VAR_P (b)
11311 : || TREE_CODE (b) == PARM_DECL
11312 : || TREE_CODE (b) == RESULT_DECL)
11313 48 : && !data->lambda_objects_accessed.contains (t)
11314 : /* Do not prepare to create target maps for locally declared
11315 : lambdas or anonymous ones. */
11316 48 : && !data->local_decls.contains (b))
11317 18 : data->lambda_objects_accessed.add (t);
11318 : }
11319 :
11320 : return NULL_TREE;
11321 : }
11322 :
11323 : /* Helper function for finish_omp_target, and also from tsubst_expr.
11324 : Create additional clauses for mapping of non-static members, lambda objects,
11325 : etc. */
11326 :
11327 : void
11328 6981 : finish_omp_target_clauses (location_t loc, tree body, tree *clauses_ptr)
11329 : {
11330 6981 : omp_target_walk_data data;
11331 6981 : data.this_expr_accessed = false;
11332 6981 : data.current_object = NULL_TREE;
11333 :
11334 6981 : if (DECL_NONSTATIC_MEMBER_P (current_function_decl) && current_class_ptr)
11335 96 : if (tree ct = current_nonlambda_class_type ())
11336 : {
11337 95 : tree object = maybe_dummy_object (ct, NULL);
11338 95 : object = maybe_resolve_dummy (object, true);
11339 95 : data.current_object = object;
11340 : }
11341 :
11342 6981 : if (DECL_LAMBDA_FUNCTION_P (current_function_decl))
11343 : {
11344 8 : tree closure = DECL_ARGUMENTS (current_function_decl);
11345 8 : data.current_closure = build_indirect_ref (loc, closure, RO_UNARY_STAR);
11346 : }
11347 : else
11348 : data.current_closure = NULL_TREE;
11349 :
11350 6981 : auto_vec<tree, 16> new_clauses;
11351 :
11352 6981 : if (!processing_template_decl)
11353 : {
11354 6981 : hash_set<omp_name_type<tree> > seen_types;
11355 6981 : auto_vec<tree> mapper_fns;
11356 6981 : omp_mapper_list<tree> mlist (&seen_types, &mapper_fns);
11357 6981 : data.mappers = &mlist;
11358 :
11359 6981 : cp_walk_tree_without_duplicates (&body, finish_omp_target_clauses_r,
11360 : &data);
11361 :
11362 6981 : unsigned int i;
11363 6981 : tree mapper_fn;
11364 14055 : FOR_EACH_VEC_ELT (mapper_fns, i, mapper_fn)
11365 93 : c_omp_find_nested_mappers (&mlist, mapper_fn);
11366 :
11367 7144 : FOR_EACH_VEC_ELT (mapper_fns, i, mapper_fn)
11368 : {
11369 93 : tree mapper = cxx_omp_extract_mapper_directive (mapper_fn);
11370 93 : if (mapper == error_mark_node)
11371 0 : continue;
11372 93 : tree mapper_name = OMP_DECLARE_MAPPER_ID (mapper);
11373 93 : tree decl = OMP_DECLARE_MAPPER_DECL (mapper);
11374 93 : if (BASELINK_P (mapper_fn))
11375 0 : mapper_fn = BASELINK_FUNCTIONS (mapper_fn);
11376 :
11377 93 : tree c = build_omp_clause (loc, OMP_CLAUSE__MAPPER_BINDING_);
11378 93 : OMP_CLAUSE__MAPPER_BINDING__ID (c) = mapper_name;
11379 93 : OMP_CLAUSE__MAPPER_BINDING__DECL (c) = decl;
11380 93 : OMP_CLAUSE__MAPPER_BINDING__MAPPER (c) = mapper_fn;
11381 :
11382 93 : new_clauses.safe_push (c);
11383 : }
11384 6981 : }
11385 : else
11386 : {
11387 0 : data.mappers = NULL;
11388 0 : cp_walk_tree_without_duplicates (&body, finish_omp_target_clauses_r,
11389 : &data);
11390 : }
11391 :
11392 6981 : tree omp_target_this_expr = NULL_TREE;
11393 6981 : tree *explicit_this_deref_map = NULL;
11394 6981 : if (data.this_expr_accessed)
11395 : {
11396 31 : omp_target_this_expr = TREE_OPERAND (data.current_object, 0);
11397 :
11398 : /* See if explicit user-specified map(this[:]) clause already exists.
11399 : If not, we create an implicit map(tofrom:this[:1]) clause. */
11400 80 : for (tree *cp = clauses_ptr; *cp; cp = &OMP_CLAUSE_CHAIN (*cp))
11401 50 : if (OMP_CLAUSE_CODE (*cp) == OMP_CLAUSE_MAP
11402 47 : && (TREE_CODE (OMP_CLAUSE_DECL (*cp)) == INDIRECT_REF
11403 40 : || TREE_CODE (OMP_CLAUSE_DECL (*cp)) == MEM_REF)
11404 57 : && operand_equal_p (TREE_OPERAND (OMP_CLAUSE_DECL (*cp), 0),
11405 : omp_target_this_expr))
11406 : {
11407 : explicit_this_deref_map = cp;
11408 : break;
11409 : }
11410 : }
11411 :
11412 6981 : if (DECL_LAMBDA_FUNCTION_P (current_function_decl)
11413 6981 : && (data.this_expr_accessed
11414 1 : || !data.closure_vars_accessed.is_empty ()))
11415 : {
11416 : /* For lambda functions, we need to first create a copy of the
11417 : __closure object. */
11418 8 : tree closure = DECL_ARGUMENTS (current_function_decl);
11419 8 : tree c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11420 8 : OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_TO);
11421 8 : OMP_CLAUSE_DECL (c)
11422 8 : = build_indirect_ref (loc, closure, RO_UNARY_STAR);
11423 8 : OMP_CLAUSE_SIZE (c)
11424 8 : = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (closure)));
11425 8 : new_clauses.safe_push (c);
11426 :
11427 8 : tree closure_obj = OMP_CLAUSE_DECL (c);
11428 8 : tree closure_type = TREE_TYPE (closure_obj);
11429 :
11430 16 : gcc_assert (LAMBDA_TYPE_P (closure_type)
11431 : && CLASS_TYPE_P (closure_type));
11432 :
11433 8 : tree c2 = build_omp_clause (loc, OMP_CLAUSE_MAP);
11434 8 : OMP_CLAUSE_SET_MAP_KIND (c2, GOMP_MAP_FIRSTPRIVATE_POINTER);
11435 8 : OMP_CLAUSE_DECL (c2) = closure;
11436 8 : OMP_CLAUSE_SIZE (c2) = size_zero_node;
11437 8 : new_clauses.safe_push (c2);
11438 : }
11439 :
11440 6981 : if (data.this_expr_accessed)
11441 : {
11442 : /* If the this-expr was accessed, create a map(*this) clause. */
11443 31 : enum gomp_map_kind kind = GOMP_MAP_TOFROM;
11444 31 : if (explicit_this_deref_map)
11445 : {
11446 1 : tree this_map = *explicit_this_deref_map;
11447 1 : tree nc = OMP_CLAUSE_CHAIN (this_map);
11448 2 : gcc_assert (nc != NULL_TREE
11449 : && OMP_CLAUSE_CODE (nc) == OMP_CLAUSE_MAP
11450 : && (OMP_CLAUSE_MAP_KIND (nc)
11451 : == GOMP_MAP_FIRSTPRIVATE_POINTER));
11452 1 : kind = OMP_CLAUSE_MAP_KIND (this_map);
11453 : /* Remove the original 'map(*this) map(firstprivate_ptr:this)'
11454 : two-map sequence away from the chain. */
11455 1 : *explicit_this_deref_map = OMP_CLAUSE_CHAIN (nc);
11456 : }
11457 31 : tree c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11458 31 : OMP_CLAUSE_SET_MAP_KIND (c, kind);
11459 31 : OMP_CLAUSE_DECL (c)
11460 31 : = build_indirect_ref (loc, omp_target_this_expr, RO_UNARY_STAR);
11461 31 : OMP_CLAUSE_SIZE (c)
11462 31 : = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (omp_target_this_expr)));
11463 31 : new_clauses.safe_push (c);
11464 :
11465 : /* If we're in a lambda function, the this-pointer will actually be
11466 : '__closure->this', a mapped member of __closure, hence always_pointer.
11467 : Otherwise it's a firstprivate pointer. */
11468 31 : enum gomp_map_kind ptr_kind
11469 31 : = (DECL_LAMBDA_FUNCTION_P (current_function_decl)
11470 31 : ? GOMP_MAP_ALWAYS_POINTER
11471 24 : : GOMP_MAP_FIRSTPRIVATE_POINTER);
11472 31 : c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11473 31 : OMP_CLAUSE_SET_MAP_KIND (c, ptr_kind);
11474 31 : OMP_CLAUSE_DECL (c) = omp_target_this_expr;
11475 31 : OMP_CLAUSE_SIZE (c) = size_zero_node;
11476 31 : new_clauses.safe_push (c);
11477 : }
11478 :
11479 6981 : if (DECL_LAMBDA_FUNCTION_P (current_function_decl))
11480 : {
11481 8 : if (omp_target_this_expr)
11482 : {
11483 7 : STRIP_NOPS (omp_target_this_expr);
11484 7 : gcc_assert (DECL_HAS_VALUE_EXPR_P (omp_target_this_expr));
11485 7 : omp_target_this_expr = DECL_VALUE_EXPR (omp_target_this_expr);
11486 : }
11487 :
11488 17 : for (hash_set<tree>::iterator i = data.closure_vars_accessed.begin ();
11489 25 : i != data.closure_vars_accessed.end (); ++i)
11490 : {
11491 9 : tree orig_decl = *i;
11492 9 : tree closure_expr = DECL_VALUE_EXPR (orig_decl);
11493 :
11494 9 : if (TREE_CODE (TREE_TYPE (orig_decl)) == POINTER_TYPE
11495 9 : || TREE_CODE (TREE_TYPE (orig_decl)) == REFERENCE_TYPE)
11496 : {
11497 : /* this-pointer is processed above, outside this loop. */
11498 3 : if (omp_target_this_expr
11499 3 : && operand_equal_p (closure_expr, omp_target_this_expr))
11500 0 : continue;
11501 :
11502 3 : bool ptr_p = TREE_CODE (TREE_TYPE (orig_decl)) == POINTER_TYPE;
11503 3 : enum gomp_map_kind kind, ptr_kind, nc_kind;
11504 3 : tree size;
11505 :
11506 3 : if (ptr_p)
11507 : {
11508 : /* For pointers, default mapped as zero-length array
11509 : section. */
11510 2 : kind = GOMP_MAP_ALLOC;
11511 2 : nc_kind = GOMP_MAP_FIRSTPRIVATE_POINTER;
11512 2 : ptr_kind = GOMP_MAP_ATTACH_ZERO_LENGTH_ARRAY_SECTION;
11513 2 : size = size_zero_node;
11514 : }
11515 : else
11516 : {
11517 : /* For references, default mapped as appearing on map
11518 : clause. */
11519 1 : kind = GOMP_MAP_TOFROM;
11520 1 : nc_kind = GOMP_MAP_FIRSTPRIVATE_REFERENCE;
11521 1 : ptr_kind = GOMP_MAP_ALWAYS_POINTER;
11522 1 : size = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (closure_expr)));
11523 : }
11524 :
11525 6 : for (tree *p = clauses_ptr; *p; p = &OMP_CLAUSE_CHAIN (*p))
11526 3 : if (OMP_CLAUSE_CODE (*p) == OMP_CLAUSE_MAP
11527 1 : && (TREE_CODE (OMP_CLAUSE_DECL (*p)) == INDIRECT_REF
11528 1 : || TREE_CODE (OMP_CLAUSE_DECL (*p)) == MEM_REF)
11529 3 : && operand_equal_p (TREE_OPERAND (OMP_CLAUSE_DECL (*p), 0),
11530 : orig_decl))
11531 : {
11532 : /* If this was already specified by user as a map,
11533 : save the user specified map kind, delete the
11534 : "map(*ptr/ref), map(firstprivate ptr/ref)" sequence,
11535 : and insert our own sequence:
11536 : "map(*__closure->ptr/ref), map(<ptr_kind>:__closure->ref"
11537 : */
11538 0 : tree nc = OMP_CLAUSE_CHAIN (*p);
11539 0 : gcc_assert (nc != NULL_TREE
11540 : && OMP_CLAUSE_CODE (nc) == OMP_CLAUSE_MAP
11541 : && OMP_CLAUSE_MAP_KIND (nc) == nc_kind);
11542 : /* Update with user specified kind and size. */
11543 0 : kind = OMP_CLAUSE_MAP_KIND (*p);
11544 0 : size = OMP_CLAUSE_SIZE (*p);
11545 0 : *p = OMP_CLAUSE_CHAIN (nc);
11546 0 : break;
11547 : }
11548 :
11549 3 : tree c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11550 3 : OMP_CLAUSE_SET_MAP_KIND (c, kind);
11551 3 : OMP_CLAUSE_DECL (c)
11552 3 : = build_indirect_ref (loc, closure_expr, RO_UNARY_STAR);
11553 3 : OMP_CLAUSE_SIZE (c) = size;
11554 3 : if (ptr_p)
11555 2 : OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (c) = 1;
11556 3 : new_clauses.safe_push (c);
11557 :
11558 3 : c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11559 3 : OMP_CLAUSE_SET_MAP_KIND (c, ptr_kind);
11560 3 : OMP_CLAUSE_DECL (c) = closure_expr;
11561 3 : OMP_CLAUSE_SIZE (c) = size_zero_node;
11562 3 : new_clauses.safe_push (c);
11563 : }
11564 : }
11565 : }
11566 :
11567 6981 : if (!data.ptr_members_accessed.is_empty ())
11568 14 : for (hash_map<tree, tree>::iterator i = data.ptr_members_accessed.begin ();
11569 42 : i != data.ptr_members_accessed.end (); ++i)
11570 : {
11571 : /* For each referenced member that is of pointer or reference-to-pointer
11572 : type, create the equivalent of map(alloc:this->ptr[:0]). */
11573 14 : tree field_decl = (*i).first;
11574 14 : tree ptr_member = (*i).second;
11575 :
11576 26 : for (tree c = *clauses_ptr; c; c = OMP_CLAUSE_CHAIN (c))
11577 : {
11578 16 : if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP)
11579 2 : continue;
11580 : /* If map(this->ptr[:N]) already exists, avoid creating another
11581 : such map. */
11582 14 : tree decl = OMP_CLAUSE_DECL (c);
11583 14 : if ((TREE_CODE (decl) == INDIRECT_REF
11584 10 : || TREE_CODE (decl) == MEM_REF)
11585 14 : && operand_equal_p (TREE_OPERAND (decl, 0), ptr_member))
11586 4 : goto next_ptr_member;
11587 : }
11588 :
11589 10 : if (!cxx_mark_addressable (ptr_member))
11590 0 : gcc_unreachable ();
11591 :
11592 10 : if (TREE_CODE (TREE_TYPE (field_decl)) == REFERENCE_TYPE)
11593 : {
11594 : /* For reference to pointers, we need to map the referenced
11595 : pointer first for things to be correct. */
11596 4 : tree ptr_member_type = TREE_TYPE (ptr_member);
11597 :
11598 : /* Map pointer target as zero-length array section. */
11599 4 : tree c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11600 4 : OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_ALLOC);
11601 4 : OMP_CLAUSE_DECL (c)
11602 4 : = build1 (INDIRECT_REF, TREE_TYPE (ptr_member_type), ptr_member);
11603 4 : OMP_CLAUSE_SIZE (c) = size_zero_node;
11604 4 : OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (c) = 1;
11605 :
11606 : /* Map pointer to zero-length array section. */
11607 4 : tree c2 = build_omp_clause (loc, OMP_CLAUSE_MAP);
11608 4 : OMP_CLAUSE_SET_MAP_KIND
11609 : (c2, GOMP_MAP_POINTER_TO_ZERO_LENGTH_ARRAY_SECTION);
11610 4 : OMP_CLAUSE_DECL (c2) = ptr_member;
11611 4 : OMP_CLAUSE_SIZE (c2) = size_zero_node;
11612 :
11613 : /* Attach reference-to-pointer field to pointer. */
11614 4 : tree c3 = build_omp_clause (loc, OMP_CLAUSE_MAP);
11615 4 : OMP_CLAUSE_SET_MAP_KIND (c3, GOMP_MAP_ATTACH);
11616 4 : OMP_CLAUSE_DECL (c3) = TREE_OPERAND (ptr_member, 0);
11617 4 : OMP_CLAUSE_SIZE (c3) = size_zero_node;
11618 :
11619 4 : new_clauses.safe_push (c);
11620 4 : new_clauses.safe_push (c2);
11621 4 : new_clauses.safe_push (c3);
11622 : }
11623 6 : else if (TREE_CODE (TREE_TYPE (field_decl)) == POINTER_TYPE)
11624 : {
11625 : /* Map pointer target as zero-length array section. */
11626 6 : tree c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11627 6 : OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_ALLOC);
11628 6 : OMP_CLAUSE_DECL (c) = build_indirect_ref (loc, ptr_member,
11629 : RO_UNARY_STAR);
11630 6 : OMP_CLAUSE_SIZE (c) = size_zero_node;
11631 6 : OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (c) = 1;
11632 :
11633 : /* Attach zero-length array section to pointer. */
11634 6 : tree c2 = build_omp_clause (loc, OMP_CLAUSE_MAP);
11635 6 : OMP_CLAUSE_SET_MAP_KIND
11636 : (c2, GOMP_MAP_ATTACH_ZERO_LENGTH_ARRAY_SECTION);
11637 6 : OMP_CLAUSE_DECL (c2) = ptr_member;
11638 6 : OMP_CLAUSE_SIZE (c2) = size_zero_node;
11639 :
11640 6 : new_clauses.safe_push (c);
11641 6 : new_clauses.safe_push (c2);
11642 : }
11643 : else
11644 0 : gcc_unreachable ();
11645 :
11646 14 : next_ptr_member:
11647 14 : ;
11648 : }
11649 :
11650 6999 : for (hash_set<tree>::iterator i = data.lambda_objects_accessed.begin ();
11651 6999 : i != data.lambda_objects_accessed.end (); ++i)
11652 : {
11653 18 : tree lobj = *i;
11654 18 : if (TREE_CODE (lobj) == TARGET_EXPR)
11655 0 : lobj = TARGET_EXPR_SLOT (lobj);
11656 :
11657 18 : tree lt = TREE_TYPE (lobj);
11658 36 : gcc_assert (LAMBDA_TYPE_P (lt) && CLASS_TYPE_P (lt));
11659 :
11660 18 : tree lc = build_omp_clause (loc, OMP_CLAUSE_MAP);
11661 18 : OMP_CLAUSE_SET_MAP_KIND (lc, GOMP_MAP_TO);
11662 18 : OMP_CLAUSE_DECL (lc) = lobj;
11663 18 : OMP_CLAUSE_SIZE (lc) = TYPE_SIZE_UNIT (lt);
11664 18 : new_clauses.safe_push (lc);
11665 :
11666 274 : for (tree fld = TYPE_FIELDS (lt); fld; fld = DECL_CHAIN (fld))
11667 : {
11668 256 : if (TREE_CODE (TREE_TYPE (fld)) == POINTER_TYPE)
11669 : {
11670 4 : tree exp = build3 (COMPONENT_REF, TREE_TYPE (fld),
11671 : lobj, fld, NULL_TREE);
11672 4 : tree c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11673 4 : OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_ALLOC);
11674 4 : OMP_CLAUSE_DECL (c)
11675 4 : = build_indirect_ref (loc, exp, RO_UNARY_STAR);
11676 4 : OMP_CLAUSE_SIZE (c) = size_zero_node;
11677 4 : OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (c) = 1;
11678 4 : new_clauses.safe_push (c);
11679 :
11680 4 : c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11681 4 : OMP_CLAUSE_SET_MAP_KIND
11682 : (c, GOMP_MAP_ATTACH_ZERO_LENGTH_ARRAY_SECTION);
11683 4 : OMP_CLAUSE_DECL (c) = exp;
11684 4 : OMP_CLAUSE_SIZE (c) = size_zero_node;
11685 4 : new_clauses.safe_push (c);
11686 : }
11687 252 : else if (TREE_CODE (TREE_TYPE (fld)) == REFERENCE_TYPE)
11688 : {
11689 14 : tree exp = build3 (COMPONENT_REF, TREE_TYPE (fld),
11690 : lobj, fld, NULL_TREE);
11691 14 : tree c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11692 14 : OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_TOFROM);
11693 14 : OMP_CLAUSE_DECL (c)
11694 14 : = build1 (INDIRECT_REF, TREE_TYPE (TREE_TYPE (exp)), exp);
11695 14 : OMP_CLAUSE_SIZE (c)
11696 14 : = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (exp)));
11697 14 : new_clauses.safe_push (c);
11698 :
11699 14 : c = build_omp_clause (loc, OMP_CLAUSE_MAP);
11700 14 : OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_ALWAYS_POINTER);
11701 14 : OMP_CLAUSE_DECL (c) = exp;
11702 14 : OMP_CLAUSE_SIZE (c) = size_zero_node;
11703 14 : new_clauses.safe_push (c);
11704 : }
11705 : }
11706 : }
11707 :
11708 6981 : tree c = *clauses_ptr;
11709 14217 : for (int i = new_clauses.length () - 1; i >= 0; i--)
11710 : {
11711 255 : OMP_CLAUSE_CHAIN (new_clauses[i]) = c;
11712 255 : c = new_clauses[i];
11713 : }
11714 6981 : *clauses_ptr = c;
11715 6981 : }
11716 :
11717 : /* Called from cp_parser_omp_target. Create additional implicit clauses for
11718 : OpenMP target directives, and do sanity checks. */
11719 :
11720 : tree
11721 6971 : finish_omp_target (location_t loc, tree clauses, tree body, bool combined_p)
11722 : {
11723 6971 : if (!processing_template_decl)
11724 6165 : finish_omp_target_clauses (loc, body, &clauses);
11725 :
11726 6971 : tree stmt = make_node (OMP_TARGET);
11727 6971 : TREE_TYPE (stmt) = void_type_node;
11728 6971 : OMP_TARGET_CLAUSES (stmt) = clauses;
11729 6971 : OMP_TARGET_BODY (stmt) = body;
11730 6971 : OMP_TARGET_COMBINED (stmt) = combined_p;
11731 6971 : SET_EXPR_LOCATION (stmt, loc);
11732 :
11733 6971 : tree c = clauses;
11734 16792 : while (c)
11735 : {
11736 9821 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP)
11737 5724 : switch (OMP_CLAUSE_MAP_KIND (c))
11738 : {
11739 : case GOMP_MAP_TO:
11740 : case GOMP_MAP_ALWAYS_TO:
11741 : case GOMP_MAP_PRESENT_TO:
11742 : case GOMP_MAP_ALWAYS_PRESENT_TO:
11743 : case GOMP_MAP_FROM:
11744 : case GOMP_MAP_ALWAYS_FROM:
11745 : case GOMP_MAP_PRESENT_FROM:
11746 : case GOMP_MAP_ALWAYS_PRESENT_FROM:
11747 : case GOMP_MAP_TOFROM:
11748 : case GOMP_MAP_ALWAYS_TOFROM:
11749 : case GOMP_MAP_PRESENT_TOFROM:
11750 : case GOMP_MAP_ALWAYS_PRESENT_TOFROM:
11751 : case GOMP_MAP_ALLOC:
11752 : case GOMP_MAP_PRESENT_ALLOC:
11753 : case GOMP_MAP_FIRSTPRIVATE_POINTER:
11754 : case GOMP_MAP_FIRSTPRIVATE_REFERENCE:
11755 : case GOMP_MAP_ALWAYS_POINTER:
11756 : case GOMP_MAP_ATTACH_DETACH:
11757 : case GOMP_MAP_ATTACH:
11758 : case GOMP_MAP_ATTACH_ZERO_LENGTH_ARRAY_SECTION:
11759 : case GOMP_MAP_POINTER:
11760 : case GOMP_MAP_POINTER_TO_ZERO_LENGTH_ARRAY_SECTION:
11761 : break;
11762 3 : default:
11763 3 : error_at (OMP_CLAUSE_LOCATION (c),
11764 : "%<#pragma omp target%> with map-type other "
11765 : "than %<to%>, %<from%>, %<tofrom%> or %<alloc%> "
11766 : "on %<map%> clause");
11767 3 : break;
11768 : }
11769 9821 : c = OMP_CLAUSE_CHAIN (c);
11770 : }
11771 6971 : return add_stmt (stmt);
11772 : }
11773 :
11774 : tree
11775 9458 : finish_omp_parallel (tree clauses, tree body)
11776 : {
11777 9458 : tree stmt;
11778 :
11779 9458 : body = finish_omp_structured_block (body);
11780 :
11781 9458 : stmt = make_node (OMP_PARALLEL);
11782 9458 : TREE_TYPE (stmt) = void_type_node;
11783 9458 : OMP_PARALLEL_CLAUSES (stmt) = clauses;
11784 9458 : OMP_PARALLEL_BODY (stmt) = body;
11785 :
11786 9458 : return add_stmt (stmt);
11787 : }
11788 :
11789 : tree
11790 2411 : begin_omp_task (void)
11791 : {
11792 2411 : keep_next_level (true);
11793 2411 : return begin_omp_structured_block ();
11794 : }
11795 :
11796 : tree
11797 2411 : finish_omp_task (tree clauses, tree body)
11798 : {
11799 2411 : tree stmt;
11800 :
11801 2411 : body = finish_omp_structured_block (body);
11802 :
11803 2411 : stmt = make_node (OMP_TASK);
11804 2411 : TREE_TYPE (stmt) = void_type_node;
11805 2411 : OMP_TASK_CLAUSES (stmt) = clauses;
11806 2411 : OMP_TASK_BODY (stmt) = body;
11807 :
11808 2411 : return add_stmt (stmt);
11809 : }
11810 :
11811 : /* Helper function for finish_omp_for. Convert Ith random access iterator
11812 : into integral iterator. Return FALSE if successful. */
11813 :
11814 : static bool
11815 813 : handle_omp_for_class_iterator (int i, location_t locus, enum tree_code code,
11816 : tree declv, tree orig_declv, tree initv,
11817 : tree condv, tree incrv, tree *body,
11818 : tree *pre_body, tree &clauses,
11819 : int collapse, int ordered)
11820 : {
11821 813 : tree diff, iter_init, iter_incr = NULL, last;
11822 813 : tree incr_var = NULL, orig_pre_body, orig_body, c;
11823 813 : tree decl = TREE_VEC_ELT (declv, i);
11824 813 : tree init = TREE_VEC_ELT (initv, i);
11825 813 : tree cond = TREE_VEC_ELT (condv, i);
11826 813 : tree incr = TREE_VEC_ELT (incrv, i);
11827 813 : tree iter = decl;
11828 813 : location_t elocus = locus;
11829 :
11830 813 : if (init && EXPR_HAS_LOCATION (init))
11831 12 : elocus = EXPR_LOCATION (init);
11832 :
11833 813 : switch (TREE_CODE (cond))
11834 : {
11835 810 : case GT_EXPR:
11836 810 : case GE_EXPR:
11837 810 : case LT_EXPR:
11838 810 : case LE_EXPR:
11839 810 : case NE_EXPR:
11840 810 : if (TREE_OPERAND (cond, 1) == iter)
11841 42 : cond = build2 (swap_tree_comparison (TREE_CODE (cond)),
11842 42 : TREE_TYPE (cond), iter, TREE_OPERAND (cond, 0));
11843 810 : if (TREE_OPERAND (cond, 0) != iter)
11844 0 : cond = error_mark_node;
11845 : else
11846 : {
11847 810 : tree tem = build_x_binary_op (EXPR_LOCATION (cond),
11848 810 : TREE_CODE (cond),
11849 : iter, ERROR_MARK,
11850 810 : TREE_OPERAND (cond, 1), ERROR_MARK,
11851 : NULL_TREE, NULL, tf_warning_or_error);
11852 810 : if (error_operand_p (tem))
11853 : return true;
11854 : }
11855 : break;
11856 3 : default:
11857 3 : cond = error_mark_node;
11858 3 : break;
11859 : }
11860 810 : if (cond == error_mark_node)
11861 : {
11862 3 : error_at (elocus, "invalid controlling predicate");
11863 3 : return true;
11864 : }
11865 807 : diff = build_x_binary_op (elocus, MINUS_EXPR,
11866 807 : TREE_OPERAND (cond, 1), ERROR_MARK,
11867 : iter, ERROR_MARK,
11868 : NULL_TREE, NULL, tf_warning_or_error);
11869 807 : diff = cp_fully_fold (diff);
11870 807 : if (error_operand_p (diff))
11871 : return true;
11872 807 : if (TREE_CODE (TREE_TYPE (diff)) != INTEGER_TYPE)
11873 : {
11874 0 : error_at (elocus, "difference between %qE and %qD does not have integer type",
11875 0 : TREE_OPERAND (cond, 1), iter);
11876 0 : return true;
11877 : }
11878 807 : if (!c_omp_check_loop_iv_exprs (locus, code, orig_declv, i,
11879 807 : TREE_VEC_ELT (declv, i), NULL_TREE,
11880 : cond, cp_walk_subtrees))
11881 : return true;
11882 :
11883 762 : switch (TREE_CODE (incr))
11884 : {
11885 370 : case PREINCREMENT_EXPR:
11886 370 : case PREDECREMENT_EXPR:
11887 370 : case POSTINCREMENT_EXPR:
11888 370 : case POSTDECREMENT_EXPR:
11889 370 : if (TREE_OPERAND (incr, 0) != iter)
11890 : {
11891 0 : incr = error_mark_node;
11892 0 : break;
11893 : }
11894 370 : iter_incr = build_x_unary_op (EXPR_LOCATION (incr),
11895 370 : TREE_CODE (incr), iter,
11896 : NULL_TREE, tf_warning_or_error);
11897 370 : if (error_operand_p (iter_incr))
11898 : return true;
11899 370 : else if (TREE_CODE (incr) == PREINCREMENT_EXPR
11900 219 : || TREE_CODE (incr) == POSTINCREMENT_EXPR)
11901 299 : incr = integer_one_node;
11902 : else
11903 71 : incr = integer_minus_one_node;
11904 : break;
11905 392 : case MODIFY_EXPR:
11906 392 : if (TREE_OPERAND (incr, 0) != iter)
11907 0 : incr = error_mark_node;
11908 392 : else if (TREE_CODE (TREE_OPERAND (incr, 1)) == PLUS_EXPR
11909 392 : || TREE_CODE (TREE_OPERAND (incr, 1)) == MINUS_EXPR)
11910 : {
11911 392 : tree rhs = TREE_OPERAND (incr, 1);
11912 392 : if (TREE_OPERAND (rhs, 0) == iter)
11913 : {
11914 299 : if (TREE_CODE (TREE_TYPE (TREE_OPERAND (rhs, 1)))
11915 : != INTEGER_TYPE)
11916 0 : incr = error_mark_node;
11917 : else
11918 : {
11919 299 : iter_incr = build_x_modify_expr (EXPR_LOCATION (rhs),
11920 299 : iter, TREE_CODE (rhs),
11921 299 : TREE_OPERAND (rhs, 1),
11922 : NULL_TREE,
11923 : tf_warning_or_error);
11924 299 : if (error_operand_p (iter_incr))
11925 : return true;
11926 299 : incr = TREE_OPERAND (rhs, 1);
11927 299 : incr = cp_convert (TREE_TYPE (diff), incr,
11928 : tf_warning_or_error);
11929 299 : if (TREE_CODE (rhs) == MINUS_EXPR)
11930 : {
11931 16 : incr = build1 (NEGATE_EXPR, TREE_TYPE (diff), incr);
11932 16 : incr = fold_simple (incr);
11933 : }
11934 299 : if (TREE_CODE (incr) != INTEGER_CST
11935 299 : && (TREE_CODE (incr) != NOP_EXPR
11936 66 : || (TREE_CODE (TREE_OPERAND (incr, 0))
11937 : != INTEGER_CST)))
11938 : iter_incr = NULL;
11939 : }
11940 : }
11941 93 : else if (TREE_OPERAND (rhs, 1) == iter)
11942 : {
11943 93 : if (TREE_CODE (TREE_TYPE (TREE_OPERAND (rhs, 0))) != INTEGER_TYPE
11944 93 : || TREE_CODE (rhs) != PLUS_EXPR)
11945 0 : incr = error_mark_node;
11946 : else
11947 : {
11948 93 : iter_incr = build_x_binary_op (EXPR_LOCATION (rhs),
11949 : PLUS_EXPR,
11950 93 : TREE_OPERAND (rhs, 0),
11951 : ERROR_MARK, iter,
11952 : ERROR_MARK, NULL_TREE, NULL,
11953 : tf_warning_or_error);
11954 93 : if (error_operand_p (iter_incr))
11955 : return true;
11956 93 : iter_incr = build_x_modify_expr (EXPR_LOCATION (rhs),
11957 : iter, NOP_EXPR,
11958 : iter_incr, NULL_TREE,
11959 : tf_warning_or_error);
11960 93 : if (error_operand_p (iter_incr))
11961 : return true;
11962 93 : incr = TREE_OPERAND (rhs, 0);
11963 93 : iter_incr = NULL;
11964 : }
11965 : }
11966 : else
11967 0 : incr = error_mark_node;
11968 : }
11969 : else
11970 0 : incr = error_mark_node;
11971 : break;
11972 0 : default:
11973 0 : incr = error_mark_node;
11974 0 : break;
11975 : }
11976 :
11977 762 : if (incr == error_mark_node)
11978 : {
11979 0 : error_at (elocus, "invalid increment expression");
11980 0 : return true;
11981 : }
11982 :
11983 762 : incr = cp_convert (TREE_TYPE (diff), incr, tf_warning_or_error);
11984 762 : incr = cp_fully_fold (incr);
11985 762 : tree loop_iv_seen = NULL_TREE;
11986 1735 : for (c = clauses; c ; c = OMP_CLAUSE_CHAIN (c))
11987 1093 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
11988 1093 : && OMP_CLAUSE_DECL (c) == iter)
11989 : {
11990 120 : if (code == OMP_TASKLOOP || code == OMP_LOOP)
11991 : {
11992 60 : loop_iv_seen = c;
11993 60 : OMP_CLAUSE_LASTPRIVATE_LOOP_IV (c) = 1;
11994 : }
11995 : break;
11996 : }
11997 973 : else if ((code == OMP_TASKLOOP || code == OMP_LOOP)
11998 113 : && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_PRIVATE
11999 1007 : && OMP_CLAUSE_DECL (c) == iter)
12000 : {
12001 30 : loop_iv_seen = c;
12002 30 : if (code == OMP_TASKLOOP)
12003 25 : OMP_CLAUSE_PRIVATE_TASKLOOP_IV (c) = 1;
12004 : }
12005 :
12006 762 : decl = create_temporary_var (TREE_TYPE (diff));
12007 762 : pushdecl (decl);
12008 762 : add_decl_expr (decl);
12009 762 : last = create_temporary_var (TREE_TYPE (diff));
12010 762 : pushdecl (last);
12011 762 : add_decl_expr (last);
12012 762 : if (c && iter_incr == NULL && TREE_CODE (incr) != INTEGER_CST
12013 10 : && (!ordered || (i < collapse && collapse > 1)))
12014 : {
12015 10 : incr_var = create_temporary_var (TREE_TYPE (diff));
12016 10 : pushdecl (incr_var);
12017 10 : add_decl_expr (incr_var);
12018 : }
12019 762 : gcc_assert (stmts_are_full_exprs_p ());
12020 762 : tree diffvar = NULL_TREE;
12021 762 : if (code == OMP_TASKLOOP)
12022 : {
12023 101 : if (!loop_iv_seen)
12024 : {
12025 38 : tree ivc = build_omp_clause (locus, OMP_CLAUSE_FIRSTPRIVATE);
12026 38 : OMP_CLAUSE_DECL (ivc) = iter;
12027 38 : cxx_omp_finish_clause (ivc, NULL, false);
12028 38 : OMP_CLAUSE_CHAIN (ivc) = clauses;
12029 38 : clauses = ivc;
12030 : }
12031 101 : tree lvc = build_omp_clause (locus, OMP_CLAUSE_FIRSTPRIVATE);
12032 101 : OMP_CLAUSE_DECL (lvc) = last;
12033 101 : OMP_CLAUSE_CHAIN (lvc) = clauses;
12034 101 : clauses = lvc;
12035 101 : diffvar = create_temporary_var (TREE_TYPE (diff));
12036 101 : pushdecl (diffvar);
12037 101 : add_decl_expr (diffvar);
12038 : }
12039 661 : else if (code == OMP_LOOP)
12040 : {
12041 43 : if (!loop_iv_seen)
12042 : {
12043 : /* While iterators on the loop construct are predetermined
12044 : lastprivate, if the decl is not declared inside of the
12045 : loop, OMP_CLAUSE_LASTPRIVATE should have been added
12046 : already. */
12047 16 : loop_iv_seen = build_omp_clause (locus, OMP_CLAUSE_FIRSTPRIVATE);
12048 16 : OMP_CLAUSE_DECL (loop_iv_seen) = iter;
12049 16 : OMP_CLAUSE_CHAIN (loop_iv_seen) = clauses;
12050 16 : clauses = loop_iv_seen;
12051 : }
12052 27 : else if (OMP_CLAUSE_CODE (loop_iv_seen) == OMP_CLAUSE_PRIVATE)
12053 : {
12054 5 : OMP_CLAUSE_PRIVATE_DEBUG (loop_iv_seen) = 0;
12055 5 : OMP_CLAUSE_PRIVATE_OUTER_REF (loop_iv_seen) = 0;
12056 5 : OMP_CLAUSE_CODE (loop_iv_seen) = OMP_CLAUSE_FIRSTPRIVATE;
12057 : }
12058 43 : if (OMP_CLAUSE_CODE (loop_iv_seen) == OMP_CLAUSE_FIRSTPRIVATE)
12059 21 : cxx_omp_finish_clause (loop_iv_seen, NULL, false);
12060 : }
12061 :
12062 762 : orig_pre_body = *pre_body;
12063 762 : *pre_body = push_stmt_list ();
12064 762 : if (orig_pre_body)
12065 610 : add_stmt (orig_pre_body);
12066 762 : if (init != NULL)
12067 61 : finish_expr_stmt (build_x_modify_expr (elocus,
12068 : iter, NOP_EXPR, init,
12069 : NULL_TREE, tf_warning_or_error));
12070 762 : init = build_int_cst (TREE_TYPE (diff), 0);
12071 762 : if (c && iter_incr == NULL
12072 28 : && (!ordered || (i < collapse && collapse > 1)))
12073 : {
12074 28 : if (incr_var)
12075 : {
12076 10 : finish_expr_stmt (build_x_modify_expr (elocus,
12077 : incr_var, NOP_EXPR,
12078 : incr, NULL_TREE,
12079 : tf_warning_or_error));
12080 10 : incr = incr_var;
12081 : }
12082 28 : iter_incr = build_x_modify_expr (elocus,
12083 : iter, PLUS_EXPR, incr,
12084 : NULL_TREE, tf_warning_or_error);
12085 : }
12086 762 : if (c && ordered && i < collapse && collapse > 1)
12087 762 : iter_incr = incr;
12088 762 : finish_expr_stmt (build_x_modify_expr (elocus,
12089 : last, NOP_EXPR, init,
12090 : NULL_TREE, tf_warning_or_error));
12091 762 : if (diffvar)
12092 : {
12093 101 : finish_expr_stmt (build_x_modify_expr (elocus,
12094 : diffvar, NOP_EXPR,
12095 : diff, NULL_TREE, tf_warning_or_error));
12096 101 : diff = diffvar;
12097 : }
12098 762 : *pre_body = pop_stmt_list (*pre_body);
12099 :
12100 1524 : cond = cp_build_binary_op (elocus,
12101 762 : TREE_CODE (cond), decl, diff,
12102 : tf_warning_or_error);
12103 762 : incr = build_modify_expr (elocus, decl, NULL_TREE, PLUS_EXPR,
12104 : elocus, incr, NULL_TREE);
12105 :
12106 762 : orig_body = *body;
12107 762 : *body = push_stmt_list ();
12108 762 : iter_init = build2 (MINUS_EXPR, TREE_TYPE (diff), decl, last);
12109 762 : iter_init = build_x_modify_expr (elocus,
12110 : iter, PLUS_EXPR, iter_init,
12111 : NULL_TREE, tf_warning_or_error);
12112 762 : if (iter_init != error_mark_node)
12113 759 : iter_init = build1 (NOP_EXPR, void_type_node, iter_init);
12114 762 : finish_expr_stmt (iter_init);
12115 762 : finish_expr_stmt (build_x_modify_expr (elocus,
12116 : last, NOP_EXPR, decl,
12117 : NULL_TREE, tf_warning_or_error));
12118 762 : add_stmt (orig_body);
12119 762 : *body = pop_stmt_list (*body);
12120 :
12121 762 : if (c)
12122 : {
12123 120 : OMP_CLAUSE_LASTPRIVATE_STMT (c) = push_stmt_list ();
12124 120 : if (!ordered)
12125 114 : finish_expr_stmt (iter_incr);
12126 : else
12127 : {
12128 6 : iter_init = decl;
12129 6 : if (i < collapse && collapse > 1 && !error_operand_p (iter_incr))
12130 2 : iter_init = build2 (PLUS_EXPR, TREE_TYPE (diff),
12131 : iter_init, iter_incr);
12132 6 : iter_init = build2 (MINUS_EXPR, TREE_TYPE (diff), iter_init, last);
12133 6 : iter_init = build_x_modify_expr (elocus,
12134 : iter, PLUS_EXPR, iter_init,
12135 : NULL_TREE, tf_warning_or_error);
12136 6 : if (iter_init != error_mark_node)
12137 6 : iter_init = build1 (NOP_EXPR, void_type_node, iter_init);
12138 6 : finish_expr_stmt (iter_init);
12139 : }
12140 120 : OMP_CLAUSE_LASTPRIVATE_STMT (c)
12141 240 : = pop_stmt_list (OMP_CLAUSE_LASTPRIVATE_STMT (c));
12142 : }
12143 :
12144 762 : if (TREE_CODE (TREE_VEC_ELT (orig_declv, i)) == TREE_LIST)
12145 : {
12146 116 : tree t = TREE_VEC_ELT (orig_declv, i);
12147 116 : gcc_assert (TREE_PURPOSE (t) == NULL_TREE
12148 : && TREE_VALUE (t) == NULL_TREE
12149 : && TREE_CODE (TREE_CHAIN (t)) == TREE_VEC);
12150 116 : TREE_PURPOSE (t) = TREE_VEC_ELT (declv, i);
12151 116 : TREE_VALUE (t) = last;
12152 : }
12153 : else
12154 646 : TREE_VEC_ELT (orig_declv, i)
12155 1292 : = tree_cons (TREE_VEC_ELT (declv, i), last, NULL_TREE);
12156 762 : TREE_VEC_ELT (declv, i) = decl;
12157 762 : TREE_VEC_ELT (initv, i) = init;
12158 762 : TREE_VEC_ELT (condv, i) = cond;
12159 762 : TREE_VEC_ELT (incrv, i) = incr;
12160 :
12161 762 : return false;
12162 : }
12163 :
12164 : /* Build and validate an OMP_FOR statement. CLAUSES, BODY, COND, INCR
12165 : are directly for their associated operands in the statement. DECL
12166 : and INIT are a combo; if DECL is NULL then INIT ought to be a
12167 : MODIFY_EXPR, and the DECL should be extracted. PRE_BODY are
12168 : optional statements that need to go before the loop into its
12169 : sk_omp scope. */
12170 :
12171 : tree
12172 21288 : finish_omp_for (location_t locus, enum tree_code code, tree declv,
12173 : tree orig_declv, tree initv, tree condv, tree incrv,
12174 : tree body, tree pre_body, vec<tree> *orig_inits, tree clauses)
12175 : {
12176 21288 : tree omp_for = NULL, orig_incr = NULL;
12177 21288 : tree decl = NULL, init, cond, incr;
12178 21288 : location_t elocus;
12179 21288 : int i;
12180 21288 : int collapse = 1;
12181 21288 : int ordered = 0;
12182 21288 : auto_vec<location_t> init_locv;
12183 :
12184 21288 : gcc_assert (TREE_VEC_LENGTH (declv) == TREE_VEC_LENGTH (initv));
12185 21288 : gcc_assert (TREE_VEC_LENGTH (declv) == TREE_VEC_LENGTH (condv));
12186 21288 : gcc_assert (TREE_VEC_LENGTH (declv) == TREE_VEC_LENGTH (incrv));
12187 21288 : if (TREE_VEC_LENGTH (declv) > 1)
12188 : {
12189 4054 : if (tree ti = omp_find_clause (clauses, OMP_CLAUSE_TILE))
12190 83 : collapse = list_length (OMP_CLAUSE_TILE_LIST (ti));
12191 : else
12192 : {
12193 3971 : if (tree co = omp_find_clause (clauses, OMP_CLAUSE_COLLAPSE))
12194 3501 : collapse = tree_to_shwi (OMP_CLAUSE_COLLAPSE_EXPR (co));
12195 470 : else if (tree si = omp_find_clause (clauses, OMP_CLAUSE_SIZES))
12196 394 : collapse = list_length (OMP_CLAUSE_SIZES_LIST (si));
12197 3971 : if (collapse != TREE_VEC_LENGTH (declv))
12198 100 : ordered = TREE_VEC_LENGTH (declv);
12199 : }
12200 : }
12201 48921 : for (i = 0; i < TREE_VEC_LENGTH (declv); i++)
12202 : {
12203 27669 : decl = TREE_VEC_ELT (declv, i);
12204 27669 : init = TREE_VEC_ELT (initv, i);
12205 27669 : cond = TREE_VEC_ELT (condv, i);
12206 27669 : incr = TREE_VEC_ELT (incrv, i);
12207 27669 : elocus = locus;
12208 :
12209 27669 : if (decl == global_namespace)
12210 : {
12211 1101 : gcc_assert (init == NULL_TREE && cond == NULL_TREE && incr == NULL_TREE);
12212 1101 : TREE_VEC_ELT (declv, i) = NULL_TREE;
12213 1101 : init_locv.safe_push (UNKNOWN_LOCATION);
12214 1101 : continue;
12215 : }
12216 : /* We are going to throw out the init's original MODIFY_EXPR or
12217 : MODOP_EXPR below. Save its location so we can use it when
12218 : reconstructing the expression farther down. Alternatively, if the
12219 : initializer is a binding of the iteration variable, save
12220 : that location. Any of these locations in the initialization clause
12221 : for the current nested loop are better than using the argument locus,
12222 : that points to the "for" of the outermost loop in the nest. */
12223 26568 : if (init && EXPR_HAS_LOCATION (init))
12224 17962 : elocus = EXPR_LOCATION (init);
12225 8606 : else if (decl && INDIRECT_REF_P (decl) && EXPR_HAS_LOCATION (decl))
12226 : /* This can happen for class iterators. */
12227 0 : elocus = EXPR_LOCATION (decl);
12228 8606 : else if (decl && DECL_P (decl))
12229 : {
12230 8579 : if (DECL_SOURCE_LOCATION (decl) != UNKNOWN_LOCATION)
12231 8579 : elocus = DECL_SOURCE_LOCATION (decl);
12232 0 : else if (DECL_INITIAL (decl)
12233 0 : && EXPR_HAS_LOCATION (DECL_INITIAL (decl)))
12234 0 : elocus = EXPR_LOCATION (DECL_INITIAL (decl));
12235 : }
12236 26568 : init_locv.safe_push (elocus);
12237 :
12238 26568 : if (decl == NULL)
12239 : {
12240 16654 : if (init != NULL)
12241 16651 : switch (TREE_CODE (init))
12242 : {
12243 16244 : case MODIFY_EXPR:
12244 16244 : decl = TREE_OPERAND (init, 0);
12245 16244 : init = TREE_OPERAND (init, 1);
12246 16244 : break;
12247 389 : case MODOP_EXPR:
12248 389 : if (TREE_CODE (TREE_OPERAND (init, 1)) == NOP_EXPR)
12249 : {
12250 389 : decl = TREE_OPERAND (init, 0);
12251 389 : init = TREE_OPERAND (init, 2);
12252 : }
12253 : break;
12254 : default:
12255 : break;
12256 : }
12257 :
12258 16654 : if (decl == NULL)
12259 : {
12260 21 : error_at (locus,
12261 : "expected iteration declaration or initialization");
12262 21 : return NULL;
12263 : }
12264 : }
12265 :
12266 26547 : if (cond == global_namespace)
12267 170 : continue;
12268 :
12269 26377 : if (cond == NULL)
12270 : {
12271 9 : error_at (elocus, "missing controlling predicate");
12272 9 : return NULL;
12273 : }
12274 :
12275 26368 : if (incr == NULL)
12276 : {
12277 6 : error_at (elocus, "missing increment expression");
12278 6 : return NULL;
12279 : }
12280 :
12281 26362 : TREE_VEC_ELT (declv, i) = decl;
12282 26362 : TREE_VEC_ELT (initv, i) = init;
12283 : }
12284 :
12285 21252 : if (orig_inits)
12286 : {
12287 : bool fail = false;
12288 : tree orig_init;
12289 21352 : FOR_EACH_VEC_ELT (*orig_inits, i, orig_init)
12290 1181 : if (orig_init
12291 3396 : && !c_omp_check_loop_iv_exprs (locus, code,
12292 : orig_declv ? orig_declv : declv, i,
12293 1164 : TREE_VEC_ELT (declv, i), orig_init,
12294 : NULL_TREE, cp_walk_subtrees))
12295 : fail = true;
12296 20171 : if (fail)
12297 21288 : return NULL;
12298 : }
12299 :
12300 21195 : if (dependent_omp_for_p (declv, initv, condv, incrv, body))
12301 : {
12302 453 : tree stmt;
12303 :
12304 453 : stmt = make_node (code);
12305 :
12306 1499 : for (i = 0; i < TREE_VEC_LENGTH (declv); i++)
12307 : {
12308 593 : if (TREE_VEC_ELT (declv, i) == NULL_TREE)
12309 9 : continue;
12310 : /* This is really just a place-holder. We'll be decomposing this
12311 : again and going through the cp_build_modify_expr path below when
12312 : we instantiate the thing. */
12313 584 : TREE_VEC_ELT (initv, i)
12314 1168 : = build2_loc (init_locv[i], MODIFY_EXPR, void_type_node,
12315 584 : TREE_VEC_ELT (declv, i), TREE_VEC_ELT (initv, i));
12316 : }
12317 :
12318 453 : TREE_TYPE (stmt) = void_type_node;
12319 453 : OMP_FOR_INIT (stmt) = initv;
12320 453 : OMP_FOR_COND (stmt) = condv;
12321 453 : OMP_FOR_INCR (stmt) = incrv;
12322 453 : OMP_FOR_BODY (stmt) = body;
12323 453 : OMP_FOR_PRE_BODY (stmt) = pre_body;
12324 453 : OMP_FOR_CLAUSES (stmt) = clauses;
12325 :
12326 453 : SET_EXPR_LOCATION (stmt, locus);
12327 453 : return add_stmt (stmt);
12328 : }
12329 :
12330 20742 : if (!orig_declv)
12331 19933 : orig_declv = copy_node (declv);
12332 :
12333 20742 : if (processing_template_decl)
12334 634 : orig_incr = make_tree_vec (TREE_VEC_LENGTH (incrv));
12335 :
12336 48350 : for (i = 0; i < TREE_VEC_LENGTH (declv); )
12337 : {
12338 27700 : decl = TREE_VEC_ELT (declv, i);
12339 27700 : init = TREE_VEC_ELT (initv, i);
12340 27700 : cond = TREE_VEC_ELT (condv, i);
12341 27700 : incr = TREE_VEC_ELT (incrv, i);
12342 27700 : if (orig_incr)
12343 866 : TREE_VEC_ELT (orig_incr, i) = incr;
12344 27700 : elocus = init_locv[i];
12345 :
12346 27700 : if (decl == NULL_TREE)
12347 : {
12348 1092 : i++;
12349 1092 : continue;
12350 : }
12351 :
12352 26608 : if (!DECL_P (decl))
12353 : {
12354 6 : error_at (elocus, "expected iteration declaration or initialization");
12355 6 : return NULL;
12356 : }
12357 :
12358 26602 : if (incr && TREE_CODE (incr) == MODOP_EXPR)
12359 : {
12360 1 : if (orig_incr)
12361 1 : TREE_VEC_ELT (orig_incr, i) = incr;
12362 1 : incr = cp_build_modify_expr (elocus, TREE_OPERAND (incr, 0),
12363 1 : TREE_CODE (TREE_OPERAND (incr, 1)),
12364 1 : TREE_OPERAND (incr, 2),
12365 : tf_warning_or_error);
12366 : }
12367 :
12368 26602 : if (CLASS_TYPE_P (TREE_TYPE (decl)))
12369 : {
12370 825 : if (code == OMP_SIMD)
12371 : {
12372 12 : error_at (elocus, "%<#pragma omp simd%> used with class "
12373 : "iteration variable %qE", decl);
12374 12 : return NULL;
12375 : }
12376 813 : if (handle_omp_for_class_iterator (i, locus, code, declv, orig_declv,
12377 : initv, condv, incrv, &body,
12378 : &pre_body, clauses,
12379 : collapse, ordered))
12380 : return NULL;
12381 762 : continue;
12382 : }
12383 :
12384 51554 : if (!INTEGRAL_TYPE_P (TREE_TYPE (decl))
12385 27363 : && !TYPE_PTR_P (TREE_TYPE (decl)))
12386 : {
12387 14 : error_at (elocus, "invalid type for iteration variable %qE", decl);
12388 14 : return NULL;
12389 : }
12390 :
12391 25763 : if (!processing_template_decl && TREE_CODE (init) != TREE_VEC)
12392 24980 : init = cp_build_modify_expr (elocus, decl, NOP_EXPR, init,
12393 : tf_warning_or_error);
12394 : else
12395 783 : init = build2_loc (elocus, MODIFY_EXPR, void_type_node, decl, init);
12396 25763 : if (decl == error_mark_node || init == error_mark_node)
12397 : return NULL;
12398 :
12399 25754 : TREE_VEC_ELT (declv, i) = decl;
12400 25754 : TREE_VEC_ELT (initv, i) = init;
12401 25754 : TREE_VEC_ELT (condv, i) = cond;
12402 25754 : TREE_VEC_ELT (incrv, i) = incr;
12403 25754 : i++;
12404 : }
12405 :
12406 20650 : if (pre_body && IS_EMPTY_STMT (pre_body))
12407 0 : pre_body = NULL;
12408 :
12409 41300 : omp_for = c_finish_omp_for (locus, code, declv, orig_declv, initv, condv,
12410 : incrv, body, pre_body,
12411 20650 : !processing_template_decl);
12412 :
12413 : /* Check for iterators appearing in lb, b or incr expressions. */
12414 20650 : if (omp_for && !c_omp_check_loop_iv (omp_for, orig_declv, cp_walk_subtrees))
12415 : omp_for = NULL_TREE;
12416 :
12417 20164 : if (omp_for == NULL)
12418 : return NULL;
12419 :
12420 19948 : add_stmt (omp_for);
12421 :
12422 65716 : for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INCR (omp_for)); i++)
12423 : {
12424 25820 : init = TREE_VEC_ELT (OMP_FOR_INIT (omp_for), i);
12425 25820 : if (init == NULL_TREE)
12426 1032 : continue;
12427 24788 : decl = TREE_OPERAND (init, 0);
12428 24788 : cond = TREE_VEC_ELT (OMP_FOR_COND (omp_for), i);
12429 24788 : incr = TREE_VEC_ELT (OMP_FOR_INCR (omp_for), i);
12430 :
12431 24788 : if (!processing_template_decl)
12432 : {
12433 24245 : if (TREE_CODE (TREE_OPERAND (init, 1)) == TREE_VEC)
12434 : {
12435 106 : tree t = TREE_VEC_ELT (TREE_OPERAND (init, 1), 1);
12436 106 : TREE_VEC_ELT (TREE_OPERAND (init, 1), 1)
12437 106 : = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
12438 106 : t = TREE_VEC_ELT (TREE_OPERAND (init, 1), 2);
12439 106 : TREE_VEC_ELT (TREE_OPERAND (init, 1), 2)
12440 212 : = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
12441 : }
12442 : else
12443 : {
12444 24139 : tree t = TREE_OPERAND (init, 1);
12445 24139 : TREE_OPERAND (init, 1)
12446 48278 : = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
12447 : }
12448 24245 : if (TREE_CODE (TREE_OPERAND (cond, 1)) == TREE_VEC)
12449 : {
12450 121 : tree t = TREE_VEC_ELT (TREE_OPERAND (cond, 1), 1);
12451 121 : TREE_VEC_ELT (TREE_OPERAND (cond, 1), 1)
12452 121 : = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
12453 121 : t = TREE_VEC_ELT (TREE_OPERAND (cond, 1), 2);
12454 121 : TREE_VEC_ELT (TREE_OPERAND (cond, 1), 2)
12455 242 : = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
12456 : }
12457 : else
12458 : {
12459 24124 : tree t = TREE_OPERAND (cond, 1);
12460 24124 : TREE_OPERAND (cond, 1)
12461 48248 : = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
12462 : }
12463 : }
12464 :
12465 24788 : if (TREE_CODE (incr) != MODIFY_EXPR)
12466 18583 : continue;
12467 :
12468 6205 : if (TREE_SIDE_EFFECTS (TREE_OPERAND (incr, 1))
12469 70 : && BINARY_CLASS_P (TREE_OPERAND (incr, 1))
12470 6275 : && !processing_template_decl)
12471 : {
12472 64 : tree t = TREE_OPERAND (TREE_OPERAND (incr, 1), 0);
12473 64 : if (TREE_SIDE_EFFECTS (t)
12474 8 : && t != decl
12475 70 : && (TREE_CODE (t) != NOP_EXPR
12476 0 : || TREE_OPERAND (t, 0) != decl))
12477 6 : TREE_OPERAND (TREE_OPERAND (incr, 1), 0)
12478 12 : = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
12479 :
12480 64 : t = TREE_OPERAND (TREE_OPERAND (incr, 1), 1);
12481 64 : if (TREE_SIDE_EFFECTS (t)
12482 56 : && t != decl
12483 120 : && (TREE_CODE (t) != NOP_EXPR
12484 5 : || TREE_OPERAND (t, 0) != decl))
12485 56 : TREE_OPERAND (TREE_OPERAND (incr, 1), 1)
12486 112 : = fold_build_cleanup_point_expr (TREE_TYPE (t), t);
12487 : }
12488 :
12489 6205 : if (orig_incr)
12490 177 : TREE_VEC_ELT (OMP_FOR_INCR (omp_for), i) = TREE_VEC_ELT (orig_incr, i);
12491 : }
12492 19948 : OMP_FOR_CLAUSES (omp_for) = clauses;
12493 :
12494 : /* For simd loops with non-static data member iterators, we could have added
12495 : OMP_CLAUSE_LINEAR clauses without OMP_CLAUSE_LINEAR_STEP. As we know the
12496 : step at this point, fill it in. */
12497 4783 : if (code == OMP_SIMD && !processing_template_decl
12498 24687 : && TREE_VEC_LENGTH (OMP_FOR_INCR (omp_for)) == 1)
12499 4667 : for (tree c = omp_find_clause (clauses, OMP_CLAUSE_LINEAR); c;
12500 561 : c = omp_find_clause (OMP_CLAUSE_CHAIN (c), OMP_CLAUSE_LINEAR))
12501 561 : if (OMP_CLAUSE_LINEAR_STEP (c) == NULL_TREE)
12502 : {
12503 4 : decl = TREE_OPERAND (TREE_VEC_ELT (OMP_FOR_INIT (omp_for), 0), 0);
12504 4 : gcc_assert (decl == OMP_CLAUSE_DECL (c));
12505 4 : incr = TREE_VEC_ELT (OMP_FOR_INCR (omp_for), 0);
12506 4 : tree step, stept;
12507 4 : switch (TREE_CODE (incr))
12508 : {
12509 0 : case PREINCREMENT_EXPR:
12510 0 : case POSTINCREMENT_EXPR:
12511 : /* c_omp_for_incr_canonicalize_ptr() should have been
12512 : called to massage things appropriately. */
12513 0 : gcc_assert (!INDIRECT_TYPE_P (TREE_TYPE (decl)));
12514 0 : OMP_CLAUSE_LINEAR_STEP (c) = build_int_cst (TREE_TYPE (decl), 1);
12515 0 : break;
12516 0 : case PREDECREMENT_EXPR:
12517 0 : case POSTDECREMENT_EXPR:
12518 : /* c_omp_for_incr_canonicalize_ptr() should have been
12519 : called to massage things appropriately. */
12520 0 : gcc_assert (!INDIRECT_TYPE_P (TREE_TYPE (decl)));
12521 0 : OMP_CLAUSE_LINEAR_STEP (c)
12522 0 : = build_int_cst (TREE_TYPE (decl), -1);
12523 0 : break;
12524 4 : case MODIFY_EXPR:
12525 4 : gcc_assert (TREE_OPERAND (incr, 0) == decl);
12526 4 : incr = TREE_OPERAND (incr, 1);
12527 4 : switch (TREE_CODE (incr))
12528 : {
12529 4 : case PLUS_EXPR:
12530 4 : if (TREE_OPERAND (incr, 1) == decl)
12531 0 : step = TREE_OPERAND (incr, 0);
12532 : else
12533 4 : step = TREE_OPERAND (incr, 1);
12534 : break;
12535 0 : case MINUS_EXPR:
12536 0 : case POINTER_PLUS_EXPR:
12537 0 : gcc_assert (TREE_OPERAND (incr, 0) == decl);
12538 0 : step = TREE_OPERAND (incr, 1);
12539 0 : break;
12540 0 : default:
12541 0 : gcc_unreachable ();
12542 : }
12543 4 : stept = TREE_TYPE (decl);
12544 4 : if (INDIRECT_TYPE_P (stept))
12545 0 : stept = sizetype;
12546 4 : step = fold_convert (stept, step);
12547 4 : if (TREE_CODE (incr) == MINUS_EXPR)
12548 0 : step = fold_build1 (NEGATE_EXPR, stept, step);
12549 4 : OMP_CLAUSE_LINEAR_STEP (c) = step;
12550 4 : break;
12551 0 : default:
12552 0 : gcc_unreachable ();
12553 : }
12554 : }
12555 : /* Override saved methods on OMP_LOOP's OMP_CLAUSE_LASTPRIVATE_LOOP_IV
12556 : clauses, we need copy ctor for those rather than default ctor,
12557 : plus as for other lastprivates assignment op and dtor. */
12558 19948 : if (code == OMP_LOOP && !processing_template_decl)
12559 1993 : for (tree c = clauses; c; c = OMP_CLAUSE_CHAIN (c))
12560 1285 : if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
12561 204 : && OMP_CLAUSE_LASTPRIVATE_LOOP_IV (c)
12562 1307 : && cxx_omp_create_clause_info (c, TREE_TYPE (OMP_CLAUSE_DECL (c)),
12563 : false, true, true, true))
12564 0 : CP_OMP_CLAUSE_INFO (c) = NULL_TREE;
12565 :
12566 : return omp_for;
12567 21288 : }
12568 :
12569 : /* Code walker for finish_omp_for_block: extract binding of DP->var
12570 : from its current block and move it to a new BIND_EXPR DP->b
12571 : surrounding the body of DP->omp_for. */
12572 :
12573 : struct fofb_data {
12574 : tree var;
12575 : tree b;
12576 : tree omp_for;
12577 : };
12578 :
12579 : static tree
12580 389 : finish_omp_for_block_walker (tree *tp, int *walk_subtrees, void *dp)
12581 : {
12582 389 : struct fofb_data *fofb = (struct fofb_data *)dp;
12583 389 : if (TREE_CODE (*tp) == BIND_EXPR)
12584 578 : for (tree *p = &BIND_EXPR_VARS (*tp); *p; p = &DECL_CHAIN (*p))
12585 : {
12586 576 : if (*p == fofb->var)
12587 : {
12588 363 : *p = DECL_CHAIN (*p);
12589 363 : if (fofb->b == NULL_TREE)
12590 : {
12591 214 : fofb->b = make_node (BLOCK);
12592 214 : fofb->b = build3 (BIND_EXPR, void_type_node, NULL_TREE,
12593 214 : OMP_FOR_BODY (fofb->omp_for), fofb->b);
12594 214 : TREE_SIDE_EFFECTS (fofb->b) = 1;
12595 214 : OMP_FOR_BODY (fofb->omp_for) = fofb->b;
12596 : }
12597 363 : DECL_CHAIN (fofb->var) = BIND_EXPR_VARS (fofb->b);
12598 363 : BIND_EXPR_VARS (fofb->b) = fofb->var;
12599 363 : BLOCK_VARS (BIND_EXPR_BLOCK (fofb->b)) = fofb->var;
12600 363 : BLOCK_VARS (BIND_EXPR_BLOCK (*tp)) = BIND_EXPR_VARS (*tp);
12601 363 : return *tp;
12602 : }
12603 : }
12604 26 : if (TREE_CODE (*tp) != BIND_EXPR && TREE_CODE (*tp) != STATEMENT_LIST)
12605 22 : *walk_subtrees = false;
12606 : return NULL_TREE;
12607 : }
12608 :
12609 : /* Fix up range for decls. Those decls were pushed into BIND's
12610 : BIND_EXPR_VARS, or that of a nested BIND_EXPR inside its body,
12611 : and need to be moved into a new BIND_EXPR surrounding OMP_FOR's body
12612 : so that processing of combined loop directives can find them. */
12613 : tree
12614 14707 : finish_omp_for_block (tree bind, tree omp_for)
12615 : {
12616 14707 : if (omp_for == NULL_TREE
12617 14660 : || !OMP_FOR_ORIG_DECLS (omp_for)
12618 28777 : || bind == NULL_TREE)
12619 637 : return bind;
12620 14070 : struct fofb_data fofb;
12621 14070 : fofb.b = NULL_TREE;
12622 14070 : fofb.omp_for = omp_for;
12623 33667 : for (int i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (omp_for)); i++)
12624 19597 : if (TREE_VEC_ELT (OMP_FOR_INIT (omp_for), i)
12625 19375 : && (TREE_CODE (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (omp_for), i))
12626 : == TREE_LIST)
12627 20428 : && TREE_CHAIN (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (omp_for), i)))
12628 : {
12629 237 : tree v = TREE_CHAIN (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (omp_for), i));
12630 602 : for (int j = 2; j < TREE_VEC_LENGTH (v); j++)
12631 : {
12632 365 : fofb.var = TREE_VEC_ELT (v, j);
12633 365 : cp_walk_tree (&bind, finish_omp_for_block_walker,
12634 : (void *)&fofb, NULL);
12635 : }
12636 : }
12637 14070 : return bind;
12638 : }
12639 :
12640 : void
12641 3345 : finish_omp_atomic (location_t loc, enum tree_code code, enum tree_code opcode,
12642 : tree lhs, tree rhs, tree v, tree lhs1, tree rhs1, tree r,
12643 : tree clauses, enum omp_memory_order mo, bool weak)
12644 : {
12645 3345 : tree orig_lhs;
12646 3345 : tree orig_rhs;
12647 3345 : tree orig_v;
12648 3345 : tree orig_lhs1;
12649 3345 : tree orig_rhs1;
12650 3345 : tree orig_r;
12651 3345 : bool dependent_p;
12652 3345 : tree stmt;
12653 :
12654 3345 : orig_lhs = lhs;
12655 3345 : orig_rhs = rhs;
12656 3345 : orig_v = v;
12657 3345 : orig_lhs1 = lhs1;
12658 3345 : orig_rhs1 = rhs1;
12659 3345 : orig_r = r;
12660 3345 : dependent_p = false;
12661 3345 : stmt = NULL_TREE;
12662 :
12663 : /* Even in a template, we can detect invalid uses of the atomic
12664 : pragma if neither LHS nor RHS is type-dependent. */
12665 3345 : if (processing_template_decl)
12666 : {
12667 600 : dependent_p = (type_dependent_expression_p (lhs)
12668 237 : || (rhs && type_dependent_expression_p (rhs))
12669 234 : || (v && type_dependent_expression_p (v))
12670 234 : || (lhs1 && type_dependent_expression_p (lhs1))
12671 234 : || (rhs1 && type_dependent_expression_p (rhs1))
12672 834 : || (r
12673 25 : && r != void_list_node
12674 16 : && type_dependent_expression_p (r)));
12675 600 : if (clauses)
12676 : {
12677 30 : gcc_assert (TREE_CODE (clauses) == OMP_CLAUSE
12678 : && OMP_CLAUSE_CODE (clauses) == OMP_CLAUSE_HINT
12679 : && OMP_CLAUSE_CHAIN (clauses) == NULL_TREE);
12680 30 : if (type_dependent_expression_p (OMP_CLAUSE_HINT_EXPR (clauses))
12681 30 : || TREE_CODE (OMP_CLAUSE_HINT_EXPR (clauses)) != INTEGER_CST)
12682 : dependent_p = true;
12683 : }
12684 : }
12685 576 : if (!dependent_p)
12686 : {
12687 2961 : bool swapped = false;
12688 2961 : if (rhs1 && opcode != COND_EXPR && cp_tree_equal (lhs, rhs))
12689 : {
12690 143 : std::swap (rhs, rhs1);
12691 143 : swapped = !commutative_tree_code (opcode);
12692 : }
12693 2961 : if (rhs1 && opcode != COND_EXPR && !cp_tree_equal (lhs, rhs1))
12694 : {
12695 0 : if (code == OMP_ATOMIC)
12696 0 : error ("%<#pragma omp atomic update%> uses two different "
12697 : "expressions for memory");
12698 : else
12699 0 : error ("%<#pragma omp atomic capture%> uses two different "
12700 : "expressions for memory");
12701 : return;
12702 : }
12703 2961 : if (lhs1 && !cp_tree_equal (lhs, lhs1))
12704 : {
12705 0 : if (code == OMP_ATOMIC)
12706 0 : error ("%<#pragma omp atomic update%> uses two different "
12707 : "expressions for memory");
12708 : else
12709 0 : error ("%<#pragma omp atomic capture%> uses two different "
12710 : "expressions for memory");
12711 : return;
12712 : }
12713 5922 : stmt = c_finish_omp_atomic (loc, code, opcode, lhs, rhs,
12714 : v, lhs1, rhs1, r, swapped, mo, weak,
12715 2961 : processing_template_decl != 0);
12716 2961 : if (stmt == error_mark_node)
12717 : return;
12718 : }
12719 3315 : if (processing_template_decl)
12720 : {
12721 591 : if (code == OMP_ATOMIC_READ)
12722 : {
12723 167 : stmt = build_min_nt_loc (loc, OMP_ATOMIC_READ, orig_lhs);
12724 167 : OMP_ATOMIC_MEMORY_ORDER (stmt) = mo;
12725 167 : stmt = build2 (MODIFY_EXPR, void_type_node, orig_v, stmt);
12726 : }
12727 : else
12728 : {
12729 424 : if (opcode == NOP_EXPR)
12730 35 : stmt = build2 (MODIFY_EXPR, void_type_node, orig_lhs, orig_rhs);
12731 389 : else if (opcode == COND_EXPR)
12732 : {
12733 124 : stmt = build2 (EQ_EXPR, boolean_type_node, orig_lhs, orig_rhs);
12734 124 : if (orig_r)
12735 50 : stmt = build2 (MODIFY_EXPR, boolean_type_node, orig_r,
12736 : stmt);
12737 124 : stmt = build3 (COND_EXPR, void_type_node, stmt, orig_rhs1,
12738 : orig_lhs);
12739 124 : orig_rhs1 = NULL_TREE;
12740 : }
12741 : else
12742 265 : stmt = build2 (opcode, void_type_node, orig_lhs, orig_rhs);
12743 424 : if (orig_rhs1)
12744 182 : stmt = build_min_nt_loc (EXPR_LOCATION (orig_rhs1),
12745 : COMPOUND_EXPR, orig_rhs1, stmt);
12746 424 : if (code != OMP_ATOMIC)
12747 : {
12748 233 : stmt = build_min_nt_loc (loc, code, orig_lhs1, stmt);
12749 233 : OMP_ATOMIC_MEMORY_ORDER (stmt) = mo;
12750 233 : OMP_ATOMIC_WEAK (stmt) = weak;
12751 233 : stmt = build2 (MODIFY_EXPR, void_type_node, orig_v, stmt);
12752 : }
12753 : }
12754 591 : stmt = build2 (OMP_ATOMIC, void_type_node,
12755 : clauses ? clauses : integer_zero_node, stmt);
12756 591 : OMP_ATOMIC_MEMORY_ORDER (stmt) = mo;
12757 591 : OMP_ATOMIC_WEAK (stmt) = weak;
12758 591 : SET_EXPR_LOCATION (stmt, loc);
12759 : }
12760 :
12761 : /* Avoid -Wunused-value warnings here, the whole construct has side-effects
12762 : and even if it might be wrapped from fold-const.cc or c-omp.cc wrapped
12763 : in some tree that appears to be unused, the value is not unused. */
12764 3315 : warning_sentinel w (warn_unused_value);
12765 3315 : finish_expr_stmt (stmt);
12766 3315 : }
12767 :
12768 : void
12769 359 : finish_omp_barrier (void)
12770 : {
12771 359 : tree fn = builtin_decl_explicit (BUILT_IN_GOMP_BARRIER);
12772 359 : releasing_vec vec;
12773 359 : vec->quick_push (build_int_cst (integer_type_node, GOMP_BARRIER_EXPLICIT));
12774 359 : tree stmt = finish_call_expr (fn, &vec, false, false, tf_warning_or_error);
12775 359 : finish_expr_stmt (stmt);
12776 359 : }
12777 :
12778 : void
12779 397 : finish_omp_depobj (location_t loc, tree depobj,
12780 : enum omp_clause_depend_kind kind, tree clause)
12781 : {
12782 397 : if (!error_operand_p (depobj) && !type_dependent_expression_p (depobj))
12783 : {
12784 343 : if (!lvalue_p (depobj))
12785 : {
12786 6 : error_at (EXPR_LOC_OR_LOC (depobj, loc),
12787 : "%<depobj%> expression is not lvalue expression");
12788 6 : depobj = error_mark_node;
12789 : }
12790 : }
12791 :
12792 397 : if (processing_template_decl)
12793 : {
12794 114 : if (clause == NULL_TREE)
12795 47 : clause = build_int_cst (integer_type_node, kind);
12796 114 : add_stmt (build_min_nt_loc (loc, OMP_DEPOBJ, depobj, clause));
12797 114 : return;
12798 : }
12799 :
12800 283 : if (!error_operand_p (depobj))
12801 : {
12802 274 : tree addr = cp_build_addr_expr (depobj, tf_warning_or_error);
12803 274 : if (addr == error_mark_node)
12804 : depobj = error_mark_node;
12805 : else
12806 274 : depobj = cp_build_indirect_ref (loc, addr, RO_UNARY_STAR,
12807 : tf_warning_or_error);
12808 : }
12809 :
12810 283 : c_finish_omp_depobj (loc, depobj, kind, clause);
12811 : }
12812 :
12813 : void
12814 162 : finish_omp_flush (int mo)
12815 : {
12816 162 : tree fn = builtin_decl_explicit (BUILT_IN_SYNC_SYNCHRONIZE);
12817 162 : releasing_vec vec;
12818 162 : if (mo != MEMMODEL_LAST && mo != MEMMODEL_SEQ_CST)
12819 : {
12820 54 : fn = builtin_decl_explicit (BUILT_IN_ATOMIC_THREAD_FENCE);
12821 54 : vec->quick_push (build_int_cst (integer_type_node, mo));
12822 : }
12823 162 : tree stmt = finish_call_expr (fn, &vec, false, false, tf_warning_or_error);
12824 162 : finish_expr_stmt (stmt);
12825 162 : }
12826 :
12827 : void
12828 111 : finish_omp_taskwait (void)
12829 : {
12830 111 : tree fn = builtin_decl_explicit (BUILT_IN_GOMP_TASKWAIT);
12831 111 : releasing_vec vec;
12832 111 : tree stmt = finish_call_expr (fn, &vec, false, false, tf_warning_or_error);
12833 111 : finish_expr_stmt (stmt);
12834 111 : }
12835 :
12836 : void
12837 16 : finish_omp_taskyield (void)
12838 : {
12839 16 : tree fn = builtin_decl_explicit (BUILT_IN_GOMP_TASKYIELD);
12840 16 : releasing_vec vec;
12841 16 : tree stmt = finish_call_expr (fn, &vec, false, false, tf_warning_or_error);
12842 16 : finish_expr_stmt (stmt);
12843 16 : }
12844 :
12845 : void
12846 596 : finish_omp_cancel (tree clauses)
12847 : {
12848 596 : tree fn = builtin_decl_explicit (BUILT_IN_GOMP_CANCEL);
12849 596 : int mask = 0;
12850 596 : if (omp_find_clause (clauses, OMP_CLAUSE_PARALLEL))
12851 : mask = 1;
12852 414 : else if (omp_find_clause (clauses, OMP_CLAUSE_FOR))
12853 : mask = 2;
12854 285 : else if (omp_find_clause (clauses, OMP_CLAUSE_SECTIONS))
12855 : mask = 4;
12856 164 : else if (omp_find_clause (clauses, OMP_CLAUSE_TASKGROUP))
12857 : mask = 8;
12858 : else
12859 : {
12860 0 : error ("%<#pragma omp cancel%> must specify one of "
12861 : "%<parallel%>, %<for%>, %<sections%> or %<taskgroup%> clauses");
12862 0 : return;
12863 : }
12864 596 : releasing_vec vec;
12865 596 : tree ifc = omp_find_clause (clauses, OMP_CLAUSE_IF);
12866 596 : if (ifc != NULL_TREE)
12867 : {
12868 70 : if (OMP_CLAUSE_IF_MODIFIER (ifc) != ERROR_MARK
12869 70 : && OMP_CLAUSE_IF_MODIFIER (ifc) != VOID_CST)
12870 6 : error_at (OMP_CLAUSE_LOCATION (ifc),
12871 : "expected %<cancel%> %<if%> clause modifier");
12872 : else
12873 : {
12874 64 : tree ifc2 = omp_find_clause (OMP_CLAUSE_CHAIN (ifc), OMP_CLAUSE_IF);
12875 64 : if (ifc2 != NULL_TREE)
12876 : {
12877 3 : gcc_assert (OMP_CLAUSE_IF_MODIFIER (ifc) == VOID_CST
12878 : && OMP_CLAUSE_IF_MODIFIER (ifc2) != ERROR_MARK
12879 : && OMP_CLAUSE_IF_MODIFIER (ifc2) != VOID_CST);
12880 3 : error_at (OMP_CLAUSE_LOCATION (ifc2),
12881 : "expected %<cancel%> %<if%> clause modifier");
12882 : }
12883 : }
12884 :
12885 70 : if (!processing_template_decl)
12886 61 : ifc = maybe_convert_cond (OMP_CLAUSE_IF_EXPR (ifc));
12887 : else
12888 9 : ifc = build_x_binary_op (OMP_CLAUSE_LOCATION (ifc), NE_EXPR,
12889 9 : OMP_CLAUSE_IF_EXPR (ifc), ERROR_MARK,
12890 : integer_zero_node, ERROR_MARK,
12891 : NULL_TREE, NULL, tf_warning_or_error);
12892 : }
12893 : else
12894 526 : ifc = boolean_true_node;
12895 596 : vec->quick_push (build_int_cst (integer_type_node, mask));
12896 596 : vec->quick_push (ifc);
12897 596 : tree stmt = finish_call_expr (fn, &vec, false, false, tf_warning_or_error);
12898 596 : finish_expr_stmt (stmt);
12899 596 : }
12900 :
12901 : void
12902 494 : finish_omp_cancellation_point (tree clauses)
12903 : {
12904 494 : tree fn = builtin_decl_explicit (BUILT_IN_GOMP_CANCELLATION_POINT);
12905 494 : int mask = 0;
12906 494 : if (omp_find_clause (clauses, OMP_CLAUSE_PARALLEL))
12907 : mask = 1;
12908 366 : else if (omp_find_clause (clauses, OMP_CLAUSE_FOR))
12909 : mask = 2;
12910 261 : else if (omp_find_clause (clauses, OMP_CLAUSE_SECTIONS))
12911 : mask = 4;
12912 156 : else if (omp_find_clause (clauses, OMP_CLAUSE_TASKGROUP))
12913 : mask = 8;
12914 : else
12915 : {
12916 3 : error ("%<#pragma omp cancellation point%> must specify one of "
12917 : "%<parallel%>, %<for%>, %<sections%> or %<taskgroup%> clauses");
12918 3 : return;
12919 : }
12920 491 : releasing_vec vec
12921 491 : = make_tree_vector_single (build_int_cst (integer_type_node, mask));
12922 491 : tree stmt = finish_call_expr (fn, &vec, false, false, tf_warning_or_error);
12923 491 : finish_expr_stmt (stmt);
12924 491 : }
12925 :
12926 : /* Begin a __transaction_atomic or __transaction_relaxed statement.
12927 : If PCOMPOUND is non-null, this is for a function-transaction-block, and we
12928 : should create an extra compound stmt. */
12929 :
12930 : tree
12931 303 : begin_transaction_stmt (location_t loc, tree *pcompound, int flags)
12932 : {
12933 303 : tree r;
12934 :
12935 303 : if (pcompound)
12936 21 : *pcompound = begin_compound_stmt (0);
12937 :
12938 303 : r = build_stmt (loc, TRANSACTION_EXPR, NULL_TREE);
12939 :
12940 : /* Only add the statement to the function if support enabled. */
12941 303 : if (flag_tm)
12942 297 : add_stmt (r);
12943 : else
12944 12 : error_at (loc, ((flags & TM_STMT_ATTR_RELAXED) != 0
12945 : ? G_("%<__transaction_relaxed%> without "
12946 : "transactional memory support enabled")
12947 : : G_("%<__transaction_atomic%> without "
12948 : "transactional memory support enabled")));
12949 :
12950 303 : TRANSACTION_EXPR_BODY (r) = push_stmt_list ();
12951 303 : TREE_SIDE_EFFECTS (r) = 1;
12952 303 : return r;
12953 : }
12954 :
12955 : /* End a __transaction_atomic or __transaction_relaxed statement.
12956 : If COMPOUND_STMT is non-null, this is for a function-transaction-block,
12957 : and we should end the compound. If NOEX is non-NULL, we wrap the body in
12958 : a MUST_NOT_THROW_EXPR with NOEX as condition. */
12959 :
12960 : void
12961 303 : finish_transaction_stmt (tree stmt, tree compound_stmt, int flags, tree noex)
12962 : {
12963 303 : TRANSACTION_EXPR_BODY (stmt) = pop_stmt_list (TRANSACTION_EXPR_BODY (stmt));
12964 303 : TRANSACTION_EXPR_OUTER (stmt) = (flags & TM_STMT_ATTR_OUTER) != 0;
12965 303 : TRANSACTION_EXPR_RELAXED (stmt) = (flags & TM_STMT_ATTR_RELAXED) != 0;
12966 303 : TRANSACTION_EXPR_IS_STMT (stmt) = 1;
12967 :
12968 : /* noexcept specifications are not allowed for function transactions. */
12969 303 : gcc_assert (!(noex && compound_stmt));
12970 303 : if (noex)
12971 : {
12972 51 : tree body = build_must_not_throw_expr (TRANSACTION_EXPR_BODY (stmt),
12973 : noex);
12974 51 : protected_set_expr_location
12975 51 : (body, EXPR_LOCATION (TRANSACTION_EXPR_BODY (stmt)));
12976 51 : TREE_SIDE_EFFECTS (body) = 1;
12977 51 : TRANSACTION_EXPR_BODY (stmt) = body;
12978 : }
12979 :
12980 303 : if (compound_stmt)
12981 21 : finish_compound_stmt (compound_stmt);
12982 303 : }
12983 :
12984 : /* Build a __transaction_atomic or __transaction_relaxed expression. If
12985 : NOEX is non-NULL, we wrap the body in a MUST_NOT_THROW_EXPR with NOEX as
12986 : condition. */
12987 :
12988 : tree
12989 116 : build_transaction_expr (location_t loc, tree expr, int flags, tree noex)
12990 : {
12991 116 : tree ret;
12992 116 : if (noex)
12993 : {
12994 57 : expr = build_must_not_throw_expr (expr, noex);
12995 57 : protected_set_expr_location (expr, loc);
12996 57 : TREE_SIDE_EFFECTS (expr) = 1;
12997 : }
12998 116 : ret = build1 (TRANSACTION_EXPR, TREE_TYPE (expr), expr);
12999 116 : if (flags & TM_STMT_ATTR_RELAXED)
13000 4 : TRANSACTION_EXPR_RELAXED (ret) = 1;
13001 116 : TREE_SIDE_EFFECTS (ret) = 1;
13002 116 : SET_EXPR_LOCATION (ret, loc);
13003 116 : return ret;
13004 : }
13005 :
13006 : void
13007 101489 : init_cp_semantics (void)
13008 : {
13009 101489 : }
13010 :
13011 :
13012 : /* Get constant string at LOCATION. Returns true if successful,
13013 : otherwise false. */
13014 :
13015 : bool
13016 11440373 : cexpr_str::type_check (location_t location, bool allow_char8_t /*=false*/)
13017 : {
13018 11440373 : tsubst_flags_t complain = tf_warning_or_error;
13019 :
13020 11440373 : if (message == NULL_TREE
13021 11440373 : || message == error_mark_node
13022 22880743 : || check_for_bare_parameter_packs (message))
13023 : return false;
13024 :
13025 11440370 : if (TREE_CODE (message) != STRING_CST
13026 11440370 : && !type_dependent_expression_p (message))
13027 : {
13028 1053 : message_sz
13029 1053 : = finish_class_member_access_expr (message,
13030 : get_identifier ("size"),
13031 : false, complain);
13032 1053 : if (message_sz != error_mark_node)
13033 952 : message_data
13034 952 : = finish_class_member_access_expr (message,
13035 : get_identifier ("data"),
13036 : false, complain);
13037 1053 : if (message_sz == error_mark_node || message_data == error_mark_node)
13038 : {
13039 139 : error_at (location, "constexpr string must be a string "
13040 : "literal or object with %<size%> and "
13041 : "%<data%> members");
13042 322 : return false;
13043 : }
13044 914 : releasing_vec size_args, data_args;
13045 914 : message_sz = finish_call_expr (message_sz, &size_args, false, false,
13046 : complain);
13047 914 : message_data = finish_call_expr (message_data, &data_args, false, false,
13048 : complain);
13049 914 : if (message_sz == error_mark_node || message_data == error_mark_node)
13050 : return false;
13051 800 : message_sz = build_converted_constant_expr (size_type_node, message_sz,
13052 : complain);
13053 800 : if (message_sz == error_mark_node)
13054 : {
13055 15 : error_at (location, "constexpr string %<size()%> "
13056 : "must be implicitly convertible to "
13057 : "%<std::size_t%>");
13058 15 : return false;
13059 : }
13060 :
13061 785 : if (allow_char8_t
13062 74 : && POINTER_TYPE_P (TREE_TYPE (message_data))
13063 74 : && (TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (message_data)))
13064 74 : == char8_type_node)
13065 805 : && (TYPE_QUALS (TREE_TYPE (TREE_TYPE (message_data)))
13066 : == TYPE_QUAL_CONST))
13067 : return true;
13068 :
13069 765 : message_data = build_converted_constant_expr (const_string_type_node,
13070 : message_data, complain);
13071 765 : if (message_data == error_mark_node)
13072 : {
13073 34 : error_at (location, "constexpr string %<data()%> "
13074 : "must be implicitly convertible to "
13075 : "%<const char*%>");
13076 34 : return false;
13077 : }
13078 914 : }
13079 : return true;
13080 : }
13081 :
13082 : /* Extract constant string at LOCATON into output string STR.
13083 : Returns true if successful, otherwise false. */
13084 :
13085 : bool
13086 405 : cexpr_str::extract (location_t location, tree &str)
13087 : {
13088 405 : const char *msg;
13089 405 : int len;
13090 405 : if (!extract (location, msg, len))
13091 : return false;
13092 343 : str = build_string (len, msg);
13093 343 : return true;
13094 : }
13095 :
13096 : /* Extract constant string at LOCATION into output string MSG with LEN.
13097 : Returns true if successful, otherwise false. */
13098 :
13099 : bool
13100 2707 : cexpr_str::extract (location_t location, const char * &msg, int &len,
13101 : const constexpr_ctx *ctx /* = NULL */,
13102 : bool *non_constant_p /* = NULL */,
13103 : bool *overflow_p /* = NULL */,
13104 : tree *jump_target /* = NULL */)
13105 : {
13106 2707 : tsubst_flags_t complain = tf_warning_or_error;
13107 :
13108 2707 : msg = NULL;
13109 2707 : if (message_sz && message_data)
13110 : {
13111 677 : tree msz;
13112 677 : if (ctx)
13113 : {
13114 110 : msz = cxx_eval_constant_expression (ctx, message_sz, vc_prvalue,
13115 : non_constant_p, overflow_p,
13116 : jump_target);
13117 110 : if (*jump_target || *non_constant_p)
13118 : return false;
13119 : }
13120 : else
13121 567 : msz = cxx_constant_value (message_sz, NULL_TREE, complain);
13122 669 : if (!tree_fits_uhwi_p (msz))
13123 : {
13124 35 : if (!ctx || !cxx_constexpr_quiet_p (ctx))
13125 35 : error_at (location,
13126 : "constexpr string %<size()%> "
13127 : "must be a constant expression");
13128 : return false;
13129 : }
13130 634 : else if ((unsigned HOST_WIDE_INT) (int) tree_to_uhwi (msz)
13131 : != tree_to_uhwi (msz))
13132 : {
13133 0 : if (!ctx || !cxx_constexpr_quiet_p (ctx))
13134 0 : error_at (location,
13135 : "constexpr string message %<size()%> "
13136 : "%qE too large", msz);
13137 : return false;
13138 : }
13139 634 : len = tree_to_uhwi (msz);
13140 634 : tree data;
13141 634 : if (ctx)
13142 : {
13143 102 : data = cxx_eval_constant_expression (ctx, message_data, vc_prvalue,
13144 : non_constant_p, overflow_p,
13145 : jump_target);
13146 102 : if (*jump_target || *non_constant_p)
13147 : return false;
13148 94 : STRIP_NOPS (data);
13149 94 : if (TREE_CODE (data) != ADDR_EXPR)
13150 : {
13151 0 : unhandled:
13152 0 : if (!cxx_constexpr_quiet_p (ctx))
13153 0 : error_at (location, "unhandled return from %<data()%>");
13154 : return false;
13155 : }
13156 94 : tree str = TREE_OPERAND (data, 0);
13157 94 : unsigned HOST_WIDE_INT off = 0;
13158 94 : if (TREE_CODE (str) == ARRAY_REF
13159 94 : && tree_fits_uhwi_p (TREE_OPERAND (str, 1)))
13160 : {
13161 12 : off = tree_to_uhwi (TREE_OPERAND (str, 1));
13162 12 : str = TREE_OPERAND (str, 0);
13163 : }
13164 94 : str = cxx_eval_constant_expression (ctx, str, vc_prvalue,
13165 : non_constant_p, overflow_p,
13166 : jump_target);
13167 94 : if (*jump_target || *non_constant_p)
13168 : return false;
13169 94 : if (TREE_CODE (str) == STRING_CST)
13170 : {
13171 84 : if (TREE_STRING_LENGTH (str) < len
13172 84 : || (unsigned) TREE_STRING_LENGTH (str) < off
13173 168 : || (unsigned) TREE_STRING_LENGTH (str) < off + len)
13174 0 : goto unhandled;
13175 84 : msg = TREE_STRING_POINTER (str) + off;
13176 84 : goto translate;
13177 : }
13178 10 : if (TREE_CODE (str) != CONSTRUCTOR
13179 10 : || TREE_CODE (TREE_TYPE (str)) != ARRAY_TYPE)
13180 0 : goto unhandled;
13181 10 : char *b;
13182 10 : if (len < 64)
13183 10 : b = XALLOCAVEC (char, len + 1);
13184 : else
13185 : {
13186 0 : buf = XNEWVEC (char, len + 1);
13187 0 : b = buf;
13188 : }
13189 10 : msg = b;
13190 10 : memset (b, 0, len + 1);
13191 10 : tree field, value;
13192 10 : unsigned k;
13193 10 : unsigned HOST_WIDE_INT l = 0;
13194 158 : FOR_EACH_CONSTRUCTOR_ELT (CONSTRUCTOR_ELTS (str), k, field, value)
13195 158 : if (!tree_fits_shwi_p (value))
13196 0 : goto unhandled;
13197 158 : else if (field == NULL_TREE)
13198 : {
13199 0 : if (integer_zerop (value))
13200 : break;
13201 0 : if (l >= off && l < off + len)
13202 0 : b[l - off] = tree_to_shwi (value);
13203 0 : ++l;
13204 : }
13205 158 : else if (TREE_CODE (field) == RANGE_EXPR)
13206 : {
13207 0 : tree lo = TREE_OPERAND (field, 0);
13208 0 : tree hi = TREE_OPERAND (field, 1);
13209 0 : if (!tree_fits_uhwi_p (lo) || !tree_fits_uhwi_p (hi))
13210 0 : goto unhandled;
13211 0 : if (integer_zerop (value))
13212 : break;
13213 0 : unsigned HOST_WIDE_INT m = tree_to_uhwi (hi);
13214 0 : for (l = tree_to_uhwi (lo); l <= m; ++l)
13215 0 : if (l >= off && l < off + len)
13216 0 : b[l - off] = tree_to_shwi (value);
13217 : }
13218 158 : else if (tree_fits_uhwi_p (field))
13219 : {
13220 158 : l = tree_to_uhwi (field);
13221 158 : if (integer_zerop (value))
13222 : break;
13223 148 : if (l >= off && l < off + len)
13224 148 : b[l - off] = tree_to_shwi (value);
13225 148 : l++;
13226 : }
13227 10 : b[len] = '\0';
13228 : }
13229 : else
13230 : {
13231 532 : data = maybe_constant_value (message_data, NULL_TREE, mce_true);
13232 532 : if (!reduced_constant_expression_p (data))
13233 96 : data = NULL_TREE;
13234 532 : if (len)
13235 : {
13236 455 : if (data)
13237 381 : msg = c_getstr (data);
13238 455 : if (msg == NULL)
13239 119 : buf = XNEWVEC (char, len);
13240 1458 : for (int i = 0; i < len; ++i)
13241 : {
13242 1033 : tree t = message_data;
13243 1033 : if (i)
13244 1156 : t = build2 (POINTER_PLUS_EXPR,
13245 578 : TREE_TYPE (message_data), message_data,
13246 578 : size_int (i));
13247 1033 : t = build1 (INDIRECT_REF, TREE_TYPE (TREE_TYPE (t)), t);
13248 1033 : tree t2 = cxx_constant_value (t, NULL_TREE, complain);
13249 1033 : if (!tree_fits_shwi_p (t2))
13250 : {
13251 30 : error_at (location,
13252 : "constexpr string %<data()[%d]%> "
13253 : "must be a constant expression", i);
13254 30 : return false;
13255 : }
13256 1003 : if (msg == NULL)
13257 362 : buf[i] = tree_to_shwi (t2);
13258 : /* If c_getstr worked, just verify the first and
13259 : last characters using constant evaluation. */
13260 641 : else if (len > 2 && i == 0)
13261 268 : i = len - 2;
13262 : }
13263 425 : if (msg == NULL)
13264 104 : msg = buf;
13265 : }
13266 77 : else if (!data)
13267 : {
13268 : /* We don't have any function to test whether some
13269 : expression is a core constant expression. So, instead
13270 : test whether (message.data (), 0) is a constant
13271 : expression. */
13272 22 : data = build2 (COMPOUND_EXPR, integer_type_node,
13273 : message_data, integer_zero_node);
13274 22 : tree t = cxx_constant_value (data, NULL_TREE, complain);
13275 22 : if (!integer_zerop (t))
13276 : {
13277 22 : error_at (location,
13278 : "constexpr string %<data()%> "
13279 : "must be a core constant expression");
13280 22 : return false;
13281 : }
13282 : }
13283 : }
13284 : }
13285 : else
13286 : {
13287 2030 : tree eltype = TREE_TYPE (TREE_TYPE (message));
13288 2030 : int sz = TREE_INT_CST_LOW (TYPE_SIZE_UNIT (eltype));
13289 2030 : msg = TREE_STRING_POINTER (message);
13290 2030 : len = TREE_STRING_LENGTH (message) / sz - 1;
13291 : }
13292 2604 : translate:
13293 2604 : if ((message_sz && message_data) || ctx)
13294 : {
13295 : /* Convert the string from execution charset to SOURCE_CHARSET. */
13296 768 : cpp_string istr, ostr;
13297 768 : istr.len = len;
13298 768 : istr.text = (const unsigned char *) msg;
13299 768 : enum cpp_ttype type = CPP_STRING;
13300 768 : if (message_sz && message_data)
13301 : {
13302 574 : if (POINTER_TYPE_P (TREE_TYPE (message_data))
13303 574 : && (TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (message_data)))
13304 574 : == char8_type_node))
13305 : type = CPP_UTF8STRING;
13306 : }
13307 194 : else if (TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (message)))
13308 194 : == char8_type_node)
13309 768 : type = CPP_UTF8STRING;
13310 768 : if (len == 0)
13311 : ;
13312 643 : else if (!cpp_translate_string (parse_in, &istr, &ostr, type,
13313 : true))
13314 : {
13315 0 : if (type == CPP_UTF8STRING)
13316 0 : error_at (location, "could not convert constexpr string from "
13317 : "UTF-8 encoding to source character "
13318 : "set");
13319 : else
13320 0 : error_at (location, "could not convert constexpr string from "
13321 : "ordinary literal encoding to source character "
13322 : "set");
13323 0 : return false;
13324 : }
13325 : else
13326 : {
13327 643 : if (buf)
13328 104 : XDELETEVEC (buf);
13329 643 : msg = buf = const_cast <char *> ((const char *) ostr.text);
13330 643 : len = ostr.len;
13331 : }
13332 : }
13333 :
13334 : return true;
13335 : }
13336 :
13337 : /* Build a STATIC_ASSERT for a static assertion with the condition
13338 : CONDITION and the message text MESSAGE. LOCATION is the location
13339 : of the static assertion in the source code. When MEMBER_P, this
13340 : static assertion is a member of a class. If SHOW_EXPR_P is true,
13341 : print the condition (because it was instantiation-dependent).
13342 : If CONSTEVAL_BLOCK_P is true, this static assertion represents
13343 : a consteval block. */
13344 :
13345 : void
13346 11439682 : finish_static_assert (tree condition, tree message, location_t location,
13347 : bool member_p, bool show_expr_p,
13348 : bool consteval_block_p/*=false*/)
13349 : {
13350 11439682 : tsubst_flags_t complain = tf_warning_or_error;
13351 :
13352 11439682 : if (condition == NULL_TREE
13353 11439682 : || condition == error_mark_node)
13354 4855232 : return;
13355 :
13356 11439456 : if (check_for_bare_parameter_packs (condition))
13357 : return;
13358 :
13359 11439453 : cexpr_str cstr(message);
13360 11439453 : if (!cstr.type_check (location))
13361 : return;
13362 :
13363 : /* Save the condition in case it was a concept check. */
13364 11439359 : tree orig_condition = condition;
13365 :
13366 11439359 : if (instantiation_dependent_expression_p (condition)
13367 11439359 : || instantiation_dependent_expression_p (message))
13368 : {
13369 : /* We're in a template; build a STATIC_ASSERT and put it in
13370 : the right place. */
13371 4854365 : defer:
13372 4854365 : tree assertion = make_node (STATIC_ASSERT);
13373 4854365 : STATIC_ASSERT_CONDITION (assertion) = orig_condition;
13374 4854365 : STATIC_ASSERT_MESSAGE (assertion) = cstr.message;
13375 4854365 : STATIC_ASSERT_SOURCE_LOCATION (assertion) = location;
13376 4854365 : CONSTEVAL_BLOCK_P (assertion) = consteval_block_p;
13377 :
13378 4854365 : if (member_p)
13379 2490750 : maybe_add_class_template_decl_list (current_class_type,
13380 : assertion,
13381 : /*friend_p=*/0);
13382 : else
13383 2363615 : add_stmt (assertion);
13384 :
13385 : return;
13386 : }
13387 :
13388 : /* Evaluate the consteval { }. This must be done only once. */
13389 6591048 : if (consteval_block_p)
13390 : {
13391 519 : cxx_constant_value (condition);
13392 519 : return;
13393 : }
13394 :
13395 : /* Fold the expression and convert it to a boolean value. */
13396 6590529 : condition = contextual_conv_bool (condition, complain);
13397 6590529 : condition = fold_non_dependent_expr (condition, complain,
13398 : /*manifestly_const_eval=*/true);
13399 :
13400 6590527 : if (TREE_CODE (condition) == INTEGER_CST && !integer_zerop (condition))
13401 : /* Do nothing; the condition is satisfied. */
13402 : ;
13403 : else
13404 : {
13405 8916 : iloc_sentinel ils (location);
13406 :
13407 8916 : if (integer_zerop (condition))
13408 : {
13409 : /* CWG2518: static_assert failure in a template is not IFNDR. */
13410 8052 : if (processing_template_decl)
13411 6054 : goto defer;
13412 :
13413 1998 : int len;
13414 1998 : const char *msg = NULL;
13415 1998 : if (!cstr.extract (location, msg, len))
13416 25 : return;
13417 :
13418 : /* See if we can find which clause was failing (for logical AND). */
13419 1973 : tree bad = find_failing_clause (NULL, orig_condition);
13420 : /* If not, or its location is unusable, fall back to the previous
13421 : location. */
13422 1973 : location_t cloc = cp_expr_loc_or_loc (bad, location);
13423 :
13424 1973 : auto_diagnostic_group d;
13425 :
13426 : /* Report the error. */
13427 1973 : if (len == 0)
13428 1261 : error_at (cloc, "static assertion failed");
13429 : else
13430 712 : error_at (cloc, "static assertion failed: %.*s", len, msg);
13431 :
13432 1973 : diagnose_failing_condition (bad, cloc, show_expr_p);
13433 :
13434 : /* Suppress -Wreturn-type for functions with failed static_asserts.
13435 : Otherwise templates like:
13436 : if constexpr (whatever)
13437 : return something (args);
13438 : else
13439 : static_assert (false, "explanation");
13440 : get a useless extra -Wreturn-type warning. */
13441 1973 : if (current_function_decl)
13442 758 : suppress_warning (current_function_decl, OPT_Wreturn_type);
13443 1973 : }
13444 864 : else if (condition && condition != error_mark_node)
13445 : {
13446 858 : error ("non-constant condition for static assertion");
13447 858 : if (require_rvalue_constant_expression (condition))
13448 796 : cxx_constant_value (condition);
13449 : }
13450 8916 : }
13451 11439451 : }
13452 :
13453 : /* Implements the C++0x decltype keyword. Returns the type of EXPR,
13454 : suitable for use as a type-specifier.
13455 :
13456 : ID_EXPRESSION_OR_MEMBER_ACCESS_P is true when EXPR was parsed as an
13457 : id-expression or a class member access, FALSE when it was parsed as
13458 : a full expression. */
13459 :
13460 : tree
13461 44219077 : finish_decltype_type (tree expr, bool id_expression_or_member_access_p,
13462 : tsubst_flags_t complain)
13463 : {
13464 44219077 : tree type = NULL_TREE;
13465 :
13466 44219077 : if (!expr || error_operand_p (expr))
13467 243073 : return error_mark_node;
13468 :
13469 43976004 : if (TYPE_P (expr)
13470 43976004 : || TREE_CODE (expr) == TYPE_DECL
13471 87951988 : || (TREE_CODE (expr) == BIT_NOT_EXPR
13472 16547 : && TYPE_P (TREE_OPERAND (expr, 0))))
13473 : {
13474 29 : if (complain & tf_error)
13475 29 : error ("argument to %<decltype%> must be an expression");
13476 29 : return error_mark_node;
13477 : }
13478 :
13479 : /* decltype is an unevaluated context. */
13480 43975975 : cp_unevaluated u;
13481 :
13482 43975975 : processing_template_decl_sentinel ptds (/*reset=*/false);
13483 :
13484 : /* Depending on the resolution of DR 1172, we may later need to distinguish
13485 : instantiation-dependent but not type-dependent expressions so that, say,
13486 : A<decltype(sizeof(T))>::U doesn't require 'typename'. */
13487 43975975 : if (instantiation_dependent_uneval_expression_p (expr))
13488 : {
13489 7448613 : dependent:
13490 7449189 : type = cxx_make_type (DECLTYPE_TYPE);
13491 7449189 : DECLTYPE_TYPE_EXPR (type) = expr;
13492 14898378 : DECLTYPE_TYPE_ID_EXPR_OR_MEMBER_ACCESS_P (type)
13493 7449189 : = id_expression_or_member_access_p;
13494 7449189 : SET_TYPE_STRUCTURAL_EQUALITY (type);
13495 :
13496 7449189 : return type;
13497 : }
13498 36527362 : else if (processing_template_decl)
13499 : {
13500 7485 : expr = instantiate_non_dependent_expr (expr, complain|tf_decltype);
13501 7485 : if (expr == error_mark_node)
13502 : return error_mark_node;
13503 : /* Keep processing_template_decl cleared for the rest of the function
13504 : (for sake of the call to lvalue_kind below, which handles templated
13505 : and non-templated COND_EXPR differently). */
13506 7448 : processing_template_decl = 0;
13507 : }
13508 :
13509 : /* The type denoted by decltype(e) is defined as follows: */
13510 :
13511 36527325 : expr = resolve_nondeduced_context (expr, complain);
13512 36527325 : if (!mark_single_function (expr, complain))
13513 0 : return error_mark_node;
13514 :
13515 36527325 : if (invalid_nonstatic_memfn_p (input_location, expr, complain))
13516 18 : return error_mark_node;
13517 :
13518 36527307 : if (type_unknown_p (expr))
13519 : {
13520 18 : if (complain & tf_error)
13521 6 : error ("%<decltype%> cannot resolve address of overloaded function");
13522 18 : return error_mark_node;
13523 : }
13524 :
13525 36527289 : if (id_expression_or_member_access_p)
13526 : {
13527 : /* If e is an id-expression or a class member access (5.2.5
13528 : [expr.ref]), decltype(e) is defined as the type of the entity
13529 : named by e. If there is no such entity, or e names a set of
13530 : overloaded functions, the program is ill-formed. */
13531 551348 : if (identifier_p (expr))
13532 0 : expr = lookup_name (expr);
13533 :
13534 : /* If e is a constified expression inside a contract assertion,
13535 : strip the const wrapper. Per P2900R14, "For a function f with the
13536 : return type T , the result name is an lvalue of type const T , decltype(r)
13537 : is T , and decltype((r)) is const T&." */
13538 551348 : expr = strip_contract_const_wrapper (expr);
13539 :
13540 376103 : if (REFERENCE_REF_P (expr)
13541 551353 : || TREE_CODE (expr) == VIEW_CONVERT_EXPR)
13542 : /* This can happen when the expression is, e.g., "a.b". Just
13543 : look at the underlying operand. */
13544 379374 : expr = TREE_OPERAND (expr, 0);
13545 :
13546 551348 : if (TREE_CODE (expr) == OFFSET_REF
13547 551348 : || TREE_CODE (expr) == MEMBER_REF
13548 551348 : || TREE_CODE (expr) == SCOPE_REF)
13549 : /* We're only interested in the field itself. If it is a
13550 : BASELINK, we will need to see through it in the next
13551 : step. */
13552 0 : expr = TREE_OPERAND (expr, 1);
13553 :
13554 551348 : if (BASELINK_P (expr))
13555 : /* See through BASELINK nodes to the underlying function. */
13556 7 : expr = BASELINK_FUNCTIONS (expr);
13557 :
13558 : /* decltype of a decomposition name drops references in the tuple case
13559 : (unlike decltype of a normal variable) and keeps cv-qualifiers from
13560 : the containing object in the other cases (unlike decltype of a member
13561 : access expression). */
13562 551348 : if (DECL_DECOMPOSITION_P (expr))
13563 : {
13564 1449 : if (ptds.saved)
13565 : {
13566 275 : gcc_checking_assert (DECL_HAS_VALUE_EXPR_P (expr)
13567 : || (DECL_CONTEXT (expr)
13568 : != current_function_decl));
13569 : /* DECL_HAS_VALUE_EXPR_P is always set if
13570 : processing_template_decl at least for structured bindings
13571 : within the template. If lookup_decomp_type
13572 : returns non-NULL, it is the tuple case. */
13573 275 : if (tree ret = lookup_decomp_type (expr))
13574 : return ret;
13575 191 : gcc_checking_assert (DECL_HAS_VALUE_EXPR_P (expr));
13576 : }
13577 1365 : if (DECL_HAS_VALUE_EXPR_P (expr))
13578 : /* Expr is an array or struct subobject proxy, handle
13579 : bit-fields properly. */
13580 1021 : return unlowered_expr_type (expr);
13581 : else
13582 : /* Expr is a reference variable for the tuple case. */
13583 344 : return lookup_decomp_type (expr);
13584 : }
13585 :
13586 549899 : switch (TREE_CODE (expr))
13587 : {
13588 650 : case FIELD_DECL:
13589 650 : if (DECL_BIT_FIELD_TYPE (expr))
13590 : {
13591 : type = DECL_BIT_FIELD_TYPE (expr);
13592 : break;
13593 : }
13594 : /* Fall through for fields that aren't bitfields. */
13595 147940 : gcc_fallthrough ();
13596 :
13597 147940 : case VAR_DECL:
13598 147940 : if (is_capture_proxy (expr))
13599 : {
13600 99 : if (is_normal_capture_proxy (expr))
13601 : {
13602 21 : expr = DECL_CAPTURED_VARIABLE (expr);
13603 21 : type = TREE_TYPE (expr);
13604 : }
13605 : else
13606 : {
13607 78 : expr = DECL_VALUE_EXPR (expr);
13608 78 : gcc_assert (TREE_CODE (expr) == COMPONENT_REF);
13609 78 : expr = TREE_OPERAND (expr, 1);
13610 78 : type = TREE_TYPE (expr);
13611 : }
13612 : break;
13613 : }
13614 : /* Fall through for variables that aren't capture proxies. */
13615 538827 : gcc_fallthrough ();
13616 :
13617 538827 : case FUNCTION_DECL:
13618 538827 : case CONST_DECL:
13619 538827 : case PARM_DECL:
13620 538827 : case RESULT_DECL:
13621 538827 : case TEMPLATE_PARM_INDEX:
13622 538827 : expr = mark_type_use (expr);
13623 538827 : type = TREE_TYPE (expr);
13624 538827 : if (VAR_P (expr) && DECL_NTTP_OBJECT_P (expr))
13625 : {
13626 : /* decltype of an NTTP object is the type of the template
13627 : parameter, which is the object type modulo cv-quals. */
13628 2643 : int quals = cp_type_quals (type);
13629 2643 : gcc_checking_assert (quals & TYPE_QUAL_CONST);
13630 2643 : type = cv_unqualified (type);
13631 : }
13632 : break;
13633 :
13634 0 : case ERROR_MARK:
13635 0 : type = error_mark_node;
13636 0 : break;
13637 :
13638 3520 : case COMPONENT_REF:
13639 3520 : case COMPOUND_EXPR:
13640 3520 : mark_type_use (expr);
13641 3520 : type = is_bitfield_expr_with_lowered_type (expr);
13642 3520 : if (!type)
13643 3483 : type = TREE_TYPE (TREE_OPERAND (expr, 1));
13644 : break;
13645 :
13646 0 : case BIT_FIELD_REF:
13647 0 : gcc_unreachable ();
13648 :
13649 3508 : case INTEGER_CST:
13650 3508 : case PTRMEM_CST:
13651 : /* We can get here when the id-expression refers to an
13652 : enumerator or non-type template parameter. */
13653 3508 : type = TREE_TYPE (expr);
13654 3508 : break;
13655 :
13656 3945 : default:
13657 : /* Handle instantiated template non-type arguments. */
13658 3945 : type = TREE_TYPE (expr);
13659 3945 : break;
13660 : }
13661 : }
13662 : else
13663 : {
13664 35975941 : tree decl = STRIP_REFERENCE_REF (expr);
13665 35975941 : tree lam = current_lambda_expr ();
13666 35975941 : if (lam && outer_automatic_var_p (decl))
13667 : {
13668 : /* [expr.prim.id.unqual]/3: If naming the entity from outside of an
13669 : unevaluated operand within S would refer to an entity captured by
13670 : copy in some intervening lambda-expression, then let E be the
13671 : innermost such lambda-expression.
13672 :
13673 : If there is such a lambda-expression and if P is in E's function
13674 : parameter scope but not its parameter-declaration-clause, then the
13675 : type of the expression is the type of a class member access
13676 : expression naming the non-static data member that would be declared
13677 : for such a capture in the object parameter of the function call
13678 : operator of E." */
13679 : /* FIXME: This transformation needs to happen for all uses of an outer
13680 : local variable inside decltype, not just decltype((x)) (PR83167).
13681 : And we don't handle nested lambdas properly, where we need to
13682 : consider the outer lambdas as well (PR112926). */
13683 1379 : tree cap = lookup_name (DECL_NAME (decl), LOOK_where::BLOCK,
13684 : LOOK_want::HIDDEN_LAMBDA);
13685 :
13686 1379 : if (cap && is_capture_proxy (cap))
13687 467 : type = TREE_TYPE (cap);
13688 912 : else if (LAMBDA_EXPR_DEFAULT_CAPTURE_MODE (lam) == CPLD_COPY)
13689 : {
13690 738 : type = TREE_TYPE (decl);
13691 738 : if (TYPE_REF_P (type)
13692 738 : && TREE_CODE (TREE_TYPE (type)) != FUNCTION_TYPE)
13693 36 : type = TREE_TYPE (type);
13694 : }
13695 :
13696 1205 : if (type && !TYPE_REF_P (type))
13697 : {
13698 1121 : int quals;
13699 1121 : if (current_function_decl
13700 2104 : && LAMBDA_FUNCTION_P (current_function_decl)
13701 2104 : && DECL_XOBJ_MEMBER_FUNCTION_P (current_function_decl))
13702 : {
13703 900 : tree obtype = TREE_TYPE (DECL_ARGUMENTS (current_function_decl));
13704 900 : if (WILDCARD_TYPE_P (non_reference (obtype)))
13705 : /* We don't know what the eventual obtype quals will be. */
13706 576 : goto dependent;
13707 648 : auto direct_type = [](tree t){
13708 324 : if (INDIRECT_TYPE_P (t))
13709 162 : return TREE_TYPE (t);
13710 : return t;
13711 : };
13712 648 : quals = (cp_type_quals (type)
13713 324 : | cp_type_quals (direct_type (obtype)));
13714 : }
13715 : else
13716 : /* We are in the parameter clause, trailing return type, or
13717 : the requires clause and have no relevant c_f_decl yet. */
13718 349 : quals = (LAMBDA_EXPR_CONST_QUAL_P (lam)
13719 221 : ? TYPE_QUAL_CONST : TYPE_UNQUALIFIED);
13720 545 : type = cp_build_qualified_type (type, quals);
13721 545 : type = build_reference_type (type);
13722 : }
13723 : }
13724 35974562 : else if (error_operand_p (expr))
13725 0 : type = error_mark_node;
13726 35974562 : else if (expr == current_class_ptr)
13727 : /* If the expression is just "this", we want the
13728 : cv-unqualified pointer for the "this" type. */
13729 0 : type = TYPE_MAIN_VARIANT (TREE_TYPE (expr));
13730 :
13731 545 : if (!type)
13732 : {
13733 : /* Otherwise, where T is the type of e, if e is an lvalue,
13734 : decltype(e) is defined as T&; if an xvalue, T&&; otherwise, T. */
13735 35974736 : cp_lvalue_kind clk = lvalue_kind (expr);
13736 35974736 : type = unlowered_expr_type (expr);
13737 35974736 : gcc_assert (!TYPE_REF_P (type));
13738 :
13739 : /* For vector types, pick a non-opaque variant. */
13740 35974736 : if (VECTOR_TYPE_P (type))
13741 4421 : type = strip_typedefs (type);
13742 :
13743 35974736 : if (clk != clk_none && !(clk & clk_class))
13744 9157894 : type = cp_build_reference_type (type, (clk & clk_rvalueref));
13745 : }
13746 : }
13747 :
13748 : return type;
13749 43975975 : }
13750 :
13751 : /* Called from trait_expr_value to evaluate either __has_nothrow_assign or
13752 : __has_nothrow_copy, depending on assign_p. Returns true iff all
13753 : the copy {ctor,assign} fns are nothrow. */
13754 :
13755 : static bool
13756 351 : classtype_has_nothrow_assign_or_copy_p (tree type, bool assign_p)
13757 : {
13758 351 : tree fns = NULL_TREE;
13759 :
13760 351 : if (assign_p || TYPE_HAS_COPY_CTOR (type))
13761 348 : fns = get_class_binding (type, assign_p ? assign_op_identifier
13762 : : ctor_identifier);
13763 :
13764 351 : bool saw_copy = false;
13765 894 : for (ovl_iterator iter (fns); iter; ++iter)
13766 : {
13767 561 : tree fn = *iter;
13768 :
13769 561 : if (copy_fn_p (fn) > 0)
13770 : {
13771 525 : saw_copy = true;
13772 525 : if (!maybe_instantiate_noexcept (fn)
13773 525 : || !TYPE_NOTHROW_P (TREE_TYPE (fn)))
13774 234 : return false;
13775 : }
13776 : }
13777 :
13778 117 : return saw_copy;
13779 : }
13780 :
13781 : /* Return true if BASE is a pointer-interconvertible base of DERIVED. */
13782 :
13783 : bool
13784 183 : pointer_interconvertible_base_of_p (tree base, tree derived,
13785 : bool explain/*=false*/)
13786 : {
13787 183 : if (base == error_mark_node || derived == error_mark_node)
13788 : return false;
13789 :
13790 183 : base = TYPE_MAIN_VARIANT (base);
13791 183 : derived = TYPE_MAIN_VARIANT (derived);
13792 183 : if (!NON_UNION_CLASS_TYPE_P (base))
13793 : {
13794 17 : if (explain)
13795 3 : inform (location_of (base),
13796 : "%qT is not a non-union class type", base);
13797 : return false;
13798 : }
13799 166 : if (!NON_UNION_CLASS_TYPE_P (derived))
13800 : {
13801 8 : if (explain)
13802 3 : inform (location_of (derived),
13803 : "%qT is not a non-union class type", derived);
13804 : return false;
13805 : }
13806 :
13807 158 : if (same_type_p (base, derived))
13808 : return true;
13809 :
13810 117 : if (!std_layout_type_p (derived))
13811 : {
13812 18 : if (explain)
13813 6 : inform (location_of (derived),
13814 : "%qT is not a standard-layout type", derived);
13815 : return false;
13816 : }
13817 :
13818 99 : if (!uniquely_derived_from_p (base, derived))
13819 : {
13820 18 : if (explain)
13821 : {
13822 : /* An ambiguous base should already be impossible due to
13823 : the std_layout_type_p check. */
13824 3 : gcc_checking_assert (!DERIVED_FROM_P (base, derived));
13825 3 : inform (location_of (derived),
13826 : "%qT is not a base of %qT", base, derived);
13827 : }
13828 : return false;
13829 : }
13830 :
13831 : return true;
13832 : }
13833 :
13834 : /* Helper function for fold_builtin_is_pointer_inverconvertible_with_class,
13835 : return true if MEMBERTYPE is the type of the first non-static data member
13836 : of TYPE or for unions of any members. */
13837 : static bool
13838 637 : first_nonstatic_data_member_p (tree type, tree membertype)
13839 : {
13840 1297 : for (tree field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
13841 : {
13842 1222 : if (TREE_CODE (field) != FIELD_DECL)
13843 135 : continue;
13844 1087 : if (DECL_FIELD_IS_BASE (field) && is_empty_field (field))
13845 60 : continue;
13846 1027 : if (DECL_FIELD_IS_BASE (field))
13847 45 : return first_nonstatic_data_member_p (TREE_TYPE (field), membertype);
13848 982 : if (ANON_AGGR_TYPE_P (TREE_TYPE (field)))
13849 : {
13850 216 : if ((TREE_CODE (TREE_TYPE (field)) == UNION_TYPE
13851 138 : || std_layout_type_p (TREE_TYPE (field)))
13852 294 : && first_nonstatic_data_member_p (TREE_TYPE (field), membertype))
13853 : return true;
13854 : }
13855 766 : else if (same_type_ignoring_top_level_qualifiers_p (TREE_TYPE (field),
13856 : membertype))
13857 : return true;
13858 537 : if (TREE_CODE (type) != UNION_TYPE)
13859 : return false;
13860 : }
13861 : return false;
13862 : }
13863 :
13864 : /* Fold __builtin_is_pointer_interconvertible_with_class call. */
13865 :
13866 : tree
13867 536 : fold_builtin_is_pointer_inverconvertible_with_class (location_t loc, int nargs,
13868 : tree *args)
13869 : {
13870 : /* Unless users call the builtin directly, the following 3 checks should be
13871 : ensured from std::is_pointer_interconvertible_with_class function
13872 : template. */
13873 536 : if (nargs != 1)
13874 : {
13875 6 : error_at (loc, "%<__builtin_is_pointer_interconvertible_with_class%> "
13876 : "needs a single argument");
13877 6 : return boolean_false_node;
13878 : }
13879 530 : tree arg = args[0];
13880 530 : if (error_operand_p (arg))
13881 0 : return boolean_false_node;
13882 530 : if (!TYPE_PTRMEM_P (TREE_TYPE (arg)))
13883 : {
13884 6 : error_at (loc, "%<__builtin_is_pointer_interconvertible_with_class%> "
13885 : "argument is not pointer to member");
13886 6 : return boolean_false_node;
13887 : }
13888 :
13889 524 : if (!TYPE_PTRDATAMEM_P (TREE_TYPE (arg)))
13890 18 : return boolean_false_node;
13891 :
13892 506 : tree membertype = TREE_TYPE (TREE_TYPE (arg));
13893 506 : tree basetype = TYPE_OFFSET_BASETYPE (TREE_TYPE (arg));
13894 506 : if (!complete_type_or_else (basetype, NULL_TREE))
13895 3 : return boolean_false_node;
13896 :
13897 503 : if (TREE_CODE (basetype) != UNION_TYPE
13898 503 : && !std_layout_type_p (basetype))
13899 22 : return boolean_false_node;
13900 :
13901 481 : if (!first_nonstatic_data_member_p (basetype, membertype))
13902 132 : return boolean_false_node;
13903 :
13904 349 : if (TREE_CODE (arg) == PTRMEM_CST)
13905 68 : arg = cplus_expand_constant (arg);
13906 :
13907 349 : if (integer_nonzerop (arg))
13908 10 : return boolean_false_node;
13909 339 : if (integer_zerop (arg))
13910 71 : return boolean_true_node;
13911 :
13912 268 : return fold_build2 (EQ_EXPR, boolean_type_node, arg,
13913 : build_zero_cst (TREE_TYPE (arg)));
13914 : }
13915 :
13916 : /* Helper function for is_corresponding_member_aggr. Return true if
13917 : MEMBERTYPE pointer-to-data-member ARG can be found in anonymous
13918 : union or structure BASETYPE. */
13919 :
13920 : static bool
13921 90 : is_corresponding_member_union (tree basetype, tree membertype, tree arg)
13922 : {
13923 222 : for (tree field = TYPE_FIELDS (basetype); field; field = DECL_CHAIN (field))
13924 192 : if (TREE_CODE (field) != FIELD_DECL || DECL_BIT_FIELD_TYPE (field))
13925 36 : continue;
13926 156 : else if (same_type_ignoring_top_level_qualifiers_p (TREE_TYPE (field),
13927 : membertype))
13928 : {
13929 48 : if (TREE_CODE (arg) != INTEGER_CST
13930 48 : || tree_int_cst_equal (arg, byte_position (field)))
13931 : return true;
13932 : }
13933 108 : else if (ANON_AGGR_TYPE_P (TREE_TYPE (field)))
13934 : {
13935 18 : tree narg = arg;
13936 18 : if (TREE_CODE (basetype) != UNION_TYPE
13937 0 : && TREE_CODE (narg) == INTEGER_CST)
13938 0 : narg = size_binop (MINUS_EXPR, arg, byte_position (field));
13939 18 : if (is_corresponding_member_union (TREE_TYPE (field),
13940 : membertype, narg))
13941 : return true;
13942 : }
13943 : return false;
13944 : }
13945 :
13946 : /* Helper function for fold_builtin_is_corresponding_member call.
13947 : Return boolean_false_node if MEMBERTYPE1 BASETYPE1::*ARG1 and
13948 : MEMBERTYPE2 BASETYPE2::*ARG2 aren't corresponding members,
13949 : boolean_true_node if they are corresponding members, or for
13950 : non-constant ARG2 the highest member offset for corresponding
13951 : members. */
13952 :
13953 : static tree
13954 550 : is_corresponding_member_aggr (location_t loc, tree basetype1, tree membertype1,
13955 : tree arg1, tree basetype2, tree membertype2,
13956 : tree arg2)
13957 : {
13958 550 : tree field1 = TYPE_FIELDS (basetype1);
13959 550 : tree field2 = TYPE_FIELDS (basetype2);
13960 550 : tree ret = boolean_false_node;
13961 2376 : while (1)
13962 : {
13963 1463 : bool r = next_common_initial_sequence (field1, field2);
13964 1463 : if (field1 == NULL_TREE || field2 == NULL_TREE)
13965 : break;
13966 1331 : if (r
13967 1038 : && same_type_ignoring_top_level_qualifiers_p (TREE_TYPE (field1),
13968 : membertype1)
13969 1841 : && same_type_ignoring_top_level_qualifiers_p (TREE_TYPE (field2),
13970 : membertype2))
13971 : {
13972 504 : tree pos = byte_position (field1);
13973 504 : if (TREE_CODE (arg1) == INTEGER_CST
13974 504 : && tree_int_cst_equal (arg1, pos))
13975 : {
13976 92 : if (TREE_CODE (arg2) == INTEGER_CST)
13977 92 : return boolean_true_node;
13978 : return pos;
13979 : }
13980 412 : else if (TREE_CODE (arg1) != INTEGER_CST)
13981 1188 : ret = pos;
13982 : }
13983 1654 : else if (ANON_AGGR_TYPE_P (TREE_TYPE (field1))
13984 944 : && ANON_AGGR_TYPE_P (TREE_TYPE (field2)))
13985 : {
13986 117 : if ((!lookup_attribute ("no_unique_address",
13987 117 : DECL_ATTRIBUTES (field1)))
13988 117 : != !lookup_attribute ("no_unique_address",
13989 117 : DECL_ATTRIBUTES (field2)))
13990 : break;
13991 117 : if (!tree_int_cst_equal (bit_position (field1),
13992 117 : bit_position (field2)))
13993 : break;
13994 99 : bool overlap = true;
13995 99 : tree pos = byte_position (field1);
13996 99 : if (TREE_CODE (arg1) == INTEGER_CST)
13997 : {
13998 27 : tree off1 = fold_convert (sizetype, arg1);
13999 27 : tree sz1 = TYPE_SIZE_UNIT (TREE_TYPE (field1));
14000 27 : if (tree_int_cst_lt (off1, pos)
14001 27 : || tree_int_cst_le (size_binop (PLUS_EXPR, pos, sz1), off1))
14002 : overlap = false;
14003 : }
14004 99 : if (TREE_CODE (arg2) == INTEGER_CST)
14005 : {
14006 27 : tree off2 = fold_convert (sizetype, arg2);
14007 27 : tree sz2 = TYPE_SIZE_UNIT (TREE_TYPE (field2));
14008 27 : if (tree_int_cst_lt (off2, pos)
14009 27 : || tree_int_cst_le (size_binop (PLUS_EXPR, pos, sz2), off2))
14010 : overlap = false;
14011 : }
14012 87 : if (overlap
14013 87 : && NON_UNION_CLASS_TYPE_P (TREE_TYPE (field1))
14014 126 : && NON_UNION_CLASS_TYPE_P (TREE_TYPE (field2)))
14015 : {
14016 39 : tree narg1 = arg1;
14017 39 : if (TREE_CODE (arg1) == INTEGER_CST)
14018 9 : narg1 = size_binop (MINUS_EXPR,
14019 : fold_convert (sizetype, arg1), pos);
14020 39 : tree narg2 = arg2;
14021 39 : if (TREE_CODE (arg2) == INTEGER_CST)
14022 9 : narg2 = size_binop (MINUS_EXPR,
14023 : fold_convert (sizetype, arg2), pos);
14024 39 : tree t1 = TREE_TYPE (field1);
14025 39 : tree t2 = TREE_TYPE (field2);
14026 39 : tree nret = is_corresponding_member_aggr (loc, t1, membertype1,
14027 : narg1, t2, membertype2,
14028 : narg2);
14029 39 : if (nret != boolean_false_node)
14030 : {
14031 39 : if (nret == boolean_true_node)
14032 : return nret;
14033 30 : if (TREE_CODE (arg1) == INTEGER_CST)
14034 0 : return size_binop (PLUS_EXPR, nret, pos);
14035 30 : ret = size_binop (PLUS_EXPR, nret, pos);
14036 : }
14037 : }
14038 60 : else if (overlap
14039 48 : && TREE_CODE (TREE_TYPE (field1)) == UNION_TYPE
14040 108 : && TREE_CODE (TREE_TYPE (field2)) == UNION_TYPE)
14041 : {
14042 48 : tree narg1 = arg1;
14043 48 : if (TREE_CODE (arg1) == INTEGER_CST)
14044 6 : narg1 = size_binop (MINUS_EXPR,
14045 : fold_convert (sizetype, arg1), pos);
14046 48 : tree narg2 = arg2;
14047 48 : if (TREE_CODE (arg2) == INTEGER_CST)
14048 6 : narg2 = size_binop (MINUS_EXPR,
14049 : fold_convert (sizetype, arg2), pos);
14050 48 : if (is_corresponding_member_union (TREE_TYPE (field1),
14051 : membertype1, narg1)
14052 48 : && is_corresponding_member_union (TREE_TYPE (field2),
14053 : membertype2, narg2))
14054 : {
14055 24 : sorry_at (loc, "%<__builtin_is_corresponding_member%> "
14056 : "not well defined for anonymous unions");
14057 24 : return boolean_false_node;
14058 : }
14059 : }
14060 : }
14061 1188 : if (!r)
14062 : break;
14063 913 : field1 = DECL_CHAIN (field1);
14064 913 : field2 = DECL_CHAIN (field2);
14065 913 : }
14066 : return ret;
14067 : }
14068 :
14069 : /* Fold __builtin_is_corresponding_member call. */
14070 :
14071 : tree
14072 699 : fold_builtin_is_corresponding_member (location_t loc, int nargs,
14073 : tree *args)
14074 : {
14075 : /* Unless users call the builtin directly, the following 3 checks should be
14076 : ensured from std::is_corresponding_member function template. */
14077 699 : if (nargs != 2)
14078 : {
14079 9 : error_at (loc, "%<__builtin_is_corresponding_member%> "
14080 : "needs two arguments");
14081 9 : return boolean_false_node;
14082 : }
14083 690 : tree arg1 = args[0];
14084 690 : tree arg2 = args[1];
14085 690 : if (error_operand_p (arg1) || error_operand_p (arg2))
14086 0 : return boolean_false_node;
14087 711 : if (!TYPE_PTRMEM_P (TREE_TYPE (arg1))
14088 705 : || !TYPE_PTRMEM_P (TREE_TYPE (arg2)))
14089 : {
14090 9 : error_at (loc, "%<__builtin_is_corresponding_member%> "
14091 : "argument is not pointer to member");
14092 9 : return boolean_false_node;
14093 : }
14094 :
14095 681 : if (!TYPE_PTRDATAMEM_P (TREE_TYPE (arg1))
14096 681 : || !TYPE_PTRDATAMEM_P (TREE_TYPE (arg2)))
14097 15 : return boolean_false_node;
14098 :
14099 666 : tree membertype1 = TREE_TYPE (TREE_TYPE (arg1));
14100 666 : tree basetype1 = TYPE_OFFSET_BASETYPE (TREE_TYPE (arg1));
14101 666 : if (!complete_type_or_else (basetype1, NULL_TREE))
14102 12 : return boolean_false_node;
14103 :
14104 654 : tree membertype2 = TREE_TYPE (TREE_TYPE (arg2));
14105 654 : tree basetype2 = TYPE_OFFSET_BASETYPE (TREE_TYPE (arg2));
14106 654 : if (!complete_type_or_else (basetype2, NULL_TREE))
14107 12 : return boolean_false_node;
14108 :
14109 627 : if (!NON_UNION_CLASS_TYPE_P (basetype1)
14110 627 : || !NON_UNION_CLASS_TYPE_P (basetype2)
14111 627 : || !std_layout_type_p (basetype1)
14112 1233 : || !std_layout_type_p (basetype2))
14113 51 : return boolean_false_node;
14114 :
14115 : /* If the member types aren't layout compatible, then they
14116 : can't be corresponding members. */
14117 591 : if (!layout_compatible_type_p (membertype1, membertype2))
14118 18 : return boolean_false_node;
14119 :
14120 573 : if (TREE_CODE (arg1) == PTRMEM_CST)
14121 176 : arg1 = cplus_expand_constant (arg1);
14122 573 : if (TREE_CODE (arg2) == PTRMEM_CST)
14123 182 : arg2 = cplus_expand_constant (arg2);
14124 :
14125 573 : if (null_member_pointer_value_p (arg1)
14126 573 : || null_member_pointer_value_p (arg2))
14127 9 : return boolean_false_node;
14128 :
14129 564 : if (TREE_CODE (arg1) == INTEGER_CST
14130 182 : && TREE_CODE (arg2) == INTEGER_CST
14131 746 : && !tree_int_cst_equal (arg1, arg2))
14132 53 : return boolean_false_node;
14133 :
14134 511 : if (TREE_CODE (arg2) == INTEGER_CST
14135 129 : && TREE_CODE (arg1) != INTEGER_CST)
14136 : {
14137 : std::swap (arg1, arg2);
14138 : std::swap (membertype1, membertype2);
14139 : std::swap (basetype1, basetype2);
14140 : }
14141 :
14142 511 : tree ret = is_corresponding_member_aggr (loc, basetype1, membertype1, arg1,
14143 : basetype2, membertype2, arg2);
14144 511 : if (TREE_TYPE (ret) == boolean_type_node)
14145 : return ret;
14146 : /* If both arg1 and arg2 are INTEGER_CSTs, is_corresponding_member_aggr
14147 : already returns boolean_{true,false}_node whether those particular
14148 : members are corresponding members or not. Otherwise, if only
14149 : one of them is INTEGER_CST (canonicalized to first being INTEGER_CST
14150 : above), it returns boolean_false_node if it is certainly not a
14151 : corresponding member and otherwise we need to do a runtime check that
14152 : those two OFFSET_TYPE offsets are equal.
14153 : If neither of the operands is INTEGER_CST, is_corresponding_member_aggr
14154 : returns the largest offset at which the members would be corresponding
14155 : members, so perform arg1 <= ret && arg1 == arg2 runtime check. */
14156 304 : gcc_assert (TREE_CODE (arg2) != INTEGER_CST);
14157 304 : if (TREE_CODE (arg1) == INTEGER_CST)
14158 0 : return fold_build2 (EQ_EXPR, boolean_type_node, arg1,
14159 : fold_convert (TREE_TYPE (arg1), arg2));
14160 304 : ret = fold_build2 (LE_EXPR, boolean_type_node,
14161 : fold_convert (pointer_sized_int_node, arg1),
14162 : fold_convert (pointer_sized_int_node, ret));
14163 304 : return fold_build2 (TRUTH_AND_EXPR, boolean_type_node, ret,
14164 : fold_build2 (EQ_EXPR, boolean_type_node, arg1,
14165 : fold_convert (TREE_TYPE (arg1), arg2)));
14166 : }
14167 :
14168 : /* Fold __builtin_is_string_literal call. */
14169 :
14170 : tree
14171 4331 : fold_builtin_is_string_literal (location_t loc, int nargs, tree *args)
14172 : {
14173 : /* Unless users call the builtin directly, the following 3 checks should be
14174 : ensured from std::is_string_literal overloads. */
14175 4331 : if (nargs != 1)
14176 : {
14177 0 : error_at (loc, "%<__builtin_is_string_literal%> needs a single "
14178 : "argument");
14179 0 : return boolean_false_node;
14180 : }
14181 4331 : tree arg = args[0];
14182 4331 : if (error_operand_p (arg))
14183 0 : return boolean_false_node;
14184 4331 : if (!TYPE_PTR_P (TREE_TYPE (arg))
14185 4331 : || !TYPE_READONLY (TREE_TYPE (TREE_TYPE (arg)))
14186 8662 : || TYPE_VOLATILE (TREE_TYPE (TREE_TYPE (arg))))
14187 : {
14188 0 : arg_invalid:
14189 0 : error_at (loc, "%<__builtin_is_string_literal%> "
14190 : "argument is not %<const char*%>, %<const wchar_t*%>, "
14191 : "%<const char8_t*%>, %<const char16_t*%> or "
14192 : "%<const char32_t*%>");
14193 0 : return boolean_false_node;
14194 : }
14195 4331 : tree chart = TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (arg)));
14196 4331 : if (chart != char_type_node
14197 3460 : && chart != wchar_type_node
14198 2595 : && chart != char8_type_node
14199 1730 : && chart != char16_type_node
14200 865 : && chart != char32_type_node)
14201 0 : goto arg_invalid;
14202 :
14203 4331 : STRIP_NOPS (arg);
14204 8674 : while (TREE_CODE (arg) == POINTER_PLUS_EXPR)
14205 : {
14206 12 : arg = TREE_OPERAND (arg, 0);
14207 12 : STRIP_NOPS (arg);
14208 : }
14209 4331 : if (TREE_CODE (arg) != ADDR_EXPR)
14210 4275 : return boolean_false_node;
14211 56 : arg = TREE_OPERAND (arg, 0);
14212 56 : if (TREE_CODE (arg) == ARRAY_REF)
14213 24 : arg = TREE_OPERAND (arg, 0);
14214 56 : if (TREE_CODE (arg) != STRING_CST)
14215 16 : return boolean_false_node;
14216 40 : return boolean_true_node;
14217 : }
14218 :
14219 : /* [basic.types] 8. True iff TYPE is an object type. */
14220 :
14221 : static bool
14222 2974225 : object_type_p (const_tree type)
14223 : {
14224 2974225 : return (TREE_CODE (type) != FUNCTION_TYPE
14225 0 : && !TYPE_REF_P (type)
14226 2974225 : && !VOID_TYPE_P (type));
14227 : }
14228 :
14229 : /* [defns.referenceable] True iff TYPE is a referenceable type. */
14230 :
14231 : static bool
14232 3631700 : referenceable_type_p (const_tree type)
14233 : {
14234 3631700 : return (TYPE_REF_P (type)
14235 3632156 : || object_type_p (type)
14236 3632156 : || (FUNC_OR_METHOD_TYPE_P (type)
14237 385 : && type_memfn_quals (type) == TYPE_UNQUALIFIED
14238 319 : && type_memfn_rqual (type) == REF_QUAL_NONE));
14239 : }
14240 :
14241 : /* Actually evaluates the trait. */
14242 :
14243 : static bool
14244 18405457 : trait_expr_value (cp_trait_kind kind, tree type1, tree type2)
14245 : {
14246 18405457 : enum tree_code type_code1;
14247 18405457 : tree t;
14248 :
14249 18405457 : type_code1 = TREE_CODE (type1);
14250 :
14251 18405457 : switch (kind)
14252 : {
14253 377 : case CPTK_HAS_NOTHROW_ASSIGN:
14254 377 : type1 = strip_array_types (type1);
14255 715 : return (!CP_TYPE_CONST_P (type1) && type_code1 != REFERENCE_TYPE
14256 715 : && (trait_expr_value (CPTK_HAS_TRIVIAL_ASSIGN, type1, type2)
14257 206 : || (CLASS_TYPE_P (type1)
14258 156 : && classtype_has_nothrow_assign_or_copy_p (type1,
14259 : true))));
14260 :
14261 254 : case CPTK_HAS_NOTHROW_CONSTRUCTOR:
14262 254 : type1 = strip_array_types (type1);
14263 254 : return (trait_expr_value (CPTK_HAS_TRIVIAL_CONSTRUCTOR, type1, type2)
14264 254 : || (CLASS_TYPE_P (type1)
14265 111 : && (t = locate_ctor (type1))
14266 72 : && maybe_instantiate_noexcept (t)
14267 70 : && TYPE_NOTHROW_P (TREE_TYPE (t))));
14268 :
14269 380 : case CPTK_HAS_NOTHROW_COPY:
14270 380 : type1 = strip_array_types (type1);
14271 380 : return (trait_expr_value (CPTK_HAS_TRIVIAL_COPY, type1, type2)
14272 380 : || (CLASS_TYPE_P (type1)
14273 195 : && classtype_has_nothrow_assign_or_copy_p (type1, false)));
14274 :
14275 613 : case CPTK_HAS_TRIVIAL_ASSIGN:
14276 : /* ??? The standard seems to be missing the "or array of such a class
14277 : type" wording for this trait. */
14278 613 : type1 = strip_array_types (type1);
14279 1205 : return (!CP_TYPE_CONST_P (type1) && type_code1 != REFERENCE_TYPE
14280 1187 : && (trivial_type_p (type1)
14281 364 : || (CLASS_TYPE_P (type1)
14282 267 : && TYPE_HAS_TRIVIAL_COPY_ASSIGN (type1))));
14283 :
14284 617 : case CPTK_HAS_TRIVIAL_CONSTRUCTOR:
14285 617 : type1 = strip_array_types (type1);
14286 617 : return (trivial_type_p (type1)
14287 617 : || (CLASS_TYPE_P (type1) && TYPE_HAS_TRIVIAL_DFLT (type1)));
14288 :
14289 640 : case CPTK_HAS_TRIVIAL_COPY:
14290 : /* ??? The standard seems to be missing the "or array of such a class
14291 : type" wording for this trait. */
14292 640 : type1 = strip_array_types (type1);
14293 1073 : return (trivial_type_p (type1) || type_code1 == REFERENCE_TYPE
14294 1055 : || (CLASS_TYPE_P (type1) && TYPE_HAS_TRIVIAL_COPY_CTOR (type1)));
14295 :
14296 808 : case CPTK_HAS_TRIVIAL_DESTRUCTOR:
14297 808 : type1 = strip_array_types (type1);
14298 808 : if (CLASS_TYPE_P (type1) && type_build_dtor_call (type1))
14299 : {
14300 129 : deferring_access_check_sentinel dacs (dk_no_check);
14301 129 : cp_unevaluated un;
14302 129 : tree fn = get_dtor (type1, tf_none);
14303 129 : if (!fn && !seen_error ())
14304 3 : warning (0, "checking %qs for type %qT with a destructor that "
14305 : "cannot be called", "__has_trivial_destructor", type1);
14306 129 : }
14307 1160 : return (trivial_type_p (type1) || type_code1 == REFERENCE_TYPE
14308 1157 : || (CLASS_TYPE_P (type1)
14309 299 : && TYPE_HAS_TRIVIAL_DESTRUCTOR (type1)));
14310 :
14311 61744 : case CPTK_HAS_UNIQUE_OBJ_REPRESENTATIONS:
14312 61744 : return type_has_unique_obj_representations (type1);
14313 :
14314 338 : case CPTK_HAS_VIRTUAL_DESTRUCTOR:
14315 338 : return type_has_virtual_destructor (type1);
14316 :
14317 56958 : case CPTK_IS_ABSTRACT:
14318 56958 : return ABSTRACT_CLASS_TYPE_P (type1);
14319 :
14320 1156 : case CPTK_IS_AGGREGATE:
14321 1156 : return CP_AGGREGATE_TYPE_P (type1);
14322 :
14323 377715 : case CPTK_IS_ARRAY:
14324 377715 : return (type_code1 == ARRAY_TYPE
14325 : /* We don't want to report T[0] as being an array type.
14326 : This is for compatibility with an implementation of
14327 : std::is_array by template argument deduction, because
14328 : compute_array_index_type_loc rejects a zero-size array
14329 : in SFINAE context. */
14330 377715 : && !(TYPE_SIZE (type1) && integer_zerop (TYPE_SIZE (type1))));
14331 :
14332 1042384 : case CPTK_IS_ASSIGNABLE:
14333 1042384 : return is_xible (MODIFY_EXPR, type1, type2);
14334 :
14335 526793 : case CPTK_IS_BASE_OF:
14336 526690 : return (NON_UNION_CLASS_TYPE_P (type1) && NON_UNION_CLASS_TYPE_P (type2)
14337 1034535 : && (same_type_ignoring_top_level_qualifiers_p (type1, type2)
14338 479063 : || DERIVED_FROM_P (type1, type2)));
14339 :
14340 58747 : case CPTK_IS_BOUNDED_ARRAY:
14341 58747 : return (type_code1 == ARRAY_TYPE
14342 1668 : && TYPE_DOMAIN (type1)
14343 : /* We don't want to report T[0] as being a bounded array type.
14344 : This is for compatibility with an implementation of
14345 : std::is_bounded_array by template argument deduction, because
14346 : compute_array_index_type_loc rejects a zero-size array
14347 : in SFINAE context. */
14348 60287 : && !(TYPE_SIZE (type1) && integer_zerop (TYPE_SIZE (type1))));
14349 :
14350 548566 : case CPTK_IS_CLASS:
14351 548566 : return NON_UNION_CLASS_TYPE_P (type1);
14352 :
14353 602645 : case CPTK_IS_CONST:
14354 602645 : return CP_TYPE_CONST_P (type1);
14355 :
14356 2433174 : case CPTK_IS_CONSTRUCTIBLE:
14357 2433174 : return is_xible (INIT_EXPR, type1, type2);
14358 :
14359 3231051 : case CPTK_IS_CONVERTIBLE:
14360 3231051 : return is_convertible (type1, type2);
14361 :
14362 3364 : case CPTK_IS_DESTRUCTIBLE:
14363 3364 : return is_xible (BIT_NOT_EXPR, type1, NULL_TREE);
14364 :
14365 223842 : case CPTK_IS_EMPTY:
14366 223842 : return NON_UNION_CLASS_TYPE_P (type1) && CLASSTYPE_EMPTY_P (type1);
14367 :
14368 684426 : case CPTK_IS_ENUM:
14369 684426 : return type_code1 == ENUMERAL_TYPE;
14370 :
14371 440985 : case CPTK_IS_FINAL:
14372 440985 : return CLASS_TYPE_P (type1) && CLASSTYPE_FINAL (type1);
14373 :
14374 48590 : case CPTK_IS_FUNCTION:
14375 48590 : return type_code1 == FUNCTION_TYPE;
14376 :
14377 1397 : case CPTK_IS_IMPLICIT_LIFETIME:
14378 1397 : return implicit_lifetime_type_p (type1);
14379 :
14380 49493 : case CPTK_IS_INVOCABLE:
14381 49493 : return !error_operand_p (build_invoke (type1, type2, tf_none));
14382 :
14383 221 : case CPTK_IS_LAYOUT_COMPATIBLE:
14384 221 : return layout_compatible_type_p (type1, type2);
14385 :
14386 197 : case CPTK_IS_LITERAL_TYPE:
14387 197 : return literal_type_p (type1);
14388 :
14389 49216 : case CPTK_IS_MEMBER_FUNCTION_POINTER:
14390 49216 : return TYPE_PTRMEMFUNC_P (type1);
14391 :
14392 49203 : case CPTK_IS_MEMBER_OBJECT_POINTER:
14393 49203 : return TYPE_PTRDATAMEM_P (type1);
14394 :
14395 11103 : case CPTK_IS_MEMBER_POINTER:
14396 11103 : return TYPE_PTRMEM_P (type1);
14397 :
14398 469717 : case CPTK_IS_NOTHROW_ASSIGNABLE:
14399 469717 : return is_nothrow_xible (MODIFY_EXPR, type1, type2);
14400 :
14401 945896 : case CPTK_IS_NOTHROW_CONSTRUCTIBLE:
14402 945896 : return is_nothrow_xible (INIT_EXPR, type1, type2);
14403 :
14404 683 : case CPTK_IS_NOTHROW_CONVERTIBLE:
14405 683 : return is_nothrow_convertible (type1, type2);
14406 :
14407 24488 : case CPTK_IS_NOTHROW_DESTRUCTIBLE:
14408 24488 : return is_nothrow_xible (BIT_NOT_EXPR, type1, NULL_TREE);
14409 :
14410 44337 : case CPTK_IS_NOTHROW_INVOCABLE:
14411 44337 : return expr_noexcept_p (build_invoke (type1, type2, tf_none), tf_none);
14412 :
14413 1150852 : case CPTK_IS_OBJECT:
14414 1150852 : return object_type_p (type1);
14415 :
14416 168 : case CPTK_IS_POINTER_INTERCONVERTIBLE_BASE_OF:
14417 168 : return pointer_interconvertible_base_of_p (type1, type2);
14418 :
14419 11676 : case CPTK_IS_POD:
14420 11676 : return pod_type_p (type1);
14421 :
14422 153866 : case CPTK_IS_POINTER:
14423 153866 : return TYPE_PTR_P (type1);
14424 :
14425 313 : case CPTK_IS_POLYMORPHIC:
14426 313 : return CLASS_TYPE_P (type1) && TYPE_POLYMORPHIC_P (type1);
14427 :
14428 732968 : case CPTK_IS_REFERENCE:
14429 732968 : return type_code1 == REFERENCE_TYPE;
14430 :
14431 2713948 : case CPTK_IS_SAME:
14432 2713948 : return same_type_p (type1, type2);
14433 :
14434 373 : case CPTK_IS_SCOPED_ENUM:
14435 373 : return SCOPED_ENUM_P (type1);
14436 :
14437 64815 : case CPTK_IS_STD_LAYOUT:
14438 64815 : return std_layout_type_p (type1);
14439 :
14440 59947 : case CPTK_IS_TRIVIAL:
14441 59947 : return trivial_type_p (type1);
14442 :
14443 12986 : case CPTK_IS_TRIVIALLY_ASSIGNABLE:
14444 12986 : return is_trivially_xible (MODIFY_EXPR, type1, type2);
14445 :
14446 77055 : case CPTK_IS_TRIVIALLY_CONSTRUCTIBLE:
14447 77055 : return is_trivially_xible (INIT_EXPR, type1, type2);
14448 :
14449 121085 : case CPTK_IS_TRIVIALLY_COPYABLE:
14450 121085 : return trivially_copyable_p (type1);
14451 :
14452 27668 : case CPTK_IS_TRIVIALLY_DESTRUCTIBLE:
14453 27668 : return is_trivially_xible (BIT_NOT_EXPR, type1, NULL_TREE);
14454 :
14455 100337 : case CPTK_IS_UNBOUNDED_ARRAY:
14456 100337 : return array_of_unknown_bound_p (type1);
14457 :
14458 278168 : case CPTK_IS_UNION:
14459 278168 : return type_code1 == UNION_TYPE;
14460 :
14461 883 : case CPTK_IS_VIRTUAL_BASE_OF:
14462 803 : return (NON_UNION_CLASS_TYPE_P (type1) && NON_UNION_CLASS_TYPE_P (type2)
14463 1664 : && lookup_base (type2, type1, ba_require_virtual,
14464 : NULL, tf_none) != NULL_TREE);
14465 :
14466 627128 : case CPTK_IS_VOLATILE:
14467 627128 : return CP_TYPE_VOLATILE_P (type1);
14468 :
14469 224044 : case CPTK_REF_CONSTRUCTS_FROM_TEMPORARY:
14470 224044 : return ref_xes_from_temporary (type1, type2, /*direct_init=*/true);
14471 :
14472 54710 : case CPTK_REF_CONVERTS_FROM_TEMPORARY:
14473 54710 : return ref_xes_from_temporary (type1, type2, /*direct_init=*/false);
14474 :
14475 85 : case CPTK_IS_DEDUCIBLE:
14476 85 : return type_targs_deducible_from (type1, type2);
14477 :
14478 264 : case CPTK_IS_STRUCTURAL:
14479 264 : return structural_type_p (type1);
14480 :
14481 : /* __array_rank, __builtin_type_order and __builtin_structured_binding_size
14482 : are handled in finish_trait_expr. */
14483 0 : case CPTK_RANK:
14484 0 : case CPTK_TYPE_ORDER:
14485 0 : case CPTK_STRUCTURED_BINDING_SIZE:
14486 0 : gcc_unreachable ();
14487 :
14488 : #define DEFTRAIT_TYPE(CODE, NAME, ARITY) \
14489 : case CPTK_##CODE:
14490 : #include "cp-trait.def"
14491 : #undef DEFTRAIT_TYPE
14492 : /* Type-yielding traits are handled in finish_trait_type. */
14493 : break;
14494 : }
14495 :
14496 0 : gcc_unreachable ();
14497 : }
14498 :
14499 : /* Returns true if TYPE meets the requirements for the specified KIND,
14500 : false otherwise.
14501 :
14502 : When KIND == 1, TYPE must be an array of unknown bound,
14503 : or (possibly cv-qualified) void, or a complete type.
14504 :
14505 : When KIND == 2, TYPE must be a complete type, or array of complete type,
14506 : or (possibly cv-qualified) void.
14507 :
14508 : When KIND == 3:
14509 : If TYPE is a non-union class type, it must be complete.
14510 :
14511 : When KIND == 4:
14512 : If TYPE is a class type, it must be complete.
14513 :
14514 : If COMPLAIN is not tf_none, we permerror and return false if that doesn't
14515 : produce a hard error. */
14516 :
14517 : static bool
14518 19329097 : check_trait_type (tree type, int kind, tsubst_flags_t complain)
14519 : {
14520 19329097 : if (type == NULL_TREE)
14521 : return true;
14522 :
14523 19329097 : if (TREE_CODE (type) == TREE_VEC)
14524 : {
14525 6309443 : for (tree arg : tree_vec_range (type))
14526 2764207 : if (!check_trait_type (arg, kind, complain))
14527 123 : return false;
14528 3545236 : return true;
14529 : }
14530 :
14531 15783738 : if (kind == 1 && TREE_CODE (type) == ARRAY_TYPE && !TYPE_DOMAIN (type))
14532 : return true; // Array of unknown bound. Don't care about completeness.
14533 :
14534 15782859 : if (kind == 3 && !NON_UNION_CLASS_TYPE_P (type))
14535 : return true; // Not a non-union class type. Don't care about completeness.
14536 :
14537 15666657 : if (kind == 4 && TREE_CODE (type) == ARRAY_TYPE)
14538 : return true; // Not a class type. Don't care about completeness.
14539 :
14540 15665727 : if (VOID_TYPE_P (type))
14541 : return true;
14542 :
14543 15664056 : type = complete_type (strip_array_types (type));
14544 15664056 : if (!COMPLETE_TYPE_P (type)
14545 : /* If we're not emitting error messages, always return false for
14546 : incomplete types. */
14547 15664056 : && (complain == tf_none
14548 184 : || (cxx_incomplete_type_diagnostic (NULL_TREE, type,
14549 : diagnostics::kind::permerror)
14550 184 : && !flag_permissive)))
14551 889 : return false;
14552 : return true;
14553 : }
14554 :
14555 : /* True iff the conversion (if any) would be a direct reference
14556 : binding, not requiring complete types. This is LWG2939. */
14557 :
14558 : static bool
14559 6782207 : same_type_ref_bind_p (cp_trait_kind kind, tree type1, tree type2)
14560 : {
14561 6782207 : tree from, to;
14562 6782207 : switch (kind)
14563 : {
14564 : /* These put the target type first. */
14565 : case CPTK_IS_CONSTRUCTIBLE:
14566 : case CPTK_IS_NOTHROW_CONSTRUCTIBLE:
14567 : case CPTK_IS_TRIVIALLY_CONSTRUCTIBLE:
14568 : case CPTK_IS_INVOCABLE:
14569 : case CPTK_IS_NOTHROW_INVOCABLE:
14570 : case CPTK_REF_CONSTRUCTS_FROM_TEMPORARY:
14571 : case CPTK_REF_CONVERTS_FROM_TEMPORARY:
14572 : to = type1;
14573 : from = type2;
14574 : break;
14575 :
14576 : /* These put it second. */
14577 3231806 : case CPTK_IS_CONVERTIBLE:
14578 3231806 : case CPTK_IS_NOTHROW_CONVERTIBLE:
14579 3231806 : to = type2;
14580 3231806 : from = type1;
14581 3231806 : break;
14582 :
14583 0 : default:
14584 0 : gcc_unreachable ();
14585 : }
14586 :
14587 6782207 : if (TREE_CODE (to) != REFERENCE_TYPE || !from)
14588 : return false;
14589 924872 : if (TREE_CODE (from) == TREE_VEC && TREE_VEC_LENGTH (from) == 1)
14590 63157 : from = TREE_VEC_ELT (from, 0);
14591 924872 : return (TYPE_P (from)
14592 1839500 : && (same_type_ignoring_top_level_qualifiers_p
14593 914628 : (non_reference (to), non_reference (from))));
14594 : }
14595 :
14596 : /* Helper for finish_trait_expr and tsubst_expr. Handle
14597 : CPTK_STRUCTURED_BINDING_SIZE in possibly SFINAE-friendly
14598 : way. */
14599 :
14600 : tree
14601 276 : finish_structured_binding_size (location_t loc, tree type,
14602 : tsubst_flags_t complain)
14603 : {
14604 276 : if (TYPE_REF_P (type))
14605 : {
14606 105 : if (complain & tf_error)
14607 99 : error_at (loc, "%qs argument %qT is a reference",
14608 : "__builtin_structured_binding_size", type);
14609 105 : return error_mark_node;
14610 : }
14611 171 : HOST_WIDE_INT ret = cp_decomp_size (loc, type, complain);
14612 171 : if (ret == -1)
14613 60 : return error_mark_node;
14614 111 : return maybe_wrap_with_location (build_int_cst (size_type_node, ret), loc);
14615 : }
14616 :
14617 : /* Process a trait expression. */
14618 :
14619 : tree
14620 21945347 : finish_trait_expr (location_t loc, cp_trait_kind kind, tree type1, tree type2,
14621 : tsubst_flags_t complain/*=tf_warning_or_error*/)
14622 : {
14623 21945347 : if (type1 == error_mark_node
14624 21945344 : || type2 == error_mark_node)
14625 : return error_mark_node;
14626 :
14627 21945344 : if (processing_template_decl)
14628 : {
14629 3539117 : tree trait_expr = make_node (TRAIT_EXPR);
14630 3539117 : if (kind == CPTK_RANK || kind == CPTK_STRUCTURED_BINDING_SIZE)
14631 32396 : TREE_TYPE (trait_expr) = size_type_node;
14632 3506721 : else if (kind == CPTK_TYPE_ORDER)
14633 : {
14634 4607 : tree val = type_order_value (type1, type1);
14635 4607 : if (val != error_mark_node)
14636 4607 : TREE_TYPE (trait_expr) = TREE_TYPE (val);
14637 : }
14638 : else
14639 3502114 : TREE_TYPE (trait_expr) = boolean_type_node;
14640 3539117 : TRAIT_EXPR_TYPE1 (trait_expr) = type1;
14641 3539117 : TRAIT_EXPR_TYPE2 (trait_expr) = type2;
14642 3539117 : TRAIT_EXPR_KIND (trait_expr) = kind;
14643 3539117 : TRAIT_EXPR_LOCATION (trait_expr) = loc;
14644 3539117 : return trait_expr;
14645 : }
14646 :
14647 18406227 : switch (kind)
14648 : {
14649 58294 : case CPTK_HAS_NOTHROW_ASSIGN:
14650 58294 : case CPTK_HAS_TRIVIAL_ASSIGN:
14651 58294 : case CPTK_HAS_NOTHROW_CONSTRUCTOR:
14652 58294 : case CPTK_HAS_TRIVIAL_CONSTRUCTOR:
14653 58294 : case CPTK_HAS_NOTHROW_COPY:
14654 58294 : case CPTK_HAS_TRIVIAL_COPY:
14655 58294 : case CPTK_HAS_TRIVIAL_DESTRUCTOR:
14656 58294 : case CPTK_IS_DESTRUCTIBLE:
14657 58294 : case CPTK_IS_NOTHROW_DESTRUCTIBLE:
14658 58294 : case CPTK_IS_TRIVIALLY_DESTRUCTIBLE:
14659 58294 : if (!check_trait_type (type1, /*kind=*/1, complain))
14660 57 : return error_mark_node;
14661 : break;
14662 :
14663 319861 : case CPTK_IS_LITERAL_TYPE:
14664 319861 : case CPTK_IS_POD:
14665 319861 : case CPTK_IS_STD_LAYOUT:
14666 319861 : case CPTK_IS_TRIVIAL:
14667 319861 : case CPTK_IS_TRIVIALLY_COPYABLE:
14668 319861 : case CPTK_IS_STRUCTURAL:
14669 319861 : case CPTK_HAS_UNIQUE_OBJ_REPRESENTATIONS:
14670 319861 : if (!check_trait_type (type1, /* kind = */ 2, complain))
14671 133 : return error_mark_node;
14672 : break;
14673 :
14674 281490 : case CPTK_IS_ABSTRACT:
14675 281490 : case CPTK_IS_EMPTY:
14676 281490 : case CPTK_IS_POLYMORPHIC:
14677 281490 : case CPTK_HAS_VIRTUAL_DESTRUCTOR:
14678 281490 : if (!check_trait_type (type1, /* kind = */ 3, complain))
14679 39 : return error_mark_node;
14680 : break;
14681 :
14682 : /* N.B. std::is_aggregate is kind=2 but we don't need a complete element
14683 : type to know whether an array is an aggregate, so use kind=4 here. */
14684 443593 : case CPTK_IS_AGGREGATE:
14685 443593 : case CPTK_IS_FINAL:
14686 443593 : case CPTK_IS_IMPLICIT_LIFETIME:
14687 443593 : if (!check_trait_type (type1, /* kind = */ 4, complain))
14688 55 : return error_mark_node;
14689 : break;
14690 :
14691 6782207 : case CPTK_IS_CONSTRUCTIBLE:
14692 6782207 : case CPTK_IS_CONVERTIBLE:
14693 6782207 : case CPTK_IS_INVOCABLE:
14694 6782207 : case CPTK_IS_NOTHROW_CONSTRUCTIBLE:
14695 6782207 : case CPTK_IS_NOTHROW_CONVERTIBLE:
14696 6782207 : case CPTK_IS_NOTHROW_INVOCABLE:
14697 6782207 : case CPTK_IS_TRIVIALLY_CONSTRUCTIBLE:
14698 6782207 : /* Don't check completeness for direct reference binding. */;
14699 6782207 : if (same_type_ref_bind_p (kind, type1, type2))
14700 : break;
14701 7730881 : gcc_fallthrough ();
14702 :
14703 7730881 : case CPTK_IS_ASSIGNABLE:
14704 7730881 : case CPTK_IS_NOTHROW_ASSIGNABLE:
14705 7730881 : case CPTK_IS_TRIVIALLY_ASSIGNABLE:
14706 7730881 : case CPTK_REF_CONSTRUCTS_FROM_TEMPORARY:
14707 7730881 : case CPTK_REF_CONVERTS_FROM_TEMPORARY:
14708 7730881 : if (!check_trait_type (type1, /*kind=*/1, complain)
14709 7730881 : || !check_trait_type (type2, /*kind=*/1, complain))
14710 602 : return error_mark_node;
14711 : break;
14712 :
14713 526988 : case CPTK_IS_BASE_OF:
14714 526988 : case CPTK_IS_POINTER_INTERCONVERTIBLE_BASE_OF:
14715 526871 : if (NON_UNION_CLASS_TYPE_P (type1) && NON_UNION_CLASS_TYPE_P (type2)
14716 507918 : && !same_type_ignoring_top_level_qualifiers_p (type1, type2)
14717 1006186 : && !complete_type_or_maybe_complain (type2, NULL_TREE, complain))
14718 : /* We already issued an error. */
14719 27 : return error_mark_node;
14720 : break;
14721 :
14722 910 : case CPTK_IS_VIRTUAL_BASE_OF:
14723 830 : if (NON_UNION_CLASS_TYPE_P (type1) && NON_UNION_CLASS_TYPE_P (type2)
14724 1718 : && !complete_type_or_maybe_complain (type2, NULL_TREE, complain))
14725 : /* We already issued an error. */
14726 27 : return error_mark_node;
14727 : break;
14728 :
14729 : case CPTK_IS_ARRAY:
14730 : case CPTK_IS_BOUNDED_ARRAY:
14731 : case CPTK_IS_CLASS:
14732 : case CPTK_IS_CONST:
14733 : case CPTK_IS_ENUM:
14734 : case CPTK_IS_FUNCTION:
14735 : case CPTK_IS_MEMBER_FUNCTION_POINTER:
14736 : case CPTK_IS_MEMBER_OBJECT_POINTER:
14737 : case CPTK_IS_MEMBER_POINTER:
14738 : case CPTK_IS_OBJECT:
14739 : case CPTK_IS_POINTER:
14740 : case CPTK_IS_REFERENCE:
14741 : case CPTK_IS_SAME:
14742 : case CPTK_IS_SCOPED_ENUM:
14743 : case CPTK_IS_UNBOUNDED_ARRAY:
14744 : case CPTK_IS_UNION:
14745 : case CPTK_IS_VOLATILE:
14746 : break;
14747 :
14748 : case CPTK_RANK:
14749 : {
14750 : size_t rank = 0;
14751 122 : for (; TREE_CODE (type1) == ARRAY_TYPE; type1 = TREE_TYPE (type1))
14752 80 : ++rank;
14753 42 : return maybe_wrap_with_location (build_int_cst (size_type_node, rank),
14754 : loc);
14755 : }
14756 :
14757 460 : case CPTK_TYPE_ORDER:
14758 460 : return maybe_wrap_with_location (type_order_value (type1, type2), loc);
14759 :
14760 279 : case CPTK_STRUCTURED_BINDING_SIZE:
14761 279 : if (!check_trait_type (type1, /* kind = */ 4, complain))
14762 3 : return error_mark_node;
14763 276 : return finish_structured_binding_size (loc, type1, complain);
14764 :
14765 242 : case CPTK_IS_LAYOUT_COMPATIBLE:
14766 242 : if (!array_of_unknown_bound_p (type1)
14767 223 : && TREE_CODE (type1) != VOID_TYPE
14768 456 : && !complete_type_or_maybe_complain (type1, NULL_TREE, complain))
14769 : /* We already issued an error. */
14770 12 : return error_mark_node;
14771 230 : if (!array_of_unknown_bound_p (type2)
14772 203 : && TREE_CODE (type2) != VOID_TYPE
14773 424 : && !complete_type_or_maybe_complain (type2, NULL_TREE, complain))
14774 : /* We already issued an error. */
14775 9 : return error_mark_node;
14776 : break;
14777 :
14778 85 : case CPTK_IS_DEDUCIBLE:
14779 85 : if (!DECL_TYPE_TEMPLATE_P (type1))
14780 : {
14781 0 : error ("%qD is not a class or alias template", type1);
14782 0 : return error_mark_node;
14783 : }
14784 : break;
14785 :
14786 : #define DEFTRAIT_TYPE(CODE, NAME, ARITY) \
14787 : case CPTK_##CODE:
14788 : #include "cp-trait.def"
14789 : #undef DEFTRAIT_TYPE
14790 : /* Type-yielding traits are handled in finish_trait_type. */
14791 0 : gcc_unreachable ();
14792 : }
14793 :
14794 18404485 : tree val = (trait_expr_value (kind, type1, type2)
14795 18404485 : ? boolean_true_node : boolean_false_node);
14796 18404485 : return maybe_wrap_with_location (val, loc);
14797 : }
14798 :
14799 : /* Process a trait type. */
14800 :
14801 : tree
14802 8123533 : finish_trait_type (cp_trait_kind kind, tree type1, tree type2,
14803 : tsubst_flags_t complain)
14804 : {
14805 8124477 : if (type1 == error_mark_node
14806 8124474 : || type2 == error_mark_node)
14807 : return error_mark_node;
14808 :
14809 8124474 : if (processing_template_decl)
14810 : {
14811 237746 : tree type = cxx_make_type (TRAIT_TYPE);
14812 237746 : TRAIT_TYPE_TYPE1 (type) = type1;
14813 237746 : TRAIT_TYPE_TYPE2 (type) = type2;
14814 237746 : TRAIT_TYPE_KIND_RAW (type) = build_int_cstu (integer_type_node, kind);
14815 : /* These traits are intended to be used in the definition of the ::type
14816 : member of the corresponding standard library type trait and aren't
14817 : mangleable (and thus won't appear directly in template signatures),
14818 : so structural equality should suffice. */
14819 237746 : SET_TYPE_STRUCTURAL_EQUALITY (type);
14820 237746 : return type;
14821 : }
14822 :
14823 7886728 : switch (kind)
14824 : {
14825 1266541 : case CPTK_ADD_LVALUE_REFERENCE:
14826 : /* [meta.trans.ref]. */
14827 1266541 : if (referenceable_type_p (type1))
14828 1266454 : return cp_build_reference_type (type1, /*rval=*/false);
14829 : return type1;
14830 :
14831 657118 : case CPTK_ADD_POINTER:
14832 : /* [meta.trans.ptr]. */
14833 657118 : if (VOID_TYPE_P (type1) || referenceable_type_p (type1))
14834 : {
14835 657086 : if (TYPE_REF_P (type1))
14836 655885 : type1 = TREE_TYPE (type1);
14837 657086 : return build_pointer_type (type1);
14838 : }
14839 : return type1;
14840 :
14841 1708065 : case CPTK_ADD_RVALUE_REFERENCE:
14842 : /* [meta.trans.ref]. */
14843 1708065 : if (referenceable_type_p (type1))
14844 1708007 : return cp_build_reference_type (type1, /*rval=*/true);
14845 : return type1;
14846 :
14847 240846 : case CPTK_DECAY:
14848 240846 : if (TYPE_REF_P (type1))
14849 43681 : type1 = TREE_TYPE (type1);
14850 :
14851 240846 : if (TREE_CODE (type1) == ARRAY_TYPE)
14852 735 : return finish_trait_type (CPTK_ADD_POINTER, TREE_TYPE (type1), type2,
14853 735 : complain);
14854 240111 : else if (TREE_CODE (type1) == FUNCTION_TYPE)
14855 : return finish_trait_type (CPTK_ADD_POINTER, type1, type2, complain);
14856 : else
14857 239902 : return cv_unqualified (type1);
14858 :
14859 223 : case CPTK_REMOVE_ALL_EXTENTS:
14860 223 : return strip_array_types (type1);
14861 :
14862 1015378 : case CPTK_REMOVE_CV:
14863 1015378 : return cv_unqualified (type1);
14864 :
14865 485148 : case CPTK_REMOVE_CVREF:
14866 485148 : if (TYPE_REF_P (type1))
14867 184497 : type1 = TREE_TYPE (type1);
14868 485148 : return cv_unqualified (type1);
14869 :
14870 67087 : case CPTK_REMOVE_EXTENT:
14871 67087 : if (TREE_CODE (type1) == ARRAY_TYPE)
14872 9536 : type1 = TREE_TYPE (type1);
14873 : return type1;
14874 :
14875 45247 : case CPTK_REMOVE_POINTER:
14876 45247 : if (TYPE_PTR_P (type1))
14877 42345 : type1 = TREE_TYPE (type1);
14878 : return type1;
14879 :
14880 2238620 : case CPTK_REMOVE_REFERENCE:
14881 2238620 : if (TYPE_REF_P (type1))
14882 1359551 : type1 = TREE_TYPE (type1);
14883 : return type1;
14884 :
14885 113502 : case CPTK_TYPE_PACK_ELEMENT:
14886 113502 : return finish_type_pack_element (type1, type2, complain);
14887 :
14888 48953 : case CPTK_UNDERLYING_TYPE:
14889 48953 : return finish_underlying_type (type1);
14890 :
14891 : #define DEFTRAIT_EXPR(CODE, NAME, ARITY) \
14892 : case CPTK_##CODE:
14893 : #include "cp-trait.def"
14894 : #undef DEFTRAIT_EXPR
14895 : /* Expression-yielding traits are handled in finish_trait_expr. */
14896 : case CPTK_BASES:
14897 : case CPTK_DIRECT_BASES:
14898 : /* BASES and DIRECT_BASES are handled in finish_bases. */
14899 : break;
14900 : }
14901 :
14902 0 : gcc_unreachable ();
14903 : }
14904 :
14905 : /* Do-nothing variants of functions to handle pragma FLOAT_CONST_DECIMAL64,
14906 : which is ignored for C++. */
14907 :
14908 : void
14909 0 : set_float_const_decimal64 (void)
14910 : {
14911 0 : }
14912 :
14913 : void
14914 0 : clear_float_const_decimal64 (void)
14915 : {
14916 0 : }
14917 :
14918 : bool
14919 1905478 : float_const_decimal64_p (void)
14920 : {
14921 1905478 : return 0;
14922 : }
14923 :
14924 :
14925 : /* Return true if T designates the implied `this' parameter. */
14926 :
14927 : bool
14928 6730800 : is_this_parameter (tree t)
14929 : {
14930 6730800 : if (!DECL_P (t) || DECL_NAME (t) != this_identifier)
14931 : return false;
14932 3929768 : gcc_assert (TREE_CODE (t) == PARM_DECL
14933 : || (VAR_P (t) && DECL_HAS_VALUE_EXPR_P (t))
14934 : || (cp_binding_oracle && VAR_P (t)));
14935 : return true;
14936 : }
14937 :
14938 : /* As above, or a C++23 explicit object parameter. */
14939 :
14940 : bool
14941 456 : is_object_parameter (tree t)
14942 : {
14943 456 : if (is_this_parameter (t))
14944 : return true;
14945 91 : if (TREE_CODE (t) != PARM_DECL)
14946 : return false;
14947 34 : tree ctx = DECL_CONTEXT (t);
14948 34 : return (ctx && DECL_XOBJ_MEMBER_FUNCTION_P (ctx)
14949 62 : && t == DECL_ARGUMENTS (ctx));
14950 : }
14951 :
14952 : /* Insert the deduced return type for an auto function. */
14953 :
14954 : void
14955 1080968 : apply_deduced_return_type (tree fco, tree return_type)
14956 : {
14957 1080968 : tree result;
14958 :
14959 1080968 : if (return_type == error_mark_node)
14960 : return;
14961 :
14962 1080965 : if (DECL_CONV_FN_P (fco))
14963 42 : DECL_NAME (fco) = make_conv_op_name (return_type);
14964 :
14965 1080965 : TREE_TYPE (fco) = change_return_type (return_type, TREE_TYPE (fco));
14966 :
14967 1080965 : maybe_update_postconditions (fco);
14968 :
14969 : /* Apply the type to the result object. */
14970 :
14971 1080965 : result = DECL_RESULT (fco);
14972 1080965 : if (result == NULL_TREE)
14973 : return;
14974 1068394 : if (TREE_TYPE (result) == return_type)
14975 : return;
14976 :
14977 1068391 : if (!processing_template_decl && !VOID_TYPE_P (return_type)
14978 1976870 : && !complete_type_or_else (return_type, NULL_TREE))
14979 : return;
14980 :
14981 : /* We already have a DECL_RESULT from start_preparsed_function.
14982 : Now we need to redo the work it and allocate_struct_function
14983 : did to reflect the new type. */
14984 1068391 : result = build_decl (DECL_SOURCE_LOCATION (result), RESULT_DECL, NULL_TREE,
14985 1068391 : TYPE_MAIN_VARIANT (return_type));
14986 1068391 : DECL_ARTIFICIAL (result) = 1;
14987 1068391 : DECL_IGNORED_P (result) = 1;
14988 1068391 : cp_apply_type_quals_to_decl (cp_type_quals (return_type),
14989 : result);
14990 1068391 : DECL_RESULT (fco) = result;
14991 :
14992 1068391 : if (!uses_template_parms (fco))
14993 1068391 : if (function *fun = DECL_STRUCT_FUNCTION (fco))
14994 : {
14995 1067385 : bool aggr = aggregate_value_p (result, fco);
14996 : #ifdef PCC_STATIC_STRUCT_RETURN
14997 : fun->returns_pcc_struct = aggr;
14998 : #endif
14999 1067385 : fun->returns_struct = aggr;
15000 : }
15001 : }
15002 :
15003 : /* Build a unary fold expression of EXPR over OP. If IS_RIGHT is true,
15004 : this is a right unary fold. Otherwise it is a left unary fold. */
15005 :
15006 : static tree
15007 856250 : finish_unary_fold_expr (location_t loc, tree expr, int op, tree_code dir)
15008 : {
15009 : /* Build a pack expansion (assuming expr has pack type). */
15010 856250 : if (!uses_parameter_packs (expr))
15011 : {
15012 3 : error_at (location_of (expr), "operand of fold expression has no "
15013 : "unexpanded parameter packs");
15014 3 : return error_mark_node;
15015 : }
15016 856247 : tree pack = make_pack_expansion (expr);
15017 :
15018 : /* Build the fold expression. */
15019 856247 : tree code = build_int_cstu (integer_type_node, abs (op));
15020 856247 : tree fold = build_min_nt_loc (loc, dir, code, pack);
15021 856247 : FOLD_EXPR_MODIFY_P (fold) = (op < 0);
15022 856247 : TREE_TYPE (fold) = build_dependent_operator_type (NULL_TREE,
15023 856247 : FOLD_EXPR_OP (fold),
15024 856247 : FOLD_EXPR_MODIFY_P (fold));
15025 856247 : return fold;
15026 : }
15027 :
15028 : tree
15029 26347 : finish_left_unary_fold_expr (location_t loc, tree expr, int op)
15030 : {
15031 26347 : return finish_unary_fold_expr (loc, expr, op, UNARY_LEFT_FOLD_EXPR);
15032 : }
15033 :
15034 : tree
15035 829903 : finish_right_unary_fold_expr (location_t loc, tree expr, int op)
15036 : {
15037 829903 : return finish_unary_fold_expr (loc, expr, op, UNARY_RIGHT_FOLD_EXPR);
15038 : }
15039 :
15040 : /* Build a binary fold expression over EXPR1 and EXPR2. The
15041 : associativity of the fold is determined by EXPR1 and EXPR2 (whichever
15042 : has an unexpanded parameter pack). */
15043 :
15044 : static tree
15045 198330 : finish_binary_fold_expr (location_t loc, tree pack, tree init,
15046 : int op, tree_code dir)
15047 : {
15048 198330 : pack = make_pack_expansion (pack);
15049 198330 : tree code = build_int_cstu (integer_type_node, abs (op));
15050 198330 : tree fold = build_min_nt_loc (loc, dir, code, pack, init);
15051 198330 : FOLD_EXPR_MODIFY_P (fold) = (op < 0);
15052 198330 : TREE_TYPE (fold) = build_dependent_operator_type (NULL_TREE,
15053 198330 : FOLD_EXPR_OP (fold),
15054 198330 : FOLD_EXPR_MODIFY_P (fold));
15055 198330 : return fold;
15056 : }
15057 :
15058 : tree
15059 198330 : finish_binary_fold_expr (location_t loc, tree expr1, tree expr2, int op)
15060 : {
15061 : // Determine which expr has an unexpanded parameter pack and
15062 : // set the pack and initial term.
15063 198330 : bool pack1 = uses_parameter_packs (expr1);
15064 198330 : bool pack2 = uses_parameter_packs (expr2);
15065 198330 : if (pack1 && !pack2)
15066 1097 : return finish_binary_fold_expr (loc, expr1, expr2, op, BINARY_RIGHT_FOLD_EXPR);
15067 197233 : else if (pack2 && !pack1)
15068 197233 : return finish_binary_fold_expr (loc, expr2, expr1, op, BINARY_LEFT_FOLD_EXPR);
15069 : else
15070 : {
15071 0 : if (pack1)
15072 0 : error ("both arguments in binary fold have unexpanded parameter packs");
15073 : else
15074 0 : error ("no unexpanded parameter packs in binary fold");
15075 : }
15076 0 : return error_mark_node;
15077 : }
15078 :
15079 : /* Finish __builtin_launder (arg). */
15080 :
15081 : tree
15082 14354 : finish_builtin_launder (location_t loc, tree arg, tsubst_flags_t complain)
15083 : {
15084 14354 : tree orig_arg = arg;
15085 14354 : if (!type_dependent_expression_p (arg))
15086 84 : arg = decay_conversion (arg, complain);
15087 14354 : if (error_operand_p (arg))
15088 0 : return error_mark_node;
15089 14354 : if (!type_dependent_expression_p (arg) && !TYPE_PTROB_P (TREE_TYPE (arg)))
15090 : {
15091 24 : error_at (loc, "type %qT of argument to %<__builtin_launder%> "
15092 24 : "is not a pointer to object type", TREE_TYPE (arg));
15093 24 : return error_mark_node;
15094 : }
15095 14330 : if (processing_template_decl)
15096 14270 : arg = orig_arg;
15097 14330 : return build_call_expr_internal_loc (loc, IFN_LAUNDER,
15098 28660 : TREE_TYPE (arg), 1, arg);
15099 : }
15100 :
15101 : /* Finish __builtin_convertvector (arg, type). */
15102 :
15103 : tree
15104 486 : cp_build_vec_convert (tree arg, location_t loc, tree type,
15105 : tsubst_flags_t complain)
15106 : {
15107 486 : if (error_operand_p (type))
15108 9 : return error_mark_node;
15109 477 : if (error_operand_p (arg))
15110 0 : return error_mark_node;
15111 :
15112 477 : tree ret = NULL_TREE;
15113 477 : if (!type_dependent_expression_p (arg) && !dependent_type_p (type))
15114 439 : ret = c_build_vec_convert (cp_expr_loc_or_input_loc (arg),
15115 : decay_conversion (arg, complain),
15116 : loc, type, (complain & tf_error) != 0);
15117 :
15118 477 : if (!processing_template_decl)
15119 : return ret;
15120 :
15121 80 : return build_call_expr_internal_loc (loc, IFN_VEC_CONVERT, type, 1, arg);
15122 : }
15123 :
15124 : /* Finish __builtin_bit_cast (type, arg). */
15125 :
15126 : tree
15127 297015 : cp_build_bit_cast (location_t loc, tree type, tree arg,
15128 : tsubst_flags_t complain)
15129 : {
15130 297015 : if (error_operand_p (type))
15131 0 : return error_mark_node;
15132 297015 : if (!dependent_type_p (type))
15133 : {
15134 215274 : if (!complete_type_or_maybe_complain (type, NULL_TREE, complain))
15135 9 : return error_mark_node;
15136 215265 : if (TREE_CODE (type) == ARRAY_TYPE)
15137 : {
15138 : /* std::bit_cast for destination ARRAY_TYPE is not possible,
15139 : as functions may not return an array, so don't bother trying
15140 : to support this (and then deal with VLAs etc.). */
15141 9 : error_at (loc, "%<__builtin_bit_cast%> destination type %qT "
15142 : "is an array type", type);
15143 9 : return error_mark_node;
15144 : }
15145 215256 : if (!trivially_copyable_p (type))
15146 : {
15147 18 : error_at (loc, "%<__builtin_bit_cast%> destination type %qT "
15148 : "is not trivially copyable", type);
15149 18 : return error_mark_node;
15150 : }
15151 : }
15152 :
15153 296979 : if (error_operand_p (arg))
15154 0 : return error_mark_node;
15155 :
15156 296979 : if (!type_dependent_expression_p (arg))
15157 : {
15158 115694 : if (TREE_CODE (TREE_TYPE (arg)) == ARRAY_TYPE)
15159 : {
15160 : /* Don't perform array-to-pointer conversion. */
15161 375 : arg = mark_rvalue_use (arg, loc, true);
15162 375 : if (!complete_type_or_maybe_complain (TREE_TYPE (arg), arg, complain))
15163 0 : return error_mark_node;
15164 : }
15165 : else
15166 115319 : arg = decay_conversion (arg, complain);
15167 :
15168 115694 : if (error_operand_p (arg))
15169 12 : return error_mark_node;
15170 :
15171 115682 : if (!trivially_copyable_p (TREE_TYPE (arg)))
15172 : {
15173 9 : error_at (cp_expr_loc_or_loc (arg, loc),
15174 : "%<__builtin_bit_cast%> source type %qT "
15175 9 : "is not trivially copyable", TREE_TYPE (arg));
15176 9 : return error_mark_node;
15177 : }
15178 115673 : if (!dependent_type_p (type)
15179 192854 : && !cp_tree_equal (TYPE_SIZE_UNIT (type),
15180 77181 : TYPE_SIZE_UNIT (TREE_TYPE (arg))))
15181 : {
15182 18 : error_at (loc, "%<__builtin_bit_cast%> source size %qE "
15183 : "not equal to destination type size %qE",
15184 18 : TYPE_SIZE_UNIT (TREE_TYPE (arg)),
15185 18 : TYPE_SIZE_UNIT (type));
15186 18 : return error_mark_node;
15187 : }
15188 : }
15189 :
15190 296940 : tree ret = build_min (BIT_CAST_EXPR, type, arg);
15191 296940 : SET_EXPR_LOCATION (ret, loc);
15192 :
15193 296940 : if (!processing_template_decl && CLASS_TYPE_P (type))
15194 874 : ret = get_target_expr (ret, complain);
15195 :
15196 : return ret;
15197 : }
15198 :
15199 : /* Diagnose invalid #pragma GCC unroll argument and adjust
15200 : it if needed. */
15201 :
15202 : tree
15203 24724 : cp_check_pragma_unroll (location_t loc, tree unroll)
15204 : {
15205 24724 : HOST_WIDE_INT lunroll = 0;
15206 24724 : if (type_dependent_expression_p (unroll))
15207 : ;
15208 49376 : else if (!INTEGRAL_TYPE_P (TREE_TYPE (unroll))
15209 49330 : || (!value_dependent_expression_p (unroll)
15210 24612 : && (!tree_fits_shwi_p (unroll)
15211 24586 : || (lunroll = tree_to_shwi (unroll)) < 0
15212 24571 : || lunroll >= USHRT_MAX)))
15213 : {
15214 90 : error_at (loc, "%<#pragma GCC unroll%> requires an"
15215 : " assignment-expression that evaluates to a non-negative"
15216 : " integral constant less than %u", USHRT_MAX);
15217 90 : unroll = integer_one_node;
15218 : }
15219 24598 : else if (TREE_CODE (unroll) == INTEGER_CST)
15220 : {
15221 24568 : unroll = fold_convert (integer_type_node, unroll);
15222 24568 : if (integer_zerop (unroll))
15223 12 : unroll = integer_one_node;
15224 : }
15225 24724 : return unroll;
15226 : }
15227 :
15228 : #include "gt-cp-semantics.h"
|