[ree] PR rtl-optimization/78038: Handle global register dataflow definitions in ree
[official-gcc.git] / gcc / gimplify.c
blob254dc735f0f23dcdaa5e4ef0836f15c673c7514d
1 /* Tree lowering pass. This pass converts the GENERIC functions-as-trees
2 tree representation into the GIMPLE form.
3 Copyright (C) 2002-2016 Free Software Foundation, Inc.
4 Major work done by Sebastian Pop <s.pop@laposte.net>,
5 Diego Novillo <dnovillo@redhat.com> and Jason Merrill <jason@redhat.com>.
7 This file is part of GCC.
9 GCC is free software; you can redistribute it and/or modify it under
10 the terms of the GNU General Public License as published by the Free
11 Software Foundation; either version 3, or (at your option) any later
12 version.
14 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15 WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17 for more details.
19 You should have received a copy of the GNU General Public License
20 along with GCC; see the file COPYING3. If not see
21 <http://www.gnu.org/licenses/>. */
23 #include "config.h"
24 #include "system.h"
25 #include "coretypes.h"
26 #include "backend.h"
27 #include "target.h"
28 #include "rtl.h"
29 #include "tree.h"
30 #include "gimple.h"
31 #include "gimple-predict.h"
32 #include "tree-pass.h" /* FIXME: only for PROP_gimple_any */
33 #include "ssa.h"
34 #include "cgraph.h"
35 #include "tree-pretty-print.h"
36 #include "diagnostic-core.h"
37 #include "alias.h"
38 #include "fold-const.h"
39 #include "calls.h"
40 #include "varasm.h"
41 #include "stmt.h"
42 #include "expr.h"
43 #include "gimple-fold.h"
44 #include "tree-eh.h"
45 #include "gimplify.h"
46 #include "gimple-iterator.h"
47 #include "stor-layout.h"
48 #include "print-tree.h"
49 #include "tree-iterator.h"
50 #include "tree-inline.h"
51 #include "langhooks.h"
52 #include "tree-cfg.h"
53 #include "tree-ssa.h"
54 #include "omp-low.h"
55 #include "gimple-low.h"
56 #include "cilk.h"
57 #include "gomp-constants.h"
58 #include "tree-dump.h"
59 #include "gimple-walk.h"
60 #include "langhooks-def.h" /* FIXME: for lhd_set_decl_assembler_name */
61 #include "builtins.h"
63 enum gimplify_omp_var_data
65 GOVD_SEEN = 1,
66 GOVD_EXPLICIT = 2,
67 GOVD_SHARED = 4,
68 GOVD_PRIVATE = 8,
69 GOVD_FIRSTPRIVATE = 16,
70 GOVD_LASTPRIVATE = 32,
71 GOVD_REDUCTION = 64,
72 GOVD_LOCAL = 128,
73 GOVD_MAP = 256,
74 GOVD_DEBUG_PRIVATE = 512,
75 GOVD_PRIVATE_OUTER_REF = 1024,
76 GOVD_LINEAR = 2048,
77 GOVD_ALIGNED = 4096,
79 /* Flag for GOVD_MAP: don't copy back. */
80 GOVD_MAP_TO_ONLY = 8192,
82 /* Flag for GOVD_LINEAR or GOVD_LASTPRIVATE: no outer reference. */
83 GOVD_LINEAR_LASTPRIVATE_NO_OUTER = 16384,
85 GOVD_MAP_0LEN_ARRAY = 32768,
87 /* Flag for GOVD_MAP, if it is always, to or always, tofrom mapping. */
88 GOVD_MAP_ALWAYS_TO = 65536,
90 /* Flag for shared vars that are or might be stored to in the region. */
91 GOVD_WRITTEN = 131072,
93 /* Flag for GOVD_MAP, if it is a forced mapping. */
94 GOVD_MAP_FORCE = 262144,
96 GOVD_DATA_SHARE_CLASS = (GOVD_SHARED | GOVD_PRIVATE | GOVD_FIRSTPRIVATE
97 | GOVD_LASTPRIVATE | GOVD_REDUCTION | GOVD_LINEAR
98 | GOVD_LOCAL)
102 enum omp_region_type
104 ORT_WORKSHARE = 0x00,
105 ORT_SIMD = 0x01,
107 ORT_PARALLEL = 0x02,
108 ORT_COMBINED_PARALLEL = 0x03,
110 ORT_TASK = 0x04,
111 ORT_UNTIED_TASK = 0x05,
113 ORT_TEAMS = 0x08,
114 ORT_COMBINED_TEAMS = 0x09,
116 /* Data region. */
117 ORT_TARGET_DATA = 0x10,
119 /* Data region with offloading. */
120 ORT_TARGET = 0x20,
121 ORT_COMBINED_TARGET = 0x21,
123 /* OpenACC variants. */
124 ORT_ACC = 0x40, /* A generic OpenACC region. */
125 ORT_ACC_DATA = ORT_ACC | ORT_TARGET_DATA, /* Data construct. */
126 ORT_ACC_PARALLEL = ORT_ACC | ORT_TARGET, /* Parallel construct */
127 ORT_ACC_KERNELS = ORT_ACC | ORT_TARGET | 0x80, /* Kernels construct. */
128 ORT_ACC_HOST_DATA = ORT_ACC | ORT_TARGET_DATA | 0x80, /* Host data. */
130 /* Dummy OpenMP region, used to disable expansion of
131 DECL_VALUE_EXPRs in taskloop pre body. */
132 ORT_NONE = 0x100
135 /* Gimplify hashtable helper. */
137 struct gimplify_hasher : free_ptr_hash <elt_t>
139 static inline hashval_t hash (const elt_t *);
140 static inline bool equal (const elt_t *, const elt_t *);
143 struct gimplify_ctx
145 struct gimplify_ctx *prev_context;
147 vec<gbind *> bind_expr_stack;
148 tree temps;
149 gimple_seq conditional_cleanups;
150 tree exit_label;
151 tree return_temp;
153 vec<tree> case_labels;
154 /* The formal temporary table. Should this be persistent? */
155 hash_table<gimplify_hasher> *temp_htab;
157 int conditions;
158 unsigned into_ssa : 1;
159 unsigned allow_rhs_cond_expr : 1;
160 unsigned in_cleanup_point_expr : 1;
161 unsigned keep_stack : 1;
162 unsigned save_stack : 1;
163 unsigned in_switch_expr : 1;
166 struct gimplify_omp_ctx
168 struct gimplify_omp_ctx *outer_context;
169 splay_tree variables;
170 hash_set<tree> *privatized_types;
171 /* Iteration variables in an OMP_FOR. */
172 vec<tree> loop_iter_var;
173 location_t location;
174 enum omp_clause_default_kind default_kind;
175 enum omp_region_type region_type;
176 bool combined_loop;
177 bool distribute;
178 bool target_map_scalars_firstprivate;
179 bool target_map_pointers_as_0len_arrays;
180 bool target_firstprivatize_array_bases;
183 static struct gimplify_ctx *gimplify_ctxp;
184 static struct gimplify_omp_ctx *gimplify_omp_ctxp;
186 /* Forward declaration. */
187 static enum gimplify_status gimplify_compound_expr (tree *, gimple_seq *, bool);
188 static hash_map<tree, tree> *oacc_declare_returns;
189 static enum gimplify_status gimplify_expr (tree *, gimple_seq *, gimple_seq *,
190 bool (*) (tree), fallback_t, bool);
192 /* Shorter alias name for the above function for use in gimplify.c
193 only. */
195 static inline void
196 gimplify_seq_add_stmt (gimple_seq *seq_p, gimple *gs)
198 gimple_seq_add_stmt_without_update (seq_p, gs);
201 /* Append sequence SRC to the end of sequence *DST_P. If *DST_P is
202 NULL, a new sequence is allocated. This function is
203 similar to gimple_seq_add_seq, but does not scan the operands.
204 During gimplification, we need to manipulate statement sequences
205 before the def/use vectors have been constructed. */
207 static void
208 gimplify_seq_add_seq (gimple_seq *dst_p, gimple_seq src)
210 gimple_stmt_iterator si;
212 if (src == NULL)
213 return;
215 si = gsi_last (*dst_p);
216 gsi_insert_seq_after_without_update (&si, src, GSI_NEW_STMT);
220 /* Pointer to a list of allocated gimplify_ctx structs to be used for pushing
221 and popping gimplify contexts. */
223 static struct gimplify_ctx *ctx_pool = NULL;
225 /* Return a gimplify context struct from the pool. */
227 static inline struct gimplify_ctx *
228 ctx_alloc (void)
230 struct gimplify_ctx * c = ctx_pool;
232 if (c)
233 ctx_pool = c->prev_context;
234 else
235 c = XNEW (struct gimplify_ctx);
237 memset (c, '\0', sizeof (*c));
238 return c;
241 /* Put gimplify context C back into the pool. */
243 static inline void
244 ctx_free (struct gimplify_ctx *c)
246 c->prev_context = ctx_pool;
247 ctx_pool = c;
250 /* Free allocated ctx stack memory. */
252 void
253 free_gimplify_stack (void)
255 struct gimplify_ctx *c;
257 while ((c = ctx_pool))
259 ctx_pool = c->prev_context;
260 free (c);
265 /* Set up a context for the gimplifier. */
267 void
268 push_gimplify_context (bool in_ssa, bool rhs_cond_ok)
270 struct gimplify_ctx *c = ctx_alloc ();
272 c->prev_context = gimplify_ctxp;
273 gimplify_ctxp = c;
274 gimplify_ctxp->into_ssa = in_ssa;
275 gimplify_ctxp->allow_rhs_cond_expr = rhs_cond_ok;
278 /* Tear down a context for the gimplifier. If BODY is non-null, then
279 put the temporaries into the outer BIND_EXPR. Otherwise, put them
280 in the local_decls.
282 BODY is not a sequence, but the first tuple in a sequence. */
284 void
285 pop_gimplify_context (gimple *body)
287 struct gimplify_ctx *c = gimplify_ctxp;
289 gcc_assert (c
290 && (!c->bind_expr_stack.exists ()
291 || c->bind_expr_stack.is_empty ()));
292 c->bind_expr_stack.release ();
293 gimplify_ctxp = c->prev_context;
295 if (body)
296 declare_vars (c->temps, body, false);
297 else
298 record_vars (c->temps);
300 delete c->temp_htab;
301 c->temp_htab = NULL;
302 ctx_free (c);
305 /* Push a GIMPLE_BIND tuple onto the stack of bindings. */
307 static void
308 gimple_push_bind_expr (gbind *bind_stmt)
310 gimplify_ctxp->bind_expr_stack.reserve (8);
311 gimplify_ctxp->bind_expr_stack.safe_push (bind_stmt);
314 /* Pop the first element off the stack of bindings. */
316 static void
317 gimple_pop_bind_expr (void)
319 gimplify_ctxp->bind_expr_stack.pop ();
322 /* Return the first element of the stack of bindings. */
324 gbind *
325 gimple_current_bind_expr (void)
327 return gimplify_ctxp->bind_expr_stack.last ();
330 /* Return the stack of bindings created during gimplification. */
332 vec<gbind *>
333 gimple_bind_expr_stack (void)
335 return gimplify_ctxp->bind_expr_stack;
338 /* Return true iff there is a COND_EXPR between us and the innermost
339 CLEANUP_POINT_EXPR. This info is used by gimple_push_cleanup. */
341 static bool
342 gimple_conditional_context (void)
344 return gimplify_ctxp->conditions > 0;
347 /* Note that we've entered a COND_EXPR. */
349 static void
350 gimple_push_condition (void)
352 #ifdef ENABLE_GIMPLE_CHECKING
353 if (gimplify_ctxp->conditions == 0)
354 gcc_assert (gimple_seq_empty_p (gimplify_ctxp->conditional_cleanups));
355 #endif
356 ++(gimplify_ctxp->conditions);
359 /* Note that we've left a COND_EXPR. If we're back at unconditional scope
360 now, add any conditional cleanups we've seen to the prequeue. */
362 static void
363 gimple_pop_condition (gimple_seq *pre_p)
365 int conds = --(gimplify_ctxp->conditions);
367 gcc_assert (conds >= 0);
368 if (conds == 0)
370 gimplify_seq_add_seq (pre_p, gimplify_ctxp->conditional_cleanups);
371 gimplify_ctxp->conditional_cleanups = NULL;
375 /* A stable comparison routine for use with splay trees and DECLs. */
377 static int
378 splay_tree_compare_decl_uid (splay_tree_key xa, splay_tree_key xb)
380 tree a = (tree) xa;
381 tree b = (tree) xb;
383 return DECL_UID (a) - DECL_UID (b);
386 /* Create a new omp construct that deals with variable remapping. */
388 static struct gimplify_omp_ctx *
389 new_omp_context (enum omp_region_type region_type)
391 struct gimplify_omp_ctx *c;
393 c = XCNEW (struct gimplify_omp_ctx);
394 c->outer_context = gimplify_omp_ctxp;
395 c->variables = splay_tree_new (splay_tree_compare_decl_uid, 0, 0);
396 c->privatized_types = new hash_set<tree>;
397 c->location = input_location;
398 c->region_type = region_type;
399 if ((region_type & ORT_TASK) == 0)
400 c->default_kind = OMP_CLAUSE_DEFAULT_SHARED;
401 else
402 c->default_kind = OMP_CLAUSE_DEFAULT_UNSPECIFIED;
404 return c;
407 /* Destroy an omp construct that deals with variable remapping. */
409 static void
410 delete_omp_context (struct gimplify_omp_ctx *c)
412 splay_tree_delete (c->variables);
413 delete c->privatized_types;
414 c->loop_iter_var.release ();
415 XDELETE (c);
418 static void omp_add_variable (struct gimplify_omp_ctx *, tree, unsigned int);
419 static bool omp_notice_variable (struct gimplify_omp_ctx *, tree, bool);
421 /* Both gimplify the statement T and append it to *SEQ_P. This function
422 behaves exactly as gimplify_stmt, but you don't have to pass T as a
423 reference. */
425 void
426 gimplify_and_add (tree t, gimple_seq *seq_p)
428 gimplify_stmt (&t, seq_p);
431 /* Gimplify statement T into sequence *SEQ_P, and return the first
432 tuple in the sequence of generated tuples for this statement.
433 Return NULL if gimplifying T produced no tuples. */
435 static gimple *
436 gimplify_and_return_first (tree t, gimple_seq *seq_p)
438 gimple_stmt_iterator last = gsi_last (*seq_p);
440 gimplify_and_add (t, seq_p);
442 if (!gsi_end_p (last))
444 gsi_next (&last);
445 return gsi_stmt (last);
447 else
448 return gimple_seq_first_stmt (*seq_p);
451 /* Returns true iff T is a valid RHS for an assignment to an un-renamed
452 LHS, or for a call argument. */
454 static bool
455 is_gimple_mem_rhs (tree t)
457 /* If we're dealing with a renamable type, either source or dest must be
458 a renamed variable. */
459 if (is_gimple_reg_type (TREE_TYPE (t)))
460 return is_gimple_val (t);
461 else
462 return is_gimple_val (t) || is_gimple_lvalue (t);
465 /* Return true if T is a CALL_EXPR or an expression that can be
466 assigned to a temporary. Note that this predicate should only be
467 used during gimplification. See the rationale for this in
468 gimplify_modify_expr. */
470 static bool
471 is_gimple_reg_rhs_or_call (tree t)
473 return (get_gimple_rhs_class (TREE_CODE (t)) != GIMPLE_INVALID_RHS
474 || TREE_CODE (t) == CALL_EXPR);
477 /* Return true if T is a valid memory RHS or a CALL_EXPR. Note that
478 this predicate should only be used during gimplification. See the
479 rationale for this in gimplify_modify_expr. */
481 static bool
482 is_gimple_mem_rhs_or_call (tree t)
484 /* If we're dealing with a renamable type, either source or dest must be
485 a renamed variable. */
486 if (is_gimple_reg_type (TREE_TYPE (t)))
487 return is_gimple_val (t);
488 else
489 return (is_gimple_val (t) || is_gimple_lvalue (t)
490 || TREE_CODE (t) == CALL_EXPR);
493 /* Create a temporary with a name derived from VAL. Subroutine of
494 lookup_tmp_var; nobody else should call this function. */
496 static inline tree
497 create_tmp_from_val (tree val)
499 /* Drop all qualifiers and address-space information from the value type. */
500 tree type = TYPE_MAIN_VARIANT (TREE_TYPE (val));
501 tree var = create_tmp_var (type, get_name (val));
502 if (TREE_CODE (TREE_TYPE (var)) == COMPLEX_TYPE
503 || TREE_CODE (TREE_TYPE (var)) == VECTOR_TYPE)
504 DECL_GIMPLE_REG_P (var) = 1;
505 return var;
508 /* Create a temporary to hold the value of VAL. If IS_FORMAL, try to reuse
509 an existing expression temporary. */
511 static tree
512 lookup_tmp_var (tree val, bool is_formal)
514 tree ret;
516 /* If not optimizing, never really reuse a temporary. local-alloc
517 won't allocate any variable that is used in more than one basic
518 block, which means it will go into memory, causing much extra
519 work in reload and final and poorer code generation, outweighing
520 the extra memory allocation here. */
521 if (!optimize || !is_formal || TREE_SIDE_EFFECTS (val))
522 ret = create_tmp_from_val (val);
523 else
525 elt_t elt, *elt_p;
526 elt_t **slot;
528 elt.val = val;
529 if (!gimplify_ctxp->temp_htab)
530 gimplify_ctxp->temp_htab = new hash_table<gimplify_hasher> (1000);
531 slot = gimplify_ctxp->temp_htab->find_slot (&elt, INSERT);
532 if (*slot == NULL)
534 elt_p = XNEW (elt_t);
535 elt_p->val = val;
536 elt_p->temp = ret = create_tmp_from_val (val);
537 *slot = elt_p;
539 else
541 elt_p = *slot;
542 ret = elt_p->temp;
546 return ret;
549 /* Helper for get_formal_tmp_var and get_initialized_tmp_var. */
551 static tree
552 internal_get_tmp_var (tree val, gimple_seq *pre_p, gimple_seq *post_p,
553 bool is_formal, bool allow_ssa)
555 tree t, mod;
557 /* Notice that we explicitly allow VAL to be a CALL_EXPR so that we
558 can create an INIT_EXPR and convert it into a GIMPLE_CALL below. */
559 gimplify_expr (&val, pre_p, post_p, is_gimple_reg_rhs_or_call,
560 fb_rvalue);
562 if (allow_ssa
563 && gimplify_ctxp->into_ssa
564 && is_gimple_reg_type (TREE_TYPE (val)))
566 t = make_ssa_name (TYPE_MAIN_VARIANT (TREE_TYPE (val)));
567 if (! gimple_in_ssa_p (cfun))
569 const char *name = get_name (val);
570 if (name)
571 SET_SSA_NAME_VAR_OR_IDENTIFIER (t, create_tmp_var_name (name));
574 else
575 t = lookup_tmp_var (val, is_formal);
577 mod = build2 (INIT_EXPR, TREE_TYPE (t), t, unshare_expr (val));
579 SET_EXPR_LOCATION (mod, EXPR_LOC_OR_LOC (val, input_location));
581 /* gimplify_modify_expr might want to reduce this further. */
582 gimplify_and_add (mod, pre_p);
583 ggc_free (mod);
585 return t;
588 /* Return a formal temporary variable initialized with VAL. PRE_P is as
589 in gimplify_expr. Only use this function if:
591 1) The value of the unfactored expression represented by VAL will not
592 change between the initialization and use of the temporary, and
593 2) The temporary will not be otherwise modified.
595 For instance, #1 means that this is inappropriate for SAVE_EXPR temps,
596 and #2 means it is inappropriate for && temps.
598 For other cases, use get_initialized_tmp_var instead. */
600 tree
601 get_formal_tmp_var (tree val, gimple_seq *pre_p)
603 return internal_get_tmp_var (val, pre_p, NULL, true, true);
606 /* Return a temporary variable initialized with VAL. PRE_P and POST_P
607 are as in gimplify_expr. */
609 tree
610 get_initialized_tmp_var (tree val, gimple_seq *pre_p, gimple_seq *post_p,
611 bool allow_ssa)
613 return internal_get_tmp_var (val, pre_p, post_p, false, allow_ssa);
616 /* Declare all the variables in VARS in SCOPE. If DEBUG_INFO is true,
617 generate debug info for them; otherwise don't. */
619 void
620 declare_vars (tree vars, gimple *gs, bool debug_info)
622 tree last = vars;
623 if (last)
625 tree temps, block;
627 gbind *scope = as_a <gbind *> (gs);
629 temps = nreverse (last);
631 block = gimple_bind_block (scope);
632 gcc_assert (!block || TREE_CODE (block) == BLOCK);
633 if (!block || !debug_info)
635 DECL_CHAIN (last) = gimple_bind_vars (scope);
636 gimple_bind_set_vars (scope, temps);
638 else
640 /* We need to attach the nodes both to the BIND_EXPR and to its
641 associated BLOCK for debugging purposes. The key point here
642 is that the BLOCK_VARS of the BIND_EXPR_BLOCK of a BIND_EXPR
643 is a subchain of the BIND_EXPR_VARS of the BIND_EXPR. */
644 if (BLOCK_VARS (block))
645 BLOCK_VARS (block) = chainon (BLOCK_VARS (block), temps);
646 else
648 gimple_bind_set_vars (scope,
649 chainon (gimple_bind_vars (scope), temps));
650 BLOCK_VARS (block) = temps;
656 /* For VAR a VAR_DECL of variable size, try to find a constant upper bound
657 for the size and adjust DECL_SIZE/DECL_SIZE_UNIT accordingly. Abort if
658 no such upper bound can be obtained. */
660 static void
661 force_constant_size (tree var)
663 /* The only attempt we make is by querying the maximum size of objects
664 of the variable's type. */
666 HOST_WIDE_INT max_size;
668 gcc_assert (VAR_P (var));
670 max_size = max_int_size_in_bytes (TREE_TYPE (var));
672 gcc_assert (max_size >= 0);
674 DECL_SIZE_UNIT (var)
675 = build_int_cst (TREE_TYPE (DECL_SIZE_UNIT (var)), max_size);
676 DECL_SIZE (var)
677 = build_int_cst (TREE_TYPE (DECL_SIZE (var)), max_size * BITS_PER_UNIT);
680 /* Push the temporary variable TMP into the current binding. */
682 void
683 gimple_add_tmp_var_fn (struct function *fn, tree tmp)
685 gcc_assert (!DECL_CHAIN (tmp) && !DECL_SEEN_IN_BIND_EXPR_P (tmp));
687 /* Later processing assumes that the object size is constant, which might
688 not be true at this point. Force the use of a constant upper bound in
689 this case. */
690 if (!tree_fits_uhwi_p (DECL_SIZE_UNIT (tmp)))
691 force_constant_size (tmp);
693 DECL_CONTEXT (tmp) = fn->decl;
694 DECL_SEEN_IN_BIND_EXPR_P (tmp) = 1;
696 record_vars_into (tmp, fn->decl);
699 /* Push the temporary variable TMP into the current binding. */
701 void
702 gimple_add_tmp_var (tree tmp)
704 gcc_assert (!DECL_CHAIN (tmp) && !DECL_SEEN_IN_BIND_EXPR_P (tmp));
706 /* Later processing assumes that the object size is constant, which might
707 not be true at this point. Force the use of a constant upper bound in
708 this case. */
709 if (!tree_fits_uhwi_p (DECL_SIZE_UNIT (tmp)))
710 force_constant_size (tmp);
712 DECL_CONTEXT (tmp) = current_function_decl;
713 DECL_SEEN_IN_BIND_EXPR_P (tmp) = 1;
715 if (gimplify_ctxp)
717 DECL_CHAIN (tmp) = gimplify_ctxp->temps;
718 gimplify_ctxp->temps = tmp;
720 /* Mark temporaries local within the nearest enclosing parallel. */
721 if (gimplify_omp_ctxp)
723 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
724 while (ctx
725 && (ctx->region_type == ORT_WORKSHARE
726 || ctx->region_type == ORT_SIMD
727 || ctx->region_type == ORT_ACC))
728 ctx = ctx->outer_context;
729 if (ctx)
730 omp_add_variable (ctx, tmp, GOVD_LOCAL | GOVD_SEEN);
733 else if (cfun)
734 record_vars (tmp);
735 else
737 gimple_seq body_seq;
739 /* This case is for nested functions. We need to expose the locals
740 they create. */
741 body_seq = gimple_body (current_function_decl);
742 declare_vars (tmp, gimple_seq_first_stmt (body_seq), false);
748 /* This page contains routines to unshare tree nodes, i.e. to duplicate tree
749 nodes that are referenced more than once in GENERIC functions. This is
750 necessary because gimplification (translation into GIMPLE) is performed
751 by modifying tree nodes in-place, so gimplication of a shared node in a
752 first context could generate an invalid GIMPLE form in a second context.
754 This is achieved with a simple mark/copy/unmark algorithm that walks the
755 GENERIC representation top-down, marks nodes with TREE_VISITED the first
756 time it encounters them, duplicates them if they already have TREE_VISITED
757 set, and finally removes the TREE_VISITED marks it has set.
759 The algorithm works only at the function level, i.e. it generates a GENERIC
760 representation of a function with no nodes shared within the function when
761 passed a GENERIC function (except for nodes that are allowed to be shared).
763 At the global level, it is also necessary to unshare tree nodes that are
764 referenced in more than one function, for the same aforementioned reason.
765 This requires some cooperation from the front-end. There are 2 strategies:
767 1. Manual unsharing. The front-end needs to call unshare_expr on every
768 expression that might end up being shared across functions.
770 2. Deep unsharing. This is an extension of regular unsharing. Instead
771 of calling unshare_expr on expressions that might be shared across
772 functions, the front-end pre-marks them with TREE_VISITED. This will
773 ensure that they are unshared on the first reference within functions
774 when the regular unsharing algorithm runs. The counterpart is that
775 this algorithm must look deeper than for manual unsharing, which is
776 specified by LANG_HOOKS_DEEP_UNSHARING.
778 If there are only few specific cases of node sharing across functions, it is
779 probably easier for a front-end to unshare the expressions manually. On the
780 contrary, if the expressions generated at the global level are as widespread
781 as expressions generated within functions, deep unsharing is very likely the
782 way to go. */
784 /* Similar to copy_tree_r but do not copy SAVE_EXPR or TARGET_EXPR nodes.
785 These nodes model computations that must be done once. If we were to
786 unshare something like SAVE_EXPR(i++), the gimplification process would
787 create wrong code. However, if DATA is non-null, it must hold a pointer
788 set that is used to unshare the subtrees of these nodes. */
790 static tree
791 mostly_copy_tree_r (tree *tp, int *walk_subtrees, void *data)
793 tree t = *tp;
794 enum tree_code code = TREE_CODE (t);
796 /* Do not copy SAVE_EXPR, TARGET_EXPR or BIND_EXPR nodes themselves, but
797 copy their subtrees if we can make sure to do it only once. */
798 if (code == SAVE_EXPR || code == TARGET_EXPR || code == BIND_EXPR)
800 if (data && !((hash_set<tree> *)data)->add (t))
802 else
803 *walk_subtrees = 0;
806 /* Stop at types, decls, constants like copy_tree_r. */
807 else if (TREE_CODE_CLASS (code) == tcc_type
808 || TREE_CODE_CLASS (code) == tcc_declaration
809 || TREE_CODE_CLASS (code) == tcc_constant
810 /* We can't do anything sensible with a BLOCK used as an
811 expression, but we also can't just die when we see it
812 because of non-expression uses. So we avert our eyes
813 and cross our fingers. Silly Java. */
814 || code == BLOCK)
815 *walk_subtrees = 0;
817 /* Cope with the statement expression extension. */
818 else if (code == STATEMENT_LIST)
821 /* Leave the bulk of the work to copy_tree_r itself. */
822 else
823 copy_tree_r (tp, walk_subtrees, NULL);
825 return NULL_TREE;
828 /* Callback for walk_tree to unshare most of the shared trees rooted at *TP.
829 If *TP has been visited already, then *TP is deeply copied by calling
830 mostly_copy_tree_r. DATA is passed to mostly_copy_tree_r unmodified. */
832 static tree
833 copy_if_shared_r (tree *tp, int *walk_subtrees, void *data)
835 tree t = *tp;
836 enum tree_code code = TREE_CODE (t);
838 /* Skip types, decls, and constants. But we do want to look at their
839 types and the bounds of types. Mark them as visited so we properly
840 unmark their subtrees on the unmark pass. If we've already seen them,
841 don't look down further. */
842 if (TREE_CODE_CLASS (code) == tcc_type
843 || TREE_CODE_CLASS (code) == tcc_declaration
844 || TREE_CODE_CLASS (code) == tcc_constant)
846 if (TREE_VISITED (t))
847 *walk_subtrees = 0;
848 else
849 TREE_VISITED (t) = 1;
852 /* If this node has been visited already, unshare it and don't look
853 any deeper. */
854 else if (TREE_VISITED (t))
856 walk_tree (tp, mostly_copy_tree_r, data, NULL);
857 *walk_subtrees = 0;
860 /* Otherwise, mark the node as visited and keep looking. */
861 else
862 TREE_VISITED (t) = 1;
864 return NULL_TREE;
867 /* Unshare most of the shared trees rooted at *TP. DATA is passed to the
868 copy_if_shared_r callback unmodified. */
870 static inline void
871 copy_if_shared (tree *tp, void *data)
873 walk_tree (tp, copy_if_shared_r, data, NULL);
876 /* Unshare all the trees in the body of FNDECL, as well as in the bodies of
877 any nested functions. */
879 static void
880 unshare_body (tree fndecl)
882 struct cgraph_node *cgn = cgraph_node::get (fndecl);
883 /* If the language requires deep unsharing, we need a pointer set to make
884 sure we don't repeatedly unshare subtrees of unshareable nodes. */
885 hash_set<tree> *visited
886 = lang_hooks.deep_unsharing ? new hash_set<tree> : NULL;
888 copy_if_shared (&DECL_SAVED_TREE (fndecl), visited);
889 copy_if_shared (&DECL_SIZE (DECL_RESULT (fndecl)), visited);
890 copy_if_shared (&DECL_SIZE_UNIT (DECL_RESULT (fndecl)), visited);
892 delete visited;
894 if (cgn)
895 for (cgn = cgn->nested; cgn; cgn = cgn->next_nested)
896 unshare_body (cgn->decl);
899 /* Callback for walk_tree to unmark the visited trees rooted at *TP.
900 Subtrees are walked until the first unvisited node is encountered. */
902 static tree
903 unmark_visited_r (tree *tp, int *walk_subtrees, void *data ATTRIBUTE_UNUSED)
905 tree t = *tp;
907 /* If this node has been visited, unmark it and keep looking. */
908 if (TREE_VISITED (t))
909 TREE_VISITED (t) = 0;
911 /* Otherwise, don't look any deeper. */
912 else
913 *walk_subtrees = 0;
915 return NULL_TREE;
918 /* Unmark the visited trees rooted at *TP. */
920 static inline void
921 unmark_visited (tree *tp)
923 walk_tree (tp, unmark_visited_r, NULL, NULL);
926 /* Likewise, but mark all trees as not visited. */
928 static void
929 unvisit_body (tree fndecl)
931 struct cgraph_node *cgn = cgraph_node::get (fndecl);
933 unmark_visited (&DECL_SAVED_TREE (fndecl));
934 unmark_visited (&DECL_SIZE (DECL_RESULT (fndecl)));
935 unmark_visited (&DECL_SIZE_UNIT (DECL_RESULT (fndecl)));
937 if (cgn)
938 for (cgn = cgn->nested; cgn; cgn = cgn->next_nested)
939 unvisit_body (cgn->decl);
942 /* Unconditionally make an unshared copy of EXPR. This is used when using
943 stored expressions which span multiple functions, such as BINFO_VTABLE,
944 as the normal unsharing process can't tell that they're shared. */
946 tree
947 unshare_expr (tree expr)
949 walk_tree (&expr, mostly_copy_tree_r, NULL, NULL);
950 return expr;
953 /* Worker for unshare_expr_without_location. */
955 static tree
956 prune_expr_location (tree *tp, int *walk_subtrees, void *)
958 if (EXPR_P (*tp))
959 SET_EXPR_LOCATION (*tp, UNKNOWN_LOCATION);
960 else
961 *walk_subtrees = 0;
962 return NULL_TREE;
965 /* Similar to unshare_expr but also prune all expression locations
966 from EXPR. */
968 tree
969 unshare_expr_without_location (tree expr)
971 walk_tree (&expr, mostly_copy_tree_r, NULL, NULL);
972 if (EXPR_P (expr))
973 walk_tree (&expr, prune_expr_location, NULL, NULL);
974 return expr;
977 /* WRAPPER is a code such as BIND_EXPR or CLEANUP_POINT_EXPR which can both
978 contain statements and have a value. Assign its value to a temporary
979 and give it void_type_node. Return the temporary, or NULL_TREE if
980 WRAPPER was already void. */
982 tree
983 voidify_wrapper_expr (tree wrapper, tree temp)
985 tree type = TREE_TYPE (wrapper);
986 if (type && !VOID_TYPE_P (type))
988 tree *p;
990 /* Set p to point to the body of the wrapper. Loop until we find
991 something that isn't a wrapper. */
992 for (p = &wrapper; p && *p; )
994 switch (TREE_CODE (*p))
996 case BIND_EXPR:
997 TREE_SIDE_EFFECTS (*p) = 1;
998 TREE_TYPE (*p) = void_type_node;
999 /* For a BIND_EXPR, the body is operand 1. */
1000 p = &BIND_EXPR_BODY (*p);
1001 break;
1003 case CLEANUP_POINT_EXPR:
1004 case TRY_FINALLY_EXPR:
1005 case TRY_CATCH_EXPR:
1006 TREE_SIDE_EFFECTS (*p) = 1;
1007 TREE_TYPE (*p) = void_type_node;
1008 p = &TREE_OPERAND (*p, 0);
1009 break;
1011 case STATEMENT_LIST:
1013 tree_stmt_iterator i = tsi_last (*p);
1014 TREE_SIDE_EFFECTS (*p) = 1;
1015 TREE_TYPE (*p) = void_type_node;
1016 p = tsi_end_p (i) ? NULL : tsi_stmt_ptr (i);
1018 break;
1020 case COMPOUND_EXPR:
1021 /* Advance to the last statement. Set all container types to
1022 void. */
1023 for (; TREE_CODE (*p) == COMPOUND_EXPR; p = &TREE_OPERAND (*p, 1))
1025 TREE_SIDE_EFFECTS (*p) = 1;
1026 TREE_TYPE (*p) = void_type_node;
1028 break;
1030 case TRANSACTION_EXPR:
1031 TREE_SIDE_EFFECTS (*p) = 1;
1032 TREE_TYPE (*p) = void_type_node;
1033 p = &TRANSACTION_EXPR_BODY (*p);
1034 break;
1036 default:
1037 /* Assume that any tree upon which voidify_wrapper_expr is
1038 directly called is a wrapper, and that its body is op0. */
1039 if (p == &wrapper)
1041 TREE_SIDE_EFFECTS (*p) = 1;
1042 TREE_TYPE (*p) = void_type_node;
1043 p = &TREE_OPERAND (*p, 0);
1044 break;
1046 goto out;
1050 out:
1051 if (p == NULL || IS_EMPTY_STMT (*p))
1052 temp = NULL_TREE;
1053 else if (temp)
1055 /* The wrapper is on the RHS of an assignment that we're pushing
1056 down. */
1057 gcc_assert (TREE_CODE (temp) == INIT_EXPR
1058 || TREE_CODE (temp) == MODIFY_EXPR);
1059 TREE_OPERAND (temp, 1) = *p;
1060 *p = temp;
1062 else
1064 temp = create_tmp_var (type, "retval");
1065 *p = build2 (INIT_EXPR, type, temp, *p);
1068 return temp;
1071 return NULL_TREE;
1074 /* Prepare calls to builtins to SAVE and RESTORE the stack as well as
1075 a temporary through which they communicate. */
1077 static void
1078 build_stack_save_restore (gcall **save, gcall **restore)
1080 tree tmp_var;
1082 *save = gimple_build_call (builtin_decl_implicit (BUILT_IN_STACK_SAVE), 0);
1083 tmp_var = create_tmp_var (ptr_type_node, "saved_stack");
1084 gimple_call_set_lhs (*save, tmp_var);
1086 *restore
1087 = gimple_build_call (builtin_decl_implicit (BUILT_IN_STACK_RESTORE),
1088 1, tmp_var);
1091 /* Gimplify a BIND_EXPR. Just voidify and recurse. */
1093 static enum gimplify_status
1094 gimplify_bind_expr (tree *expr_p, gimple_seq *pre_p)
1096 tree bind_expr = *expr_p;
1097 bool old_keep_stack = gimplify_ctxp->keep_stack;
1098 bool old_save_stack = gimplify_ctxp->save_stack;
1099 tree t;
1100 gbind *bind_stmt;
1101 gimple_seq body, cleanup;
1102 gcall *stack_save;
1103 location_t start_locus = 0, end_locus = 0;
1104 tree ret_clauses = NULL;
1106 tree temp = voidify_wrapper_expr (bind_expr, NULL);
1108 /* Mark variables seen in this bind expr. */
1109 for (t = BIND_EXPR_VARS (bind_expr); t ; t = DECL_CHAIN (t))
1111 if (VAR_P (t))
1113 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
1115 /* Mark variable as local. */
1116 if (ctx && ctx->region_type != ORT_NONE && !DECL_EXTERNAL (t)
1117 && (! DECL_SEEN_IN_BIND_EXPR_P (t)
1118 || splay_tree_lookup (ctx->variables,
1119 (splay_tree_key) t) == NULL))
1121 if (ctx->region_type == ORT_SIMD
1122 && TREE_ADDRESSABLE (t)
1123 && !TREE_STATIC (t))
1124 omp_add_variable (ctx, t, GOVD_PRIVATE | GOVD_SEEN);
1125 else
1126 omp_add_variable (ctx, t, GOVD_LOCAL | GOVD_SEEN);
1129 DECL_SEEN_IN_BIND_EXPR_P (t) = 1;
1131 if (DECL_HARD_REGISTER (t) && !is_global_var (t) && cfun)
1132 cfun->has_local_explicit_reg_vars = true;
1135 /* Preliminarily mark non-addressed complex variables as eligible
1136 for promotion to gimple registers. We'll transform their uses
1137 as we find them. */
1138 if ((TREE_CODE (TREE_TYPE (t)) == COMPLEX_TYPE
1139 || TREE_CODE (TREE_TYPE (t)) == VECTOR_TYPE)
1140 && !TREE_THIS_VOLATILE (t)
1141 && (VAR_P (t) && !DECL_HARD_REGISTER (t))
1142 && !needs_to_live_in_memory (t))
1143 DECL_GIMPLE_REG_P (t) = 1;
1146 bind_stmt = gimple_build_bind (BIND_EXPR_VARS (bind_expr), NULL,
1147 BIND_EXPR_BLOCK (bind_expr));
1148 gimple_push_bind_expr (bind_stmt);
1150 gimplify_ctxp->keep_stack = false;
1151 gimplify_ctxp->save_stack = false;
1153 /* Gimplify the body into the GIMPLE_BIND tuple's body. */
1154 body = NULL;
1155 gimplify_stmt (&BIND_EXPR_BODY (bind_expr), &body);
1156 gimple_bind_set_body (bind_stmt, body);
1158 /* Source location wise, the cleanup code (stack_restore and clobbers)
1159 belongs to the end of the block, so propagate what we have. The
1160 stack_save operation belongs to the beginning of block, which we can
1161 infer from the bind_expr directly if the block has no explicit
1162 assignment. */
1163 if (BIND_EXPR_BLOCK (bind_expr))
1165 end_locus = BLOCK_SOURCE_END_LOCATION (BIND_EXPR_BLOCK (bind_expr));
1166 start_locus = BLOCK_SOURCE_LOCATION (BIND_EXPR_BLOCK (bind_expr));
1168 if (start_locus == 0)
1169 start_locus = EXPR_LOCATION (bind_expr);
1171 cleanup = NULL;
1172 stack_save = NULL;
1174 /* If the code both contains VLAs and calls alloca, then we cannot reclaim
1175 the stack space allocated to the VLAs. */
1176 if (gimplify_ctxp->save_stack && !gimplify_ctxp->keep_stack)
1178 gcall *stack_restore;
1180 /* Save stack on entry and restore it on exit. Add a try_finally
1181 block to achieve this. */
1182 build_stack_save_restore (&stack_save, &stack_restore);
1184 gimple_set_location (stack_save, start_locus);
1185 gimple_set_location (stack_restore, end_locus);
1187 gimplify_seq_add_stmt (&cleanup, stack_restore);
1190 /* Add clobbers for all variables that go out of scope. */
1191 for (t = BIND_EXPR_VARS (bind_expr); t ; t = DECL_CHAIN (t))
1193 if (VAR_P (t)
1194 && !is_global_var (t)
1195 && DECL_CONTEXT (t) == current_function_decl
1196 && !DECL_HARD_REGISTER (t)
1197 && !TREE_THIS_VOLATILE (t)
1198 && !DECL_HAS_VALUE_EXPR_P (t)
1199 /* Only care for variables that have to be in memory. Others
1200 will be rewritten into SSA names, hence moved to the top-level. */
1201 && !is_gimple_reg (t)
1202 && flag_stack_reuse != SR_NONE)
1204 tree clobber = build_constructor (TREE_TYPE (t), NULL);
1205 gimple *clobber_stmt;
1206 TREE_THIS_VOLATILE (clobber) = 1;
1207 clobber_stmt = gimple_build_assign (t, clobber);
1208 gimple_set_location (clobber_stmt, end_locus);
1209 gimplify_seq_add_stmt (&cleanup, clobber_stmt);
1211 if (flag_openacc && oacc_declare_returns != NULL)
1213 tree *c = oacc_declare_returns->get (t);
1214 if (c != NULL)
1216 if (ret_clauses)
1217 OMP_CLAUSE_CHAIN (*c) = ret_clauses;
1219 ret_clauses = *c;
1221 oacc_declare_returns->remove (t);
1223 if (oacc_declare_returns->elements () == 0)
1225 delete oacc_declare_returns;
1226 oacc_declare_returns = NULL;
1233 if (ret_clauses)
1235 gomp_target *stmt;
1236 gimple_stmt_iterator si = gsi_start (cleanup);
1238 stmt = gimple_build_omp_target (NULL, GF_OMP_TARGET_KIND_OACC_DECLARE,
1239 ret_clauses);
1240 gsi_insert_seq_before_without_update (&si, stmt, GSI_NEW_STMT);
1243 if (cleanup)
1245 gtry *gs;
1246 gimple_seq new_body;
1248 new_body = NULL;
1249 gs = gimple_build_try (gimple_bind_body (bind_stmt), cleanup,
1250 GIMPLE_TRY_FINALLY);
1252 if (stack_save)
1253 gimplify_seq_add_stmt (&new_body, stack_save);
1254 gimplify_seq_add_stmt (&new_body, gs);
1255 gimple_bind_set_body (bind_stmt, new_body);
1258 /* keep_stack propagates all the way up to the outermost BIND_EXPR. */
1259 if (!gimplify_ctxp->keep_stack)
1260 gimplify_ctxp->keep_stack = old_keep_stack;
1261 gimplify_ctxp->save_stack = old_save_stack;
1263 gimple_pop_bind_expr ();
1265 gimplify_seq_add_stmt (pre_p, bind_stmt);
1267 if (temp)
1269 *expr_p = temp;
1270 return GS_OK;
1273 *expr_p = NULL_TREE;
1274 return GS_ALL_DONE;
1277 /* Gimplify a RETURN_EXPR. If the expression to be returned is not a
1278 GIMPLE value, it is assigned to a new temporary and the statement is
1279 re-written to return the temporary.
1281 PRE_P points to the sequence where side effects that must happen before
1282 STMT should be stored. */
1284 static enum gimplify_status
1285 gimplify_return_expr (tree stmt, gimple_seq *pre_p)
1287 greturn *ret;
1288 tree ret_expr = TREE_OPERAND (stmt, 0);
1289 tree result_decl, result;
1291 if (ret_expr == error_mark_node)
1292 return GS_ERROR;
1294 /* Implicit _Cilk_sync must be inserted right before any return statement
1295 if there is a _Cilk_spawn in the function. If the user has provided a
1296 _Cilk_sync, the optimizer should remove this duplicate one. */
1297 if (fn_contains_cilk_spawn_p (cfun))
1299 tree impl_sync = build0 (CILK_SYNC_STMT, void_type_node);
1300 gimplify_and_add (impl_sync, pre_p);
1303 if (!ret_expr
1304 || TREE_CODE (ret_expr) == RESULT_DECL
1305 || ret_expr == error_mark_node)
1307 greturn *ret = gimple_build_return (ret_expr);
1308 gimple_set_no_warning (ret, TREE_NO_WARNING (stmt));
1309 gimplify_seq_add_stmt (pre_p, ret);
1310 return GS_ALL_DONE;
1313 if (VOID_TYPE_P (TREE_TYPE (TREE_TYPE (current_function_decl))))
1314 result_decl = NULL_TREE;
1315 else
1317 result_decl = TREE_OPERAND (ret_expr, 0);
1319 /* See through a return by reference. */
1320 if (TREE_CODE (result_decl) == INDIRECT_REF)
1321 result_decl = TREE_OPERAND (result_decl, 0);
1323 gcc_assert ((TREE_CODE (ret_expr) == MODIFY_EXPR
1324 || TREE_CODE (ret_expr) == INIT_EXPR)
1325 && TREE_CODE (result_decl) == RESULT_DECL);
1328 /* If aggregate_value_p is true, then we can return the bare RESULT_DECL.
1329 Recall that aggregate_value_p is FALSE for any aggregate type that is
1330 returned in registers. If we're returning values in registers, then
1331 we don't want to extend the lifetime of the RESULT_DECL, particularly
1332 across another call. In addition, for those aggregates for which
1333 hard_function_value generates a PARALLEL, we'll die during normal
1334 expansion of structure assignments; there's special code in expand_return
1335 to handle this case that does not exist in expand_expr. */
1336 if (!result_decl)
1337 result = NULL_TREE;
1338 else if (aggregate_value_p (result_decl, TREE_TYPE (current_function_decl)))
1340 if (TREE_CODE (DECL_SIZE (result_decl)) != INTEGER_CST)
1342 if (!TYPE_SIZES_GIMPLIFIED (TREE_TYPE (result_decl)))
1343 gimplify_type_sizes (TREE_TYPE (result_decl), pre_p);
1344 /* Note that we don't use gimplify_vla_decl because the RESULT_DECL
1345 should be effectively allocated by the caller, i.e. all calls to
1346 this function must be subject to the Return Slot Optimization. */
1347 gimplify_one_sizepos (&DECL_SIZE (result_decl), pre_p);
1348 gimplify_one_sizepos (&DECL_SIZE_UNIT (result_decl), pre_p);
1350 result = result_decl;
1352 else if (gimplify_ctxp->return_temp)
1353 result = gimplify_ctxp->return_temp;
1354 else
1356 result = create_tmp_reg (TREE_TYPE (result_decl));
1358 /* ??? With complex control flow (usually involving abnormal edges),
1359 we can wind up warning about an uninitialized value for this. Due
1360 to how this variable is constructed and initialized, this is never
1361 true. Give up and never warn. */
1362 TREE_NO_WARNING (result) = 1;
1364 gimplify_ctxp->return_temp = result;
1367 /* Smash the lhs of the MODIFY_EXPR to the temporary we plan to use.
1368 Then gimplify the whole thing. */
1369 if (result != result_decl)
1370 TREE_OPERAND (ret_expr, 0) = result;
1372 gimplify_and_add (TREE_OPERAND (stmt, 0), pre_p);
1374 ret = gimple_build_return (result);
1375 gimple_set_no_warning (ret, TREE_NO_WARNING (stmt));
1376 gimplify_seq_add_stmt (pre_p, ret);
1378 return GS_ALL_DONE;
1381 /* Gimplify a variable-length array DECL. */
1383 static void
1384 gimplify_vla_decl (tree decl, gimple_seq *seq_p)
1386 /* This is a variable-sized decl. Simplify its size and mark it
1387 for deferred expansion. */
1388 tree t, addr, ptr_type;
1390 gimplify_one_sizepos (&DECL_SIZE (decl), seq_p);
1391 gimplify_one_sizepos (&DECL_SIZE_UNIT (decl), seq_p);
1393 /* Don't mess with a DECL_VALUE_EXPR set by the front-end. */
1394 if (DECL_HAS_VALUE_EXPR_P (decl))
1395 return;
1397 /* All occurrences of this decl in final gimplified code will be
1398 replaced by indirection. Setting DECL_VALUE_EXPR does two
1399 things: First, it lets the rest of the gimplifier know what
1400 replacement to use. Second, it lets the debug info know
1401 where to find the value. */
1402 ptr_type = build_pointer_type (TREE_TYPE (decl));
1403 addr = create_tmp_var (ptr_type, get_name (decl));
1404 DECL_IGNORED_P (addr) = 0;
1405 t = build_fold_indirect_ref (addr);
1406 TREE_THIS_NOTRAP (t) = 1;
1407 SET_DECL_VALUE_EXPR (decl, t);
1408 DECL_HAS_VALUE_EXPR_P (decl) = 1;
1410 t = builtin_decl_explicit (BUILT_IN_ALLOCA_WITH_ALIGN);
1411 t = build_call_expr (t, 2, DECL_SIZE_UNIT (decl),
1412 size_int (DECL_ALIGN (decl)));
1413 /* The call has been built for a variable-sized object. */
1414 CALL_ALLOCA_FOR_VAR_P (t) = 1;
1415 t = fold_convert (ptr_type, t);
1416 t = build2 (MODIFY_EXPR, TREE_TYPE (addr), addr, t);
1418 gimplify_and_add (t, seq_p);
1421 /* A helper function to be called via walk_tree. Mark all labels under *TP
1422 as being forced. To be called for DECL_INITIAL of static variables. */
1424 static tree
1425 force_labels_r (tree *tp, int *walk_subtrees, void *data ATTRIBUTE_UNUSED)
1427 if (TYPE_P (*tp))
1428 *walk_subtrees = 0;
1429 if (TREE_CODE (*tp) == LABEL_DECL)
1431 FORCED_LABEL (*tp) = 1;
1432 cfun->has_forced_label_in_static = 1;
1435 return NULL_TREE;
1438 /* Gimplify a DECL_EXPR node *STMT_P by making any necessary allocation
1439 and initialization explicit. */
1441 static enum gimplify_status
1442 gimplify_decl_expr (tree *stmt_p, gimple_seq *seq_p)
1444 tree stmt = *stmt_p;
1445 tree decl = DECL_EXPR_DECL (stmt);
1447 *stmt_p = NULL_TREE;
1449 if (TREE_TYPE (decl) == error_mark_node)
1450 return GS_ERROR;
1452 if ((TREE_CODE (decl) == TYPE_DECL
1453 || VAR_P (decl))
1454 && !TYPE_SIZES_GIMPLIFIED (TREE_TYPE (decl)))
1456 gimplify_type_sizes (TREE_TYPE (decl), seq_p);
1457 if (TREE_CODE (TREE_TYPE (decl)) == REFERENCE_TYPE)
1458 gimplify_type_sizes (TREE_TYPE (TREE_TYPE (decl)), seq_p);
1461 /* ??? DECL_ORIGINAL_TYPE is streamed for LTO so it needs to be gimplified
1462 in case its size expressions contain problematic nodes like CALL_EXPR. */
1463 if (TREE_CODE (decl) == TYPE_DECL
1464 && DECL_ORIGINAL_TYPE (decl)
1465 && !TYPE_SIZES_GIMPLIFIED (DECL_ORIGINAL_TYPE (decl)))
1467 gimplify_type_sizes (DECL_ORIGINAL_TYPE (decl), seq_p);
1468 if (TREE_CODE (DECL_ORIGINAL_TYPE (decl)) == REFERENCE_TYPE)
1469 gimplify_type_sizes (TREE_TYPE (DECL_ORIGINAL_TYPE (decl)), seq_p);
1472 if (VAR_P (decl) && !DECL_EXTERNAL (decl))
1474 tree init = DECL_INITIAL (decl);
1476 if (TREE_CODE (DECL_SIZE_UNIT (decl)) != INTEGER_CST
1477 || (!TREE_STATIC (decl)
1478 && flag_stack_check == GENERIC_STACK_CHECK
1479 && compare_tree_int (DECL_SIZE_UNIT (decl),
1480 STACK_CHECK_MAX_VAR_SIZE) > 0))
1481 gimplify_vla_decl (decl, seq_p);
1483 /* Some front ends do not explicitly declare all anonymous
1484 artificial variables. We compensate here by declaring the
1485 variables, though it would be better if the front ends would
1486 explicitly declare them. */
1487 if (!DECL_SEEN_IN_BIND_EXPR_P (decl)
1488 && DECL_ARTIFICIAL (decl) && DECL_NAME (decl) == NULL_TREE)
1489 gimple_add_tmp_var (decl);
1491 if (init && init != error_mark_node)
1493 if (!TREE_STATIC (decl))
1495 DECL_INITIAL (decl) = NULL_TREE;
1496 init = build2 (INIT_EXPR, void_type_node, decl, init);
1497 gimplify_and_add (init, seq_p);
1498 ggc_free (init);
1500 else
1501 /* We must still examine initializers for static variables
1502 as they may contain a label address. */
1503 walk_tree (&init, force_labels_r, NULL, NULL);
1507 return GS_ALL_DONE;
1510 /* Gimplify a LOOP_EXPR. Normally this just involves gimplifying the body
1511 and replacing the LOOP_EXPR with goto, but if the loop contains an
1512 EXIT_EXPR, we need to append a label for it to jump to. */
1514 static enum gimplify_status
1515 gimplify_loop_expr (tree *expr_p, gimple_seq *pre_p)
1517 tree saved_label = gimplify_ctxp->exit_label;
1518 tree start_label = create_artificial_label (UNKNOWN_LOCATION);
1520 gimplify_seq_add_stmt (pre_p, gimple_build_label (start_label));
1522 gimplify_ctxp->exit_label = NULL_TREE;
1524 gimplify_and_add (LOOP_EXPR_BODY (*expr_p), pre_p);
1526 gimplify_seq_add_stmt (pre_p, gimple_build_goto (start_label));
1528 if (gimplify_ctxp->exit_label)
1529 gimplify_seq_add_stmt (pre_p,
1530 gimple_build_label (gimplify_ctxp->exit_label));
1532 gimplify_ctxp->exit_label = saved_label;
1534 *expr_p = NULL;
1535 return GS_ALL_DONE;
1538 /* Gimplify a statement list onto a sequence. These may be created either
1539 by an enlightened front-end, or by shortcut_cond_expr. */
1541 static enum gimplify_status
1542 gimplify_statement_list (tree *expr_p, gimple_seq *pre_p)
1544 tree temp = voidify_wrapper_expr (*expr_p, NULL);
1546 tree_stmt_iterator i = tsi_start (*expr_p);
1548 while (!tsi_end_p (i))
1550 gimplify_stmt (tsi_stmt_ptr (i), pre_p);
1551 tsi_delink (&i);
1554 if (temp)
1556 *expr_p = temp;
1557 return GS_OK;
1560 return GS_ALL_DONE;
1563 /* Callback for walk_gimple_seq. */
1565 static tree
1566 warn_switch_unreachable_r (gimple_stmt_iterator *gsi_p, bool *handled_ops_p,
1567 struct walk_stmt_info *wi)
1569 gimple *stmt = gsi_stmt (*gsi_p);
1571 *handled_ops_p = true;
1572 switch (gimple_code (stmt))
1574 case GIMPLE_TRY:
1575 /* A compiler-generated cleanup or a user-written try block.
1576 If it's empty, don't dive into it--that would result in
1577 worse location info. */
1578 if (gimple_try_eval (stmt) == NULL)
1580 wi->info = stmt;
1581 return integer_zero_node;
1583 /* Fall through. */
1584 case GIMPLE_BIND:
1585 case GIMPLE_CATCH:
1586 case GIMPLE_EH_FILTER:
1587 case GIMPLE_TRANSACTION:
1588 /* Walk the sub-statements. */
1589 *handled_ops_p = false;
1590 break;
1591 default:
1592 /* Save the first "real" statement (not a decl/lexical scope/...). */
1593 wi->info = stmt;
1594 return integer_zero_node;
1596 return NULL_TREE;
1599 /* Possibly warn about unreachable statements between switch's controlling
1600 expression and the first case. SEQ is the body of a switch expression. */
1602 static void
1603 maybe_warn_switch_unreachable (gimple_seq seq)
1605 if (!warn_switch_unreachable
1606 /* This warning doesn't play well with Fortran when optimizations
1607 are on. */
1608 || lang_GNU_Fortran ()
1609 || seq == NULL)
1610 return;
1612 struct walk_stmt_info wi;
1613 memset (&wi, 0, sizeof (wi));
1614 walk_gimple_seq (seq, warn_switch_unreachable_r, NULL, &wi);
1615 gimple *stmt = (gimple *) wi.info;
1617 if (stmt && gimple_code (stmt) != GIMPLE_LABEL)
1619 if (gimple_code (stmt) == GIMPLE_GOTO
1620 && TREE_CODE (gimple_goto_dest (stmt)) == LABEL_DECL
1621 && DECL_ARTIFICIAL (gimple_goto_dest (stmt)))
1622 /* Don't warn for compiler-generated gotos. These occur
1623 in Duff's devices, for example. */;
1624 else
1625 warning_at (gimple_location (stmt), OPT_Wswitch_unreachable,
1626 "statement will never be executed");
1631 /* A label entry that pairs label and a location. */
1632 struct label_entry
1634 tree label;
1635 location_t loc;
1638 /* Find LABEL in vector of label entries VEC. */
1640 static struct label_entry *
1641 find_label_entry (const auto_vec<struct label_entry> *vec, tree label)
1643 unsigned int i;
1644 struct label_entry *l;
1646 FOR_EACH_VEC_ELT (*vec, i, l)
1647 if (l->label == label)
1648 return l;
1649 return NULL;
1652 /* Return true if LABEL, a LABEL_DECL, represents a case label
1653 in a vector of labels CASES. */
1655 static bool
1656 case_label_p (const vec<tree> *cases, tree label)
1658 unsigned int i;
1659 tree l;
1661 FOR_EACH_VEC_ELT (*cases, i, l)
1662 if (CASE_LABEL (l) == label)
1663 return true;
1664 return false;
1667 /* Find the last statement in a scope STMT. */
1669 static gimple *
1670 last_stmt_in_scope (gimple *stmt)
1672 if (!stmt)
1673 return NULL;
1675 switch (gimple_code (stmt))
1677 case GIMPLE_BIND:
1679 gbind *bind = as_a <gbind *> (stmt);
1680 stmt = gimple_seq_last_stmt (gimple_bind_body (bind));
1681 return last_stmt_in_scope (stmt);
1684 case GIMPLE_TRY:
1686 gtry *try_stmt = as_a <gtry *> (stmt);
1687 stmt = gimple_seq_last_stmt (gimple_try_eval (try_stmt));
1688 gimple *last_eval = last_stmt_in_scope (stmt);
1689 if (gimple_stmt_may_fallthru (last_eval)
1690 && (last_eval == NULL
1691 || !gimple_call_internal_p (last_eval, IFN_FALLTHROUGH))
1692 && gimple_try_kind (try_stmt) == GIMPLE_TRY_FINALLY)
1694 stmt = gimple_seq_last_stmt (gimple_try_cleanup (try_stmt));
1695 return last_stmt_in_scope (stmt);
1697 else
1698 return last_eval;
1701 default:
1702 return stmt;
1706 /* Collect interesting labels in LABELS and return the statement preceding
1707 another case label, or a user-defined label. */
1709 static gimple *
1710 collect_fallthrough_labels (gimple_stmt_iterator *gsi_p,
1711 auto_vec <struct label_entry> *labels)
1713 gimple *prev = NULL;
1717 if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_BIND
1718 || gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_TRY)
1720 /* Nested scope. Only look at the last statement of
1721 the innermost scope. */
1722 location_t bind_loc = gimple_location (gsi_stmt (*gsi_p));
1723 gimple *last = last_stmt_in_scope (gsi_stmt (*gsi_p));
1724 if (last)
1726 prev = last;
1727 /* It might be a label without a location. Use the
1728 location of the scope then. */
1729 if (!gimple_has_location (prev))
1730 gimple_set_location (prev, bind_loc);
1732 gsi_next (gsi_p);
1733 continue;
1736 /* Ifs are tricky. */
1737 if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_COND)
1739 gcond *cond_stmt = as_a <gcond *> (gsi_stmt (*gsi_p));
1740 tree false_lab = gimple_cond_false_label (cond_stmt);
1741 location_t if_loc = gimple_location (cond_stmt);
1743 /* If we have e.g.
1744 if (i > 1) goto <D.2259>; else goto D;
1745 we can't do much with the else-branch. */
1746 if (!DECL_ARTIFICIAL (false_lab))
1747 break;
1749 /* Go on until the false label, then one step back. */
1750 for (; !gsi_end_p (*gsi_p); gsi_next (gsi_p))
1752 gimple *stmt = gsi_stmt (*gsi_p);
1753 if (gimple_code (stmt) == GIMPLE_LABEL
1754 && gimple_label_label (as_a <glabel *> (stmt)) == false_lab)
1755 break;
1758 /* Not found? Oops. */
1759 if (gsi_end_p (*gsi_p))
1760 break;
1762 struct label_entry l = { false_lab, if_loc };
1763 labels->safe_push (l);
1765 /* Go to the last statement of the then branch. */
1766 gsi_prev (gsi_p);
1768 /* if (i != 0) goto <D.1759>; else goto <D.1760>;
1769 <D.1759>:
1770 <stmt>;
1771 goto <D.1761>;
1772 <D.1760>:
1774 if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_GOTO
1775 && !gimple_has_location (gsi_stmt (*gsi_p)))
1777 /* Look at the statement before, it might be
1778 attribute fallthrough, in which case don't warn. */
1779 gsi_prev (gsi_p);
1780 bool fallthru_before_dest
1781 = gimple_call_internal_p (gsi_stmt (*gsi_p), IFN_FALLTHROUGH);
1782 gsi_next (gsi_p);
1783 tree goto_dest = gimple_goto_dest (gsi_stmt (*gsi_p));
1784 if (!fallthru_before_dest)
1786 struct label_entry l = { goto_dest, if_loc };
1787 labels->safe_push (l);
1790 /* And move back. */
1791 gsi_next (gsi_p);
1794 /* Remember the last statement. Skip labels that are of no interest
1795 to us. */
1796 if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_LABEL)
1798 tree label = gimple_label_label (as_a <glabel *> (gsi_stmt (*gsi_p)));
1799 if (find_label_entry (labels, label))
1800 prev = gsi_stmt (*gsi_p);
1802 else
1803 prev = gsi_stmt (*gsi_p);
1804 gsi_next (gsi_p);
1806 while (!gsi_end_p (*gsi_p)
1807 /* Stop if we find a case or a user-defined label. */
1808 && (gimple_code (gsi_stmt (*gsi_p)) != GIMPLE_LABEL
1809 || !gimple_has_location (gsi_stmt (*gsi_p))));
1811 return prev;
1814 /* Return true if the switch fallthough warning should occur. LABEL is
1815 the label statement that we're falling through to. */
1817 static bool
1818 should_warn_for_implicit_fallthrough (gimple_stmt_iterator *gsi_p, tree label)
1820 gimple_stmt_iterator gsi = *gsi_p;
1822 /* Don't warn if the label is marked with a "falls through" comment. */
1823 if (FALLTHROUGH_LABEL_P (label))
1824 return false;
1826 /* Don't warn for a non-case label followed by a statement:
1827 case 0:
1828 foo ();
1829 label:
1830 bar ();
1831 as these are likely intentional. */
1832 if (!case_label_p (&gimplify_ctxp->case_labels, label))
1834 gsi_next (&gsi);
1835 if (gsi_end_p (gsi) || gimple_code (gsi_stmt (gsi)) != GIMPLE_LABEL)
1836 return false;
1839 /* Don't warn for terminated branches, i.e. when the subsequent case labels
1840 immediately breaks. */
1841 gsi = *gsi_p;
1843 /* Skip all immediately following labels. */
1844 while (!gsi_end_p (gsi) && gimple_code (gsi_stmt (gsi)) == GIMPLE_LABEL)
1845 gsi_next (&gsi);
1847 /* { ... something; default:; } */
1848 if (gsi_end_p (gsi)
1849 /* { ... something; default: break; } or
1850 { ... something; default: goto L; } */
1851 || gimple_code (gsi_stmt (gsi)) == GIMPLE_GOTO
1852 /* { ... something; default: return; } */
1853 || gimple_code (gsi_stmt (gsi)) == GIMPLE_RETURN)
1854 return false;
1856 return true;
1859 /* Callback for walk_gimple_seq. */
1861 static tree
1862 warn_implicit_fallthrough_r (gimple_stmt_iterator *gsi_p, bool *handled_ops_p,
1863 struct walk_stmt_info *)
1865 gimple *stmt = gsi_stmt (*gsi_p);
1867 *handled_ops_p = true;
1868 switch (gimple_code (stmt))
1870 case GIMPLE_TRY:
1871 case GIMPLE_BIND:
1872 case GIMPLE_CATCH:
1873 case GIMPLE_EH_FILTER:
1874 case GIMPLE_TRANSACTION:
1875 /* Walk the sub-statements. */
1876 *handled_ops_p = false;
1877 break;
1879 /* Find a sequence of form:
1881 GIMPLE_LABEL
1882 [...]
1883 <may fallthru stmt>
1884 GIMPLE_LABEL
1886 and possibly warn. */
1887 case GIMPLE_LABEL:
1889 /* Found a label. Skip all immediately following labels. */
1890 while (!gsi_end_p (*gsi_p)
1891 && gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_LABEL)
1892 gsi_next (gsi_p);
1894 /* There might be no more statements. */
1895 if (gsi_end_p (*gsi_p))
1896 return integer_zero_node;
1898 /* Vector of labels that fall through. */
1899 auto_vec <struct label_entry> labels;
1900 gimple *prev = collect_fallthrough_labels (gsi_p, &labels);
1902 /* There might be no more statements. */
1903 if (gsi_end_p (*gsi_p))
1904 return integer_zero_node;
1906 gimple *next = gsi_stmt (*gsi_p);
1907 tree label;
1908 /* If what follows is a label, then we may have a fallthrough. */
1909 if (gimple_code (next) == GIMPLE_LABEL
1910 && gimple_has_location (next)
1911 && (label = gimple_label_label (as_a <glabel *> (next)))
1912 && prev != NULL)
1914 struct label_entry *l;
1915 bool warned_p = false;
1916 if (!should_warn_for_implicit_fallthrough (gsi_p, label))
1917 /* Quiet. */;
1918 else if (gimple_code (prev) == GIMPLE_LABEL
1919 && (label = gimple_label_label (as_a <glabel *> (prev)))
1920 && (l = find_label_entry (&labels, label)))
1921 warned_p = warning_at (l->loc, OPT_Wimplicit_fallthrough_,
1922 "this statement may fall through");
1923 else if (!gimple_call_internal_p (prev, IFN_FALLTHROUGH)
1924 /* Try to be clever and don't warn when the statement
1925 can't actually fall through. */
1926 && gimple_stmt_may_fallthru (prev)
1927 && gimple_has_location (prev))
1928 warned_p = warning_at (gimple_location (prev),
1929 OPT_Wimplicit_fallthrough_,
1930 "this statement may fall through");
1931 if (warned_p)
1932 inform (gimple_location (next), "here");
1934 /* Mark this label as processed so as to prevent multiple
1935 warnings in nested switches. */
1936 FALLTHROUGH_LABEL_P (label) = true;
1938 /* So that next warn_implicit_fallthrough_r will start looking for
1939 a new sequence starting with this label. */
1940 gsi_prev (gsi_p);
1943 break;
1944 default:
1945 break;
1947 return NULL_TREE;
1950 /* Warn when a switch case falls through. */
1952 static void
1953 maybe_warn_implicit_fallthrough (gimple_seq seq)
1955 if (!warn_implicit_fallthrough)
1956 return;
1958 /* This warning is meant for C/C++/ObjC/ObjC++ only. */
1959 if (!(lang_GNU_C ()
1960 || lang_GNU_CXX ()
1961 || lang_GNU_OBJC ()))
1962 return;
1964 struct walk_stmt_info wi;
1965 memset (&wi, 0, sizeof (wi));
1966 walk_gimple_seq (seq, warn_implicit_fallthrough_r, NULL, &wi);
1969 /* Callback for walk_gimple_seq. */
1971 static tree
1972 expand_FALLTHROUGH_r (gimple_stmt_iterator *gsi_p, bool *handled_ops_p,
1973 struct walk_stmt_info *)
1975 gimple *stmt = gsi_stmt (*gsi_p);
1977 *handled_ops_p = true;
1978 switch (gimple_code (stmt))
1980 case GIMPLE_TRY:
1981 case GIMPLE_BIND:
1982 case GIMPLE_CATCH:
1983 case GIMPLE_EH_FILTER:
1984 case GIMPLE_TRANSACTION:
1985 /* Walk the sub-statements. */
1986 *handled_ops_p = false;
1987 break;
1988 case GIMPLE_CALL:
1989 if (gimple_call_internal_p (stmt, IFN_FALLTHROUGH))
1991 gsi_remove (gsi_p, true);
1992 if (gsi_end_p (*gsi_p))
1993 return integer_zero_node;
1995 bool found = false;
1996 location_t loc = gimple_location (stmt);
1998 gimple_stmt_iterator gsi2 = *gsi_p;
1999 stmt = gsi_stmt (gsi2);
2000 if (gimple_code (stmt) == GIMPLE_GOTO && !gimple_has_location (stmt))
2002 /* Go on until the artificial label. */
2003 tree goto_dest = gimple_goto_dest (stmt);
2004 for (; !gsi_end_p (gsi2); gsi_next (&gsi2))
2006 if (gimple_code (gsi_stmt (gsi2)) == GIMPLE_LABEL
2007 && gimple_label_label (as_a <glabel *> (gsi_stmt (gsi2)))
2008 == goto_dest)
2009 break;
2012 /* Not found? Stop. */
2013 if (gsi_end_p (gsi2))
2014 break;
2016 /* Look one past it. */
2017 gsi_next (&gsi2);
2020 /* We're looking for a case label or default label here. */
2021 while (!gsi_end_p (gsi2))
2023 stmt = gsi_stmt (gsi2);
2024 if (gimple_code (stmt) == GIMPLE_LABEL)
2026 tree label = gimple_label_label (as_a <glabel *> (stmt));
2027 if (gimple_has_location (stmt) && DECL_ARTIFICIAL (label))
2029 found = true;
2030 break;
2033 else
2034 /* Something other than a label. That's not expected. */
2035 break;
2036 gsi_next (&gsi2);
2038 if (!found)
2039 warning_at (loc, 0, "attribute %<fallthrough%> not preceding "
2040 "a case label or default label");
2042 break;
2043 default:
2044 break;
2046 return NULL_TREE;
2049 /* Expand all FALLTHROUGH () calls in SEQ. */
2051 static void
2052 expand_FALLTHROUGH (gimple_seq *seq_p)
2054 struct walk_stmt_info wi;
2055 memset (&wi, 0, sizeof (wi));
2056 walk_gimple_seq_mod (seq_p, expand_FALLTHROUGH_r, NULL, &wi);
2060 /* Gimplify a SWITCH_EXPR, and collect the vector of labels it can
2061 branch to. */
2063 static enum gimplify_status
2064 gimplify_switch_expr (tree *expr_p, gimple_seq *pre_p)
2066 tree switch_expr = *expr_p;
2067 gimple_seq switch_body_seq = NULL;
2068 enum gimplify_status ret;
2069 tree index_type = TREE_TYPE (switch_expr);
2070 if (index_type == NULL_TREE)
2071 index_type = TREE_TYPE (SWITCH_COND (switch_expr));
2073 ret = gimplify_expr (&SWITCH_COND (switch_expr), pre_p, NULL, is_gimple_val,
2074 fb_rvalue);
2075 if (ret == GS_ERROR || ret == GS_UNHANDLED)
2076 return ret;
2078 if (SWITCH_BODY (switch_expr))
2080 vec<tree> labels;
2081 vec<tree> saved_labels;
2082 tree default_case = NULL_TREE;
2083 gswitch *switch_stmt;
2085 /* If someone can be bothered to fill in the labels, they can
2086 be bothered to null out the body too. */
2087 gcc_assert (!SWITCH_LABELS (switch_expr));
2089 /* Save old labels, get new ones from body, then restore the old
2090 labels. Save all the things from the switch body to append after. */
2091 saved_labels = gimplify_ctxp->case_labels;
2092 gimplify_ctxp->case_labels.create (8);
2093 bool old_in_switch_expr = gimplify_ctxp->in_switch_expr;
2094 gimplify_ctxp->in_switch_expr = true;
2096 gimplify_stmt (&SWITCH_BODY (switch_expr), &switch_body_seq);
2098 gimplify_ctxp->in_switch_expr = old_in_switch_expr;
2099 maybe_warn_switch_unreachable (switch_body_seq);
2100 maybe_warn_implicit_fallthrough (switch_body_seq);
2101 /* Only do this for the outermost GIMPLE_SWITCH. */
2102 if (!gimplify_ctxp->in_switch_expr)
2103 expand_FALLTHROUGH (&switch_body_seq);
2105 labels = gimplify_ctxp->case_labels;
2106 gimplify_ctxp->case_labels = saved_labels;
2108 preprocess_case_label_vec_for_gimple (labels, index_type,
2109 &default_case);
2111 if (!default_case)
2113 glabel *new_default;
2115 default_case
2116 = build_case_label (NULL_TREE, NULL_TREE,
2117 create_artificial_label (UNKNOWN_LOCATION));
2118 new_default = gimple_build_label (CASE_LABEL (default_case));
2119 gimplify_seq_add_stmt (&switch_body_seq, new_default);
2122 switch_stmt = gimple_build_switch (SWITCH_COND (switch_expr),
2123 default_case, labels);
2124 gimplify_seq_add_stmt (pre_p, switch_stmt);
2125 gimplify_seq_add_seq (pre_p, switch_body_seq);
2126 labels.release ();
2128 else
2129 gcc_assert (SWITCH_LABELS (switch_expr));
2131 return GS_ALL_DONE;
2134 /* Gimplify the LABEL_EXPR pointed to by EXPR_P. */
2136 static enum gimplify_status
2137 gimplify_label_expr (tree *expr_p, gimple_seq *pre_p)
2139 gcc_assert (decl_function_context (LABEL_EXPR_LABEL (*expr_p))
2140 == current_function_decl);
2142 glabel *label_stmt = gimple_build_label (LABEL_EXPR_LABEL (*expr_p));
2143 gimple_set_location (label_stmt, EXPR_LOCATION (*expr_p));
2144 gimplify_seq_add_stmt (pre_p, label_stmt);
2146 return GS_ALL_DONE;
2149 /* Gimplify the CASE_LABEL_EXPR pointed to by EXPR_P. */
2151 static enum gimplify_status
2152 gimplify_case_label_expr (tree *expr_p, gimple_seq *pre_p)
2154 struct gimplify_ctx *ctxp;
2155 glabel *label_stmt;
2157 /* Invalid programs can play Duff's Device type games with, for example,
2158 #pragma omp parallel. At least in the C front end, we don't
2159 detect such invalid branches until after gimplification, in the
2160 diagnose_omp_blocks pass. */
2161 for (ctxp = gimplify_ctxp; ; ctxp = ctxp->prev_context)
2162 if (ctxp->case_labels.exists ())
2163 break;
2165 label_stmt = gimple_build_label (CASE_LABEL (*expr_p));
2166 gimple_set_location (label_stmt, EXPR_LOCATION (*expr_p));
2167 ctxp->case_labels.safe_push (*expr_p);
2168 gimplify_seq_add_stmt (pre_p, label_stmt);
2170 return GS_ALL_DONE;
2173 /* Build a GOTO to the LABEL_DECL pointed to by LABEL_P, building it first
2174 if necessary. */
2176 tree
2177 build_and_jump (tree *label_p)
2179 if (label_p == NULL)
2180 /* If there's nowhere to jump, just fall through. */
2181 return NULL_TREE;
2183 if (*label_p == NULL_TREE)
2185 tree label = create_artificial_label (UNKNOWN_LOCATION);
2186 *label_p = label;
2189 return build1 (GOTO_EXPR, void_type_node, *label_p);
2192 /* Gimplify an EXIT_EXPR by converting to a GOTO_EXPR inside a COND_EXPR.
2193 This also involves building a label to jump to and communicating it to
2194 gimplify_loop_expr through gimplify_ctxp->exit_label. */
2196 static enum gimplify_status
2197 gimplify_exit_expr (tree *expr_p)
2199 tree cond = TREE_OPERAND (*expr_p, 0);
2200 tree expr;
2202 expr = build_and_jump (&gimplify_ctxp->exit_label);
2203 expr = build3 (COND_EXPR, void_type_node, cond, expr, NULL_TREE);
2204 *expr_p = expr;
2206 return GS_OK;
2209 /* *EXPR_P is a COMPONENT_REF being used as an rvalue. If its type is
2210 different from its canonical type, wrap the whole thing inside a
2211 NOP_EXPR and force the type of the COMPONENT_REF to be the canonical
2212 type.
2214 The canonical type of a COMPONENT_REF is the type of the field being
2215 referenced--unless the field is a bit-field which can be read directly
2216 in a smaller mode, in which case the canonical type is the
2217 sign-appropriate type corresponding to that mode. */
2219 static void
2220 canonicalize_component_ref (tree *expr_p)
2222 tree expr = *expr_p;
2223 tree type;
2225 gcc_assert (TREE_CODE (expr) == COMPONENT_REF);
2227 if (INTEGRAL_TYPE_P (TREE_TYPE (expr)))
2228 type = TREE_TYPE (get_unwidened (expr, NULL_TREE));
2229 else
2230 type = TREE_TYPE (TREE_OPERAND (expr, 1));
2232 /* One could argue that all the stuff below is not necessary for
2233 the non-bitfield case and declare it a FE error if type
2234 adjustment would be needed. */
2235 if (TREE_TYPE (expr) != type)
2237 #ifdef ENABLE_TYPES_CHECKING
2238 tree old_type = TREE_TYPE (expr);
2239 #endif
2240 int type_quals;
2242 /* We need to preserve qualifiers and propagate them from
2243 operand 0. */
2244 type_quals = TYPE_QUALS (type)
2245 | TYPE_QUALS (TREE_TYPE (TREE_OPERAND (expr, 0)));
2246 if (TYPE_QUALS (type) != type_quals)
2247 type = build_qualified_type (TYPE_MAIN_VARIANT (type), type_quals);
2249 /* Set the type of the COMPONENT_REF to the underlying type. */
2250 TREE_TYPE (expr) = type;
2252 #ifdef ENABLE_TYPES_CHECKING
2253 /* It is now a FE error, if the conversion from the canonical
2254 type to the original expression type is not useless. */
2255 gcc_assert (useless_type_conversion_p (old_type, type));
2256 #endif
2260 /* If a NOP conversion is changing a pointer to array of foo to a pointer
2261 to foo, embed that change in the ADDR_EXPR by converting
2262 T array[U];
2263 (T *)&array
2265 &array[L]
2266 where L is the lower bound. For simplicity, only do this for constant
2267 lower bound.
2268 The constraint is that the type of &array[L] is trivially convertible
2269 to T *. */
2271 static void
2272 canonicalize_addr_expr (tree *expr_p)
2274 tree expr = *expr_p;
2275 tree addr_expr = TREE_OPERAND (expr, 0);
2276 tree datype, ddatype, pddatype;
2278 /* We simplify only conversions from an ADDR_EXPR to a pointer type. */
2279 if (!POINTER_TYPE_P (TREE_TYPE (expr))
2280 || TREE_CODE (addr_expr) != ADDR_EXPR)
2281 return;
2283 /* The addr_expr type should be a pointer to an array. */
2284 datype = TREE_TYPE (TREE_TYPE (addr_expr));
2285 if (TREE_CODE (datype) != ARRAY_TYPE)
2286 return;
2288 /* The pointer to element type shall be trivially convertible to
2289 the expression pointer type. */
2290 ddatype = TREE_TYPE (datype);
2291 pddatype = build_pointer_type (ddatype);
2292 if (!useless_type_conversion_p (TYPE_MAIN_VARIANT (TREE_TYPE (expr)),
2293 pddatype))
2294 return;
2296 /* The lower bound and element sizes must be constant. */
2297 if (!TYPE_SIZE_UNIT (ddatype)
2298 || TREE_CODE (TYPE_SIZE_UNIT (ddatype)) != INTEGER_CST
2299 || !TYPE_DOMAIN (datype) || !TYPE_MIN_VALUE (TYPE_DOMAIN (datype))
2300 || TREE_CODE (TYPE_MIN_VALUE (TYPE_DOMAIN (datype))) != INTEGER_CST)
2301 return;
2303 /* All checks succeeded. Build a new node to merge the cast. */
2304 *expr_p = build4 (ARRAY_REF, ddatype, TREE_OPERAND (addr_expr, 0),
2305 TYPE_MIN_VALUE (TYPE_DOMAIN (datype)),
2306 NULL_TREE, NULL_TREE);
2307 *expr_p = build1 (ADDR_EXPR, pddatype, *expr_p);
2309 /* We can have stripped a required restrict qualifier above. */
2310 if (!useless_type_conversion_p (TREE_TYPE (expr), TREE_TYPE (*expr_p)))
2311 *expr_p = fold_convert (TREE_TYPE (expr), *expr_p);
2314 /* *EXPR_P is a NOP_EXPR or CONVERT_EXPR. Remove it and/or other conversions
2315 underneath as appropriate. */
2317 static enum gimplify_status
2318 gimplify_conversion (tree *expr_p)
2320 location_t loc = EXPR_LOCATION (*expr_p);
2321 gcc_assert (CONVERT_EXPR_P (*expr_p));
2323 /* Then strip away all but the outermost conversion. */
2324 STRIP_SIGN_NOPS (TREE_OPERAND (*expr_p, 0));
2326 /* And remove the outermost conversion if it's useless. */
2327 if (tree_ssa_useless_type_conversion (*expr_p))
2328 *expr_p = TREE_OPERAND (*expr_p, 0);
2330 /* If we still have a conversion at the toplevel,
2331 then canonicalize some constructs. */
2332 if (CONVERT_EXPR_P (*expr_p))
2334 tree sub = TREE_OPERAND (*expr_p, 0);
2336 /* If a NOP conversion is changing the type of a COMPONENT_REF
2337 expression, then canonicalize its type now in order to expose more
2338 redundant conversions. */
2339 if (TREE_CODE (sub) == COMPONENT_REF)
2340 canonicalize_component_ref (&TREE_OPERAND (*expr_p, 0));
2342 /* If a NOP conversion is changing a pointer to array of foo
2343 to a pointer to foo, embed that change in the ADDR_EXPR. */
2344 else if (TREE_CODE (sub) == ADDR_EXPR)
2345 canonicalize_addr_expr (expr_p);
2348 /* If we have a conversion to a non-register type force the
2349 use of a VIEW_CONVERT_EXPR instead. */
2350 if (CONVERT_EXPR_P (*expr_p) && !is_gimple_reg_type (TREE_TYPE (*expr_p)))
2351 *expr_p = fold_build1_loc (loc, VIEW_CONVERT_EXPR, TREE_TYPE (*expr_p),
2352 TREE_OPERAND (*expr_p, 0));
2354 /* Canonicalize CONVERT_EXPR to NOP_EXPR. */
2355 if (TREE_CODE (*expr_p) == CONVERT_EXPR)
2356 TREE_SET_CODE (*expr_p, NOP_EXPR);
2358 return GS_OK;
2361 /* Nonlocal VLAs seen in the current function. */
2362 static hash_set<tree> *nonlocal_vlas;
2364 /* The VAR_DECLs created for nonlocal VLAs for debug info purposes. */
2365 static tree nonlocal_vla_vars;
2367 /* Gimplify a VAR_DECL or PARM_DECL. Return GS_OK if we expanded a
2368 DECL_VALUE_EXPR, and it's worth re-examining things. */
2370 static enum gimplify_status
2371 gimplify_var_or_parm_decl (tree *expr_p)
2373 tree decl = *expr_p;
2375 /* ??? If this is a local variable, and it has not been seen in any
2376 outer BIND_EXPR, then it's probably the result of a duplicate
2377 declaration, for which we've already issued an error. It would
2378 be really nice if the front end wouldn't leak these at all.
2379 Currently the only known culprit is C++ destructors, as seen
2380 in g++.old-deja/g++.jason/binding.C. */
2381 if (VAR_P (decl)
2382 && !DECL_SEEN_IN_BIND_EXPR_P (decl)
2383 && !TREE_STATIC (decl) && !DECL_EXTERNAL (decl)
2384 && decl_function_context (decl) == current_function_decl)
2386 gcc_assert (seen_error ());
2387 return GS_ERROR;
2390 /* When within an OMP context, notice uses of variables. */
2391 if (gimplify_omp_ctxp && omp_notice_variable (gimplify_omp_ctxp, decl, true))
2392 return GS_ALL_DONE;
2394 /* If the decl is an alias for another expression, substitute it now. */
2395 if (DECL_HAS_VALUE_EXPR_P (decl))
2397 tree value_expr = DECL_VALUE_EXPR (decl);
2399 /* For referenced nonlocal VLAs add a decl for debugging purposes
2400 to the current function. */
2401 if (VAR_P (decl)
2402 && TREE_CODE (DECL_SIZE_UNIT (decl)) != INTEGER_CST
2403 && nonlocal_vlas != NULL
2404 && TREE_CODE (value_expr) == INDIRECT_REF
2405 && TREE_CODE (TREE_OPERAND (value_expr, 0)) == VAR_DECL
2406 && decl_function_context (decl) != current_function_decl)
2408 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
2409 while (ctx
2410 && (ctx->region_type == ORT_WORKSHARE
2411 || ctx->region_type == ORT_SIMD
2412 || ctx->region_type == ORT_ACC))
2413 ctx = ctx->outer_context;
2414 if (!ctx && !nonlocal_vlas->add (decl))
2416 tree copy = copy_node (decl);
2418 lang_hooks.dup_lang_specific_decl (copy);
2419 SET_DECL_RTL (copy, 0);
2420 TREE_USED (copy) = 1;
2421 DECL_CHAIN (copy) = nonlocal_vla_vars;
2422 nonlocal_vla_vars = copy;
2423 SET_DECL_VALUE_EXPR (copy, unshare_expr (value_expr));
2424 DECL_HAS_VALUE_EXPR_P (copy) = 1;
2428 *expr_p = unshare_expr (value_expr);
2429 return GS_OK;
2432 return GS_ALL_DONE;
2435 /* Recalculate the value of the TREE_SIDE_EFFECTS flag for T. */
2437 static void
2438 recalculate_side_effects (tree t)
2440 enum tree_code code = TREE_CODE (t);
2441 int len = TREE_OPERAND_LENGTH (t);
2442 int i;
2444 switch (TREE_CODE_CLASS (code))
2446 case tcc_expression:
2447 switch (code)
2449 case INIT_EXPR:
2450 case MODIFY_EXPR:
2451 case VA_ARG_EXPR:
2452 case PREDECREMENT_EXPR:
2453 case PREINCREMENT_EXPR:
2454 case POSTDECREMENT_EXPR:
2455 case POSTINCREMENT_EXPR:
2456 /* All of these have side-effects, no matter what their
2457 operands are. */
2458 return;
2460 default:
2461 break;
2463 /* Fall through. */
2465 case tcc_comparison: /* a comparison expression */
2466 case tcc_unary: /* a unary arithmetic expression */
2467 case tcc_binary: /* a binary arithmetic expression */
2468 case tcc_reference: /* a reference */
2469 case tcc_vl_exp: /* a function call */
2470 TREE_SIDE_EFFECTS (t) = TREE_THIS_VOLATILE (t);
2471 for (i = 0; i < len; ++i)
2473 tree op = TREE_OPERAND (t, i);
2474 if (op && TREE_SIDE_EFFECTS (op))
2475 TREE_SIDE_EFFECTS (t) = 1;
2477 break;
2479 case tcc_constant:
2480 /* No side-effects. */
2481 return;
2483 default:
2484 gcc_unreachable ();
2488 /* Gimplify the COMPONENT_REF, ARRAY_REF, REALPART_EXPR or IMAGPART_EXPR
2489 node *EXPR_P.
2491 compound_lval
2492 : min_lval '[' val ']'
2493 | min_lval '.' ID
2494 | compound_lval '[' val ']'
2495 | compound_lval '.' ID
2497 This is not part of the original SIMPLE definition, which separates
2498 array and member references, but it seems reasonable to handle them
2499 together. Also, this way we don't run into problems with union
2500 aliasing; gcc requires that for accesses through a union to alias, the
2501 union reference must be explicit, which was not always the case when we
2502 were splitting up array and member refs.
2504 PRE_P points to the sequence where side effects that must happen before
2505 *EXPR_P should be stored.
2507 POST_P points to the sequence where side effects that must happen after
2508 *EXPR_P should be stored. */
2510 static enum gimplify_status
2511 gimplify_compound_lval (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
2512 fallback_t fallback)
2514 tree *p;
2515 enum gimplify_status ret = GS_ALL_DONE, tret;
2516 int i;
2517 location_t loc = EXPR_LOCATION (*expr_p);
2518 tree expr = *expr_p;
2520 /* Create a stack of the subexpressions so later we can walk them in
2521 order from inner to outer. */
2522 auto_vec<tree, 10> expr_stack;
2524 /* We can handle anything that get_inner_reference can deal with. */
2525 for (p = expr_p; ; p = &TREE_OPERAND (*p, 0))
2527 restart:
2528 /* Fold INDIRECT_REFs now to turn them into ARRAY_REFs. */
2529 if (TREE_CODE (*p) == INDIRECT_REF)
2530 *p = fold_indirect_ref_loc (loc, *p);
2532 if (handled_component_p (*p))
2534 /* Expand DECL_VALUE_EXPR now. In some cases that may expose
2535 additional COMPONENT_REFs. */
2536 else if ((VAR_P (*p) || TREE_CODE (*p) == PARM_DECL)
2537 && gimplify_var_or_parm_decl (p) == GS_OK)
2538 goto restart;
2539 else
2540 break;
2542 expr_stack.safe_push (*p);
2545 gcc_assert (expr_stack.length ());
2547 /* Now EXPR_STACK is a stack of pointers to all the refs we've
2548 walked through and P points to the innermost expression.
2550 Java requires that we elaborated nodes in source order. That
2551 means we must gimplify the inner expression followed by each of
2552 the indices, in order. But we can't gimplify the inner
2553 expression until we deal with any variable bounds, sizes, or
2554 positions in order to deal with PLACEHOLDER_EXPRs.
2556 So we do this in three steps. First we deal with the annotations
2557 for any variables in the components, then we gimplify the base,
2558 then we gimplify any indices, from left to right. */
2559 for (i = expr_stack.length () - 1; i >= 0; i--)
2561 tree t = expr_stack[i];
2563 if (TREE_CODE (t) == ARRAY_REF || TREE_CODE (t) == ARRAY_RANGE_REF)
2565 /* Gimplify the low bound and element type size and put them into
2566 the ARRAY_REF. If these values are set, they have already been
2567 gimplified. */
2568 if (TREE_OPERAND (t, 2) == NULL_TREE)
2570 tree low = unshare_expr (array_ref_low_bound (t));
2571 if (!is_gimple_min_invariant (low))
2573 TREE_OPERAND (t, 2) = low;
2574 tret = gimplify_expr (&TREE_OPERAND (t, 2), pre_p,
2575 post_p, is_gimple_reg,
2576 fb_rvalue);
2577 ret = MIN (ret, tret);
2580 else
2582 tret = gimplify_expr (&TREE_OPERAND (t, 2), pre_p, post_p,
2583 is_gimple_reg, fb_rvalue);
2584 ret = MIN (ret, tret);
2587 if (TREE_OPERAND (t, 3) == NULL_TREE)
2589 tree elmt_type = TREE_TYPE (TREE_TYPE (TREE_OPERAND (t, 0)));
2590 tree elmt_size = unshare_expr (array_ref_element_size (t));
2591 tree factor = size_int (TYPE_ALIGN_UNIT (elmt_type));
2593 /* Divide the element size by the alignment of the element
2594 type (above). */
2595 elmt_size
2596 = size_binop_loc (loc, EXACT_DIV_EXPR, elmt_size, factor);
2598 if (!is_gimple_min_invariant (elmt_size))
2600 TREE_OPERAND (t, 3) = elmt_size;
2601 tret = gimplify_expr (&TREE_OPERAND (t, 3), pre_p,
2602 post_p, is_gimple_reg,
2603 fb_rvalue);
2604 ret = MIN (ret, tret);
2607 else
2609 tret = gimplify_expr (&TREE_OPERAND (t, 3), pre_p, post_p,
2610 is_gimple_reg, fb_rvalue);
2611 ret = MIN (ret, tret);
2614 else if (TREE_CODE (t) == COMPONENT_REF)
2616 /* Set the field offset into T and gimplify it. */
2617 if (TREE_OPERAND (t, 2) == NULL_TREE)
2619 tree offset = unshare_expr (component_ref_field_offset (t));
2620 tree field = TREE_OPERAND (t, 1);
2621 tree factor
2622 = size_int (DECL_OFFSET_ALIGN (field) / BITS_PER_UNIT);
2624 /* Divide the offset by its alignment. */
2625 offset = size_binop_loc (loc, EXACT_DIV_EXPR, offset, factor);
2627 if (!is_gimple_min_invariant (offset))
2629 TREE_OPERAND (t, 2) = offset;
2630 tret = gimplify_expr (&TREE_OPERAND (t, 2), pre_p,
2631 post_p, is_gimple_reg,
2632 fb_rvalue);
2633 ret = MIN (ret, tret);
2636 else
2638 tret = gimplify_expr (&TREE_OPERAND (t, 2), pre_p, post_p,
2639 is_gimple_reg, fb_rvalue);
2640 ret = MIN (ret, tret);
2645 /* Step 2 is to gimplify the base expression. Make sure lvalue is set
2646 so as to match the min_lval predicate. Failure to do so may result
2647 in the creation of large aggregate temporaries. */
2648 tret = gimplify_expr (p, pre_p, post_p, is_gimple_min_lval,
2649 fallback | fb_lvalue);
2650 ret = MIN (ret, tret);
2652 /* And finally, the indices and operands of ARRAY_REF. During this
2653 loop we also remove any useless conversions. */
2654 for (; expr_stack.length () > 0; )
2656 tree t = expr_stack.pop ();
2658 if (TREE_CODE (t) == ARRAY_REF || TREE_CODE (t) == ARRAY_RANGE_REF)
2660 /* Gimplify the dimension. */
2661 if (!is_gimple_min_invariant (TREE_OPERAND (t, 1)))
2663 tret = gimplify_expr (&TREE_OPERAND (t, 1), pre_p, post_p,
2664 is_gimple_val, fb_rvalue);
2665 ret = MIN (ret, tret);
2669 STRIP_USELESS_TYPE_CONVERSION (TREE_OPERAND (t, 0));
2671 /* The innermost expression P may have originally had
2672 TREE_SIDE_EFFECTS set which would have caused all the outer
2673 expressions in *EXPR_P leading to P to also have had
2674 TREE_SIDE_EFFECTS set. */
2675 recalculate_side_effects (t);
2678 /* If the outermost expression is a COMPONENT_REF, canonicalize its type. */
2679 if ((fallback & fb_rvalue) && TREE_CODE (*expr_p) == COMPONENT_REF)
2681 canonicalize_component_ref (expr_p);
2684 expr_stack.release ();
2686 gcc_assert (*expr_p == expr || ret != GS_ALL_DONE);
2688 return ret;
2691 /* Gimplify the self modifying expression pointed to by EXPR_P
2692 (++, --, +=, -=).
2694 PRE_P points to the list where side effects that must happen before
2695 *EXPR_P should be stored.
2697 POST_P points to the list where side effects that must happen after
2698 *EXPR_P should be stored.
2700 WANT_VALUE is nonzero iff we want to use the value of this expression
2701 in another expression.
2703 ARITH_TYPE is the type the computation should be performed in. */
2705 enum gimplify_status
2706 gimplify_self_mod_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
2707 bool want_value, tree arith_type)
2709 enum tree_code code;
2710 tree lhs, lvalue, rhs, t1;
2711 gimple_seq post = NULL, *orig_post_p = post_p;
2712 bool postfix;
2713 enum tree_code arith_code;
2714 enum gimplify_status ret;
2715 location_t loc = EXPR_LOCATION (*expr_p);
2717 code = TREE_CODE (*expr_p);
2719 gcc_assert (code == POSTINCREMENT_EXPR || code == POSTDECREMENT_EXPR
2720 || code == PREINCREMENT_EXPR || code == PREDECREMENT_EXPR);
2722 /* Prefix or postfix? */
2723 if (code == POSTINCREMENT_EXPR || code == POSTDECREMENT_EXPR)
2724 /* Faster to treat as prefix if result is not used. */
2725 postfix = want_value;
2726 else
2727 postfix = false;
2729 /* For postfix, make sure the inner expression's post side effects
2730 are executed after side effects from this expression. */
2731 if (postfix)
2732 post_p = &post;
2734 /* Add or subtract? */
2735 if (code == PREINCREMENT_EXPR || code == POSTINCREMENT_EXPR)
2736 arith_code = PLUS_EXPR;
2737 else
2738 arith_code = MINUS_EXPR;
2740 /* Gimplify the LHS into a GIMPLE lvalue. */
2741 lvalue = TREE_OPERAND (*expr_p, 0);
2742 ret = gimplify_expr (&lvalue, pre_p, post_p, is_gimple_lvalue, fb_lvalue);
2743 if (ret == GS_ERROR)
2744 return ret;
2746 /* Extract the operands to the arithmetic operation. */
2747 lhs = lvalue;
2748 rhs = TREE_OPERAND (*expr_p, 1);
2750 /* For postfix operator, we evaluate the LHS to an rvalue and then use
2751 that as the result value and in the postqueue operation. */
2752 if (postfix)
2754 ret = gimplify_expr (&lhs, pre_p, post_p, is_gimple_val, fb_rvalue);
2755 if (ret == GS_ERROR)
2756 return ret;
2758 lhs = get_initialized_tmp_var (lhs, pre_p, NULL);
2761 /* For POINTERs increment, use POINTER_PLUS_EXPR. */
2762 if (POINTER_TYPE_P (TREE_TYPE (lhs)))
2764 rhs = convert_to_ptrofftype_loc (loc, rhs);
2765 if (arith_code == MINUS_EXPR)
2766 rhs = fold_build1_loc (loc, NEGATE_EXPR, TREE_TYPE (rhs), rhs);
2767 t1 = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (*expr_p), lhs, rhs);
2769 else
2770 t1 = fold_convert (TREE_TYPE (*expr_p),
2771 fold_build2 (arith_code, arith_type,
2772 fold_convert (arith_type, lhs),
2773 fold_convert (arith_type, rhs)));
2775 if (postfix)
2777 gimplify_assign (lvalue, t1, pre_p);
2778 gimplify_seq_add_seq (orig_post_p, post);
2779 *expr_p = lhs;
2780 return GS_ALL_DONE;
2782 else
2784 *expr_p = build2 (MODIFY_EXPR, TREE_TYPE (lvalue), lvalue, t1);
2785 return GS_OK;
2789 /* If *EXPR_P has a variable sized type, wrap it in a WITH_SIZE_EXPR. */
2791 static void
2792 maybe_with_size_expr (tree *expr_p)
2794 tree expr = *expr_p;
2795 tree type = TREE_TYPE (expr);
2796 tree size;
2798 /* If we've already wrapped this or the type is error_mark_node, we can't do
2799 anything. */
2800 if (TREE_CODE (expr) == WITH_SIZE_EXPR
2801 || type == error_mark_node)
2802 return;
2804 /* If the size isn't known or is a constant, we have nothing to do. */
2805 size = TYPE_SIZE_UNIT (type);
2806 if (!size || TREE_CODE (size) == INTEGER_CST)
2807 return;
2809 /* Otherwise, make a WITH_SIZE_EXPR. */
2810 size = unshare_expr (size);
2811 size = SUBSTITUTE_PLACEHOLDER_IN_EXPR (size, expr);
2812 *expr_p = build2 (WITH_SIZE_EXPR, type, expr, size);
2815 /* Helper for gimplify_call_expr. Gimplify a single argument *ARG_P
2816 Store any side-effects in PRE_P. CALL_LOCATION is the location of
2817 the CALL_EXPR. If ALLOW_SSA is set the actual parameter may be
2818 gimplified to an SSA name. */
2820 enum gimplify_status
2821 gimplify_arg (tree *arg_p, gimple_seq *pre_p, location_t call_location,
2822 bool allow_ssa)
2824 bool (*test) (tree);
2825 fallback_t fb;
2827 /* In general, we allow lvalues for function arguments to avoid
2828 extra overhead of copying large aggregates out of even larger
2829 aggregates into temporaries only to copy the temporaries to
2830 the argument list. Make optimizers happy by pulling out to
2831 temporaries those types that fit in registers. */
2832 if (is_gimple_reg_type (TREE_TYPE (*arg_p)))
2833 test = is_gimple_val, fb = fb_rvalue;
2834 else
2836 test = is_gimple_lvalue, fb = fb_either;
2837 /* Also strip a TARGET_EXPR that would force an extra copy. */
2838 if (TREE_CODE (*arg_p) == TARGET_EXPR)
2840 tree init = TARGET_EXPR_INITIAL (*arg_p);
2841 if (init
2842 && !VOID_TYPE_P (TREE_TYPE (init)))
2843 *arg_p = init;
2847 /* If this is a variable sized type, we must remember the size. */
2848 maybe_with_size_expr (arg_p);
2850 /* FIXME diagnostics: This will mess up gcc.dg/Warray-bounds.c. */
2851 /* Make sure arguments have the same location as the function call
2852 itself. */
2853 protected_set_expr_location (*arg_p, call_location);
2855 /* There is a sequence point before a function call. Side effects in
2856 the argument list must occur before the actual call. So, when
2857 gimplifying arguments, force gimplify_expr to use an internal
2858 post queue which is then appended to the end of PRE_P. */
2859 return gimplify_expr (arg_p, pre_p, NULL, test, fb, allow_ssa);
2862 /* Don't fold inside offloading or taskreg regions: it can break code by
2863 adding decl references that weren't in the source. We'll do it during
2864 omplower pass instead. */
2866 static bool
2867 maybe_fold_stmt (gimple_stmt_iterator *gsi)
2869 struct gimplify_omp_ctx *ctx;
2870 for (ctx = gimplify_omp_ctxp; ctx; ctx = ctx->outer_context)
2871 if ((ctx->region_type & (ORT_TARGET | ORT_PARALLEL | ORT_TASK)) != 0)
2872 return false;
2873 return fold_stmt (gsi);
2876 /* Gimplify the CALL_EXPR node *EXPR_P into the GIMPLE sequence PRE_P.
2877 WANT_VALUE is true if the result of the call is desired. */
2879 static enum gimplify_status
2880 gimplify_call_expr (tree *expr_p, gimple_seq *pre_p, bool want_value)
2882 tree fndecl, parms, p, fnptrtype;
2883 enum gimplify_status ret;
2884 int i, nargs;
2885 gcall *call;
2886 bool builtin_va_start_p = false;
2887 location_t loc = EXPR_LOCATION (*expr_p);
2889 gcc_assert (TREE_CODE (*expr_p) == CALL_EXPR);
2891 /* For reliable diagnostics during inlining, it is necessary that
2892 every call_expr be annotated with file and line. */
2893 if (! EXPR_HAS_LOCATION (*expr_p))
2894 SET_EXPR_LOCATION (*expr_p, input_location);
2896 /* Gimplify internal functions created in the FEs. */
2897 if (CALL_EXPR_FN (*expr_p) == NULL_TREE)
2899 if (want_value)
2900 return GS_ALL_DONE;
2902 nargs = call_expr_nargs (*expr_p);
2903 enum internal_fn ifn = CALL_EXPR_IFN (*expr_p);
2904 auto_vec<tree> vargs (nargs);
2906 for (i = 0; i < nargs; i++)
2908 gimplify_arg (&CALL_EXPR_ARG (*expr_p, i), pre_p,
2909 EXPR_LOCATION (*expr_p));
2910 vargs.quick_push (CALL_EXPR_ARG (*expr_p, i));
2912 gimple *call = gimple_build_call_internal_vec (ifn, vargs);
2913 gimplify_seq_add_stmt (pre_p, call);
2914 return GS_ALL_DONE;
2917 /* This may be a call to a builtin function.
2919 Builtin function calls may be transformed into different
2920 (and more efficient) builtin function calls under certain
2921 circumstances. Unfortunately, gimplification can muck things
2922 up enough that the builtin expanders are not aware that certain
2923 transformations are still valid.
2925 So we attempt transformation/gimplification of the call before
2926 we gimplify the CALL_EXPR. At this time we do not manage to
2927 transform all calls in the same manner as the expanders do, but
2928 we do transform most of them. */
2929 fndecl = get_callee_fndecl (*expr_p);
2930 if (fndecl
2931 && DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_NORMAL)
2932 switch (DECL_FUNCTION_CODE (fndecl))
2934 case BUILT_IN_ALLOCA:
2935 case BUILT_IN_ALLOCA_WITH_ALIGN:
2936 /* If the call has been built for a variable-sized object, then we
2937 want to restore the stack level when the enclosing BIND_EXPR is
2938 exited to reclaim the allocated space; otherwise, we precisely
2939 need to do the opposite and preserve the latest stack level. */
2940 if (CALL_ALLOCA_FOR_VAR_P (*expr_p))
2941 gimplify_ctxp->save_stack = true;
2942 else
2943 gimplify_ctxp->keep_stack = true;
2944 break;
2946 case BUILT_IN_VA_START:
2948 builtin_va_start_p = TRUE;
2949 if (call_expr_nargs (*expr_p) < 2)
2951 error ("too few arguments to function %<va_start%>");
2952 *expr_p = build_empty_stmt (EXPR_LOCATION (*expr_p));
2953 return GS_OK;
2956 if (fold_builtin_next_arg (*expr_p, true))
2958 *expr_p = build_empty_stmt (EXPR_LOCATION (*expr_p));
2959 return GS_OK;
2961 break;
2964 default:
2967 if (fndecl && DECL_BUILT_IN (fndecl))
2969 tree new_tree = fold_call_expr (input_location, *expr_p, !want_value);
2970 if (new_tree && new_tree != *expr_p)
2972 /* There was a transformation of this call which computes the
2973 same value, but in a more efficient way. Return and try
2974 again. */
2975 *expr_p = new_tree;
2976 return GS_OK;
2980 /* Remember the original function pointer type. */
2981 fnptrtype = TREE_TYPE (CALL_EXPR_FN (*expr_p));
2983 /* There is a sequence point before the call, so any side effects in
2984 the calling expression must occur before the actual call. Force
2985 gimplify_expr to use an internal post queue. */
2986 ret = gimplify_expr (&CALL_EXPR_FN (*expr_p), pre_p, NULL,
2987 is_gimple_call_addr, fb_rvalue);
2989 nargs = call_expr_nargs (*expr_p);
2991 /* Get argument types for verification. */
2992 fndecl = get_callee_fndecl (*expr_p);
2993 parms = NULL_TREE;
2994 if (fndecl)
2995 parms = TYPE_ARG_TYPES (TREE_TYPE (fndecl));
2996 else
2997 parms = TYPE_ARG_TYPES (TREE_TYPE (fnptrtype));
2999 if (fndecl && DECL_ARGUMENTS (fndecl))
3000 p = DECL_ARGUMENTS (fndecl);
3001 else if (parms)
3002 p = parms;
3003 else
3004 p = NULL_TREE;
3005 for (i = 0; i < nargs && p; i++, p = TREE_CHAIN (p))
3008 /* If the last argument is __builtin_va_arg_pack () and it is not
3009 passed as a named argument, decrease the number of CALL_EXPR
3010 arguments and set instead the CALL_EXPR_VA_ARG_PACK flag. */
3011 if (!p
3012 && i < nargs
3013 && TREE_CODE (CALL_EXPR_ARG (*expr_p, nargs - 1)) == CALL_EXPR)
3015 tree last_arg = CALL_EXPR_ARG (*expr_p, nargs - 1);
3016 tree last_arg_fndecl = get_callee_fndecl (last_arg);
3018 if (last_arg_fndecl
3019 && TREE_CODE (last_arg_fndecl) == FUNCTION_DECL
3020 && DECL_BUILT_IN_CLASS (last_arg_fndecl) == BUILT_IN_NORMAL
3021 && DECL_FUNCTION_CODE (last_arg_fndecl) == BUILT_IN_VA_ARG_PACK)
3023 tree call = *expr_p;
3025 --nargs;
3026 *expr_p = build_call_array_loc (loc, TREE_TYPE (call),
3027 CALL_EXPR_FN (call),
3028 nargs, CALL_EXPR_ARGP (call));
3030 /* Copy all CALL_EXPR flags, location and block, except
3031 CALL_EXPR_VA_ARG_PACK flag. */
3032 CALL_EXPR_STATIC_CHAIN (*expr_p) = CALL_EXPR_STATIC_CHAIN (call);
3033 CALL_EXPR_TAILCALL (*expr_p) = CALL_EXPR_TAILCALL (call);
3034 CALL_EXPR_RETURN_SLOT_OPT (*expr_p)
3035 = CALL_EXPR_RETURN_SLOT_OPT (call);
3036 CALL_FROM_THUNK_P (*expr_p) = CALL_FROM_THUNK_P (call);
3037 SET_EXPR_LOCATION (*expr_p, EXPR_LOCATION (call));
3039 /* Set CALL_EXPR_VA_ARG_PACK. */
3040 CALL_EXPR_VA_ARG_PACK (*expr_p) = 1;
3044 /* If the call returns twice then after building the CFG the call
3045 argument computations will no longer dominate the call because
3046 we add an abnormal incoming edge to the call. So do not use SSA
3047 vars there. */
3048 bool returns_twice = call_expr_flags (*expr_p) & ECF_RETURNS_TWICE;
3050 /* Gimplify the function arguments. */
3051 if (nargs > 0)
3053 for (i = (PUSH_ARGS_REVERSED ? nargs - 1 : 0);
3054 PUSH_ARGS_REVERSED ? i >= 0 : i < nargs;
3055 PUSH_ARGS_REVERSED ? i-- : i++)
3057 enum gimplify_status t;
3059 /* Avoid gimplifying the second argument to va_start, which needs to
3060 be the plain PARM_DECL. */
3061 if ((i != 1) || !builtin_va_start_p)
3063 t = gimplify_arg (&CALL_EXPR_ARG (*expr_p, i), pre_p,
3064 EXPR_LOCATION (*expr_p), ! returns_twice);
3066 if (t == GS_ERROR)
3067 ret = GS_ERROR;
3072 /* Gimplify the static chain. */
3073 if (CALL_EXPR_STATIC_CHAIN (*expr_p))
3075 if (fndecl && !DECL_STATIC_CHAIN (fndecl))
3076 CALL_EXPR_STATIC_CHAIN (*expr_p) = NULL;
3077 else
3079 enum gimplify_status t;
3080 t = gimplify_arg (&CALL_EXPR_STATIC_CHAIN (*expr_p), pre_p,
3081 EXPR_LOCATION (*expr_p), ! returns_twice);
3082 if (t == GS_ERROR)
3083 ret = GS_ERROR;
3087 /* Verify the function result. */
3088 if (want_value && fndecl
3089 && VOID_TYPE_P (TREE_TYPE (TREE_TYPE (fnptrtype))))
3091 error_at (loc, "using result of function returning %<void%>");
3092 ret = GS_ERROR;
3095 /* Try this again in case gimplification exposed something. */
3096 if (ret != GS_ERROR)
3098 tree new_tree = fold_call_expr (input_location, *expr_p, !want_value);
3100 if (new_tree && new_tree != *expr_p)
3102 /* There was a transformation of this call which computes the
3103 same value, but in a more efficient way. Return and try
3104 again. */
3105 *expr_p = new_tree;
3106 return GS_OK;
3109 else
3111 *expr_p = error_mark_node;
3112 return GS_ERROR;
3115 /* If the function is "const" or "pure", then clear TREE_SIDE_EFFECTS on its
3116 decl. This allows us to eliminate redundant or useless
3117 calls to "const" functions. */
3118 if (TREE_CODE (*expr_p) == CALL_EXPR)
3120 int flags = call_expr_flags (*expr_p);
3121 if (flags & (ECF_CONST | ECF_PURE)
3122 /* An infinite loop is considered a side effect. */
3123 && !(flags & (ECF_LOOPING_CONST_OR_PURE)))
3124 TREE_SIDE_EFFECTS (*expr_p) = 0;
3127 /* If the value is not needed by the caller, emit a new GIMPLE_CALL
3128 and clear *EXPR_P. Otherwise, leave *EXPR_P in its gimplified
3129 form and delegate the creation of a GIMPLE_CALL to
3130 gimplify_modify_expr. This is always possible because when
3131 WANT_VALUE is true, the caller wants the result of this call into
3132 a temporary, which means that we will emit an INIT_EXPR in
3133 internal_get_tmp_var which will then be handled by
3134 gimplify_modify_expr. */
3135 if (!want_value)
3137 /* The CALL_EXPR in *EXPR_P is already in GIMPLE form, so all we
3138 have to do is replicate it as a GIMPLE_CALL tuple. */
3139 gimple_stmt_iterator gsi;
3140 call = gimple_build_call_from_tree (*expr_p);
3141 gimple_call_set_fntype (call, TREE_TYPE (fnptrtype));
3142 notice_special_calls (call);
3143 gimplify_seq_add_stmt (pre_p, call);
3144 gsi = gsi_last (*pre_p);
3145 maybe_fold_stmt (&gsi);
3146 *expr_p = NULL_TREE;
3148 else
3149 /* Remember the original function type. */
3150 CALL_EXPR_FN (*expr_p) = build1 (NOP_EXPR, fnptrtype,
3151 CALL_EXPR_FN (*expr_p));
3153 return ret;
3156 /* Handle shortcut semantics in the predicate operand of a COND_EXPR by
3157 rewriting it into multiple COND_EXPRs, and possibly GOTO_EXPRs.
3159 TRUE_LABEL_P and FALSE_LABEL_P point to the labels to jump to if the
3160 condition is true or false, respectively. If null, we should generate
3161 our own to skip over the evaluation of this specific expression.
3163 LOCUS is the source location of the COND_EXPR.
3165 This function is the tree equivalent of do_jump.
3167 shortcut_cond_r should only be called by shortcut_cond_expr. */
3169 static tree
3170 shortcut_cond_r (tree pred, tree *true_label_p, tree *false_label_p,
3171 location_t locus)
3173 tree local_label = NULL_TREE;
3174 tree t, expr = NULL;
3176 /* OK, it's not a simple case; we need to pull apart the COND_EXPR to
3177 retain the shortcut semantics. Just insert the gotos here;
3178 shortcut_cond_expr will append the real blocks later. */
3179 if (TREE_CODE (pred) == TRUTH_ANDIF_EXPR)
3181 location_t new_locus;
3183 /* Turn if (a && b) into
3185 if (a); else goto no;
3186 if (b) goto yes; else goto no;
3187 (no:) */
3189 if (false_label_p == NULL)
3190 false_label_p = &local_label;
3192 /* Keep the original source location on the first 'if'. */
3193 t = shortcut_cond_r (TREE_OPERAND (pred, 0), NULL, false_label_p, locus);
3194 append_to_statement_list (t, &expr);
3196 /* Set the source location of the && on the second 'if'. */
3197 new_locus = EXPR_HAS_LOCATION (pred) ? EXPR_LOCATION (pred) : locus;
3198 t = shortcut_cond_r (TREE_OPERAND (pred, 1), true_label_p, false_label_p,
3199 new_locus);
3200 append_to_statement_list (t, &expr);
3202 else if (TREE_CODE (pred) == TRUTH_ORIF_EXPR)
3204 location_t new_locus;
3206 /* Turn if (a || b) into
3208 if (a) goto yes;
3209 if (b) goto yes; else goto no;
3210 (yes:) */
3212 if (true_label_p == NULL)
3213 true_label_p = &local_label;
3215 /* Keep the original source location on the first 'if'. */
3216 t = shortcut_cond_r (TREE_OPERAND (pred, 0), true_label_p, NULL, locus);
3217 append_to_statement_list (t, &expr);
3219 /* Set the source location of the || on the second 'if'. */
3220 new_locus = EXPR_HAS_LOCATION (pred) ? EXPR_LOCATION (pred) : locus;
3221 t = shortcut_cond_r (TREE_OPERAND (pred, 1), true_label_p, false_label_p,
3222 new_locus);
3223 append_to_statement_list (t, &expr);
3225 else if (TREE_CODE (pred) == COND_EXPR
3226 && !VOID_TYPE_P (TREE_TYPE (TREE_OPERAND (pred, 1)))
3227 && !VOID_TYPE_P (TREE_TYPE (TREE_OPERAND (pred, 2))))
3229 location_t new_locus;
3231 /* As long as we're messing with gotos, turn if (a ? b : c) into
3232 if (a)
3233 if (b) goto yes; else goto no;
3234 else
3235 if (c) goto yes; else goto no;
3237 Don't do this if one of the arms has void type, which can happen
3238 in C++ when the arm is throw. */
3240 /* Keep the original source location on the first 'if'. Set the source
3241 location of the ? on the second 'if'. */
3242 new_locus = EXPR_HAS_LOCATION (pred) ? EXPR_LOCATION (pred) : locus;
3243 expr = build3 (COND_EXPR, void_type_node, TREE_OPERAND (pred, 0),
3244 shortcut_cond_r (TREE_OPERAND (pred, 1), true_label_p,
3245 false_label_p, locus),
3246 shortcut_cond_r (TREE_OPERAND (pred, 2), true_label_p,
3247 false_label_p, new_locus));
3249 else
3251 expr = build3 (COND_EXPR, void_type_node, pred,
3252 build_and_jump (true_label_p),
3253 build_and_jump (false_label_p));
3254 SET_EXPR_LOCATION (expr, locus);
3257 if (local_label)
3259 t = build1 (LABEL_EXPR, void_type_node, local_label);
3260 append_to_statement_list (t, &expr);
3263 return expr;
3266 /* Given a conditional expression EXPR with short-circuit boolean
3267 predicates using TRUTH_ANDIF_EXPR or TRUTH_ORIF_EXPR, break the
3268 predicate apart into the equivalent sequence of conditionals. */
3270 static tree
3271 shortcut_cond_expr (tree expr)
3273 tree pred = TREE_OPERAND (expr, 0);
3274 tree then_ = TREE_OPERAND (expr, 1);
3275 tree else_ = TREE_OPERAND (expr, 2);
3276 tree true_label, false_label, end_label, t;
3277 tree *true_label_p;
3278 tree *false_label_p;
3279 bool emit_end, emit_false, jump_over_else;
3280 bool then_se = then_ && TREE_SIDE_EFFECTS (then_);
3281 bool else_se = else_ && TREE_SIDE_EFFECTS (else_);
3283 /* First do simple transformations. */
3284 if (!else_se)
3286 /* If there is no 'else', turn
3287 if (a && b) then c
3288 into
3289 if (a) if (b) then c. */
3290 while (TREE_CODE (pred) == TRUTH_ANDIF_EXPR)
3292 /* Keep the original source location on the first 'if'. */
3293 location_t locus = EXPR_LOC_OR_LOC (expr, input_location);
3294 TREE_OPERAND (expr, 0) = TREE_OPERAND (pred, 1);
3295 /* Set the source location of the && on the second 'if'. */
3296 if (EXPR_HAS_LOCATION (pred))
3297 SET_EXPR_LOCATION (expr, EXPR_LOCATION (pred));
3298 then_ = shortcut_cond_expr (expr);
3299 then_se = then_ && TREE_SIDE_EFFECTS (then_);
3300 pred = TREE_OPERAND (pred, 0);
3301 expr = build3 (COND_EXPR, void_type_node, pred, then_, NULL_TREE);
3302 SET_EXPR_LOCATION (expr, locus);
3306 if (!then_se)
3308 /* If there is no 'then', turn
3309 if (a || b); else d
3310 into
3311 if (a); else if (b); else d. */
3312 while (TREE_CODE (pred) == TRUTH_ORIF_EXPR)
3314 /* Keep the original source location on the first 'if'. */
3315 location_t locus = EXPR_LOC_OR_LOC (expr, input_location);
3316 TREE_OPERAND (expr, 0) = TREE_OPERAND (pred, 1);
3317 /* Set the source location of the || on the second 'if'. */
3318 if (EXPR_HAS_LOCATION (pred))
3319 SET_EXPR_LOCATION (expr, EXPR_LOCATION (pred));
3320 else_ = shortcut_cond_expr (expr);
3321 else_se = else_ && TREE_SIDE_EFFECTS (else_);
3322 pred = TREE_OPERAND (pred, 0);
3323 expr = build3 (COND_EXPR, void_type_node, pred, NULL_TREE, else_);
3324 SET_EXPR_LOCATION (expr, locus);
3328 /* If we're done, great. */
3329 if (TREE_CODE (pred) != TRUTH_ANDIF_EXPR
3330 && TREE_CODE (pred) != TRUTH_ORIF_EXPR)
3331 return expr;
3333 /* Otherwise we need to mess with gotos. Change
3334 if (a) c; else d;
3336 if (a); else goto no;
3337 c; goto end;
3338 no: d; end:
3339 and recursively gimplify the condition. */
3341 true_label = false_label = end_label = NULL_TREE;
3343 /* If our arms just jump somewhere, hijack those labels so we don't
3344 generate jumps to jumps. */
3346 if (then_
3347 && TREE_CODE (then_) == GOTO_EXPR
3348 && TREE_CODE (GOTO_DESTINATION (then_)) == LABEL_DECL)
3350 true_label = GOTO_DESTINATION (then_);
3351 then_ = NULL;
3352 then_se = false;
3355 if (else_
3356 && TREE_CODE (else_) == GOTO_EXPR
3357 && TREE_CODE (GOTO_DESTINATION (else_)) == LABEL_DECL)
3359 false_label = GOTO_DESTINATION (else_);
3360 else_ = NULL;
3361 else_se = false;
3364 /* If we aren't hijacking a label for the 'then' branch, it falls through. */
3365 if (true_label)
3366 true_label_p = &true_label;
3367 else
3368 true_label_p = NULL;
3370 /* The 'else' branch also needs a label if it contains interesting code. */
3371 if (false_label || else_se)
3372 false_label_p = &false_label;
3373 else
3374 false_label_p = NULL;
3376 /* If there was nothing else in our arms, just forward the label(s). */
3377 if (!then_se && !else_se)
3378 return shortcut_cond_r (pred, true_label_p, false_label_p,
3379 EXPR_LOC_OR_LOC (expr, input_location));
3381 /* If our last subexpression already has a terminal label, reuse it. */
3382 if (else_se)
3383 t = expr_last (else_);
3384 else if (then_se)
3385 t = expr_last (then_);
3386 else
3387 t = NULL;
3388 if (t && TREE_CODE (t) == LABEL_EXPR)
3389 end_label = LABEL_EXPR_LABEL (t);
3391 /* If we don't care about jumping to the 'else' branch, jump to the end
3392 if the condition is false. */
3393 if (!false_label_p)
3394 false_label_p = &end_label;
3396 /* We only want to emit these labels if we aren't hijacking them. */
3397 emit_end = (end_label == NULL_TREE);
3398 emit_false = (false_label == NULL_TREE);
3400 /* We only emit the jump over the else clause if we have to--if the
3401 then clause may fall through. Otherwise we can wind up with a
3402 useless jump and a useless label at the end of gimplified code,
3403 which will cause us to think that this conditional as a whole
3404 falls through even if it doesn't. If we then inline a function
3405 which ends with such a condition, that can cause us to issue an
3406 inappropriate warning about control reaching the end of a
3407 non-void function. */
3408 jump_over_else = block_may_fallthru (then_);
3410 pred = shortcut_cond_r (pred, true_label_p, false_label_p,
3411 EXPR_LOC_OR_LOC (expr, input_location));
3413 expr = NULL;
3414 append_to_statement_list (pred, &expr);
3416 append_to_statement_list (then_, &expr);
3417 if (else_se)
3419 if (jump_over_else)
3421 tree last = expr_last (expr);
3422 t = build_and_jump (&end_label);
3423 if (EXPR_HAS_LOCATION (last))
3424 SET_EXPR_LOCATION (t, EXPR_LOCATION (last));
3425 append_to_statement_list (t, &expr);
3427 if (emit_false)
3429 t = build1 (LABEL_EXPR, void_type_node, false_label);
3430 append_to_statement_list (t, &expr);
3432 append_to_statement_list (else_, &expr);
3434 if (emit_end && end_label)
3436 t = build1 (LABEL_EXPR, void_type_node, end_label);
3437 append_to_statement_list (t, &expr);
3440 return expr;
3443 /* EXPR is used in a boolean context; make sure it has BOOLEAN_TYPE. */
3445 tree
3446 gimple_boolify (tree expr)
3448 tree type = TREE_TYPE (expr);
3449 location_t loc = EXPR_LOCATION (expr);
3451 if (TREE_CODE (expr) == NE_EXPR
3452 && TREE_CODE (TREE_OPERAND (expr, 0)) == CALL_EXPR
3453 && integer_zerop (TREE_OPERAND (expr, 1)))
3455 tree call = TREE_OPERAND (expr, 0);
3456 tree fn = get_callee_fndecl (call);
3458 /* For __builtin_expect ((long) (x), y) recurse into x as well
3459 if x is truth_value_p. */
3460 if (fn
3461 && DECL_BUILT_IN_CLASS (fn) == BUILT_IN_NORMAL
3462 && DECL_FUNCTION_CODE (fn) == BUILT_IN_EXPECT
3463 && call_expr_nargs (call) == 2)
3465 tree arg = CALL_EXPR_ARG (call, 0);
3466 if (arg)
3468 if (TREE_CODE (arg) == NOP_EXPR
3469 && TREE_TYPE (arg) == TREE_TYPE (call))
3470 arg = TREE_OPERAND (arg, 0);
3471 if (truth_value_p (TREE_CODE (arg)))
3473 arg = gimple_boolify (arg);
3474 CALL_EXPR_ARG (call, 0)
3475 = fold_convert_loc (loc, TREE_TYPE (call), arg);
3481 switch (TREE_CODE (expr))
3483 case TRUTH_AND_EXPR:
3484 case TRUTH_OR_EXPR:
3485 case TRUTH_XOR_EXPR:
3486 case TRUTH_ANDIF_EXPR:
3487 case TRUTH_ORIF_EXPR:
3488 /* Also boolify the arguments of truth exprs. */
3489 TREE_OPERAND (expr, 1) = gimple_boolify (TREE_OPERAND (expr, 1));
3490 /* FALLTHRU */
3492 case TRUTH_NOT_EXPR:
3493 TREE_OPERAND (expr, 0) = gimple_boolify (TREE_OPERAND (expr, 0));
3495 /* These expressions always produce boolean results. */
3496 if (TREE_CODE (type) != BOOLEAN_TYPE)
3497 TREE_TYPE (expr) = boolean_type_node;
3498 return expr;
3500 case ANNOTATE_EXPR:
3501 switch ((enum annot_expr_kind) TREE_INT_CST_LOW (TREE_OPERAND (expr, 1)))
3503 case annot_expr_ivdep_kind:
3504 case annot_expr_no_vector_kind:
3505 case annot_expr_vector_kind:
3506 TREE_OPERAND (expr, 0) = gimple_boolify (TREE_OPERAND (expr, 0));
3507 if (TREE_CODE (type) != BOOLEAN_TYPE)
3508 TREE_TYPE (expr) = boolean_type_node;
3509 return expr;
3510 default:
3511 gcc_unreachable ();
3514 default:
3515 if (COMPARISON_CLASS_P (expr))
3517 /* There expressions always prduce boolean results. */
3518 if (TREE_CODE (type) != BOOLEAN_TYPE)
3519 TREE_TYPE (expr) = boolean_type_node;
3520 return expr;
3522 /* Other expressions that get here must have boolean values, but
3523 might need to be converted to the appropriate mode. */
3524 if (TREE_CODE (type) == BOOLEAN_TYPE)
3525 return expr;
3526 return fold_convert_loc (loc, boolean_type_node, expr);
3530 /* Given a conditional expression *EXPR_P without side effects, gimplify
3531 its operands. New statements are inserted to PRE_P. */
3533 static enum gimplify_status
3534 gimplify_pure_cond_expr (tree *expr_p, gimple_seq *pre_p)
3536 tree expr = *expr_p, cond;
3537 enum gimplify_status ret, tret;
3538 enum tree_code code;
3540 cond = gimple_boolify (COND_EXPR_COND (expr));
3542 /* We need to handle && and || specially, as their gimplification
3543 creates pure cond_expr, thus leading to an infinite cycle otherwise. */
3544 code = TREE_CODE (cond);
3545 if (code == TRUTH_ANDIF_EXPR)
3546 TREE_SET_CODE (cond, TRUTH_AND_EXPR);
3547 else if (code == TRUTH_ORIF_EXPR)
3548 TREE_SET_CODE (cond, TRUTH_OR_EXPR);
3549 ret = gimplify_expr (&cond, pre_p, NULL, is_gimple_condexpr, fb_rvalue);
3550 COND_EXPR_COND (*expr_p) = cond;
3552 tret = gimplify_expr (&COND_EXPR_THEN (expr), pre_p, NULL,
3553 is_gimple_val, fb_rvalue);
3554 ret = MIN (ret, tret);
3555 tret = gimplify_expr (&COND_EXPR_ELSE (expr), pre_p, NULL,
3556 is_gimple_val, fb_rvalue);
3558 return MIN (ret, tret);
3561 /* Return true if evaluating EXPR could trap.
3562 EXPR is GENERIC, while tree_could_trap_p can be called
3563 only on GIMPLE. */
3565 static bool
3566 generic_expr_could_trap_p (tree expr)
3568 unsigned i, n;
3570 if (!expr || is_gimple_val (expr))
3571 return false;
3573 if (!EXPR_P (expr) || tree_could_trap_p (expr))
3574 return true;
3576 n = TREE_OPERAND_LENGTH (expr);
3577 for (i = 0; i < n; i++)
3578 if (generic_expr_could_trap_p (TREE_OPERAND (expr, i)))
3579 return true;
3581 return false;
3584 /* Convert the conditional expression pointed to by EXPR_P '(p) ? a : b;'
3585 into
3587 if (p) if (p)
3588 t1 = a; a;
3589 else or else
3590 t1 = b; b;
3593 The second form is used when *EXPR_P is of type void.
3595 PRE_P points to the list where side effects that must happen before
3596 *EXPR_P should be stored. */
3598 static enum gimplify_status
3599 gimplify_cond_expr (tree *expr_p, gimple_seq *pre_p, fallback_t fallback)
3601 tree expr = *expr_p;
3602 tree type = TREE_TYPE (expr);
3603 location_t loc = EXPR_LOCATION (expr);
3604 tree tmp, arm1, arm2;
3605 enum gimplify_status ret;
3606 tree label_true, label_false, label_cont;
3607 bool have_then_clause_p, have_else_clause_p;
3608 gcond *cond_stmt;
3609 enum tree_code pred_code;
3610 gimple_seq seq = NULL;
3612 /* If this COND_EXPR has a value, copy the values into a temporary within
3613 the arms. */
3614 if (!VOID_TYPE_P (type))
3616 tree then_ = TREE_OPERAND (expr, 1), else_ = TREE_OPERAND (expr, 2);
3617 tree result;
3619 /* If either an rvalue is ok or we do not require an lvalue, create the
3620 temporary. But we cannot do that if the type is addressable. */
3621 if (((fallback & fb_rvalue) || !(fallback & fb_lvalue))
3622 && !TREE_ADDRESSABLE (type))
3624 if (gimplify_ctxp->allow_rhs_cond_expr
3625 /* If either branch has side effects or could trap, it can't be
3626 evaluated unconditionally. */
3627 && !TREE_SIDE_EFFECTS (then_)
3628 && !generic_expr_could_trap_p (then_)
3629 && !TREE_SIDE_EFFECTS (else_)
3630 && !generic_expr_could_trap_p (else_))
3631 return gimplify_pure_cond_expr (expr_p, pre_p);
3633 tmp = create_tmp_var (type, "iftmp");
3634 result = tmp;
3637 /* Otherwise, only create and copy references to the values. */
3638 else
3640 type = build_pointer_type (type);
3642 if (!VOID_TYPE_P (TREE_TYPE (then_)))
3643 then_ = build_fold_addr_expr_loc (loc, then_);
3645 if (!VOID_TYPE_P (TREE_TYPE (else_)))
3646 else_ = build_fold_addr_expr_loc (loc, else_);
3648 expr
3649 = build3 (COND_EXPR, type, TREE_OPERAND (expr, 0), then_, else_);
3651 tmp = create_tmp_var (type, "iftmp");
3652 result = build_simple_mem_ref_loc (loc, tmp);
3655 /* Build the new then clause, `tmp = then_;'. But don't build the
3656 assignment if the value is void; in C++ it can be if it's a throw. */
3657 if (!VOID_TYPE_P (TREE_TYPE (then_)))
3658 TREE_OPERAND (expr, 1) = build2 (MODIFY_EXPR, type, tmp, then_);
3660 /* Similarly, build the new else clause, `tmp = else_;'. */
3661 if (!VOID_TYPE_P (TREE_TYPE (else_)))
3662 TREE_OPERAND (expr, 2) = build2 (MODIFY_EXPR, type, tmp, else_);
3664 TREE_TYPE (expr) = void_type_node;
3665 recalculate_side_effects (expr);
3667 /* Move the COND_EXPR to the prequeue. */
3668 gimplify_stmt (&expr, pre_p);
3670 *expr_p = result;
3671 return GS_ALL_DONE;
3674 /* Remove any COMPOUND_EXPR so the following cases will be caught. */
3675 STRIP_TYPE_NOPS (TREE_OPERAND (expr, 0));
3676 if (TREE_CODE (TREE_OPERAND (expr, 0)) == COMPOUND_EXPR)
3677 gimplify_compound_expr (&TREE_OPERAND (expr, 0), pre_p, true);
3679 /* Make sure the condition has BOOLEAN_TYPE. */
3680 TREE_OPERAND (expr, 0) = gimple_boolify (TREE_OPERAND (expr, 0));
3682 /* Break apart && and || conditions. */
3683 if (TREE_CODE (TREE_OPERAND (expr, 0)) == TRUTH_ANDIF_EXPR
3684 || TREE_CODE (TREE_OPERAND (expr, 0)) == TRUTH_ORIF_EXPR)
3686 expr = shortcut_cond_expr (expr);
3688 if (expr != *expr_p)
3690 *expr_p = expr;
3692 /* We can't rely on gimplify_expr to re-gimplify the expanded
3693 form properly, as cleanups might cause the target labels to be
3694 wrapped in a TRY_FINALLY_EXPR. To prevent that, we need to
3695 set up a conditional context. */
3696 gimple_push_condition ();
3697 gimplify_stmt (expr_p, &seq);
3698 gimple_pop_condition (pre_p);
3699 gimple_seq_add_seq (pre_p, seq);
3701 return GS_ALL_DONE;
3705 /* Now do the normal gimplification. */
3707 /* Gimplify condition. */
3708 ret = gimplify_expr (&TREE_OPERAND (expr, 0), pre_p, NULL, is_gimple_condexpr,
3709 fb_rvalue);
3710 if (ret == GS_ERROR)
3711 return GS_ERROR;
3712 gcc_assert (TREE_OPERAND (expr, 0) != NULL_TREE);
3714 gimple_push_condition ();
3716 have_then_clause_p = have_else_clause_p = false;
3717 if (TREE_OPERAND (expr, 1) != NULL
3718 && TREE_CODE (TREE_OPERAND (expr, 1)) == GOTO_EXPR
3719 && TREE_CODE (GOTO_DESTINATION (TREE_OPERAND (expr, 1))) == LABEL_DECL
3720 && (DECL_CONTEXT (GOTO_DESTINATION (TREE_OPERAND (expr, 1)))
3721 == current_function_decl)
3722 /* For -O0 avoid this optimization if the COND_EXPR and GOTO_EXPR
3723 have different locations, otherwise we end up with incorrect
3724 location information on the branches. */
3725 && (optimize
3726 || !EXPR_HAS_LOCATION (expr)
3727 || !EXPR_HAS_LOCATION (TREE_OPERAND (expr, 1))
3728 || EXPR_LOCATION (expr) == EXPR_LOCATION (TREE_OPERAND (expr, 1))))
3730 label_true = GOTO_DESTINATION (TREE_OPERAND (expr, 1));
3731 have_then_clause_p = true;
3733 else
3734 label_true = create_artificial_label (UNKNOWN_LOCATION);
3735 if (TREE_OPERAND (expr, 2) != NULL
3736 && TREE_CODE (TREE_OPERAND (expr, 2)) == GOTO_EXPR
3737 && TREE_CODE (GOTO_DESTINATION (TREE_OPERAND (expr, 2))) == LABEL_DECL
3738 && (DECL_CONTEXT (GOTO_DESTINATION (TREE_OPERAND (expr, 2)))
3739 == current_function_decl)
3740 /* For -O0 avoid this optimization if the COND_EXPR and GOTO_EXPR
3741 have different locations, otherwise we end up with incorrect
3742 location information on the branches. */
3743 && (optimize
3744 || !EXPR_HAS_LOCATION (expr)
3745 || !EXPR_HAS_LOCATION (TREE_OPERAND (expr, 2))
3746 || EXPR_LOCATION (expr) == EXPR_LOCATION (TREE_OPERAND (expr, 2))))
3748 label_false = GOTO_DESTINATION (TREE_OPERAND (expr, 2));
3749 have_else_clause_p = true;
3751 else
3752 label_false = create_artificial_label (UNKNOWN_LOCATION);
3754 gimple_cond_get_ops_from_tree (COND_EXPR_COND (expr), &pred_code, &arm1,
3755 &arm2);
3756 cond_stmt = gimple_build_cond (pred_code, arm1, arm2, label_true,
3757 label_false);
3758 gimple_set_no_warning (cond_stmt, TREE_NO_WARNING (COND_EXPR_COND (expr)));
3759 gimplify_seq_add_stmt (&seq, cond_stmt);
3760 gimple_stmt_iterator gsi = gsi_last (seq);
3761 maybe_fold_stmt (&gsi);
3763 label_cont = NULL_TREE;
3764 if (!have_then_clause_p)
3766 /* For if (...) {} else { code; } put label_true after
3767 the else block. */
3768 if (TREE_OPERAND (expr, 1) == NULL_TREE
3769 && !have_else_clause_p
3770 && TREE_OPERAND (expr, 2) != NULL_TREE)
3771 label_cont = label_true;
3772 else
3774 gimplify_seq_add_stmt (&seq, gimple_build_label (label_true));
3775 have_then_clause_p = gimplify_stmt (&TREE_OPERAND (expr, 1), &seq);
3776 /* For if (...) { code; } else {} or
3777 if (...) { code; } else goto label; or
3778 if (...) { code; return; } else { ... }
3779 label_cont isn't needed. */
3780 if (!have_else_clause_p
3781 && TREE_OPERAND (expr, 2) != NULL_TREE
3782 && gimple_seq_may_fallthru (seq))
3784 gimple *g;
3785 label_cont = create_artificial_label (UNKNOWN_LOCATION);
3787 g = gimple_build_goto (label_cont);
3789 /* GIMPLE_COND's are very low level; they have embedded
3790 gotos. This particular embedded goto should not be marked
3791 with the location of the original COND_EXPR, as it would
3792 correspond to the COND_EXPR's condition, not the ELSE or the
3793 THEN arms. To avoid marking it with the wrong location, flag
3794 it as "no location". */
3795 gimple_set_do_not_emit_location (g);
3797 gimplify_seq_add_stmt (&seq, g);
3801 if (!have_else_clause_p)
3803 gimplify_seq_add_stmt (&seq, gimple_build_label (label_false));
3804 have_else_clause_p = gimplify_stmt (&TREE_OPERAND (expr, 2), &seq);
3806 if (label_cont)
3807 gimplify_seq_add_stmt (&seq, gimple_build_label (label_cont));
3809 gimple_pop_condition (pre_p);
3810 gimple_seq_add_seq (pre_p, seq);
3812 if (ret == GS_ERROR)
3813 ; /* Do nothing. */
3814 else if (have_then_clause_p || have_else_clause_p)
3815 ret = GS_ALL_DONE;
3816 else
3818 /* Both arms are empty; replace the COND_EXPR with its predicate. */
3819 expr = TREE_OPERAND (expr, 0);
3820 gimplify_stmt (&expr, pre_p);
3823 *expr_p = NULL;
3824 return ret;
3827 /* Prepare the node pointed to by EXPR_P, an is_gimple_addressable expression,
3828 to be marked addressable.
3830 We cannot rely on such an expression being directly markable if a temporary
3831 has been created by the gimplification. In this case, we create another
3832 temporary and initialize it with a copy, which will become a store after we
3833 mark it addressable. This can happen if the front-end passed us something
3834 that it could not mark addressable yet, like a Fortran pass-by-reference
3835 parameter (int) floatvar. */
3837 static void
3838 prepare_gimple_addressable (tree *expr_p, gimple_seq *seq_p)
3840 while (handled_component_p (*expr_p))
3841 expr_p = &TREE_OPERAND (*expr_p, 0);
3842 if (is_gimple_reg (*expr_p))
3844 /* Do not allow an SSA name as the temporary. */
3845 tree var = get_initialized_tmp_var (*expr_p, seq_p, NULL, false);
3846 DECL_GIMPLE_REG_P (var) = 0;
3847 *expr_p = var;
3851 /* A subroutine of gimplify_modify_expr. Replace a MODIFY_EXPR with
3852 a call to __builtin_memcpy. */
3854 static enum gimplify_status
3855 gimplify_modify_expr_to_memcpy (tree *expr_p, tree size, bool want_value,
3856 gimple_seq *seq_p)
3858 tree t, to, to_ptr, from, from_ptr;
3859 gcall *gs;
3860 location_t loc = EXPR_LOCATION (*expr_p);
3862 to = TREE_OPERAND (*expr_p, 0);
3863 from = TREE_OPERAND (*expr_p, 1);
3865 /* Mark the RHS addressable. Beware that it may not be possible to do so
3866 directly if a temporary has been created by the gimplification. */
3867 prepare_gimple_addressable (&from, seq_p);
3869 mark_addressable (from);
3870 from_ptr = build_fold_addr_expr_loc (loc, from);
3871 gimplify_arg (&from_ptr, seq_p, loc);
3873 mark_addressable (to);
3874 to_ptr = build_fold_addr_expr_loc (loc, to);
3875 gimplify_arg (&to_ptr, seq_p, loc);
3877 t = builtin_decl_implicit (BUILT_IN_MEMCPY);
3879 gs = gimple_build_call (t, 3, to_ptr, from_ptr, size);
3881 if (want_value)
3883 /* tmp = memcpy() */
3884 t = create_tmp_var (TREE_TYPE (to_ptr));
3885 gimple_call_set_lhs (gs, t);
3886 gimplify_seq_add_stmt (seq_p, gs);
3888 *expr_p = build_simple_mem_ref (t);
3889 return GS_ALL_DONE;
3892 gimplify_seq_add_stmt (seq_p, gs);
3893 *expr_p = NULL;
3894 return GS_ALL_DONE;
3897 /* A subroutine of gimplify_modify_expr. Replace a MODIFY_EXPR with
3898 a call to __builtin_memset. In this case we know that the RHS is
3899 a CONSTRUCTOR with an empty element list. */
3901 static enum gimplify_status
3902 gimplify_modify_expr_to_memset (tree *expr_p, tree size, bool want_value,
3903 gimple_seq *seq_p)
3905 tree t, from, to, to_ptr;
3906 gcall *gs;
3907 location_t loc = EXPR_LOCATION (*expr_p);
3909 /* Assert our assumptions, to abort instead of producing wrong code
3910 silently if they are not met. Beware that the RHS CONSTRUCTOR might
3911 not be immediately exposed. */
3912 from = TREE_OPERAND (*expr_p, 1);
3913 if (TREE_CODE (from) == WITH_SIZE_EXPR)
3914 from = TREE_OPERAND (from, 0);
3916 gcc_assert (TREE_CODE (from) == CONSTRUCTOR
3917 && vec_safe_is_empty (CONSTRUCTOR_ELTS (from)));
3919 /* Now proceed. */
3920 to = TREE_OPERAND (*expr_p, 0);
3922 to_ptr = build_fold_addr_expr_loc (loc, to);
3923 gimplify_arg (&to_ptr, seq_p, loc);
3924 t = builtin_decl_implicit (BUILT_IN_MEMSET);
3926 gs = gimple_build_call (t, 3, to_ptr, integer_zero_node, size);
3928 if (want_value)
3930 /* tmp = memset() */
3931 t = create_tmp_var (TREE_TYPE (to_ptr));
3932 gimple_call_set_lhs (gs, t);
3933 gimplify_seq_add_stmt (seq_p, gs);
3935 *expr_p = build1 (INDIRECT_REF, TREE_TYPE (to), t);
3936 return GS_ALL_DONE;
3939 gimplify_seq_add_stmt (seq_p, gs);
3940 *expr_p = NULL;
3941 return GS_ALL_DONE;
3944 /* A subroutine of gimplify_init_ctor_preeval. Called via walk_tree,
3945 determine, cautiously, if a CONSTRUCTOR overlaps the lhs of an
3946 assignment. Return non-null if we detect a potential overlap. */
3948 struct gimplify_init_ctor_preeval_data
3950 /* The base decl of the lhs object. May be NULL, in which case we
3951 have to assume the lhs is indirect. */
3952 tree lhs_base_decl;
3954 /* The alias set of the lhs object. */
3955 alias_set_type lhs_alias_set;
3958 static tree
3959 gimplify_init_ctor_preeval_1 (tree *tp, int *walk_subtrees, void *xdata)
3961 struct gimplify_init_ctor_preeval_data *data
3962 = (struct gimplify_init_ctor_preeval_data *) xdata;
3963 tree t = *tp;
3965 /* If we find the base object, obviously we have overlap. */
3966 if (data->lhs_base_decl == t)
3967 return t;
3969 /* If the constructor component is indirect, determine if we have a
3970 potential overlap with the lhs. The only bits of information we
3971 have to go on at this point are addressability and alias sets. */
3972 if ((INDIRECT_REF_P (t)
3973 || TREE_CODE (t) == MEM_REF)
3974 && (!data->lhs_base_decl || TREE_ADDRESSABLE (data->lhs_base_decl))
3975 && alias_sets_conflict_p (data->lhs_alias_set, get_alias_set (t)))
3976 return t;
3978 /* If the constructor component is a call, determine if it can hide a
3979 potential overlap with the lhs through an INDIRECT_REF like above.
3980 ??? Ugh - this is completely broken. In fact this whole analysis
3981 doesn't look conservative. */
3982 if (TREE_CODE (t) == CALL_EXPR)
3984 tree type, fntype = TREE_TYPE (TREE_TYPE (CALL_EXPR_FN (t)));
3986 for (type = TYPE_ARG_TYPES (fntype); type; type = TREE_CHAIN (type))
3987 if (POINTER_TYPE_P (TREE_VALUE (type))
3988 && (!data->lhs_base_decl || TREE_ADDRESSABLE (data->lhs_base_decl))
3989 && alias_sets_conflict_p (data->lhs_alias_set,
3990 get_alias_set
3991 (TREE_TYPE (TREE_VALUE (type)))))
3992 return t;
3995 if (IS_TYPE_OR_DECL_P (t))
3996 *walk_subtrees = 0;
3997 return NULL;
4000 /* A subroutine of gimplify_init_constructor. Pre-evaluate EXPR,
4001 force values that overlap with the lhs (as described by *DATA)
4002 into temporaries. */
4004 static void
4005 gimplify_init_ctor_preeval (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
4006 struct gimplify_init_ctor_preeval_data *data)
4008 enum gimplify_status one;
4010 /* If the value is constant, then there's nothing to pre-evaluate. */
4011 if (TREE_CONSTANT (*expr_p))
4013 /* Ensure it does not have side effects, it might contain a reference to
4014 the object we're initializing. */
4015 gcc_assert (!TREE_SIDE_EFFECTS (*expr_p));
4016 return;
4019 /* If the type has non-trivial constructors, we can't pre-evaluate. */
4020 if (TREE_ADDRESSABLE (TREE_TYPE (*expr_p)))
4021 return;
4023 /* Recurse for nested constructors. */
4024 if (TREE_CODE (*expr_p) == CONSTRUCTOR)
4026 unsigned HOST_WIDE_INT ix;
4027 constructor_elt *ce;
4028 vec<constructor_elt, va_gc> *v = CONSTRUCTOR_ELTS (*expr_p);
4030 FOR_EACH_VEC_SAFE_ELT (v, ix, ce)
4031 gimplify_init_ctor_preeval (&ce->value, pre_p, post_p, data);
4033 return;
4036 /* If this is a variable sized type, we must remember the size. */
4037 maybe_with_size_expr (expr_p);
4039 /* Gimplify the constructor element to something appropriate for the rhs
4040 of a MODIFY_EXPR. Given that we know the LHS is an aggregate, we know
4041 the gimplifier will consider this a store to memory. Doing this
4042 gimplification now means that we won't have to deal with complicated
4043 language-specific trees, nor trees like SAVE_EXPR that can induce
4044 exponential search behavior. */
4045 one = gimplify_expr (expr_p, pre_p, post_p, is_gimple_mem_rhs, fb_rvalue);
4046 if (one == GS_ERROR)
4048 *expr_p = NULL;
4049 return;
4052 /* If we gimplified to a bare decl, we can be sure that it doesn't overlap
4053 with the lhs, since "a = { .x=a }" doesn't make sense. This will
4054 always be true for all scalars, since is_gimple_mem_rhs insists on a
4055 temporary variable for them. */
4056 if (DECL_P (*expr_p))
4057 return;
4059 /* If this is of variable size, we have no choice but to assume it doesn't
4060 overlap since we can't make a temporary for it. */
4061 if (TREE_CODE (TYPE_SIZE (TREE_TYPE (*expr_p))) != INTEGER_CST)
4062 return;
4064 /* Otherwise, we must search for overlap ... */
4065 if (!walk_tree (expr_p, gimplify_init_ctor_preeval_1, data, NULL))
4066 return;
4068 /* ... and if found, force the value into a temporary. */
4069 *expr_p = get_formal_tmp_var (*expr_p, pre_p);
4072 /* A subroutine of gimplify_init_ctor_eval. Create a loop for
4073 a RANGE_EXPR in a CONSTRUCTOR for an array.
4075 var = lower;
4076 loop_entry:
4077 object[var] = value;
4078 if (var == upper)
4079 goto loop_exit;
4080 var = var + 1;
4081 goto loop_entry;
4082 loop_exit:
4084 We increment var _after_ the loop exit check because we might otherwise
4085 fail if upper == TYPE_MAX_VALUE (type for upper).
4087 Note that we never have to deal with SAVE_EXPRs here, because this has
4088 already been taken care of for us, in gimplify_init_ctor_preeval(). */
4090 static void gimplify_init_ctor_eval (tree, vec<constructor_elt, va_gc> *,
4091 gimple_seq *, bool);
4093 static void
4094 gimplify_init_ctor_eval_range (tree object, tree lower, tree upper,
4095 tree value, tree array_elt_type,
4096 gimple_seq *pre_p, bool cleared)
4098 tree loop_entry_label, loop_exit_label, fall_thru_label;
4099 tree var, var_type, cref, tmp;
4101 loop_entry_label = create_artificial_label (UNKNOWN_LOCATION);
4102 loop_exit_label = create_artificial_label (UNKNOWN_LOCATION);
4103 fall_thru_label = create_artificial_label (UNKNOWN_LOCATION);
4105 /* Create and initialize the index variable. */
4106 var_type = TREE_TYPE (upper);
4107 var = create_tmp_var (var_type);
4108 gimplify_seq_add_stmt (pre_p, gimple_build_assign (var, lower));
4110 /* Add the loop entry label. */
4111 gimplify_seq_add_stmt (pre_p, gimple_build_label (loop_entry_label));
4113 /* Build the reference. */
4114 cref = build4 (ARRAY_REF, array_elt_type, unshare_expr (object),
4115 var, NULL_TREE, NULL_TREE);
4117 /* If we are a constructor, just call gimplify_init_ctor_eval to do
4118 the store. Otherwise just assign value to the reference. */
4120 if (TREE_CODE (value) == CONSTRUCTOR)
4121 /* NB we might have to call ourself recursively through
4122 gimplify_init_ctor_eval if the value is a constructor. */
4123 gimplify_init_ctor_eval (cref, CONSTRUCTOR_ELTS (value),
4124 pre_p, cleared);
4125 else
4126 gimplify_seq_add_stmt (pre_p, gimple_build_assign (cref, value));
4128 /* We exit the loop when the index var is equal to the upper bound. */
4129 gimplify_seq_add_stmt (pre_p,
4130 gimple_build_cond (EQ_EXPR, var, upper,
4131 loop_exit_label, fall_thru_label));
4133 gimplify_seq_add_stmt (pre_p, gimple_build_label (fall_thru_label));
4135 /* Otherwise, increment the index var... */
4136 tmp = build2 (PLUS_EXPR, var_type, var,
4137 fold_convert (var_type, integer_one_node));
4138 gimplify_seq_add_stmt (pre_p, gimple_build_assign (var, tmp));
4140 /* ...and jump back to the loop entry. */
4141 gimplify_seq_add_stmt (pre_p, gimple_build_goto (loop_entry_label));
4143 /* Add the loop exit label. */
4144 gimplify_seq_add_stmt (pre_p, gimple_build_label (loop_exit_label));
4147 /* Return true if FDECL is accessing a field that is zero sized. */
4149 static bool
4150 zero_sized_field_decl (const_tree fdecl)
4152 if (TREE_CODE (fdecl) == FIELD_DECL && DECL_SIZE (fdecl)
4153 && integer_zerop (DECL_SIZE (fdecl)))
4154 return true;
4155 return false;
4158 /* Return true if TYPE is zero sized. */
4160 static bool
4161 zero_sized_type (const_tree type)
4163 if (AGGREGATE_TYPE_P (type) && TYPE_SIZE (type)
4164 && integer_zerop (TYPE_SIZE (type)))
4165 return true;
4166 return false;
4169 /* A subroutine of gimplify_init_constructor. Generate individual
4170 MODIFY_EXPRs for a CONSTRUCTOR. OBJECT is the LHS against which the
4171 assignments should happen. ELTS is the CONSTRUCTOR_ELTS of the
4172 CONSTRUCTOR. CLEARED is true if the entire LHS object has been
4173 zeroed first. */
4175 static void
4176 gimplify_init_ctor_eval (tree object, vec<constructor_elt, va_gc> *elts,
4177 gimple_seq *pre_p, bool cleared)
4179 tree array_elt_type = NULL;
4180 unsigned HOST_WIDE_INT ix;
4181 tree purpose, value;
4183 if (TREE_CODE (TREE_TYPE (object)) == ARRAY_TYPE)
4184 array_elt_type = TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (object)));
4186 FOR_EACH_CONSTRUCTOR_ELT (elts, ix, purpose, value)
4188 tree cref;
4190 /* NULL values are created above for gimplification errors. */
4191 if (value == NULL)
4192 continue;
4194 if (cleared && initializer_zerop (value))
4195 continue;
4197 /* ??? Here's to hoping the front end fills in all of the indices,
4198 so we don't have to figure out what's missing ourselves. */
4199 gcc_assert (purpose);
4201 /* Skip zero-sized fields, unless value has side-effects. This can
4202 happen with calls to functions returning a zero-sized type, which
4203 we shouldn't discard. As a number of downstream passes don't
4204 expect sets of zero-sized fields, we rely on the gimplification of
4205 the MODIFY_EXPR we make below to drop the assignment statement. */
4206 if (! TREE_SIDE_EFFECTS (value) && zero_sized_field_decl (purpose))
4207 continue;
4209 /* If we have a RANGE_EXPR, we have to build a loop to assign the
4210 whole range. */
4211 if (TREE_CODE (purpose) == RANGE_EXPR)
4213 tree lower = TREE_OPERAND (purpose, 0);
4214 tree upper = TREE_OPERAND (purpose, 1);
4216 /* If the lower bound is equal to upper, just treat it as if
4217 upper was the index. */
4218 if (simple_cst_equal (lower, upper))
4219 purpose = upper;
4220 else
4222 gimplify_init_ctor_eval_range (object, lower, upper, value,
4223 array_elt_type, pre_p, cleared);
4224 continue;
4228 if (array_elt_type)
4230 /* Do not use bitsizetype for ARRAY_REF indices. */
4231 if (TYPE_DOMAIN (TREE_TYPE (object)))
4232 purpose
4233 = fold_convert (TREE_TYPE (TYPE_DOMAIN (TREE_TYPE (object))),
4234 purpose);
4235 cref = build4 (ARRAY_REF, array_elt_type, unshare_expr (object),
4236 purpose, NULL_TREE, NULL_TREE);
4238 else
4240 gcc_assert (TREE_CODE (purpose) == FIELD_DECL);
4241 cref = build3 (COMPONENT_REF, TREE_TYPE (purpose),
4242 unshare_expr (object), purpose, NULL_TREE);
4245 if (TREE_CODE (value) == CONSTRUCTOR
4246 && TREE_CODE (TREE_TYPE (value)) != VECTOR_TYPE)
4247 gimplify_init_ctor_eval (cref, CONSTRUCTOR_ELTS (value),
4248 pre_p, cleared);
4249 else
4251 tree init = build2 (INIT_EXPR, TREE_TYPE (cref), cref, value);
4252 gimplify_and_add (init, pre_p);
4253 ggc_free (init);
4258 /* Return the appropriate RHS predicate for this LHS. */
4260 gimple_predicate
4261 rhs_predicate_for (tree lhs)
4263 if (is_gimple_reg (lhs))
4264 return is_gimple_reg_rhs_or_call;
4265 else
4266 return is_gimple_mem_rhs_or_call;
4269 /* Return the initial guess for an appropriate RHS predicate for this LHS,
4270 before the LHS has been gimplified. */
4272 static gimple_predicate
4273 initial_rhs_predicate_for (tree lhs)
4275 if (is_gimple_reg_type (TREE_TYPE (lhs)))
4276 return is_gimple_reg_rhs_or_call;
4277 else
4278 return is_gimple_mem_rhs_or_call;
4281 /* Gimplify a C99 compound literal expression. This just means adding
4282 the DECL_EXPR before the current statement and using its anonymous
4283 decl instead. */
4285 static enum gimplify_status
4286 gimplify_compound_literal_expr (tree *expr_p, gimple_seq *pre_p,
4287 bool (*gimple_test_f) (tree),
4288 fallback_t fallback)
4290 tree decl_s = COMPOUND_LITERAL_EXPR_DECL_EXPR (*expr_p);
4291 tree decl = DECL_EXPR_DECL (decl_s);
4292 tree init = DECL_INITIAL (decl);
4293 /* Mark the decl as addressable if the compound literal
4294 expression is addressable now, otherwise it is marked too late
4295 after we gimplify the initialization expression. */
4296 if (TREE_ADDRESSABLE (*expr_p))
4297 TREE_ADDRESSABLE (decl) = 1;
4298 /* Otherwise, if we don't need an lvalue and have a literal directly
4299 substitute it. Check if it matches the gimple predicate, as
4300 otherwise we'd generate a new temporary, and we can as well just
4301 use the decl we already have. */
4302 else if (!TREE_ADDRESSABLE (decl)
4303 && init
4304 && (fallback & fb_lvalue) == 0
4305 && gimple_test_f (init))
4307 *expr_p = init;
4308 return GS_OK;
4311 /* Preliminarily mark non-addressed complex variables as eligible
4312 for promotion to gimple registers. We'll transform their uses
4313 as we find them. */
4314 if ((TREE_CODE (TREE_TYPE (decl)) == COMPLEX_TYPE
4315 || TREE_CODE (TREE_TYPE (decl)) == VECTOR_TYPE)
4316 && !TREE_THIS_VOLATILE (decl)
4317 && !needs_to_live_in_memory (decl))
4318 DECL_GIMPLE_REG_P (decl) = 1;
4320 /* If the decl is not addressable, then it is being used in some
4321 expression or on the right hand side of a statement, and it can
4322 be put into a readonly data section. */
4323 if (!TREE_ADDRESSABLE (decl) && (fallback & fb_lvalue) == 0)
4324 TREE_READONLY (decl) = 1;
4326 /* This decl isn't mentioned in the enclosing block, so add it to the
4327 list of temps. FIXME it seems a bit of a kludge to say that
4328 anonymous artificial vars aren't pushed, but everything else is. */
4329 if (DECL_NAME (decl) == NULL_TREE && !DECL_SEEN_IN_BIND_EXPR_P (decl))
4330 gimple_add_tmp_var (decl);
4332 gimplify_and_add (decl_s, pre_p);
4333 *expr_p = decl;
4334 return GS_OK;
4337 /* Optimize embedded COMPOUND_LITERAL_EXPRs within a CONSTRUCTOR,
4338 return a new CONSTRUCTOR if something changed. */
4340 static tree
4341 optimize_compound_literals_in_ctor (tree orig_ctor)
4343 tree ctor = orig_ctor;
4344 vec<constructor_elt, va_gc> *elts = CONSTRUCTOR_ELTS (ctor);
4345 unsigned int idx, num = vec_safe_length (elts);
4347 for (idx = 0; idx < num; idx++)
4349 tree value = (*elts)[idx].value;
4350 tree newval = value;
4351 if (TREE_CODE (value) == CONSTRUCTOR)
4352 newval = optimize_compound_literals_in_ctor (value);
4353 else if (TREE_CODE (value) == COMPOUND_LITERAL_EXPR)
4355 tree decl_s = COMPOUND_LITERAL_EXPR_DECL_EXPR (value);
4356 tree decl = DECL_EXPR_DECL (decl_s);
4357 tree init = DECL_INITIAL (decl);
4359 if (!TREE_ADDRESSABLE (value)
4360 && !TREE_ADDRESSABLE (decl)
4361 && init
4362 && TREE_CODE (init) == CONSTRUCTOR)
4363 newval = optimize_compound_literals_in_ctor (init);
4365 if (newval == value)
4366 continue;
4368 if (ctor == orig_ctor)
4370 ctor = copy_node (orig_ctor);
4371 CONSTRUCTOR_ELTS (ctor) = vec_safe_copy (elts);
4372 elts = CONSTRUCTOR_ELTS (ctor);
4374 (*elts)[idx].value = newval;
4376 return ctor;
4379 /* A subroutine of gimplify_modify_expr. Break out elements of a
4380 CONSTRUCTOR used as an initializer into separate MODIFY_EXPRs.
4382 Note that we still need to clear any elements that don't have explicit
4383 initializers, so if not all elements are initialized we keep the
4384 original MODIFY_EXPR, we just remove all of the constructor elements.
4386 If NOTIFY_TEMP_CREATION is true, do not gimplify, just return
4387 GS_ERROR if we would have to create a temporary when gimplifying
4388 this constructor. Otherwise, return GS_OK.
4390 If NOTIFY_TEMP_CREATION is false, just do the gimplification. */
4392 static enum gimplify_status
4393 gimplify_init_constructor (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
4394 bool want_value, bool notify_temp_creation)
4396 tree object, ctor, type;
4397 enum gimplify_status ret;
4398 vec<constructor_elt, va_gc> *elts;
4400 gcc_assert (TREE_CODE (TREE_OPERAND (*expr_p, 1)) == CONSTRUCTOR);
4402 if (!notify_temp_creation)
4404 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
4405 is_gimple_lvalue, fb_lvalue);
4406 if (ret == GS_ERROR)
4407 return ret;
4410 object = TREE_OPERAND (*expr_p, 0);
4411 ctor = TREE_OPERAND (*expr_p, 1) =
4412 optimize_compound_literals_in_ctor (TREE_OPERAND (*expr_p, 1));
4413 type = TREE_TYPE (ctor);
4414 elts = CONSTRUCTOR_ELTS (ctor);
4415 ret = GS_ALL_DONE;
4417 switch (TREE_CODE (type))
4419 case RECORD_TYPE:
4420 case UNION_TYPE:
4421 case QUAL_UNION_TYPE:
4422 case ARRAY_TYPE:
4424 struct gimplify_init_ctor_preeval_data preeval_data;
4425 HOST_WIDE_INT num_ctor_elements, num_nonzero_elements;
4426 bool cleared, complete_p, valid_const_initializer;
4428 /* Aggregate types must lower constructors to initialization of
4429 individual elements. The exception is that a CONSTRUCTOR node
4430 with no elements indicates zero-initialization of the whole. */
4431 if (vec_safe_is_empty (elts))
4433 if (notify_temp_creation)
4434 return GS_OK;
4435 break;
4438 /* Fetch information about the constructor to direct later processing.
4439 We might want to make static versions of it in various cases, and
4440 can only do so if it known to be a valid constant initializer. */
4441 valid_const_initializer
4442 = categorize_ctor_elements (ctor, &num_nonzero_elements,
4443 &num_ctor_elements, &complete_p);
4445 /* If a const aggregate variable is being initialized, then it
4446 should never be a lose to promote the variable to be static. */
4447 if (valid_const_initializer
4448 && num_nonzero_elements > 1
4449 && TREE_READONLY (object)
4450 && VAR_P (object)
4451 && (flag_merge_constants >= 2 || !TREE_ADDRESSABLE (object)))
4453 if (notify_temp_creation)
4454 return GS_ERROR;
4455 DECL_INITIAL (object) = ctor;
4456 TREE_STATIC (object) = 1;
4457 if (!DECL_NAME (object))
4458 DECL_NAME (object) = create_tmp_var_name ("C");
4459 walk_tree (&DECL_INITIAL (object), force_labels_r, NULL, NULL);
4461 /* ??? C++ doesn't automatically append a .<number> to the
4462 assembler name, and even when it does, it looks at FE private
4463 data structures to figure out what that number should be,
4464 which are not set for this variable. I suppose this is
4465 important for local statics for inline functions, which aren't
4466 "local" in the object file sense. So in order to get a unique
4467 TU-local symbol, we must invoke the lhd version now. */
4468 lhd_set_decl_assembler_name (object);
4470 *expr_p = NULL_TREE;
4471 break;
4474 /* If there are "lots" of initialized elements, even discounting
4475 those that are not address constants (and thus *must* be
4476 computed at runtime), then partition the constructor into
4477 constant and non-constant parts. Block copy the constant
4478 parts in, then generate code for the non-constant parts. */
4479 /* TODO. There's code in cp/typeck.c to do this. */
4481 if (int_size_in_bytes (TREE_TYPE (ctor)) < 0)
4482 /* store_constructor will ignore the clearing of variable-sized
4483 objects. Initializers for such objects must explicitly set
4484 every field that needs to be set. */
4485 cleared = false;
4486 else if (!complete_p && !CONSTRUCTOR_NO_CLEARING (ctor))
4487 /* If the constructor isn't complete, clear the whole object
4488 beforehand, unless CONSTRUCTOR_NO_CLEARING is set on it.
4490 ??? This ought not to be needed. For any element not present
4491 in the initializer, we should simply set them to zero. Except
4492 we'd need to *find* the elements that are not present, and that
4493 requires trickery to avoid quadratic compile-time behavior in
4494 large cases or excessive memory use in small cases. */
4495 cleared = true;
4496 else if (num_ctor_elements - num_nonzero_elements
4497 > CLEAR_RATIO (optimize_function_for_speed_p (cfun))
4498 && num_nonzero_elements < num_ctor_elements / 4)
4499 /* If there are "lots" of zeros, it's more efficient to clear
4500 the memory and then set the nonzero elements. */
4501 cleared = true;
4502 else
4503 cleared = false;
4505 /* If there are "lots" of initialized elements, and all of them
4506 are valid address constants, then the entire initializer can
4507 be dropped to memory, and then memcpy'd out. Don't do this
4508 for sparse arrays, though, as it's more efficient to follow
4509 the standard CONSTRUCTOR behavior of memset followed by
4510 individual element initialization. Also don't do this for small
4511 all-zero initializers (which aren't big enough to merit
4512 clearing), and don't try to make bitwise copies of
4513 TREE_ADDRESSABLE types.
4515 We cannot apply such transformation when compiling chkp static
4516 initializer because creation of initializer image in the memory
4517 will require static initialization of bounds for it. It should
4518 result in another gimplification of similar initializer and we
4519 may fall into infinite loop. */
4520 if (valid_const_initializer
4521 && !(cleared || num_nonzero_elements == 0)
4522 && !TREE_ADDRESSABLE (type)
4523 && (!current_function_decl
4524 || !lookup_attribute ("chkp ctor",
4525 DECL_ATTRIBUTES (current_function_decl))))
4527 HOST_WIDE_INT size = int_size_in_bytes (type);
4528 unsigned int align;
4530 /* ??? We can still get unbounded array types, at least
4531 from the C++ front end. This seems wrong, but attempt
4532 to work around it for now. */
4533 if (size < 0)
4535 size = int_size_in_bytes (TREE_TYPE (object));
4536 if (size >= 0)
4537 TREE_TYPE (ctor) = type = TREE_TYPE (object);
4540 /* Find the maximum alignment we can assume for the object. */
4541 /* ??? Make use of DECL_OFFSET_ALIGN. */
4542 if (DECL_P (object))
4543 align = DECL_ALIGN (object);
4544 else
4545 align = TYPE_ALIGN (type);
4547 /* Do a block move either if the size is so small as to make
4548 each individual move a sub-unit move on average, or if it
4549 is so large as to make individual moves inefficient. */
4550 if (size > 0
4551 && num_nonzero_elements > 1
4552 && (size < num_nonzero_elements
4553 || !can_move_by_pieces (size, align)))
4555 if (notify_temp_creation)
4556 return GS_ERROR;
4558 walk_tree (&ctor, force_labels_r, NULL, NULL);
4559 ctor = tree_output_constant_def (ctor);
4560 if (!useless_type_conversion_p (type, TREE_TYPE (ctor)))
4561 ctor = build1 (VIEW_CONVERT_EXPR, type, ctor);
4562 TREE_OPERAND (*expr_p, 1) = ctor;
4564 /* This is no longer an assignment of a CONSTRUCTOR, but
4565 we still may have processing to do on the LHS. So
4566 pretend we didn't do anything here to let that happen. */
4567 return GS_UNHANDLED;
4571 /* If the target is volatile, we have non-zero elements and more than
4572 one field to assign, initialize the target from a temporary. */
4573 if (TREE_THIS_VOLATILE (object)
4574 && !TREE_ADDRESSABLE (type)
4575 && num_nonzero_elements > 0
4576 && vec_safe_length (elts) > 1)
4578 tree temp = create_tmp_var (TYPE_MAIN_VARIANT (type));
4579 TREE_OPERAND (*expr_p, 0) = temp;
4580 *expr_p = build2 (COMPOUND_EXPR, TREE_TYPE (*expr_p),
4581 *expr_p,
4582 build2 (MODIFY_EXPR, void_type_node,
4583 object, temp));
4584 return GS_OK;
4587 if (notify_temp_creation)
4588 return GS_OK;
4590 /* If there are nonzero elements and if needed, pre-evaluate to capture
4591 elements overlapping with the lhs into temporaries. We must do this
4592 before clearing to fetch the values before they are zeroed-out. */
4593 if (num_nonzero_elements > 0 && TREE_CODE (*expr_p) != INIT_EXPR)
4595 preeval_data.lhs_base_decl = get_base_address (object);
4596 if (!DECL_P (preeval_data.lhs_base_decl))
4597 preeval_data.lhs_base_decl = NULL;
4598 preeval_data.lhs_alias_set = get_alias_set (object);
4600 gimplify_init_ctor_preeval (&TREE_OPERAND (*expr_p, 1),
4601 pre_p, post_p, &preeval_data);
4604 bool ctor_has_side_effects_p
4605 = TREE_SIDE_EFFECTS (TREE_OPERAND (*expr_p, 1));
4607 if (cleared)
4609 /* Zap the CONSTRUCTOR element list, which simplifies this case.
4610 Note that we still have to gimplify, in order to handle the
4611 case of variable sized types. Avoid shared tree structures. */
4612 CONSTRUCTOR_ELTS (ctor) = NULL;
4613 TREE_SIDE_EFFECTS (ctor) = 0;
4614 object = unshare_expr (object);
4615 gimplify_stmt (expr_p, pre_p);
4618 /* If we have not block cleared the object, or if there are nonzero
4619 elements in the constructor, or if the constructor has side effects,
4620 add assignments to the individual scalar fields of the object. */
4621 if (!cleared
4622 || num_nonzero_elements > 0
4623 || ctor_has_side_effects_p)
4624 gimplify_init_ctor_eval (object, elts, pre_p, cleared);
4626 *expr_p = NULL_TREE;
4628 break;
4630 case COMPLEX_TYPE:
4632 tree r, i;
4634 if (notify_temp_creation)
4635 return GS_OK;
4637 /* Extract the real and imaginary parts out of the ctor. */
4638 gcc_assert (elts->length () == 2);
4639 r = (*elts)[0].value;
4640 i = (*elts)[1].value;
4641 if (r == NULL || i == NULL)
4643 tree zero = build_zero_cst (TREE_TYPE (type));
4644 if (r == NULL)
4645 r = zero;
4646 if (i == NULL)
4647 i = zero;
4650 /* Complex types have either COMPLEX_CST or COMPLEX_EXPR to
4651 represent creation of a complex value. */
4652 if (TREE_CONSTANT (r) && TREE_CONSTANT (i))
4654 ctor = build_complex (type, r, i);
4655 TREE_OPERAND (*expr_p, 1) = ctor;
4657 else
4659 ctor = build2 (COMPLEX_EXPR, type, r, i);
4660 TREE_OPERAND (*expr_p, 1) = ctor;
4661 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 1),
4662 pre_p,
4663 post_p,
4664 rhs_predicate_for (TREE_OPERAND (*expr_p, 0)),
4665 fb_rvalue);
4668 break;
4670 case VECTOR_TYPE:
4672 unsigned HOST_WIDE_INT ix;
4673 constructor_elt *ce;
4675 if (notify_temp_creation)
4676 return GS_OK;
4678 /* Go ahead and simplify constant constructors to VECTOR_CST. */
4679 if (TREE_CONSTANT (ctor))
4681 bool constant_p = true;
4682 tree value;
4684 /* Even when ctor is constant, it might contain non-*_CST
4685 elements, such as addresses or trapping values like
4686 1.0/0.0 - 1.0/0.0. Such expressions don't belong
4687 in VECTOR_CST nodes. */
4688 FOR_EACH_CONSTRUCTOR_VALUE (elts, ix, value)
4689 if (!CONSTANT_CLASS_P (value))
4691 constant_p = false;
4692 break;
4695 if (constant_p)
4697 TREE_OPERAND (*expr_p, 1) = build_vector_from_ctor (type, elts);
4698 break;
4701 TREE_CONSTANT (ctor) = 0;
4704 /* Vector types use CONSTRUCTOR all the way through gimple
4705 compilation as a general initializer. */
4706 FOR_EACH_VEC_SAFE_ELT (elts, ix, ce)
4708 enum gimplify_status tret;
4709 tret = gimplify_expr (&ce->value, pre_p, post_p, is_gimple_val,
4710 fb_rvalue);
4711 if (tret == GS_ERROR)
4712 ret = GS_ERROR;
4713 else if (TREE_STATIC (ctor)
4714 && !initializer_constant_valid_p (ce->value,
4715 TREE_TYPE (ce->value)))
4716 TREE_STATIC (ctor) = 0;
4718 if (!is_gimple_reg (TREE_OPERAND (*expr_p, 0)))
4719 TREE_OPERAND (*expr_p, 1) = get_formal_tmp_var (ctor, pre_p);
4721 break;
4723 default:
4724 /* So how did we get a CONSTRUCTOR for a scalar type? */
4725 gcc_unreachable ();
4728 if (ret == GS_ERROR)
4729 return GS_ERROR;
4730 else if (want_value)
4732 *expr_p = object;
4733 return GS_OK;
4735 else
4737 /* If we have gimplified both sides of the initializer but have
4738 not emitted an assignment, do so now. */
4739 if (*expr_p)
4741 tree lhs = TREE_OPERAND (*expr_p, 0);
4742 tree rhs = TREE_OPERAND (*expr_p, 1);
4743 gassign *init = gimple_build_assign (lhs, rhs);
4744 gimplify_seq_add_stmt (pre_p, init);
4745 *expr_p = NULL;
4748 return GS_ALL_DONE;
4752 /* Given a pointer value OP0, return a simplified version of an
4753 indirection through OP0, or NULL_TREE if no simplification is
4754 possible. This may only be applied to a rhs of an expression.
4755 Note that the resulting type may be different from the type pointed
4756 to in the sense that it is still compatible from the langhooks
4757 point of view. */
4759 static tree
4760 gimple_fold_indirect_ref_rhs (tree t)
4762 return gimple_fold_indirect_ref (t);
4765 /* Subroutine of gimplify_modify_expr to do simplifications of
4766 MODIFY_EXPRs based on the code of the RHS. We loop for as long as
4767 something changes. */
4769 static enum gimplify_status
4770 gimplify_modify_expr_rhs (tree *expr_p, tree *from_p, tree *to_p,
4771 gimple_seq *pre_p, gimple_seq *post_p,
4772 bool want_value)
4774 enum gimplify_status ret = GS_UNHANDLED;
4775 bool changed;
4779 changed = false;
4780 switch (TREE_CODE (*from_p))
4782 case VAR_DECL:
4783 /* If we're assigning from a read-only variable initialized with
4784 a constructor, do the direct assignment from the constructor,
4785 but only if neither source nor target are volatile since this
4786 latter assignment might end up being done on a per-field basis. */
4787 if (DECL_INITIAL (*from_p)
4788 && TREE_READONLY (*from_p)
4789 && !TREE_THIS_VOLATILE (*from_p)
4790 && !TREE_THIS_VOLATILE (*to_p)
4791 && TREE_CODE (DECL_INITIAL (*from_p)) == CONSTRUCTOR)
4793 tree old_from = *from_p;
4794 enum gimplify_status subret;
4796 /* Move the constructor into the RHS. */
4797 *from_p = unshare_expr (DECL_INITIAL (*from_p));
4799 /* Let's see if gimplify_init_constructor will need to put
4800 it in memory. */
4801 subret = gimplify_init_constructor (expr_p, NULL, NULL,
4802 false, true);
4803 if (subret == GS_ERROR)
4805 /* If so, revert the change. */
4806 *from_p = old_from;
4808 else
4810 ret = GS_OK;
4811 changed = true;
4814 break;
4815 case INDIRECT_REF:
4817 /* If we have code like
4819 *(const A*)(A*)&x
4821 where the type of "x" is a (possibly cv-qualified variant
4822 of "A"), treat the entire expression as identical to "x".
4823 This kind of code arises in C++ when an object is bound
4824 to a const reference, and if "x" is a TARGET_EXPR we want
4825 to take advantage of the optimization below. */
4826 bool volatile_p = TREE_THIS_VOLATILE (*from_p);
4827 tree t = gimple_fold_indirect_ref_rhs (TREE_OPERAND (*from_p, 0));
4828 if (t)
4830 if (TREE_THIS_VOLATILE (t) != volatile_p)
4832 if (DECL_P (t))
4833 t = build_simple_mem_ref_loc (EXPR_LOCATION (*from_p),
4834 build_fold_addr_expr (t));
4835 if (REFERENCE_CLASS_P (t))
4836 TREE_THIS_VOLATILE (t) = volatile_p;
4838 *from_p = t;
4839 ret = GS_OK;
4840 changed = true;
4842 break;
4845 case TARGET_EXPR:
4847 /* If we are initializing something from a TARGET_EXPR, strip the
4848 TARGET_EXPR and initialize it directly, if possible. This can't
4849 be done if the initializer is void, since that implies that the
4850 temporary is set in some non-trivial way.
4852 ??? What about code that pulls out the temp and uses it
4853 elsewhere? I think that such code never uses the TARGET_EXPR as
4854 an initializer. If I'm wrong, we'll die because the temp won't
4855 have any RTL. In that case, I guess we'll need to replace
4856 references somehow. */
4857 tree init = TARGET_EXPR_INITIAL (*from_p);
4859 if (init
4860 && !VOID_TYPE_P (TREE_TYPE (init)))
4862 *from_p = init;
4863 ret = GS_OK;
4864 changed = true;
4867 break;
4869 case COMPOUND_EXPR:
4870 /* Remove any COMPOUND_EXPR in the RHS so the following cases will be
4871 caught. */
4872 gimplify_compound_expr (from_p, pre_p, true);
4873 ret = GS_OK;
4874 changed = true;
4875 break;
4877 case CONSTRUCTOR:
4878 /* If we already made some changes, let the front end have a
4879 crack at this before we break it down. */
4880 if (ret != GS_UNHANDLED)
4881 break;
4882 /* If we're initializing from a CONSTRUCTOR, break this into
4883 individual MODIFY_EXPRs. */
4884 return gimplify_init_constructor (expr_p, pre_p, post_p, want_value,
4885 false);
4887 case COND_EXPR:
4888 /* If we're assigning to a non-register type, push the assignment
4889 down into the branches. This is mandatory for ADDRESSABLE types,
4890 since we cannot generate temporaries for such, but it saves a
4891 copy in other cases as well. */
4892 if (!is_gimple_reg_type (TREE_TYPE (*from_p)))
4894 /* This code should mirror the code in gimplify_cond_expr. */
4895 enum tree_code code = TREE_CODE (*expr_p);
4896 tree cond = *from_p;
4897 tree result = *to_p;
4899 ret = gimplify_expr (&result, pre_p, post_p,
4900 is_gimple_lvalue, fb_lvalue);
4901 if (ret != GS_ERROR)
4902 ret = GS_OK;
4904 if (TREE_TYPE (TREE_OPERAND (cond, 1)) != void_type_node)
4905 TREE_OPERAND (cond, 1)
4906 = build2 (code, void_type_node, result,
4907 TREE_OPERAND (cond, 1));
4908 if (TREE_TYPE (TREE_OPERAND (cond, 2)) != void_type_node)
4909 TREE_OPERAND (cond, 2)
4910 = build2 (code, void_type_node, unshare_expr (result),
4911 TREE_OPERAND (cond, 2));
4913 TREE_TYPE (cond) = void_type_node;
4914 recalculate_side_effects (cond);
4916 if (want_value)
4918 gimplify_and_add (cond, pre_p);
4919 *expr_p = unshare_expr (result);
4921 else
4922 *expr_p = cond;
4923 return ret;
4925 break;
4927 case CALL_EXPR:
4928 /* For calls that return in memory, give *to_p as the CALL_EXPR's
4929 return slot so that we don't generate a temporary. */
4930 if (!CALL_EXPR_RETURN_SLOT_OPT (*from_p)
4931 && aggregate_value_p (*from_p, *from_p))
4933 bool use_target;
4935 if (!(rhs_predicate_for (*to_p))(*from_p))
4936 /* If we need a temporary, *to_p isn't accurate. */
4937 use_target = false;
4938 /* It's OK to use the return slot directly unless it's an NRV. */
4939 else if (TREE_CODE (*to_p) == RESULT_DECL
4940 && DECL_NAME (*to_p) == NULL_TREE
4941 && needs_to_live_in_memory (*to_p))
4942 use_target = true;
4943 else if (is_gimple_reg_type (TREE_TYPE (*to_p))
4944 || (DECL_P (*to_p) && DECL_REGISTER (*to_p)))
4945 /* Don't force regs into memory. */
4946 use_target = false;
4947 else if (TREE_CODE (*expr_p) == INIT_EXPR)
4948 /* It's OK to use the target directly if it's being
4949 initialized. */
4950 use_target = true;
4951 else if (TREE_CODE (TYPE_SIZE_UNIT (TREE_TYPE (*to_p)))
4952 != INTEGER_CST)
4953 /* Always use the target and thus RSO for variable-sized types.
4954 GIMPLE cannot deal with a variable-sized assignment
4955 embedded in a call statement. */
4956 use_target = true;
4957 else if (TREE_CODE (*to_p) != SSA_NAME
4958 && (!is_gimple_variable (*to_p)
4959 || needs_to_live_in_memory (*to_p)))
4960 /* Don't use the original target if it's already addressable;
4961 if its address escapes, and the called function uses the
4962 NRV optimization, a conforming program could see *to_p
4963 change before the called function returns; see c++/19317.
4964 When optimizing, the return_slot pass marks more functions
4965 as safe after we have escape info. */
4966 use_target = false;
4967 else
4968 use_target = true;
4970 if (use_target)
4972 CALL_EXPR_RETURN_SLOT_OPT (*from_p) = 1;
4973 mark_addressable (*to_p);
4976 break;
4978 case WITH_SIZE_EXPR:
4979 /* Likewise for calls that return an aggregate of non-constant size,
4980 since we would not be able to generate a temporary at all. */
4981 if (TREE_CODE (TREE_OPERAND (*from_p, 0)) == CALL_EXPR)
4983 *from_p = TREE_OPERAND (*from_p, 0);
4984 /* We don't change ret in this case because the
4985 WITH_SIZE_EXPR might have been added in
4986 gimplify_modify_expr, so returning GS_OK would lead to an
4987 infinite loop. */
4988 changed = true;
4990 break;
4992 /* If we're initializing from a container, push the initialization
4993 inside it. */
4994 case CLEANUP_POINT_EXPR:
4995 case BIND_EXPR:
4996 case STATEMENT_LIST:
4998 tree wrap = *from_p;
4999 tree t;
5001 ret = gimplify_expr (to_p, pre_p, post_p, is_gimple_min_lval,
5002 fb_lvalue);
5003 if (ret != GS_ERROR)
5004 ret = GS_OK;
5006 t = voidify_wrapper_expr (wrap, *expr_p);
5007 gcc_assert (t == *expr_p);
5009 if (want_value)
5011 gimplify_and_add (wrap, pre_p);
5012 *expr_p = unshare_expr (*to_p);
5014 else
5015 *expr_p = wrap;
5016 return GS_OK;
5019 case COMPOUND_LITERAL_EXPR:
5021 tree complit = TREE_OPERAND (*expr_p, 1);
5022 tree decl_s = COMPOUND_LITERAL_EXPR_DECL_EXPR (complit);
5023 tree decl = DECL_EXPR_DECL (decl_s);
5024 tree init = DECL_INITIAL (decl);
5026 /* struct T x = (struct T) { 0, 1, 2 } can be optimized
5027 into struct T x = { 0, 1, 2 } if the address of the
5028 compound literal has never been taken. */
5029 if (!TREE_ADDRESSABLE (complit)
5030 && !TREE_ADDRESSABLE (decl)
5031 && init)
5033 *expr_p = copy_node (*expr_p);
5034 TREE_OPERAND (*expr_p, 1) = init;
5035 return GS_OK;
5039 default:
5040 break;
5043 while (changed);
5045 return ret;
5049 /* Return true if T looks like a valid GIMPLE statement. */
5051 static bool
5052 is_gimple_stmt (tree t)
5054 const enum tree_code code = TREE_CODE (t);
5056 switch (code)
5058 case NOP_EXPR:
5059 /* The only valid NOP_EXPR is the empty statement. */
5060 return IS_EMPTY_STMT (t);
5062 case BIND_EXPR:
5063 case COND_EXPR:
5064 /* These are only valid if they're void. */
5065 return TREE_TYPE (t) == NULL || VOID_TYPE_P (TREE_TYPE (t));
5067 case SWITCH_EXPR:
5068 case GOTO_EXPR:
5069 case RETURN_EXPR:
5070 case LABEL_EXPR:
5071 case CASE_LABEL_EXPR:
5072 case TRY_CATCH_EXPR:
5073 case TRY_FINALLY_EXPR:
5074 case EH_FILTER_EXPR:
5075 case CATCH_EXPR:
5076 case ASM_EXPR:
5077 case STATEMENT_LIST:
5078 case OACC_PARALLEL:
5079 case OACC_KERNELS:
5080 case OACC_DATA:
5081 case OACC_HOST_DATA:
5082 case OACC_DECLARE:
5083 case OACC_UPDATE:
5084 case OACC_ENTER_DATA:
5085 case OACC_EXIT_DATA:
5086 case OACC_CACHE:
5087 case OMP_PARALLEL:
5088 case OMP_FOR:
5089 case OMP_SIMD:
5090 case CILK_SIMD:
5091 case OMP_DISTRIBUTE:
5092 case OACC_LOOP:
5093 case OMP_SECTIONS:
5094 case OMP_SECTION:
5095 case OMP_SINGLE:
5096 case OMP_MASTER:
5097 case OMP_TASKGROUP:
5098 case OMP_ORDERED:
5099 case OMP_CRITICAL:
5100 case OMP_TASK:
5101 case OMP_TARGET:
5102 case OMP_TARGET_DATA:
5103 case OMP_TARGET_UPDATE:
5104 case OMP_TARGET_ENTER_DATA:
5105 case OMP_TARGET_EXIT_DATA:
5106 case OMP_TASKLOOP:
5107 case OMP_TEAMS:
5108 /* These are always void. */
5109 return true;
5111 case CALL_EXPR:
5112 case MODIFY_EXPR:
5113 case PREDICT_EXPR:
5114 /* These are valid regardless of their type. */
5115 return true;
5117 default:
5118 return false;
5123 /* Promote partial stores to COMPLEX variables to total stores. *EXPR_P is
5124 a MODIFY_EXPR with a lhs of a REAL/IMAGPART_EXPR of a variable with
5125 DECL_GIMPLE_REG_P set.
5127 IMPORTANT NOTE: This promotion is performed by introducing a load of the
5128 other, unmodified part of the complex object just before the total store.
5129 As a consequence, if the object is still uninitialized, an undefined value
5130 will be loaded into a register, which may result in a spurious exception
5131 if the register is floating-point and the value happens to be a signaling
5132 NaN for example. Then the fully-fledged complex operations lowering pass
5133 followed by a DCE pass are necessary in order to fix things up. */
5135 static enum gimplify_status
5136 gimplify_modify_expr_complex_part (tree *expr_p, gimple_seq *pre_p,
5137 bool want_value)
5139 enum tree_code code, ocode;
5140 tree lhs, rhs, new_rhs, other, realpart, imagpart;
5142 lhs = TREE_OPERAND (*expr_p, 0);
5143 rhs = TREE_OPERAND (*expr_p, 1);
5144 code = TREE_CODE (lhs);
5145 lhs = TREE_OPERAND (lhs, 0);
5147 ocode = code == REALPART_EXPR ? IMAGPART_EXPR : REALPART_EXPR;
5148 other = build1 (ocode, TREE_TYPE (rhs), lhs);
5149 TREE_NO_WARNING (other) = 1;
5150 other = get_formal_tmp_var (other, pre_p);
5152 realpart = code == REALPART_EXPR ? rhs : other;
5153 imagpart = code == REALPART_EXPR ? other : rhs;
5155 if (TREE_CONSTANT (realpart) && TREE_CONSTANT (imagpart))
5156 new_rhs = build_complex (TREE_TYPE (lhs), realpart, imagpart);
5157 else
5158 new_rhs = build2 (COMPLEX_EXPR, TREE_TYPE (lhs), realpart, imagpart);
5160 gimplify_seq_add_stmt (pre_p, gimple_build_assign (lhs, new_rhs));
5161 *expr_p = (want_value) ? rhs : NULL_TREE;
5163 return GS_ALL_DONE;
5166 /* Gimplify the MODIFY_EXPR node pointed to by EXPR_P.
5168 modify_expr
5169 : varname '=' rhs
5170 | '*' ID '=' rhs
5172 PRE_P points to the list where side effects that must happen before
5173 *EXPR_P should be stored.
5175 POST_P points to the list where side effects that must happen after
5176 *EXPR_P should be stored.
5178 WANT_VALUE is nonzero iff we want to use the value of this expression
5179 in another expression. */
5181 static enum gimplify_status
5182 gimplify_modify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
5183 bool want_value)
5185 tree *from_p = &TREE_OPERAND (*expr_p, 1);
5186 tree *to_p = &TREE_OPERAND (*expr_p, 0);
5187 enum gimplify_status ret = GS_UNHANDLED;
5188 gimple *assign;
5189 location_t loc = EXPR_LOCATION (*expr_p);
5190 gimple_stmt_iterator gsi;
5192 gcc_assert (TREE_CODE (*expr_p) == MODIFY_EXPR
5193 || TREE_CODE (*expr_p) == INIT_EXPR);
5195 /* Trying to simplify a clobber using normal logic doesn't work,
5196 so handle it here. */
5197 if (TREE_CLOBBER_P (*from_p))
5199 ret = gimplify_expr (to_p, pre_p, post_p, is_gimple_lvalue, fb_lvalue);
5200 if (ret == GS_ERROR)
5201 return ret;
5202 gcc_assert (!want_value
5203 && (VAR_P (*to_p) || TREE_CODE (*to_p) == MEM_REF));
5204 gimplify_seq_add_stmt (pre_p, gimple_build_assign (*to_p, *from_p));
5205 *expr_p = NULL;
5206 return GS_ALL_DONE;
5209 /* Insert pointer conversions required by the middle-end that are not
5210 required by the frontend. This fixes middle-end type checking for
5211 for example gcc.dg/redecl-6.c. */
5212 if (POINTER_TYPE_P (TREE_TYPE (*to_p)))
5214 STRIP_USELESS_TYPE_CONVERSION (*from_p);
5215 if (!useless_type_conversion_p (TREE_TYPE (*to_p), TREE_TYPE (*from_p)))
5216 *from_p = fold_convert_loc (loc, TREE_TYPE (*to_p), *from_p);
5219 /* See if any simplifications can be done based on what the RHS is. */
5220 ret = gimplify_modify_expr_rhs (expr_p, from_p, to_p, pre_p, post_p,
5221 want_value);
5222 if (ret != GS_UNHANDLED)
5223 return ret;
5225 /* For zero sized types only gimplify the left hand side and right hand
5226 side as statements and throw away the assignment. Do this after
5227 gimplify_modify_expr_rhs so we handle TARGET_EXPRs of addressable
5228 types properly. */
5229 if (zero_sized_type (TREE_TYPE (*from_p)) && !want_value)
5231 gimplify_stmt (from_p, pre_p);
5232 gimplify_stmt (to_p, pre_p);
5233 *expr_p = NULL_TREE;
5234 return GS_ALL_DONE;
5237 /* If the value being copied is of variable width, compute the length
5238 of the copy into a WITH_SIZE_EXPR. Note that we need to do this
5239 before gimplifying any of the operands so that we can resolve any
5240 PLACEHOLDER_EXPRs in the size. Also note that the RTL expander uses
5241 the size of the expression to be copied, not of the destination, so
5242 that is what we must do here. */
5243 maybe_with_size_expr (from_p);
5245 /* As a special case, we have to temporarily allow for assignments
5246 with a CALL_EXPR on the RHS. Since in GIMPLE a function call is
5247 a toplevel statement, when gimplifying the GENERIC expression
5248 MODIFY_EXPR <a, CALL_EXPR <foo>>, we cannot create the tuple
5249 GIMPLE_ASSIGN <a, GIMPLE_CALL <foo>>.
5251 Instead, we need to create the tuple GIMPLE_CALL <a, foo>. To
5252 prevent gimplify_expr from trying to create a new temporary for
5253 foo's LHS, we tell it that it should only gimplify until it
5254 reaches the CALL_EXPR. On return from gimplify_expr, the newly
5255 created GIMPLE_CALL <foo> will be the last statement in *PRE_P
5256 and all we need to do here is set 'a' to be its LHS. */
5258 /* Gimplify the RHS first for C++17 and bug 71104. */
5259 gimple_predicate initial_pred = initial_rhs_predicate_for (*to_p);
5260 ret = gimplify_expr (from_p, pre_p, post_p, initial_pred, fb_rvalue);
5261 if (ret == GS_ERROR)
5262 return ret;
5264 /* Then gimplify the LHS. */
5265 /* If we gimplified the RHS to a CALL_EXPR and that call may return
5266 twice we have to make sure to gimplify into non-SSA as otherwise
5267 the abnormal edge added later will make those defs not dominate
5268 their uses.
5269 ??? Technically this applies only to the registers used in the
5270 resulting non-register *TO_P. */
5271 bool saved_into_ssa = gimplify_ctxp->into_ssa;
5272 if (saved_into_ssa
5273 && TREE_CODE (*from_p) == CALL_EXPR
5274 && call_expr_flags (*from_p) & ECF_RETURNS_TWICE)
5275 gimplify_ctxp->into_ssa = false;
5276 ret = gimplify_expr (to_p, pre_p, post_p, is_gimple_lvalue, fb_lvalue);
5277 gimplify_ctxp->into_ssa = saved_into_ssa;
5278 if (ret == GS_ERROR)
5279 return ret;
5281 /* Now that the LHS is gimplified, re-gimplify the RHS if our initial
5282 guess for the predicate was wrong. */
5283 gimple_predicate final_pred = rhs_predicate_for (*to_p);
5284 if (final_pred != initial_pred)
5286 ret = gimplify_expr (from_p, pre_p, post_p, final_pred, fb_rvalue);
5287 if (ret == GS_ERROR)
5288 return ret;
5291 /* In case of va_arg internal fn wrappped in a WITH_SIZE_EXPR, add the type
5292 size as argument to the call. */
5293 if (TREE_CODE (*from_p) == WITH_SIZE_EXPR)
5295 tree call = TREE_OPERAND (*from_p, 0);
5296 tree vlasize = TREE_OPERAND (*from_p, 1);
5298 if (TREE_CODE (call) == CALL_EXPR
5299 && CALL_EXPR_IFN (call) == IFN_VA_ARG)
5301 int nargs = call_expr_nargs (call);
5302 tree type = TREE_TYPE (call);
5303 tree ap = CALL_EXPR_ARG (call, 0);
5304 tree tag = CALL_EXPR_ARG (call, 1);
5305 tree aptag = CALL_EXPR_ARG (call, 2);
5306 tree newcall = build_call_expr_internal_loc (EXPR_LOCATION (call),
5307 IFN_VA_ARG, type,
5308 nargs + 1, ap, tag,
5309 aptag, vlasize);
5310 TREE_OPERAND (*from_p, 0) = newcall;
5314 /* Now see if the above changed *from_p to something we handle specially. */
5315 ret = gimplify_modify_expr_rhs (expr_p, from_p, to_p, pre_p, post_p,
5316 want_value);
5317 if (ret != GS_UNHANDLED)
5318 return ret;
5320 /* If we've got a variable sized assignment between two lvalues (i.e. does
5321 not involve a call), then we can make things a bit more straightforward
5322 by converting the assignment to memcpy or memset. */
5323 if (TREE_CODE (*from_p) == WITH_SIZE_EXPR)
5325 tree from = TREE_OPERAND (*from_p, 0);
5326 tree size = TREE_OPERAND (*from_p, 1);
5328 if (TREE_CODE (from) == CONSTRUCTOR)
5329 return gimplify_modify_expr_to_memset (expr_p, size, want_value, pre_p);
5331 if (is_gimple_addressable (from))
5333 *from_p = from;
5334 return gimplify_modify_expr_to_memcpy (expr_p, size, want_value,
5335 pre_p);
5339 /* Transform partial stores to non-addressable complex variables into
5340 total stores. This allows us to use real instead of virtual operands
5341 for these variables, which improves optimization. */
5342 if ((TREE_CODE (*to_p) == REALPART_EXPR
5343 || TREE_CODE (*to_p) == IMAGPART_EXPR)
5344 && is_gimple_reg (TREE_OPERAND (*to_p, 0)))
5345 return gimplify_modify_expr_complex_part (expr_p, pre_p, want_value);
5347 /* Try to alleviate the effects of the gimplification creating artificial
5348 temporaries (see for example is_gimple_reg_rhs) on the debug info, but
5349 make sure not to create DECL_DEBUG_EXPR links across functions. */
5350 if (!gimplify_ctxp->into_ssa
5351 && VAR_P (*from_p)
5352 && DECL_IGNORED_P (*from_p)
5353 && DECL_P (*to_p)
5354 && !DECL_IGNORED_P (*to_p)
5355 && decl_function_context (*to_p) == current_function_decl)
5357 if (!DECL_NAME (*from_p) && DECL_NAME (*to_p))
5358 DECL_NAME (*from_p)
5359 = create_tmp_var_name (IDENTIFIER_POINTER (DECL_NAME (*to_p)));
5360 DECL_HAS_DEBUG_EXPR_P (*from_p) = 1;
5361 SET_DECL_DEBUG_EXPR (*from_p, *to_p);
5364 if (want_value && TREE_THIS_VOLATILE (*to_p))
5365 *from_p = get_initialized_tmp_var (*from_p, pre_p, post_p);
5367 if (TREE_CODE (*from_p) == CALL_EXPR)
5369 /* Since the RHS is a CALL_EXPR, we need to create a GIMPLE_CALL
5370 instead of a GIMPLE_ASSIGN. */
5371 gcall *call_stmt;
5372 if (CALL_EXPR_FN (*from_p) == NULL_TREE)
5374 /* Gimplify internal functions created in the FEs. */
5375 int nargs = call_expr_nargs (*from_p), i;
5376 enum internal_fn ifn = CALL_EXPR_IFN (*from_p);
5377 auto_vec<tree> vargs (nargs);
5379 for (i = 0; i < nargs; i++)
5381 gimplify_arg (&CALL_EXPR_ARG (*from_p, i), pre_p,
5382 EXPR_LOCATION (*from_p));
5383 vargs.quick_push (CALL_EXPR_ARG (*from_p, i));
5385 call_stmt = gimple_build_call_internal_vec (ifn, vargs);
5386 gimple_set_location (call_stmt, EXPR_LOCATION (*expr_p));
5388 else
5390 tree fnptrtype = TREE_TYPE (CALL_EXPR_FN (*from_p));
5391 CALL_EXPR_FN (*from_p) = TREE_OPERAND (CALL_EXPR_FN (*from_p), 0);
5392 STRIP_USELESS_TYPE_CONVERSION (CALL_EXPR_FN (*from_p));
5393 tree fndecl = get_callee_fndecl (*from_p);
5394 if (fndecl
5395 && DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_NORMAL
5396 && DECL_FUNCTION_CODE (fndecl) == BUILT_IN_EXPECT
5397 && call_expr_nargs (*from_p) == 3)
5398 call_stmt = gimple_build_call_internal (IFN_BUILTIN_EXPECT, 3,
5399 CALL_EXPR_ARG (*from_p, 0),
5400 CALL_EXPR_ARG (*from_p, 1),
5401 CALL_EXPR_ARG (*from_p, 2));
5402 else
5404 call_stmt = gimple_build_call_from_tree (*from_p);
5405 gimple_call_set_fntype (call_stmt, TREE_TYPE (fnptrtype));
5408 notice_special_calls (call_stmt);
5409 if (!gimple_call_noreturn_p (call_stmt) || !should_remove_lhs_p (*to_p))
5410 gimple_call_set_lhs (call_stmt, *to_p);
5411 else if (TREE_CODE (*to_p) == SSA_NAME)
5412 /* The above is somewhat premature, avoid ICEing later for a
5413 SSA name w/o a definition. We may have uses in the GIMPLE IL.
5414 ??? This doesn't make it a default-def. */
5415 SSA_NAME_DEF_STMT (*to_p) = gimple_build_nop ();
5416 assign = call_stmt;
5418 else
5420 assign = gimple_build_assign (*to_p, *from_p);
5421 gimple_set_location (assign, EXPR_LOCATION (*expr_p));
5422 if (COMPARISON_CLASS_P (*from_p))
5423 gimple_set_no_warning (assign, TREE_NO_WARNING (*from_p));
5426 if (gimplify_ctxp->into_ssa && is_gimple_reg (*to_p))
5428 /* We should have got an SSA name from the start. */
5429 gcc_assert (TREE_CODE (*to_p) == SSA_NAME
5430 || ! gimple_in_ssa_p (cfun));
5433 gimplify_seq_add_stmt (pre_p, assign);
5434 gsi = gsi_last (*pre_p);
5435 maybe_fold_stmt (&gsi);
5437 if (want_value)
5439 *expr_p = TREE_THIS_VOLATILE (*to_p) ? *from_p : unshare_expr (*to_p);
5440 return GS_OK;
5442 else
5443 *expr_p = NULL;
5445 return GS_ALL_DONE;
5448 /* Gimplify a comparison between two variable-sized objects. Do this
5449 with a call to BUILT_IN_MEMCMP. */
5451 static enum gimplify_status
5452 gimplify_variable_sized_compare (tree *expr_p)
5454 location_t loc = EXPR_LOCATION (*expr_p);
5455 tree op0 = TREE_OPERAND (*expr_p, 0);
5456 tree op1 = TREE_OPERAND (*expr_p, 1);
5457 tree t, arg, dest, src, expr;
5459 arg = TYPE_SIZE_UNIT (TREE_TYPE (op0));
5460 arg = unshare_expr (arg);
5461 arg = SUBSTITUTE_PLACEHOLDER_IN_EXPR (arg, op0);
5462 src = build_fold_addr_expr_loc (loc, op1);
5463 dest = build_fold_addr_expr_loc (loc, op0);
5464 t = builtin_decl_implicit (BUILT_IN_MEMCMP);
5465 t = build_call_expr_loc (loc, t, 3, dest, src, arg);
5467 expr
5468 = build2 (TREE_CODE (*expr_p), TREE_TYPE (*expr_p), t, integer_zero_node);
5469 SET_EXPR_LOCATION (expr, loc);
5470 *expr_p = expr;
5472 return GS_OK;
5475 /* Gimplify a comparison between two aggregate objects of integral scalar
5476 mode as a comparison between the bitwise equivalent scalar values. */
5478 static enum gimplify_status
5479 gimplify_scalar_mode_aggregate_compare (tree *expr_p)
5481 location_t loc = EXPR_LOCATION (*expr_p);
5482 tree op0 = TREE_OPERAND (*expr_p, 0);
5483 tree op1 = TREE_OPERAND (*expr_p, 1);
5485 tree type = TREE_TYPE (op0);
5486 tree scalar_type = lang_hooks.types.type_for_mode (TYPE_MODE (type), 1);
5488 op0 = fold_build1_loc (loc, VIEW_CONVERT_EXPR, scalar_type, op0);
5489 op1 = fold_build1_loc (loc, VIEW_CONVERT_EXPR, scalar_type, op1);
5491 *expr_p
5492 = fold_build2_loc (loc, TREE_CODE (*expr_p), TREE_TYPE (*expr_p), op0, op1);
5494 return GS_OK;
5497 /* Gimplify an expression sequence. This function gimplifies each
5498 expression and rewrites the original expression with the last
5499 expression of the sequence in GIMPLE form.
5501 PRE_P points to the list where the side effects for all the
5502 expressions in the sequence will be emitted.
5504 WANT_VALUE is true when the result of the last COMPOUND_EXPR is used. */
5506 static enum gimplify_status
5507 gimplify_compound_expr (tree *expr_p, gimple_seq *pre_p, bool want_value)
5509 tree t = *expr_p;
5513 tree *sub_p = &TREE_OPERAND (t, 0);
5515 if (TREE_CODE (*sub_p) == COMPOUND_EXPR)
5516 gimplify_compound_expr (sub_p, pre_p, false);
5517 else
5518 gimplify_stmt (sub_p, pre_p);
5520 t = TREE_OPERAND (t, 1);
5522 while (TREE_CODE (t) == COMPOUND_EXPR);
5524 *expr_p = t;
5525 if (want_value)
5526 return GS_OK;
5527 else
5529 gimplify_stmt (expr_p, pre_p);
5530 return GS_ALL_DONE;
5534 /* Gimplify a SAVE_EXPR node. EXPR_P points to the expression to
5535 gimplify. After gimplification, EXPR_P will point to a new temporary
5536 that holds the original value of the SAVE_EXPR node.
5538 PRE_P points to the list where side effects that must happen before
5539 *EXPR_P should be stored. */
5541 static enum gimplify_status
5542 gimplify_save_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
5544 enum gimplify_status ret = GS_ALL_DONE;
5545 tree val;
5547 gcc_assert (TREE_CODE (*expr_p) == SAVE_EXPR);
5548 val = TREE_OPERAND (*expr_p, 0);
5550 /* If the SAVE_EXPR has not been resolved, then evaluate it once. */
5551 if (!SAVE_EXPR_RESOLVED_P (*expr_p))
5553 /* The operand may be a void-valued expression such as SAVE_EXPRs
5554 generated by the Java frontend for class initialization. It is
5555 being executed only for its side-effects. */
5556 if (TREE_TYPE (val) == void_type_node)
5558 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
5559 is_gimple_stmt, fb_none);
5560 val = NULL;
5562 else
5563 /* The temporary may not be an SSA name as later abnormal and EH
5564 control flow may invalidate use/def domination. */
5565 val = get_initialized_tmp_var (val, pre_p, post_p, false);
5567 TREE_OPERAND (*expr_p, 0) = val;
5568 SAVE_EXPR_RESOLVED_P (*expr_p) = 1;
5571 *expr_p = val;
5573 return ret;
5576 /* Rewrite the ADDR_EXPR node pointed to by EXPR_P
5578 unary_expr
5579 : ...
5580 | '&' varname
5583 PRE_P points to the list where side effects that must happen before
5584 *EXPR_P should be stored.
5586 POST_P points to the list where side effects that must happen after
5587 *EXPR_P should be stored. */
5589 static enum gimplify_status
5590 gimplify_addr_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
5592 tree expr = *expr_p;
5593 tree op0 = TREE_OPERAND (expr, 0);
5594 enum gimplify_status ret;
5595 location_t loc = EXPR_LOCATION (*expr_p);
5597 switch (TREE_CODE (op0))
5599 case INDIRECT_REF:
5600 do_indirect_ref:
5601 /* Check if we are dealing with an expression of the form '&*ptr'.
5602 While the front end folds away '&*ptr' into 'ptr', these
5603 expressions may be generated internally by the compiler (e.g.,
5604 builtins like __builtin_va_end). */
5605 /* Caution: the silent array decomposition semantics we allow for
5606 ADDR_EXPR means we can't always discard the pair. */
5607 /* Gimplification of the ADDR_EXPR operand may drop
5608 cv-qualification conversions, so make sure we add them if
5609 needed. */
5611 tree op00 = TREE_OPERAND (op0, 0);
5612 tree t_expr = TREE_TYPE (expr);
5613 tree t_op00 = TREE_TYPE (op00);
5615 if (!useless_type_conversion_p (t_expr, t_op00))
5616 op00 = fold_convert_loc (loc, TREE_TYPE (expr), op00);
5617 *expr_p = op00;
5618 ret = GS_OK;
5620 break;
5622 case VIEW_CONVERT_EXPR:
5623 /* Take the address of our operand and then convert it to the type of
5624 this ADDR_EXPR.
5626 ??? The interactions of VIEW_CONVERT_EXPR and aliasing is not at
5627 all clear. The impact of this transformation is even less clear. */
5629 /* If the operand is a useless conversion, look through it. Doing so
5630 guarantees that the ADDR_EXPR and its operand will remain of the
5631 same type. */
5632 if (tree_ssa_useless_type_conversion (TREE_OPERAND (op0, 0)))
5633 op0 = TREE_OPERAND (op0, 0);
5635 *expr_p = fold_convert_loc (loc, TREE_TYPE (expr),
5636 build_fold_addr_expr_loc (loc,
5637 TREE_OPERAND (op0, 0)));
5638 ret = GS_OK;
5639 break;
5641 case MEM_REF:
5642 if (integer_zerop (TREE_OPERAND (op0, 1)))
5643 goto do_indirect_ref;
5645 /* fall through */
5647 default:
5648 /* If we see a call to a declared builtin or see its address
5649 being taken (we can unify those cases here) then we can mark
5650 the builtin for implicit generation by GCC. */
5651 if (TREE_CODE (op0) == FUNCTION_DECL
5652 && DECL_BUILT_IN_CLASS (op0) == BUILT_IN_NORMAL
5653 && builtin_decl_declared_p (DECL_FUNCTION_CODE (op0)))
5654 set_builtin_decl_implicit_p (DECL_FUNCTION_CODE (op0), true);
5656 /* We use fb_either here because the C frontend sometimes takes
5657 the address of a call that returns a struct; see
5658 gcc.dg/c99-array-lval-1.c. The gimplifier will correctly make
5659 the implied temporary explicit. */
5661 /* Make the operand addressable. */
5662 ret = gimplify_expr (&TREE_OPERAND (expr, 0), pre_p, post_p,
5663 is_gimple_addressable, fb_either);
5664 if (ret == GS_ERROR)
5665 break;
5667 /* Then mark it. Beware that it may not be possible to do so directly
5668 if a temporary has been created by the gimplification. */
5669 prepare_gimple_addressable (&TREE_OPERAND (expr, 0), pre_p);
5671 op0 = TREE_OPERAND (expr, 0);
5673 /* For various reasons, the gimplification of the expression
5674 may have made a new INDIRECT_REF. */
5675 if (TREE_CODE (op0) == INDIRECT_REF)
5676 goto do_indirect_ref;
5678 mark_addressable (TREE_OPERAND (expr, 0));
5680 /* The FEs may end up building ADDR_EXPRs early on a decl with
5681 an incomplete type. Re-build ADDR_EXPRs in canonical form
5682 here. */
5683 if (!types_compatible_p (TREE_TYPE (op0), TREE_TYPE (TREE_TYPE (expr))))
5684 *expr_p = build_fold_addr_expr (op0);
5686 /* Make sure TREE_CONSTANT and TREE_SIDE_EFFECTS are set properly. */
5687 recompute_tree_invariant_for_addr_expr (*expr_p);
5689 /* If we re-built the ADDR_EXPR add a conversion to the original type
5690 if required. */
5691 if (!useless_type_conversion_p (TREE_TYPE (expr), TREE_TYPE (*expr_p)))
5692 *expr_p = fold_convert (TREE_TYPE (expr), *expr_p);
5694 break;
5697 return ret;
5700 /* Gimplify the operands of an ASM_EXPR. Input operands should be a gimple
5701 value; output operands should be a gimple lvalue. */
5703 static enum gimplify_status
5704 gimplify_asm_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
5706 tree expr;
5707 int noutputs;
5708 const char **oconstraints;
5709 int i;
5710 tree link;
5711 const char *constraint;
5712 bool allows_mem, allows_reg, is_inout;
5713 enum gimplify_status ret, tret;
5714 gasm *stmt;
5715 vec<tree, va_gc> *inputs;
5716 vec<tree, va_gc> *outputs;
5717 vec<tree, va_gc> *clobbers;
5718 vec<tree, va_gc> *labels;
5719 tree link_next;
5721 expr = *expr_p;
5722 noutputs = list_length (ASM_OUTPUTS (expr));
5723 oconstraints = (const char **) alloca ((noutputs) * sizeof (const char *));
5725 inputs = NULL;
5726 outputs = NULL;
5727 clobbers = NULL;
5728 labels = NULL;
5730 ret = GS_ALL_DONE;
5731 link_next = NULL_TREE;
5732 for (i = 0, link = ASM_OUTPUTS (expr); link; ++i, link = link_next)
5734 bool ok;
5735 size_t constraint_len;
5737 link_next = TREE_CHAIN (link);
5739 oconstraints[i]
5740 = constraint
5741 = TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (link)));
5742 constraint_len = strlen (constraint);
5743 if (constraint_len == 0)
5744 continue;
5746 ok = parse_output_constraint (&constraint, i, 0, 0,
5747 &allows_mem, &allows_reg, &is_inout);
5748 if (!ok)
5750 ret = GS_ERROR;
5751 is_inout = false;
5754 if (!allows_reg && allows_mem)
5755 mark_addressable (TREE_VALUE (link));
5757 tret = gimplify_expr (&TREE_VALUE (link), pre_p, post_p,
5758 is_inout ? is_gimple_min_lval : is_gimple_lvalue,
5759 fb_lvalue | fb_mayfail);
5760 if (tret == GS_ERROR)
5762 error ("invalid lvalue in asm output %d", i);
5763 ret = tret;
5766 /* If the constraint does not allow memory make sure we gimplify
5767 it to a register if it is not already but its base is. This
5768 happens for complex and vector components. */
5769 if (!allows_mem)
5771 tree op = TREE_VALUE (link);
5772 if (! is_gimple_val (op)
5773 && is_gimple_reg_type (TREE_TYPE (op))
5774 && is_gimple_reg (get_base_address (op)))
5776 tree tem = create_tmp_reg (TREE_TYPE (op));
5777 tree ass;
5778 if (is_inout)
5780 ass = build2 (MODIFY_EXPR, TREE_TYPE (tem),
5781 tem, unshare_expr (op));
5782 gimplify_and_add (ass, pre_p);
5784 ass = build2 (MODIFY_EXPR, TREE_TYPE (tem), op, tem);
5785 gimplify_and_add (ass, post_p);
5787 TREE_VALUE (link) = tem;
5788 tret = GS_OK;
5792 vec_safe_push (outputs, link);
5793 TREE_CHAIN (link) = NULL_TREE;
5795 if (is_inout)
5797 /* An input/output operand. To give the optimizers more
5798 flexibility, split it into separate input and output
5799 operands. */
5800 tree input;
5801 /* Buffer big enough to format a 32-bit UINT_MAX into. */
5802 char buf[11];
5804 /* Turn the in/out constraint into an output constraint. */
5805 char *p = xstrdup (constraint);
5806 p[0] = '=';
5807 TREE_VALUE (TREE_PURPOSE (link)) = build_string (constraint_len, p);
5809 /* And add a matching input constraint. */
5810 if (allows_reg)
5812 sprintf (buf, "%u", i);
5814 /* If there are multiple alternatives in the constraint,
5815 handle each of them individually. Those that allow register
5816 will be replaced with operand number, the others will stay
5817 unchanged. */
5818 if (strchr (p, ',') != NULL)
5820 size_t len = 0, buflen = strlen (buf);
5821 char *beg, *end, *str, *dst;
5823 for (beg = p + 1;;)
5825 end = strchr (beg, ',');
5826 if (end == NULL)
5827 end = strchr (beg, '\0');
5828 if ((size_t) (end - beg) < buflen)
5829 len += buflen + 1;
5830 else
5831 len += end - beg + 1;
5832 if (*end)
5833 beg = end + 1;
5834 else
5835 break;
5838 str = (char *) alloca (len);
5839 for (beg = p + 1, dst = str;;)
5841 const char *tem;
5842 bool mem_p, reg_p, inout_p;
5844 end = strchr (beg, ',');
5845 if (end)
5846 *end = '\0';
5847 beg[-1] = '=';
5848 tem = beg - 1;
5849 parse_output_constraint (&tem, i, 0, 0,
5850 &mem_p, &reg_p, &inout_p);
5851 if (dst != str)
5852 *dst++ = ',';
5853 if (reg_p)
5855 memcpy (dst, buf, buflen);
5856 dst += buflen;
5858 else
5860 if (end)
5861 len = end - beg;
5862 else
5863 len = strlen (beg);
5864 memcpy (dst, beg, len);
5865 dst += len;
5867 if (end)
5868 beg = end + 1;
5869 else
5870 break;
5872 *dst = '\0';
5873 input = build_string (dst - str, str);
5875 else
5876 input = build_string (strlen (buf), buf);
5878 else
5879 input = build_string (constraint_len - 1, constraint + 1);
5881 free (p);
5883 input = build_tree_list (build_tree_list (NULL_TREE, input),
5884 unshare_expr (TREE_VALUE (link)));
5885 ASM_INPUTS (expr) = chainon (ASM_INPUTS (expr), input);
5889 link_next = NULL_TREE;
5890 for (link = ASM_INPUTS (expr); link; ++i, link = link_next)
5892 link_next = TREE_CHAIN (link);
5893 constraint = TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (link)));
5894 parse_input_constraint (&constraint, 0, 0, noutputs, 0,
5895 oconstraints, &allows_mem, &allows_reg);
5897 /* If we can't make copies, we can only accept memory. */
5898 if (TREE_ADDRESSABLE (TREE_TYPE (TREE_VALUE (link))))
5900 if (allows_mem)
5901 allows_reg = 0;
5902 else
5904 error ("impossible constraint in %<asm%>");
5905 error ("non-memory input %d must stay in memory", i);
5906 return GS_ERROR;
5910 /* If the operand is a memory input, it should be an lvalue. */
5911 if (!allows_reg && allows_mem)
5913 tree inputv = TREE_VALUE (link);
5914 STRIP_NOPS (inputv);
5915 if (TREE_CODE (inputv) == PREDECREMENT_EXPR
5916 || TREE_CODE (inputv) == PREINCREMENT_EXPR
5917 || TREE_CODE (inputv) == POSTDECREMENT_EXPR
5918 || TREE_CODE (inputv) == POSTINCREMENT_EXPR
5919 || TREE_CODE (inputv) == MODIFY_EXPR)
5920 TREE_VALUE (link) = error_mark_node;
5921 tret = gimplify_expr (&TREE_VALUE (link), pre_p, post_p,
5922 is_gimple_lvalue, fb_lvalue | fb_mayfail);
5923 if (tret != GS_ERROR)
5925 /* Unlike output operands, memory inputs are not guaranteed
5926 to be lvalues by the FE, and while the expressions are
5927 marked addressable there, if it is e.g. a statement
5928 expression, temporaries in it might not end up being
5929 addressable. They might be already used in the IL and thus
5930 it is too late to make them addressable now though. */
5931 tree x = TREE_VALUE (link);
5932 while (handled_component_p (x))
5933 x = TREE_OPERAND (x, 0);
5934 if (TREE_CODE (x) == MEM_REF
5935 && TREE_CODE (TREE_OPERAND (x, 0)) == ADDR_EXPR)
5936 x = TREE_OPERAND (TREE_OPERAND (x, 0), 0);
5937 if ((VAR_P (x)
5938 || TREE_CODE (x) == PARM_DECL
5939 || TREE_CODE (x) == RESULT_DECL)
5940 && !TREE_ADDRESSABLE (x)
5941 && is_gimple_reg (x))
5943 warning_at (EXPR_LOC_OR_LOC (TREE_VALUE (link),
5944 input_location), 0,
5945 "memory input %d is not directly addressable",
5947 prepare_gimple_addressable (&TREE_VALUE (link), pre_p);
5950 mark_addressable (TREE_VALUE (link));
5951 if (tret == GS_ERROR)
5953 error_at (EXPR_LOC_OR_LOC (TREE_VALUE (link), input_location),
5954 "memory input %d is not directly addressable", i);
5955 ret = tret;
5958 else
5960 tret = gimplify_expr (&TREE_VALUE (link), pre_p, post_p,
5961 is_gimple_asm_val, fb_rvalue);
5962 if (tret == GS_ERROR)
5963 ret = tret;
5966 TREE_CHAIN (link) = NULL_TREE;
5967 vec_safe_push (inputs, link);
5970 link_next = NULL_TREE;
5971 for (link = ASM_CLOBBERS (expr); link; ++i, link = link_next)
5973 link_next = TREE_CHAIN (link);
5974 TREE_CHAIN (link) = NULL_TREE;
5975 vec_safe_push (clobbers, link);
5978 link_next = NULL_TREE;
5979 for (link = ASM_LABELS (expr); link; ++i, link = link_next)
5981 link_next = TREE_CHAIN (link);
5982 TREE_CHAIN (link) = NULL_TREE;
5983 vec_safe_push (labels, link);
5986 /* Do not add ASMs with errors to the gimple IL stream. */
5987 if (ret != GS_ERROR)
5989 stmt = gimple_build_asm_vec (TREE_STRING_POINTER (ASM_STRING (expr)),
5990 inputs, outputs, clobbers, labels);
5992 gimple_asm_set_volatile (stmt, ASM_VOLATILE_P (expr) || noutputs == 0);
5993 gimple_asm_set_input (stmt, ASM_INPUT_P (expr));
5995 gimplify_seq_add_stmt (pre_p, stmt);
5998 return ret;
6001 /* Gimplify a CLEANUP_POINT_EXPR. Currently this works by adding
6002 GIMPLE_WITH_CLEANUP_EXPRs to the prequeue as we encounter cleanups while
6003 gimplifying the body, and converting them to TRY_FINALLY_EXPRs when we
6004 return to this function.
6006 FIXME should we complexify the prequeue handling instead? Or use flags
6007 for all the cleanups and let the optimizer tighten them up? The current
6008 code seems pretty fragile; it will break on a cleanup within any
6009 non-conditional nesting. But any such nesting would be broken, anyway;
6010 we can't write a TRY_FINALLY_EXPR that starts inside a nesting construct
6011 and continues out of it. We can do that at the RTL level, though, so
6012 having an optimizer to tighten up try/finally regions would be a Good
6013 Thing. */
6015 static enum gimplify_status
6016 gimplify_cleanup_point_expr (tree *expr_p, gimple_seq *pre_p)
6018 gimple_stmt_iterator iter;
6019 gimple_seq body_sequence = NULL;
6021 tree temp = voidify_wrapper_expr (*expr_p, NULL);
6023 /* We only care about the number of conditions between the innermost
6024 CLEANUP_POINT_EXPR and the cleanup. So save and reset the count and
6025 any cleanups collected outside the CLEANUP_POINT_EXPR. */
6026 int old_conds = gimplify_ctxp->conditions;
6027 gimple_seq old_cleanups = gimplify_ctxp->conditional_cleanups;
6028 bool old_in_cleanup_point_expr = gimplify_ctxp->in_cleanup_point_expr;
6029 gimplify_ctxp->conditions = 0;
6030 gimplify_ctxp->conditional_cleanups = NULL;
6031 gimplify_ctxp->in_cleanup_point_expr = true;
6033 gimplify_stmt (&TREE_OPERAND (*expr_p, 0), &body_sequence);
6035 gimplify_ctxp->conditions = old_conds;
6036 gimplify_ctxp->conditional_cleanups = old_cleanups;
6037 gimplify_ctxp->in_cleanup_point_expr = old_in_cleanup_point_expr;
6039 for (iter = gsi_start (body_sequence); !gsi_end_p (iter); )
6041 gimple *wce = gsi_stmt (iter);
6043 if (gimple_code (wce) == GIMPLE_WITH_CLEANUP_EXPR)
6045 if (gsi_one_before_end_p (iter))
6047 /* Note that gsi_insert_seq_before and gsi_remove do not
6048 scan operands, unlike some other sequence mutators. */
6049 if (!gimple_wce_cleanup_eh_only (wce))
6050 gsi_insert_seq_before_without_update (&iter,
6051 gimple_wce_cleanup (wce),
6052 GSI_SAME_STMT);
6053 gsi_remove (&iter, true);
6054 break;
6056 else
6058 gtry *gtry;
6059 gimple_seq seq;
6060 enum gimple_try_flags kind;
6062 if (gimple_wce_cleanup_eh_only (wce))
6063 kind = GIMPLE_TRY_CATCH;
6064 else
6065 kind = GIMPLE_TRY_FINALLY;
6066 seq = gsi_split_seq_after (iter);
6068 gtry = gimple_build_try (seq, gimple_wce_cleanup (wce), kind);
6069 /* Do not use gsi_replace here, as it may scan operands.
6070 We want to do a simple structural modification only. */
6071 gsi_set_stmt (&iter, gtry);
6072 iter = gsi_start (gtry->eval);
6075 else
6076 gsi_next (&iter);
6079 gimplify_seq_add_seq (pre_p, body_sequence);
6080 if (temp)
6082 *expr_p = temp;
6083 return GS_OK;
6085 else
6087 *expr_p = NULL;
6088 return GS_ALL_DONE;
6092 /* Insert a cleanup marker for gimplify_cleanup_point_expr. CLEANUP
6093 is the cleanup action required. EH_ONLY is true if the cleanup should
6094 only be executed if an exception is thrown, not on normal exit. */
6096 static void
6097 gimple_push_cleanup (tree var, tree cleanup, bool eh_only, gimple_seq *pre_p)
6099 gimple *wce;
6100 gimple_seq cleanup_stmts = NULL;
6102 /* Errors can result in improperly nested cleanups. Which results in
6103 confusion when trying to resolve the GIMPLE_WITH_CLEANUP_EXPR. */
6104 if (seen_error ())
6105 return;
6107 if (gimple_conditional_context ())
6109 /* If we're in a conditional context, this is more complex. We only
6110 want to run the cleanup if we actually ran the initialization that
6111 necessitates it, but we want to run it after the end of the
6112 conditional context. So we wrap the try/finally around the
6113 condition and use a flag to determine whether or not to actually
6114 run the destructor. Thus
6116 test ? f(A()) : 0
6118 becomes (approximately)
6120 flag = 0;
6121 try {
6122 if (test) { A::A(temp); flag = 1; val = f(temp); }
6123 else { val = 0; }
6124 } finally {
6125 if (flag) A::~A(temp);
6129 tree flag = create_tmp_var (boolean_type_node, "cleanup");
6130 gassign *ffalse = gimple_build_assign (flag, boolean_false_node);
6131 gassign *ftrue = gimple_build_assign (flag, boolean_true_node);
6133 cleanup = build3 (COND_EXPR, void_type_node, flag, cleanup, NULL);
6134 gimplify_stmt (&cleanup, &cleanup_stmts);
6135 wce = gimple_build_wce (cleanup_stmts);
6137 gimplify_seq_add_stmt (&gimplify_ctxp->conditional_cleanups, ffalse);
6138 gimplify_seq_add_stmt (&gimplify_ctxp->conditional_cleanups, wce);
6139 gimplify_seq_add_stmt (pre_p, ftrue);
6141 /* Because of this manipulation, and the EH edges that jump
6142 threading cannot redirect, the temporary (VAR) will appear
6143 to be used uninitialized. Don't warn. */
6144 TREE_NO_WARNING (var) = 1;
6146 else
6148 gimplify_stmt (&cleanup, &cleanup_stmts);
6149 wce = gimple_build_wce (cleanup_stmts);
6150 gimple_wce_set_cleanup_eh_only (wce, eh_only);
6151 gimplify_seq_add_stmt (pre_p, wce);
6155 /* Gimplify a TARGET_EXPR which doesn't appear on the rhs of an INIT_EXPR. */
6157 static enum gimplify_status
6158 gimplify_target_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
6160 tree targ = *expr_p;
6161 tree temp = TARGET_EXPR_SLOT (targ);
6162 tree init = TARGET_EXPR_INITIAL (targ);
6163 enum gimplify_status ret;
6165 if (init)
6167 tree cleanup = NULL_TREE;
6169 /* TARGET_EXPR temps aren't part of the enclosing block, so add it
6170 to the temps list. Handle also variable length TARGET_EXPRs. */
6171 if (TREE_CODE (DECL_SIZE (temp)) != INTEGER_CST)
6173 if (!TYPE_SIZES_GIMPLIFIED (TREE_TYPE (temp)))
6174 gimplify_type_sizes (TREE_TYPE (temp), pre_p);
6175 gimplify_vla_decl (temp, pre_p);
6177 else
6178 gimple_add_tmp_var (temp);
6180 /* If TARGET_EXPR_INITIAL is void, then the mere evaluation of the
6181 expression is supposed to initialize the slot. */
6182 if (VOID_TYPE_P (TREE_TYPE (init)))
6183 ret = gimplify_expr (&init, pre_p, post_p, is_gimple_stmt, fb_none);
6184 else
6186 tree init_expr = build2 (INIT_EXPR, void_type_node, temp, init);
6187 init = init_expr;
6188 ret = gimplify_expr (&init, pre_p, post_p, is_gimple_stmt, fb_none);
6189 init = NULL;
6190 ggc_free (init_expr);
6192 if (ret == GS_ERROR)
6194 /* PR c++/28266 Make sure this is expanded only once. */
6195 TARGET_EXPR_INITIAL (targ) = NULL_TREE;
6196 return GS_ERROR;
6198 if (init)
6199 gimplify_and_add (init, pre_p);
6201 /* If needed, push the cleanup for the temp. */
6202 if (TARGET_EXPR_CLEANUP (targ))
6204 if (CLEANUP_EH_ONLY (targ))
6205 gimple_push_cleanup (temp, TARGET_EXPR_CLEANUP (targ),
6206 CLEANUP_EH_ONLY (targ), pre_p);
6207 else
6208 cleanup = TARGET_EXPR_CLEANUP (targ);
6211 /* Add a clobber for the temporary going out of scope, like
6212 gimplify_bind_expr. */
6213 if (gimplify_ctxp->in_cleanup_point_expr
6214 && needs_to_live_in_memory (temp)
6215 && flag_stack_reuse == SR_ALL)
6217 tree clobber = build_constructor (TREE_TYPE (temp),
6218 NULL);
6219 TREE_THIS_VOLATILE (clobber) = true;
6220 clobber = build2 (MODIFY_EXPR, TREE_TYPE (temp), temp, clobber);
6221 if (cleanup)
6222 cleanup = build2 (COMPOUND_EXPR, void_type_node, cleanup,
6223 clobber);
6224 else
6225 cleanup = clobber;
6228 if (cleanup)
6229 gimple_push_cleanup (temp, cleanup, false, pre_p);
6231 /* Only expand this once. */
6232 TREE_OPERAND (targ, 3) = init;
6233 TARGET_EXPR_INITIAL (targ) = NULL_TREE;
6235 else
6236 /* We should have expanded this before. */
6237 gcc_assert (DECL_SEEN_IN_BIND_EXPR_P (temp));
6239 *expr_p = temp;
6240 return GS_OK;
6243 /* Gimplification of expression trees. */
6245 /* Gimplify an expression which appears at statement context. The
6246 corresponding GIMPLE statements are added to *SEQ_P. If *SEQ_P is
6247 NULL, a new sequence is allocated.
6249 Return true if we actually added a statement to the queue. */
6251 bool
6252 gimplify_stmt (tree *stmt_p, gimple_seq *seq_p)
6254 gimple_seq_node last;
6256 last = gimple_seq_last (*seq_p);
6257 gimplify_expr (stmt_p, seq_p, NULL, is_gimple_stmt, fb_none);
6258 return last != gimple_seq_last (*seq_p);
6261 /* Add FIRSTPRIVATE entries for DECL in the OpenMP the surrounding parallels
6262 to CTX. If entries already exist, force them to be some flavor of private.
6263 If there is no enclosing parallel, do nothing. */
6265 void
6266 omp_firstprivatize_variable (struct gimplify_omp_ctx *ctx, tree decl)
6268 splay_tree_node n;
6270 if (decl == NULL || !DECL_P (decl) || ctx->region_type == ORT_NONE)
6271 return;
6275 n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
6276 if (n != NULL)
6278 if (n->value & GOVD_SHARED)
6279 n->value = GOVD_FIRSTPRIVATE | (n->value & GOVD_SEEN);
6280 else if (n->value & GOVD_MAP)
6281 n->value |= GOVD_MAP_TO_ONLY;
6282 else
6283 return;
6285 else if ((ctx->region_type & ORT_TARGET) != 0)
6287 if (ctx->target_map_scalars_firstprivate)
6288 omp_add_variable (ctx, decl, GOVD_FIRSTPRIVATE);
6289 else
6290 omp_add_variable (ctx, decl, GOVD_MAP | GOVD_MAP_TO_ONLY);
6292 else if (ctx->region_type != ORT_WORKSHARE
6293 && ctx->region_type != ORT_SIMD
6294 && ctx->region_type != ORT_ACC
6295 && !(ctx->region_type & ORT_TARGET_DATA))
6296 omp_add_variable (ctx, decl, GOVD_FIRSTPRIVATE);
6298 ctx = ctx->outer_context;
6300 while (ctx);
6303 /* Similarly for each of the type sizes of TYPE. */
6305 static void
6306 omp_firstprivatize_type_sizes (struct gimplify_omp_ctx *ctx, tree type)
6308 if (type == NULL || type == error_mark_node)
6309 return;
6310 type = TYPE_MAIN_VARIANT (type);
6312 if (ctx->privatized_types->add (type))
6313 return;
6315 switch (TREE_CODE (type))
6317 case INTEGER_TYPE:
6318 case ENUMERAL_TYPE:
6319 case BOOLEAN_TYPE:
6320 case REAL_TYPE:
6321 case FIXED_POINT_TYPE:
6322 omp_firstprivatize_variable (ctx, TYPE_MIN_VALUE (type));
6323 omp_firstprivatize_variable (ctx, TYPE_MAX_VALUE (type));
6324 break;
6326 case ARRAY_TYPE:
6327 omp_firstprivatize_type_sizes (ctx, TREE_TYPE (type));
6328 omp_firstprivatize_type_sizes (ctx, TYPE_DOMAIN (type));
6329 break;
6331 case RECORD_TYPE:
6332 case UNION_TYPE:
6333 case QUAL_UNION_TYPE:
6335 tree field;
6336 for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
6337 if (TREE_CODE (field) == FIELD_DECL)
6339 omp_firstprivatize_variable (ctx, DECL_FIELD_OFFSET (field));
6340 omp_firstprivatize_type_sizes (ctx, TREE_TYPE (field));
6343 break;
6345 case POINTER_TYPE:
6346 case REFERENCE_TYPE:
6347 omp_firstprivatize_type_sizes (ctx, TREE_TYPE (type));
6348 break;
6350 default:
6351 break;
6354 omp_firstprivatize_variable (ctx, TYPE_SIZE (type));
6355 omp_firstprivatize_variable (ctx, TYPE_SIZE_UNIT (type));
6356 lang_hooks.types.omp_firstprivatize_type_sizes (ctx, type);
6359 /* Add an entry for DECL in the OMP context CTX with FLAGS. */
6361 static void
6362 omp_add_variable (struct gimplify_omp_ctx *ctx, tree decl, unsigned int flags)
6364 splay_tree_node n;
6365 unsigned int nflags;
6366 tree t;
6368 if (error_operand_p (decl) || ctx->region_type == ORT_NONE)
6369 return;
6371 /* Never elide decls whose type has TREE_ADDRESSABLE set. This means
6372 there are constructors involved somewhere. */
6373 if (TREE_ADDRESSABLE (TREE_TYPE (decl))
6374 || TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (decl)))
6375 flags |= GOVD_SEEN;
6377 n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
6378 if (n != NULL && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
6380 /* We shouldn't be re-adding the decl with the same data
6381 sharing class. */
6382 gcc_assert ((n->value & GOVD_DATA_SHARE_CLASS & flags) == 0);
6383 nflags = n->value | flags;
6384 /* The only combination of data sharing classes we should see is
6385 FIRSTPRIVATE and LASTPRIVATE. However, OpenACC permits
6386 reduction variables to be used in data sharing clauses. */
6387 gcc_assert ((ctx->region_type & ORT_ACC) != 0
6388 || ((nflags & GOVD_DATA_SHARE_CLASS)
6389 == (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE))
6390 || (flags & GOVD_DATA_SHARE_CLASS) == 0);
6391 n->value = nflags;
6392 return;
6395 /* When adding a variable-sized variable, we have to handle all sorts
6396 of additional bits of data: the pointer replacement variable, and
6397 the parameters of the type. */
6398 if (DECL_SIZE (decl) && TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
6400 /* Add the pointer replacement variable as PRIVATE if the variable
6401 replacement is private, else FIRSTPRIVATE since we'll need the
6402 address of the original variable either for SHARED, or for the
6403 copy into or out of the context. */
6404 if (!(flags & GOVD_LOCAL))
6406 if (flags & GOVD_MAP)
6407 nflags = GOVD_MAP | GOVD_MAP_TO_ONLY | GOVD_EXPLICIT;
6408 else if (flags & GOVD_PRIVATE)
6409 nflags = GOVD_PRIVATE;
6410 else if ((ctx->region_type & (ORT_TARGET | ORT_TARGET_DATA)) != 0
6411 && (flags & GOVD_FIRSTPRIVATE))
6412 nflags = GOVD_PRIVATE | GOVD_EXPLICIT;
6413 else
6414 nflags = GOVD_FIRSTPRIVATE;
6415 nflags |= flags & GOVD_SEEN;
6416 t = DECL_VALUE_EXPR (decl);
6417 gcc_assert (TREE_CODE (t) == INDIRECT_REF);
6418 t = TREE_OPERAND (t, 0);
6419 gcc_assert (DECL_P (t));
6420 omp_add_variable (ctx, t, nflags);
6423 /* Add all of the variable and type parameters (which should have
6424 been gimplified to a formal temporary) as FIRSTPRIVATE. */
6425 omp_firstprivatize_variable (ctx, DECL_SIZE_UNIT (decl));
6426 omp_firstprivatize_variable (ctx, DECL_SIZE (decl));
6427 omp_firstprivatize_type_sizes (ctx, TREE_TYPE (decl));
6429 /* The variable-sized variable itself is never SHARED, only some form
6430 of PRIVATE. The sharing would take place via the pointer variable
6431 which we remapped above. */
6432 if (flags & GOVD_SHARED)
6433 flags = GOVD_PRIVATE | GOVD_DEBUG_PRIVATE
6434 | (flags & (GOVD_SEEN | GOVD_EXPLICIT));
6436 /* We're going to make use of the TYPE_SIZE_UNIT at least in the
6437 alloca statement we generate for the variable, so make sure it
6438 is available. This isn't automatically needed for the SHARED
6439 case, since we won't be allocating local storage then.
6440 For local variables TYPE_SIZE_UNIT might not be gimplified yet,
6441 in this case omp_notice_variable will be called later
6442 on when it is gimplified. */
6443 else if (! (flags & (GOVD_LOCAL | GOVD_MAP))
6444 && DECL_P (TYPE_SIZE_UNIT (TREE_TYPE (decl))))
6445 omp_notice_variable (ctx, TYPE_SIZE_UNIT (TREE_TYPE (decl)), true);
6447 else if ((flags & (GOVD_MAP | GOVD_LOCAL)) == 0
6448 && lang_hooks.decls.omp_privatize_by_reference (decl))
6450 omp_firstprivatize_type_sizes (ctx, TREE_TYPE (decl));
6452 /* Similar to the direct variable sized case above, we'll need the
6453 size of references being privatized. */
6454 if ((flags & GOVD_SHARED) == 0)
6456 t = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl)));
6457 if (DECL_P (t))
6458 omp_notice_variable (ctx, t, true);
6462 if (n != NULL)
6463 n->value |= flags;
6464 else
6465 splay_tree_insert (ctx->variables, (splay_tree_key)decl, flags);
6467 /* For reductions clauses in OpenACC loop directives, by default create a
6468 copy clause on the enclosing parallel construct for carrying back the
6469 results. */
6470 if (ctx->region_type == ORT_ACC && (flags & GOVD_REDUCTION))
6472 struct gimplify_omp_ctx *outer_ctx = ctx->outer_context;
6473 while (outer_ctx)
6475 n = splay_tree_lookup (outer_ctx->variables, (splay_tree_key)decl);
6476 if (n != NULL)
6478 /* Ignore local variables and explicitly declared clauses. */
6479 if (n->value & (GOVD_LOCAL | GOVD_EXPLICIT))
6480 break;
6481 else if (outer_ctx->region_type == ORT_ACC_KERNELS)
6483 /* According to the OpenACC spec, such a reduction variable
6484 should already have a copy map on a kernels construct,
6485 verify that here. */
6486 gcc_assert (!(n->value & GOVD_FIRSTPRIVATE)
6487 && (n->value & GOVD_MAP));
6489 else if (outer_ctx->region_type == ORT_ACC_PARALLEL)
6491 /* Remove firstprivate and make it a copy map. */
6492 n->value &= ~GOVD_FIRSTPRIVATE;
6493 n->value |= GOVD_MAP;
6496 else if (outer_ctx->region_type == ORT_ACC_PARALLEL)
6498 splay_tree_insert (outer_ctx->variables, (splay_tree_key)decl,
6499 GOVD_MAP | GOVD_SEEN);
6500 break;
6502 outer_ctx = outer_ctx->outer_context;
6507 /* Notice a threadprivate variable DECL used in OMP context CTX.
6508 This just prints out diagnostics about threadprivate variable uses
6509 in untied tasks. If DECL2 is non-NULL, prevent this warning
6510 on that variable. */
6512 static bool
6513 omp_notice_threadprivate_variable (struct gimplify_omp_ctx *ctx, tree decl,
6514 tree decl2)
6516 splay_tree_node n;
6517 struct gimplify_omp_ctx *octx;
6519 for (octx = ctx; octx; octx = octx->outer_context)
6520 if ((octx->region_type & ORT_TARGET) != 0)
6522 n = splay_tree_lookup (octx->variables, (splay_tree_key)decl);
6523 if (n == NULL)
6525 error ("threadprivate variable %qE used in target region",
6526 DECL_NAME (decl));
6527 error_at (octx->location, "enclosing target region");
6528 splay_tree_insert (octx->variables, (splay_tree_key)decl, 0);
6530 if (decl2)
6531 splay_tree_insert (octx->variables, (splay_tree_key)decl2, 0);
6534 if (ctx->region_type != ORT_UNTIED_TASK)
6535 return false;
6536 n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
6537 if (n == NULL)
6539 error ("threadprivate variable %qE used in untied task",
6540 DECL_NAME (decl));
6541 error_at (ctx->location, "enclosing task");
6542 splay_tree_insert (ctx->variables, (splay_tree_key)decl, 0);
6544 if (decl2)
6545 splay_tree_insert (ctx->variables, (splay_tree_key)decl2, 0);
6546 return false;
6549 /* Return true if global var DECL is device resident. */
6551 static bool
6552 device_resident_p (tree decl)
6554 tree attr = lookup_attribute ("oacc declare target", DECL_ATTRIBUTES (decl));
6556 if (!attr)
6557 return false;
6559 for (tree t = TREE_VALUE (attr); t; t = TREE_PURPOSE (t))
6561 tree c = TREE_VALUE (t);
6562 if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_DEVICE_RESIDENT)
6563 return true;
6566 return false;
6569 /* Determine outer default flags for DECL mentioned in an OMP region
6570 but not declared in an enclosing clause.
6572 ??? Some compiler-generated variables (like SAVE_EXPRs) could be
6573 remapped firstprivate instead of shared. To some extent this is
6574 addressed in omp_firstprivatize_type_sizes, but not
6575 effectively. */
6577 static unsigned
6578 omp_default_clause (struct gimplify_omp_ctx *ctx, tree decl,
6579 bool in_code, unsigned flags)
6581 enum omp_clause_default_kind default_kind = ctx->default_kind;
6582 enum omp_clause_default_kind kind;
6584 kind = lang_hooks.decls.omp_predetermined_sharing (decl);
6585 if (kind != OMP_CLAUSE_DEFAULT_UNSPECIFIED)
6586 default_kind = kind;
6588 switch (default_kind)
6590 case OMP_CLAUSE_DEFAULT_NONE:
6592 const char *rtype;
6594 if (ctx->region_type & ORT_PARALLEL)
6595 rtype = "parallel";
6596 else if (ctx->region_type & ORT_TASK)
6597 rtype = "task";
6598 else if (ctx->region_type & ORT_TEAMS)
6599 rtype = "teams";
6600 else
6601 gcc_unreachable ();
6603 error ("%qE not specified in enclosing %s",
6604 DECL_NAME (lang_hooks.decls.omp_report_decl (decl)), rtype);
6605 error_at (ctx->location, "enclosing %s", rtype);
6607 /* FALLTHRU */
6608 case OMP_CLAUSE_DEFAULT_SHARED:
6609 flags |= GOVD_SHARED;
6610 break;
6611 case OMP_CLAUSE_DEFAULT_PRIVATE:
6612 flags |= GOVD_PRIVATE;
6613 break;
6614 case OMP_CLAUSE_DEFAULT_FIRSTPRIVATE:
6615 flags |= GOVD_FIRSTPRIVATE;
6616 break;
6617 case OMP_CLAUSE_DEFAULT_UNSPECIFIED:
6618 /* decl will be either GOVD_FIRSTPRIVATE or GOVD_SHARED. */
6619 gcc_assert ((ctx->region_type & ORT_TASK) != 0);
6620 if (struct gimplify_omp_ctx *octx = ctx->outer_context)
6622 omp_notice_variable (octx, decl, in_code);
6623 for (; octx; octx = octx->outer_context)
6625 splay_tree_node n2;
6627 n2 = splay_tree_lookup (octx->variables, (splay_tree_key) decl);
6628 if ((octx->region_type & (ORT_TARGET_DATA | ORT_TARGET)) != 0
6629 && (n2 == NULL || (n2->value & GOVD_DATA_SHARE_CLASS) == 0))
6630 continue;
6631 if (n2 && (n2->value & GOVD_DATA_SHARE_CLASS) != GOVD_SHARED)
6633 flags |= GOVD_FIRSTPRIVATE;
6634 goto found_outer;
6636 if ((octx->region_type & (ORT_PARALLEL | ORT_TEAMS)) != 0)
6638 flags |= GOVD_SHARED;
6639 goto found_outer;
6644 if (TREE_CODE (decl) == PARM_DECL
6645 || (!is_global_var (decl)
6646 && DECL_CONTEXT (decl) == current_function_decl))
6647 flags |= GOVD_FIRSTPRIVATE;
6648 else
6649 flags |= GOVD_SHARED;
6650 found_outer:
6651 break;
6653 default:
6654 gcc_unreachable ();
6657 return flags;
6661 /* Determine outer default flags for DECL mentioned in an OACC region
6662 but not declared in an enclosing clause. */
6664 static unsigned
6665 oacc_default_clause (struct gimplify_omp_ctx *ctx, tree decl, unsigned flags)
6667 const char *rkind;
6668 bool on_device = false;
6669 tree type = TREE_TYPE (decl);
6671 if (lang_hooks.decls.omp_privatize_by_reference (decl))
6672 type = TREE_TYPE (type);
6674 if ((ctx->region_type & (ORT_ACC_PARALLEL | ORT_ACC_KERNELS)) != 0
6675 && is_global_var (decl)
6676 && device_resident_p (decl))
6678 on_device = true;
6679 flags |= GOVD_MAP_TO_ONLY;
6682 switch (ctx->region_type)
6684 default:
6685 gcc_unreachable ();
6687 case ORT_ACC_KERNELS:
6688 /* Scalars are default 'copy' under kernels, non-scalars are default
6689 'present_or_copy'. */
6690 flags |= GOVD_MAP;
6691 if (!AGGREGATE_TYPE_P (type))
6692 flags |= GOVD_MAP_FORCE;
6694 rkind = "kernels";
6695 break;
6697 case ORT_ACC_PARALLEL:
6699 if (on_device || AGGREGATE_TYPE_P (type))
6700 /* Aggregates default to 'present_or_copy'. */
6701 flags |= GOVD_MAP;
6702 else
6703 /* Scalars default to 'firstprivate'. */
6704 flags |= GOVD_FIRSTPRIVATE;
6705 rkind = "parallel";
6707 break;
6710 if (DECL_ARTIFICIAL (decl))
6711 ; /* We can get compiler-generated decls, and should not complain
6712 about them. */
6713 else if (ctx->default_kind == OMP_CLAUSE_DEFAULT_NONE)
6715 error ("%qE not specified in enclosing OpenACC %qs construct",
6716 DECL_NAME (lang_hooks.decls.omp_report_decl (decl)), rkind);
6717 inform (ctx->location, "enclosing OpenACC %qs construct", rkind);
6719 else
6720 gcc_checking_assert (ctx->default_kind == OMP_CLAUSE_DEFAULT_SHARED);
6722 return flags;
6725 /* Record the fact that DECL was used within the OMP context CTX.
6726 IN_CODE is true when real code uses DECL, and false when we should
6727 merely emit default(none) errors. Return true if DECL is going to
6728 be remapped and thus DECL shouldn't be gimplified into its
6729 DECL_VALUE_EXPR (if any). */
6731 static bool
6732 omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
6734 splay_tree_node n;
6735 unsigned flags = in_code ? GOVD_SEEN : 0;
6736 bool ret = false, shared;
6738 if (error_operand_p (decl))
6739 return false;
6741 if (ctx->region_type == ORT_NONE)
6742 return lang_hooks.decls.omp_disregard_value_expr (decl, false);
6744 if (is_global_var (decl))
6746 /* Threadprivate variables are predetermined. */
6747 if (DECL_THREAD_LOCAL_P (decl))
6748 return omp_notice_threadprivate_variable (ctx, decl, NULL_TREE);
6750 if (DECL_HAS_VALUE_EXPR_P (decl))
6752 tree value = get_base_address (DECL_VALUE_EXPR (decl));
6754 if (value && DECL_P (value) && DECL_THREAD_LOCAL_P (value))
6755 return omp_notice_threadprivate_variable (ctx, decl, value);
6758 if (gimplify_omp_ctxp->outer_context == NULL
6759 && VAR_P (decl)
6760 && get_oacc_fn_attrib (current_function_decl))
6762 location_t loc = DECL_SOURCE_LOCATION (decl);
6764 if (lookup_attribute ("omp declare target link",
6765 DECL_ATTRIBUTES (decl)))
6767 error_at (loc,
6768 "%qE with %<link%> clause used in %<routine%> function",
6769 DECL_NAME (decl));
6770 return false;
6772 else if (!lookup_attribute ("omp declare target",
6773 DECL_ATTRIBUTES (decl)))
6775 error_at (loc,
6776 "%qE requires a %<declare%> directive for use "
6777 "in a %<routine%> function", DECL_NAME (decl));
6778 return false;
6783 n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
6784 if ((ctx->region_type & ORT_TARGET) != 0)
6786 ret = lang_hooks.decls.omp_disregard_value_expr (decl, true);
6787 if (n == NULL)
6789 unsigned nflags = flags;
6790 if (ctx->target_map_pointers_as_0len_arrays
6791 || ctx->target_map_scalars_firstprivate)
6793 bool is_declare_target = false;
6794 bool is_scalar = false;
6795 if (is_global_var (decl)
6796 && varpool_node::get_create (decl)->offloadable)
6798 struct gimplify_omp_ctx *octx;
6799 for (octx = ctx->outer_context;
6800 octx; octx = octx->outer_context)
6802 n = splay_tree_lookup (octx->variables,
6803 (splay_tree_key)decl);
6804 if (n
6805 && (n->value & GOVD_DATA_SHARE_CLASS) != GOVD_SHARED
6806 && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
6807 break;
6809 is_declare_target = octx == NULL;
6811 if (!is_declare_target && ctx->target_map_scalars_firstprivate)
6813 tree type = TREE_TYPE (decl);
6814 if (TREE_CODE (type) == REFERENCE_TYPE)
6815 type = TREE_TYPE (type);
6816 if (TREE_CODE (type) == COMPLEX_TYPE)
6817 type = TREE_TYPE (type);
6818 if (INTEGRAL_TYPE_P (type)
6819 || SCALAR_FLOAT_TYPE_P (type)
6820 || TREE_CODE (type) == POINTER_TYPE)
6821 is_scalar = true;
6823 if (is_declare_target)
6825 else if (ctx->target_map_pointers_as_0len_arrays
6826 && (TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE
6827 || (TREE_CODE (TREE_TYPE (decl)) == REFERENCE_TYPE
6828 && TREE_CODE (TREE_TYPE (TREE_TYPE (decl)))
6829 == POINTER_TYPE)))
6830 nflags |= GOVD_MAP | GOVD_MAP_0LEN_ARRAY;
6831 else if (is_scalar)
6832 nflags |= GOVD_FIRSTPRIVATE;
6835 struct gimplify_omp_ctx *octx = ctx->outer_context;
6836 if ((ctx->region_type & ORT_ACC) && octx)
6838 /* Look in outer OpenACC contexts, to see if there's a
6839 data attribute for this variable. */
6840 omp_notice_variable (octx, decl, in_code);
6842 for (; octx; octx = octx->outer_context)
6844 if (!(octx->region_type & (ORT_TARGET_DATA | ORT_TARGET)))
6845 break;
6846 splay_tree_node n2
6847 = splay_tree_lookup (octx->variables,
6848 (splay_tree_key) decl);
6849 if (n2)
6851 if (octx->region_type == ORT_ACC_HOST_DATA)
6852 error ("variable %qE declared in enclosing "
6853 "%<host_data%> region", DECL_NAME (decl));
6854 nflags |= GOVD_MAP;
6855 if (octx->region_type == ORT_ACC_DATA
6856 && (n2->value & GOVD_MAP_0LEN_ARRAY))
6857 nflags |= GOVD_MAP_0LEN_ARRAY;
6858 goto found_outer;
6864 tree type = TREE_TYPE (decl);
6866 if (nflags == flags
6867 && gimplify_omp_ctxp->target_firstprivatize_array_bases
6868 && lang_hooks.decls.omp_privatize_by_reference (decl))
6869 type = TREE_TYPE (type);
6870 if (nflags == flags
6871 && !lang_hooks.types.omp_mappable_type (type))
6873 error ("%qD referenced in target region does not have "
6874 "a mappable type", decl);
6875 nflags |= GOVD_MAP | GOVD_EXPLICIT;
6877 else if (nflags == flags)
6879 if ((ctx->region_type & ORT_ACC) != 0)
6880 nflags = oacc_default_clause (ctx, decl, flags);
6881 else
6882 nflags |= GOVD_MAP;
6885 found_outer:
6886 omp_add_variable (ctx, decl, nflags);
6888 else
6890 /* If nothing changed, there's nothing left to do. */
6891 if ((n->value & flags) == flags)
6892 return ret;
6893 flags |= n->value;
6894 n->value = flags;
6896 goto do_outer;
6899 if (n == NULL)
6901 if (ctx->region_type == ORT_WORKSHARE
6902 || ctx->region_type == ORT_SIMD
6903 || ctx->region_type == ORT_ACC
6904 || (ctx->region_type & ORT_TARGET_DATA) != 0)
6905 goto do_outer;
6907 flags = omp_default_clause (ctx, decl, in_code, flags);
6909 if ((flags & GOVD_PRIVATE)
6910 && lang_hooks.decls.omp_private_outer_ref (decl))
6911 flags |= GOVD_PRIVATE_OUTER_REF;
6913 omp_add_variable (ctx, decl, flags);
6915 shared = (flags & GOVD_SHARED) != 0;
6916 ret = lang_hooks.decls.omp_disregard_value_expr (decl, shared);
6917 goto do_outer;
6920 if ((n->value & (GOVD_SEEN | GOVD_LOCAL)) == 0
6921 && (flags & (GOVD_SEEN | GOVD_LOCAL)) == GOVD_SEEN
6922 && DECL_SIZE (decl))
6924 if (TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
6926 splay_tree_node n2;
6927 tree t = DECL_VALUE_EXPR (decl);
6928 gcc_assert (TREE_CODE (t) == INDIRECT_REF);
6929 t = TREE_OPERAND (t, 0);
6930 gcc_assert (DECL_P (t));
6931 n2 = splay_tree_lookup (ctx->variables, (splay_tree_key) t);
6932 n2->value |= GOVD_SEEN;
6934 else if (lang_hooks.decls.omp_privatize_by_reference (decl)
6935 && TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl)))
6936 && (TREE_CODE (TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl))))
6937 != INTEGER_CST))
6939 splay_tree_node n2;
6940 tree t = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl)));
6941 gcc_assert (DECL_P (t));
6942 n2 = splay_tree_lookup (ctx->variables, (splay_tree_key) t);
6943 if (n2)
6944 n2->value |= GOVD_SEEN;
6948 shared = ((flags | n->value) & GOVD_SHARED) != 0;
6949 ret = lang_hooks.decls.omp_disregard_value_expr (decl, shared);
6951 /* If nothing changed, there's nothing left to do. */
6952 if ((n->value & flags) == flags)
6953 return ret;
6954 flags |= n->value;
6955 n->value = flags;
6957 do_outer:
6958 /* If the variable is private in the current context, then we don't
6959 need to propagate anything to an outer context. */
6960 if ((flags & GOVD_PRIVATE) && !(flags & GOVD_PRIVATE_OUTER_REF))
6961 return ret;
6962 if ((flags & (GOVD_LINEAR | GOVD_LINEAR_LASTPRIVATE_NO_OUTER))
6963 == (GOVD_LINEAR | GOVD_LINEAR_LASTPRIVATE_NO_OUTER))
6964 return ret;
6965 if ((flags & (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE
6966 | GOVD_LINEAR_LASTPRIVATE_NO_OUTER))
6967 == (GOVD_LASTPRIVATE | GOVD_LINEAR_LASTPRIVATE_NO_OUTER))
6968 return ret;
6969 if (ctx->outer_context
6970 && omp_notice_variable (ctx->outer_context, decl, in_code))
6971 return true;
6972 return ret;
6975 /* Verify that DECL is private within CTX. If there's specific information
6976 to the contrary in the innermost scope, generate an error. */
6978 static bool
6979 omp_is_private (struct gimplify_omp_ctx *ctx, tree decl, int simd)
6981 splay_tree_node n;
6983 n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
6984 if (n != NULL)
6986 if (n->value & GOVD_SHARED)
6988 if (ctx == gimplify_omp_ctxp)
6990 if (simd)
6991 error ("iteration variable %qE is predetermined linear",
6992 DECL_NAME (decl));
6993 else
6994 error ("iteration variable %qE should be private",
6995 DECL_NAME (decl));
6996 n->value = GOVD_PRIVATE;
6997 return true;
6999 else
7000 return false;
7002 else if ((n->value & GOVD_EXPLICIT) != 0
7003 && (ctx == gimplify_omp_ctxp
7004 || (ctx->region_type == ORT_COMBINED_PARALLEL
7005 && gimplify_omp_ctxp->outer_context == ctx)))
7007 if ((n->value & GOVD_FIRSTPRIVATE) != 0)
7008 error ("iteration variable %qE should not be firstprivate",
7009 DECL_NAME (decl));
7010 else if ((n->value & GOVD_REDUCTION) != 0)
7011 error ("iteration variable %qE should not be reduction",
7012 DECL_NAME (decl));
7013 else if (simd == 0 && (n->value & GOVD_LINEAR) != 0)
7014 error ("iteration variable %qE should not be linear",
7015 DECL_NAME (decl));
7016 else if (simd == 1 && (n->value & GOVD_LASTPRIVATE) != 0)
7017 error ("iteration variable %qE should not be lastprivate",
7018 DECL_NAME (decl));
7019 else if (simd && (n->value & GOVD_PRIVATE) != 0)
7020 error ("iteration variable %qE should not be private",
7021 DECL_NAME (decl));
7022 else if (simd == 2 && (n->value & GOVD_LINEAR) != 0)
7023 error ("iteration variable %qE is predetermined linear",
7024 DECL_NAME (decl));
7026 return (ctx == gimplify_omp_ctxp
7027 || (ctx->region_type == ORT_COMBINED_PARALLEL
7028 && gimplify_omp_ctxp->outer_context == ctx));
7031 if (ctx->region_type != ORT_WORKSHARE
7032 && ctx->region_type != ORT_SIMD
7033 && ctx->region_type != ORT_ACC)
7034 return false;
7035 else if (ctx->outer_context)
7036 return omp_is_private (ctx->outer_context, decl, simd);
7037 return false;
7040 /* Return true if DECL is private within a parallel region
7041 that binds to the current construct's context or in parallel
7042 region's REDUCTION clause. */
7044 static bool
7045 omp_check_private (struct gimplify_omp_ctx *ctx, tree decl, bool copyprivate)
7047 splay_tree_node n;
7051 ctx = ctx->outer_context;
7052 if (ctx == NULL)
7054 if (is_global_var (decl))
7055 return false;
7057 /* References might be private, but might be shared too,
7058 when checking for copyprivate, assume they might be
7059 private, otherwise assume they might be shared. */
7060 if (copyprivate)
7061 return true;
7063 if (lang_hooks.decls.omp_privatize_by_reference (decl))
7064 return false;
7066 /* Treat C++ privatized non-static data members outside
7067 of the privatization the same. */
7068 if (omp_member_access_dummy_var (decl))
7069 return false;
7071 return true;
7074 n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
7076 if ((ctx->region_type & (ORT_TARGET | ORT_TARGET_DATA)) != 0
7077 && (n == NULL || (n->value & GOVD_DATA_SHARE_CLASS) == 0))
7078 continue;
7080 if (n != NULL)
7082 if ((n->value & GOVD_LOCAL) != 0
7083 && omp_member_access_dummy_var (decl))
7084 return false;
7085 return (n->value & GOVD_SHARED) == 0;
7088 while (ctx->region_type == ORT_WORKSHARE
7089 || ctx->region_type == ORT_SIMD
7090 || ctx->region_type == ORT_ACC);
7091 return false;
7094 /* Return true if the CTX is combined with distribute and thus
7095 lastprivate can't be supported. */
7097 static bool
7098 omp_no_lastprivate (struct gimplify_omp_ctx *ctx)
7102 if (ctx->outer_context == NULL)
7103 return false;
7104 ctx = ctx->outer_context;
7105 switch (ctx->region_type)
7107 case ORT_WORKSHARE:
7108 if (!ctx->combined_loop)
7109 return false;
7110 if (ctx->distribute)
7111 return lang_GNU_Fortran ();
7112 break;
7113 case ORT_COMBINED_PARALLEL:
7114 break;
7115 case ORT_COMBINED_TEAMS:
7116 return lang_GNU_Fortran ();
7117 default:
7118 return false;
7121 while (1);
7124 /* Callback for walk_tree to find a DECL_EXPR for the given DECL. */
7126 static tree
7127 find_decl_expr (tree *tp, int *walk_subtrees, void *data)
7129 tree t = *tp;
7131 /* If this node has been visited, unmark it and keep looking. */
7132 if (TREE_CODE (t) == DECL_EXPR && DECL_EXPR_DECL (t) == (tree) data)
7133 return t;
7135 if (IS_TYPE_OR_DECL_P (t))
7136 *walk_subtrees = 0;
7137 return NULL_TREE;
7140 /* Scan the OMP clauses in *LIST_P, installing mappings into a new
7141 and previous omp contexts. */
7143 static void
7144 gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
7145 enum omp_region_type region_type,
7146 enum tree_code code)
7148 struct gimplify_omp_ctx *ctx, *outer_ctx;
7149 tree c;
7150 hash_map<tree, tree> *struct_map_to_clause = NULL;
7151 tree *prev_list_p = NULL;
7153 ctx = new_omp_context (region_type);
7154 outer_ctx = ctx->outer_context;
7155 if (code == OMP_TARGET && !lang_GNU_Fortran ())
7157 ctx->target_map_pointers_as_0len_arrays = true;
7158 /* FIXME: For Fortran we want to set this too, when
7159 the Fortran FE is updated to OpenMP 4.5. */
7160 ctx->target_map_scalars_firstprivate = true;
7162 if (!lang_GNU_Fortran ())
7163 switch (code)
7165 case OMP_TARGET:
7166 case OMP_TARGET_DATA:
7167 case OMP_TARGET_ENTER_DATA:
7168 case OMP_TARGET_EXIT_DATA:
7169 case OACC_HOST_DATA:
7170 ctx->target_firstprivatize_array_bases = true;
7171 default:
7172 break;
7175 while ((c = *list_p) != NULL)
7177 bool remove = false;
7178 bool notice_outer = true;
7179 const char *check_non_private = NULL;
7180 unsigned int flags;
7181 tree decl;
7183 switch (OMP_CLAUSE_CODE (c))
7185 case OMP_CLAUSE_PRIVATE:
7186 flags = GOVD_PRIVATE | GOVD_EXPLICIT;
7187 if (lang_hooks.decls.omp_private_outer_ref (OMP_CLAUSE_DECL (c)))
7189 flags |= GOVD_PRIVATE_OUTER_REF;
7190 OMP_CLAUSE_PRIVATE_OUTER_REF (c) = 1;
7192 else
7193 notice_outer = false;
7194 goto do_add;
7195 case OMP_CLAUSE_SHARED:
7196 flags = GOVD_SHARED | GOVD_EXPLICIT;
7197 goto do_add;
7198 case OMP_CLAUSE_FIRSTPRIVATE:
7199 flags = GOVD_FIRSTPRIVATE | GOVD_EXPLICIT;
7200 check_non_private = "firstprivate";
7201 goto do_add;
7202 case OMP_CLAUSE_LASTPRIVATE:
7203 flags = GOVD_LASTPRIVATE | GOVD_SEEN | GOVD_EXPLICIT;
7204 check_non_private = "lastprivate";
7205 decl = OMP_CLAUSE_DECL (c);
7206 if (omp_no_lastprivate (ctx))
7208 notice_outer = false;
7209 flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
7211 else if (error_operand_p (decl))
7212 goto do_add;
7213 else if (outer_ctx
7214 && (outer_ctx->region_type == ORT_COMBINED_PARALLEL
7215 || outer_ctx->region_type == ORT_COMBINED_TEAMS)
7216 && splay_tree_lookup (outer_ctx->variables,
7217 (splay_tree_key) decl) == NULL)
7219 omp_add_variable (outer_ctx, decl, GOVD_SHARED | GOVD_SEEN);
7220 if (outer_ctx->outer_context)
7221 omp_notice_variable (outer_ctx->outer_context, decl, true);
7223 else if (outer_ctx
7224 && (outer_ctx->region_type & ORT_TASK) != 0
7225 && outer_ctx->combined_loop
7226 && splay_tree_lookup (outer_ctx->variables,
7227 (splay_tree_key) decl) == NULL)
7229 omp_add_variable (outer_ctx, decl, GOVD_LASTPRIVATE | GOVD_SEEN);
7230 if (outer_ctx->outer_context)
7231 omp_notice_variable (outer_ctx->outer_context, decl, true);
7233 else if (outer_ctx
7234 && (outer_ctx->region_type == ORT_WORKSHARE
7235 || outer_ctx->region_type == ORT_ACC)
7236 && outer_ctx->combined_loop
7237 && splay_tree_lookup (outer_ctx->variables,
7238 (splay_tree_key) decl) == NULL
7239 && !omp_check_private (outer_ctx, decl, false))
7241 omp_add_variable (outer_ctx, decl, GOVD_LASTPRIVATE | GOVD_SEEN);
7242 if (outer_ctx->outer_context
7243 && (outer_ctx->outer_context->region_type
7244 == ORT_COMBINED_PARALLEL)
7245 && splay_tree_lookup (outer_ctx->outer_context->variables,
7246 (splay_tree_key) decl) == NULL)
7248 struct gimplify_omp_ctx *octx = outer_ctx->outer_context;
7249 omp_add_variable (octx, decl, GOVD_SHARED | GOVD_SEEN);
7250 if (octx->outer_context)
7251 omp_notice_variable (octx->outer_context, decl, true);
7253 else if (outer_ctx->outer_context)
7254 omp_notice_variable (outer_ctx->outer_context, decl, true);
7256 goto do_add;
7257 case OMP_CLAUSE_REDUCTION:
7258 flags = GOVD_REDUCTION | GOVD_SEEN | GOVD_EXPLICIT;
7259 /* OpenACC permits reductions on private variables. */
7260 if (!(region_type & ORT_ACC))
7261 check_non_private = "reduction";
7262 decl = OMP_CLAUSE_DECL (c);
7263 if (TREE_CODE (decl) == MEM_REF)
7265 tree type = TREE_TYPE (decl);
7266 if (gimplify_expr (&TYPE_MAX_VALUE (TYPE_DOMAIN (type)), pre_p,
7267 NULL, is_gimple_val, fb_rvalue, false)
7268 == GS_ERROR)
7270 remove = true;
7271 break;
7273 tree v = TYPE_MAX_VALUE (TYPE_DOMAIN (type));
7274 if (DECL_P (v))
7276 omp_firstprivatize_variable (ctx, v);
7277 omp_notice_variable (ctx, v, true);
7279 decl = TREE_OPERAND (decl, 0);
7280 if (TREE_CODE (decl) == POINTER_PLUS_EXPR)
7282 if (gimplify_expr (&TREE_OPERAND (decl, 1), pre_p,
7283 NULL, is_gimple_val, fb_rvalue, false)
7284 == GS_ERROR)
7286 remove = true;
7287 break;
7289 v = TREE_OPERAND (decl, 1);
7290 if (DECL_P (v))
7292 omp_firstprivatize_variable (ctx, v);
7293 omp_notice_variable (ctx, v, true);
7295 decl = TREE_OPERAND (decl, 0);
7297 if (TREE_CODE (decl) == ADDR_EXPR
7298 || TREE_CODE (decl) == INDIRECT_REF)
7299 decl = TREE_OPERAND (decl, 0);
7301 goto do_add_decl;
7302 case OMP_CLAUSE_LINEAR:
7303 if (gimplify_expr (&OMP_CLAUSE_LINEAR_STEP (c), pre_p, NULL,
7304 is_gimple_val, fb_rvalue) == GS_ERROR)
7306 remove = true;
7307 break;
7309 else
7311 if (code == OMP_SIMD
7312 && !OMP_CLAUSE_LINEAR_NO_COPYIN (c))
7314 struct gimplify_omp_ctx *octx = outer_ctx;
7315 if (octx
7316 && octx->region_type == ORT_WORKSHARE
7317 && octx->combined_loop
7318 && !octx->distribute)
7320 if (octx->outer_context
7321 && (octx->outer_context->region_type
7322 == ORT_COMBINED_PARALLEL))
7323 octx = octx->outer_context->outer_context;
7324 else
7325 octx = octx->outer_context;
7327 if (octx
7328 && octx->region_type == ORT_WORKSHARE
7329 && octx->combined_loop
7330 && octx->distribute
7331 && !lang_GNU_Fortran ())
7333 error_at (OMP_CLAUSE_LOCATION (c),
7334 "%<linear%> clause for variable other than "
7335 "loop iterator specified on construct "
7336 "combined with %<distribute%>");
7337 remove = true;
7338 break;
7341 /* For combined #pragma omp parallel for simd, need to put
7342 lastprivate and perhaps firstprivate too on the
7343 parallel. Similarly for #pragma omp for simd. */
7344 struct gimplify_omp_ctx *octx = outer_ctx;
7345 decl = NULL_TREE;
7346 if (omp_no_lastprivate (ctx))
7347 OMP_CLAUSE_LINEAR_NO_COPYOUT (c) = 1;
7350 if (OMP_CLAUSE_LINEAR_NO_COPYIN (c)
7351 && OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
7352 break;
7353 decl = OMP_CLAUSE_DECL (c);
7354 if (error_operand_p (decl))
7356 decl = NULL_TREE;
7357 break;
7359 flags = GOVD_SEEN;
7360 if (!OMP_CLAUSE_LINEAR_NO_COPYIN (c))
7361 flags |= GOVD_FIRSTPRIVATE;
7362 if (!OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
7363 flags |= GOVD_LASTPRIVATE;
7364 if (octx
7365 && octx->region_type == ORT_WORKSHARE
7366 && octx->combined_loop)
7368 if (octx->outer_context
7369 && (octx->outer_context->region_type
7370 == ORT_COMBINED_PARALLEL))
7371 octx = octx->outer_context;
7372 else if (omp_check_private (octx, decl, false))
7373 break;
7375 else if (octx
7376 && (octx->region_type & ORT_TASK) != 0
7377 && octx->combined_loop)
7379 else if (octx
7380 && octx->region_type == ORT_COMBINED_PARALLEL
7381 && ctx->region_type == ORT_WORKSHARE
7382 && octx == outer_ctx)
7383 flags = GOVD_SEEN | GOVD_SHARED;
7384 else if (octx
7385 && octx->region_type == ORT_COMBINED_TEAMS)
7386 flags = GOVD_SEEN | GOVD_SHARED;
7387 else if (octx
7388 && octx->region_type == ORT_COMBINED_TARGET)
7390 flags &= ~GOVD_LASTPRIVATE;
7391 if (flags == GOVD_SEEN)
7392 break;
7394 else
7395 break;
7396 splay_tree_node on
7397 = splay_tree_lookup (octx->variables,
7398 (splay_tree_key) decl);
7399 if (on && (on->value & GOVD_DATA_SHARE_CLASS) != 0)
7401 octx = NULL;
7402 break;
7404 omp_add_variable (octx, decl, flags);
7405 if (octx->outer_context == NULL)
7406 break;
7407 octx = octx->outer_context;
7409 while (1);
7410 if (octx
7411 && decl
7412 && (!OMP_CLAUSE_LINEAR_NO_COPYIN (c)
7413 || !OMP_CLAUSE_LINEAR_NO_COPYOUT (c)))
7414 omp_notice_variable (octx, decl, true);
7416 flags = GOVD_LINEAR | GOVD_EXPLICIT;
7417 if (OMP_CLAUSE_LINEAR_NO_COPYIN (c)
7418 && OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
7420 notice_outer = false;
7421 flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
7423 goto do_add;
7425 case OMP_CLAUSE_MAP:
7426 decl = OMP_CLAUSE_DECL (c);
7427 if (error_operand_p (decl))
7428 remove = true;
7429 switch (code)
7431 case OMP_TARGET:
7432 break;
7433 case OACC_DATA:
7434 if (TREE_CODE (TREE_TYPE (decl)) != ARRAY_TYPE)
7435 break;
7436 /* FALLTHRU */
7437 case OMP_TARGET_DATA:
7438 case OMP_TARGET_ENTER_DATA:
7439 case OMP_TARGET_EXIT_DATA:
7440 case OACC_ENTER_DATA:
7441 case OACC_EXIT_DATA:
7442 case OACC_HOST_DATA:
7443 if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER
7444 || (OMP_CLAUSE_MAP_KIND (c)
7445 == GOMP_MAP_FIRSTPRIVATE_REFERENCE))
7446 /* For target {,enter ,exit }data only the array slice is
7447 mapped, but not the pointer to it. */
7448 remove = true;
7449 break;
7450 default:
7451 break;
7453 if (remove)
7454 break;
7455 if (DECL_P (decl) && outer_ctx && (region_type & ORT_ACC))
7457 struct gimplify_omp_ctx *octx;
7458 for (octx = outer_ctx; octx; octx = octx->outer_context)
7460 if (octx->region_type != ORT_ACC_HOST_DATA)
7461 break;
7462 splay_tree_node n2
7463 = splay_tree_lookup (octx->variables,
7464 (splay_tree_key) decl);
7465 if (n2)
7466 error_at (OMP_CLAUSE_LOCATION (c), "variable %qE "
7467 "declared in enclosing %<host_data%> region",
7468 DECL_NAME (decl));
7471 if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
7472 OMP_CLAUSE_SIZE (c) = DECL_P (decl) ? DECL_SIZE_UNIT (decl)
7473 : TYPE_SIZE_UNIT (TREE_TYPE (decl));
7474 if (gimplify_expr (&OMP_CLAUSE_SIZE (c), pre_p,
7475 NULL, is_gimple_val, fb_rvalue) == GS_ERROR)
7477 remove = true;
7478 break;
7480 else if ((OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER
7481 || (OMP_CLAUSE_MAP_KIND (c)
7482 == GOMP_MAP_FIRSTPRIVATE_REFERENCE))
7483 && TREE_CODE (OMP_CLAUSE_SIZE (c)) != INTEGER_CST)
7485 OMP_CLAUSE_SIZE (c)
7486 = get_initialized_tmp_var (OMP_CLAUSE_SIZE (c), pre_p, NULL,
7487 false);
7488 omp_add_variable (ctx, OMP_CLAUSE_SIZE (c),
7489 GOVD_FIRSTPRIVATE | GOVD_SEEN);
7491 if (!DECL_P (decl))
7493 tree d = decl, *pd;
7494 if (TREE_CODE (d) == ARRAY_REF)
7496 while (TREE_CODE (d) == ARRAY_REF)
7497 d = TREE_OPERAND (d, 0);
7498 if (TREE_CODE (d) == COMPONENT_REF
7499 && TREE_CODE (TREE_TYPE (d)) == ARRAY_TYPE)
7500 decl = d;
7502 pd = &OMP_CLAUSE_DECL (c);
7503 if (d == decl
7504 && TREE_CODE (decl) == INDIRECT_REF
7505 && TREE_CODE (TREE_OPERAND (decl, 0)) == COMPONENT_REF
7506 && (TREE_CODE (TREE_TYPE (TREE_OPERAND (decl, 0)))
7507 == REFERENCE_TYPE))
7509 pd = &TREE_OPERAND (decl, 0);
7510 decl = TREE_OPERAND (decl, 0);
7512 if (TREE_CODE (decl) == COMPONENT_REF)
7514 while (TREE_CODE (decl) == COMPONENT_REF)
7515 decl = TREE_OPERAND (decl, 0);
7516 if (TREE_CODE (decl) == INDIRECT_REF
7517 && DECL_P (TREE_OPERAND (decl, 0))
7518 && (TREE_CODE (TREE_TYPE (TREE_OPERAND (decl, 0)))
7519 == REFERENCE_TYPE))
7520 decl = TREE_OPERAND (decl, 0);
7522 if (gimplify_expr (pd, pre_p, NULL, is_gimple_lvalue, fb_lvalue)
7523 == GS_ERROR)
7525 remove = true;
7526 break;
7528 if (DECL_P (decl))
7530 if (error_operand_p (decl))
7532 remove = true;
7533 break;
7536 tree stype = TREE_TYPE (decl);
7537 if (TREE_CODE (stype) == REFERENCE_TYPE)
7538 stype = TREE_TYPE (stype);
7539 if (TYPE_SIZE_UNIT (stype) == NULL
7540 || TREE_CODE (TYPE_SIZE_UNIT (stype)) != INTEGER_CST)
7542 error_at (OMP_CLAUSE_LOCATION (c),
7543 "mapping field %qE of variable length "
7544 "structure", OMP_CLAUSE_DECL (c));
7545 remove = true;
7546 break;
7549 if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_POINTER)
7551 /* Error recovery. */
7552 if (prev_list_p == NULL)
7554 remove = true;
7555 break;
7557 if (OMP_CLAUSE_CHAIN (*prev_list_p) != c)
7559 tree ch = OMP_CLAUSE_CHAIN (*prev_list_p);
7560 if (ch == NULL_TREE || OMP_CLAUSE_CHAIN (ch) != c)
7562 remove = true;
7563 break;
7568 tree offset;
7569 HOST_WIDE_INT bitsize, bitpos;
7570 machine_mode mode;
7571 int unsignedp, reversep, volatilep = 0;
7572 tree base = OMP_CLAUSE_DECL (c);
7573 while (TREE_CODE (base) == ARRAY_REF)
7574 base = TREE_OPERAND (base, 0);
7575 if (TREE_CODE (base) == INDIRECT_REF)
7576 base = TREE_OPERAND (base, 0);
7577 base = get_inner_reference (base, &bitsize, &bitpos, &offset,
7578 &mode, &unsignedp, &reversep,
7579 &volatilep);
7580 tree orig_base = base;
7581 if ((TREE_CODE (base) == INDIRECT_REF
7582 || (TREE_CODE (base) == MEM_REF
7583 && integer_zerop (TREE_OPERAND (base, 1))))
7584 && DECL_P (TREE_OPERAND (base, 0))
7585 && (TREE_CODE (TREE_TYPE (TREE_OPERAND (base, 0)))
7586 == REFERENCE_TYPE))
7587 base = TREE_OPERAND (base, 0);
7588 gcc_assert (base == decl
7589 && (offset == NULL_TREE
7590 || TREE_CODE (offset) == INTEGER_CST));
7592 splay_tree_node n
7593 = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
7594 bool ptr = (OMP_CLAUSE_MAP_KIND (c)
7595 == GOMP_MAP_ALWAYS_POINTER);
7596 if (n == NULL || (n->value & GOVD_MAP) == 0)
7598 tree l = build_omp_clause (OMP_CLAUSE_LOCATION (c),
7599 OMP_CLAUSE_MAP);
7600 OMP_CLAUSE_SET_MAP_KIND (l, GOMP_MAP_STRUCT);
7601 if (orig_base != base)
7602 OMP_CLAUSE_DECL (l) = unshare_expr (orig_base);
7603 else
7604 OMP_CLAUSE_DECL (l) = decl;
7605 OMP_CLAUSE_SIZE (l) = size_int (1);
7606 if (struct_map_to_clause == NULL)
7607 struct_map_to_clause = new hash_map<tree, tree>;
7608 struct_map_to_clause->put (decl, l);
7609 if (ptr)
7611 enum gomp_map_kind mkind
7612 = code == OMP_TARGET_EXIT_DATA
7613 ? GOMP_MAP_RELEASE : GOMP_MAP_ALLOC;
7614 tree c2 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
7615 OMP_CLAUSE_MAP);
7616 OMP_CLAUSE_SET_MAP_KIND (c2, mkind);
7617 OMP_CLAUSE_DECL (c2)
7618 = unshare_expr (OMP_CLAUSE_DECL (c));
7619 OMP_CLAUSE_CHAIN (c2) = *prev_list_p;
7620 OMP_CLAUSE_SIZE (c2)
7621 = TYPE_SIZE_UNIT (ptr_type_node);
7622 OMP_CLAUSE_CHAIN (l) = c2;
7623 if (OMP_CLAUSE_CHAIN (*prev_list_p) != c)
7625 tree c4 = OMP_CLAUSE_CHAIN (*prev_list_p);
7626 tree c3
7627 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
7628 OMP_CLAUSE_MAP);
7629 OMP_CLAUSE_SET_MAP_KIND (c3, mkind);
7630 OMP_CLAUSE_DECL (c3)
7631 = unshare_expr (OMP_CLAUSE_DECL (c4));
7632 OMP_CLAUSE_SIZE (c3)
7633 = TYPE_SIZE_UNIT (ptr_type_node);
7634 OMP_CLAUSE_CHAIN (c3) = *prev_list_p;
7635 OMP_CLAUSE_CHAIN (c2) = c3;
7637 *prev_list_p = l;
7638 prev_list_p = NULL;
7640 else
7642 OMP_CLAUSE_CHAIN (l) = c;
7643 *list_p = l;
7644 list_p = &OMP_CLAUSE_CHAIN (l);
7646 if (orig_base != base && code == OMP_TARGET)
7648 tree c2 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
7649 OMP_CLAUSE_MAP);
7650 enum gomp_map_kind mkind
7651 = GOMP_MAP_FIRSTPRIVATE_REFERENCE;
7652 OMP_CLAUSE_SET_MAP_KIND (c2, mkind);
7653 OMP_CLAUSE_DECL (c2) = decl;
7654 OMP_CLAUSE_SIZE (c2) = size_zero_node;
7655 OMP_CLAUSE_CHAIN (c2) = OMP_CLAUSE_CHAIN (l);
7656 OMP_CLAUSE_CHAIN (l) = c2;
7658 flags = GOVD_MAP | GOVD_EXPLICIT;
7659 if (GOMP_MAP_ALWAYS_P (OMP_CLAUSE_MAP_KIND (c)) || ptr)
7660 flags |= GOVD_SEEN;
7661 goto do_add_decl;
7663 else
7665 tree *osc = struct_map_to_clause->get (decl);
7666 tree *sc = NULL, *scp = NULL;
7667 if (GOMP_MAP_ALWAYS_P (OMP_CLAUSE_MAP_KIND (c)) || ptr)
7668 n->value |= GOVD_SEEN;
7669 offset_int o1, o2;
7670 if (offset)
7671 o1 = wi::to_offset (offset);
7672 else
7673 o1 = 0;
7674 if (bitpos)
7675 o1 = o1 + bitpos / BITS_PER_UNIT;
7676 sc = &OMP_CLAUSE_CHAIN (*osc);
7677 if (*sc != c
7678 && (OMP_CLAUSE_MAP_KIND (*sc)
7679 == GOMP_MAP_FIRSTPRIVATE_REFERENCE))
7680 sc = &OMP_CLAUSE_CHAIN (*sc);
7681 for (; *sc != c; sc = &OMP_CLAUSE_CHAIN (*sc))
7682 if (ptr && sc == prev_list_p)
7683 break;
7684 else if (TREE_CODE (OMP_CLAUSE_DECL (*sc))
7685 != COMPONENT_REF
7686 && (TREE_CODE (OMP_CLAUSE_DECL (*sc))
7687 != INDIRECT_REF)
7688 && (TREE_CODE (OMP_CLAUSE_DECL (*sc))
7689 != ARRAY_REF))
7690 break;
7691 else
7693 tree offset2;
7694 HOST_WIDE_INT bitsize2, bitpos2;
7695 base = OMP_CLAUSE_DECL (*sc);
7696 if (TREE_CODE (base) == ARRAY_REF)
7698 while (TREE_CODE (base) == ARRAY_REF)
7699 base = TREE_OPERAND (base, 0);
7700 if (TREE_CODE (base) != COMPONENT_REF
7701 || (TREE_CODE (TREE_TYPE (base))
7702 != ARRAY_TYPE))
7703 break;
7705 else if (TREE_CODE (base) == INDIRECT_REF
7706 && (TREE_CODE (TREE_OPERAND (base, 0))
7707 == COMPONENT_REF)
7708 && (TREE_CODE (TREE_TYPE
7709 (TREE_OPERAND (base, 0)))
7710 == REFERENCE_TYPE))
7711 base = TREE_OPERAND (base, 0);
7712 base = get_inner_reference (base, &bitsize2,
7713 &bitpos2, &offset2,
7714 &mode, &unsignedp,
7715 &reversep, &volatilep);
7716 if ((TREE_CODE (base) == INDIRECT_REF
7717 || (TREE_CODE (base) == MEM_REF
7718 && integer_zerop (TREE_OPERAND (base,
7719 1))))
7720 && DECL_P (TREE_OPERAND (base, 0))
7721 && (TREE_CODE (TREE_TYPE (TREE_OPERAND (base,
7722 0)))
7723 == REFERENCE_TYPE))
7724 base = TREE_OPERAND (base, 0);
7725 if (base != decl)
7726 break;
7727 if (scp)
7728 continue;
7729 gcc_assert (offset == NULL_TREE
7730 || TREE_CODE (offset) == INTEGER_CST);
7731 tree d1 = OMP_CLAUSE_DECL (*sc);
7732 tree d2 = OMP_CLAUSE_DECL (c);
7733 while (TREE_CODE (d1) == ARRAY_REF)
7734 d1 = TREE_OPERAND (d1, 0);
7735 while (TREE_CODE (d2) == ARRAY_REF)
7736 d2 = TREE_OPERAND (d2, 0);
7737 if (TREE_CODE (d1) == INDIRECT_REF)
7738 d1 = TREE_OPERAND (d1, 0);
7739 if (TREE_CODE (d2) == INDIRECT_REF)
7740 d2 = TREE_OPERAND (d2, 0);
7741 while (TREE_CODE (d1) == COMPONENT_REF)
7742 if (TREE_CODE (d2) == COMPONENT_REF
7743 && TREE_OPERAND (d1, 1)
7744 == TREE_OPERAND (d2, 1))
7746 d1 = TREE_OPERAND (d1, 0);
7747 d2 = TREE_OPERAND (d2, 0);
7749 else
7750 break;
7751 if (d1 == d2)
7753 error_at (OMP_CLAUSE_LOCATION (c),
7754 "%qE appears more than once in map "
7755 "clauses", OMP_CLAUSE_DECL (c));
7756 remove = true;
7757 break;
7759 if (offset2)
7760 o2 = wi::to_offset (offset2);
7761 else
7762 o2 = 0;
7763 if (bitpos2)
7764 o2 = o2 + bitpos2 / BITS_PER_UNIT;
7765 if (wi::ltu_p (o1, o2)
7766 || (wi::eq_p (o1, o2) && bitpos < bitpos2))
7768 if (ptr)
7769 scp = sc;
7770 else
7771 break;
7774 if (remove)
7775 break;
7776 OMP_CLAUSE_SIZE (*osc)
7777 = size_binop (PLUS_EXPR, OMP_CLAUSE_SIZE (*osc),
7778 size_one_node);
7779 if (ptr)
7781 tree c2 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
7782 OMP_CLAUSE_MAP);
7783 tree cl = NULL_TREE;
7784 enum gomp_map_kind mkind
7785 = code == OMP_TARGET_EXIT_DATA
7786 ? GOMP_MAP_RELEASE : GOMP_MAP_ALLOC;
7787 OMP_CLAUSE_SET_MAP_KIND (c2, mkind);
7788 OMP_CLAUSE_DECL (c2)
7789 = unshare_expr (OMP_CLAUSE_DECL (c));
7790 OMP_CLAUSE_CHAIN (c2) = scp ? *scp : *prev_list_p;
7791 OMP_CLAUSE_SIZE (c2)
7792 = TYPE_SIZE_UNIT (ptr_type_node);
7793 cl = scp ? *prev_list_p : c2;
7794 if (OMP_CLAUSE_CHAIN (*prev_list_p) != c)
7796 tree c4 = OMP_CLAUSE_CHAIN (*prev_list_p);
7797 tree c3
7798 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
7799 OMP_CLAUSE_MAP);
7800 OMP_CLAUSE_SET_MAP_KIND (c3, mkind);
7801 OMP_CLAUSE_DECL (c3)
7802 = unshare_expr (OMP_CLAUSE_DECL (c4));
7803 OMP_CLAUSE_SIZE (c3)
7804 = TYPE_SIZE_UNIT (ptr_type_node);
7805 OMP_CLAUSE_CHAIN (c3) = *prev_list_p;
7806 if (!scp)
7807 OMP_CLAUSE_CHAIN (c2) = c3;
7808 else
7809 cl = c3;
7811 if (scp)
7812 *scp = c2;
7813 if (sc == prev_list_p)
7815 *sc = cl;
7816 prev_list_p = NULL;
7818 else
7820 *prev_list_p = OMP_CLAUSE_CHAIN (c);
7821 list_p = prev_list_p;
7822 prev_list_p = NULL;
7823 OMP_CLAUSE_CHAIN (c) = *sc;
7824 *sc = cl;
7825 continue;
7828 else if (*sc != c)
7830 *list_p = OMP_CLAUSE_CHAIN (c);
7831 OMP_CLAUSE_CHAIN (c) = *sc;
7832 *sc = c;
7833 continue;
7837 if (!remove
7838 && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ALWAYS_POINTER
7839 && OMP_CLAUSE_CHAIN (c)
7840 && OMP_CLAUSE_CODE (OMP_CLAUSE_CHAIN (c)) == OMP_CLAUSE_MAP
7841 && (OMP_CLAUSE_MAP_KIND (OMP_CLAUSE_CHAIN (c))
7842 == GOMP_MAP_ALWAYS_POINTER))
7843 prev_list_p = list_p;
7844 break;
7846 flags = GOVD_MAP | GOVD_EXPLICIT;
7847 if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_TO
7848 || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_TOFROM)
7849 flags |= GOVD_MAP_ALWAYS_TO;
7850 goto do_add;
7852 case OMP_CLAUSE_DEPEND:
7853 if (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK
7854 || OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SOURCE)
7856 /* Nothing to do. OMP_CLAUSE_DECL will be lowered in
7857 omp-low.c. */
7858 break;
7860 if (TREE_CODE (OMP_CLAUSE_DECL (c)) == COMPOUND_EXPR)
7862 gimplify_expr (&TREE_OPERAND (OMP_CLAUSE_DECL (c), 0), pre_p,
7863 NULL, is_gimple_val, fb_rvalue);
7864 OMP_CLAUSE_DECL (c) = TREE_OPERAND (OMP_CLAUSE_DECL (c), 1);
7866 if (error_operand_p (OMP_CLAUSE_DECL (c)))
7868 remove = true;
7869 break;
7871 OMP_CLAUSE_DECL (c) = build_fold_addr_expr (OMP_CLAUSE_DECL (c));
7872 if (gimplify_expr (&OMP_CLAUSE_DECL (c), pre_p, NULL,
7873 is_gimple_val, fb_rvalue) == GS_ERROR)
7875 remove = true;
7876 break;
7878 break;
7880 case OMP_CLAUSE_TO:
7881 case OMP_CLAUSE_FROM:
7882 case OMP_CLAUSE__CACHE_:
7883 decl = OMP_CLAUSE_DECL (c);
7884 if (error_operand_p (decl))
7886 remove = true;
7887 break;
7889 if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
7890 OMP_CLAUSE_SIZE (c) = DECL_P (decl) ? DECL_SIZE_UNIT (decl)
7891 : TYPE_SIZE_UNIT (TREE_TYPE (decl));
7892 if (gimplify_expr (&OMP_CLAUSE_SIZE (c), pre_p,
7893 NULL, is_gimple_val, fb_rvalue) == GS_ERROR)
7895 remove = true;
7896 break;
7898 if (!DECL_P (decl))
7900 if (gimplify_expr (&OMP_CLAUSE_DECL (c), pre_p,
7901 NULL, is_gimple_lvalue, fb_lvalue)
7902 == GS_ERROR)
7904 remove = true;
7905 break;
7907 break;
7909 goto do_notice;
7911 case OMP_CLAUSE_USE_DEVICE_PTR:
7912 flags = GOVD_FIRSTPRIVATE | GOVD_EXPLICIT;
7913 goto do_add;
7914 case OMP_CLAUSE_IS_DEVICE_PTR:
7915 flags = GOVD_FIRSTPRIVATE | GOVD_EXPLICIT;
7916 goto do_add;
7918 do_add:
7919 decl = OMP_CLAUSE_DECL (c);
7920 do_add_decl:
7921 if (error_operand_p (decl))
7923 remove = true;
7924 break;
7926 if (DECL_NAME (decl) == NULL_TREE && (flags & GOVD_SHARED) == 0)
7928 tree t = omp_member_access_dummy_var (decl);
7929 if (t)
7931 tree v = DECL_VALUE_EXPR (decl);
7932 DECL_NAME (decl) = DECL_NAME (TREE_OPERAND (v, 1));
7933 if (outer_ctx)
7934 omp_notice_variable (outer_ctx, t, true);
7937 if (code == OACC_DATA
7938 && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
7939 && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER)
7940 flags |= GOVD_MAP_0LEN_ARRAY;
7941 omp_add_variable (ctx, decl, flags);
7942 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
7943 && OMP_CLAUSE_REDUCTION_PLACEHOLDER (c))
7945 omp_add_variable (ctx, OMP_CLAUSE_REDUCTION_PLACEHOLDER (c),
7946 GOVD_LOCAL | GOVD_SEEN);
7947 if (OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (c)
7948 && walk_tree (&OMP_CLAUSE_REDUCTION_INIT (c),
7949 find_decl_expr,
7950 OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (c),
7951 NULL) == NULL_TREE)
7952 omp_add_variable (ctx,
7953 OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (c),
7954 GOVD_LOCAL | GOVD_SEEN);
7955 gimplify_omp_ctxp = ctx;
7956 push_gimplify_context ();
7958 OMP_CLAUSE_REDUCTION_GIMPLE_INIT (c) = NULL;
7959 OMP_CLAUSE_REDUCTION_GIMPLE_MERGE (c) = NULL;
7961 gimplify_and_add (OMP_CLAUSE_REDUCTION_INIT (c),
7962 &OMP_CLAUSE_REDUCTION_GIMPLE_INIT (c));
7963 pop_gimplify_context
7964 (gimple_seq_first_stmt (OMP_CLAUSE_REDUCTION_GIMPLE_INIT (c)));
7965 push_gimplify_context ();
7966 gimplify_and_add (OMP_CLAUSE_REDUCTION_MERGE (c),
7967 &OMP_CLAUSE_REDUCTION_GIMPLE_MERGE (c));
7968 pop_gimplify_context
7969 (gimple_seq_first_stmt (OMP_CLAUSE_REDUCTION_GIMPLE_MERGE (c)));
7970 OMP_CLAUSE_REDUCTION_INIT (c) = NULL_TREE;
7971 OMP_CLAUSE_REDUCTION_MERGE (c) = NULL_TREE;
7973 gimplify_omp_ctxp = outer_ctx;
7975 else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
7976 && OMP_CLAUSE_LASTPRIVATE_STMT (c))
7978 gimplify_omp_ctxp = ctx;
7979 push_gimplify_context ();
7980 if (TREE_CODE (OMP_CLAUSE_LASTPRIVATE_STMT (c)) != BIND_EXPR)
7982 tree bind = build3 (BIND_EXPR, void_type_node, NULL,
7983 NULL, NULL);
7984 TREE_SIDE_EFFECTS (bind) = 1;
7985 BIND_EXPR_BODY (bind) = OMP_CLAUSE_LASTPRIVATE_STMT (c);
7986 OMP_CLAUSE_LASTPRIVATE_STMT (c) = bind;
7988 gimplify_and_add (OMP_CLAUSE_LASTPRIVATE_STMT (c),
7989 &OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (c));
7990 pop_gimplify_context
7991 (gimple_seq_first_stmt (OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (c)));
7992 OMP_CLAUSE_LASTPRIVATE_STMT (c) = NULL_TREE;
7994 gimplify_omp_ctxp = outer_ctx;
7996 else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
7997 && OMP_CLAUSE_LINEAR_STMT (c))
7999 gimplify_omp_ctxp = ctx;
8000 push_gimplify_context ();
8001 if (TREE_CODE (OMP_CLAUSE_LINEAR_STMT (c)) != BIND_EXPR)
8003 tree bind = build3 (BIND_EXPR, void_type_node, NULL,
8004 NULL, NULL);
8005 TREE_SIDE_EFFECTS (bind) = 1;
8006 BIND_EXPR_BODY (bind) = OMP_CLAUSE_LINEAR_STMT (c);
8007 OMP_CLAUSE_LINEAR_STMT (c) = bind;
8009 gimplify_and_add (OMP_CLAUSE_LINEAR_STMT (c),
8010 &OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c));
8011 pop_gimplify_context
8012 (gimple_seq_first_stmt (OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c)));
8013 OMP_CLAUSE_LINEAR_STMT (c) = NULL_TREE;
8015 gimplify_omp_ctxp = outer_ctx;
8017 if (notice_outer)
8018 goto do_notice;
8019 break;
8021 case OMP_CLAUSE_COPYIN:
8022 case OMP_CLAUSE_COPYPRIVATE:
8023 decl = OMP_CLAUSE_DECL (c);
8024 if (error_operand_p (decl))
8026 remove = true;
8027 break;
8029 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_COPYPRIVATE
8030 && !remove
8031 && !omp_check_private (ctx, decl, true))
8033 remove = true;
8034 if (is_global_var (decl))
8036 if (DECL_THREAD_LOCAL_P (decl))
8037 remove = false;
8038 else if (DECL_HAS_VALUE_EXPR_P (decl))
8040 tree value = get_base_address (DECL_VALUE_EXPR (decl));
8042 if (value
8043 && DECL_P (value)
8044 && DECL_THREAD_LOCAL_P (value))
8045 remove = false;
8048 if (remove)
8049 error_at (OMP_CLAUSE_LOCATION (c),
8050 "copyprivate variable %qE is not threadprivate"
8051 " or private in outer context", DECL_NAME (decl));
8053 do_notice:
8054 if (outer_ctx)
8055 omp_notice_variable (outer_ctx, decl, true);
8056 if (check_non_private
8057 && region_type == ORT_WORKSHARE
8058 && (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_REDUCTION
8059 || decl == OMP_CLAUSE_DECL (c)
8060 || (TREE_CODE (OMP_CLAUSE_DECL (c)) == MEM_REF
8061 && (TREE_CODE (TREE_OPERAND (OMP_CLAUSE_DECL (c), 0))
8062 == ADDR_EXPR
8063 || (TREE_CODE (TREE_OPERAND (OMP_CLAUSE_DECL (c), 0))
8064 == POINTER_PLUS_EXPR
8065 && (TREE_CODE (TREE_OPERAND (TREE_OPERAND
8066 (OMP_CLAUSE_DECL (c), 0), 0))
8067 == ADDR_EXPR)))))
8068 && omp_check_private (ctx, decl, false))
8070 error ("%s variable %qE is private in outer context",
8071 check_non_private, DECL_NAME (decl));
8072 remove = true;
8074 break;
8076 case OMP_CLAUSE_IF:
8077 if (OMP_CLAUSE_IF_MODIFIER (c) != ERROR_MARK
8078 && OMP_CLAUSE_IF_MODIFIER (c) != code)
8080 const char *p[2];
8081 for (int i = 0; i < 2; i++)
8082 switch (i ? OMP_CLAUSE_IF_MODIFIER (c) : code)
8084 case OMP_PARALLEL: p[i] = "parallel"; break;
8085 case OMP_TASK: p[i] = "task"; break;
8086 case OMP_TASKLOOP: p[i] = "taskloop"; break;
8087 case OMP_TARGET_DATA: p[i] = "target data"; break;
8088 case OMP_TARGET: p[i] = "target"; break;
8089 case OMP_TARGET_UPDATE: p[i] = "target update"; break;
8090 case OMP_TARGET_ENTER_DATA:
8091 p[i] = "target enter data"; break;
8092 case OMP_TARGET_EXIT_DATA: p[i] = "target exit data"; break;
8093 default: gcc_unreachable ();
8095 error_at (OMP_CLAUSE_LOCATION (c),
8096 "expected %qs %<if%> clause modifier rather than %qs",
8097 p[0], p[1]);
8098 remove = true;
8100 /* Fall through. */
8102 case OMP_CLAUSE_FINAL:
8103 OMP_CLAUSE_OPERAND (c, 0)
8104 = gimple_boolify (OMP_CLAUSE_OPERAND (c, 0));
8105 /* Fall through. */
8107 case OMP_CLAUSE_SCHEDULE:
8108 case OMP_CLAUSE_NUM_THREADS:
8109 case OMP_CLAUSE_NUM_TEAMS:
8110 case OMP_CLAUSE_THREAD_LIMIT:
8111 case OMP_CLAUSE_DIST_SCHEDULE:
8112 case OMP_CLAUSE_DEVICE:
8113 case OMP_CLAUSE_PRIORITY:
8114 case OMP_CLAUSE_GRAINSIZE:
8115 case OMP_CLAUSE_NUM_TASKS:
8116 case OMP_CLAUSE_HINT:
8117 case OMP_CLAUSE__CILK_FOR_COUNT_:
8118 case OMP_CLAUSE_ASYNC:
8119 case OMP_CLAUSE_WAIT:
8120 case OMP_CLAUSE_NUM_GANGS:
8121 case OMP_CLAUSE_NUM_WORKERS:
8122 case OMP_CLAUSE_VECTOR_LENGTH:
8123 case OMP_CLAUSE_WORKER:
8124 case OMP_CLAUSE_VECTOR:
8125 if (gimplify_expr (&OMP_CLAUSE_OPERAND (c, 0), pre_p, NULL,
8126 is_gimple_val, fb_rvalue) == GS_ERROR)
8127 remove = true;
8128 break;
8130 case OMP_CLAUSE_GANG:
8131 if (gimplify_expr (&OMP_CLAUSE_OPERAND (c, 0), pre_p, NULL,
8132 is_gimple_val, fb_rvalue) == GS_ERROR)
8133 remove = true;
8134 if (gimplify_expr (&OMP_CLAUSE_OPERAND (c, 1), pre_p, NULL,
8135 is_gimple_val, fb_rvalue) == GS_ERROR)
8136 remove = true;
8137 break;
8139 case OMP_CLAUSE_TILE:
8140 for (tree list = OMP_CLAUSE_TILE_LIST (c); !remove && list;
8141 list = TREE_CHAIN (list))
8143 if (gimplify_expr (&TREE_VALUE (list), pre_p, NULL,
8144 is_gimple_val, fb_rvalue) == GS_ERROR)
8145 remove = true;
8147 break;
8149 case OMP_CLAUSE_NOWAIT:
8150 case OMP_CLAUSE_ORDERED:
8151 case OMP_CLAUSE_UNTIED:
8152 case OMP_CLAUSE_COLLAPSE:
8153 case OMP_CLAUSE_AUTO:
8154 case OMP_CLAUSE_SEQ:
8155 case OMP_CLAUSE_INDEPENDENT:
8156 case OMP_CLAUSE_MERGEABLE:
8157 case OMP_CLAUSE_PROC_BIND:
8158 case OMP_CLAUSE_SAFELEN:
8159 case OMP_CLAUSE_SIMDLEN:
8160 case OMP_CLAUSE_NOGROUP:
8161 case OMP_CLAUSE_THREADS:
8162 case OMP_CLAUSE_SIMD:
8163 break;
8165 case OMP_CLAUSE_DEFAULTMAP:
8166 ctx->target_map_scalars_firstprivate = false;
8167 break;
8169 case OMP_CLAUSE_ALIGNED:
8170 decl = OMP_CLAUSE_DECL (c);
8171 if (error_operand_p (decl))
8173 remove = true;
8174 break;
8176 if (gimplify_expr (&OMP_CLAUSE_ALIGNED_ALIGNMENT (c), pre_p, NULL,
8177 is_gimple_val, fb_rvalue) == GS_ERROR)
8179 remove = true;
8180 break;
8182 if (!is_global_var (decl)
8183 && TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE)
8184 omp_add_variable (ctx, decl, GOVD_ALIGNED);
8185 break;
8187 case OMP_CLAUSE_DEFAULT:
8188 ctx->default_kind = OMP_CLAUSE_DEFAULT_KIND (c);
8189 break;
8191 default:
8192 gcc_unreachable ();
8195 if (code == OACC_DATA
8196 && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
8197 && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER)
8198 remove = true;
8199 if (remove)
8200 *list_p = OMP_CLAUSE_CHAIN (c);
8201 else
8202 list_p = &OMP_CLAUSE_CHAIN (c);
8205 gimplify_omp_ctxp = ctx;
8206 if (struct_map_to_clause)
8207 delete struct_map_to_clause;
8210 /* Return true if DECL is a candidate for shared to firstprivate
8211 optimization. We only consider non-addressable scalars, not
8212 too big, and not references. */
8214 static bool
8215 omp_shared_to_firstprivate_optimizable_decl_p (tree decl)
8217 if (TREE_ADDRESSABLE (decl))
8218 return false;
8219 tree type = TREE_TYPE (decl);
8220 if (!is_gimple_reg_type (type)
8221 || TREE_CODE (type) == REFERENCE_TYPE
8222 || TREE_ADDRESSABLE (type))
8223 return false;
8224 /* Don't optimize too large decls, as each thread/task will have
8225 its own. */
8226 HOST_WIDE_INT len = int_size_in_bytes (type);
8227 if (len == -1 || len > 4 * POINTER_SIZE / BITS_PER_UNIT)
8228 return false;
8229 if (lang_hooks.decls.omp_privatize_by_reference (decl))
8230 return false;
8231 return true;
8234 /* Helper function of omp_find_stores_op and gimplify_adjust_omp_clauses*.
8235 For omp_shared_to_firstprivate_optimizable_decl_p decl mark it as
8236 GOVD_WRITTEN in outer contexts. */
8238 static void
8239 omp_mark_stores (struct gimplify_omp_ctx *ctx, tree decl)
8241 for (; ctx; ctx = ctx->outer_context)
8243 splay_tree_node n = splay_tree_lookup (ctx->variables,
8244 (splay_tree_key) decl);
8245 if (n == NULL)
8246 continue;
8247 else if (n->value & GOVD_SHARED)
8249 n->value |= GOVD_WRITTEN;
8250 return;
8252 else if (n->value & GOVD_DATA_SHARE_CLASS)
8253 return;
8257 /* Helper callback for walk_gimple_seq to discover possible stores
8258 to omp_shared_to_firstprivate_optimizable_decl_p decls and set
8259 GOVD_WRITTEN if they are GOVD_SHARED in some outer context
8260 for those. */
8262 static tree
8263 omp_find_stores_op (tree *tp, int *walk_subtrees, void *data)
8265 struct walk_stmt_info *wi = (struct walk_stmt_info *) data;
8267 *walk_subtrees = 0;
8268 if (!wi->is_lhs)
8269 return NULL_TREE;
8271 tree op = *tp;
8274 if (handled_component_p (op))
8275 op = TREE_OPERAND (op, 0);
8276 else if ((TREE_CODE (op) == MEM_REF || TREE_CODE (op) == TARGET_MEM_REF)
8277 && TREE_CODE (TREE_OPERAND (op, 0)) == ADDR_EXPR)
8278 op = TREE_OPERAND (TREE_OPERAND (op, 0), 0);
8279 else
8280 break;
8282 while (1);
8283 if (!DECL_P (op) || !omp_shared_to_firstprivate_optimizable_decl_p (op))
8284 return NULL_TREE;
8286 omp_mark_stores (gimplify_omp_ctxp, op);
8287 return NULL_TREE;
8290 /* Helper callback for walk_gimple_seq to discover possible stores
8291 to omp_shared_to_firstprivate_optimizable_decl_p decls and set
8292 GOVD_WRITTEN if they are GOVD_SHARED in some outer context
8293 for those. */
8295 static tree
8296 omp_find_stores_stmt (gimple_stmt_iterator *gsi_p,
8297 bool *handled_ops_p,
8298 struct walk_stmt_info *wi)
8300 gimple *stmt = gsi_stmt (*gsi_p);
8301 switch (gimple_code (stmt))
8303 /* Don't recurse on OpenMP constructs for which
8304 gimplify_adjust_omp_clauses already handled the bodies,
8305 except handle gimple_omp_for_pre_body. */
8306 case GIMPLE_OMP_FOR:
8307 *handled_ops_p = true;
8308 if (gimple_omp_for_pre_body (stmt))
8309 walk_gimple_seq (gimple_omp_for_pre_body (stmt),
8310 omp_find_stores_stmt, omp_find_stores_op, wi);
8311 break;
8312 case GIMPLE_OMP_PARALLEL:
8313 case GIMPLE_OMP_TASK:
8314 case GIMPLE_OMP_SECTIONS:
8315 case GIMPLE_OMP_SINGLE:
8316 case GIMPLE_OMP_TARGET:
8317 case GIMPLE_OMP_TEAMS:
8318 case GIMPLE_OMP_CRITICAL:
8319 *handled_ops_p = true;
8320 break;
8321 default:
8322 break;
8324 return NULL_TREE;
8327 struct gimplify_adjust_omp_clauses_data
8329 tree *list_p;
8330 gimple_seq *pre_p;
8333 /* For all variables that were not actually used within the context,
8334 remove PRIVATE, SHARED, and FIRSTPRIVATE clauses. */
8336 static int
8337 gimplify_adjust_omp_clauses_1 (splay_tree_node n, void *data)
8339 tree *list_p = ((struct gimplify_adjust_omp_clauses_data *) data)->list_p;
8340 gimple_seq *pre_p
8341 = ((struct gimplify_adjust_omp_clauses_data *) data)->pre_p;
8342 tree decl = (tree) n->key;
8343 unsigned flags = n->value;
8344 enum omp_clause_code code;
8345 tree clause;
8346 bool private_debug;
8348 if (flags & (GOVD_EXPLICIT | GOVD_LOCAL))
8349 return 0;
8350 if ((flags & GOVD_SEEN) == 0)
8351 return 0;
8352 if (flags & GOVD_DEBUG_PRIVATE)
8354 gcc_assert ((flags & GOVD_DATA_SHARE_CLASS) == GOVD_PRIVATE);
8355 private_debug = true;
8357 else if (flags & GOVD_MAP)
8358 private_debug = false;
8359 else
8360 private_debug
8361 = lang_hooks.decls.omp_private_debug_clause (decl,
8362 !!(flags & GOVD_SHARED));
8363 if (private_debug)
8364 code = OMP_CLAUSE_PRIVATE;
8365 else if (flags & GOVD_MAP)
8367 code = OMP_CLAUSE_MAP;
8368 if ((gimplify_omp_ctxp->region_type & ORT_ACC) == 0
8369 && TYPE_ATOMIC (strip_array_types (TREE_TYPE (decl))))
8371 error ("%<_Atomic%> %qD in implicit %<map%> clause", decl);
8372 return 0;
8375 else if (flags & GOVD_SHARED)
8377 if (is_global_var (decl))
8379 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp->outer_context;
8380 while (ctx != NULL)
8382 splay_tree_node on
8383 = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
8384 if (on && (on->value & (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE
8385 | GOVD_PRIVATE | GOVD_REDUCTION
8386 | GOVD_LINEAR | GOVD_MAP)) != 0)
8387 break;
8388 ctx = ctx->outer_context;
8390 if (ctx == NULL)
8391 return 0;
8393 code = OMP_CLAUSE_SHARED;
8395 else if (flags & GOVD_PRIVATE)
8396 code = OMP_CLAUSE_PRIVATE;
8397 else if (flags & GOVD_FIRSTPRIVATE)
8399 code = OMP_CLAUSE_FIRSTPRIVATE;
8400 if ((gimplify_omp_ctxp->region_type & ORT_TARGET)
8401 && (gimplify_omp_ctxp->region_type & ORT_ACC) == 0
8402 && TYPE_ATOMIC (strip_array_types (TREE_TYPE (decl))))
8404 error ("%<_Atomic%> %qD in implicit %<firstprivate%> clause on "
8405 "%<target%> construct", decl);
8406 return 0;
8409 else if (flags & GOVD_LASTPRIVATE)
8410 code = OMP_CLAUSE_LASTPRIVATE;
8411 else if (flags & GOVD_ALIGNED)
8412 return 0;
8413 else
8414 gcc_unreachable ();
8416 if (((flags & GOVD_LASTPRIVATE)
8417 || (code == OMP_CLAUSE_SHARED && (flags & GOVD_WRITTEN)))
8418 && omp_shared_to_firstprivate_optimizable_decl_p (decl))
8419 omp_mark_stores (gimplify_omp_ctxp->outer_context, decl);
8421 clause = build_omp_clause (input_location, code);
8422 OMP_CLAUSE_DECL (clause) = decl;
8423 OMP_CLAUSE_CHAIN (clause) = *list_p;
8424 if (private_debug)
8425 OMP_CLAUSE_PRIVATE_DEBUG (clause) = 1;
8426 else if (code == OMP_CLAUSE_PRIVATE && (flags & GOVD_PRIVATE_OUTER_REF))
8427 OMP_CLAUSE_PRIVATE_OUTER_REF (clause) = 1;
8428 else if (code == OMP_CLAUSE_SHARED
8429 && (flags & GOVD_WRITTEN) == 0
8430 && omp_shared_to_firstprivate_optimizable_decl_p (decl))
8431 OMP_CLAUSE_SHARED_READONLY (clause) = 1;
8432 else if (code == OMP_CLAUSE_FIRSTPRIVATE && (flags & GOVD_EXPLICIT) == 0)
8433 OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (clause) = 1;
8434 else if (code == OMP_CLAUSE_MAP && (flags & GOVD_MAP_0LEN_ARRAY) != 0)
8436 tree nc = build_omp_clause (input_location, OMP_CLAUSE_MAP);
8437 OMP_CLAUSE_DECL (nc) = decl;
8438 if (TREE_CODE (TREE_TYPE (decl)) == REFERENCE_TYPE
8439 && TREE_CODE (TREE_TYPE (TREE_TYPE (decl))) == POINTER_TYPE)
8440 OMP_CLAUSE_DECL (clause)
8441 = build_simple_mem_ref_loc (input_location, decl);
8442 OMP_CLAUSE_DECL (clause)
8443 = build2 (MEM_REF, char_type_node, OMP_CLAUSE_DECL (clause),
8444 build_int_cst (build_pointer_type (char_type_node), 0));
8445 OMP_CLAUSE_SIZE (clause) = size_zero_node;
8446 OMP_CLAUSE_SIZE (nc) = size_zero_node;
8447 OMP_CLAUSE_SET_MAP_KIND (clause, GOMP_MAP_ALLOC);
8448 OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (clause) = 1;
8449 OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_FIRSTPRIVATE_POINTER);
8450 OMP_CLAUSE_CHAIN (nc) = *list_p;
8451 OMP_CLAUSE_CHAIN (clause) = nc;
8452 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
8453 gimplify_omp_ctxp = ctx->outer_context;
8454 gimplify_expr (&TREE_OPERAND (OMP_CLAUSE_DECL (clause), 0),
8455 pre_p, NULL, is_gimple_val, fb_rvalue);
8456 gimplify_omp_ctxp = ctx;
8458 else if (code == OMP_CLAUSE_MAP)
8460 int kind = (flags & GOVD_MAP_TO_ONLY
8461 ? GOMP_MAP_TO
8462 : GOMP_MAP_TOFROM);
8463 if (flags & GOVD_MAP_FORCE)
8464 kind |= GOMP_MAP_FLAG_FORCE;
8465 OMP_CLAUSE_SET_MAP_KIND (clause, kind);
8466 if (DECL_SIZE (decl)
8467 && TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
8469 tree decl2 = DECL_VALUE_EXPR (decl);
8470 gcc_assert (TREE_CODE (decl2) == INDIRECT_REF);
8471 decl2 = TREE_OPERAND (decl2, 0);
8472 gcc_assert (DECL_P (decl2));
8473 tree mem = build_simple_mem_ref (decl2);
8474 OMP_CLAUSE_DECL (clause) = mem;
8475 OMP_CLAUSE_SIZE (clause) = TYPE_SIZE_UNIT (TREE_TYPE (decl));
8476 if (gimplify_omp_ctxp->outer_context)
8478 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp->outer_context;
8479 omp_notice_variable (ctx, decl2, true);
8480 omp_notice_variable (ctx, OMP_CLAUSE_SIZE (clause), true);
8482 tree nc = build_omp_clause (OMP_CLAUSE_LOCATION (clause),
8483 OMP_CLAUSE_MAP);
8484 OMP_CLAUSE_DECL (nc) = decl;
8485 OMP_CLAUSE_SIZE (nc) = size_zero_node;
8486 if (gimplify_omp_ctxp->target_firstprivatize_array_bases)
8487 OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_FIRSTPRIVATE_POINTER);
8488 else
8489 OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_POINTER);
8490 OMP_CLAUSE_CHAIN (nc) = OMP_CLAUSE_CHAIN (clause);
8491 OMP_CLAUSE_CHAIN (clause) = nc;
8493 else if (gimplify_omp_ctxp->target_firstprivatize_array_bases
8494 && lang_hooks.decls.omp_privatize_by_reference (decl))
8496 OMP_CLAUSE_DECL (clause) = build_simple_mem_ref (decl);
8497 OMP_CLAUSE_SIZE (clause)
8498 = unshare_expr (TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl))));
8499 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
8500 gimplify_omp_ctxp = ctx->outer_context;
8501 gimplify_expr (&OMP_CLAUSE_SIZE (clause),
8502 pre_p, NULL, is_gimple_val, fb_rvalue);
8503 gimplify_omp_ctxp = ctx;
8504 tree nc = build_omp_clause (OMP_CLAUSE_LOCATION (clause),
8505 OMP_CLAUSE_MAP);
8506 OMP_CLAUSE_DECL (nc) = decl;
8507 OMP_CLAUSE_SIZE (nc) = size_zero_node;
8508 OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_FIRSTPRIVATE_REFERENCE);
8509 OMP_CLAUSE_CHAIN (nc) = OMP_CLAUSE_CHAIN (clause);
8510 OMP_CLAUSE_CHAIN (clause) = nc;
8512 else
8513 OMP_CLAUSE_SIZE (clause) = DECL_SIZE_UNIT (decl);
8515 if (code == OMP_CLAUSE_FIRSTPRIVATE && (flags & GOVD_LASTPRIVATE) != 0)
8517 tree nc = build_omp_clause (input_location, OMP_CLAUSE_LASTPRIVATE);
8518 OMP_CLAUSE_DECL (nc) = decl;
8519 OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (nc) = 1;
8520 OMP_CLAUSE_CHAIN (nc) = *list_p;
8521 OMP_CLAUSE_CHAIN (clause) = nc;
8522 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
8523 gimplify_omp_ctxp = ctx->outer_context;
8524 lang_hooks.decls.omp_finish_clause (nc, pre_p);
8525 gimplify_omp_ctxp = ctx;
8527 *list_p = clause;
8528 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
8529 gimplify_omp_ctxp = ctx->outer_context;
8530 lang_hooks.decls.omp_finish_clause (clause, pre_p);
8531 gimplify_omp_ctxp = ctx;
8532 return 0;
8535 static void
8536 gimplify_adjust_omp_clauses (gimple_seq *pre_p, gimple_seq body, tree *list_p,
8537 enum tree_code code)
8539 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
8540 tree c, decl;
8542 if (body)
8544 struct gimplify_omp_ctx *octx;
8545 for (octx = ctx; octx; octx = octx->outer_context)
8546 if ((octx->region_type & (ORT_PARALLEL | ORT_TASK | ORT_TEAMS)) != 0)
8547 break;
8548 if (octx)
8550 struct walk_stmt_info wi;
8551 memset (&wi, 0, sizeof (wi));
8552 walk_gimple_seq (body, omp_find_stores_stmt,
8553 omp_find_stores_op, &wi);
8556 while ((c = *list_p) != NULL)
8558 splay_tree_node n;
8559 bool remove = false;
8561 switch (OMP_CLAUSE_CODE (c))
8563 case OMP_CLAUSE_FIRSTPRIVATE:
8564 if ((ctx->region_type & ORT_TARGET)
8565 && (ctx->region_type & ORT_ACC) == 0
8566 && TYPE_ATOMIC (strip_array_types
8567 (TREE_TYPE (OMP_CLAUSE_DECL (c)))))
8569 error_at (OMP_CLAUSE_LOCATION (c),
8570 "%<_Atomic%> %qD in %<firstprivate%> clause on "
8571 "%<target%> construct", OMP_CLAUSE_DECL (c));
8572 remove = true;
8573 break;
8575 /* FALLTHRU */
8576 case OMP_CLAUSE_PRIVATE:
8577 case OMP_CLAUSE_SHARED:
8578 case OMP_CLAUSE_LINEAR:
8579 decl = OMP_CLAUSE_DECL (c);
8580 n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
8581 remove = !(n->value & GOVD_SEEN);
8582 if (! remove)
8584 bool shared = OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED;
8585 if ((n->value & GOVD_DEBUG_PRIVATE)
8586 || lang_hooks.decls.omp_private_debug_clause (decl, shared))
8588 gcc_assert ((n->value & GOVD_DEBUG_PRIVATE) == 0
8589 || ((n->value & GOVD_DATA_SHARE_CLASS)
8590 == GOVD_PRIVATE));
8591 OMP_CLAUSE_SET_CODE (c, OMP_CLAUSE_PRIVATE);
8592 OMP_CLAUSE_PRIVATE_DEBUG (c) = 1;
8594 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED
8595 && (n->value & GOVD_WRITTEN) == 0
8596 && DECL_P (decl)
8597 && omp_shared_to_firstprivate_optimizable_decl_p (decl))
8598 OMP_CLAUSE_SHARED_READONLY (c) = 1;
8599 else if (DECL_P (decl)
8600 && ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED
8601 && (n->value & GOVD_WRITTEN) != 1)
8602 || (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
8603 && !OMP_CLAUSE_LINEAR_NO_COPYOUT (c)))
8604 && omp_shared_to_firstprivate_optimizable_decl_p (decl))
8605 omp_mark_stores (gimplify_omp_ctxp->outer_context, decl);
8607 break;
8609 case OMP_CLAUSE_LASTPRIVATE:
8610 /* Make sure OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE is set to
8611 accurately reflect the presence of a FIRSTPRIVATE clause. */
8612 decl = OMP_CLAUSE_DECL (c);
8613 n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
8614 OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c)
8615 = (n->value & GOVD_FIRSTPRIVATE) != 0;
8616 if (omp_no_lastprivate (ctx))
8618 if (OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c))
8619 remove = true;
8620 else
8621 OMP_CLAUSE_CODE (c) = OMP_CLAUSE_PRIVATE;
8623 else if (code == OMP_DISTRIBUTE
8624 && OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c))
8626 remove = true;
8627 error_at (OMP_CLAUSE_LOCATION (c),
8628 "same variable used in %<firstprivate%> and "
8629 "%<lastprivate%> clauses on %<distribute%> "
8630 "construct");
8632 if (!remove
8633 && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
8634 && DECL_P (decl)
8635 && omp_shared_to_firstprivate_optimizable_decl_p (decl))
8636 omp_mark_stores (gimplify_omp_ctxp->outer_context, decl);
8637 break;
8639 case OMP_CLAUSE_ALIGNED:
8640 decl = OMP_CLAUSE_DECL (c);
8641 if (!is_global_var (decl))
8643 n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
8644 remove = n == NULL || !(n->value & GOVD_SEEN);
8645 if (!remove && TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE)
8647 struct gimplify_omp_ctx *octx;
8648 if (n != NULL
8649 && (n->value & (GOVD_DATA_SHARE_CLASS
8650 & ~GOVD_FIRSTPRIVATE)))
8651 remove = true;
8652 else
8653 for (octx = ctx->outer_context; octx;
8654 octx = octx->outer_context)
8656 n = splay_tree_lookup (octx->variables,
8657 (splay_tree_key) decl);
8658 if (n == NULL)
8659 continue;
8660 if (n->value & GOVD_LOCAL)
8661 break;
8662 /* We have to avoid assigning a shared variable
8663 to itself when trying to add
8664 __builtin_assume_aligned. */
8665 if (n->value & GOVD_SHARED)
8667 remove = true;
8668 break;
8673 else if (TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE)
8675 n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
8676 if (n != NULL && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
8677 remove = true;
8679 break;
8681 case OMP_CLAUSE_MAP:
8682 if (code == OMP_TARGET_EXIT_DATA
8683 && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_POINTER)
8685 remove = true;
8686 break;
8688 decl = OMP_CLAUSE_DECL (c);
8689 /* Data clauses associated with acc parallel reductions must be
8690 compatible with present_or_copy. Warn and adjust the clause
8691 if that is not the case. */
8692 if (ctx->region_type == ORT_ACC_PARALLEL)
8694 tree t = DECL_P (decl) ? decl : TREE_OPERAND (decl, 0);
8695 n = NULL;
8697 if (DECL_P (t))
8698 n = splay_tree_lookup (ctx->variables, (splay_tree_key) t);
8700 if (n && (n->value & GOVD_REDUCTION))
8702 enum gomp_map_kind kind = OMP_CLAUSE_MAP_KIND (c);
8704 OMP_CLAUSE_MAP_IN_REDUCTION (c) = 1;
8705 if ((kind & GOMP_MAP_TOFROM) != GOMP_MAP_TOFROM
8706 && kind != GOMP_MAP_FORCE_PRESENT
8707 && kind != GOMP_MAP_POINTER)
8709 warning_at (OMP_CLAUSE_LOCATION (c), 0,
8710 "incompatible data clause with reduction "
8711 "on %qE; promoting to present_or_copy",
8712 DECL_NAME (t));
8713 OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_TOFROM);
8717 if (!DECL_P (decl))
8719 if ((ctx->region_type & ORT_TARGET) != 0
8720 && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER)
8722 if (TREE_CODE (decl) == INDIRECT_REF
8723 && TREE_CODE (TREE_OPERAND (decl, 0)) == COMPONENT_REF
8724 && (TREE_CODE (TREE_TYPE (TREE_OPERAND (decl, 0)))
8725 == REFERENCE_TYPE))
8726 decl = TREE_OPERAND (decl, 0);
8727 if (TREE_CODE (decl) == COMPONENT_REF)
8729 while (TREE_CODE (decl) == COMPONENT_REF)
8730 decl = TREE_OPERAND (decl, 0);
8731 if (DECL_P (decl))
8733 n = splay_tree_lookup (ctx->variables,
8734 (splay_tree_key) decl);
8735 if (!(n->value & GOVD_SEEN))
8736 remove = true;
8740 break;
8742 n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
8743 if ((ctx->region_type & ORT_TARGET) != 0
8744 && !(n->value & GOVD_SEEN)
8745 && GOMP_MAP_ALWAYS_P (OMP_CLAUSE_MAP_KIND (c)) == 0
8746 && !lookup_attribute ("omp declare target link",
8747 DECL_ATTRIBUTES (decl)))
8749 remove = true;
8750 /* For struct element mapping, if struct is never referenced
8751 in target block and none of the mapping has always modifier,
8752 remove all the struct element mappings, which immediately
8753 follow the GOMP_MAP_STRUCT map clause. */
8754 if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_STRUCT)
8756 HOST_WIDE_INT cnt = tree_to_shwi (OMP_CLAUSE_SIZE (c));
8757 while (cnt--)
8758 OMP_CLAUSE_CHAIN (c)
8759 = OMP_CLAUSE_CHAIN (OMP_CLAUSE_CHAIN (c));
8762 else if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_STRUCT
8763 && code == OMP_TARGET_EXIT_DATA)
8764 remove = true;
8765 else if (DECL_SIZE (decl)
8766 && TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST
8767 && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_POINTER
8768 && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_FIRSTPRIVATE_POINTER
8769 && (OMP_CLAUSE_MAP_KIND (c)
8770 != GOMP_MAP_FIRSTPRIVATE_REFERENCE))
8772 /* For GOMP_MAP_FORCE_DEVICEPTR, we'll never enter here, because
8773 for these, TREE_CODE (DECL_SIZE (decl)) will always be
8774 INTEGER_CST. */
8775 gcc_assert (OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_FORCE_DEVICEPTR);
8777 tree decl2 = DECL_VALUE_EXPR (decl);
8778 gcc_assert (TREE_CODE (decl2) == INDIRECT_REF);
8779 decl2 = TREE_OPERAND (decl2, 0);
8780 gcc_assert (DECL_P (decl2));
8781 tree mem = build_simple_mem_ref (decl2);
8782 OMP_CLAUSE_DECL (c) = mem;
8783 OMP_CLAUSE_SIZE (c) = TYPE_SIZE_UNIT (TREE_TYPE (decl));
8784 if (ctx->outer_context)
8786 omp_notice_variable (ctx->outer_context, decl2, true);
8787 omp_notice_variable (ctx->outer_context,
8788 OMP_CLAUSE_SIZE (c), true);
8790 if (((ctx->region_type & ORT_TARGET) != 0
8791 || !ctx->target_firstprivatize_array_bases)
8792 && ((n->value & GOVD_SEEN) == 0
8793 || (n->value & (GOVD_PRIVATE | GOVD_FIRSTPRIVATE)) == 0))
8795 tree nc = build_omp_clause (OMP_CLAUSE_LOCATION (c),
8796 OMP_CLAUSE_MAP);
8797 OMP_CLAUSE_DECL (nc) = decl;
8798 OMP_CLAUSE_SIZE (nc) = size_zero_node;
8799 if (ctx->target_firstprivatize_array_bases)
8800 OMP_CLAUSE_SET_MAP_KIND (nc,
8801 GOMP_MAP_FIRSTPRIVATE_POINTER);
8802 else
8803 OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_POINTER);
8804 OMP_CLAUSE_CHAIN (nc) = OMP_CLAUSE_CHAIN (c);
8805 OMP_CLAUSE_CHAIN (c) = nc;
8806 c = nc;
8809 else
8811 if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
8812 OMP_CLAUSE_SIZE (c) = DECL_SIZE_UNIT (decl);
8813 gcc_assert ((n->value & GOVD_SEEN) == 0
8814 || ((n->value & (GOVD_PRIVATE | GOVD_FIRSTPRIVATE))
8815 == 0));
8817 break;
8819 case OMP_CLAUSE_TO:
8820 case OMP_CLAUSE_FROM:
8821 case OMP_CLAUSE__CACHE_:
8822 decl = OMP_CLAUSE_DECL (c);
8823 if (!DECL_P (decl))
8824 break;
8825 if (DECL_SIZE (decl)
8826 && TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
8828 tree decl2 = DECL_VALUE_EXPR (decl);
8829 gcc_assert (TREE_CODE (decl2) == INDIRECT_REF);
8830 decl2 = TREE_OPERAND (decl2, 0);
8831 gcc_assert (DECL_P (decl2));
8832 tree mem = build_simple_mem_ref (decl2);
8833 OMP_CLAUSE_DECL (c) = mem;
8834 OMP_CLAUSE_SIZE (c) = TYPE_SIZE_UNIT (TREE_TYPE (decl));
8835 if (ctx->outer_context)
8837 omp_notice_variable (ctx->outer_context, decl2, true);
8838 omp_notice_variable (ctx->outer_context,
8839 OMP_CLAUSE_SIZE (c), true);
8842 else if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
8843 OMP_CLAUSE_SIZE (c) = DECL_SIZE_UNIT (decl);
8844 break;
8846 case OMP_CLAUSE_REDUCTION:
8847 decl = OMP_CLAUSE_DECL (c);
8848 /* OpenACC reductions need a present_or_copy data clause.
8849 Add one if necessary. Error is the reduction is private. */
8850 if (ctx->region_type == ORT_ACC_PARALLEL)
8852 n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
8853 if (n->value & (GOVD_PRIVATE | GOVD_FIRSTPRIVATE))
8854 error_at (OMP_CLAUSE_LOCATION (c), "invalid private "
8855 "reduction on %qE", DECL_NAME (decl));
8856 else if ((n->value & GOVD_MAP) == 0)
8858 tree next = OMP_CLAUSE_CHAIN (c);
8859 tree nc = build_omp_clause (UNKNOWN_LOCATION, OMP_CLAUSE_MAP);
8860 OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_TOFROM);
8861 OMP_CLAUSE_DECL (nc) = decl;
8862 OMP_CLAUSE_CHAIN (c) = nc;
8863 lang_hooks.decls.omp_finish_clause (nc, pre_p);
8864 while (1)
8866 OMP_CLAUSE_MAP_IN_REDUCTION (nc) = 1;
8867 if (OMP_CLAUSE_CHAIN (nc) == NULL)
8868 break;
8869 nc = OMP_CLAUSE_CHAIN (nc);
8871 OMP_CLAUSE_CHAIN (nc) = next;
8872 n->value |= GOVD_MAP;
8875 if (DECL_P (decl)
8876 && omp_shared_to_firstprivate_optimizable_decl_p (decl))
8877 omp_mark_stores (gimplify_omp_ctxp->outer_context, decl);
8878 break;
8879 case OMP_CLAUSE_COPYIN:
8880 case OMP_CLAUSE_COPYPRIVATE:
8881 case OMP_CLAUSE_IF:
8882 case OMP_CLAUSE_NUM_THREADS:
8883 case OMP_CLAUSE_NUM_TEAMS:
8884 case OMP_CLAUSE_THREAD_LIMIT:
8885 case OMP_CLAUSE_DIST_SCHEDULE:
8886 case OMP_CLAUSE_DEVICE:
8887 case OMP_CLAUSE_SCHEDULE:
8888 case OMP_CLAUSE_NOWAIT:
8889 case OMP_CLAUSE_ORDERED:
8890 case OMP_CLAUSE_DEFAULT:
8891 case OMP_CLAUSE_UNTIED:
8892 case OMP_CLAUSE_COLLAPSE:
8893 case OMP_CLAUSE_FINAL:
8894 case OMP_CLAUSE_MERGEABLE:
8895 case OMP_CLAUSE_PROC_BIND:
8896 case OMP_CLAUSE_SAFELEN:
8897 case OMP_CLAUSE_SIMDLEN:
8898 case OMP_CLAUSE_DEPEND:
8899 case OMP_CLAUSE_PRIORITY:
8900 case OMP_CLAUSE_GRAINSIZE:
8901 case OMP_CLAUSE_NUM_TASKS:
8902 case OMP_CLAUSE_NOGROUP:
8903 case OMP_CLAUSE_THREADS:
8904 case OMP_CLAUSE_SIMD:
8905 case OMP_CLAUSE_HINT:
8906 case OMP_CLAUSE_DEFAULTMAP:
8907 case OMP_CLAUSE_USE_DEVICE_PTR:
8908 case OMP_CLAUSE_IS_DEVICE_PTR:
8909 case OMP_CLAUSE__CILK_FOR_COUNT_:
8910 case OMP_CLAUSE_ASYNC:
8911 case OMP_CLAUSE_WAIT:
8912 case OMP_CLAUSE_INDEPENDENT:
8913 case OMP_CLAUSE_NUM_GANGS:
8914 case OMP_CLAUSE_NUM_WORKERS:
8915 case OMP_CLAUSE_VECTOR_LENGTH:
8916 case OMP_CLAUSE_GANG:
8917 case OMP_CLAUSE_WORKER:
8918 case OMP_CLAUSE_VECTOR:
8919 case OMP_CLAUSE_AUTO:
8920 case OMP_CLAUSE_SEQ:
8921 break;
8923 case OMP_CLAUSE_TILE:
8924 /* We're not yet making use of the information provided by OpenACC
8925 tile clauses. Discard these here, to simplify later middle end
8926 processing. */
8927 remove = true;
8928 break;
8930 default:
8931 gcc_unreachable ();
8934 if (remove)
8935 *list_p = OMP_CLAUSE_CHAIN (c);
8936 else
8937 list_p = &OMP_CLAUSE_CHAIN (c);
8940 /* Add in any implicit data sharing. */
8941 struct gimplify_adjust_omp_clauses_data data;
8942 data.list_p = list_p;
8943 data.pre_p = pre_p;
8944 splay_tree_foreach (ctx->variables, gimplify_adjust_omp_clauses_1, &data);
8946 gimplify_omp_ctxp = ctx->outer_context;
8947 delete_omp_context (ctx);
8950 /* Gimplify OACC_CACHE. */
8952 static void
8953 gimplify_oacc_cache (tree *expr_p, gimple_seq *pre_p)
8955 tree expr = *expr_p;
8957 gimplify_scan_omp_clauses (&OACC_CACHE_CLAUSES (expr), pre_p, ORT_ACC,
8958 OACC_CACHE);
8959 gimplify_adjust_omp_clauses (pre_p, NULL, &OACC_CACHE_CLAUSES (expr),
8960 OACC_CACHE);
8962 /* TODO: Do something sensible with this information. */
8964 *expr_p = NULL_TREE;
8967 /* Helper function of gimplify_oacc_declare. The helper's purpose is to,
8968 if required, translate 'kind' in CLAUSE into an 'entry' kind and 'exit'
8969 kind. The entry kind will replace the one in CLAUSE, while the exit
8970 kind will be used in a new omp_clause and returned to the caller. */
8972 static tree
8973 gimplify_oacc_declare_1 (tree clause)
8975 HOST_WIDE_INT kind, new_op;
8976 bool ret = false;
8977 tree c = NULL;
8979 kind = OMP_CLAUSE_MAP_KIND (clause);
8981 switch (kind)
8983 case GOMP_MAP_ALLOC:
8984 case GOMP_MAP_FORCE_ALLOC:
8985 case GOMP_MAP_FORCE_TO:
8986 new_op = GOMP_MAP_DELETE;
8987 ret = true;
8988 break;
8990 case GOMP_MAP_FORCE_FROM:
8991 OMP_CLAUSE_SET_MAP_KIND (clause, GOMP_MAP_FORCE_ALLOC);
8992 new_op = GOMP_MAP_FORCE_FROM;
8993 ret = true;
8994 break;
8996 case GOMP_MAP_FORCE_TOFROM:
8997 OMP_CLAUSE_SET_MAP_KIND (clause, GOMP_MAP_FORCE_TO);
8998 new_op = GOMP_MAP_FORCE_FROM;
8999 ret = true;
9000 break;
9002 case GOMP_MAP_FROM:
9003 OMP_CLAUSE_SET_MAP_KIND (clause, GOMP_MAP_FORCE_ALLOC);
9004 new_op = GOMP_MAP_FROM;
9005 ret = true;
9006 break;
9008 case GOMP_MAP_TOFROM:
9009 OMP_CLAUSE_SET_MAP_KIND (clause, GOMP_MAP_TO);
9010 new_op = GOMP_MAP_FROM;
9011 ret = true;
9012 break;
9014 case GOMP_MAP_DEVICE_RESIDENT:
9015 case GOMP_MAP_FORCE_DEVICEPTR:
9016 case GOMP_MAP_FORCE_PRESENT:
9017 case GOMP_MAP_LINK:
9018 case GOMP_MAP_POINTER:
9019 case GOMP_MAP_TO:
9020 break;
9022 default:
9023 gcc_unreachable ();
9024 break;
9027 if (ret)
9029 c = build_omp_clause (OMP_CLAUSE_LOCATION (clause), OMP_CLAUSE_MAP);
9030 OMP_CLAUSE_SET_MAP_KIND (c, new_op);
9031 OMP_CLAUSE_DECL (c) = OMP_CLAUSE_DECL (clause);
9034 return c;
9037 /* Gimplify OACC_DECLARE. */
9039 static void
9040 gimplify_oacc_declare (tree *expr_p, gimple_seq *pre_p)
9042 tree expr = *expr_p;
9043 gomp_target *stmt;
9044 tree clauses, t;
9046 clauses = OACC_DECLARE_CLAUSES (expr);
9048 gimplify_scan_omp_clauses (&clauses, pre_p, ORT_TARGET_DATA, OACC_DECLARE);
9050 for (t = clauses; t; t = OMP_CLAUSE_CHAIN (t))
9052 tree decl = OMP_CLAUSE_DECL (t);
9054 if (TREE_CODE (decl) == MEM_REF)
9055 continue;
9057 if (VAR_P (decl)
9058 && !is_global_var (decl)
9059 && DECL_CONTEXT (decl) == current_function_decl)
9061 tree c = gimplify_oacc_declare_1 (t);
9062 if (c)
9064 if (oacc_declare_returns == NULL)
9065 oacc_declare_returns = new hash_map<tree, tree>;
9067 oacc_declare_returns->put (decl, c);
9071 omp_add_variable (gimplify_omp_ctxp, decl, GOVD_SEEN);
9074 stmt = gimple_build_omp_target (NULL, GF_OMP_TARGET_KIND_OACC_DECLARE,
9075 clauses);
9077 gimplify_seq_add_stmt (pre_p, stmt);
9079 *expr_p = NULL_TREE;
9082 /* Gimplify the contents of an OMP_PARALLEL statement. This involves
9083 gimplification of the body, as well as scanning the body for used
9084 variables. We need to do this scan now, because variable-sized
9085 decls will be decomposed during gimplification. */
9087 static void
9088 gimplify_omp_parallel (tree *expr_p, gimple_seq *pre_p)
9090 tree expr = *expr_p;
9091 gimple *g;
9092 gimple_seq body = NULL;
9094 gimplify_scan_omp_clauses (&OMP_PARALLEL_CLAUSES (expr), pre_p,
9095 OMP_PARALLEL_COMBINED (expr)
9096 ? ORT_COMBINED_PARALLEL
9097 : ORT_PARALLEL, OMP_PARALLEL);
9099 push_gimplify_context ();
9101 g = gimplify_and_return_first (OMP_PARALLEL_BODY (expr), &body);
9102 if (gimple_code (g) == GIMPLE_BIND)
9103 pop_gimplify_context (g);
9104 else
9105 pop_gimplify_context (NULL);
9107 gimplify_adjust_omp_clauses (pre_p, body, &OMP_PARALLEL_CLAUSES (expr),
9108 OMP_PARALLEL);
9110 g = gimple_build_omp_parallel (body,
9111 OMP_PARALLEL_CLAUSES (expr),
9112 NULL_TREE, NULL_TREE);
9113 if (OMP_PARALLEL_COMBINED (expr))
9114 gimple_omp_set_subcode (g, GF_OMP_PARALLEL_COMBINED);
9115 gimplify_seq_add_stmt (pre_p, g);
9116 *expr_p = NULL_TREE;
9119 /* Gimplify the contents of an OMP_TASK statement. This involves
9120 gimplification of the body, as well as scanning the body for used
9121 variables. We need to do this scan now, because variable-sized
9122 decls will be decomposed during gimplification. */
9124 static void
9125 gimplify_omp_task (tree *expr_p, gimple_seq *pre_p)
9127 tree expr = *expr_p;
9128 gimple *g;
9129 gimple_seq body = NULL;
9131 gimplify_scan_omp_clauses (&OMP_TASK_CLAUSES (expr), pre_p,
9132 find_omp_clause (OMP_TASK_CLAUSES (expr),
9133 OMP_CLAUSE_UNTIED)
9134 ? ORT_UNTIED_TASK : ORT_TASK, OMP_TASK);
9136 push_gimplify_context ();
9138 g = gimplify_and_return_first (OMP_TASK_BODY (expr), &body);
9139 if (gimple_code (g) == GIMPLE_BIND)
9140 pop_gimplify_context (g);
9141 else
9142 pop_gimplify_context (NULL);
9144 gimplify_adjust_omp_clauses (pre_p, body, &OMP_TASK_CLAUSES (expr),
9145 OMP_TASK);
9147 g = gimple_build_omp_task (body,
9148 OMP_TASK_CLAUSES (expr),
9149 NULL_TREE, NULL_TREE,
9150 NULL_TREE, NULL_TREE, NULL_TREE);
9151 gimplify_seq_add_stmt (pre_p, g);
9152 *expr_p = NULL_TREE;
9155 /* Helper function of gimplify_omp_for, find OMP_FOR resp. OMP_SIMD
9156 with non-NULL OMP_FOR_INIT. */
9158 static tree
9159 find_combined_omp_for (tree *tp, int *walk_subtrees, void *)
9161 *walk_subtrees = 0;
9162 switch (TREE_CODE (*tp))
9164 case OMP_FOR:
9165 *walk_subtrees = 1;
9166 /* FALLTHRU */
9167 case OMP_SIMD:
9168 if (OMP_FOR_INIT (*tp) != NULL_TREE)
9169 return *tp;
9170 break;
9171 case BIND_EXPR:
9172 case STATEMENT_LIST:
9173 case OMP_PARALLEL:
9174 *walk_subtrees = 1;
9175 break;
9176 default:
9177 break;
9179 return NULL_TREE;
9182 /* Gimplify the gross structure of an OMP_FOR statement. */
9184 static enum gimplify_status
9185 gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
9187 tree for_stmt, orig_for_stmt, inner_for_stmt = NULL_TREE, decl, var, t;
9188 enum gimplify_status ret = GS_ALL_DONE;
9189 enum gimplify_status tret;
9190 gomp_for *gfor;
9191 gimple_seq for_body, for_pre_body;
9192 int i;
9193 bitmap has_decl_expr = NULL;
9194 enum omp_region_type ort = ORT_WORKSHARE;
9196 orig_for_stmt = for_stmt = *expr_p;
9198 switch (TREE_CODE (for_stmt))
9200 case OMP_FOR:
9201 case CILK_FOR:
9202 case OMP_DISTRIBUTE:
9203 break;
9204 case OACC_LOOP:
9205 ort = ORT_ACC;
9206 break;
9207 case OMP_TASKLOOP:
9208 if (find_omp_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_UNTIED))
9209 ort = ORT_UNTIED_TASK;
9210 else
9211 ort = ORT_TASK;
9212 break;
9213 case OMP_SIMD:
9214 case CILK_SIMD:
9215 ort = ORT_SIMD;
9216 break;
9217 default:
9218 gcc_unreachable ();
9221 /* Set OMP_CLAUSE_LINEAR_NO_COPYIN flag on explicit linear
9222 clause for the IV. */
9223 if (ort == ORT_SIMD && TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) == 1)
9225 t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), 0);
9226 gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
9227 decl = TREE_OPERAND (t, 0);
9228 for (tree c = OMP_FOR_CLAUSES (for_stmt); c; c = OMP_CLAUSE_CHAIN (c))
9229 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
9230 && OMP_CLAUSE_DECL (c) == decl)
9232 OMP_CLAUSE_LINEAR_NO_COPYIN (c) = 1;
9233 break;
9237 if (OMP_FOR_INIT (for_stmt) == NULL_TREE)
9239 gcc_assert (TREE_CODE (for_stmt) != OACC_LOOP);
9240 inner_for_stmt = walk_tree (&OMP_FOR_BODY (for_stmt),
9241 find_combined_omp_for, NULL, NULL);
9242 if (inner_for_stmt == NULL_TREE)
9244 gcc_assert (seen_error ());
9245 *expr_p = NULL_TREE;
9246 return GS_ERROR;
9250 if (TREE_CODE (for_stmt) != OMP_TASKLOOP)
9251 gimplify_scan_omp_clauses (&OMP_FOR_CLAUSES (for_stmt), pre_p, ort,
9252 TREE_CODE (for_stmt));
9254 if (TREE_CODE (for_stmt) == OMP_DISTRIBUTE)
9255 gimplify_omp_ctxp->distribute = true;
9257 /* Handle OMP_FOR_INIT. */
9258 for_pre_body = NULL;
9259 if (ort == ORT_SIMD && OMP_FOR_PRE_BODY (for_stmt))
9261 has_decl_expr = BITMAP_ALLOC (NULL);
9262 if (TREE_CODE (OMP_FOR_PRE_BODY (for_stmt)) == DECL_EXPR
9263 && TREE_CODE (DECL_EXPR_DECL (OMP_FOR_PRE_BODY (for_stmt)))
9264 == VAR_DECL)
9266 t = OMP_FOR_PRE_BODY (for_stmt);
9267 bitmap_set_bit (has_decl_expr, DECL_UID (DECL_EXPR_DECL (t)));
9269 else if (TREE_CODE (OMP_FOR_PRE_BODY (for_stmt)) == STATEMENT_LIST)
9271 tree_stmt_iterator si;
9272 for (si = tsi_start (OMP_FOR_PRE_BODY (for_stmt)); !tsi_end_p (si);
9273 tsi_next (&si))
9275 t = tsi_stmt (si);
9276 if (TREE_CODE (t) == DECL_EXPR
9277 && TREE_CODE (DECL_EXPR_DECL (t)) == VAR_DECL)
9278 bitmap_set_bit (has_decl_expr, DECL_UID (DECL_EXPR_DECL (t)));
9282 if (OMP_FOR_PRE_BODY (for_stmt))
9284 if (TREE_CODE (for_stmt) != OMP_TASKLOOP || gimplify_omp_ctxp)
9285 gimplify_and_add (OMP_FOR_PRE_BODY (for_stmt), &for_pre_body);
9286 else
9288 struct gimplify_omp_ctx ctx;
9289 memset (&ctx, 0, sizeof (ctx));
9290 ctx.region_type = ORT_NONE;
9291 gimplify_omp_ctxp = &ctx;
9292 gimplify_and_add (OMP_FOR_PRE_BODY (for_stmt), &for_pre_body);
9293 gimplify_omp_ctxp = NULL;
9296 OMP_FOR_PRE_BODY (for_stmt) = NULL_TREE;
9298 if (OMP_FOR_INIT (for_stmt) == NULL_TREE)
9299 for_stmt = inner_for_stmt;
9301 /* For taskloop, need to gimplify the start, end and step before the
9302 taskloop, outside of the taskloop omp context. */
9303 if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP)
9305 for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
9307 t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
9308 if (!is_gimple_constant (TREE_OPERAND (t, 1)))
9310 TREE_OPERAND (t, 1)
9311 = get_initialized_tmp_var (TREE_OPERAND (t, 1),
9312 pre_p, NULL, false);
9313 tree c = build_omp_clause (input_location,
9314 OMP_CLAUSE_FIRSTPRIVATE);
9315 OMP_CLAUSE_DECL (c) = TREE_OPERAND (t, 1);
9316 OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (orig_for_stmt);
9317 OMP_FOR_CLAUSES (orig_for_stmt) = c;
9320 /* Handle OMP_FOR_COND. */
9321 t = TREE_VEC_ELT (OMP_FOR_COND (for_stmt), i);
9322 if (!is_gimple_constant (TREE_OPERAND (t, 1)))
9324 TREE_OPERAND (t, 1)
9325 = get_initialized_tmp_var (TREE_OPERAND (t, 1),
9326 gimple_seq_empty_p (for_pre_body)
9327 ? pre_p : &for_pre_body, NULL,
9328 false);
9329 tree c = build_omp_clause (input_location,
9330 OMP_CLAUSE_FIRSTPRIVATE);
9331 OMP_CLAUSE_DECL (c) = TREE_OPERAND (t, 1);
9332 OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (orig_for_stmt);
9333 OMP_FOR_CLAUSES (orig_for_stmt) = c;
9336 /* Handle OMP_FOR_INCR. */
9337 t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
9338 if (TREE_CODE (t) == MODIFY_EXPR)
9340 decl = TREE_OPERAND (t, 0);
9341 t = TREE_OPERAND (t, 1);
9342 tree *tp = &TREE_OPERAND (t, 1);
9343 if (TREE_CODE (t) == PLUS_EXPR && *tp == decl)
9344 tp = &TREE_OPERAND (t, 0);
9346 if (!is_gimple_constant (*tp))
9348 gimple_seq *seq = gimple_seq_empty_p (for_pre_body)
9349 ? pre_p : &for_pre_body;
9350 *tp = get_initialized_tmp_var (*tp, seq, NULL, false);
9351 tree c = build_omp_clause (input_location,
9352 OMP_CLAUSE_FIRSTPRIVATE);
9353 OMP_CLAUSE_DECL (c) = *tp;
9354 OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (orig_for_stmt);
9355 OMP_FOR_CLAUSES (orig_for_stmt) = c;
9360 gimplify_scan_omp_clauses (&OMP_FOR_CLAUSES (orig_for_stmt), pre_p, ort,
9361 OMP_TASKLOOP);
9364 if (orig_for_stmt != for_stmt)
9365 gimplify_omp_ctxp->combined_loop = true;
9367 for_body = NULL;
9368 gcc_assert (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt))
9369 == TREE_VEC_LENGTH (OMP_FOR_COND (for_stmt)));
9370 gcc_assert (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt))
9371 == TREE_VEC_LENGTH (OMP_FOR_INCR (for_stmt)));
9373 tree c = find_omp_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_ORDERED);
9374 bool is_doacross = false;
9375 if (c && OMP_CLAUSE_ORDERED_EXPR (c))
9377 is_doacross = true;
9378 gimplify_omp_ctxp->loop_iter_var.create (TREE_VEC_LENGTH
9379 (OMP_FOR_INIT (for_stmt))
9380 * 2);
9382 int collapse = 1;
9383 c = find_omp_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_COLLAPSE);
9384 if (c)
9385 collapse = tree_to_shwi (OMP_CLAUSE_COLLAPSE_EXPR (c));
9386 for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
9388 t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
9389 gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
9390 decl = TREE_OPERAND (t, 0);
9391 gcc_assert (DECL_P (decl));
9392 gcc_assert (INTEGRAL_TYPE_P (TREE_TYPE (decl))
9393 || POINTER_TYPE_P (TREE_TYPE (decl)));
9394 if (is_doacross)
9396 if (TREE_CODE (for_stmt) == OMP_FOR && OMP_FOR_ORIG_DECLS (for_stmt))
9397 gimplify_omp_ctxp->loop_iter_var.quick_push
9398 (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (for_stmt), i));
9399 else
9400 gimplify_omp_ctxp->loop_iter_var.quick_push (decl);
9401 gimplify_omp_ctxp->loop_iter_var.quick_push (decl);
9404 /* Make sure the iteration variable is private. */
9405 tree c = NULL_TREE;
9406 tree c2 = NULL_TREE;
9407 if (orig_for_stmt != for_stmt)
9408 /* Do this only on innermost construct for combined ones. */;
9409 else if (ort == ORT_SIMD)
9411 splay_tree_node n = splay_tree_lookup (gimplify_omp_ctxp->variables,
9412 (splay_tree_key) decl);
9413 omp_is_private (gimplify_omp_ctxp, decl,
9414 1 + (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt))
9415 != 1));
9416 if (n != NULL && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
9417 omp_notice_variable (gimplify_omp_ctxp, decl, true);
9418 else if (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) == 1)
9420 c = build_omp_clause (input_location, OMP_CLAUSE_LINEAR);
9421 OMP_CLAUSE_LINEAR_NO_COPYIN (c) = 1;
9422 unsigned int flags = GOVD_LINEAR | GOVD_EXPLICIT | GOVD_SEEN;
9423 if ((has_decl_expr
9424 && bitmap_bit_p (has_decl_expr, DECL_UID (decl)))
9425 || omp_no_lastprivate (gimplify_omp_ctxp))
9427 OMP_CLAUSE_LINEAR_NO_COPYOUT (c) = 1;
9428 flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
9430 struct gimplify_omp_ctx *outer
9431 = gimplify_omp_ctxp->outer_context;
9432 if (outer && !OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
9434 if (outer->region_type == ORT_WORKSHARE
9435 && outer->combined_loop)
9437 n = splay_tree_lookup (outer->variables,
9438 (splay_tree_key)decl);
9439 if (n != NULL && (n->value & GOVD_LOCAL) != 0)
9441 OMP_CLAUSE_LINEAR_NO_COPYOUT (c) = 1;
9442 flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
9444 else
9446 struct gimplify_omp_ctx *octx = outer->outer_context;
9447 if (octx
9448 && octx->region_type == ORT_COMBINED_PARALLEL
9449 && octx->outer_context
9450 && (octx->outer_context->region_type
9451 == ORT_WORKSHARE)
9452 && octx->outer_context->combined_loop)
9454 octx = octx->outer_context;
9455 n = splay_tree_lookup (octx->variables,
9456 (splay_tree_key)decl);
9457 if (n != NULL && (n->value & GOVD_LOCAL) != 0)
9459 OMP_CLAUSE_LINEAR_NO_COPYOUT (c) = 1;
9460 flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
9467 OMP_CLAUSE_DECL (c) = decl;
9468 OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (for_stmt);
9469 OMP_FOR_CLAUSES (for_stmt) = c;
9470 omp_add_variable (gimplify_omp_ctxp, decl, flags);
9471 if (outer && !OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
9473 if (outer->region_type == ORT_WORKSHARE
9474 && outer->combined_loop)
9476 if (outer->outer_context
9477 && (outer->outer_context->region_type
9478 == ORT_COMBINED_PARALLEL))
9479 outer = outer->outer_context;
9480 else if (omp_check_private (outer, decl, false))
9481 outer = NULL;
9483 else if (((outer->region_type & ORT_TASK) != 0)
9484 && outer->combined_loop
9485 && !omp_check_private (gimplify_omp_ctxp,
9486 decl, false))
9488 else if (outer->region_type != ORT_COMBINED_PARALLEL)
9490 omp_notice_variable (outer, decl, true);
9491 outer = NULL;
9493 if (outer)
9495 n = splay_tree_lookup (outer->variables,
9496 (splay_tree_key)decl);
9497 if (n == NULL || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
9499 omp_add_variable (outer, decl,
9500 GOVD_LASTPRIVATE | GOVD_SEEN);
9501 if (outer->region_type == ORT_COMBINED_PARALLEL
9502 && outer->outer_context
9503 && (outer->outer_context->region_type
9504 == ORT_WORKSHARE)
9505 && outer->outer_context->combined_loop)
9507 outer = outer->outer_context;
9508 n = splay_tree_lookup (outer->variables,
9509 (splay_tree_key)decl);
9510 if (omp_check_private (outer, decl, false))
9511 outer = NULL;
9512 else if (n == NULL
9513 || ((n->value & GOVD_DATA_SHARE_CLASS)
9514 == 0))
9515 omp_add_variable (outer, decl,
9516 GOVD_LASTPRIVATE
9517 | GOVD_SEEN);
9518 else
9519 outer = NULL;
9521 if (outer && outer->outer_context
9522 && (outer->outer_context->region_type
9523 == ORT_COMBINED_TEAMS))
9525 outer = outer->outer_context;
9526 n = splay_tree_lookup (outer->variables,
9527 (splay_tree_key)decl);
9528 if (n == NULL
9529 || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
9530 omp_add_variable (outer, decl,
9531 GOVD_SHARED | GOVD_SEEN);
9532 else
9533 outer = NULL;
9535 if (outer && outer->outer_context)
9536 omp_notice_variable (outer->outer_context, decl,
9537 true);
9542 else
9544 bool lastprivate
9545 = (!has_decl_expr
9546 || !bitmap_bit_p (has_decl_expr, DECL_UID (decl)))
9547 && !omp_no_lastprivate (gimplify_omp_ctxp);
9548 struct gimplify_omp_ctx *outer
9549 = gimplify_omp_ctxp->outer_context;
9550 if (outer && lastprivate)
9552 if (outer->region_type == ORT_WORKSHARE
9553 && outer->combined_loop)
9555 n = splay_tree_lookup (outer->variables,
9556 (splay_tree_key)decl);
9557 if (n != NULL && (n->value & GOVD_LOCAL) != 0)
9559 lastprivate = false;
9560 outer = NULL;
9562 else if (outer->outer_context
9563 && (outer->outer_context->region_type
9564 == ORT_COMBINED_PARALLEL))
9565 outer = outer->outer_context;
9566 else if (omp_check_private (outer, decl, false))
9567 outer = NULL;
9569 else if (((outer->region_type & ORT_TASK) != 0)
9570 && outer->combined_loop
9571 && !omp_check_private (gimplify_omp_ctxp,
9572 decl, false))
9574 else if (outer->region_type != ORT_COMBINED_PARALLEL)
9576 omp_notice_variable (outer, decl, true);
9577 outer = NULL;
9579 if (outer)
9581 n = splay_tree_lookup (outer->variables,
9582 (splay_tree_key)decl);
9583 if (n == NULL || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
9585 omp_add_variable (outer, decl,
9586 GOVD_LASTPRIVATE | GOVD_SEEN);
9587 if (outer->region_type == ORT_COMBINED_PARALLEL
9588 && outer->outer_context
9589 && (outer->outer_context->region_type
9590 == ORT_WORKSHARE)
9591 && outer->outer_context->combined_loop)
9593 outer = outer->outer_context;
9594 n = splay_tree_lookup (outer->variables,
9595 (splay_tree_key)decl);
9596 if (omp_check_private (outer, decl, false))
9597 outer = NULL;
9598 else if (n == NULL
9599 || ((n->value & GOVD_DATA_SHARE_CLASS)
9600 == 0))
9601 omp_add_variable (outer, decl,
9602 GOVD_LASTPRIVATE
9603 | GOVD_SEEN);
9604 else
9605 outer = NULL;
9607 if (outer && outer->outer_context
9608 && (outer->outer_context->region_type
9609 == ORT_COMBINED_TEAMS))
9611 outer = outer->outer_context;
9612 n = splay_tree_lookup (outer->variables,
9613 (splay_tree_key)decl);
9614 if (n == NULL
9615 || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
9616 omp_add_variable (outer, decl,
9617 GOVD_SHARED | GOVD_SEEN);
9618 else
9619 outer = NULL;
9621 if (outer && outer->outer_context)
9622 omp_notice_variable (outer->outer_context, decl,
9623 true);
9628 c = build_omp_clause (input_location,
9629 lastprivate ? OMP_CLAUSE_LASTPRIVATE
9630 : OMP_CLAUSE_PRIVATE);
9631 OMP_CLAUSE_DECL (c) = decl;
9632 OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (for_stmt);
9633 OMP_FOR_CLAUSES (for_stmt) = c;
9634 omp_add_variable (gimplify_omp_ctxp, decl,
9635 (lastprivate ? GOVD_LASTPRIVATE : GOVD_PRIVATE)
9636 | GOVD_EXPLICIT | GOVD_SEEN);
9637 c = NULL_TREE;
9640 else if (omp_is_private (gimplify_omp_ctxp, decl, 0))
9641 omp_notice_variable (gimplify_omp_ctxp, decl, true);
9642 else
9643 omp_add_variable (gimplify_omp_ctxp, decl, GOVD_PRIVATE | GOVD_SEEN);
9645 /* If DECL is not a gimple register, create a temporary variable to act
9646 as an iteration counter. This is valid, since DECL cannot be
9647 modified in the body of the loop. Similarly for any iteration vars
9648 in simd with collapse > 1 where the iterator vars must be
9649 lastprivate. */
9650 if (orig_for_stmt != for_stmt)
9651 var = decl;
9652 else if (!is_gimple_reg (decl)
9653 || (ort == ORT_SIMD
9654 && TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) > 1))
9656 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
9657 /* Make sure omp_add_variable is not called on it prematurely.
9658 We call it ourselves a few lines later. */
9659 gimplify_omp_ctxp = NULL;
9660 var = create_tmp_var (TREE_TYPE (decl), get_name (decl));
9661 gimplify_omp_ctxp = ctx;
9662 TREE_OPERAND (t, 0) = var;
9664 gimplify_seq_add_stmt (&for_body, gimple_build_assign (decl, var));
9666 if (ort == ORT_SIMD
9667 && TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) == 1)
9669 c2 = build_omp_clause (input_location, OMP_CLAUSE_LINEAR);
9670 OMP_CLAUSE_LINEAR_NO_COPYIN (c2) = 1;
9671 OMP_CLAUSE_LINEAR_NO_COPYOUT (c2) = 1;
9672 OMP_CLAUSE_DECL (c2) = var;
9673 OMP_CLAUSE_CHAIN (c2) = OMP_FOR_CLAUSES (for_stmt);
9674 OMP_FOR_CLAUSES (for_stmt) = c2;
9675 omp_add_variable (gimplify_omp_ctxp, var,
9676 GOVD_LINEAR | GOVD_EXPLICIT | GOVD_SEEN);
9677 if (c == NULL_TREE)
9679 c = c2;
9680 c2 = NULL_TREE;
9683 else
9684 omp_add_variable (gimplify_omp_ctxp, var,
9685 GOVD_PRIVATE | GOVD_SEEN);
9687 else
9688 var = decl;
9690 tret = gimplify_expr (&TREE_OPERAND (t, 1), &for_pre_body, NULL,
9691 is_gimple_val, fb_rvalue, false);
9692 ret = MIN (ret, tret);
9693 if (ret == GS_ERROR)
9694 return ret;
9696 /* Handle OMP_FOR_COND. */
9697 t = TREE_VEC_ELT (OMP_FOR_COND (for_stmt), i);
9698 gcc_assert (COMPARISON_CLASS_P (t));
9699 gcc_assert (TREE_OPERAND (t, 0) == decl);
9701 tret = gimplify_expr (&TREE_OPERAND (t, 1), &for_pre_body, NULL,
9702 is_gimple_val, fb_rvalue, false);
9703 ret = MIN (ret, tret);
9705 /* Handle OMP_FOR_INCR. */
9706 t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
9707 switch (TREE_CODE (t))
9709 case PREINCREMENT_EXPR:
9710 case POSTINCREMENT_EXPR:
9712 tree decl = TREE_OPERAND (t, 0);
9713 /* c_omp_for_incr_canonicalize_ptr() should have been
9714 called to massage things appropriately. */
9715 gcc_assert (!POINTER_TYPE_P (TREE_TYPE (decl)));
9717 if (orig_for_stmt != for_stmt)
9718 break;
9719 t = build_int_cst (TREE_TYPE (decl), 1);
9720 if (c)
9721 OMP_CLAUSE_LINEAR_STEP (c) = t;
9722 t = build2 (PLUS_EXPR, TREE_TYPE (decl), var, t);
9723 t = build2 (MODIFY_EXPR, TREE_TYPE (var), var, t);
9724 TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i) = t;
9725 break;
9728 case PREDECREMENT_EXPR:
9729 case POSTDECREMENT_EXPR:
9730 /* c_omp_for_incr_canonicalize_ptr() should have been
9731 called to massage things appropriately. */
9732 gcc_assert (!POINTER_TYPE_P (TREE_TYPE (decl)));
9733 if (orig_for_stmt != for_stmt)
9734 break;
9735 t = build_int_cst (TREE_TYPE (decl), -1);
9736 if (c)
9737 OMP_CLAUSE_LINEAR_STEP (c) = t;
9738 t = build2 (PLUS_EXPR, TREE_TYPE (decl), var, t);
9739 t = build2 (MODIFY_EXPR, TREE_TYPE (var), var, t);
9740 TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i) = t;
9741 break;
9743 case MODIFY_EXPR:
9744 gcc_assert (TREE_OPERAND (t, 0) == decl);
9745 TREE_OPERAND (t, 0) = var;
9747 t = TREE_OPERAND (t, 1);
9748 switch (TREE_CODE (t))
9750 case PLUS_EXPR:
9751 if (TREE_OPERAND (t, 1) == decl)
9753 TREE_OPERAND (t, 1) = TREE_OPERAND (t, 0);
9754 TREE_OPERAND (t, 0) = var;
9755 break;
9758 /* Fallthru. */
9759 case MINUS_EXPR:
9760 case POINTER_PLUS_EXPR:
9761 gcc_assert (TREE_OPERAND (t, 0) == decl);
9762 TREE_OPERAND (t, 0) = var;
9763 break;
9764 default:
9765 gcc_unreachable ();
9768 tret = gimplify_expr (&TREE_OPERAND (t, 1), &for_pre_body, NULL,
9769 is_gimple_val, fb_rvalue, false);
9770 ret = MIN (ret, tret);
9771 if (c)
9773 tree step = TREE_OPERAND (t, 1);
9774 tree stept = TREE_TYPE (decl);
9775 if (POINTER_TYPE_P (stept))
9776 stept = sizetype;
9777 step = fold_convert (stept, step);
9778 if (TREE_CODE (t) == MINUS_EXPR)
9779 step = fold_build1 (NEGATE_EXPR, stept, step);
9780 OMP_CLAUSE_LINEAR_STEP (c) = step;
9781 if (step != TREE_OPERAND (t, 1))
9783 tret = gimplify_expr (&OMP_CLAUSE_LINEAR_STEP (c),
9784 &for_pre_body, NULL,
9785 is_gimple_val, fb_rvalue, false);
9786 ret = MIN (ret, tret);
9789 break;
9791 default:
9792 gcc_unreachable ();
9795 if (c2)
9797 gcc_assert (c);
9798 OMP_CLAUSE_LINEAR_STEP (c2) = OMP_CLAUSE_LINEAR_STEP (c);
9801 if ((var != decl || collapse > 1) && orig_for_stmt == for_stmt)
9803 for (c = OMP_FOR_CLAUSES (for_stmt); c ; c = OMP_CLAUSE_CHAIN (c))
9804 if (((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
9805 && OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (c) == NULL)
9806 || (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
9807 && !OMP_CLAUSE_LINEAR_NO_COPYOUT (c)
9808 && OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c) == NULL))
9809 && OMP_CLAUSE_DECL (c) == decl)
9811 if (is_doacross && (collapse == 1 || i >= collapse))
9812 t = var;
9813 else
9815 t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
9816 gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
9817 gcc_assert (TREE_OPERAND (t, 0) == var);
9818 t = TREE_OPERAND (t, 1);
9819 gcc_assert (TREE_CODE (t) == PLUS_EXPR
9820 || TREE_CODE (t) == MINUS_EXPR
9821 || TREE_CODE (t) == POINTER_PLUS_EXPR);
9822 gcc_assert (TREE_OPERAND (t, 0) == var);
9823 t = build2 (TREE_CODE (t), TREE_TYPE (decl),
9824 is_doacross ? var : decl,
9825 TREE_OPERAND (t, 1));
9827 gimple_seq *seq;
9828 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE)
9829 seq = &OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (c);
9830 else
9831 seq = &OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c);
9832 gimplify_assign (decl, t, seq);
9837 BITMAP_FREE (has_decl_expr);
9839 if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP)
9841 push_gimplify_context ();
9842 if (TREE_CODE (OMP_FOR_BODY (orig_for_stmt)) != BIND_EXPR)
9844 OMP_FOR_BODY (orig_for_stmt)
9845 = build3 (BIND_EXPR, void_type_node, NULL,
9846 OMP_FOR_BODY (orig_for_stmt), NULL);
9847 TREE_SIDE_EFFECTS (OMP_FOR_BODY (orig_for_stmt)) = 1;
9851 gimple *g = gimplify_and_return_first (OMP_FOR_BODY (orig_for_stmt),
9852 &for_body);
9854 if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP)
9856 if (gimple_code (g) == GIMPLE_BIND)
9857 pop_gimplify_context (g);
9858 else
9859 pop_gimplify_context (NULL);
9862 if (orig_for_stmt != for_stmt)
9863 for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
9865 t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
9866 decl = TREE_OPERAND (t, 0);
9867 struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
9868 if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP)
9869 gimplify_omp_ctxp = ctx->outer_context;
9870 var = create_tmp_var (TREE_TYPE (decl), get_name (decl));
9871 gimplify_omp_ctxp = ctx;
9872 omp_add_variable (gimplify_omp_ctxp, var, GOVD_PRIVATE | GOVD_SEEN);
9873 TREE_OPERAND (t, 0) = var;
9874 t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
9875 TREE_OPERAND (t, 1) = copy_node (TREE_OPERAND (t, 1));
9876 TREE_OPERAND (TREE_OPERAND (t, 1), 0) = var;
9879 gimplify_adjust_omp_clauses (pre_p, for_body,
9880 &OMP_FOR_CLAUSES (orig_for_stmt),
9881 TREE_CODE (orig_for_stmt));
9883 int kind;
9884 switch (TREE_CODE (orig_for_stmt))
9886 case OMP_FOR: kind = GF_OMP_FOR_KIND_FOR; break;
9887 case OMP_SIMD: kind = GF_OMP_FOR_KIND_SIMD; break;
9888 case CILK_SIMD: kind = GF_OMP_FOR_KIND_CILKSIMD; break;
9889 case CILK_FOR: kind = GF_OMP_FOR_KIND_CILKFOR; break;
9890 case OMP_DISTRIBUTE: kind = GF_OMP_FOR_KIND_DISTRIBUTE; break;
9891 case OMP_TASKLOOP: kind = GF_OMP_FOR_KIND_TASKLOOP; break;
9892 case OACC_LOOP: kind = GF_OMP_FOR_KIND_OACC_LOOP; break;
9893 default:
9894 gcc_unreachable ();
9896 gfor = gimple_build_omp_for (for_body, kind, OMP_FOR_CLAUSES (orig_for_stmt),
9897 TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)),
9898 for_pre_body);
9899 if (orig_for_stmt != for_stmt)
9900 gimple_omp_for_set_combined_p (gfor, true);
9901 if (gimplify_omp_ctxp
9902 && (gimplify_omp_ctxp->combined_loop
9903 || (gimplify_omp_ctxp->region_type == ORT_COMBINED_PARALLEL
9904 && gimplify_omp_ctxp->outer_context
9905 && gimplify_omp_ctxp->outer_context->combined_loop)))
9907 gimple_omp_for_set_combined_into_p (gfor, true);
9908 if (gimplify_omp_ctxp->combined_loop)
9909 gcc_assert (TREE_CODE (orig_for_stmt) == OMP_SIMD);
9910 else
9911 gcc_assert (TREE_CODE (orig_for_stmt) == OMP_FOR);
9914 for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
9916 t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
9917 gimple_omp_for_set_index (gfor, i, TREE_OPERAND (t, 0));
9918 gimple_omp_for_set_initial (gfor, i, TREE_OPERAND (t, 1));
9919 t = TREE_VEC_ELT (OMP_FOR_COND (for_stmt), i);
9920 gimple_omp_for_set_cond (gfor, i, TREE_CODE (t));
9921 gimple_omp_for_set_final (gfor, i, TREE_OPERAND (t, 1));
9922 t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
9923 gimple_omp_for_set_incr (gfor, i, TREE_OPERAND (t, 1));
9926 /* OMP_TASKLOOP is gimplified as two GIMPLE_OMP_FOR taskloop
9927 constructs with GIMPLE_OMP_TASK sandwiched in between them.
9928 The outer taskloop stands for computing the number of iterations,
9929 counts for collapsed loops and holding taskloop specific clauses.
9930 The task construct stands for the effect of data sharing on the
9931 explicit task it creates and the inner taskloop stands for expansion
9932 of the static loop inside of the explicit task construct. */
9933 if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP)
9935 tree *gfor_clauses_ptr = gimple_omp_for_clauses_ptr (gfor);
9936 tree task_clauses = NULL_TREE;
9937 tree c = *gfor_clauses_ptr;
9938 tree *gtask_clauses_ptr = &task_clauses;
9939 tree outer_for_clauses = NULL_TREE;
9940 tree *gforo_clauses_ptr = &outer_for_clauses;
9941 for (; c; c = OMP_CLAUSE_CHAIN (c))
9942 switch (OMP_CLAUSE_CODE (c))
9944 /* These clauses are allowed on task, move them there. */
9945 case OMP_CLAUSE_SHARED:
9946 case OMP_CLAUSE_FIRSTPRIVATE:
9947 case OMP_CLAUSE_DEFAULT:
9948 case OMP_CLAUSE_IF:
9949 case OMP_CLAUSE_UNTIED:
9950 case OMP_CLAUSE_FINAL:
9951 case OMP_CLAUSE_MERGEABLE:
9952 case OMP_CLAUSE_PRIORITY:
9953 *gtask_clauses_ptr = c;
9954 gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
9955 break;
9956 case OMP_CLAUSE_PRIVATE:
9957 if (OMP_CLAUSE_PRIVATE_TASKLOOP_IV (c))
9959 /* We want private on outer for and firstprivate
9960 on task. */
9961 *gtask_clauses_ptr
9962 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
9963 OMP_CLAUSE_FIRSTPRIVATE);
9964 OMP_CLAUSE_DECL (*gtask_clauses_ptr) = OMP_CLAUSE_DECL (c);
9965 lang_hooks.decls.omp_finish_clause (*gtask_clauses_ptr, NULL);
9966 gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (*gtask_clauses_ptr);
9967 *gforo_clauses_ptr = c;
9968 gforo_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
9970 else
9972 *gtask_clauses_ptr = c;
9973 gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
9975 break;
9976 /* These clauses go into outer taskloop clauses. */
9977 case OMP_CLAUSE_GRAINSIZE:
9978 case OMP_CLAUSE_NUM_TASKS:
9979 case OMP_CLAUSE_NOGROUP:
9980 *gforo_clauses_ptr = c;
9981 gforo_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
9982 break;
9983 /* Taskloop clause we duplicate on both taskloops. */
9984 case OMP_CLAUSE_COLLAPSE:
9985 *gfor_clauses_ptr = c;
9986 gfor_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
9987 *gforo_clauses_ptr = copy_node (c);
9988 gforo_clauses_ptr = &OMP_CLAUSE_CHAIN (*gforo_clauses_ptr);
9989 break;
9990 /* For lastprivate, keep the clause on inner taskloop, and add
9991 a shared clause on task. If the same decl is also firstprivate,
9992 add also firstprivate clause on the inner taskloop. */
9993 case OMP_CLAUSE_LASTPRIVATE:
9994 if (OMP_CLAUSE_LASTPRIVATE_TASKLOOP_IV (c))
9996 /* For taskloop C++ lastprivate IVs, we want:
9997 1) private on outer taskloop
9998 2) firstprivate and shared on task
9999 3) lastprivate on inner taskloop */
10000 *gtask_clauses_ptr
10001 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
10002 OMP_CLAUSE_FIRSTPRIVATE);
10003 OMP_CLAUSE_DECL (*gtask_clauses_ptr) = OMP_CLAUSE_DECL (c);
10004 lang_hooks.decls.omp_finish_clause (*gtask_clauses_ptr, NULL);
10005 gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (*gtask_clauses_ptr);
10006 OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c) = 1;
10007 *gforo_clauses_ptr = build_omp_clause (OMP_CLAUSE_LOCATION (c),
10008 OMP_CLAUSE_PRIVATE);
10009 OMP_CLAUSE_DECL (*gforo_clauses_ptr) = OMP_CLAUSE_DECL (c);
10010 OMP_CLAUSE_PRIVATE_TASKLOOP_IV (*gforo_clauses_ptr) = 1;
10011 TREE_TYPE (*gforo_clauses_ptr) = TREE_TYPE (c);
10012 gforo_clauses_ptr = &OMP_CLAUSE_CHAIN (*gforo_clauses_ptr);
10014 *gfor_clauses_ptr = c;
10015 gfor_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
10016 *gtask_clauses_ptr
10017 = build_omp_clause (OMP_CLAUSE_LOCATION (c), OMP_CLAUSE_SHARED);
10018 OMP_CLAUSE_DECL (*gtask_clauses_ptr) = OMP_CLAUSE_DECL (c);
10019 if (OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c))
10020 OMP_CLAUSE_SHARED_FIRSTPRIVATE (*gtask_clauses_ptr) = 1;
10021 gtask_clauses_ptr
10022 = &OMP_CLAUSE_CHAIN (*gtask_clauses_ptr);
10023 break;
10024 default:
10025 gcc_unreachable ();
10027 *gfor_clauses_ptr = NULL_TREE;
10028 *gtask_clauses_ptr = NULL_TREE;
10029 *gforo_clauses_ptr = NULL_TREE;
10030 g = gimple_build_bind (NULL_TREE, gfor, NULL_TREE);
10031 g = gimple_build_omp_task (g, task_clauses, NULL_TREE, NULL_TREE,
10032 NULL_TREE, NULL_TREE, NULL_TREE);
10033 gimple_omp_task_set_taskloop_p (g, true);
10034 g = gimple_build_bind (NULL_TREE, g, NULL_TREE);
10035 gomp_for *gforo
10036 = gimple_build_omp_for (g, GF_OMP_FOR_KIND_TASKLOOP, outer_for_clauses,
10037 gimple_omp_for_collapse (gfor),
10038 gimple_omp_for_pre_body (gfor));
10039 gimple_omp_for_set_pre_body (gfor, NULL);
10040 gimple_omp_for_set_combined_p (gforo, true);
10041 gimple_omp_for_set_combined_into_p (gfor, true);
10042 for (i = 0; i < (int) gimple_omp_for_collapse (gfor); i++)
10044 t = unshare_expr (gimple_omp_for_index (gfor, i));
10045 gimple_omp_for_set_index (gforo, i, t);
10046 t = unshare_expr (gimple_omp_for_initial (gfor, i));
10047 gimple_omp_for_set_initial (gforo, i, t);
10048 gimple_omp_for_set_cond (gforo, i,
10049 gimple_omp_for_cond (gfor, i));
10050 t = unshare_expr (gimple_omp_for_final (gfor, i));
10051 gimple_omp_for_set_final (gforo, i, t);
10052 t = unshare_expr (gimple_omp_for_incr (gfor, i));
10053 gimple_omp_for_set_incr (gforo, i, t);
10055 gimplify_seq_add_stmt (pre_p, gforo);
10057 else
10058 gimplify_seq_add_stmt (pre_p, gfor);
10059 if (ret != GS_ALL_DONE)
10060 return GS_ERROR;
10061 *expr_p = NULL_TREE;
10062 return GS_ALL_DONE;
10065 /* Helper function of optimize_target_teams, find OMP_TEAMS inside
10066 of OMP_TARGET's body. */
10068 static tree
10069 find_omp_teams (tree *tp, int *walk_subtrees, void *)
10071 *walk_subtrees = 0;
10072 switch (TREE_CODE (*tp))
10074 case OMP_TEAMS:
10075 return *tp;
10076 case BIND_EXPR:
10077 case STATEMENT_LIST:
10078 *walk_subtrees = 1;
10079 break;
10080 default:
10081 break;
10083 return NULL_TREE;
10086 /* Helper function of optimize_target_teams, determine if the expression
10087 can be computed safely before the target construct on the host. */
10089 static tree
10090 computable_teams_clause (tree *tp, int *walk_subtrees, void *)
10092 splay_tree_node n;
10094 if (TYPE_P (*tp))
10096 *walk_subtrees = 0;
10097 return NULL_TREE;
10099 switch (TREE_CODE (*tp))
10101 case VAR_DECL:
10102 case PARM_DECL:
10103 case RESULT_DECL:
10104 *walk_subtrees = 0;
10105 if (error_operand_p (*tp)
10106 || !INTEGRAL_TYPE_P (TREE_TYPE (*tp))
10107 || DECL_HAS_VALUE_EXPR_P (*tp)
10108 || DECL_THREAD_LOCAL_P (*tp)
10109 || TREE_SIDE_EFFECTS (*tp)
10110 || TREE_THIS_VOLATILE (*tp))
10111 return *tp;
10112 if (is_global_var (*tp)
10113 && (lookup_attribute ("omp declare target", DECL_ATTRIBUTES (*tp))
10114 || lookup_attribute ("omp declare target link",
10115 DECL_ATTRIBUTES (*tp))))
10116 return *tp;
10117 n = splay_tree_lookup (gimplify_omp_ctxp->variables,
10118 (splay_tree_key) *tp);
10119 if (n == NULL)
10121 if (gimplify_omp_ctxp->target_map_scalars_firstprivate)
10122 return NULL_TREE;
10123 return *tp;
10125 else if (n->value & GOVD_LOCAL)
10126 return *tp;
10127 else if (n->value & GOVD_FIRSTPRIVATE)
10128 return NULL_TREE;
10129 else if ((n->value & (GOVD_MAP | GOVD_MAP_ALWAYS_TO))
10130 == (GOVD_MAP | GOVD_MAP_ALWAYS_TO))
10131 return NULL_TREE;
10132 return *tp;
10133 case INTEGER_CST:
10134 if (!INTEGRAL_TYPE_P (TREE_TYPE (*tp)))
10135 return *tp;
10136 return NULL_TREE;
10137 case TARGET_EXPR:
10138 if (TARGET_EXPR_INITIAL (*tp)
10139 || TREE_CODE (TARGET_EXPR_SLOT (*tp)) != VAR_DECL)
10140 return *tp;
10141 return computable_teams_clause (&TARGET_EXPR_SLOT (*tp),
10142 walk_subtrees, NULL);
10143 /* Allow some reasonable subset of integral arithmetics. */
10144 case PLUS_EXPR:
10145 case MINUS_EXPR:
10146 case MULT_EXPR:
10147 case TRUNC_DIV_EXPR:
10148 case CEIL_DIV_EXPR:
10149 case FLOOR_DIV_EXPR:
10150 case ROUND_DIV_EXPR:
10151 case TRUNC_MOD_EXPR:
10152 case CEIL_MOD_EXPR:
10153 case FLOOR_MOD_EXPR:
10154 case ROUND_MOD_EXPR:
10155 case RDIV_EXPR:
10156 case EXACT_DIV_EXPR:
10157 case MIN_EXPR:
10158 case MAX_EXPR:
10159 case LSHIFT_EXPR:
10160 case RSHIFT_EXPR:
10161 case BIT_IOR_EXPR:
10162 case BIT_XOR_EXPR:
10163 case BIT_AND_EXPR:
10164 case NEGATE_EXPR:
10165 case ABS_EXPR:
10166 case BIT_NOT_EXPR:
10167 case NON_LVALUE_EXPR:
10168 CASE_CONVERT:
10169 if (!INTEGRAL_TYPE_P (TREE_TYPE (*tp)))
10170 return *tp;
10171 return NULL_TREE;
10172 /* And disallow anything else, except for comparisons. */
10173 default:
10174 if (COMPARISON_CLASS_P (*tp))
10175 return NULL_TREE;
10176 return *tp;
10180 /* Try to determine if the num_teams and/or thread_limit expressions
10181 can have their values determined already before entering the
10182 target construct.
10183 INTEGER_CSTs trivially are,
10184 integral decls that are firstprivate (explicitly or implicitly)
10185 or explicitly map(always, to:) or map(always, tofrom:) on the target
10186 region too, and expressions involving simple arithmetics on those
10187 too, function calls are not ok, dereferencing something neither etc.
10188 Add NUM_TEAMS and THREAD_LIMIT clauses to the OMP_CLAUSES of
10189 EXPR based on what we find:
10190 0 stands for clause not specified at all, use implementation default
10191 -1 stands for value that can't be determined easily before entering
10192 the target construct.
10193 If teams construct is not present at all, use 1 for num_teams
10194 and 0 for thread_limit (only one team is involved, and the thread
10195 limit is implementation defined. */
10197 static void
10198 optimize_target_teams (tree target, gimple_seq *pre_p)
10200 tree body = OMP_BODY (target);
10201 tree teams = walk_tree (&body, find_omp_teams, NULL, NULL);
10202 tree num_teams = integer_zero_node;
10203 tree thread_limit = integer_zero_node;
10204 location_t num_teams_loc = EXPR_LOCATION (target);
10205 location_t thread_limit_loc = EXPR_LOCATION (target);
10206 tree c, *p, expr;
10207 struct gimplify_omp_ctx *target_ctx = gimplify_omp_ctxp;
10209 if (teams == NULL_TREE)
10210 num_teams = integer_one_node;
10211 else
10212 for (c = OMP_TEAMS_CLAUSES (teams); c; c = OMP_CLAUSE_CHAIN (c))
10214 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_NUM_TEAMS)
10216 p = &num_teams;
10217 num_teams_loc = OMP_CLAUSE_LOCATION (c);
10219 else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_THREAD_LIMIT)
10221 p = &thread_limit;
10222 thread_limit_loc = OMP_CLAUSE_LOCATION (c);
10224 else
10225 continue;
10226 expr = OMP_CLAUSE_OPERAND (c, 0);
10227 if (TREE_CODE (expr) == INTEGER_CST)
10229 *p = expr;
10230 continue;
10232 if (walk_tree (&expr, computable_teams_clause, NULL, NULL))
10234 *p = integer_minus_one_node;
10235 continue;
10237 *p = expr;
10238 gimplify_omp_ctxp = gimplify_omp_ctxp->outer_context;
10239 if (gimplify_expr (p, pre_p, NULL, is_gimple_val, fb_rvalue, false)
10240 == GS_ERROR)
10242 gimplify_omp_ctxp = target_ctx;
10243 *p = integer_minus_one_node;
10244 continue;
10246 gimplify_omp_ctxp = target_ctx;
10247 if (!DECL_P (expr) && TREE_CODE (expr) != TARGET_EXPR)
10248 OMP_CLAUSE_OPERAND (c, 0) = *p;
10250 c = build_omp_clause (thread_limit_loc, OMP_CLAUSE_THREAD_LIMIT);
10251 OMP_CLAUSE_THREAD_LIMIT_EXPR (c) = thread_limit;
10252 OMP_CLAUSE_CHAIN (c) = OMP_TARGET_CLAUSES (target);
10253 OMP_TARGET_CLAUSES (target) = c;
10254 c = build_omp_clause (num_teams_loc, OMP_CLAUSE_NUM_TEAMS);
10255 OMP_CLAUSE_NUM_TEAMS_EXPR (c) = num_teams;
10256 OMP_CLAUSE_CHAIN (c) = OMP_TARGET_CLAUSES (target);
10257 OMP_TARGET_CLAUSES (target) = c;
10260 /* Gimplify the gross structure of several OMP constructs. */
10262 static void
10263 gimplify_omp_workshare (tree *expr_p, gimple_seq *pre_p)
10265 tree expr = *expr_p;
10266 gimple *stmt;
10267 gimple_seq body = NULL;
10268 enum omp_region_type ort;
10270 switch (TREE_CODE (expr))
10272 case OMP_SECTIONS:
10273 case OMP_SINGLE:
10274 ort = ORT_WORKSHARE;
10275 break;
10276 case OMP_TARGET:
10277 ort = OMP_TARGET_COMBINED (expr) ? ORT_COMBINED_TARGET : ORT_TARGET;
10278 break;
10279 case OACC_KERNELS:
10280 ort = ORT_ACC_KERNELS;
10281 break;
10282 case OACC_PARALLEL:
10283 ort = ORT_ACC_PARALLEL;
10284 break;
10285 case OACC_DATA:
10286 ort = ORT_ACC_DATA;
10287 break;
10288 case OMP_TARGET_DATA:
10289 ort = ORT_TARGET_DATA;
10290 break;
10291 case OMP_TEAMS:
10292 ort = OMP_TEAMS_COMBINED (expr) ? ORT_COMBINED_TEAMS : ORT_TEAMS;
10293 break;
10294 case OACC_HOST_DATA:
10295 ort = ORT_ACC_HOST_DATA;
10296 break;
10297 default:
10298 gcc_unreachable ();
10300 gimplify_scan_omp_clauses (&OMP_CLAUSES (expr), pre_p, ort,
10301 TREE_CODE (expr));
10302 if (TREE_CODE (expr) == OMP_TARGET)
10303 optimize_target_teams (expr, pre_p);
10304 if ((ort & (ORT_TARGET | ORT_TARGET_DATA)) != 0)
10306 push_gimplify_context ();
10307 gimple *g = gimplify_and_return_first (OMP_BODY (expr), &body);
10308 if (gimple_code (g) == GIMPLE_BIND)
10309 pop_gimplify_context (g);
10310 else
10311 pop_gimplify_context (NULL);
10312 if ((ort & ORT_TARGET_DATA) != 0)
10314 enum built_in_function end_ix;
10315 switch (TREE_CODE (expr))
10317 case OACC_DATA:
10318 case OACC_HOST_DATA:
10319 end_ix = BUILT_IN_GOACC_DATA_END;
10320 break;
10321 case OMP_TARGET_DATA:
10322 end_ix = BUILT_IN_GOMP_TARGET_END_DATA;
10323 break;
10324 default:
10325 gcc_unreachable ();
10327 tree fn = builtin_decl_explicit (end_ix);
10328 g = gimple_build_call (fn, 0);
10329 gimple_seq cleanup = NULL;
10330 gimple_seq_add_stmt (&cleanup, g);
10331 g = gimple_build_try (body, cleanup, GIMPLE_TRY_FINALLY);
10332 body = NULL;
10333 gimple_seq_add_stmt (&body, g);
10336 else
10337 gimplify_and_add (OMP_BODY (expr), &body);
10338 gimplify_adjust_omp_clauses (pre_p, body, &OMP_CLAUSES (expr),
10339 TREE_CODE (expr));
10341 switch (TREE_CODE (expr))
10343 case OACC_DATA:
10344 stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_DATA,
10345 OMP_CLAUSES (expr));
10346 break;
10347 case OACC_KERNELS:
10348 stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_KERNELS,
10349 OMP_CLAUSES (expr));
10350 break;
10351 case OACC_HOST_DATA:
10352 stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_HOST_DATA,
10353 OMP_CLAUSES (expr));
10354 break;
10355 case OACC_PARALLEL:
10356 stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_PARALLEL,
10357 OMP_CLAUSES (expr));
10358 break;
10359 case OMP_SECTIONS:
10360 stmt = gimple_build_omp_sections (body, OMP_CLAUSES (expr));
10361 break;
10362 case OMP_SINGLE:
10363 stmt = gimple_build_omp_single (body, OMP_CLAUSES (expr));
10364 break;
10365 case OMP_TARGET:
10366 stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_REGION,
10367 OMP_CLAUSES (expr));
10368 break;
10369 case OMP_TARGET_DATA:
10370 stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_DATA,
10371 OMP_CLAUSES (expr));
10372 break;
10373 case OMP_TEAMS:
10374 stmt = gimple_build_omp_teams (body, OMP_CLAUSES (expr));
10375 break;
10376 default:
10377 gcc_unreachable ();
10380 gimplify_seq_add_stmt (pre_p, stmt);
10381 *expr_p = NULL_TREE;
10384 /* Gimplify the gross structure of OpenACC enter/exit data, update, and OpenMP
10385 target update constructs. */
10387 static void
10388 gimplify_omp_target_update (tree *expr_p, gimple_seq *pre_p)
10390 tree expr = *expr_p;
10391 int kind;
10392 gomp_target *stmt;
10393 enum omp_region_type ort = ORT_WORKSHARE;
10395 switch (TREE_CODE (expr))
10397 case OACC_ENTER_DATA:
10398 case OACC_EXIT_DATA:
10399 kind = GF_OMP_TARGET_KIND_OACC_ENTER_EXIT_DATA;
10400 ort = ORT_ACC;
10401 break;
10402 case OACC_UPDATE:
10403 kind = GF_OMP_TARGET_KIND_OACC_UPDATE;
10404 ort = ORT_ACC;
10405 break;
10406 case OMP_TARGET_UPDATE:
10407 kind = GF_OMP_TARGET_KIND_UPDATE;
10408 break;
10409 case OMP_TARGET_ENTER_DATA:
10410 kind = GF_OMP_TARGET_KIND_ENTER_DATA;
10411 break;
10412 case OMP_TARGET_EXIT_DATA:
10413 kind = GF_OMP_TARGET_KIND_EXIT_DATA;
10414 break;
10415 default:
10416 gcc_unreachable ();
10418 gimplify_scan_omp_clauses (&OMP_STANDALONE_CLAUSES (expr), pre_p,
10419 ort, TREE_CODE (expr));
10420 gimplify_adjust_omp_clauses (pre_p, NULL, &OMP_STANDALONE_CLAUSES (expr),
10421 TREE_CODE (expr));
10422 stmt = gimple_build_omp_target (NULL, kind, OMP_STANDALONE_CLAUSES (expr));
10424 gimplify_seq_add_stmt (pre_p, stmt);
10425 *expr_p = NULL_TREE;
10428 /* A subroutine of gimplify_omp_atomic. The front end is supposed to have
10429 stabilized the lhs of the atomic operation as *ADDR. Return true if
10430 EXPR is this stabilized form. */
10432 static bool
10433 goa_lhs_expr_p (tree expr, tree addr)
10435 /* Also include casts to other type variants. The C front end is fond
10436 of adding these for e.g. volatile variables. This is like
10437 STRIP_TYPE_NOPS but includes the main variant lookup. */
10438 STRIP_USELESS_TYPE_CONVERSION (expr);
10440 if (TREE_CODE (expr) == INDIRECT_REF)
10442 expr = TREE_OPERAND (expr, 0);
10443 while (expr != addr
10444 && (CONVERT_EXPR_P (expr)
10445 || TREE_CODE (expr) == NON_LVALUE_EXPR)
10446 && TREE_CODE (expr) == TREE_CODE (addr)
10447 && types_compatible_p (TREE_TYPE (expr), TREE_TYPE (addr)))
10449 expr = TREE_OPERAND (expr, 0);
10450 addr = TREE_OPERAND (addr, 0);
10452 if (expr == addr)
10453 return true;
10454 return (TREE_CODE (addr) == ADDR_EXPR
10455 && TREE_CODE (expr) == ADDR_EXPR
10456 && TREE_OPERAND (addr, 0) == TREE_OPERAND (expr, 0));
10458 if (TREE_CODE (addr) == ADDR_EXPR && expr == TREE_OPERAND (addr, 0))
10459 return true;
10460 return false;
10463 /* Walk *EXPR_P and replace appearances of *LHS_ADDR with LHS_VAR. If an
10464 expression does not involve the lhs, evaluate it into a temporary.
10465 Return 1 if the lhs appeared as a subexpression, 0 if it did not,
10466 or -1 if an error was encountered. */
10468 static int
10469 goa_stabilize_expr (tree *expr_p, gimple_seq *pre_p, tree lhs_addr,
10470 tree lhs_var)
10472 tree expr = *expr_p;
10473 int saw_lhs;
10475 if (goa_lhs_expr_p (expr, lhs_addr))
10477 *expr_p = lhs_var;
10478 return 1;
10480 if (is_gimple_val (expr))
10481 return 0;
10483 saw_lhs = 0;
10484 switch (TREE_CODE_CLASS (TREE_CODE (expr)))
10486 case tcc_binary:
10487 case tcc_comparison:
10488 saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 1), pre_p, lhs_addr,
10489 lhs_var);
10490 /* FALLTHRU */
10491 case tcc_unary:
10492 saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 0), pre_p, lhs_addr,
10493 lhs_var);
10494 break;
10495 case tcc_expression:
10496 switch (TREE_CODE (expr))
10498 case TRUTH_ANDIF_EXPR:
10499 case TRUTH_ORIF_EXPR:
10500 case TRUTH_AND_EXPR:
10501 case TRUTH_OR_EXPR:
10502 case TRUTH_XOR_EXPR:
10503 saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 1), pre_p,
10504 lhs_addr, lhs_var);
10505 /* FALLTHRU */
10506 case TRUTH_NOT_EXPR:
10507 saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 0), pre_p,
10508 lhs_addr, lhs_var);
10509 break;
10510 case COMPOUND_EXPR:
10511 /* Break out any preevaluations from cp_build_modify_expr. */
10512 for (; TREE_CODE (expr) == COMPOUND_EXPR;
10513 expr = TREE_OPERAND (expr, 1))
10514 gimplify_stmt (&TREE_OPERAND (expr, 0), pre_p);
10515 *expr_p = expr;
10516 return goa_stabilize_expr (expr_p, pre_p, lhs_addr, lhs_var);
10517 default:
10518 break;
10520 break;
10521 default:
10522 break;
10525 if (saw_lhs == 0)
10527 enum gimplify_status gs;
10528 gs = gimplify_expr (expr_p, pre_p, NULL, is_gimple_val, fb_rvalue);
10529 if (gs != GS_ALL_DONE)
10530 saw_lhs = -1;
10533 return saw_lhs;
10536 /* Gimplify an OMP_ATOMIC statement. */
10538 static enum gimplify_status
10539 gimplify_omp_atomic (tree *expr_p, gimple_seq *pre_p)
10541 tree addr = TREE_OPERAND (*expr_p, 0);
10542 tree rhs = TREE_CODE (*expr_p) == OMP_ATOMIC_READ
10543 ? NULL : TREE_OPERAND (*expr_p, 1);
10544 tree type = TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (addr)));
10545 tree tmp_load;
10546 gomp_atomic_load *loadstmt;
10547 gomp_atomic_store *storestmt;
10549 tmp_load = create_tmp_reg (type);
10550 if (rhs && goa_stabilize_expr (&rhs, pre_p, addr, tmp_load) < 0)
10551 return GS_ERROR;
10553 if (gimplify_expr (&addr, pre_p, NULL, is_gimple_val, fb_rvalue)
10554 != GS_ALL_DONE)
10555 return GS_ERROR;
10557 loadstmt = gimple_build_omp_atomic_load (tmp_load, addr);
10558 gimplify_seq_add_stmt (pre_p, loadstmt);
10559 if (rhs && gimplify_expr (&rhs, pre_p, NULL, is_gimple_val, fb_rvalue)
10560 != GS_ALL_DONE)
10561 return GS_ERROR;
10563 if (TREE_CODE (*expr_p) == OMP_ATOMIC_READ)
10564 rhs = tmp_load;
10565 storestmt = gimple_build_omp_atomic_store (rhs);
10566 gimplify_seq_add_stmt (pre_p, storestmt);
10567 if (OMP_ATOMIC_SEQ_CST (*expr_p))
10569 gimple_omp_atomic_set_seq_cst (loadstmt);
10570 gimple_omp_atomic_set_seq_cst (storestmt);
10572 switch (TREE_CODE (*expr_p))
10574 case OMP_ATOMIC_READ:
10575 case OMP_ATOMIC_CAPTURE_OLD:
10576 *expr_p = tmp_load;
10577 gimple_omp_atomic_set_need_value (loadstmt);
10578 break;
10579 case OMP_ATOMIC_CAPTURE_NEW:
10580 *expr_p = rhs;
10581 gimple_omp_atomic_set_need_value (storestmt);
10582 break;
10583 default:
10584 *expr_p = NULL;
10585 break;
10588 return GS_ALL_DONE;
10591 /* Gimplify a TRANSACTION_EXPR. This involves gimplification of the
10592 body, and adding some EH bits. */
10594 static enum gimplify_status
10595 gimplify_transaction (tree *expr_p, gimple_seq *pre_p)
10597 tree expr = *expr_p, temp, tbody = TRANSACTION_EXPR_BODY (expr);
10598 gimple *body_stmt;
10599 gtransaction *trans_stmt;
10600 gimple_seq body = NULL;
10601 int subcode = 0;
10603 /* Wrap the transaction body in a BIND_EXPR so we have a context
10604 where to put decls for OMP. */
10605 if (TREE_CODE (tbody) != BIND_EXPR)
10607 tree bind = build3 (BIND_EXPR, void_type_node, NULL, tbody, NULL);
10608 TREE_SIDE_EFFECTS (bind) = 1;
10609 SET_EXPR_LOCATION (bind, EXPR_LOCATION (tbody));
10610 TRANSACTION_EXPR_BODY (expr) = bind;
10613 push_gimplify_context ();
10614 temp = voidify_wrapper_expr (*expr_p, NULL);
10616 body_stmt = gimplify_and_return_first (TRANSACTION_EXPR_BODY (expr), &body);
10617 pop_gimplify_context (body_stmt);
10619 trans_stmt = gimple_build_transaction (body);
10620 if (TRANSACTION_EXPR_OUTER (expr))
10621 subcode = GTMA_IS_OUTER;
10622 else if (TRANSACTION_EXPR_RELAXED (expr))
10623 subcode = GTMA_IS_RELAXED;
10624 gimple_transaction_set_subcode (trans_stmt, subcode);
10626 gimplify_seq_add_stmt (pre_p, trans_stmt);
10628 if (temp)
10630 *expr_p = temp;
10631 return GS_OK;
10634 *expr_p = NULL_TREE;
10635 return GS_ALL_DONE;
10638 /* Gimplify an OMP_ORDERED construct. EXPR is the tree version. BODY
10639 is the OMP_BODY of the original EXPR (which has already been
10640 gimplified so it's not present in the EXPR).
10642 Return the gimplified GIMPLE_OMP_ORDERED tuple. */
10644 static gimple *
10645 gimplify_omp_ordered (tree expr, gimple_seq body)
10647 tree c, decls;
10648 int failures = 0;
10649 unsigned int i;
10650 tree source_c = NULL_TREE;
10651 tree sink_c = NULL_TREE;
10653 if (gimplify_omp_ctxp)
10655 for (c = OMP_ORDERED_CLAUSES (expr); c; c = OMP_CLAUSE_CHAIN (c))
10656 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
10657 && gimplify_omp_ctxp->loop_iter_var.is_empty ()
10658 && (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK
10659 || OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SOURCE))
10661 error_at (OMP_CLAUSE_LOCATION (c),
10662 "%<ordered%> construct with %<depend%> clause must be "
10663 "closely nested inside a loop with %<ordered%> clause "
10664 "with a parameter");
10665 failures++;
10667 else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
10668 && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK)
10670 bool fail = false;
10671 for (decls = OMP_CLAUSE_DECL (c), i = 0;
10672 decls && TREE_CODE (decls) == TREE_LIST;
10673 decls = TREE_CHAIN (decls), ++i)
10674 if (i >= gimplify_omp_ctxp->loop_iter_var.length () / 2)
10675 continue;
10676 else if (TREE_VALUE (decls)
10677 != gimplify_omp_ctxp->loop_iter_var[2 * i])
10679 error_at (OMP_CLAUSE_LOCATION (c),
10680 "variable %qE is not an iteration "
10681 "of outermost loop %d, expected %qE",
10682 TREE_VALUE (decls), i + 1,
10683 gimplify_omp_ctxp->loop_iter_var[2 * i]);
10684 fail = true;
10685 failures++;
10687 else
10688 TREE_VALUE (decls)
10689 = gimplify_omp_ctxp->loop_iter_var[2 * i + 1];
10690 if (!fail && i != gimplify_omp_ctxp->loop_iter_var.length () / 2)
10692 error_at (OMP_CLAUSE_LOCATION (c),
10693 "number of variables in %<depend(sink)%> "
10694 "clause does not match number of "
10695 "iteration variables");
10696 failures++;
10698 sink_c = c;
10700 else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
10701 && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SOURCE)
10703 if (source_c)
10705 error_at (OMP_CLAUSE_LOCATION (c),
10706 "more than one %<depend(source)%> clause on an "
10707 "%<ordered%> construct");
10708 failures++;
10710 else
10711 source_c = c;
10714 if (source_c && sink_c)
10716 error_at (OMP_CLAUSE_LOCATION (source_c),
10717 "%<depend(source)%> clause specified together with "
10718 "%<depend(sink:)%> clauses on the same construct");
10719 failures++;
10722 if (failures)
10723 return gimple_build_nop ();
10724 return gimple_build_omp_ordered (body, OMP_ORDERED_CLAUSES (expr));
10727 /* Convert the GENERIC expression tree *EXPR_P to GIMPLE. If the
10728 expression produces a value to be used as an operand inside a GIMPLE
10729 statement, the value will be stored back in *EXPR_P. This value will
10730 be a tree of class tcc_declaration, tcc_constant, tcc_reference or
10731 an SSA_NAME. The corresponding sequence of GIMPLE statements is
10732 emitted in PRE_P and POST_P.
10734 Additionally, this process may overwrite parts of the input
10735 expression during gimplification. Ideally, it should be
10736 possible to do non-destructive gimplification.
10738 EXPR_P points to the GENERIC expression to convert to GIMPLE. If
10739 the expression needs to evaluate to a value to be used as
10740 an operand in a GIMPLE statement, this value will be stored in
10741 *EXPR_P on exit. This happens when the caller specifies one
10742 of fb_lvalue or fb_rvalue fallback flags.
10744 PRE_P will contain the sequence of GIMPLE statements corresponding
10745 to the evaluation of EXPR and all the side-effects that must
10746 be executed before the main expression. On exit, the last
10747 statement of PRE_P is the core statement being gimplified. For
10748 instance, when gimplifying 'if (++a)' the last statement in
10749 PRE_P will be 'if (t.1)' where t.1 is the result of
10750 pre-incrementing 'a'.
10752 POST_P will contain the sequence of GIMPLE statements corresponding
10753 to the evaluation of all the side-effects that must be executed
10754 after the main expression. If this is NULL, the post
10755 side-effects are stored at the end of PRE_P.
10757 The reason why the output is split in two is to handle post
10758 side-effects explicitly. In some cases, an expression may have
10759 inner and outer post side-effects which need to be emitted in
10760 an order different from the one given by the recursive
10761 traversal. For instance, for the expression (*p--)++ the post
10762 side-effects of '--' must actually occur *after* the post
10763 side-effects of '++'. However, gimplification will first visit
10764 the inner expression, so if a separate POST sequence was not
10765 used, the resulting sequence would be:
10767 1 t.1 = *p
10768 2 p = p - 1
10769 3 t.2 = t.1 + 1
10770 4 *p = t.2
10772 However, the post-decrement operation in line #2 must not be
10773 evaluated until after the store to *p at line #4, so the
10774 correct sequence should be:
10776 1 t.1 = *p
10777 2 t.2 = t.1 + 1
10778 3 *p = t.2
10779 4 p = p - 1
10781 So, by specifying a separate post queue, it is possible
10782 to emit the post side-effects in the correct order.
10783 If POST_P is NULL, an internal queue will be used. Before
10784 returning to the caller, the sequence POST_P is appended to
10785 the main output sequence PRE_P.
10787 GIMPLE_TEST_F points to a function that takes a tree T and
10788 returns nonzero if T is in the GIMPLE form requested by the
10789 caller. The GIMPLE predicates are in gimple.c.
10791 FALLBACK tells the function what sort of a temporary we want if
10792 gimplification cannot produce an expression that complies with
10793 GIMPLE_TEST_F.
10795 fb_none means that no temporary should be generated
10796 fb_rvalue means that an rvalue is OK to generate
10797 fb_lvalue means that an lvalue is OK to generate
10798 fb_either means that either is OK, but an lvalue is preferable.
10799 fb_mayfail means that gimplification may fail (in which case
10800 GS_ERROR will be returned)
10802 The return value is either GS_ERROR or GS_ALL_DONE, since this
10803 function iterates until EXPR is completely gimplified or an error
10804 occurs. */
10806 enum gimplify_status
10807 gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
10808 bool (*gimple_test_f) (tree), fallback_t fallback)
10810 tree tmp;
10811 gimple_seq internal_pre = NULL;
10812 gimple_seq internal_post = NULL;
10813 tree save_expr;
10814 bool is_statement;
10815 location_t saved_location;
10816 enum gimplify_status ret;
10817 gimple_stmt_iterator pre_last_gsi, post_last_gsi;
10819 save_expr = *expr_p;
10820 if (save_expr == NULL_TREE)
10821 return GS_ALL_DONE;
10823 /* If we are gimplifying a top-level statement, PRE_P must be valid. */
10824 is_statement = gimple_test_f == is_gimple_stmt;
10825 if (is_statement)
10826 gcc_assert (pre_p);
10828 /* Consistency checks. */
10829 if (gimple_test_f == is_gimple_reg)
10830 gcc_assert (fallback & (fb_rvalue | fb_lvalue));
10831 else if (gimple_test_f == is_gimple_val
10832 || gimple_test_f == is_gimple_call_addr
10833 || gimple_test_f == is_gimple_condexpr
10834 || gimple_test_f == is_gimple_mem_rhs
10835 || gimple_test_f == is_gimple_mem_rhs_or_call
10836 || gimple_test_f == is_gimple_reg_rhs
10837 || gimple_test_f == is_gimple_reg_rhs_or_call
10838 || gimple_test_f == is_gimple_asm_val
10839 || gimple_test_f == is_gimple_mem_ref_addr)
10840 gcc_assert (fallback & fb_rvalue);
10841 else if (gimple_test_f == is_gimple_min_lval
10842 || gimple_test_f == is_gimple_lvalue)
10843 gcc_assert (fallback & fb_lvalue);
10844 else if (gimple_test_f == is_gimple_addressable)
10845 gcc_assert (fallback & fb_either);
10846 else if (gimple_test_f == is_gimple_stmt)
10847 gcc_assert (fallback == fb_none);
10848 else
10850 /* We should have recognized the GIMPLE_TEST_F predicate to
10851 know what kind of fallback to use in case a temporary is
10852 needed to hold the value or address of *EXPR_P. */
10853 gcc_unreachable ();
10856 /* We used to check the predicate here and return immediately if it
10857 succeeds. This is wrong; the design is for gimplification to be
10858 idempotent, and for the predicates to only test for valid forms, not
10859 whether they are fully simplified. */
10860 if (pre_p == NULL)
10861 pre_p = &internal_pre;
10863 if (post_p == NULL)
10864 post_p = &internal_post;
10866 /* Remember the last statements added to PRE_P and POST_P. Every
10867 new statement added by the gimplification helpers needs to be
10868 annotated with location information. To centralize the
10869 responsibility, we remember the last statement that had been
10870 added to both queues before gimplifying *EXPR_P. If
10871 gimplification produces new statements in PRE_P and POST_P, those
10872 statements will be annotated with the same location information
10873 as *EXPR_P. */
10874 pre_last_gsi = gsi_last (*pre_p);
10875 post_last_gsi = gsi_last (*post_p);
10877 saved_location = input_location;
10878 if (save_expr != error_mark_node
10879 && EXPR_HAS_LOCATION (*expr_p))
10880 input_location = EXPR_LOCATION (*expr_p);
10882 /* Loop over the specific gimplifiers until the toplevel node
10883 remains the same. */
10886 /* Strip away as many useless type conversions as possible
10887 at the toplevel. */
10888 STRIP_USELESS_TYPE_CONVERSION (*expr_p);
10890 /* Remember the expr. */
10891 save_expr = *expr_p;
10893 /* Die, die, die, my darling. */
10894 if (save_expr == error_mark_node
10895 || (TREE_TYPE (save_expr)
10896 && TREE_TYPE (save_expr) == error_mark_node))
10898 ret = GS_ERROR;
10899 break;
10902 /* Do any language-specific gimplification. */
10903 ret = ((enum gimplify_status)
10904 lang_hooks.gimplify_expr (expr_p, pre_p, post_p));
10905 if (ret == GS_OK)
10907 if (*expr_p == NULL_TREE)
10908 break;
10909 if (*expr_p != save_expr)
10910 continue;
10912 else if (ret != GS_UNHANDLED)
10913 break;
10915 /* Make sure that all the cases set 'ret' appropriately. */
10916 ret = GS_UNHANDLED;
10917 switch (TREE_CODE (*expr_p))
10919 /* First deal with the special cases. */
10921 case POSTINCREMENT_EXPR:
10922 case POSTDECREMENT_EXPR:
10923 case PREINCREMENT_EXPR:
10924 case PREDECREMENT_EXPR:
10925 ret = gimplify_self_mod_expr (expr_p, pre_p, post_p,
10926 fallback != fb_none,
10927 TREE_TYPE (*expr_p));
10928 break;
10930 case VIEW_CONVERT_EXPR:
10931 if (is_gimple_reg_type (TREE_TYPE (*expr_p))
10932 && is_gimple_reg_type (TREE_TYPE (TREE_OPERAND (*expr_p, 0))))
10934 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
10935 post_p, is_gimple_val, fb_rvalue);
10936 recalculate_side_effects (*expr_p);
10937 break;
10939 /* Fallthru. */
10941 case ARRAY_REF:
10942 case ARRAY_RANGE_REF:
10943 case REALPART_EXPR:
10944 case IMAGPART_EXPR:
10945 case COMPONENT_REF:
10946 ret = gimplify_compound_lval (expr_p, pre_p, post_p,
10947 fallback ? fallback : fb_rvalue);
10948 break;
10950 case COND_EXPR:
10951 ret = gimplify_cond_expr (expr_p, pre_p, fallback);
10953 /* C99 code may assign to an array in a structure value of a
10954 conditional expression, and this has undefined behavior
10955 only on execution, so create a temporary if an lvalue is
10956 required. */
10957 if (fallback == fb_lvalue)
10959 *expr_p = get_initialized_tmp_var (*expr_p, pre_p, post_p, false);
10960 mark_addressable (*expr_p);
10961 ret = GS_OK;
10963 break;
10965 case CALL_EXPR:
10966 ret = gimplify_call_expr (expr_p, pre_p, fallback != fb_none);
10968 /* C99 code may assign to an array in a structure returned
10969 from a function, and this has undefined behavior only on
10970 execution, so create a temporary if an lvalue is
10971 required. */
10972 if (fallback == fb_lvalue)
10974 *expr_p = get_initialized_tmp_var (*expr_p, pre_p, post_p, false);
10975 mark_addressable (*expr_p);
10976 ret = GS_OK;
10978 break;
10980 case TREE_LIST:
10981 gcc_unreachable ();
10983 case COMPOUND_EXPR:
10984 ret = gimplify_compound_expr (expr_p, pre_p, fallback != fb_none);
10985 break;
10987 case COMPOUND_LITERAL_EXPR:
10988 ret = gimplify_compound_literal_expr (expr_p, pre_p,
10989 gimple_test_f, fallback);
10990 break;
10992 case MODIFY_EXPR:
10993 case INIT_EXPR:
10994 ret = gimplify_modify_expr (expr_p, pre_p, post_p,
10995 fallback != fb_none);
10996 break;
10998 case TRUTH_ANDIF_EXPR:
10999 case TRUTH_ORIF_EXPR:
11001 /* Preserve the original type of the expression and the
11002 source location of the outer expression. */
11003 tree org_type = TREE_TYPE (*expr_p);
11004 *expr_p = gimple_boolify (*expr_p);
11005 *expr_p = build3_loc (input_location, COND_EXPR,
11006 org_type, *expr_p,
11007 fold_convert_loc
11008 (input_location,
11009 org_type, boolean_true_node),
11010 fold_convert_loc
11011 (input_location,
11012 org_type, boolean_false_node));
11013 ret = GS_OK;
11014 break;
11017 case TRUTH_NOT_EXPR:
11019 tree type = TREE_TYPE (*expr_p);
11020 /* The parsers are careful to generate TRUTH_NOT_EXPR
11021 only with operands that are always zero or one.
11022 We do not fold here but handle the only interesting case
11023 manually, as fold may re-introduce the TRUTH_NOT_EXPR. */
11024 *expr_p = gimple_boolify (*expr_p);
11025 if (TYPE_PRECISION (TREE_TYPE (*expr_p)) == 1)
11026 *expr_p = build1_loc (input_location, BIT_NOT_EXPR,
11027 TREE_TYPE (*expr_p),
11028 TREE_OPERAND (*expr_p, 0));
11029 else
11030 *expr_p = build2_loc (input_location, BIT_XOR_EXPR,
11031 TREE_TYPE (*expr_p),
11032 TREE_OPERAND (*expr_p, 0),
11033 build_int_cst (TREE_TYPE (*expr_p), 1));
11034 if (!useless_type_conversion_p (type, TREE_TYPE (*expr_p)))
11035 *expr_p = fold_convert_loc (input_location, type, *expr_p);
11036 ret = GS_OK;
11037 break;
11040 case ADDR_EXPR:
11041 ret = gimplify_addr_expr (expr_p, pre_p, post_p);
11042 break;
11044 case ANNOTATE_EXPR:
11046 tree cond = TREE_OPERAND (*expr_p, 0);
11047 tree kind = TREE_OPERAND (*expr_p, 1);
11048 tree type = TREE_TYPE (cond);
11049 if (!INTEGRAL_TYPE_P (type))
11051 *expr_p = cond;
11052 ret = GS_OK;
11053 break;
11055 tree tmp = create_tmp_var (type);
11056 gimplify_arg (&cond, pre_p, EXPR_LOCATION (*expr_p));
11057 gcall *call
11058 = gimple_build_call_internal (IFN_ANNOTATE, 2, cond, kind);
11059 gimple_call_set_lhs (call, tmp);
11060 gimplify_seq_add_stmt (pre_p, call);
11061 *expr_p = tmp;
11062 ret = GS_ALL_DONE;
11063 break;
11066 case VA_ARG_EXPR:
11067 ret = gimplify_va_arg_expr (expr_p, pre_p, post_p);
11068 break;
11070 CASE_CONVERT:
11071 if (IS_EMPTY_STMT (*expr_p))
11073 ret = GS_ALL_DONE;
11074 break;
11077 if (VOID_TYPE_P (TREE_TYPE (*expr_p))
11078 || fallback == fb_none)
11080 /* Just strip a conversion to void (or in void context) and
11081 try again. */
11082 *expr_p = TREE_OPERAND (*expr_p, 0);
11083 ret = GS_OK;
11084 break;
11087 ret = gimplify_conversion (expr_p);
11088 if (ret == GS_ERROR)
11089 break;
11090 if (*expr_p != save_expr)
11091 break;
11092 /* FALLTHRU */
11094 case FIX_TRUNC_EXPR:
11095 /* unary_expr: ... | '(' cast ')' val | ... */
11096 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
11097 is_gimple_val, fb_rvalue);
11098 recalculate_side_effects (*expr_p);
11099 break;
11101 case INDIRECT_REF:
11103 bool volatilep = TREE_THIS_VOLATILE (*expr_p);
11104 bool notrap = TREE_THIS_NOTRAP (*expr_p);
11105 tree saved_ptr_type = TREE_TYPE (TREE_OPERAND (*expr_p, 0));
11107 *expr_p = fold_indirect_ref_loc (input_location, *expr_p);
11108 if (*expr_p != save_expr)
11110 ret = GS_OK;
11111 break;
11114 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
11115 is_gimple_reg, fb_rvalue);
11116 if (ret == GS_ERROR)
11117 break;
11119 recalculate_side_effects (*expr_p);
11120 *expr_p = fold_build2_loc (input_location, MEM_REF,
11121 TREE_TYPE (*expr_p),
11122 TREE_OPERAND (*expr_p, 0),
11123 build_int_cst (saved_ptr_type, 0));
11124 TREE_THIS_VOLATILE (*expr_p) = volatilep;
11125 TREE_THIS_NOTRAP (*expr_p) = notrap;
11126 ret = GS_OK;
11127 break;
11130 /* We arrive here through the various re-gimplifcation paths. */
11131 case MEM_REF:
11132 /* First try re-folding the whole thing. */
11133 tmp = fold_binary (MEM_REF, TREE_TYPE (*expr_p),
11134 TREE_OPERAND (*expr_p, 0),
11135 TREE_OPERAND (*expr_p, 1));
11136 if (tmp)
11138 REF_REVERSE_STORAGE_ORDER (tmp)
11139 = REF_REVERSE_STORAGE_ORDER (*expr_p);
11140 *expr_p = tmp;
11141 recalculate_side_effects (*expr_p);
11142 ret = GS_OK;
11143 break;
11145 /* Avoid re-gimplifying the address operand if it is already
11146 in suitable form. Re-gimplifying would mark the address
11147 operand addressable. Always gimplify when not in SSA form
11148 as we still may have to gimplify decls with value-exprs. */
11149 if (!gimplify_ctxp || !gimple_in_ssa_p (cfun)
11150 || !is_gimple_mem_ref_addr (TREE_OPERAND (*expr_p, 0)))
11152 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
11153 is_gimple_mem_ref_addr, fb_rvalue);
11154 if (ret == GS_ERROR)
11155 break;
11157 recalculate_side_effects (*expr_p);
11158 ret = GS_ALL_DONE;
11159 break;
11161 /* Constants need not be gimplified. */
11162 case INTEGER_CST:
11163 case REAL_CST:
11164 case FIXED_CST:
11165 case STRING_CST:
11166 case COMPLEX_CST:
11167 case VECTOR_CST:
11168 /* Drop the overflow flag on constants, we do not want
11169 that in the GIMPLE IL. */
11170 if (TREE_OVERFLOW_P (*expr_p))
11171 *expr_p = drop_tree_overflow (*expr_p);
11172 ret = GS_ALL_DONE;
11173 break;
11175 case CONST_DECL:
11176 /* If we require an lvalue, such as for ADDR_EXPR, retain the
11177 CONST_DECL node. Otherwise the decl is replaceable by its
11178 value. */
11179 /* ??? Should be == fb_lvalue, but ADDR_EXPR passes fb_either. */
11180 if (fallback & fb_lvalue)
11181 ret = GS_ALL_DONE;
11182 else
11184 *expr_p = DECL_INITIAL (*expr_p);
11185 ret = GS_OK;
11187 break;
11189 case DECL_EXPR:
11190 ret = gimplify_decl_expr (expr_p, pre_p);
11191 break;
11193 case BIND_EXPR:
11194 ret = gimplify_bind_expr (expr_p, pre_p);
11195 break;
11197 case LOOP_EXPR:
11198 ret = gimplify_loop_expr (expr_p, pre_p);
11199 break;
11201 case SWITCH_EXPR:
11202 ret = gimplify_switch_expr (expr_p, pre_p);
11203 break;
11205 case EXIT_EXPR:
11206 ret = gimplify_exit_expr (expr_p);
11207 break;
11209 case GOTO_EXPR:
11210 /* If the target is not LABEL, then it is a computed jump
11211 and the target needs to be gimplified. */
11212 if (TREE_CODE (GOTO_DESTINATION (*expr_p)) != LABEL_DECL)
11214 ret = gimplify_expr (&GOTO_DESTINATION (*expr_p), pre_p,
11215 NULL, is_gimple_val, fb_rvalue);
11216 if (ret == GS_ERROR)
11217 break;
11219 gimplify_seq_add_stmt (pre_p,
11220 gimple_build_goto (GOTO_DESTINATION (*expr_p)));
11221 ret = GS_ALL_DONE;
11222 break;
11224 case PREDICT_EXPR:
11225 gimplify_seq_add_stmt (pre_p,
11226 gimple_build_predict (PREDICT_EXPR_PREDICTOR (*expr_p),
11227 PREDICT_EXPR_OUTCOME (*expr_p)));
11228 ret = GS_ALL_DONE;
11229 break;
11231 case LABEL_EXPR:
11232 ret = gimplify_label_expr (expr_p, pre_p);
11233 break;
11235 case CASE_LABEL_EXPR:
11236 ret = gimplify_case_label_expr (expr_p, pre_p);
11237 break;
11239 case RETURN_EXPR:
11240 ret = gimplify_return_expr (*expr_p, pre_p);
11241 break;
11243 case CONSTRUCTOR:
11244 /* Don't reduce this in place; let gimplify_init_constructor work its
11245 magic. Buf if we're just elaborating this for side effects, just
11246 gimplify any element that has side-effects. */
11247 if (fallback == fb_none)
11249 unsigned HOST_WIDE_INT ix;
11250 tree val;
11251 tree temp = NULL_TREE;
11252 FOR_EACH_CONSTRUCTOR_VALUE (CONSTRUCTOR_ELTS (*expr_p), ix, val)
11253 if (TREE_SIDE_EFFECTS (val))
11254 append_to_statement_list (val, &temp);
11256 *expr_p = temp;
11257 ret = temp ? GS_OK : GS_ALL_DONE;
11259 /* C99 code may assign to an array in a constructed
11260 structure or union, and this has undefined behavior only
11261 on execution, so create a temporary if an lvalue is
11262 required. */
11263 else if (fallback == fb_lvalue)
11265 *expr_p = get_initialized_tmp_var (*expr_p, pre_p, post_p, false);
11266 mark_addressable (*expr_p);
11267 ret = GS_OK;
11269 else
11270 ret = GS_ALL_DONE;
11271 break;
11273 /* The following are special cases that are not handled by the
11274 original GIMPLE grammar. */
11276 /* SAVE_EXPR nodes are converted into a GIMPLE identifier and
11277 eliminated. */
11278 case SAVE_EXPR:
11279 ret = gimplify_save_expr (expr_p, pre_p, post_p);
11280 break;
11282 case BIT_FIELD_REF:
11283 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
11284 post_p, is_gimple_lvalue, fb_either);
11285 recalculate_side_effects (*expr_p);
11286 break;
11288 case TARGET_MEM_REF:
11290 enum gimplify_status r0 = GS_ALL_DONE, r1 = GS_ALL_DONE;
11292 if (TMR_BASE (*expr_p))
11293 r0 = gimplify_expr (&TMR_BASE (*expr_p), pre_p,
11294 post_p, is_gimple_mem_ref_addr, fb_either);
11295 if (TMR_INDEX (*expr_p))
11296 r1 = gimplify_expr (&TMR_INDEX (*expr_p), pre_p,
11297 post_p, is_gimple_val, fb_rvalue);
11298 if (TMR_INDEX2 (*expr_p))
11299 r1 = gimplify_expr (&TMR_INDEX2 (*expr_p), pre_p,
11300 post_p, is_gimple_val, fb_rvalue);
11301 /* TMR_STEP and TMR_OFFSET are always integer constants. */
11302 ret = MIN (r0, r1);
11304 break;
11306 case NON_LVALUE_EXPR:
11307 /* This should have been stripped above. */
11308 gcc_unreachable ();
11310 case ASM_EXPR:
11311 ret = gimplify_asm_expr (expr_p, pre_p, post_p);
11312 break;
11314 case TRY_FINALLY_EXPR:
11315 case TRY_CATCH_EXPR:
11317 gimple_seq eval, cleanup;
11318 gtry *try_;
11320 /* Calls to destructors are generated automatically in FINALLY/CATCH
11321 block. They should have location as UNKNOWN_LOCATION. However,
11322 gimplify_call_expr will reset these call stmts to input_location
11323 if it finds stmt's location is unknown. To prevent resetting for
11324 destructors, we set the input_location to unknown.
11325 Note that this only affects the destructor calls in FINALLY/CATCH
11326 block, and will automatically reset to its original value by the
11327 end of gimplify_expr. */
11328 input_location = UNKNOWN_LOCATION;
11329 eval = cleanup = NULL;
11330 gimplify_and_add (TREE_OPERAND (*expr_p, 0), &eval);
11331 gimplify_and_add (TREE_OPERAND (*expr_p, 1), &cleanup);
11332 /* Don't create bogus GIMPLE_TRY with empty cleanup. */
11333 if (gimple_seq_empty_p (cleanup))
11335 gimple_seq_add_seq (pre_p, eval);
11336 ret = GS_ALL_DONE;
11337 break;
11339 try_ = gimple_build_try (eval, cleanup,
11340 TREE_CODE (*expr_p) == TRY_FINALLY_EXPR
11341 ? GIMPLE_TRY_FINALLY
11342 : GIMPLE_TRY_CATCH);
11343 if (EXPR_HAS_LOCATION (save_expr))
11344 gimple_set_location (try_, EXPR_LOCATION (save_expr));
11345 else if (LOCATION_LOCUS (saved_location) != UNKNOWN_LOCATION)
11346 gimple_set_location (try_, saved_location);
11347 if (TREE_CODE (*expr_p) == TRY_CATCH_EXPR)
11348 gimple_try_set_catch_is_cleanup (try_,
11349 TRY_CATCH_IS_CLEANUP (*expr_p));
11350 gimplify_seq_add_stmt (pre_p, try_);
11351 ret = GS_ALL_DONE;
11352 break;
11355 case CLEANUP_POINT_EXPR:
11356 ret = gimplify_cleanup_point_expr (expr_p, pre_p);
11357 break;
11359 case TARGET_EXPR:
11360 ret = gimplify_target_expr (expr_p, pre_p, post_p);
11361 break;
11363 case CATCH_EXPR:
11365 gimple *c;
11366 gimple_seq handler = NULL;
11367 gimplify_and_add (CATCH_BODY (*expr_p), &handler);
11368 c = gimple_build_catch (CATCH_TYPES (*expr_p), handler);
11369 gimplify_seq_add_stmt (pre_p, c);
11370 ret = GS_ALL_DONE;
11371 break;
11374 case EH_FILTER_EXPR:
11376 gimple *ehf;
11377 gimple_seq failure = NULL;
11379 gimplify_and_add (EH_FILTER_FAILURE (*expr_p), &failure);
11380 ehf = gimple_build_eh_filter (EH_FILTER_TYPES (*expr_p), failure);
11381 gimple_set_no_warning (ehf, TREE_NO_WARNING (*expr_p));
11382 gimplify_seq_add_stmt (pre_p, ehf);
11383 ret = GS_ALL_DONE;
11384 break;
11387 case OBJ_TYPE_REF:
11389 enum gimplify_status r0, r1;
11390 r0 = gimplify_expr (&OBJ_TYPE_REF_OBJECT (*expr_p), pre_p,
11391 post_p, is_gimple_val, fb_rvalue);
11392 r1 = gimplify_expr (&OBJ_TYPE_REF_EXPR (*expr_p), pre_p,
11393 post_p, is_gimple_val, fb_rvalue);
11394 TREE_SIDE_EFFECTS (*expr_p) = 0;
11395 ret = MIN (r0, r1);
11397 break;
11399 case LABEL_DECL:
11400 /* We get here when taking the address of a label. We mark
11401 the label as "forced"; meaning it can never be removed and
11402 it is a potential target for any computed goto. */
11403 FORCED_LABEL (*expr_p) = 1;
11404 ret = GS_ALL_DONE;
11405 break;
11407 case STATEMENT_LIST:
11408 ret = gimplify_statement_list (expr_p, pre_p);
11409 break;
11411 case WITH_SIZE_EXPR:
11413 gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
11414 post_p == &internal_post ? NULL : post_p,
11415 gimple_test_f, fallback);
11416 gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p, post_p,
11417 is_gimple_val, fb_rvalue);
11418 ret = GS_ALL_DONE;
11420 break;
11422 case VAR_DECL:
11423 case PARM_DECL:
11424 ret = gimplify_var_or_parm_decl (expr_p);
11425 break;
11427 case RESULT_DECL:
11428 /* When within an OMP context, notice uses of variables. */
11429 if (gimplify_omp_ctxp)
11430 omp_notice_variable (gimplify_omp_ctxp, *expr_p, true);
11431 ret = GS_ALL_DONE;
11432 break;
11434 case SSA_NAME:
11435 /* Allow callbacks into the gimplifier during optimization. */
11436 ret = GS_ALL_DONE;
11437 break;
11439 case OMP_PARALLEL:
11440 gimplify_omp_parallel (expr_p, pre_p);
11441 ret = GS_ALL_DONE;
11442 break;
11444 case OMP_TASK:
11445 gimplify_omp_task (expr_p, pre_p);
11446 ret = GS_ALL_DONE;
11447 break;
11449 case OMP_FOR:
11450 case OMP_SIMD:
11451 case CILK_SIMD:
11452 case CILK_FOR:
11453 case OMP_DISTRIBUTE:
11454 case OMP_TASKLOOP:
11455 case OACC_LOOP:
11456 ret = gimplify_omp_for (expr_p, pre_p);
11457 break;
11459 case OACC_CACHE:
11460 gimplify_oacc_cache (expr_p, pre_p);
11461 ret = GS_ALL_DONE;
11462 break;
11464 case OACC_DECLARE:
11465 gimplify_oacc_declare (expr_p, pre_p);
11466 ret = GS_ALL_DONE;
11467 break;
11469 case OACC_HOST_DATA:
11470 case OACC_DATA:
11471 case OACC_KERNELS:
11472 case OACC_PARALLEL:
11473 case OMP_SECTIONS:
11474 case OMP_SINGLE:
11475 case OMP_TARGET:
11476 case OMP_TARGET_DATA:
11477 case OMP_TEAMS:
11478 gimplify_omp_workshare (expr_p, pre_p);
11479 ret = GS_ALL_DONE;
11480 break;
11482 case OACC_ENTER_DATA:
11483 case OACC_EXIT_DATA:
11484 case OACC_UPDATE:
11485 case OMP_TARGET_UPDATE:
11486 case OMP_TARGET_ENTER_DATA:
11487 case OMP_TARGET_EXIT_DATA:
11488 gimplify_omp_target_update (expr_p, pre_p);
11489 ret = GS_ALL_DONE;
11490 break;
11492 case OMP_SECTION:
11493 case OMP_MASTER:
11494 case OMP_TASKGROUP:
11495 case OMP_ORDERED:
11496 case OMP_CRITICAL:
11498 gimple_seq body = NULL;
11499 gimple *g;
11501 gimplify_and_add (OMP_BODY (*expr_p), &body);
11502 switch (TREE_CODE (*expr_p))
11504 case OMP_SECTION:
11505 g = gimple_build_omp_section (body);
11506 break;
11507 case OMP_MASTER:
11508 g = gimple_build_omp_master (body);
11509 break;
11510 case OMP_TASKGROUP:
11512 gimple_seq cleanup = NULL;
11513 tree fn
11514 = builtin_decl_explicit (BUILT_IN_GOMP_TASKGROUP_END);
11515 g = gimple_build_call (fn, 0);
11516 gimple_seq_add_stmt (&cleanup, g);
11517 g = gimple_build_try (body, cleanup, GIMPLE_TRY_FINALLY);
11518 body = NULL;
11519 gimple_seq_add_stmt (&body, g);
11520 g = gimple_build_omp_taskgroup (body);
11522 break;
11523 case OMP_ORDERED:
11524 g = gimplify_omp_ordered (*expr_p, body);
11525 break;
11526 case OMP_CRITICAL:
11527 gimplify_scan_omp_clauses (&OMP_CRITICAL_CLAUSES (*expr_p),
11528 pre_p, ORT_WORKSHARE, OMP_CRITICAL);
11529 gimplify_adjust_omp_clauses (pre_p, body,
11530 &OMP_CRITICAL_CLAUSES (*expr_p),
11531 OMP_CRITICAL);
11532 g = gimple_build_omp_critical (body,
11533 OMP_CRITICAL_NAME (*expr_p),
11534 OMP_CRITICAL_CLAUSES (*expr_p));
11535 break;
11536 default:
11537 gcc_unreachable ();
11539 gimplify_seq_add_stmt (pre_p, g);
11540 ret = GS_ALL_DONE;
11541 break;
11544 case OMP_ATOMIC:
11545 case OMP_ATOMIC_READ:
11546 case OMP_ATOMIC_CAPTURE_OLD:
11547 case OMP_ATOMIC_CAPTURE_NEW:
11548 ret = gimplify_omp_atomic (expr_p, pre_p);
11549 break;
11551 case TRANSACTION_EXPR:
11552 ret = gimplify_transaction (expr_p, pre_p);
11553 break;
11555 case TRUTH_AND_EXPR:
11556 case TRUTH_OR_EXPR:
11557 case TRUTH_XOR_EXPR:
11559 tree orig_type = TREE_TYPE (*expr_p);
11560 tree new_type, xop0, xop1;
11561 *expr_p = gimple_boolify (*expr_p);
11562 new_type = TREE_TYPE (*expr_p);
11563 if (!useless_type_conversion_p (orig_type, new_type))
11565 *expr_p = fold_convert_loc (input_location, orig_type, *expr_p);
11566 ret = GS_OK;
11567 break;
11570 /* Boolified binary truth expressions are semantically equivalent
11571 to bitwise binary expressions. Canonicalize them to the
11572 bitwise variant. */
11573 switch (TREE_CODE (*expr_p))
11575 case TRUTH_AND_EXPR:
11576 TREE_SET_CODE (*expr_p, BIT_AND_EXPR);
11577 break;
11578 case TRUTH_OR_EXPR:
11579 TREE_SET_CODE (*expr_p, BIT_IOR_EXPR);
11580 break;
11581 case TRUTH_XOR_EXPR:
11582 TREE_SET_CODE (*expr_p, BIT_XOR_EXPR);
11583 break;
11584 default:
11585 break;
11587 /* Now make sure that operands have compatible type to
11588 expression's new_type. */
11589 xop0 = TREE_OPERAND (*expr_p, 0);
11590 xop1 = TREE_OPERAND (*expr_p, 1);
11591 if (!useless_type_conversion_p (new_type, TREE_TYPE (xop0)))
11592 TREE_OPERAND (*expr_p, 0) = fold_convert_loc (input_location,
11593 new_type,
11594 xop0);
11595 if (!useless_type_conversion_p (new_type, TREE_TYPE (xop1)))
11596 TREE_OPERAND (*expr_p, 1) = fold_convert_loc (input_location,
11597 new_type,
11598 xop1);
11599 /* Continue classified as tcc_binary. */
11600 goto expr_2;
11603 case VEC_COND_EXPR:
11605 enum gimplify_status r0, r1, r2;
11607 r0 = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
11608 post_p, is_gimple_condexpr, fb_rvalue);
11609 r1 = gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p,
11610 post_p, is_gimple_val, fb_rvalue);
11611 r2 = gimplify_expr (&TREE_OPERAND (*expr_p, 2), pre_p,
11612 post_p, is_gimple_val, fb_rvalue);
11614 ret = MIN (MIN (r0, r1), r2);
11615 recalculate_side_effects (*expr_p);
11617 break;
11619 case FMA_EXPR:
11620 case VEC_PERM_EXPR:
11621 /* Classified as tcc_expression. */
11622 goto expr_3;
11624 case BIT_INSERT_EXPR:
11625 /* Argument 3 is a constant. */
11626 goto expr_2;
11628 case POINTER_PLUS_EXPR:
11630 enum gimplify_status r0, r1;
11631 r0 = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
11632 post_p, is_gimple_val, fb_rvalue);
11633 r1 = gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p,
11634 post_p, is_gimple_val, fb_rvalue);
11635 recalculate_side_effects (*expr_p);
11636 ret = MIN (r0, r1);
11637 break;
11640 case CILK_SYNC_STMT:
11642 if (!fn_contains_cilk_spawn_p (cfun))
11644 error_at (EXPR_LOCATION (*expr_p),
11645 "expected %<_Cilk_spawn%> before %<_Cilk_sync%>");
11646 ret = GS_ERROR;
11648 else
11650 gimplify_cilk_sync (expr_p, pre_p);
11651 ret = GS_ALL_DONE;
11653 break;
11656 default:
11657 switch (TREE_CODE_CLASS (TREE_CODE (*expr_p)))
11659 case tcc_comparison:
11660 /* Handle comparison of objects of non scalar mode aggregates
11661 with a call to memcmp. It would be nice to only have to do
11662 this for variable-sized objects, but then we'd have to allow
11663 the same nest of reference nodes we allow for MODIFY_EXPR and
11664 that's too complex.
11666 Compare scalar mode aggregates as scalar mode values. Using
11667 memcmp for them would be very inefficient at best, and is
11668 plain wrong if bitfields are involved. */
11670 tree type = TREE_TYPE (TREE_OPERAND (*expr_p, 1));
11672 /* Vector comparisons need no boolification. */
11673 if (TREE_CODE (type) == VECTOR_TYPE)
11674 goto expr_2;
11675 else if (!AGGREGATE_TYPE_P (type))
11677 tree org_type = TREE_TYPE (*expr_p);
11678 *expr_p = gimple_boolify (*expr_p);
11679 if (!useless_type_conversion_p (org_type,
11680 TREE_TYPE (*expr_p)))
11682 *expr_p = fold_convert_loc (input_location,
11683 org_type, *expr_p);
11684 ret = GS_OK;
11686 else
11687 goto expr_2;
11689 else if (TYPE_MODE (type) != BLKmode)
11690 ret = gimplify_scalar_mode_aggregate_compare (expr_p);
11691 else
11692 ret = gimplify_variable_sized_compare (expr_p);
11694 break;
11697 /* If *EXPR_P does not need to be special-cased, handle it
11698 according to its class. */
11699 case tcc_unary:
11700 ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
11701 post_p, is_gimple_val, fb_rvalue);
11702 break;
11704 case tcc_binary:
11705 expr_2:
11707 enum gimplify_status r0, r1;
11709 r0 = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
11710 post_p, is_gimple_val, fb_rvalue);
11711 r1 = gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p,
11712 post_p, is_gimple_val, fb_rvalue);
11714 ret = MIN (r0, r1);
11715 break;
11718 expr_3:
11720 enum gimplify_status r0, r1, r2;
11722 r0 = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
11723 post_p, is_gimple_val, fb_rvalue);
11724 r1 = gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p,
11725 post_p, is_gimple_val, fb_rvalue);
11726 r2 = gimplify_expr (&TREE_OPERAND (*expr_p, 2), pre_p,
11727 post_p, is_gimple_val, fb_rvalue);
11729 ret = MIN (MIN (r0, r1), r2);
11730 break;
11733 case tcc_declaration:
11734 case tcc_constant:
11735 ret = GS_ALL_DONE;
11736 goto dont_recalculate;
11738 default:
11739 gcc_unreachable ();
11742 recalculate_side_effects (*expr_p);
11744 dont_recalculate:
11745 break;
11748 gcc_assert (*expr_p || ret != GS_OK);
11750 while (ret == GS_OK);
11752 /* If we encountered an error_mark somewhere nested inside, either
11753 stub out the statement or propagate the error back out. */
11754 if (ret == GS_ERROR)
11756 if (is_statement)
11757 *expr_p = NULL;
11758 goto out;
11761 /* This was only valid as a return value from the langhook, which
11762 we handled. Make sure it doesn't escape from any other context. */
11763 gcc_assert (ret != GS_UNHANDLED);
11765 if (fallback == fb_none && *expr_p && !is_gimple_stmt (*expr_p))
11767 /* We aren't looking for a value, and we don't have a valid
11768 statement. If it doesn't have side-effects, throw it away. */
11769 if (!TREE_SIDE_EFFECTS (*expr_p))
11770 *expr_p = NULL;
11771 else if (!TREE_THIS_VOLATILE (*expr_p))
11773 /* This is probably a _REF that contains something nested that
11774 has side effects. Recurse through the operands to find it. */
11775 enum tree_code code = TREE_CODE (*expr_p);
11777 switch (code)
11779 case COMPONENT_REF:
11780 case REALPART_EXPR:
11781 case IMAGPART_EXPR:
11782 case VIEW_CONVERT_EXPR:
11783 gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
11784 gimple_test_f, fallback);
11785 break;
11787 case ARRAY_REF:
11788 case ARRAY_RANGE_REF:
11789 gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
11790 gimple_test_f, fallback);
11791 gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p, post_p,
11792 gimple_test_f, fallback);
11793 break;
11795 default:
11796 /* Anything else with side-effects must be converted to
11797 a valid statement before we get here. */
11798 gcc_unreachable ();
11801 *expr_p = NULL;
11803 else if (COMPLETE_TYPE_P (TREE_TYPE (*expr_p))
11804 && TYPE_MODE (TREE_TYPE (*expr_p)) != BLKmode)
11806 /* Historically, the compiler has treated a bare reference
11807 to a non-BLKmode volatile lvalue as forcing a load. */
11808 tree type = TYPE_MAIN_VARIANT (TREE_TYPE (*expr_p));
11810 /* Normally, we do not want to create a temporary for a
11811 TREE_ADDRESSABLE type because such a type should not be
11812 copied by bitwise-assignment. However, we make an
11813 exception here, as all we are doing here is ensuring that
11814 we read the bytes that make up the type. We use
11815 create_tmp_var_raw because create_tmp_var will abort when
11816 given a TREE_ADDRESSABLE type. */
11817 tree tmp = create_tmp_var_raw (type, "vol");
11818 gimple_add_tmp_var (tmp);
11819 gimplify_assign (tmp, *expr_p, pre_p);
11820 *expr_p = NULL;
11822 else
11823 /* We can't do anything useful with a volatile reference to
11824 an incomplete type, so just throw it away. Likewise for
11825 a BLKmode type, since any implicit inner load should
11826 already have been turned into an explicit one by the
11827 gimplification process. */
11828 *expr_p = NULL;
11831 /* If we are gimplifying at the statement level, we're done. Tack
11832 everything together and return. */
11833 if (fallback == fb_none || is_statement)
11835 /* Since *EXPR_P has been converted into a GIMPLE tuple, clear
11836 it out for GC to reclaim it. */
11837 *expr_p = NULL_TREE;
11839 if (!gimple_seq_empty_p (internal_pre)
11840 || !gimple_seq_empty_p (internal_post))
11842 gimplify_seq_add_seq (&internal_pre, internal_post);
11843 gimplify_seq_add_seq (pre_p, internal_pre);
11846 /* The result of gimplifying *EXPR_P is going to be the last few
11847 statements in *PRE_P and *POST_P. Add location information
11848 to all the statements that were added by the gimplification
11849 helpers. */
11850 if (!gimple_seq_empty_p (*pre_p))
11851 annotate_all_with_location_after (*pre_p, pre_last_gsi, input_location);
11853 if (!gimple_seq_empty_p (*post_p))
11854 annotate_all_with_location_after (*post_p, post_last_gsi,
11855 input_location);
11857 goto out;
11860 #ifdef ENABLE_GIMPLE_CHECKING
11861 if (*expr_p)
11863 enum tree_code code = TREE_CODE (*expr_p);
11864 /* These expressions should already be in gimple IR form. */
11865 gcc_assert (code != MODIFY_EXPR
11866 && code != ASM_EXPR
11867 && code != BIND_EXPR
11868 && code != CATCH_EXPR
11869 && (code != COND_EXPR || gimplify_ctxp->allow_rhs_cond_expr)
11870 && code != EH_FILTER_EXPR
11871 && code != GOTO_EXPR
11872 && code != LABEL_EXPR
11873 && code != LOOP_EXPR
11874 && code != SWITCH_EXPR
11875 && code != TRY_FINALLY_EXPR
11876 && code != OACC_PARALLEL
11877 && code != OACC_KERNELS
11878 && code != OACC_DATA
11879 && code != OACC_HOST_DATA
11880 && code != OACC_DECLARE
11881 && code != OACC_UPDATE
11882 && code != OACC_ENTER_DATA
11883 && code != OACC_EXIT_DATA
11884 && code != OACC_CACHE
11885 && code != OMP_CRITICAL
11886 && code != OMP_FOR
11887 && code != OACC_LOOP
11888 && code != OMP_MASTER
11889 && code != OMP_TASKGROUP
11890 && code != OMP_ORDERED
11891 && code != OMP_PARALLEL
11892 && code != OMP_SECTIONS
11893 && code != OMP_SECTION
11894 && code != OMP_SINGLE);
11896 #endif
11898 /* Otherwise we're gimplifying a subexpression, so the resulting
11899 value is interesting. If it's a valid operand that matches
11900 GIMPLE_TEST_F, we're done. Unless we are handling some
11901 post-effects internally; if that's the case, we need to copy into
11902 a temporary before adding the post-effects to POST_P. */
11903 if (gimple_seq_empty_p (internal_post) && (*gimple_test_f) (*expr_p))
11904 goto out;
11906 /* Otherwise, we need to create a new temporary for the gimplified
11907 expression. */
11909 /* We can't return an lvalue if we have an internal postqueue. The
11910 object the lvalue refers to would (probably) be modified by the
11911 postqueue; we need to copy the value out first, which means an
11912 rvalue. */
11913 if ((fallback & fb_lvalue)
11914 && gimple_seq_empty_p (internal_post)
11915 && is_gimple_addressable (*expr_p))
11917 /* An lvalue will do. Take the address of the expression, store it
11918 in a temporary, and replace the expression with an INDIRECT_REF of
11919 that temporary. */
11920 tmp = build_fold_addr_expr_loc (input_location, *expr_p);
11921 gimplify_expr (&tmp, pre_p, post_p, is_gimple_reg, fb_rvalue);
11922 *expr_p = build_simple_mem_ref (tmp);
11924 else if ((fallback & fb_rvalue) && is_gimple_reg_rhs_or_call (*expr_p))
11926 /* An rvalue will do. Assign the gimplified expression into a
11927 new temporary TMP and replace the original expression with
11928 TMP. First, make sure that the expression has a type so that
11929 it can be assigned into a temporary. */
11930 gcc_assert (!VOID_TYPE_P (TREE_TYPE (*expr_p)));
11931 *expr_p = get_formal_tmp_var (*expr_p, pre_p);
11933 else
11935 #ifdef ENABLE_GIMPLE_CHECKING
11936 if (!(fallback & fb_mayfail))
11938 fprintf (stderr, "gimplification failed:\n");
11939 print_generic_expr (stderr, *expr_p, 0);
11940 debug_tree (*expr_p);
11941 internal_error ("gimplification failed");
11943 #endif
11944 gcc_assert (fallback & fb_mayfail);
11946 /* If this is an asm statement, and the user asked for the
11947 impossible, don't die. Fail and let gimplify_asm_expr
11948 issue an error. */
11949 ret = GS_ERROR;
11950 goto out;
11953 /* Make sure the temporary matches our predicate. */
11954 gcc_assert ((*gimple_test_f) (*expr_p));
11956 if (!gimple_seq_empty_p (internal_post))
11958 annotate_all_with_location (internal_post, input_location);
11959 gimplify_seq_add_seq (pre_p, internal_post);
11962 out:
11963 input_location = saved_location;
11964 return ret;
11967 /* Like gimplify_expr but make sure the gimplified result is not itself
11968 a SSA name (but a decl if it were). Temporaries required by
11969 evaluating *EXPR_P may be still SSA names. */
11971 static enum gimplify_status
11972 gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
11973 bool (*gimple_test_f) (tree), fallback_t fallback,
11974 bool allow_ssa)
11976 bool was_ssa_name_p = TREE_CODE (*expr_p) == SSA_NAME;
11977 enum gimplify_status ret = gimplify_expr (expr_p, pre_p, post_p,
11978 gimple_test_f, fallback);
11979 if (! allow_ssa
11980 && TREE_CODE (*expr_p) == SSA_NAME)
11982 tree name = *expr_p;
11983 if (was_ssa_name_p)
11984 *expr_p = get_initialized_tmp_var (*expr_p, pre_p, NULL, false);
11985 else
11987 /* Avoid the extra copy if possible. */
11988 *expr_p = create_tmp_reg (TREE_TYPE (name));
11989 gimple_set_lhs (SSA_NAME_DEF_STMT (name), *expr_p);
11990 release_ssa_name (name);
11993 return ret;
11996 /* Look through TYPE for variable-sized objects and gimplify each such
11997 size that we find. Add to LIST_P any statements generated. */
11999 void
12000 gimplify_type_sizes (tree type, gimple_seq *list_p)
12002 tree field, t;
12004 if (type == NULL || type == error_mark_node)
12005 return;
12007 /* We first do the main variant, then copy into any other variants. */
12008 type = TYPE_MAIN_VARIANT (type);
12010 /* Avoid infinite recursion. */
12011 if (TYPE_SIZES_GIMPLIFIED (type))
12012 return;
12014 TYPE_SIZES_GIMPLIFIED (type) = 1;
12016 switch (TREE_CODE (type))
12018 case INTEGER_TYPE:
12019 case ENUMERAL_TYPE:
12020 case BOOLEAN_TYPE:
12021 case REAL_TYPE:
12022 case FIXED_POINT_TYPE:
12023 gimplify_one_sizepos (&TYPE_MIN_VALUE (type), list_p);
12024 gimplify_one_sizepos (&TYPE_MAX_VALUE (type), list_p);
12026 for (t = TYPE_NEXT_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
12028 TYPE_MIN_VALUE (t) = TYPE_MIN_VALUE (type);
12029 TYPE_MAX_VALUE (t) = TYPE_MAX_VALUE (type);
12031 break;
12033 case ARRAY_TYPE:
12034 /* These types may not have declarations, so handle them here. */
12035 gimplify_type_sizes (TREE_TYPE (type), list_p);
12036 gimplify_type_sizes (TYPE_DOMAIN (type), list_p);
12037 /* Ensure VLA bounds aren't removed, for -O0 they should be variables
12038 with assigned stack slots, for -O1+ -g they should be tracked
12039 by VTA. */
12040 if (!(TYPE_NAME (type)
12041 && TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
12042 && DECL_IGNORED_P (TYPE_NAME (type)))
12043 && TYPE_DOMAIN (type)
12044 && INTEGRAL_TYPE_P (TYPE_DOMAIN (type)))
12046 t = TYPE_MIN_VALUE (TYPE_DOMAIN (type));
12047 if (t && VAR_P (t) && DECL_ARTIFICIAL (t))
12048 DECL_IGNORED_P (t) = 0;
12049 t = TYPE_MAX_VALUE (TYPE_DOMAIN (type));
12050 if (t && VAR_P (t) && DECL_ARTIFICIAL (t))
12051 DECL_IGNORED_P (t) = 0;
12053 break;
12055 case RECORD_TYPE:
12056 case UNION_TYPE:
12057 case QUAL_UNION_TYPE:
12058 for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
12059 if (TREE_CODE (field) == FIELD_DECL)
12061 gimplify_one_sizepos (&DECL_FIELD_OFFSET (field), list_p);
12062 gimplify_one_sizepos (&DECL_SIZE (field), list_p);
12063 gimplify_one_sizepos (&DECL_SIZE_UNIT (field), list_p);
12064 gimplify_type_sizes (TREE_TYPE (field), list_p);
12066 break;
12068 case POINTER_TYPE:
12069 case REFERENCE_TYPE:
12070 /* We used to recurse on the pointed-to type here, which turned out to
12071 be incorrect because its definition might refer to variables not
12072 yet initialized at this point if a forward declaration is involved.
12074 It was actually useful for anonymous pointed-to types to ensure
12075 that the sizes evaluation dominates every possible later use of the
12076 values. Restricting to such types here would be safe since there
12077 is no possible forward declaration around, but would introduce an
12078 undesirable middle-end semantic to anonymity. We then defer to
12079 front-ends the responsibility of ensuring that the sizes are
12080 evaluated both early and late enough, e.g. by attaching artificial
12081 type declarations to the tree. */
12082 break;
12084 default:
12085 break;
12088 gimplify_one_sizepos (&TYPE_SIZE (type), list_p);
12089 gimplify_one_sizepos (&TYPE_SIZE_UNIT (type), list_p);
12091 for (t = TYPE_NEXT_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
12093 TYPE_SIZE (t) = TYPE_SIZE (type);
12094 TYPE_SIZE_UNIT (t) = TYPE_SIZE_UNIT (type);
12095 TYPE_SIZES_GIMPLIFIED (t) = 1;
12099 /* A subroutine of gimplify_type_sizes to make sure that *EXPR_P,
12100 a size or position, has had all of its SAVE_EXPRs evaluated.
12101 We add any required statements to *STMT_P. */
12103 void
12104 gimplify_one_sizepos (tree *expr_p, gimple_seq *stmt_p)
12106 tree expr = *expr_p;
12108 /* We don't do anything if the value isn't there, is constant, or contains
12109 A PLACEHOLDER_EXPR. We also don't want to do anything if it's already
12110 a VAR_DECL. If it's a VAR_DECL from another function, the gimplifier
12111 will want to replace it with a new variable, but that will cause problems
12112 if this type is from outside the function. It's OK to have that here. */
12113 if (is_gimple_sizepos (expr))
12114 return;
12116 *expr_p = unshare_expr (expr);
12118 /* SSA names in decl/type fields are a bad idea - they'll get reclaimed
12119 if the def vanishes. */
12120 gimplify_expr (expr_p, stmt_p, NULL, is_gimple_val, fb_rvalue, false);
12123 /* Gimplify the body of statements of FNDECL and return a GIMPLE_BIND node
12124 containing the sequence of corresponding GIMPLE statements. If DO_PARMS
12125 is true, also gimplify the parameters. */
12127 gbind *
12128 gimplify_body (tree fndecl, bool do_parms)
12130 location_t saved_location = input_location;
12131 gimple_seq parm_stmts, seq;
12132 gimple *outer_stmt;
12133 gbind *outer_bind;
12134 struct cgraph_node *cgn;
12136 timevar_push (TV_TREE_GIMPLIFY);
12138 init_tree_ssa (cfun);
12140 /* Initialize for optimize_insn_for_s{ize,peed}_p possibly called during
12141 gimplification. */
12142 default_rtl_profile ();
12144 gcc_assert (gimplify_ctxp == NULL);
12145 push_gimplify_context (true);
12147 if (flag_openacc || flag_openmp)
12149 gcc_assert (gimplify_omp_ctxp == NULL);
12150 if (lookup_attribute ("omp declare target", DECL_ATTRIBUTES (fndecl)))
12151 gimplify_omp_ctxp = new_omp_context (ORT_TARGET);
12154 /* Unshare most shared trees in the body and in that of any nested functions.
12155 It would seem we don't have to do this for nested functions because
12156 they are supposed to be output and then the outer function gimplified
12157 first, but the g++ front end doesn't always do it that way. */
12158 unshare_body (fndecl);
12159 unvisit_body (fndecl);
12161 cgn = cgraph_node::get (fndecl);
12162 if (cgn && cgn->origin)
12163 nonlocal_vlas = new hash_set<tree>;
12165 /* Make sure input_location isn't set to something weird. */
12166 input_location = DECL_SOURCE_LOCATION (fndecl);
12168 /* Resolve callee-copies. This has to be done before processing
12169 the body so that DECL_VALUE_EXPR gets processed correctly. */
12170 parm_stmts = do_parms ? gimplify_parameters () : NULL;
12172 /* Gimplify the function's body. */
12173 seq = NULL;
12174 gimplify_stmt (&DECL_SAVED_TREE (fndecl), &seq);
12175 outer_stmt = gimple_seq_first_stmt (seq);
12176 if (!outer_stmt)
12178 outer_stmt = gimple_build_nop ();
12179 gimplify_seq_add_stmt (&seq, outer_stmt);
12182 /* The body must contain exactly one statement, a GIMPLE_BIND. If this is
12183 not the case, wrap everything in a GIMPLE_BIND to make it so. */
12184 if (gimple_code (outer_stmt) == GIMPLE_BIND
12185 && gimple_seq_first (seq) == gimple_seq_last (seq))
12186 outer_bind = as_a <gbind *> (outer_stmt);
12187 else
12188 outer_bind = gimple_build_bind (NULL_TREE, seq, NULL);
12190 DECL_SAVED_TREE (fndecl) = NULL_TREE;
12192 /* If we had callee-copies statements, insert them at the beginning
12193 of the function and clear DECL_VALUE_EXPR_P on the parameters. */
12194 if (!gimple_seq_empty_p (parm_stmts))
12196 tree parm;
12198 gimplify_seq_add_seq (&parm_stmts, gimple_bind_body (outer_bind));
12199 gimple_bind_set_body (outer_bind, parm_stmts);
12201 for (parm = DECL_ARGUMENTS (current_function_decl);
12202 parm; parm = DECL_CHAIN (parm))
12203 if (DECL_HAS_VALUE_EXPR_P (parm))
12205 DECL_HAS_VALUE_EXPR_P (parm) = 0;
12206 DECL_IGNORED_P (parm) = 0;
12210 if (nonlocal_vlas)
12212 if (nonlocal_vla_vars)
12214 /* tree-nested.c may later on call declare_vars (..., true);
12215 which relies on BLOCK_VARS chain to be the tail of the
12216 gimple_bind_vars chain. Ensure we don't violate that
12217 assumption. */
12218 if (gimple_bind_block (outer_bind)
12219 == DECL_INITIAL (current_function_decl))
12220 declare_vars (nonlocal_vla_vars, outer_bind, true);
12221 else
12222 BLOCK_VARS (DECL_INITIAL (current_function_decl))
12223 = chainon (BLOCK_VARS (DECL_INITIAL (current_function_decl)),
12224 nonlocal_vla_vars);
12225 nonlocal_vla_vars = NULL_TREE;
12227 delete nonlocal_vlas;
12228 nonlocal_vlas = NULL;
12231 if ((flag_openacc || flag_openmp || flag_openmp_simd)
12232 && gimplify_omp_ctxp)
12234 delete_omp_context (gimplify_omp_ctxp);
12235 gimplify_omp_ctxp = NULL;
12238 pop_gimplify_context (outer_bind);
12239 gcc_assert (gimplify_ctxp == NULL);
12241 if (flag_checking && !seen_error ())
12242 verify_gimple_in_seq (gimple_bind_body (outer_bind));
12244 timevar_pop (TV_TREE_GIMPLIFY);
12245 input_location = saved_location;
12247 return outer_bind;
12250 typedef char *char_p; /* For DEF_VEC_P. */
12252 /* Return whether we should exclude FNDECL from instrumentation. */
12254 static bool
12255 flag_instrument_functions_exclude_p (tree fndecl)
12257 vec<char_p> *v;
12259 v = (vec<char_p> *) flag_instrument_functions_exclude_functions;
12260 if (v && v->length () > 0)
12262 const char *name;
12263 int i;
12264 char *s;
12266 name = lang_hooks.decl_printable_name (fndecl, 0);
12267 FOR_EACH_VEC_ELT (*v, i, s)
12268 if (strstr (name, s) != NULL)
12269 return true;
12272 v = (vec<char_p> *) flag_instrument_functions_exclude_files;
12273 if (v && v->length () > 0)
12275 const char *name;
12276 int i;
12277 char *s;
12279 name = DECL_SOURCE_FILE (fndecl);
12280 FOR_EACH_VEC_ELT (*v, i, s)
12281 if (strstr (name, s) != NULL)
12282 return true;
12285 return false;
12288 /* Entry point to the gimplification pass. FNDECL is the FUNCTION_DECL
12289 node for the function we want to gimplify.
12291 Return the sequence of GIMPLE statements corresponding to the body
12292 of FNDECL. */
12294 void
12295 gimplify_function_tree (tree fndecl)
12297 tree parm, ret;
12298 gimple_seq seq;
12299 gbind *bind;
12301 gcc_assert (!gimple_body (fndecl));
12303 if (DECL_STRUCT_FUNCTION (fndecl))
12304 push_cfun (DECL_STRUCT_FUNCTION (fndecl));
12305 else
12306 push_struct_function (fndecl);
12308 /* Tentatively set PROP_gimple_lva here, and reset it in gimplify_va_arg_expr
12309 if necessary. */
12310 cfun->curr_properties |= PROP_gimple_lva;
12312 for (parm = DECL_ARGUMENTS (fndecl); parm ; parm = DECL_CHAIN (parm))
12314 /* Preliminarily mark non-addressed complex variables as eligible
12315 for promotion to gimple registers. We'll transform their uses
12316 as we find them. */
12317 if ((TREE_CODE (TREE_TYPE (parm)) == COMPLEX_TYPE
12318 || TREE_CODE (TREE_TYPE (parm)) == VECTOR_TYPE)
12319 && !TREE_THIS_VOLATILE (parm)
12320 && !needs_to_live_in_memory (parm))
12321 DECL_GIMPLE_REG_P (parm) = 1;
12324 ret = DECL_RESULT (fndecl);
12325 if ((TREE_CODE (TREE_TYPE (ret)) == COMPLEX_TYPE
12326 || TREE_CODE (TREE_TYPE (ret)) == VECTOR_TYPE)
12327 && !needs_to_live_in_memory (ret))
12328 DECL_GIMPLE_REG_P (ret) = 1;
12330 bind = gimplify_body (fndecl, true);
12332 /* The tree body of the function is no longer needed, replace it
12333 with the new GIMPLE body. */
12334 seq = NULL;
12335 gimple_seq_add_stmt (&seq, bind);
12336 gimple_set_body (fndecl, seq);
12338 /* If we're instrumenting function entry/exit, then prepend the call to
12339 the entry hook and wrap the whole function in a TRY_FINALLY_EXPR to
12340 catch the exit hook. */
12341 /* ??? Add some way to ignore exceptions for this TFE. */
12342 if (flag_instrument_function_entry_exit
12343 && !DECL_NO_INSTRUMENT_FUNCTION_ENTRY_EXIT (fndecl)
12344 && !flag_instrument_functions_exclude_p (fndecl))
12346 tree x;
12347 gbind *new_bind;
12348 gimple *tf;
12349 gimple_seq cleanup = NULL, body = NULL;
12350 tree tmp_var;
12351 gcall *call;
12353 x = builtin_decl_implicit (BUILT_IN_RETURN_ADDRESS);
12354 call = gimple_build_call (x, 1, integer_zero_node);
12355 tmp_var = create_tmp_var (ptr_type_node, "return_addr");
12356 gimple_call_set_lhs (call, tmp_var);
12357 gimplify_seq_add_stmt (&cleanup, call);
12358 x = builtin_decl_implicit (BUILT_IN_PROFILE_FUNC_EXIT);
12359 call = gimple_build_call (x, 2,
12360 build_fold_addr_expr (current_function_decl),
12361 tmp_var);
12362 gimplify_seq_add_stmt (&cleanup, call);
12363 tf = gimple_build_try (seq, cleanup, GIMPLE_TRY_FINALLY);
12365 x = builtin_decl_implicit (BUILT_IN_RETURN_ADDRESS);
12366 call = gimple_build_call (x, 1, integer_zero_node);
12367 tmp_var = create_tmp_var (ptr_type_node, "return_addr");
12368 gimple_call_set_lhs (call, tmp_var);
12369 gimplify_seq_add_stmt (&body, call);
12370 x = builtin_decl_implicit (BUILT_IN_PROFILE_FUNC_ENTER);
12371 call = gimple_build_call (x, 2,
12372 build_fold_addr_expr (current_function_decl),
12373 tmp_var);
12374 gimplify_seq_add_stmt (&body, call);
12375 gimplify_seq_add_stmt (&body, tf);
12376 new_bind = gimple_build_bind (NULL, body, NULL);
12378 /* Replace the current function body with the body
12379 wrapped in the try/finally TF. */
12380 seq = NULL;
12381 gimple_seq_add_stmt (&seq, new_bind);
12382 gimple_set_body (fndecl, seq);
12383 bind = new_bind;
12386 if ((flag_sanitize & SANITIZE_THREAD) != 0
12387 && !lookup_attribute ("no_sanitize_thread", DECL_ATTRIBUTES (fndecl)))
12389 gcall *call = gimple_build_call_internal (IFN_TSAN_FUNC_EXIT, 0);
12390 gimple *tf = gimple_build_try (seq, call, GIMPLE_TRY_FINALLY);
12391 gbind *new_bind = gimple_build_bind (NULL, tf, NULL);
12392 /* Replace the current function body with the body
12393 wrapped in the try/finally TF. */
12394 seq = NULL;
12395 gimple_seq_add_stmt (&seq, new_bind);
12396 gimple_set_body (fndecl, seq);
12399 DECL_SAVED_TREE (fndecl) = NULL_TREE;
12400 cfun->curr_properties |= PROP_gimple_any;
12402 pop_cfun ();
12404 dump_function (TDI_generic, fndecl);
12407 /* Return a dummy expression of type TYPE in order to keep going after an
12408 error. */
12410 static tree
12411 dummy_object (tree type)
12413 tree t = build_int_cst (build_pointer_type (type), 0);
12414 return build2 (MEM_REF, type, t, t);
12417 /* Gimplify __builtin_va_arg, aka VA_ARG_EXPR, which is not really a
12418 builtin function, but a very special sort of operator. */
12420 enum gimplify_status
12421 gimplify_va_arg_expr (tree *expr_p, gimple_seq *pre_p,
12422 gimple_seq *post_p ATTRIBUTE_UNUSED)
12424 tree promoted_type, have_va_type;
12425 tree valist = TREE_OPERAND (*expr_p, 0);
12426 tree type = TREE_TYPE (*expr_p);
12427 tree t, tag, aptag;
12428 location_t loc = EXPR_LOCATION (*expr_p);
12430 /* Verify that valist is of the proper type. */
12431 have_va_type = TREE_TYPE (valist);
12432 if (have_va_type == error_mark_node)
12433 return GS_ERROR;
12434 have_va_type = targetm.canonical_va_list_type (have_va_type);
12435 if (have_va_type == NULL_TREE
12436 && TREE_CODE (valist) == ADDR_EXPR)
12437 /* Handle 'Case 1: Not an array type' from c-common.c/build_va_arg. */
12438 have_va_type
12439 = targetm.canonical_va_list_type (TREE_TYPE (TREE_TYPE (valist)));
12440 gcc_assert (have_va_type != NULL_TREE);
12442 /* Generate a diagnostic for requesting data of a type that cannot
12443 be passed through `...' due to type promotion at the call site. */
12444 if ((promoted_type = lang_hooks.types.type_promotes_to (type))
12445 != type)
12447 static bool gave_help;
12448 bool warned;
12449 /* Use the expansion point to handle cases such as passing bool (defined
12450 in a system header) through `...'. */
12451 source_location xloc
12452 = expansion_point_location_if_in_system_header (loc);
12454 /* Unfortunately, this is merely undefined, rather than a constraint
12455 violation, so we cannot make this an error. If this call is never
12456 executed, the program is still strictly conforming. */
12457 warned = warning_at (xloc, 0,
12458 "%qT is promoted to %qT when passed through %<...%>",
12459 type, promoted_type);
12460 if (!gave_help && warned)
12462 gave_help = true;
12463 inform (xloc, "(so you should pass %qT not %qT to %<va_arg%>)",
12464 promoted_type, type);
12467 /* We can, however, treat "undefined" any way we please.
12468 Call abort to encourage the user to fix the program. */
12469 if (warned)
12470 inform (xloc, "if this code is reached, the program will abort");
12471 /* Before the abort, allow the evaluation of the va_list
12472 expression to exit or longjmp. */
12473 gimplify_and_add (valist, pre_p);
12474 t = build_call_expr_loc (loc,
12475 builtin_decl_implicit (BUILT_IN_TRAP), 0);
12476 gimplify_and_add (t, pre_p);
12478 /* This is dead code, but go ahead and finish so that the
12479 mode of the result comes out right. */
12480 *expr_p = dummy_object (type);
12481 return GS_ALL_DONE;
12484 tag = build_int_cst (build_pointer_type (type), 0);
12485 aptag = build_int_cst (TREE_TYPE (valist), 0);
12487 *expr_p = build_call_expr_internal_loc (loc, IFN_VA_ARG, type, 3,
12488 valist, tag, aptag);
12490 /* Clear the tentatively set PROP_gimple_lva, to indicate that IFN_VA_ARG
12491 needs to be expanded. */
12492 cfun->curr_properties &= ~PROP_gimple_lva;
12494 return GS_OK;
12497 /* Build a new GIMPLE_ASSIGN tuple and append it to the end of *SEQ_P.
12499 DST/SRC are the destination and source respectively. You can pass
12500 ungimplified trees in DST or SRC, in which case they will be
12501 converted to a gimple operand if necessary.
12503 This function returns the newly created GIMPLE_ASSIGN tuple. */
12505 gimple *
12506 gimplify_assign (tree dst, tree src, gimple_seq *seq_p)
12508 tree t = build2 (MODIFY_EXPR, TREE_TYPE (dst), dst, src);
12509 gimplify_and_add (t, seq_p);
12510 ggc_free (t);
12511 return gimple_seq_last_stmt (*seq_p);
12514 inline hashval_t
12515 gimplify_hasher::hash (const elt_t *p)
12517 tree t = p->val;
12518 return iterative_hash_expr (t, 0);
12521 inline bool
12522 gimplify_hasher::equal (const elt_t *p1, const elt_t *p2)
12524 tree t1 = p1->val;
12525 tree t2 = p2->val;
12526 enum tree_code code = TREE_CODE (t1);
12528 if (TREE_CODE (t2) != code
12529 || TREE_TYPE (t1) != TREE_TYPE (t2))
12530 return false;
12532 if (!operand_equal_p (t1, t2, 0))
12533 return false;
12535 /* Only allow them to compare equal if they also hash equal; otherwise
12536 results are nondeterminate, and we fail bootstrap comparison. */
12537 gcc_checking_assert (hash (p1) == hash (p2));
12539 return true;